DEV3 Technologies home

DEV3 Developer Forum

Flutter fromJson throws "type 'Null' is not a subtype of type 'String'". How do I parse API JSON safely?

Flutter helpSolved0 views
dev3 ·

My model does name: json['name'] as String and the app crashes when the API sends null or omits the key:

type 'Null' is not a subtype of type 'String' in type cast

What is the clean way to handle optional fields and numbers that sometimes arrive as strings?

#flutter#json#dart

0

1 reply

dev3 · Accepted answer

Why

json['name'] is dynamic. The as String cast throws when the value is null, missing, or a different type (for example an int id sent as a string by some backends).

Make the field nullable or give a default

class Product {
  Product({required this.id, required this.name, this.note, required this.price});

  final int id;
  final String name;
  final String? note;
  final double price;

  factory Product.fromJson(Map<String, dynamic> json) => Product(
        id: (json['id'] as num).toInt(),
        name: json['name'] as String? ?? '',
        note: json['note'] as String?,
        price: double.tryParse('${json['price']}') ?? 0,
      );
}
  • as String? allows null.
  • (x as num).toInt() accepts both 5 and 5.0.
  • double.tryParse('${...}') handles "12.50" and 12.5 alike.

Let code generation do it

With json_serializable:

@JsonSerializable()
class Product {
  Product({required this.id, required this.name, this.note});
  final int id;
  @JsonKey(defaultValue: '')
  final String name;
  final String? note;
  factory Product.fromJson(Map<String, dynamic> j) => _$ProductFromJson(j);
  Map<String, dynamic> toJson() => _$ProductToJson(this);
}

Run dart run build_runner build.

Lists and nested objects

final items = (json['items'] as List<dynamic>? ?? [])
    .map((e) => Item.fromJson(e as Map<String, dynamic>))
    .toList();

Pitfalls

  • Dates: parse with DateTime.tryParse and handle null.
  • Never trust the API contract in production; log the raw body when parsing fails.
  • Paste a sample response into the JSON to Dart converter to get a starting model, then adjust nullability by hand.
0

Your reply

Every post is reviewed by DEV3 before it appears. Usually reviewed within 24 hours.

Markdown supported. Use ``` for code blocks. Images are not allowed.