Skip to content

pigeon: implement primitive enum return values and arguments #87307

Description

@gaaclarke

example:

enum Foo {
  one,
  two,
}

@HostApi
abstract class Api {
  Foo lookup(int identifier);
  void set(int identifier, Foo foo);
}

Activity

  1. added
    P3Issues that are less important to the Flutter project
    on Oct 12, 2021
  2. bparrishMines commented on Dec 28, 2021

    @bparrishMines
    Contributor

    For Dart and Android, support for this feature is pretty straightforward. It can be solved by just updating the codec with enum indexes:

    Dart:

    enum Fruit {
      apple,
      banana,
    }
    
    class ACodec extends StandardMessageCodec {
      const ACodec();
      
      @override
      void writeValue(WriteBuffer buffer, Object? value) {
        if (value is Fruit) {
          buffer.putUint8(128);
          writeValue(buffer, value.index);
        } else {
          super.writeValue(buffer, value);
        }
      }
    
      @override
      Object? readValueOfType(int type, ReadBuffer buffer) {
        switch (type) {
          case 128:
            return Fruit.values[readValue(buffer)! as int];
          default:
            return super.readValueOfType(type, buffer);
        }
      }
    }

    Java:

    public enum Fruit {
      apple(0),
      banana(1);
    
      private int index;
      Fruit(final int index) {
        this.index = index;
      }
    }
    
    private static class ACodec extends StandardMessageCodec {
      public static final ACodec INSTANCE = new ACodec();
      private ACodec() {}
      @Override
      protected Object readValueOfType(byte type, ByteBuffer buffer) {
        switch (type) {
          case (byte)128:
            return Fruit.values()[(int) readValue(buffer)];
          default:        
            return super.readValueOfType(type, buffer);
          
        }
      }
      @Override
      protected void writeValue(ByteArrayOutputStream stream, Object value)     {
        if (value instanceof Fruit) {
          stream.write(128);
          writeValue(stream, ((Fruit) value).index);
        } else {
          super.writeValue(stream, value);
        }
      }
    }

    But, the codec for Objective-C doesn't handle Objective-C type enums well. e.g:

    typedef NS_ENUM(NSUInteger, Fruit) {
      FruitApple = 0,
      FruitBanana = 1,
    };

    FlutterStandardReader.readValueOfType and FlutterStandardWriter.writeValue require an object, not a primitive, to be returned or passed respectively. So, the solution won't be as straightforward as other languages. A couple of solutions I came up with are:

    1. [Breaking Change] The Objective-C generation could create Enum like classes with static variables. e.g.
    @interface Fruit : NSObject
    @property(readonly) NSUInteger index;
    - (instancetype)init NS_UNAVAILABLE;
    + (Fruit *)apple;
    + (Fruit *)banana;
    @end
    1. Methods for HostApis/FlutterApis could take and/or return enum wrappers. e.g.
    typedef NS_ENUM(NSUInteger, Fruit) {
      FruitApple = 0,
      FruitBanana = 1,
    };
    
    @interface FruitEnum : NSObject
    @property(readonly) Fruit value;
    - (instancetype)initWithValue:(Fruit)value;
    @end
    
    @protocol AClass
    - (void)aMethod:(NSArray<FruitEnum *> *)fruits error:(FlutterError *_Nullable *_Nonnull)error;
    @end
  3. TheBuggedYRN commented on Oct 11, 2022

    @TheBuggedYRN

    After merging flutter/packages#1871:

    1. Enum argument works ✅:

      void bar(Foo foo);
    2. List<Enum> argument does not work ❌:

      void bar(List<Foo> foo);

    @gaaclarke is this intended?

  4. hawkkiller commented on Dec 26, 2022

    @hawkkiller
  5. mchouchane-enedis commented on Apr 11, 2023

    @mchouchane-enedis
  6. added
    P1High-priority issues at the top of the work list
    and removed
    P3Issues that are less important to the Flutter project
    on Apr 17, 2023
  7. timukasr commented on Jul 6, 2023

    @timukasr

    Confused how #130064 is duplicate of this. From my (user) point of view, #87307 is already implemented, but it is not working correctly.

    If this feature is not supported, then pigeon generator should give error and not generate code that crashes in production.

  8. added a commit that references this issue on Aug 28, 2023
  9. github-actions commented on Sep 11, 2023

    @github-actions

    This thread has been automatically locked since there has not been any recent activity after it was closed. If you are still experiencing a similar issue, please open a new bug, including the output of flutter doctor -v and a minimal reproduction of the issue.

  10. locked as resolved and limited conversation to collaborators on Sep 11, 2023
  11. added a commit that references this issue on Jun 19, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    P1High-priority issues at the top of the work listc: proposalA detailed proposal for a change to Flutterp: pigeonrelated to pigeon messaging codegen toolpackageflutter/packages repository. See also p: labels.team-ecosystemOwned by Ecosystem teamtriaged-ecosystemTriaged by Ecosystem team

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions