Flutter Engine
 
Loading...
Searching...
No Matches
fl_basic_message_channel_test.cc
Go to the documentation of this file.
1// Copyright 2013 The Flutter Authors. All rights reserved.
2// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
5// Included first as it collides with the X11 headers.
6#include "gtest/gtest.h"
7
9
13
14// Checks sending a message without a response works.
15// MOCK_ENGINE_PROC is leaky by design
16// NOLINTBEGIN(clang-analyzer-core.StackAddressEscape)
17TEST(FlBasicMessageChannelTest, SendMessageWithoutResponse) {
18 g_autoptr(FlMockBinaryMessenger) messenger = fl_mock_binary_messenger_new();
19 gboolean called = FALSE;
21 messenger, "test",
22 [](FlMockBinaryMessenger* messenger, GTask* task, FlValue* message,
23 gpointer user_data) {
24 gboolean* called = static_cast<gboolean*>(user_data);
25 *called = TRUE;
26
27 EXPECT_NE(message, nullptr);
29 EXPECT_STREQ(fl_value_get_string(message), "Marco!");
30
31 // No response.
32 return static_cast<FlValue*>(nullptr);
33 },
34 &called);
35
36 g_autoptr(FlStandardMessageCodec) codec = fl_standard_message_codec_new();
37 g_autoptr(FlBasicMessageChannel) channel = fl_basic_message_channel_new(
38 FL_BINARY_MESSENGER(messenger), "test", FL_MESSAGE_CODEC(codec));
40 fl_basic_message_channel_send(channel, message, nullptr, nullptr, nullptr);
41
42 EXPECT_TRUE(called);
43}
44// NOLINTEND(clang-analyzer-core.StackAddressEscape)
45
46// Checks sending a message with a response works.
47TEST(FlBasicMessageChannelTest, SendMessageWithResponse) {
48 g_autoptr(GMainLoop) loop = g_main_loop_new(nullptr, 0);
49
50 g_autoptr(FlMockBinaryMessenger) messenger = fl_mock_binary_messenger_new();
52 messenger, "test",
53 [](FlMockBinaryMessenger* messenger, GTask* task, FlValue* message,
54 gpointer user_data) {
55 EXPECT_NE(message, nullptr);
57 EXPECT_STREQ(fl_value_get_string(message), "Marco!");
58
59 return fl_value_new_string("Polo!");
60 },
61 nullptr);
62
63 g_autoptr(FlStandardMessageCodec) codec = fl_standard_message_codec_new();
64 g_autoptr(FlBasicMessageChannel) channel = fl_basic_message_channel_new(
65 FL_BINARY_MESSENGER(messenger), "test", FL_MESSAGE_CODEC(codec));
68 channel, message, nullptr,
69 [](GObject* object, GAsyncResult* result, gpointer user_data) {
70 g_autoptr(GError) error = nullptr;
72 FL_BASIC_MESSAGE_CHANNEL(object), result, &error);
73 EXPECT_NE(message, nullptr);
74 EXPECT_EQ(error, nullptr);
75
77 EXPECT_STREQ(fl_value_get_string(message), "Polo!");
78
79 g_main_loop_quit(static_cast<GMainLoop*>(user_data));
80 },
81 loop);
82
83 g_main_loop_run(loop);
84}
85
86// Checks the engine reporting a send failure is handled.
87TEST(FlBasicMessageChannelTest, SendFailure) {
88 g_autoptr(GMainLoop) loop = g_main_loop_new(nullptr, 0);
89
90 g_autoptr(FlMockBinaryMessenger) messenger = fl_mock_binary_messenger_new();
91 fl_mock_binary_messenger_set_error_channel(messenger, "test", 42, "Error");
92
93 g_autoptr(FlStandardMessageCodec) codec = fl_standard_message_codec_new();
94 g_autoptr(FlBasicMessageChannel) channel = fl_basic_message_channel_new(
95 FL_BINARY_MESSENGER(messenger), "test", FL_MESSAGE_CODEC(codec));
98 channel, message, nullptr,
99 [](GObject* object, GAsyncResult* result, gpointer user_data) {
100 g_autoptr(GError) error = nullptr;
102 FL_BASIC_MESSAGE_CHANNEL(object), result, &error);
103 EXPECT_EQ(message, nullptr);
104 EXPECT_NE(error, nullptr);
105 EXPECT_EQ(error->code, 42);
106 EXPECT_STREQ(error->message, "Error");
107
108 g_main_loop_quit(static_cast<GMainLoop*>(user_data));
109 },
110 loop);
111
112 g_main_loop_run(loop);
113}
114
115// Checks the shell able to receive and respond to messages from the engine.
116TEST(FlBasicMessageChannelTest, ReceiveMessage) {
117 g_autoptr(FlMockBinaryMessenger) messenger = fl_mock_binary_messenger_new();
118
119 // Listen for messages from the engine.
120 g_autoptr(FlStandardMessageCodec) codec = fl_standard_message_codec_new();
121 g_autoptr(FlBasicMessageChannel) messages_channel =
122 fl_basic_message_channel_new(FL_BINARY_MESSENGER(messenger), "test",
123 FL_MESSAGE_CODEC(codec));
125 messages_channel,
126 [](FlBasicMessageChannel* channel, FlValue* message,
127 FlBasicMessageChannelResponseHandle* response_handle,
128 gpointer user_data) {
129 EXPECT_NE(message, nullptr);
131 EXPECT_STREQ(fl_value_get_string(message), "Marco!");
132
133 g_autoptr(GError) error = nullptr;
134 g_autoptr(FlValue) response = fl_value_new_string("Polo!");
135 EXPECT_TRUE(fl_basic_message_channel_respond(channel, response_handle,
136 response, &error));
137 EXPECT_EQ(error, nullptr);
138 },
139 nullptr, nullptr);
140
141 // Trigger the engine to send a message.
143 gboolean called = FALSE;
145 messenger, "test", message,
146 [](FlMockBinaryMessenger* messenger, FlValue* response,
147 gpointer user_data) {
148 gboolean* called = static_cast<gboolean*>(user_data);
149 *called = TRUE;
150
151 EXPECT_NE(response, nullptr);
152 EXPECT_EQ(fl_value_get_type(response), FL_VALUE_TYPE_STRING);
153 EXPECT_STREQ(fl_value_get_string(response), "Polo!");
154 },
155 &called);
156
157 EXPECT_TRUE(called);
158}
159
160// Checks sending a null message with a response works.
161TEST(FlBasicMessageChannelTest, SendNullMessageWithResponse) {
162 g_autoptr(GMainLoop) loop = g_main_loop_new(nullptr, 0);
163
164 g_autoptr(FlMockBinaryMessenger) messenger = fl_mock_binary_messenger_new();
166 messenger, "test",
167 [](FlMockBinaryMessenger* messenger, GTask* task, FlValue* message,
168 gpointer user_data) { return fl_value_new_null(); },
169 nullptr);
170
171 g_autoptr(FlStandardMessageCodec) codec = fl_standard_message_codec_new();
172 g_autoptr(FlBasicMessageChannel) channel = fl_basic_message_channel_new(
173 FL_BINARY_MESSENGER(messenger), "test", FL_MESSAGE_CODEC(codec));
175 channel, nullptr, nullptr,
176 [](GObject* object, GAsyncResult* result, gpointer user_data) {
177 g_autoptr(GError) error = nullptr;
179 FL_BASIC_MESSAGE_CHANNEL(object), result, &error);
180 EXPECT_NE(message, nullptr);
181 EXPECT_EQ(error, nullptr);
182
184
185 g_main_loop_quit(static_cast<GMainLoop*>(user_data));
186 },
187 loop);
188
189 g_main_loop_run(loop);
190}
191
192// Checks sending a message with a custom type generates an error.
193TEST(FlBasicMessageChannelTest, CustomType) {
194 g_autoptr(GMainLoop) loop = g_main_loop_new(nullptr, 0);
195
196 g_autoptr(FlMockBinaryMessenger) messenger = fl_mock_binary_messenger_new();
198 messenger, "test",
199 [](FlMockBinaryMessenger* messenger, GTask* task, FlValue* message,
200 gpointer user_data) { return fl_value_new_null(); },
201 nullptr);
202
203 g_autoptr(FlStandardMessageCodec) codec = fl_standard_message_codec_new();
204 g_autoptr(FlBasicMessageChannel) channel = fl_basic_message_channel_new(
205 FL_BINARY_MESSENGER(messenger), "test", FL_MESSAGE_CODEC(codec));
206 g_autoptr(FlValue) message = fl_value_new_custom(42, nullptr, nullptr);
208 channel, message, nullptr,
209 [](GObject* object, GAsyncResult* result, gpointer user_data) {
210 g_autoptr(GError) error = nullptr;
212 FL_BASIC_MESSAGE_CHANNEL(object), result, &error);
213 EXPECT_EQ(message, nullptr);
214 EXPECT_NE(error, nullptr);
215 EXPECT_STREQ(error->message, "Custom value not implemented");
216
217 g_main_loop_quit(static_cast<GMainLoop*>(user_data));
218 },
219 loop);
220
221 g_main_loop_run(loop);
222}
G_MODULE_EXPORT FlBasicMessageChannel * fl_basic_message_channel_new(FlBinaryMessenger *messenger, const gchar *name, FlMessageCodec *codec)
G_MODULE_EXPORT void fl_basic_message_channel_set_message_handler(FlBasicMessageChannel *self, FlBasicMessageChannelMessageHandler handler, gpointer user_data, GDestroyNotify destroy_notify)
G_MODULE_EXPORT gboolean fl_basic_message_channel_respond(FlBasicMessageChannel *self, FlBasicMessageChannelResponseHandle *response_handle, FlValue *message, GError **error)
G_MODULE_EXPORT FlValue * fl_basic_message_channel_send_finish(FlBasicMessageChannel *self, GAsyncResult *result, GError **error)
G_MODULE_EXPORT void fl_basic_message_channel_send(FlBasicMessageChannel *self, FlValue *message, GCancellable *cancellable, GAsyncReadyCallback callback, gpointer user_data)
TEST(FlBasicMessageChannelTest, SendMessageWithoutResponse)
g_autoptr(GMutexLocker) locker
return TRUE
void fl_mock_binary_messenger_set_error_channel(FlMockBinaryMessenger *self, const gchar *channel, gint code, const gchar *message)
const gchar * channel
void fl_mock_binary_messenger_send_standard_message(FlMockBinaryMessenger *self, const gchar *channel, FlValue *message, FlMockBinaryMessengerMessageCallback callback, gpointer user_data)
FlMockBinaryMessenger * fl_mock_binary_messenger_new()
void fl_mock_binary_messenger_set_standard_message_channel(FlMockBinaryMessenger *self, const gchar *channel, FlMockBinaryMessengerMessageChannelHandler handler, gpointer user_data)
G_BEGIN_DECLS GBytes * message
const uint8_t uint32_t uint32_t GError ** error
G_MODULE_EXPORT FlStandardMessageCodec * fl_standard_message_codec_new()
G_MODULE_EXPORT FlValue * fl_value_new_custom(int type, gconstpointer value, GDestroyNotify destroy_notify)
Definition fl_value.cc:374
G_MODULE_EXPORT FlValueType fl_value_get_type(FlValue *self)
Definition fl_value.cc:466
G_MODULE_EXPORT FlValue * fl_value_new_null()
Definition fl_value.cc:251
G_MODULE_EXPORT FlValue * fl_value_new_string(const gchar *value)
Definition fl_value.cc:276
G_MODULE_EXPORT const gchar * fl_value_get_string(FlValue *self)
Definition fl_value.cc:682
typedefG_BEGIN_DECLS struct _FlValue FlValue
Definition fl_value.h:42
@ FL_VALUE_TYPE_STRING
Definition fl_value.h:68
@ FL_VALUE_TYPE_NULL
Definition fl_value.h:64