| Flutter Linux Embedder |

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
8 #include "flutter/shell/platform/linux/public/flutter_linux/fl_basic_message_channel.h"
9
10 #include "flutter/shell/platform/linux/public/flutter_linux/fl_message_codec.h"
11 #include "flutter/shell/platform/linux/public/flutter_linux/fl_standard_message_codec.h"
12 #include "flutter/shell/platform/linux/testing/fl_mock_binary_messenger.h"
13
14 // Checks sending a message without a response works.
15 // MOCK_ENGINE_PROC is leaky by design
16 // NOLINTBEGIN(clang-analyzer-core.StackAddressEscape)
17 TEST(FlBasicMessageChannelTest, SendMessageWithoutResponse) {
18 g_autoptr(FlMockBinaryMessenger) messenger = fl_mock_binary_messenger_new();
19 gboolean called = FALSE;
20 fl_mock_binary_messenger_set_standard_message_channel(
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);
28 EXPECT_EQ(fl_value_get_type(message), FL_VALUE_TYPE_STRING);
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));
39 g_autoptr(FlValue) message = fl_value_new_string("Marco!");
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.
47 TEST(FlBasicMessageChannelTest, SendMessageWithResponse) {
48 g_autoptr(GMainLoop) loop = g_main_loop_new(nullptr, 0);
49
50 g_autoptr(FlMockBinaryMessenger) messenger = fl_mock_binary_messenger_new();
51 fl_mock_binary_messenger_set_standard_message_channel(
52 messenger, "test",
53 [](FlMockBinaryMessenger* messenger, GTask* task, FlValue* message,
54 gpointer user_data) {
55 EXPECT_NE(message, nullptr);
56 EXPECT_EQ(fl_value_get_type(message), FL_VALUE_TYPE_STRING);
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));
66 g_autoptr(FlValue) message = fl_value_new_string("Marco!");
67 fl_basic_message_channel_send(
68 channel, message, nullptr,
69 [](GObject* object, GAsyncResult* result, gpointer user_data) {
70 g_autoptr(GError) error = nullptr;
71 g_autoptr(FlValue) message = fl_basic_message_channel_send_finish(
72 FL_BASIC_MESSAGE_CHANNEL(object), result, &error);
73 EXPECT_NE(message, nullptr);
74 EXPECT_EQ(error, nullptr);
75
76 EXPECT_EQ(fl_value_get_type(message), FL_VALUE_TYPE_STRING);
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.
87 TEST(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));
96 g_autoptr(FlValue) message = fl_value_new_string("Hello World!");
97 fl_basic_message_channel_send(
98 channel, message, nullptr,
99 [](GObject* object, GAsyncResult* result, gpointer user_data) {
100 g_autoptr(GError) error = nullptr;
101 g_autoptr(FlValue) message = fl_basic_message_channel_send_finish(
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.
116 TEST(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));
124 fl_basic_message_channel_set_message_handler(
125 messages_channel,
126 [](FlBasicMessageChannel* channel, FlValue* message,
127 FlBasicMessageChannelResponseHandle* response_handle,
128 gpointer user_data) {
129 EXPECT_NE(message, nullptr);
130 EXPECT_EQ(fl_value_get_type(message), FL_VALUE_TYPE_STRING);
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.
142 g_autoptr(FlValue) message = fl_value_new_string("Marco!");
143 gboolean called = FALSE;
144 fl_mock_binary_messenger_send_standard_message(
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.
161 TEST(FlBasicMessageChannelTest, SendNullMessageWithResponse) {
162 g_autoptr(GMainLoop) loop = g_main_loop_new(nullptr, 0);
163
164 g_autoptr(FlMockBinaryMessenger) messenger = fl_mock_binary_messenger_new();
165 fl_mock_binary_messenger_set_standard_message_channel(
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));
174 fl_basic_message_channel_send(
175 channel, nullptr, nullptr,
176 [](GObject* object, GAsyncResult* result, gpointer user_data) {
177 g_autoptr(GError) error = nullptr;
178 g_autoptr(FlValue) message = fl_basic_message_channel_send_finish(
179 FL_BASIC_MESSAGE_CHANNEL(object), result, &error);
180 EXPECT_NE(message, nullptr);
181 EXPECT_EQ(error, nullptr);
182
183 EXPECT_EQ(fl_value_get_type(message), FL_VALUE_TYPE_NULL);
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.
193 TEST(FlBasicMessageChannelTest, CustomType) {
194 g_autoptr(GMainLoop) loop = g_main_loop_new(nullptr, 0);
195
196 g_autoptr(FlMockBinaryMessenger) messenger = fl_mock_binary_messenger_new();
197 fl_mock_binary_messenger_set_standard_message_channel(
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);
207 fl_basic_message_channel_send(
208 channel, message, nullptr,
209 [](GObject* object, GAsyncResult* result, gpointer user_data) {
210 g_autoptr(GError) error = nullptr;
211 g_autoptr(FlValue) message = fl_basic_message_channel_send_finish(
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 }
fl_basic_message_channel_send_finish
G_MODULE_EXPORT FlValue * fl_basic_message_channel_send_finish(FlBasicMessageChannel *self, GAsyncResult *result, GError **error)
Definition: fl_basic_message_channel.cc:253
fl_basic_message_channel_set_message_handler
G_MODULE_EXPORT void fl_basic_message_channel_set_message_handler(FlBasicMessageChannel *self, FlBasicMessageChannelMessageHandler handler, gpointer user_data, GDestroyNotify destroy_notify)
Definition: fl_basic_message_channel.cc:176
fl_basic_message_channel_new
G_MODULE_EXPORT FlBasicMessageChannel * fl_basic_message_channel_new(FlBinaryMessenger *messenger, const gchar *name, FlMessageCodec *codec)
Definition: fl_basic_message_channel.cc:154
fl_basic_message_channel_respond
G_MODULE_EXPORT gboolean fl_basic_message_channel_respond(FlBasicMessageChannel *self, FlBasicMessageChannelResponseHandle *response_handle, FlValue *message, GError **error)
Definition: fl_basic_message_channel.cc:204
fl_basic_message_channel_send
G_MODULE_EXPORT void fl_basic_message_channel_send(FlBasicMessageChannel *self, FlValue *message, GCancellable *cancellable, GAsyncReadyCallback callback, gpointer user_data)
Definition: fl_basic_message_channel.cc:226
fl_basic_message_channel.h
TEST
TEST(FlBasicMessageChannelTest, SendMessageWithoutResponse)
Definition: fl_basic_message_channel_test.cc:17
g_autoptr
g_autoptr(GMutexLocker) locker
TRUE
return TRUE
Definition: fl_compositor_software.cc:68
user_data
G_BEGIN_DECLS G_MODULE_EXPORT FlValue gpointer user_data
Definition: fl_event_channel.h:90
fl_message_codec.h
error
const uint8_t uint32_t uint32_t GError ** error
Definition: fl_pixel_buffer_texture_test.cc:40
fl_standard_message_codec_new
G_MODULE_EXPORT FlStandardMessageCodec * fl_standard_message_codec_new()
Definition: fl_standard_message_codec.cc:637
fl_standard_message_codec.h
fl_value_new_custom
G_MODULE_EXPORT FlValue * fl_value_new_custom(int type, gconstpointer value, GDestroyNotify destroy_notify)
Definition: fl_value.cc:374
fl_value_new_string
G_MODULE_EXPORT FlValue * fl_value_new_string(const gchar *value)
Definition: fl_value.cc:276
fl_value_get_type
G_MODULE_EXPORT FlValueType fl_value_get_type(FlValue *self)
Definition: fl_value.cc:466
fl_value_new_null
G_MODULE_EXPORT FlValue * fl_value_new_null()
Definition: fl_value.cc:251
fl_value_get_string
G_MODULE_EXPORT const gchar * fl_value_get_string(FlValue *self)
Definition: fl_value.cc:682
FlValue
typedefG_BEGIN_DECLS struct _FlValue FlValue
Definition: fl_value.h:42
FL_VALUE_TYPE_STRING
@ FL_VALUE_TYPE_STRING
Definition: fl_value.h:68
FL_VALUE_TYPE_NULL
@ FL_VALUE_TYPE_NULL
Definition: fl_value.h:64