Old iron remember to forward, Brother Mao will present more Flutter good articles~~~~

WeChat group ducafecat

b station https://space.bilibili.com/404904528

original

https://medium.com/teamkraken/converting-json-api-response-to-dart-objects-with-chopper-and-jsonserializable-8ec98b762ac1

Code

https://github.com/ErkinKurt/chopper_json_serializable

reference

text

However, the JSON response format differs from service to service; there are some shared conventions, such as JSON: API, HAL... Today, I will try to show how to start from scratch and convert JSON: API responses into Dart objects in a Flutter project.

If you want to follow the source code, here is: Chopper json serializable

https://github.com/ErkinKurt/chopper_json_serializable

1. Create a project and add dependencies

Packages to be used:

  • Chopper:
    Dart and Flutter Http client generators using source gen and Retrofit
  • Json Serializable:
    By using it, JSON conversion of entities will be automatically generated
  • Japx:
    Parser, which turns complex JSON: API structure into simple JSON, and vice versa

Thank you so much for these awesome packages!

Since JsonSerializable and Chopper use meta programming, they need BuildRunner to handle code generation. Here is the pubspec.yaml file to be used:

2. Implement Mock Http Client to get the response in JSON: API format

The response model is provided in the assets folder because we want to use a mock http client and do not rely on any remote sources. The response model is taken from JAPX assets.

If you want to use chopper with regular http client just ignore this part and follow the following part...

3. Create a model and use JsonSerializable

Although for the sake of simplicity, we have two entities, Article and People, but they will inherit from the Entity class to demonstrate how to use JsonSerializable with inheritance. Because every entity has a type and id value in JSON: API, we created a base class with type and id.

abstract class Entity {
  final String type;
  final String id;

  Entity(this.type, this.id);
}

Let us implement two models with JsonSerializable. We need to write part'<model-name>. At the end of the day, the json and FromJson constructors will be generated by the runner built in this directory.

We are defining fromJsonFactory to be used in JsonTypeConvertor, and we will see its use later.

After completing our implementation, we need to run flutter pub run build runner build in the root directory of the project, so that the build runner can perform its magic. After successful execution, we see. The G file is generated without errors.

4. Create Chopper Service

Let's create the network layer and Chopper service. Chopper Services uses automatic generation to create the underlying http client implementation, so we don't need to worry about http client requests.

We provide a static creation method to inject services into ChopperClients. In addition, we also have getArticle and getPerson methods to get a single entity through the http client.

As you can see, we have some red lights on. This is because chopper uses code generation with the help of (build runner the underlying hero).

Let us run the flutter pub run build \_ runner build command as before. If the execution is successful, we will not see any errors. Please take a look at the generated code to see how chopper handles basic http client requests.

5. Implement Chopper Client

Now we need to implement the Chopper client to use the Chopper service we created. Chopper Client provides service properties and sets up multiple services. For client use, there are two options, either create a client as a singleton and deliver all services, or create a client whenever needed.

For this example, let's create a chopper client instance and pass it to the widget tree. However, we can use getIt or provider as dependency injection. For the sake of simplicity, we will use it as a pillar.

Below is a ChopperClientBuilder, which provides a method to build our ChopperClientBuilder client.

6. Use the JAPX decoder in the user interface to use the Chopper service

We have a stateful widget with chopper client as a prop. We will implement two methods getArticle and getPeople. In this part, JAPX played an important role. Because our JSON response has a JSON: API response format, we need to smooth and complex responses.

However, the above example works well; we need to make an explicit conversion:

  • json.decode to get mapped json object
  • Japx.decode to flatten the map.
  • Instantiate dart object with our model’s fromJsonFactory methods.

There are two problems with this approach:

  • Explicit conversion will cause code duplication
  • Service method Response<dynamic> return type.

Let's see how to deal with these problems...

7. Implement JsonConvertor for response type specification

In some way, we need to manipulate Chopper Responses to return the model type we defined earlier. Thanks to special interceptors called converters, we can handle the conversion of responses, requests, and errors. All we need to do is to create a converter and inject it into the Chopper client, which we use.

Let's create the jsonserializableeconverter class for Chopper Client. In order to do this, we need to extend our class from Chopper's JsonConverter class and override the convertResponse, convertRequest and convertError methods.

Now we convert in the convertResponse method, which also solves the code duplication problem, because this method is called every time a successful response is made. However, there is still a type conversion problem that needs to be resolved.

jsonRes.copyWith<ResultType>(body: JsonTypeParser.decode<Item>(flatJson["data"]))

This is the key statement to parse the response of the Dart model:

  • In fact, we hope that the return type used by the service method ResultType is List or or BuiltList will be our return type. In order to define the return type in the service method, we need to add the model type we expect

After this change, whenever convertResponse is triggered, the ResultType will be People or Article.

  • However, we still need to call the fromJsonFactory method of our model to convert the response object into a Dart object. In order to do this, we create the JsonTypeParser class, which will hold the conversion logic of the Dart object

JsonTypeParser has factories attribute of type Map<Type, JsonFactory>, which contains models and models from JsonFactory methods. Whenever we have a new model, we need to add its type and factory to the factory so that it can be parsed by the \_ decodeMap method. JsonSerializableConverter executes the decode <t> method, where t is ResultType or Item, and calls factory get of the matching type to instantiate our model.

Let us follow this change and modify the user interface part, we consume chopping service...

Let's insert jsonserializableeconverter into our chopper client:

According to these changes, we can now directly use the response body, which has type safety.

to sum up

I know that there are a lot of things to digest, but there are still a lot of things to discuss, such as JsonSerializable and Chopper's custom type converters that respond incorrectly. If I write a medium-level article, I will connect this topic.

All in all, what I want to show is that various response models can be solved by chopping and json serialization without losing the type-safe clean way.


© Cat brother

https://ducafecat.tech/

https://github.com/ducafecat

Past

Open source

GetX Quick Start

https://github.com/ducafecat/getx_quick_start

News client

https://github.com/ducafecat/flutter_learn_news

strapi manual translation

https://getstrapi.cn

WeChat discussion group ducafecat

Series collection

Translation

https://ducafecat.tech/categories/%E8%AF%91%E6%96%87/

Open source project

https://ducafecat.tech/categories/%E5%BC%80%E6%BA%90/

Dart programming language basics

https://space.bilibili.com/404904528/channel/detail?cid=111585

Getting started with Flutter zero foundation

https://space.bilibili.com/404904528/channel/detail?cid=123470

Flutter actual combat from scratch news client

https://space.bilibili.com/404904528/channel/detail?cid=106755

Flutter component development

https://space.bilibili.com/404904528/channel/detail?cid=144262

Flutter Bloc

https://space.bilibili.com/404904528/channel/detail?cid=177519

Flutter Getx4

https://space.bilibili.com/404904528/channel/detail?cid=177514

Docker Yapi

https://space.bilibili.com/404904528/channel/detail?cid=130578


独立开发者_猫哥
666 声望126 粉丝