mcpField
D
dart-model-from-json

dart-model-from-json

github.com/somnio-softwareDevelopment863 installsUpdated 2d ago
Repository

About dart-model-from-json

A skill that turns a supplied JSON structure into Dart model classes using `json_annotation` and `equatable`. It specifies field types, nested classes, equality, serialization, and output ordering.

Key features

  1. 01JSON-to-Dart type mapping
  2. 02Nested object classes
  3. 03`fromJson` and `toJson` methods
  4. 04`copyWith` and value equality
  5. 05Classes output in dependency order

Use cases

  1. 01Create Dart models from an API response
  2. 02Represent nested JSON objects in Dart
  3. 03Generate serializable models with equality

Install

Copy the command and run it in a terminal.

$npx skills add https://github.com/somnio-software/somnio-ai-tools --skill dart-model-from-json

After installing, type/dart-model-from-jsonin Claude Code to confirm it loaded.

Details

From the project README

Dart Model from JSON

Generates Dart model classes from a JSON structure using json_annotation and equatable.


Input

The user provides a JSON object — either as a code block or pasted inline. If no JSON is provided, ask for it before proceeding.


Requirements

  • Use json_annotation for JSON serialization
  • Use equatable for value equality
  • Include copyWith method
  • Include fromJson and toJson methods
  • Include props getter for equatable
  • No @immutable decorator
  • No documentation comments
  • No @JsonKey annotations unless explicitly requested

Model Structure

import 'package:equatable/equatable.dart';
import 'package:json_annotation/json_annotation.dart';

part 'model_name.g.dart';

@JsonSerializable()
class ModelName extends Equatable {
  ModelName({
    required this.field1,
    this.field2,
    this.field3 = defaultValue,
  });

  final String field1;
  final int? field2;
  final bool field3;

  ModelName copyWith({
    String? field1,
    int? field2,
    bool? field3,
  }) {
    return ModelName(
      field1: field1 ?? this.field1,
      field2: field2 ?? this.field2,
      field3: field3 ?? this.field3,
    );
  }

  static ModelName fromJson(Map<String, dynamic> json) => _$ModelNameFromJson(json);
  Map<String, dynamic> toJson() => _$ModelNameToJson(this);

  @override
  List<Object?> get props => [field1, field2, field3];
}

Field Type Mapping

JSON typeDart type
stringString
number (integer)int
number (decimal)double
booleanbool
null or absentnullable type (e.g., String?)
array of primitivesList<Type>
array of objectsList<ClassName>
objectseparate class

Naming Conventions

  • Class names: PascalCase
  • Field names: camelCase
  • Required fields: non-nullable with required keyword
  • Optional fields: nullable with ?

Nested Object Rules

When to create separate classes
  • Always create a class for objects with multiple properties
  • Always create a class for array items that are objects
  • Use List<String>, List<int>, etc. for primitive arrays — no class needed
Class name inference
ContextClass name
address field (object)Address
profile.preferences (nested object)Preferences
orders[] (array of objects)Order
orders[].items[] (nested array)OrderItem

If context is unclear, ask the user for the desired class name.


Output Format

Output each class as a separate code block labeled with the suggested filename:

user.dart

// ... User class

address.dart

// ... Address class

List all required classes in dependency order (leaf classes first, root last).


Example

Input JSON:

{
  "id": "123",
  "name": "John Doe",
  "age": 30,
  "isActive": true,
  "tags": ["tag1", "tag2"],
  "address": {
    "street": "123 Main St",
    "city": "New York",
    "zipCode": "10001"
  }
}

Output:

address.dart

import 'package:equatable/equatable.dart';
import 'package:json_annotation/json_annotation.dart';

part 'address.g.dart';

@JsonSerializable()
class Address extends Equatable {
  Address({
    required this.street,
    required this.city,
    required this.zipCode,
  });

  final String street;
  final String city;
  final String zipCode;

  Address copyWith({
    String? street,
    String? city,
    String? zipCode,
  }) {
    return Address(
      street: street ?? this.street,
      city: city ?? this.city,
      zipCode: zipCode ?? this.zipCode,
    );
  }

  static Address fromJson(Map<String, dynamic> json) => _$AddressFromJson(json);
  Map<String, dynamic> toJson() => _$AddressToJson(this);

  @override
  List<Object?> get props => [street, city, zipCode];
}

user.dart

import 'package:equatable/equatable.dart';
import 'package:json_annotation/json_annotation.dart';

import 'address.dart';

part 'user.g.dart';

@JsonSerializable()
class User extends Equatable {
  User({
    required this.id,
    required this.name,
    required this.age,
    required this.isActive,
    required this.tags,
    required this.address,
  });

  final String id;
  final String name;
  final int age;
  final bool isActive;
  final List<String> tags;
  final Address address;

  User copyWith({
    String? id,
    String? name,
    int? age,
    bool? isActive,
    List<String>? tags,
    Address? address,
  }) {
    return User(
      id: id ?? this.id,
      name: name ?? this.name,
      age: age ?? this.age,
      isActive: isActive ?? this.isActive,
      tags: tags ?? this.tags,
      address: address ?? this.address,
    );
  }

  static User fromJson(Map<String, dynamic> json) => _$UserFromJson(json);
  Map<String, dynamic> toJson() => _$UserToJson(this);

  @override
  List<Object?> get props => [id, name, age, isActive, tags, address];
}

Comments

Markdown supported