首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >Freezed创建子类

Freezed创建子类
EN

Stack Overflow用户
提问于 2020-12-02 22:09:54
回答 1查看 261关注 0票数 0

我有一个来自API的JSON数据结构,其中包含一些字段。

我想创建一个Freezed模型,它有一个工厂来创建正确的子类,这取决于其中一个字段的类型。

下面是我的代码:

代码语言:javascript
复制
abstract class ItineraryData<T> implements _$ItineraryData<T> {
  const ItineraryData._();

  const factory ItineraryData({
    List<dynamic> summary,
    double totalPrice,
    double totalSeparatePay,
    double totalTax,
    List<String> covidAlerts,
  }) = _ItineraryData;

  const factory ItineraryData.flight({
    List<FlightSummary> summary,
    double totalPrice,
    double totalSeparatePay,
    double totalTax,
    List<String> covidAlerts,
  }) = _FlightItineraryData;

  const factory ItineraryData.hotel({
    List<HotelSummary> summary,
    double totalPrice,
    double totalSeparatePay,
    double totalTax,
  }) = _HotelItineraryData;

  const factory ItineraryData.car({
    List<CarSummary> summary,
    double totalPrice,
    double totalSeparatePay,
    double totalTax,
    List<String> covidAlerts,
  }) = _CarItineraryData;

  factory ItineraryData.fromJson(Map json) => _$ItineraryDataFromJson(json);
}

在这种情况下,访问ItineraryData<A>的引用将永远不会有summary列表字段(它应该始终存在,但类型不同)。

然后,我尝试将未命名的构造函数更改为在列表类型中使用<T>

代码语言:javascript
复制
const factory ItineraryData({
    List<T> summary,
    double totalPrice,
    double totalSeparatePay,
    double totalTax,
    List<String> covidAlerts,
}) = _ItineraryData;

但随后我得到了以下错误:

代码语言:javascript
复制
Could not generate `fromJson` code for `summary` because of type `T` (type parameter).
None of the provided `TypeHelper` instances support the defined type.
To support type paramaters (generic types) you can:
1) Use `JsonConverter`
  https://pub.dev/documentation/json_annotation/latest/json_annotation/JsonConverter-class.html
2) Use `JsonKey` fields `fromJson` and `toJson`
  https://pub.dev/documentation/json_annotation/latest/json_annotation/JsonKey/fromJson.html
  https://pub.dev/documentation/json_annotation/latest/json_annotation/JsonKey/toJson.html
3) Set `JsonSerializable.genericArgumentFactories` to `true`
  https://pub.dev/documentation/json_annotation/latest/json_annotation/JsonSerializable/genericArgumentFactories.html
package:<???>/models/itinerary_data.freezed.dart:253:17
    ╷
253 │   final List<T> summary;
    │                 ^^^^^^^
    ╵
[INFO] Running build completed, took 221ms

我确实尝试添加了一个转换器,如下所示:

代码语言:javascript
复制
class ItineraryDataConverter
    implements JsonConverter<ItineraryData, Map<String, dynamic>> {
  const ItineraryDataConverter();

  @override
  ItineraryData fromJson(Map<String, dynamic> json) {
    if (json == null || !json.containsKey('data')) {
      return null;
    }

    json = json['data'];
    // type data was already set (e.g. because we serialized it ourselves)
    if (!json.keys
        .any((k) => ['cabin_class', 'hotel', 'car_type'].contains(k))) {
      return ItineraryData.fromJson(json);
    }
    // you need to find some condition to know which type it is. e.g. check the presence of some field in the json
    if (json.containsKey('cabin_class')) {
      return _FlightItineraryData.fromJson(json);
    } else if (json.containsKey('hotel')) {
      return _HotelItineraryData.fromJson(json);
    } else if (json.containsKey('car_type')) {
      return _CarItineraryData.fromJson(json);
    } else {
      throw Exception(
          'Could not determine the constructor for mapping from JSON');
    }
  }

  @override
  Map<String, dynamic> toJson(ItineraryData data) => data.toJson();
}

但我仍然得到相同的错误。

如何确保summary在子类中是可见的、强类型的?

或者,对此更好的方法是什么?

EN

回答 1

Stack Overflow用户

发布于 2020-12-02 23:52:22

您是否尝试过为类型T添加自定义转换器

代码语言:javascript
复制
const factory ItineraryData({
  @CustomConverter() List<T> summary,
  ...


...

class CustomConverter<T> implements JsonConverter<T, Object> {
  const CustomConverter();

  @override
  T fromJson(Object json) {
    // TODO: implement fromJson
    throw UnimplementedError();
  }

  @override
  Object toJson(T object) {
    // TODO: implement toJson
    throw UnimplementedError();
  }
}
票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/65109738

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档