constructor(node, context, upper) {
    this.node = node
    this.context = context
    /** Upper scope component */
    this.upper = upper

    /** @type {Map<string, boolean>} */
    const maybeFunctions = new Map()
    /** @type {FunctionData[]} */
    const functions = []

    // Extract properties
    for (const property of utils.iterateProperties(node, GROUPS)) {
      if (property.type === 'array') {
        continue
      }
      switch (property.groupName) {
        case 'data': {
          maybeFunctions.set(
            property.name,
            maybeFunction(context, property.property.value)
          )
          break
        }
        case 'props': {
          const types = getComponentPropsTypes(context, property)
          maybeFunctions.set(
            property.name,
            !types || types.some((type) => !NATIVE_NOT_FUNCTION_TYPES.has(type))
          )
          break
        }
        case 'computed': {
          let value = property.property.value
          if (value.type === 'ObjectExpression') {
            const getProp = utils.findProperty(value, 'get')
            if (getProp) {
              value = getProp.value
            }
          }
          processFunction(property.name, value, 'computed')
          break
        }
        case 'methods': {
          const value = property.property.value
          processFunction(property.name, value, 'methods')
          maybeFunctions.set(property.name, true)
          break
        }
      }
    }
    this.maybeFunctions = maybeFunctions
    this.functions = functions
    /** @type {CallMember[]} */
    this.callMembers = []
    /** @type {Map<Expression, boolean>} */
    this.cacheMaybeFunctionExpressions = new Map()

    /**
     * @param {string} name
     * @param {Expression} value
     * @param {'methods' | 'computed'} kind
     */
    function processFunction(name, value, kind) {
      if (value.type === 'FunctionExpression') {
        functions.push(new FunctionData(name, kind, value, context))
      } else if (value.type === 'ArrowFunctionExpression') {
        const data = new FunctionData(name, kind, value, context)
        if (value.expression) {
          data.addReturnValue(value.body)
        }
        functions.push(data)
      }
    }
  }
@param {ObjectExpression} node
@param {RuleContext} context
@param {ComponentStack | null} upper