Thanks to visit codestin.com
Credit goes to github.com

Skip to content

Commit 9038e30

Browse files
committed
[python] Rework of enum handling to simplify and add features [behavior change]
So now, if you have an enum: <enum name="CarColor" encodingType="char"> <validValue name="Black">B</validValue> <validValue name="White">W</validValue> </enum> The generated CarColor now has a __str__() method for displaying the name of the enum value. When retrieving the value of an enum field, you now get an object that is an instance of the enum. So: print('The color is: {}'.format(car.getColor())) would display something like: "The color is: Black" rather than "The color is: 66" or "The color is: B". To encode an enum, you would pass a value of the enum like: car.setColor(CarColor.Black) or the raw value: car.setColor('B') Since retrieving an emum yields an instance of the enum, its underlying value is in its "value" property: if car.getColor().value == CarColor.Black: handleBlackCar(car)
1 parent 7a441e2 commit 9038e30

File tree

1 file changed

+49
-44
lines changed

1 file changed

+49
-44
lines changed

main/java/uk/co/real_logic/sbe/generation/python/PythonGenerator.java

Lines changed: 49 additions & 44 deletions
Original file line numberDiff line numberDiff line change
@@ -431,9 +431,9 @@ private void generateEnum(final List<Token> tokens) throws IOException
431431
try (final Writer out = outputManager.createOutput(enumName))
432432
{
433433
out.append(generateFileHeader(ir.applicableNamespace().replace('.', '_'), null));
434-
out.append(generateEnumDeclaration(enumName));
434+
out.append(generateClassDeclaration(enumName));
435435
out.append(generateEnumValues(tokens.subList(1, tokens.size() - 1), enumToken));
436-
out.append(generateEnumLookupMethod(tokens.subList(1, tokens.size() - 1), enumToken));
436+
out.append(generateEnumMethods(enumName));
437437
}
438438
}
439439

@@ -513,55 +513,65 @@ private CharSequence generateEnumValues(final List<Token> tokens, final Token en
513513
final StringBuilder sb = new StringBuilder();
514514
final Encoding encoding = encodingToken.encoding();
515515

516-
sb.append(" class Value:\n");
516+
for (final Token token : tokens)
517+
{
518+
if (encoding.primitiveType() == PrimitiveType.CHAR)
519+
{
520+
final char constVal = (char) token.encoding().constValue().longValue();
521+
sb.append(" ").append(token.name()).append(" = '").append(constVal).append("'\n");
522+
}
523+
else
524+
{
525+
final CharSequence constVal = generateLiteral(
526+
token.encoding().primitiveType(), token.encoding().constValue().toString());
527+
sb.append(" ").append(token.name()).append(" = ").append(constVal).append("\n");
528+
}
529+
}
530+
531+
// generate the null value
517532

533+
if (encoding.primitiveType() == PrimitiveType.CHAR)
534+
{
535+
sb.append(" NULL_VALUE = '\\0'");
536+
}
537+
else
538+
{
539+
sb.append(String.format(
540+
" NULL_VALUE = %1$s",
541+
generateLiteral(encoding.primitiveType(), encoding.applicableNullValue().toString())
542+
));
543+
}
544+
sb.append("\n\n");
545+
546+
sb.append(" VALID_VALUES = {\n");
518547
for (final Token token : tokens)
519548
{
520-
final CharSequence constVal = generateLiteral(
521-
token.encoding().primitiveType(), token.encoding().constValue().toString());
522-
sb.append(" ").append(token.name()).append(" = ").append(constVal).append("\n");
549+
sb.append(" ").append(token.name()).append(",\n");
523550
}
551+
sb.append(" NULL_VALUE,\n }\n\n");
524552

525-
sb.append(String.format(
526-
" NULL_VALUE = %1$s",
527-
generateLiteral(encoding.primitiveType(), encoding.applicableNullValue().toString())
528-
));
553+
sb.append(" AS_TEXT = {\n");
529554

530-
sb.append("\n\n");
555+
for (final Token token : tokens)
556+
{
557+
sb.append(" ").append(token.name()).append(" : '").append(token.name()).append("',\n");
558+
}
559+
sb.append(" NULL_VALUE : 'NULL_VALUE',\n }\n\n");
531560

532561
return sb;
533562
}
534563

535-
private CharSequence generateEnumLookupMethod(final List<Token> tokens, final Token encodingToken)
564+
private CharSequence generateEnumMethods(final String name)
536565
{
537-
final String enumName = formatClassName(encodingToken.name());
538566
final StringBuilder sb = new StringBuilder();
539567

540-
sb.append(
541-
" @staticmethod\n" +
542-
" def get(value):\n" +
543-
" values = {\n");
544-
545-
for (final Token token : tokens)
546-
{
547-
sb.append(String.format(
548-
" %1$s : %3$s.Value.%2$s,\n",
549-
token.encoding().constValue().toString(),
550-
token.name(),
551-
enumName)
552-
);
553-
}
554-
555-
sb.append(String.format(
556-
" %1$s : %2$s.Value.NULL_VALUE\n" +
557-
" }\n" +
558-
" if type(value) is int:\n" +
559-
" return values[value]\n" +
560-
" else:\n" +
561-
" return values[ord(value)]\n",
562-
encodingToken.encoding().applicableNullValue().toString(),
563-
enumName
564-
));
568+
sb.append(" def __init__(self, value):\n");
569+
sb.append(" self.value = value\n");
570+
sb.append(" if self.value not in ").append(name).append(".VALID_VALUES:\n");
571+
sb.append(" raise ValueError('Invalid value for ").append(name).append(": {}'.format(value))\n");
572+
sb.append("\n");
573+
sb.append(" def __str__(self):\n");
574+
sb.append(" return ").append(name).append(".AS_TEXT[self.value]\n");
565575

566576
return sb;
567577
}
@@ -623,11 +633,6 @@ private CharSequence generateClassDeclaration(final String name)
623633
return "class " + name + ":\n";
624634
}
625635

626-
private CharSequence generateEnumDeclaration(final String name)
627-
{
628-
return "class " + name + ":\n";
629-
}
630-
631636
private CharSequence generatePrimitivePropertyEncodings(
632637
final String containingClassName, final List<Token> tokens, final String indent)
633638
{
@@ -1053,7 +1058,7 @@ private CharSequence generateEnumProperty(
10531058
sb.append(String.format(
10541059
"\n" +
10551060
indent + " def get%2$s(self):\n" +
1056-
indent + " return %1$s.%1$s.get(struct.unpack_from( '%5$s', self.buffer_, self.offset_ + %6$d)[0])\n\n",
1061+
indent + " return %1$s.%1$s(struct.unpack_from( '%5$s', self.buffer_, self.offset_ + %6$d)[0])\n\n",
10571062
enumName,
10581063
toUpperFirstChar(propertyName),
10591064
generateEnumFieldNotPresentCondition(token.version(), enumName, indent),

0 commit comments

Comments
 (0)