Skip to content

Commit 24982c5

Browse files
authored
Merge pull request #5426 from msupply-foundation/5383-android-12
5383 Android - Load Plugins after they've be registered properly
2 parents a08bb89 + b6939e6 commit 24982c5

File tree

4 files changed

+52
-18
lines changed

4 files changed

+52
-18
lines changed

client/packages/android/README.MD

+5-5
Original file line numberDiff line numberDiff line change
@@ -12,22 +12,22 @@ The UI is not bundled within Capacitor, it is served by the server the client co
1212
Before building the Android app, the Rust server library that allows us to run the mSupply server on the mobile device needs to be built.
1313
This requires a couple of steps.
1414

15-
- Install Android Studio
15+
- Install Android Studio (Ladybug at time of writing 15/11/24)
1616
- Install NDK (26.1.10909125 at the time of writing on the 8/4/24)
1717

1818
![omSupply Android NDK](./doc/omSupply_android_ndk.png)
1919

20-
Currently, we support two Android architectures;
20+
Currently, we support only 1 Android architecture (64bit);
2121

2222
| rust target | android ABI |
23-
| ----------------------- | ----------- |
2423
| aarch64-linux-android | arm64-v8a |
25-
| armv7-linux-androideabi | armeabi-v7a |
24+
| ----------------------- | ----------- |
25+
2626

2727
To add the required build targets to Rust run:
2828

2929
```bash
30-
rustup target add aarch64-linux-android && rustup target add armv7-linux-androideabi
30+
rustup target add aarch64-linux-android
3131
```
3232

3333
Next we have to tell Rust where to find the Android NDK binaries required to link the server library.

client/packages/android/app/src/main/java/org/openmsupply/client/ExtendedWebViewClient.java

+29-12
Original file line numberDiff line numberDiff line change
@@ -11,16 +11,24 @@
1111

1212
import java.util.Arrays;
1313
import java.util.List;
14+
import java.util.ArrayList;
15+
16+
1417

1518
public class ExtendedWebViewClient extends BridgeWebViewClient {
1619
Bridge bridge;
1720
String jsInject;
1821

1922
public ExtendedWebViewClient(Bridge bridge) {
2023
super(bridge);
21-
2224
this.bridge = bridge;
23-
this.jsInject = this.generatePluginScript();
25+
}
26+
27+
public void loadJsInject() {
28+
if(this.jsInject == null) {
29+
Logger.debug("Generating JS");
30+
this.jsInject = this.generatePluginScript();
31+
}
2432
}
2533

2634
// Have to manually inject Capacitor JS, this typically happens in
@@ -31,26 +39,35 @@ public ExtendedWebViewClient(Bridge bridge) {
3139
public void onPageStarted(WebView webView, String url, Bitmap favicon) {
3240
if (url.startsWith("data:text")) return;
3341

42+
// Just incase the js hasn't been generated yet, generate it here.
43+
this.loadJsInject();
44+
3445
if(this.jsInject != null) {
46+
Logger.debug("injecting JS");
3547
// .post to run on UI thread
3648
webView.post(() -> webView.evaluateJavascript(this.jsInject, null));
49+
} else {
50+
Logger.error("JS not generated, not injecting");
51+
webView.post(() -> webView.evaluateJavascript("alert('Error unable to load javascript to inject. Please contact mSupply Support for assistance.')", null));
3752
}
3853
}
3954

4055
String generatePluginScript() {
4156
// TODO make sure this is only injected for pages in native bundle
4257
// There is no way to get the full list of plugins from bridge, use 'debug' and
4358
// see what plugins to add
44-
List<PluginHandle> pluginList = Arrays.asList(
45-
bridge.getPlugin("NativeApi"),
46-
bridge.getPlugin("Keyboard"),
47-
bridge.getPlugin("WebView"),
48-
bridge.getPlugin("BarcodeScanner"),
49-
bridge.getPlugin("Preferences"),
50-
bridge.getPlugin("KeepAwake"),
51-
bridge.getPlugin("App"),
52-
bridge.getPlugin("Printer")
53-
);
59+
60+
// This function needs to run after plugins are registered, so can't be part of the constructor as order doesn't appear to be consistent.
61+
List<String> pluginNames = Arrays.asList("NativeApi","Keyboard", "WebView","BarcodeScanner","Preferences", "KeepAwake", "App", "Printer");
62+
List<PluginHandle> pluginList = new ArrayList<>();
63+
for (String pluginName : pluginNames) {
64+
PluginHandle plugin = bridge.getPlugin(pluginName);
65+
if (plugin == null) {
66+
Logger.error("Couldn't find plugin : " + pluginName);
67+
return null;
68+
}
69+
pluginList.add(plugin);
70+
}
5471

5572
try {
5673
// From Bridge.getJSInjector()

client/packages/android/app/src/main/java/org/openmsupply/client/NativeApi.java

+15-1
Original file line numberDiff line numberDiff line change
@@ -64,11 +64,13 @@ public class NativeApi extends Plugin implements NsdManager.DiscoveryListener {
6464
boolean isResolvingServer;
6565
boolean shouldRestartDiscovery;
6666

67+
CertWebViewClient client;
68+
6769
@Override
6870
public void load() {
6971
super.load();
7072

71-
CertWebViewClient client = new CertWebViewClient(this.getBridge(), this.getContext().getFilesDir(), this);
73+
client = new CertWebViewClient(this.getBridge(), this.getContext().getFilesDir(), this);
7274
bridge.setWebViewClient(client);
7375

7476
serversToResolve = new ArrayDeque<NsdServiceInfo>();
@@ -111,7 +113,19 @@ private void sleep(int delay) {
111113

112114
@Override
113115
protected void handleOnStart() {
116+
Logger.debug("NativeAPI.handleOnStart()");
114117
WebView webView = this.getBridge().getWebView();
118+
119+
// Normally javascript would be loaded by Capacitor by loading the generated javascript from WEBVIEW_SERVER_URL
120+
// However we'd get an SSL issue with this approach, so we need to generate it ourselves and inject it later.
121+
122+
// NOTE: There have been various timing issues with this javascript injection loading
123+
// We do the actual injection during onPageStarted in ExtendedWebViewClient
124+
// We call it here as well as in ExtendedWebViewClient as this gives more time for it to be generated before the webview loads
125+
// Potentially avoiding issues if it takes too long to generate.
126+
client.loadJsInject();
127+
128+
115129
// this method (handleOnStart) is called when resuming and switching to the app
116130
// the webView url will be DEFAULT_URL only on the initial load
117131
// so this test is a quick check to see if we should be redirecting to the

client/packages/android/app/src/main/java/org/openmsupply/client/RemoteServer.java

+3
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,7 @@
11
package org.openmsupply.client;
22

3+
import com.getcapacitor.Logger;
4+
35
public class RemoteServer {
46
static {
57
// This will load libremote_server_android, from app/src/main/jniLib/ directory
@@ -12,6 +14,7 @@ public RemoteServer() {
1214
}
1315

1416
public void start(int port, String filesDir, String cacheDir, String androidId) {
17+
Logger.info("Starting OMS Rust Server");
1518
startServer(port, filesDir, cacheDir, androidId);
1619
}
1720

0 commit comments

Comments
 (0)