Skip to content

Auto add builder factories for nested built_collection classes #1254

Open

Description

@JosephNK

When using BuiltMap nesting, is it not automatically created?

abstract class Calendar implements Built<Calendar, CalendarBuilder> { 
  ...
  @BuiltValueField(wireName: 'calendar')
    BuiltMap<String, BuiltMap<String, BuiltList<DayDTO>>>? get calendar;
  ...
}

automatically generated below

..addBuilderFactory(
          const FullType(BuiltMap, const [
            const FullType(String),
            const FullType(BuiltMap, const [
              const FullType(String),
              const FullType(
                  BuiltList, const [const FullType(DayDTO)])
            ])
          ]),
          () => new MapBuilder<String,
              BuiltMap<String, BuiltList<DayDTO>>>())

however, the below needs to be added manually.

..addBuilderFactory(
          const FullType(BuiltMap, const [
            const FullType(String),
            const FullType(
                BuiltList, const [const FullType(DayDTO)])
          ]),
          () => new MapBuilder<String, BuiltList<DayDTO>>())
..addBuilderFactory(
        const FullType(
            BuiltList, const [const FullType(DayDTO)]),
        () => new ListBuilder<DayDTO>())

It won't work unless you add it manually in the code above. So you have to add it manually, but it works.

Is there a way to automatically generate it?

Activity

  1. JosephNK commented on Jun 3, 2023

    @JosephNK
    Author

    I added the following code for auto-generation.

    Is it correct to use it like this?

    abstract class Calendar implements Built<Calendar, CalendarBuilder> { 
      ...
      @BuiltValueField(wireName: 'calendar')
        BuiltMap<String, BuiltMap<String, BuiltList<DayDTO>>>? get calendar;
      ...
      BuiltMap<String, BuiltList<DayDTO>>? get autogen01; <-- added
      BuiltList<DayDTO>? get autogen02;  <-- added
    }
    
  2. davidmorgan commented on Jun 5, 2023

    @davidmorgan
    Collaborator

    Yes, it's necessary to add builder factories manually in some cases.

    It's true that you could add fields as in your second post so the builder factories get generated for you, but then you will end up with a very weird class :) ... maybe you could put all such fields in a single class that you don't use, as a more convenient way to add builder factories.

    Sorry that this part of built_value is so awkward, there is a long standing feature request to improve it but I haven't had a chance to tackle it!

  3. self-assigned this
    on Jun 5, 2023
  4. changed the title [-]When using BuiltMap nesting, is it not automatically created?[/-] [+]Auto add builder factories for nested built_collection classes[/+] on Dec 22, 2023
  5. pierremrtn commented on Sep 1, 2024

    @pierremrtn

    I was considering using built_value for a project, but this is a big deal to me. The amount of boilerplate can be huge and hard to write.

  6. tp commented on Oct 19, 2024

    @tp

    I was considering using built_value for a project, but this is a big deal to me. The amount of boilerplate can be huge and hard to write.

    @pierremrtn I understand that concern. For a current project (which internally uses built_value with the Dio OpenAPI generator) the value gained form this package much outweighs the extra effort / headache caused by this.

    For the case where we now want to deal with e.g. BuiltMap<String, BuiltList<Foo>> I added a helper method:

    extension on SerializersBuilder {
      /* Adds support for values of type `BuiltMap<Key, BuiltList<Value>>` */
      void addMapOfList<Key, Value>() {
        addBuilderFactory(
          FullType(BuiltMap, [
            FullType(Key),
            FullType(
              BuiltList,
              [FullType(Value)],
            )
          ]),
          () => new MapBuilder<Key, BuiltList<Value>>(),
        );
    
        addBuilderFactory(
          FullType(BuiltList, [FullType(Value)]),
          () => new ListBuilder<Value>(),
        );
      }
    }

    With that we only have to call addMapOfList<String, X>() for each case on the SerializersBuilder on init. So after the initial setup this is now easy to use, should this ever come up again.

    Maybe this helps anyone else to work around this problem quickly until it's supported via code generation.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

Type

No type

Projects

No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions