Skip to content
This repository was archived by the owner on Feb 25, 2025. It is now read-only.

Commit 47409d5

Browse files
committed
Revert "Revert "Android Background Platform Channels (#29147)""
This reverts commit 7ed91e14ccc1f5ffc4cb13d1d37e27d370c8f7cd.
1 parent 770f4e6 commit 47409d5

35 files changed

+832
-182
lines changed

ci/licenses_golden/licenses_flutter

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -708,6 +708,7 @@ FILE: ../../../flutter/shell/common/persistent_cache_unittests.cc
708708
FILE: ../../../flutter/shell/common/pipeline.cc
709709
FILE: ../../../flutter/shell/common/pipeline.h
710710
FILE: ../../../flutter/shell/common/pipeline_unittests.cc
711+
FILE: ../../../flutter/shell/common/platform_message_handler.h
711712
FILE: ../../../flutter/shell/common/platform_view.cc
712713
FILE: ../../../flutter/shell/common/platform_view.h
713714
FILE: ../../../flutter/shell/common/pointer_data_dispatcher.cc
@@ -841,6 +842,7 @@ FILE: ../../../flutter/shell/platform/android/io/flutter/embedding/engine/Flutte
841842
FILE: ../../../flutter/shell/platform/android/io/flutter/embedding/engine/dart/DartExecutor.java
842843
FILE: ../../../flutter/shell/platform/android/io/flutter/embedding/engine/dart/DartMessenger.java
843844
FILE: ../../../flutter/shell/platform/android/io/flutter/embedding/engine/dart/PlatformMessageHandler.java
845+
FILE: ../../../flutter/shell/platform/android/io/flutter/embedding/engine/dart/PlatformTaskQueue.java
844846
FILE: ../../../flutter/shell/platform/android/io/flutter/embedding/engine/deferredcomponents/DeferredComponentManager.java
845847
FILE: ../../../flutter/shell/platform/android/io/flutter/embedding/engine/deferredcomponents/PlayStoreDeferredComponentManager.java
846848
FILE: ../../../flutter/shell/platform/android/io/flutter/embedding/engine/loader/ApplicationInfoLoader.java
@@ -938,6 +940,8 @@ FILE: ../../../flutter/shell/platform/android/jni/jni_mock_unittest.cc
938940
FILE: ../../../flutter/shell/platform/android/jni/platform_view_android_jni.cc
939941
FILE: ../../../flutter/shell/platform/android/jni/platform_view_android_jni.h
940942
FILE: ../../../flutter/shell/platform/android/library_loader.cc
943+
FILE: ../../../flutter/shell/platform/android/platform_message_handler_android.cc
944+
FILE: ../../../flutter/shell/platform/android/platform_message_handler_android.h
941945
FILE: ../../../flutter/shell/platform/android/platform_message_response_android.cc
942946
FILE: ../../../flutter/shell/platform/android/platform_message_response_android.h
943947
FILE: ../../../flutter/shell/platform/android/platform_view_android.cc

shell/common/BUILD.gn

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -73,6 +73,7 @@ source_set("common") {
7373
"engine.h",
7474
"pipeline.cc",
7575
"pipeline.h",
76+
"platform_message_handler.h",
7677
"platform_view.cc",
7778
"platform_view.h",
7879
"pointer_data_dispatcher.cc",
Lines changed: 39 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,39 @@
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+
#ifndef SHELL_COMMON_PLATFORM_MESSAGE_HANDLER_H_
6+
#define SHELL_COMMON_PLATFORM_MESSAGE_HANDLER_H_
7+
8+
#include <memory>
9+
10+
#include "flutter/lib/ui/window/platform_message.h"
11+
12+
namespace flutter {
13+
14+
/// An interface over the ability to handle PlatformMessages that are being sent
15+
/// from Flutter to the host platform.
16+
class PlatformMessageHandler {
17+
public:
18+
virtual ~PlatformMessageHandler() = default;
19+
20+
/// Ultimately sends the PlatformMessage to the host platform.
21+
/// This method is invoked on the ui thread.
22+
virtual void HandlePlatformMessage(
23+
std::unique_ptr<PlatformMessage> message) = 0;
24+
25+
/// Performs the return procedure for an associated call to
26+
/// HandlePlatformMessage.
27+
/// This method should be thread-safe and able to be invoked on any thread.
28+
virtual void InvokePlatformMessageResponseCallback(
29+
int response_id,
30+
std::unique_ptr<fml::Mapping> mapping) = 0;
31+
32+
/// Performs the return procedure for an associated call to
33+
/// HandlePlatformMessage where there is no return value.
34+
/// This method should be thread-safe and able to be invoked on any thread.
35+
virtual void InvokePlatformMessageEmptyResponseCallback(int response_id) = 0;
36+
};
37+
} // namespace flutter
38+
39+
#endif // SHELL_COMMON_PLATFORM_MESSAGE_HANDLER_H_

shell/common/platform_view.cc

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -184,4 +184,9 @@ PlatformView::CreateSnapshotSurfaceProducer() {
184184
return nullptr;
185185
}
186186

187+
std::shared_ptr<PlatformMessageHandler>
188+
PlatformView::GetPlatformMessageHandler() const {
189+
return nullptr;
190+
}
191+
187192
} // namespace flutter

shell/common/platform_view.h

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,7 @@
2222
#include "flutter/lib/ui/window/pointer_data_packet.h"
2323
#include "flutter/lib/ui/window/pointer_data_packet_converter.h"
2424
#include "flutter/lib/ui/window/viewport_metrics.h"
25+
#include "flutter/shell/common/platform_message_handler.h"
2526
#include "flutter/shell/common/pointer_data_dispatcher.h"
2627
#include "flutter/shell/common/vsync_waiter.h"
2728
#include "third_party/skia/include/core/SkSize.h"
@@ -810,6 +811,17 @@ class PlatformView {
810811
virtual std::unique_ptr<SnapshotSurfaceProducer>
811812
CreateSnapshotSurfaceProducer();
812813

814+
//--------------------------------------------------------------------------
815+
/// @brief Specifies a delegate that will receive PlatformMessages from
816+
/// Flutter to the host platform.
817+
///
818+
/// @details If this returns `null` that means PlatformMessages should be sent
819+
/// to the PlatformView. That is to protect legacy behavior, any embedder
820+
/// that wants to support executing Platform Channel handlers on background
821+
/// threads should be returing a thread-safe PlatformMessageHandler instead.
822+
virtual std::shared_ptr<PlatformMessageHandler> GetPlatformMessageHandler()
823+
const;
824+
813825
protected:
814826
PlatformView::Delegate& delegate_;
815827
const TaskRunners task_runners_;

shell/common/shell.cc

Lines changed: 17 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -625,6 +625,7 @@ bool Shell::Setup(std::unique_ptr<PlatformView> platform_view,
625625
}
626626

627627
platform_view_ = std::move(platform_view);
628+
platform_message_handler_ = platform_view_->GetPlatformMessageHandler();
628629
engine_ = std::move(engine);
629630
rasterizer_ = std::move(rasterizer);
630631
io_manager_ = std::move(io_manager);
@@ -1192,13 +1193,17 @@ void Shell::OnEngineHandlePlatformMessage(
11921193
return;
11931194
}
11941195

1195-
task_runners_.GetPlatformTaskRunner()->PostTask(
1196-
fml::MakeCopyable([view = platform_view_->GetWeakPtr(),
1197-
message = std::move(message)]() mutable {
1198-
if (view) {
1199-
view->HandlePlatformMessage(std::move(message));
1200-
}
1201-
}));
1196+
if (platform_message_handler_) {
1197+
platform_message_handler_->HandlePlatformMessage(std::move(message));
1198+
} else {
1199+
task_runners_.GetPlatformTaskRunner()->PostTask(
1200+
fml::MakeCopyable([view = platform_view_->GetWeakPtr(),
1201+
message = std::move(message)]() mutable {
1202+
if (view) {
1203+
view->HandlePlatformMessage(std::move(message));
1204+
}
1205+
}));
1206+
}
12021207
}
12031208

12041209
void Shell::HandleEngineSkiaMessage(std::unique_ptr<PlatformMessage> message) {
@@ -1867,4 +1872,9 @@ fml::TimePoint Shell::GetCurrentTimePoint() {
18671872
return fml::TimePoint::Now();
18681873
}
18691874

1875+
const std::shared_ptr<PlatformMessageHandler>&
1876+
Shell::GetPlatformMessageHandler() const {
1877+
return platform_message_handler_;
1878+
}
1879+
18701880
} // namespace flutter

shell/common/shell.h

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -395,6 +395,12 @@ class Shell final : public PlatformView::Delegate,
395395
/// @see `CreateCompatibleGenerator`
396396
void RegisterImageDecoder(ImageGeneratorFactory factory, int32_t priority);
397397

398+
//----------------------------------------------------------------------------
399+
/// @brief Returns the delegate object that handles PlatformMessage's from
400+
/// Flutter to the host platform (and its responses).
401+
const std::shared_ptr<PlatformMessageHandler>& GetPlatformMessageHandler()
402+
const;
403+
398404
private:
399405
using ServiceProtocolHandler =
400406
std::function<bool(const ServiceProtocol::Handler::ServiceProtocolMap&,
@@ -412,6 +418,7 @@ class Shell final : public PlatformView::Delegate,
412418
std::unique_ptr<ShellIOManager> io_manager_; // on IO task runner
413419
std::shared_ptr<fml::SyncSwitch> is_gpu_disabled_sync_switch_;
414420
std::shared_ptr<VolatilePathTracker> volatile_path_tracker_;
421+
std::shared_ptr<PlatformMessageHandler> platform_message_handler_;
415422

416423
fml::WeakPtr<Engine> weak_engine_; // to be shared across threads
417424
fml::TaskRunnerAffineWeakPtr<Rasterizer>

shell/common/shell_test.cc

Lines changed: 18 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -325,7 +325,8 @@ std::unique_ptr<Shell> ShellTest::CreateShell(
325325
std::shared_ptr<ShellTestExternalViewEmbedder>
326326
shell_test_external_view_embedder,
327327
bool is_gpu_disabled,
328-
ShellTestPlatformView::BackendType rendering_backend) {
328+
ShellTestPlatformView::BackendType rendering_backend,
329+
Shell::CreateCallback<PlatformView> platform_view_create_callback) {
329330
const auto vsync_clock = std::make_shared<ShellTestVsyncClock>();
330331

331332
CreateVsyncWaiter create_vsync_waiter = [&]() {
@@ -338,29 +339,29 @@ std::unique_ptr<Shell> ShellTest::CreateShell(
338339
}
339340
};
340341

341-
Shell::CreateCallback<PlatformView> platfrom_view_create_callback =
342-
[vsync_clock, //
343-
&create_vsync_waiter, //
344-
shell_test_external_view_embedder, //
345-
rendering_backend //
346-
](Shell& shell) {
347-
return ShellTestPlatformView::Create(
348-
shell, //
349-
shell.GetTaskRunners(), //
350-
vsync_clock, //
351-
std::move(create_vsync_waiter), //
352-
rendering_backend, //
353-
shell_test_external_view_embedder //
354-
);
355-
};
342+
if (!platform_view_create_callback) {
343+
platform_view_create_callback = [vsync_clock, //
344+
&create_vsync_waiter, //
345+
shell_test_external_view_embedder, //
346+
rendering_backend //
347+
](Shell& shell) {
348+
return ShellTestPlatformView::Create(shell, //
349+
shell.GetTaskRunners(), //
350+
vsync_clock, //
351+
std::move(create_vsync_waiter), //
352+
rendering_backend, //
353+
shell_test_external_view_embedder //
354+
);
355+
};
356+
}
356357

357358
Shell::CreateCallback<Rasterizer> rasterizer_create_callback =
358359
[](Shell& shell) { return std::make_unique<Rasterizer>(shell); };
359360

360361
return Shell::Create(flutter::PlatformData(), //
361362
task_runners, //
362363
settings, //
363-
platfrom_view_create_callback, //
364+
platform_view_create_callback, //
364365
rasterizer_create_callback, //
365366
is_gpu_disabled //
366367
);

shell/common/shell_test.h

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -43,7 +43,9 @@ class ShellTest : public FixtureTest {
4343
shell_test_external_view_embedder = nullptr,
4444
bool is_gpu_disabled = false,
4545
ShellTestPlatformView::BackendType rendering_backend =
46-
ShellTestPlatformView::BackendType::kDefaultBackend);
46+
ShellTestPlatformView::BackendType::kDefaultBackend,
47+
Shell::CreateCallback<PlatformView> platform_view_create_callback =
48+
nullptr);
4749
void DestroyShell(std::unique_ptr<Shell> shell);
4850
void DestroyShell(std::unique_ptr<Shell> shell, TaskRunners task_runners);
4951
TaskRunners GetTaskRunnersForFixture();

shell/common/shell_unittests.cc

Lines changed: 70 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -45,6 +45,10 @@
4545

4646
namespace flutter {
4747
namespace testing {
48+
49+
using ::testing::_;
50+
using ::testing::Return;
51+
4852
namespace {
4953
class MockPlatformViewDelegate : public PlatformView::Delegate {
5054
MOCK_METHOD1(OnPlatformViewCreated, void(std::unique_ptr<Surface> surface));
@@ -119,6 +123,27 @@ class MockPlatformView : public PlatformView {
119123
MockPlatformView(MockPlatformViewDelegate& delegate, TaskRunners task_runners)
120124
: PlatformView(delegate, task_runners) {}
121125
MOCK_METHOD0(CreateRenderingSurface, std::unique_ptr<Surface>());
126+
MOCK_CONST_METHOD0(GetPlatformMessageHandler,
127+
std::shared_ptr<PlatformMessageHandler>());
128+
};
129+
130+
class MockPlatformMessageHandler : public PlatformMessageHandler {
131+
public:
132+
MOCK_METHOD1(HandlePlatformMessage,
133+
void(std::unique_ptr<PlatformMessage> message));
134+
MOCK_METHOD2(InvokePlatformMessageResponseCallback,
135+
void(int response_id, std::unique_ptr<fml::Mapping> mapping));
136+
MOCK_METHOD1(InvokePlatformMessageEmptyResponseCallback,
137+
void(int response_id));
138+
};
139+
140+
class MockPlatformMessageResponse : public PlatformMessageResponse {
141+
public:
142+
static fml::RefPtr<MockPlatformMessageResponse> Create() {
143+
return fml::AdoptRef(new MockPlatformMessageResponse());
144+
}
145+
MOCK_METHOD1(Complete, void(std::unique_ptr<fml::Mapping> data));
146+
MOCK_METHOD0(CompleteEmpty, void());
122147
};
123148
} // namespace
124149

@@ -3162,7 +3187,52 @@ TEST_F(ShellTest, UIWorkAfterOnPlatformViewDestroyed) {
31623187
shell->GetTaskRunners().GetUITaskRunner(),
31633188
[&ui_flush_latch]() { ui_flush_latch.Signal(); });
31643189
ui_flush_latch.Wait();
3190+
DestroyShell(std::move(shell));
3191+
}
31653192

3193+
TEST_F(ShellTest, UsesPlatformMessageHandler) {
3194+
TaskRunners task_runners = GetTaskRunnersForFixture();
3195+
auto settings = CreateSettingsForFixture();
3196+
MockPlatformViewDelegate platform_view_delegate;
3197+
auto platform_message_handler =
3198+
std::make_shared<MockPlatformMessageHandler>();
3199+
int message_id = 1;
3200+
EXPECT_CALL(*platform_message_handler, HandlePlatformMessage(_));
3201+
EXPECT_CALL(*platform_message_handler,
3202+
InvokePlatformMessageEmptyResponseCallback(message_id));
3203+
Shell::CreateCallback<PlatformView> platform_view_create_callback =
3204+
[&platform_view_delegate, task_runners,
3205+
platform_message_handler](flutter::Shell& shell) {
3206+
auto result = std::make_unique<MockPlatformView>(platform_view_delegate,
3207+
task_runners);
3208+
EXPECT_CALL(*result, GetPlatformMessageHandler())
3209+
.WillOnce(Return(platform_message_handler));
3210+
return result;
3211+
};
3212+
auto shell = CreateShell(
3213+
/*settings=*/std::move(settings),
3214+
/*task_runners=*/task_runners,
3215+
/*simulate_vsync=*/false,
3216+
/*shell_test_external_view_embedder=*/nullptr,
3217+
/*is_gpu_disabled=*/false,
3218+
/*rendering_backend=*/
3219+
ShellTestPlatformView::BackendType::kDefaultBackend,
3220+
/*platform_view_create_callback=*/platform_view_create_callback);
3221+
3222+
EXPECT_EQ(platform_message_handler, shell->GetPlatformMessageHandler());
3223+
PostSync(task_runners.GetUITaskRunner(), [&shell]() {
3224+
size_t data_size = 4;
3225+
fml::MallocMapping bytes =
3226+
fml::MallocMapping(static_cast<uint8_t*>(malloc(data_size)), data_size);
3227+
fml::RefPtr<MockPlatformMessageResponse> response =
3228+
MockPlatformMessageResponse::Create();
3229+
auto message = std::make_unique<PlatformMessage>(
3230+
/*channel=*/"foo", /*data=*/std::move(bytes), /*response=*/response);
3231+
(static_cast<Engine::Delegate*>(shell.get()))
3232+
->OnEngineHandlePlatformMessage(std::move(message));
3233+
});
3234+
shell->GetPlatformMessageHandler()
3235+
->InvokePlatformMessageEmptyResponseCallback(message_id);
31663236
DestroyShell(std::move(shell));
31673237
}
31683238

shell/platform/android/BUILD.gn

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -79,6 +79,8 @@ source_set("flutter_shell_native_src") {
7979
"flutter_main.cc",
8080
"flutter_main.h",
8181
"library_loader.cc",
82+
"platform_message_handler_android.cc",
83+
"platform_message_handler_android.h",
8284
"platform_message_response_android.cc",
8385
"platform_message_response_android.h",
8486
"platform_view_android.cc",
@@ -186,6 +188,7 @@ android_java_sources = [
186188
"io/flutter/embedding/engine/dart/DartExecutor.java",
187189
"io/flutter/embedding/engine/dart/DartMessenger.java",
188190
"io/flutter/embedding/engine/dart/PlatformMessageHandler.java",
191+
"io/flutter/embedding/engine/dart/PlatformTaskQueue.java",
189192
"io/flutter/embedding/engine/deferredcomponents/DeferredComponentManager.java",
190193
"io/flutter/embedding/engine/deferredcomponents/PlayStoreDeferredComponentManager.java",
191194
"io/flutter/embedding/engine/loader/ApplicationInfoLoader.java",

shell/platform/android/android_shell_holder.h

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,7 @@
1616
#include "flutter/shell/common/shell.h"
1717
#include "flutter/shell/common/thread_host.h"
1818
#include "flutter/shell/platform/android/jni/platform_view_android_jni.h"
19+
#include "flutter/shell/platform/android/platform_message_handler_android.h"
1920
#include "flutter/shell/platform/android/platform_view_android.h"
2021

2122
namespace flutter {
@@ -96,6 +97,11 @@ class AndroidShellHolder {
9697

9798
void NotifyLowMemoryWarning();
9899

100+
const std::shared_ptr<PlatformMessageHandler>& GetPlatformMessageHandler()
101+
const {
102+
return shell_->GetPlatformMessageHandler();
103+
}
104+
99105
private:
100106
const flutter::Settings settings_;
101107
const std::shared_ptr<PlatformViewAndroidJNI> jni_facade_;

0 commit comments

Comments
 (0)