createArgForParam function

Expression createArgForParam(
  1. BaseParameterAnnotation annotation,
  2. ServerParam param
)

Implementation

Expression createArgForParam(
  BaseParameterAnnotation annotation,
  ServerParam param,
) {
  var variable = switch (annotation.type) {
    AnnotationType.body => createBodyVar(annotation),
    AnnotationType.query ||
    AnnotationType.queryAll => createQueryVar(annotation, param),
    AnnotationType.cookie => createCookieVar(annotation, param),
    AnnotationType.param => createParamVar(annotation, param),
    AnnotationType.header ||
    AnnotationType.headerAll => createHeaderVar(annotation, param),
    AnnotationType.binds => createBindsVar(annotation, param),
    AnnotationType.data => createDataVar(param),
  };

  if (annotation.type
      case AnnotationType.headerAll || AnnotationType.queryAll) {
    variable = switch (param.type.iterableType) {
      IterableType.list => variable.nullSafeProperty('toList').call([]),
      IterableType.set => variable.nullSafeProperty('toSet').call([]),
      IterableType.iterable => variable,
      null => variable,
    };
  }

  if (annotation case HasPipe(:final pipe?)) {
    return createPipe(
      pipe,
      param: param,
      annotation: annotation,
      access: variable,
    );
  }

  final fromJson = switch (param.annotations.data) {
    true => refer('data'),
    false => createFromJson(param.type, refer('data')),
  };

  if (param.type.isDynamic) {
    return fromJson ?? variable;
  }

  final rawType = switch (param.annotations.data) {
    true => param.type.nonNullName,
    false => getRawType(param.type).replaceAll('?', ''),
  };

  return createSwitchPattern(variable, {
    Block.of([
      declareFinal('data', type: refer(rawType)).code,
      if (rawType.startsWith('Map')) ...[
        const Code('when'),
        refer('data').property('isNotEmpty').code,
      ],
    ]): fromJson ??
        switch (param.type) {
          ServerType(:final iterableType?) => switch (iterableType) {
            IterableType.list => refer('data').property('cast').call([]),
            IterableType.set => refer(
              'data',
            ).property('toSet').call([]).property('cast').call([]),
            IterableType.iterable => refer('data'),
          },
          _ => refer('data'),
        },
    if (param.defaultValue case final defaultValue?)
      const Code('_'): CodeExpression(Code(defaultValue))
    else ...{
      if (param.type.isNullable)
        Block.of([
          literalNull.code,
          if (rawType.startsWith('Map')) ...[
            const Code('||'),
            const Code('Map()'),
          ] else if (rawType.startsWith('List')) ...[
            const Code('||'),
            const Code('List()'),
          ],
        ]): literalNull,
      const Code('_'): createMissingArgumentException(
        key: annotation.name ?? param.name,
        location: annotation.type.location,
      ).thrown,
    },
  });
}