Browse Source

Merge pull request #199 from provokateurin/fix/dynamite

Fix a few dynamite things
pull/200/head
Kate 2 years ago committed by GitHub
parent
commit
b23fe7cb44
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
  1. 29
      packages/dynamite/lib/src/models/schema.dart
  2. 12
      packages/dynamite/lib/src/models/schema.g.dart
  3. 132
      packages/dynamite/lib/src/openapi_builder.dart

29
packages/dynamite/lib/src/models/schema.dart

@ -24,6 +24,8 @@ class Schema {
this.contentSchema,
this.discriminator,
this.pattern,
this.minLength,
this.maxLength,
});
factory Schema.fromJson(final Map<String, dynamic> json) => _$SchemaFromJson(json);
@ -60,7 +62,10 @@ class Schema {
final Schema? items;
final bool? additionalProperties;
@JsonKey(
fromJson: _parseAdditionalProperties,
)
final Schema? additionalProperties;
final String? contentMediaType;
@ -70,5 +75,27 @@ class Schema {
final String? pattern;
final int? minLength;
final int? maxLength;
bool get isContentString => type == 'string' && (contentMediaType?.isNotEmpty ?? false) && contentSchema != null;
}
class EmptySchema extends Schema {}
Schema? _parseAdditionalProperties(final dynamic data) {
if (data == null) {
return null;
}
if (data is bool) {
return data ? EmptySchema() : null;
}
if (data is Map<String, dynamic>) {
return Schema.fromJson(data);
}
throw Exception('Can not parse additionalProperties from $data');
}

12
packages/dynamite/lib/src/models/schema.g.dart

@ -27,7 +27,9 @@ Schema _$SchemaFromJson(Map<String, dynamic> json) {
'contentMediaType',
'contentSchema',
'discriminator',
'pattern'
'pattern',
'minLength',
'maxLength'
],
);
return Schema(
@ -46,13 +48,15 @@ Schema _$SchemaFromJson(Map<String, dynamic> json) {
),
required: (json['required'] as List<dynamic>?)?.map((e) => e as String).toList(),
items: json['items'] == null ? null : Schema.fromJson(json['items'] as Map<String, dynamic>),
additionalProperties: json['additionalProperties'] as bool?,
additionalProperties: _parseAdditionalProperties(json['additionalProperties']),
contentMediaType: json['contentMediaType'] as String?,
contentSchema:
json['contentSchema'] == null ? null : Schema.fromJson(json['contentSchema'] as Map<String, dynamic>),
discriminator:
json['discriminator'] == null ? null : Discriminator.fromJson(json['discriminator'] as Map<String, dynamic>),
pattern: json['pattern'] as String?,
minLength: json['minLength'] as int?,
maxLength: json['maxLength'] as int?,
);
}
@ -78,10 +82,12 @@ Map<String, dynamic> _$SchemaToJson(Schema instance) {
writeNotNull('properties', instance.properties?.map((k, e) => MapEntry(k, e.toJson())));
writeNotNull('required', instance.required);
writeNotNull('items', instance.items?.toJson());
writeNotNull('additionalProperties', instance.additionalProperties);
writeNotNull('additionalProperties', instance.additionalProperties?.toJson());
writeNotNull('contentMediaType', instance.contentMediaType);
writeNotNull('contentSchema', instance.contentSchema?.toJson());
writeNotNull('discriminator', instance.discriminator?.toJson());
writeNotNull('pattern', instance.pattern);
writeNotNull('minLength', instance.minLength);
writeNotNull('maxLength', instance.maxLength);
return val;
}

132
packages/dynamite/lib/src/openapi_builder.dart

