Skip to content

Commit 9a94bfd

Browse files
authored
Fix unnecessary toList/fromList calls during encode/decode process (flutter#6426)
Fix unnecessary toList/fromList calls during encode/decode process. also makes some kotlin code more idiomatic. removes the ability to have collisions with the name `list`. fixes flutter#119351
1 parent 4efbbb5 commit 9a94bfd

File tree

48 files changed

+1309
-1357
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

48 files changed

+1309
-1357
lines changed

packages/pigeon/CHANGELOG.md

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,9 @@
1+
## 18.0.1
2+
3+
* Fixes unnecessary calls of `toList` and `fromList` when encoding/decoding data classes.
4+
* [kotlin] Changes to some code to make it more idiomatic.
5+
* Removes collisions with the word `list`.
6+
17
## 18.0.0
28

39
* Adds message channel suffix option to all APIs.

packages/pigeon/example/app/android/app/src/main/java/io/flutter/plugins/Messages.java

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -186,15 +186,15 @@ ArrayList<Object> toList() {
186186
return toListResult;
187187
}
188188

189-
static @NonNull MessageData fromList(@NonNull ArrayList<Object> list) {
189+
static @NonNull MessageData fromList(@NonNull ArrayList<Object> __pigeon_list) {
190190
MessageData pigeonResult = new MessageData();
191-
Object name = list.get(0);
191+
Object name = __pigeon_list.get(0);
192192
pigeonResult.setName((String) name);
193-
Object description = list.get(1);
193+
Object description = __pigeon_list.get(1);
194194
pigeonResult.setDescription((String) description);
195-
Object code = list.get(2);
195+
Object code = __pigeon_list.get(2);
196196
pigeonResult.setCode(Code.values()[(int) code]);
197-
Object data = list.get(3);
197+
Object data = __pigeon_list.get(3);
198198
pigeonResult.setData((Map<String, String>) data);
199199
return pigeonResult;
200200
}

packages/pigeon/example/app/android/app/src/main/kotlin/dev/flutter/pigeon_example_app/Messages.g.kt

Lines changed: 24 additions & 26 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@
33
// found in the LICENSE file.
44
// Autogenerated from Pigeon, do not edit directly.
55
// See also: https://pub.dev/packages/pigeon
6+
@file:Suppress("UNCHECKED_CAST", "ArrayInDataClass")
67

78
import android.util.Log
89
import io.flutter.plugin.common.BasicMessageChannel
@@ -17,10 +18,10 @@ private fun wrapResult(result: Any?): List<Any?> {
1718
}
1819

1920
private fun wrapError(exception: Throwable): List<Any?> {
20-
if (exception is FlutterError) {
21-
return listOf(exception.code, exception.message, exception.details)
21+
return if (exception is FlutterError) {
22+
listOf(exception.code, exception.message, exception.details)
2223
} else {
23-
return listOf(
24+
listOf(
2425
exception.javaClass.simpleName,
2526
exception.toString(),
2627
"Cause: " + exception.cause + ", Stacktrace: " + Log.getStackTraceString(exception))
@@ -64,12 +65,12 @@ data class MessageData(
6465
val data: Map<String?, String?>
6566
) {
6667
companion object {
67-
@Suppress("UNCHECKED_CAST")
68-
fun fromList(list: List<Any?>): MessageData {
69-
val name = list[0] as String?
70-
val description = list[1] as String?
71-
val code = Code.ofRaw(list[2] as Int)!!
72-
val data = list[3] as Map<String?, String?>
68+
@Suppress("LocalVariableName")
69+
fun fromList(__pigeon_list: List<Any?>): MessageData {
70+
val name = __pigeon_list[0] as String?
71+
val description = __pigeon_list[1] as String?
72+
val code = Code.ofRaw(__pigeon_list[2] as Int)!!
73+
val data = __pigeon_list[3] as Map<String?, String?>
7374
return MessageData(name, description, code, data)
7475
}
7576
}
@@ -84,7 +85,6 @@ data class MessageData(
8485
}
8586
}
8687

87-
@Suppress("UNCHECKED_CAST")
8888
private object ExampleHostApiCodec : StandardMessageCodec() {
8989
override fun readValueOfType(type: Byte, buffer: ByteBuffer): Any? {
9090
return when (type) {
@@ -118,7 +118,6 @@ interface ExampleHostApi {
118118
/** The codec used by ExampleHostApi. */
119119
val codec: MessageCodec<Any?> by lazy { ExampleHostApiCodec }
120120
/** Sets up an instance of `ExampleHostApi` to handle messages through the `binaryMessenger`. */
121-
@Suppress("UNCHECKED_CAST")
122121
fun setUp(
123122
binaryMessenger: BinaryMessenger,
124123
api: ExampleHostApi?,
@@ -134,12 +133,12 @@ interface ExampleHostApi {
134133
codec)
135134
if (api != null) {
136135
channel.setMessageHandler { _, reply ->
137-
var wrapped: List<Any?>
138-
try {
139-
wrapped = listOf<Any?>(api.getHostLanguage())
140-
} catch (exception: Throwable) {
141-
wrapped = wrapError(exception)
142-
}
136+
val wrapped: List<Any?> =
137+
try {
138+
listOf<Any?>(api.getHostLanguage())
139+
} catch (exception: Throwable) {
140+
wrapError(exception)
141+
}
143142
reply.reply(wrapped)
144143
}
145144
} else {
@@ -155,14 +154,14 @@ interface ExampleHostApi {
155154
if (api != null) {
156155
channel.setMessageHandler { message, reply ->
157156
val args = message as List<Any?>
158-
val aArg = args[0].let { if (it is Int) it.toLong() else it as Long }
159-
val bArg = args[1].let { if (it is Int) it.toLong() else it as Long }
160-
var wrapped: List<Any?>
161-
try {
162-
wrapped = listOf<Any?>(api.add(aArg, bArg))
163-
} catch (exception: Throwable) {
164-
wrapped = wrapError(exception)
165-
}
157+
val aArg = args[0].let { num -> if (num is Int) num.toLong() else num as Long }
158+
val bArg = args[1].let { num -> if (num is Int) num.toLong() else num as Long }
159+
val wrapped: List<Any?> =
160+
try {
161+
listOf<Any?>(api.add(aArg, bArg))
162+
} catch (exception: Throwable) {
163+
wrapError(exception)
164+
}
166165
reply.reply(wrapped)
167166
}
168167
} else {
@@ -197,7 +196,6 @@ interface ExampleHostApi {
197196
}
198197
}
199198
/** Generated class from Pigeon that represents Flutter messages that can be called from Kotlin. */
200-
@Suppress("UNCHECKED_CAST")
201199
class MessageFlutterApi(
202200
private val binaryMessenger: BinaryMessenger,
203201
private val messageChannelSuffix: String = ""

packages/pigeon/example/app/ios/Runner/Messages.g.swift

Lines changed: 6 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -60,11 +60,12 @@ struct MessageData {
6060
var code: Code
6161
var data: [String?: String?]
6262

63-
static func fromList(_ list: [Any?]) -> MessageData? {
64-
let name: String? = nilOrValue(list[0])
65-
let description: String? = nilOrValue(list[1])
66-
let code = Code(rawValue: list[2] as! Int)!
67-
let data = list[3] as! [String?: String?]
63+
// swift-format-ignore: AlwaysUseLowerCamelCase
64+
static func fromList(_ __pigeon_list: [Any?]) -> MessageData? {
65+
let name: String? = nilOrValue(__pigeon_list[0])
66+
let description: String? = nilOrValue(__pigeon_list[1])
67+
let code = Code(rawValue: __pigeon_list[2] as! Int)!
68+
let data = __pigeon_list[3] as! [String?: String?]
6869

6970
return MessageData(
7071
name: name,

packages/pigeon/lib/ast.dart

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -518,7 +518,7 @@ class TypeDeclaration {
518518
@override
519519
String toString() {
520520
final String typeArgumentsStr =
521-
typeArguments.isEmpty ? '' : 'typeArguments:$typeArguments';
521+
typeArguments.isEmpty ? '' : ' typeArguments:$typeArguments';
522522
return '(TypeDeclaration baseName:$baseName isNullable:$isNullable$typeArgumentsStr isEnum:$isEnum isClass:$isClass isProxyApi:$isProxyApi)';
523523
}
524524
}

packages/pigeon/lib/cpp_generator.dart

Lines changed: 34 additions & 29 deletions
Original file line numberDiff line numberDiff line change
@@ -787,8 +787,12 @@ class CppSourceGenerator extends StructuredGenerator<CppOptions> {
787787
final HostDatatype hostDatatype =
788788
getFieldHostDatatype(field, _shortBaseCppTypeForBuiltinDartType);
789789
final String encodableValue = _wrappedHostApiArgumentExpression(
790-
root, _makeInstanceVariableName(field), field.type, hostDatatype,
791-
preSerializeClasses: true);
790+
root,
791+
_makeInstanceVariableName(field),
792+
field.type,
793+
hostDatatype,
794+
true,
795+
);
792796
indent.writeln('list.push_back($encodableValue);');
793797
}
794798
indent.writeln('return list;');
@@ -815,11 +819,8 @@ class CppSourceGenerator extends StructuredGenerator<CppOptions> {
815819
} else {
816820
final HostDatatype hostDatatype =
817821
getFieldHostDatatype(field, _shortBaseCppTypeForBuiltinDartType);
818-
if (!hostDatatype.isBuiltin &&
819-
root.classes
820-
.map((Class x) => x.name)
821-
.contains(field.type.baseName)) {
822-
return '${hostDatatype.datatype}::FromEncodableList(std::get<EncodableList>($encodable))';
822+
if (field.type.isClass) {
823+
return _classReferenceFromEncodableValue(hostDatatype, encodable);
823824
} else {
824825
return 'std::get<${hostDatatype.datatype}>($encodable)';
825826
}
@@ -960,8 +961,12 @@ class CppSourceGenerator extends StructuredGenerator<CppOptions> {
960961
indent.addScoped('EncodableValue(EncodableList{', '});', () {
961962
for (final _HostNamedType param in hostParameters) {
962963
final String encodedArgument = _wrappedHostApiArgumentExpression(
963-
root, param.name, param.originalType, param.hostType,
964-
preSerializeClasses: false);
964+
root,
965+
param.name,
966+
param.originalType,
967+
param.hostType,
968+
false,
969+
);
965970
indent.writeln('$encodedArgument,');
966971
}
967972
});
@@ -1452,27 +1457,20 @@ ${prefix}reply(EncodableValue(std::move(wrapped)));''';
14521457

14531458
/// Returns the expression to create an EncodableValue from a host API argument
14541459
/// with the given [variableName] and types.
1455-
///
1456-
/// If [preSerializeClasses] is true, custom classes will be returned as
1457-
/// encodable lists rather than CustomEncodableValues; see
1458-
/// https://github.com/flutter/flutter/issues/119351 for why this is currently
1459-
/// needed.
1460-
String _wrappedHostApiArgumentExpression(Root root, String variableName,
1461-
TypeDeclaration dartType, HostDatatype hostType,
1462-
{required bool preSerializeClasses}) {
1460+
String _wrappedHostApiArgumentExpression(
1461+
Root root,
1462+
String variableName,
1463+
TypeDeclaration dartType,
1464+
HostDatatype hostType,
1465+
bool isNestedClass,
1466+
) {
14631467
final String encodableValue;
14641468
if (!hostType.isBuiltin &&
14651469
root.classes.any((Class c) => c.name == dartType.baseName)) {
1466-
if (preSerializeClasses) {
1467-
final String operator =
1468-
hostType.isNullable || _isPointerField(hostType) ? '->' : '.';
1469-
encodableValue =
1470-
'EncodableValue($variableName${operator}ToEncodableList())';
1471-
} else {
1472-
final String nonNullValue =
1473-
hostType.isNullable ? '*$variableName' : variableName;
1474-
encodableValue = 'CustomEncodableValue($nonNullValue)';
1475-
}
1470+
final String nonNullValue = hostType.isNullable || isNestedClass
1471+
? '*$variableName'
1472+
: variableName;
1473+
encodableValue = 'CustomEncodableValue($nonNullValue)';
14761474
} else if (!hostType.isBuiltin &&
14771475
root.enums.any((Enum e) => e.name == dartType.baseName)) {
14781476
final String nonNullValue =
@@ -1537,7 +1535,7 @@ ${prefix}reply(EncodableValue(std::move(wrapped)));''';
15371535
}
15381536
} else {
15391537
indent.writeln(
1540-
'const auto* $argName = &(std::any_cast<const ${hostType.datatype}&>(std::get<CustomEncodableValue>($encodableArgName)));');
1538+
'const auto* $argName = &(${_classReferenceFromEncodableValue(hostType, encodableArgName)});');
15411539
}
15421540
} else {
15431541
// Non-nullable arguments are either passed by value or reference, but the
@@ -1562,7 +1560,7 @@ ${prefix}reply(EncodableValue(std::move(wrapped)));''';
15621560
'const ${hostType.datatype}& $argName = (${hostType.datatype})$encodableArgName.LongValue();');
15631561
} else {
15641562
indent.writeln(
1565-
'const auto& $argName = std::any_cast<const ${hostType.datatype}&>(std::get<CustomEncodableValue>($encodableArgName));');
1563+
'const auto& $argName = ${_classReferenceFromEncodableValue(hostType, encodableArgName)};');
15661564
}
15671565
}
15681566
}
@@ -1573,6 +1571,13 @@ ${prefix}reply(EncodableValue(std::move(wrapped)));''';
15731571
String? _shortBaseCppTypeForBuiltinDartType(TypeDeclaration type) {
15741572
return _baseCppTypeForBuiltinDartType(type, includeFlutterNamespace: false);
15751573
}
1574+
1575+
/// Returns the code to extract a `const {type.datatype}&` from an EncodableValue
1576+
/// variable [variableName] that contains an instance of [type].
1577+
String _classReferenceFromEncodableValue(
1578+
HostDatatype type, String variableName) {
1579+
return 'std::any_cast<const ${type.datatype}&>(std::get<CustomEncodableValue>($variableName))';
1580+
}
15761581
}
15771582

15781583
/// Contains information about a host function argument.

0 commit comments

Comments
 (0)