Skip to content

ESP Enum encoding breaks TypeScript? #34

@jackwootton

Description

@jackwootton

From my own experiments with a local ESP and gRPC backend, it seems proto defined enums such as

syntax = "proto3";
package main;

enum MyType {
   NUMBER = 0;
   STRING = 1;
   BOOLEAN = 2;
}

...are received on the (web) client as enum names (strings) and not enum values:

"NUMBER", "STRING", "BOOLEAN"

I could change my client-side TypeScript enums from:

export enum MyType {
  NUMBER = 0,
  STRING,
  BOOLEAN,
}

to

// tslint:disable:no-any
export enum MyType {
  NUMBER = 'NUMBER' as any,
  STRING = 'STRING' as any,
  BOOLEAN = 'BOOLEAN' as any,
}
// tslint:enable:no-any

This works when receiving an enum from the gRPC backend (via the ESP). However, the same enum cannot then be used when the (web) client makes a request (the numeric value must be used).

This appears to be WIA since in ProtoToJson the message is serialized using SerializeToString

std::string binary = message.SerializeAsString();

I'm unsure why my JavaScript client doesn't balk at this, regardless, the result is, an enum with string values. console.log(myEnumInstance) yields:

["OBJECT", "STRING", "BOOLEAN"]

This means while the underlying type is a string (thanks to ESP), any comparison causes a compilation error:

myEnumInstance.map((t:MyType) => {
   console.log(t, typeof t);
   return t;
});

...yields:

OBJECT string
STRING string
BOOLEAN string

Yet the following causes a compilation error:

// Operator '==' cannot be applied to types 'MyType' and '"OBJECT"'.
console.log(t == 'OBJECT');

So, I'm stuck with string values in my enum that I can't use. Again, IDK how it is the web client's OK with this. Perhaps there's some coercion by the HTTP module in Angular?

Metadata

Metadata

Assignees

Labels

No labels
No labels

Type

No type

Projects

No projects

Milestone

No milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions