0

I'm trying to make a Freezed class with a generic type that has toJson and fromJson:

import 'package:freezed_annotation/freezed_annotation.dart';

part 'option.freezed.dart';
part 'option.g.dart';

@Freezed(genericArgumentFactories: true)
class Option<TData> with _$Option<TData> {
  const factory Option(
      {required TData id,
      required String name,
      String? fontFamily,
      required int iconCodePoint}) = _Option;

  const factory Option.empty({
    @Default(0) int iconCodePoint,
    @Default(0 as TData) TData id,
    @Default('') String name,
    @Default(null) String? fontFamily,
  }) = _Empty;

  factory Option.fromJson(
          Map<String, dynamic> json, TData Function(Object?) fromJsonTData) =>
      _$OptionFromJson(json, fromJsonTData);

  @override
  Map<String, dynamic> toJson(Object? Function(TData) toJsonTData) {
    return _$$_OptionToJson<TData>(this as _$_Option<TData>, toJsonTData);
  }

  Map<String, dynamic> _$$_OptionToJson<TData>(
    _$_Option<TData> instance,
    Object? Function(TData value) toJsonTData,
  ) =>
      <String, dynamic>{
        'id': toJsonTData(instance.id),
        'name': instance.name,
        'fontFamily': instance.fontFamily,
        'iconCodePoint': instance.iconCodePoint,
        'runtimeType': instance.$type,
      };
}

The build runner executes the code generation without error, but when I try to run the app I get:

Error: The non-abstract class '_$_Option' is missing implementations
for these members: lib/…/option/option.freezed.dart:190
     - Option._$$_OptionToJson
    Try to either
     - provide an implementation,
     - inherit an implementation from a superclass or mixin,
     - mark the class as abstract, or
     - provide a 'noSuchMethod' implementation.
    class _$_Option<TData> implements _Option<TData> {
          ^^^^^^^^^ : Context: 'Option._$$_OptionToJson' is defined here. lib/…/option/option.dart:30
      Map<String, dynamic> _$$_OptionToJson<TData>(
                           ^^^^^^^^^^^^^^^^ : Error: The non-abstract class '_$_Empty' is missing implementations for these members:
lib/…/option/option.freezed.dart:403
     - Option._$$_OptionToJson
    Try to either
     - provide an implementation,
     - inherit an implementation from a superclass or mixin,
     - mark the class as abstract, or
     - provide a 'noSuchMethod' implementation.
    class _$_Empty<TData> implements _Empty<TData> {
          ^^^^^^^^ : Context: 'Option._$$_OptionToJson' is defined here. lib/…/option/option.dart:30
      Map<String, dynamic> _$$_OptionToJson<TData>(
                           ^^^^^^^^^^^^^^^^ : Error: Type variables can't be used in static members. lib/…/option/option.freezed.dart:406
          this.id = 0 as TData,
                         ^^^^^ : Error: Type variables can't be used as constants. lib/…/option/option.freezed.dart:406
          this.id = 0 as TData,
                         ^^^^^ : Error: Type variables can't be used as constants. lib/…/option/option.dart:16
        @Default(0 as TData) TData id,

It looks like in the docs we don't need toJson but when I remove it I get this error in all the classes that contain a field of type Option

RangeError (index): Invalid value: Only valid value is 0: -1

when I run the build runner. What am I doing wrong?

lrn
  • 64,680
  • 7
  • 105
  • 121
BeniaminoBaggins
  • 11,202
  • 41
  • 152
  • 287

1 Answers1

0

Shouldn't the first constructor be

const factory Option.option(

?

I had a similar problem, see https://github.com/rrousselGit/freezed/issues/766