diff --git a/packages/dynamite/lib/src/models/discriminator.dart b/packages/dynamite/lib/src/models/discriminator.dart new file mode 100644 index 00000000..5968aeb6 --- /dev/null +++ b/packages/dynamite/lib/src/models/discriminator.dart @@ -0,0 +1,18 @@ +import 'package:json_annotation/json_annotation.dart'; + +part 'discriminator.g.dart'; + +@JsonSerializable() +class Discriminator { + Discriminator({ + required this.propertyName, + this.mapping, + }); + + factory Discriminator.fromJson(final Map json) => _$DiscriminatorFromJson(json); + Map toJson() => _$DiscriminatorToJson(this); + + final String propertyName; + + final Map? mapping; +} diff --git a/packages/dynamite/lib/src/models/discriminator.g.dart b/packages/dynamite/lib/src/models/discriminator.g.dart new file mode 100644 index 00000000..26d90580 --- /dev/null +++ b/packages/dynamite/lib/src/models/discriminator.g.dart @@ -0,0 +1,35 @@ +// GENERATED CODE - DO NOT MODIFY BY HAND + +part of 'discriminator.dart'; + +// ************************************************************************** +// JsonSerializableGenerator +// ************************************************************************** + +Discriminator _$DiscriminatorFromJson(Map json) { + $checkKeys( + json, + allowedKeys: const ['propertyName', 'mapping'], + ); + return Discriminator( + propertyName: json['propertyName'] as String, + mapping: (json['mapping'] as Map?)?.map( + (k, e) => MapEntry(k, e as String), + ), + ); +} + +Map _$DiscriminatorToJson(Discriminator instance) { + final val = { + 'propertyName': instance.propertyName, + }; + + void writeNotNull(String key, dynamic value) { + if (value != null) { + val[key] = value; + } + } + + writeNotNull('mapping', instance.mapping); + return val; +} diff --git a/packages/dynamite/lib/src/models/schema.dart b/packages/dynamite/lib/src/models/schema.dart index fc59f41f..bd424564 100644 --- a/packages/dynamite/lib/src/models/schema.dart +++ b/packages/dynamite/lib/src/models/schema.dart @@ -1,3 +1,4 @@ +import 'package:dynamite/src/models/discriminator.dart'; import 'package:json_annotation/json_annotation.dart'; part 'schema.g.dart'; @@ -21,6 +22,7 @@ class Schema { this.additionalProperties, this.contentMediaType, this.contentSchema, + this.discriminator, }); factory Schema.fromJson(final Map json) => _$SchemaFromJson(json); @@ -63,5 +65,7 @@ class Schema { final Schema? contentSchema; + final Discriminator? discriminator; + bool get isJsonString => type == 'string' && contentMediaType == 'application/json' && contentSchema != null; } diff --git a/packages/dynamite/lib/src/models/schema.g.dart b/packages/dynamite/lib/src/models/schema.g.dart index 1afeb5be..a2e7b0cb 100644 --- a/packages/dynamite/lib/src/models/schema.g.dart +++ b/packages/dynamite/lib/src/models/schema.g.dart @@ -25,7 +25,8 @@ Schema _$SchemaFromJson(Map json) { 'items', 'additionalProperties', 'contentMediaType', - 'contentSchema' + 'contentSchema', + 'discriminator' ], ); return Schema( @@ -48,6 +49,8 @@ Schema _$SchemaFromJson(Map json) { contentMediaType: json['contentMediaType'] as String?, contentSchema: json['contentSchema'] == null ? null : Schema.fromJson(json['contentSchema'] as Map), + discriminator: + json['discriminator'] == null ? null : Discriminator.fromJson(json['discriminator'] as Map), ); } @@ -76,5 +79,6 @@ Map _$SchemaToJson(Schema instance) { writeNotNull('additionalProperties', instance.additionalProperties); writeNotNull('contentMediaType', instance.contentMediaType); writeNotNull('contentSchema', instance.contentSchema?.toJson()); + writeNotNull('discriminator', instance.discriminator?.toJson()); return val; } diff --git a/packages/dynamite/lib/src/openapi_builder.dart b/packages/dynamite/lib/src/openapi_builder.dart index 60674678..9dbf7642 100644 --- a/packages/dynamite/lib/src/openapi_builder.dart +++ b/packages/dynamite/lib/src/openapi_builder.dart @@ -1278,10 +1278,30 @@ TypeResult resolveType( [ 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}'", + 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}')) + .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) ...[ + '}', + ], ], if (schema.oneOf != null) ...[ "assert([${fields.values.join(',')}].where((final x) => x != null).length == 1, 'Need oneOf for \$data');", diff --git a/packages/nextcloud/lib/src/nextcloud.openapi.dart b/packages/nextcloud/lib/src/nextcloud.openapi.dart index 8ebf5bfc..f27fa3ee 100644 --- a/packages/nextcloud/lib/src/nextcloud.openapi.dart +++ b/packages/nextcloud/lib/src/nextcloud.openapi.dart @@ -2814,10 +2814,10 @@ class CoreNavigationApps_Ocs_Data_Order { factory CoreNavigationApps_Ocs_Data_Order.fromJson(dynamic data) { int? $int; + String? string; try { $int = (data as int); } catch (_) {} - String? string; try { string = (data as String); } catch (_) {} @@ -3976,10 +3976,10 @@ class UserStatusClearAt_Time { factory UserStatusClearAt_Time.fromJson(dynamic data) { UserStatusClearAt_Time0? userStatusClearAtTime0; + int? $int; try { userStatusClearAtTime0 = UserStatusClearAt_Time0.fromValue(data as String); } catch (_) {} - int? $int; try { $int = (data as int); } catch (_) {} @@ -4039,10 +4039,10 @@ class UserStatusPublicUserStatus_ClearAt { factory UserStatusPublicUserStatus_ClearAt.fromJson(dynamic data) { UserStatusClearAt? userStatusClearAt; + int? $int; try { userStatusClearAt = UserStatusClearAt.fromJson(data as Map); } catch (_) {} - int? $int; try { $int = (data as int); } catch (_) {} @@ -4254,10 +4254,10 @@ class UserStatus_ClearAt { factory UserStatus_ClearAt.fromJson(dynamic data) { UserStatusClearAt? userStatusClearAt; + int? $int; try { userStatusClearAt = UserStatusClearAt.fromJson(data as Map); } catch (_) {} - int? $int; try { $int = (data as int); } catch (_) {} @@ -4406,10 +4406,10 @@ class UserStatusPredefinedStatus_ClearAt { factory UserStatusPredefinedStatus_ClearAt.fromJson(dynamic data) { UserStatusClearAt? userStatusClearAt; + int? $int; try { userStatusClearAt = UserStatusClearAt.fromJson(data as Map); } catch (_) {} - int? $int; try { $int = (data as int); } catch (_) {}