diff --git a/packages/pigeon/CHANGELOG.md b/packages/pigeon/CHANGELOG.md index 2b4ad06c17..7aaf8f9d78 100644 --- a/packages/pigeon/CHANGELOG.md +++ b/packages/pigeon/CHANGELOG.md @@ -2,6 +2,7 @@ * Fixed Dart compilation for later versions that support null safety, opting out of it for now. +* Fixed nested types in the Java runtime. ## 0.1.6 diff --git a/packages/pigeon/lib/java_generator.dart b/packages/pigeon/lib/java_generator.dart index 0710bb09ed..9ad7a2380b 100644 --- a/packages/pigeon/lib/java_generator.dart +++ b/packages/pigeon/lib/java_generator.dart @@ -178,6 +178,9 @@ String _castObject(Field field, List classes, String varName) { getHostDatatype(field, classes, _javaTypeForDartType); if (field.dataType == 'int') { return '($varName == null) ? null : (($varName instanceof Integer) ? (Integer)$varName : (${hostDatatype.datatype})$varName)'; + } else if (!hostDatatype.isBuiltin && + classes.map((Class x) => x.name).contains(field.dataType)) { + return '${hostDatatype.datatype}.fromMap((HashMap)$varName)'; } else { return '(${hostDatatype.datatype})$varName'; } @@ -186,6 +189,8 @@ String _castObject(Field field, List classes, String varName) { /// Generates the ".java" file for the AST represented by [root] to [sink] with the /// provided [options]. void generateJava(JavaOptions options, Root root, StringSink sink) { + final Set rootClassNameSet = + root.classes.map((Class x) => x.name).toSet(); final Indent indent = Indent(sink); indent.writeln('// $generatedCodeWarning'); indent.writeln('// $seeAlsoWarning'); @@ -227,7 +232,16 @@ void generateJava(JavaOptions options, Root root, StringSink sink) { indent.writeln( 'HashMap toMapResult = new HashMap<>();'); for (Field field in klass.fields) { - indent.writeln('toMapResult.put("${field.name}", ${field.name});'); + final HostDatatype hostDatatype = + getHostDatatype(field, root.classes, _javaTypeForDartType); + String toWriteValue = ''; + if (!hostDatatype.isBuiltin && + rootClassNameSet.contains(field.dataType)) { + toWriteValue = '${field.name}.toMap()'; + } else { + toWriteValue = field.name; + } + indent.writeln('toMapResult.put("${field.name}", $toWriteValue);'); } indent.writeln('return toMapResult;'); }); diff --git a/packages/pigeon/test/java_generator_test.dart b/packages/pigeon/test/java_generator_test.dart index 7174c2b76a..11a582ab11 100644 --- a/packages/pigeon/test/java_generator_test.dart +++ b/packages/pigeon/test/java_generator_test.dart @@ -229,4 +229,35 @@ void main() { expect(code, contains('public static class Foobar')); expect(code, contains('private HashMap field1;')); }); + + test('gen nested', () { + final Class klass = Class() + ..name = 'Outer' + ..fields = [ + Field() + ..name = 'nested' + ..dataType = 'Nested' + ]; + final Class nestedClass = Class() + ..name = 'Nested' + ..fields = [ + Field() + ..name = 'data' + ..dataType = 'int' + ]; + final Root root = Root() + ..apis = [] + ..classes = [klass, nestedClass]; + final StringBuffer sink = StringBuffer(); + final JavaOptions javaOptions = JavaOptions(); + javaOptions.className = 'Messages'; + generateJava(javaOptions, root, sink); + final String code = sink.toString(); + expect(code, contains('public class Messages')); + expect(code, contains('public static class Outer')); + expect(code, contains('public static class Nested')); + expect(code, contains('private Nested nested;')); + expect(code, contains('Nested.fromMap((HashMap)nested);')); + expect(code, contains('put("nested", nested.toMap());')); + }); }