Je suis nouveau dans le flutter et l'objectif est de sérialiser des objets JSON complexes qui contiennent d'autres objets plus petits.
L'utilisation de json_serializable: ^2.0.0
et du fichier pubspec.yaml
ressemble à ceci.
targets: $default: builders: built_value_generator|built_value: generate_for: - model/*.dart json_serializable|json_serializable: generate_for: - model/*.dart
Le user.dart
ressemble à ceci
import 'package:json_annotation/json_annotation.dart'; part 'user.g.dart'; @JsonSerializable(nullable: false) class User { final String firstName; final String lastName; final DateTime dateOfBirth; User({this.firstName, this.lastName, this.dateOfBirth}); factory User.fromJson(Map<String, dynamic> json) => _$UserFromJson(json); Map<String, dynamic> toJson() => _$UserToJson(this); }
J'ai essayé la flutter pub run build_runner build
mais le fichier user.g.dart n'est pas créé et je suis confronté à un problème avec cela.
J'ai également ajouté le fichier build.yaml
avec le code suivant
dependencies: intl: ^0.15.7 json_annotation: ^2.0.0 built_value: ^6.7.1 flutter: sdk: flutter dev_dependencies: build_runner: ^1.0.0 json_serializable: ^2.0.0 built_value_generator: ^6.7.1 flutter_test: sdk: flutter
Quelqu'un peut-il me dire ce qui me manque ici. Merci
4 Réponses :
L'argument du constructeur ne doit pas être facultatif
part 'User.g.dart';
Ils devraient être obligatoires:
'user.g.dart';
Et la partie
User(this.firstName, this.lastName, this.dateOfBirth);
doit correspondre à la classe Uppercase User:
User({this.firstName, this.lastName, this.dateOfBirth});
J'ai essayé d'avoir des arguments optionnels et cela a très bien fonctionné. Joyeux flottement.
l'argument obligatoire est correct mais les majuscules ne fonctionnent pas vraiment. Mais les arguments.
Merci, le constructeur d'argument optionnel semblait être le problème pour moi.
Si vous avez une classe comme LoggedUser dans un fichier nommé Logged_user.dart, utilisez la part 'logged_user.g.dart'
Le nom du fichier, la classe et la part 'Book.g.dart';
devrait tous correspondre.
Votre commentaire sur la réponse de Jalil suggérait que cela fonctionnait avec un constructeur d'arguments optionnel. Une chance que vous puissiez insérer le code dans cette réponse? Le passage de l'option aux arguments obligatoires est la seule chose qui a permis à cela de fonctionner pour moi.
J'ai eu cette erreur suivante
Erreur
[WARNING] json_serializable:json_serializable on lib/day10/models/sentence.dart: Missing "part 'sentence.g.dart';".
J'ai remarqué que je devais changer sur le fichier modèle cette part 'Sentence.g.dart';
à cette part 'sentence.g.dart';
en d'autres termes, je devais le mettre en minuscules.
import 'package:json_annotation/json_annotation.dart';
part
après import
instructions d' import
part
fichier est nommé d' après votre nom de fichier de classe ( et non la classe elle - même nom), avec un g
ajoutéCacheItem
avec ...cache-item.dart
...part 'cache-item.g.dart';
obtient la directive part
correspondante.part
n'est pas nommée d'après votre classe réelle, mais le nom du fichier de classe.@JsonSerializable()
au-dessus du nom de la classefactory <Class>.fromJson(json) => _$ClassFromJson(json);
toJson() => _$ClassToJson(this)
_
underscore)$
factory
fournit (Map<String,dynamic> json)
comme argumenttoJson()
renvoie Map<String,dynamic>
Lorsque tout cela est terminé, essayez d'exécuter le générateur à partir du répertoire racine du projet ...
Dans Flutter:
flutter pub run build_runner build
En pur Dart:
pub run build_runner build
Bad state: Unexpected diagnostics:
Voir cette sortie lors de l'exécution de build_runner est probablement un problème avec flutter et json_annotation
selon une version incompatible de l' analyzer
. Cela se produit avec les versions de json_serializable
antérieures à 3.5 nécessitant un dependency_override de l'analyseur à 0.39.14 ou 0.39.17.
Votre premier pas devrait être d'essayer la dernière version de json_serilizable de pub.dev qui n'a apparemment pas ce problème de dépendance .
Si vous ne pouvez pas mettre à niveau json_serializable, vous pouvez essayer de placer les lignes de remplacement sous dev_dependences
:
// GENERATED CODE - DO NOT MODIFY BY HAND part of 'cache-item.dart'; // ************************************************************************** // JsonSerializableGenerator // ************************************************************************** CacheItem _$CacheItemFromJson(Map<String, dynamic> json) { return CacheItem( response: json['response'] as String, ) ..created = json['created'] as int ..keywords = json['keywords'] as String; } Map<String, dynamic> _$CacheItemToJson(CacheItem instance) => <String, dynamic>{ 'created': instance.created, 'keywords': instance.keywords, 'response': instance.response, };
Sous-classe / classe parent
Si votre classe est un enfant d'une classe parent et que vous souhaitez sérialiser les champs / propriétés de l'enfant uniquement, vous ne pouvez annoter que la sous-classe . Les champs de classe parente seront automatiquement trouvés et inclus dans les fichiers de classe générés pour la sous-classe.
Si vous voulez pouvoir sérialiser / désérialiser le parent et l'enfant séparément , continuez et @JsonSerializable
également les classes de base / parent avec @JsonSerializable
.
par exemple, nom de fichier account.dart
import 'package:json_annotation/json_annotation.dart'; part 'cache-item.g.dart'; @JsonSerializable() class CacheItem { int created; String keywords; String response; CacheItem({this.response}); factory CacheItem.fromJson(Map<String,dynamic> json) => _$CacheItemFromJson(json); Map<String,dynamic> toJson() => _$CacheItemToJson(this); }
Produit:
// GENERATED CODE - DO NOT MODIFY BY HAND part of 'cache-item.dart'; // ************************************************************************** // JsonSerializableGenerator // ************************************************************************** CacheItem _$CacheItemFromJson(Map<String, dynamic> json) { return CacheItem( json['created'] as int, json['keywords'] as String, json['response'] as String, ); } Map<String, dynamic> _$CacheItemToJson(CacheItem instance) => <String, dynamic>{ 'created': instance.created, 'keywords': instance.keywords, 'response': instance.response, };
import 'package:json_annotation/json_annotation.dart'; part 'cache-item.g.dart'; @JsonSerializable() class CacheItem { int created; String keywords; String response; CacheItem(this.created, this.keywords, this.response); factory CacheItem.fromJson(Map<String,dynamic> json) => _$CacheItemFromJson(json); Map<String,dynamic> toJson() => _$CacheItemToJson(this); }
// GENERATED CODE - DO NOT MODIFY BY HAND part of 'account.dart'; // ************************************************************************** // JsonSerializableGenerator // ************************************************************************** Account _$AccountFromJson(Map<String, dynamic> json) { return Account() ..created = json['created'] as int ..username = json['username'] as String ..password = json['password'] as String ..id = json['id'] as int; } Map<String, dynamic> _$AccountToJson(Account instance) => <String, dynamic>{ 'created': instance.created, 'username': instance.username, 'password': instance.password, 'id': instance.id, };
Cet exemple est le même que ci-dessus sauf que le constructeur manque certains champs et a une response
facultative.
C'est bon.
Le générateur utilisera simplement les setters publics (implicites) après avoir instancié l'objet pour affecter les valeurs.
import 'package:json_annotation/json_annotation.dart'; part 'account.g.dart'; class AccountBase { int created; String username; String password; } @JsonSerializable() class Account extends AccountBase { int id; Account(); factory Account.fromJson(Map<String,dynamic> json) => _$AccountFromJson(json); Map<String,dynamic> toJson() => _$AccountToJson(this); }
dev_dependencies: build_runner: ^1.9.0 flutter_test: sdk: flutter json_serializable: 3.3.0 test: ^1.14.3 dependency_overrides: analyzer: '0.39.14'
Celui-ci était vraiment utile, le plus important est de ne pas utiliser de dépendances supplémentaires, utilisez simplement ce qui est suggéré par @Baker. +1
J'ai tout vérifié et je confirme que je ne génère pas la méthode de conversion model-json
MEILLEURE RÉPONSE JAMAIS!