@ -582,12 +582,28 @@ class OpenAPIBuilder implements Builder {
parameter.schema!,
);
if (result.name == 'String' && parameter.schema?.pattern != null) {
code.write('''
if (!RegExp(r'${parameter.schema!.pattern!}').hasMatch(${_toDartName(parameter.name)})) {
throw Exception('Invalid value "\$${_toDartName(parameter.name)}" for parameter "${_toDartName(parameter.name)}" with pattern "' r'${parameter.schema!.pattern!}"'); // coverage:ignore-line
if (result.name == 'String') {
if (parameter.schema?.pattern != null) {
code.write('''
if (!RegExp(r'${parameter.schema!.pattern!}').hasMatch(${_toDartName(parameter.name)})) {
throw Exception('Invalid value "\$${_toDartName(parameter.name)}" for parameter "${_toDartName(parameter.name)}" with pattern "' r'${parameter.schema!.pattern!}"'); // coverage:ignore-line
}
''');
}
if (parameter.schema?.minLength != null) {
code.write('''
if (${_toDartName(parameter.name)}.length < ${parameter.schema!.minLength!}) {
throw Exception('Parameter "${_toDartName(parameter.name)}" has to be at least ${parameter.schema!.minLength!} characters long'); // coverage:ignore-line
}
''');
}
if (parameter.schema?.maxLength != null) {
code.write('''
if (${_toDartName(parameter.name)}.length > ${parameter.schema!.maxLength!}) {
throw Exception('Parameter "${_toDartName(parameter.name)}" has to be at most ${parameter.schema!.maxLength!} characters long'); // coverage:ignore-line
}
''');
}
''');
}
final defaultValueCode = parameter.schema?.default_ != null
@ -1082,7 +1098,7 @@ TypeResult resolveObject(
refer('JsonSerializable').call(
[],
{
if (schema.additionalProperties ?? false) ...{
if (schema.additionalProperties != null) ...{
'disallowUnrecognizedKeys': refer('false'),
},
if (extraJsonSerializableValues != null) ...{
@ -1351,7 +1367,7 @@ TypeResult resolveType(
final s = schema.ofs![results.indexOf(result)];
b
..name = fields[result.name]
..type = refer(_makeNullable(result.name, true))
..type = refer(_makeNullable(result.name, !(schema.allOf?.contains(s) ?? false)))
..modifier = FieldModifier.final$
..docs.addAll(_descriptionToDocs(s.description));
},
@ -1374,7 +1390,8 @@ TypeResult resolveType(
(final b) => b
..name = fields[result.name]!
..toThis = true
..named = true,
..named = true
..required = schema.allOf != null,
),
],
]),
@ -1393,48 +1410,54 @@ TypeResult resolveType(
)
..body = Code(
<String>[
for (final result in results) ...[
'${result.name}? ${fields[result.name]!};',
],
for (final result in results) ...[
if (schema.discriminator != null) ...[
"if (data['${schema.discriminator!.propertyName}'] == '${result.name.replaceFirst(state.prefix, '')}'",
if (schema.discriminator!.mapping != null &&
schema.discriminator!.mapping!.isNotEmpty) ...[
for (final key in schema.discriminator!.mapping!.entries
.where(
(final entry) =>
entry.value.endsWith('/${result.name.replaceFirst(state.prefix, '')}'),
)
.map((final entry) => entry.key)) ...[
" || data['${schema.discriminator!.propertyName}'] == '$key'",
if (schema.allOf != null) ...[
'return ${state.prefix}$identifier(',
'data,',
for (final result in results) ...[
'${fields[result.name]!}: ${result.deserialize('data')},',
],
');',
] else ...[
for (final result in results) ...[
'${result.name}? ${fields[result.name]!};',
],
for (final result in results) ...[
if (schema.discriminator != null) ...[
"if (data['${schema.discriminator!.propertyName}'] == '${result.name.replaceFirst(state.prefix, '')}'",
if (schema.discriminator!.mapping != null &&
schema.discriminator!.mapping!.isNotEmpty) ...[
for (final key in schema.discriminator!.mapping!.entries
.where(
(final entry) =>
entry.value.endsWith('/${result.name.replaceFirst(state.prefix, '')}'),
)
.map((final entry) => entry.key)) ...[
" || data['${schema.discriminator!.propertyName}'] == '$key'",
],
],
') {',
],
'try {',
'${fields[result.name]!} = ${result.deserialize('data')};',
'} catch (_) {',
if (schema.discriminator != null) ...[
'rethrow;',
],
'}',
if (schema.discriminator != null) ...[
'}',
],
') {',
],
'try {',
'${fields[result.name]!} = ${result.deserialize('data')};',
'} catch (_) {',
if (schema.discriminator != null) ...[
'rethrow;',
if (schema.oneOf != null) ...[
"assert([${fields.values.join(',')}].where((final x) => x != null).length == 1, 'Need oneOf for \$data');",
],
'}',
if (schema.discriminator != null) ...[
'}',
'return ${state.prefix}$identifier(',
'data,',
for (final result in results) ...[
'${fields[result.name]!}: ${fields[result.name]!},',
],
');',
],
if (schema.oneOf != null) ...[
"assert([${fields.values.join(',')}].where((final x) => x != null).length == 1, 'Need oneOf for \$data');",
],
if (schema.allOf != null) ...[
"assert([${fields.values.join(',')}].where((final x) => x != null).length == ${fields.length}, 'Need allOf for \$data');",
],
'return ${state.prefix}$identifier(',
'data,',
for (final result in results) ...[
'${fields[result.name]!}: ${fields[result.name]!},',
],
');',
].join(),
);
},
@ -1543,6 +1566,27 @@ TypeResult resolveType(
break;
case 'object':
if (schema.properties == null) {
if (schema.additionalProperties != null) {
if (schema.additionalProperties is EmptySchema) {
result = TypeResultMap(
'Map<String, dynamic>',
TypeResultBase('dynamic'),
);
} else {
final subResult = resolveType(
spec,
state,
identifier,
schema.additionalProperties!,
extraJsonSerializableValues: extraJsonSerializableValues,
);
result = TypeResultMap(
'Map<String, ${subResult.name}>',
TypeResultBase('dynamic'),
);
}
break;
}
result = TypeResultBase('dynamic');
break;
}

Loading…
Cancel
Save