From a868854ea9e2f5ac823bbcffe8a8ff342c59065b Mon Sep 17 00:00:00 2001 From: Akash Kava <39438041+ackava@users.noreply.github.com> Date: Thu, 15 Aug 2024 19:08:17 +0530 Subject: [PATCH] Serialization fixed --- NativeShell/Controls/NativeWebView.cs | 16 ++++++++- NativeShell/Core/GlobalClr.cs | 44 +++++++++++++++++++++++ NativeShell/Engine/JSContextExtensions.cs | 11 ++++-- NativeShell/NativeShell.csproj | 4 +-- NativeShell/Resources/NativeShell.js | 8 ++--- NativeShellApp/App.xaml.cs | 2 +- NativeShellApp/NativeShellApp.csproj | 9 +++-- yantra | 2 +- 8 files changed, 83 insertions(+), 13 deletions(-) diff --git a/NativeShell/Controls/NativeWebView.cs b/NativeShell/Controls/NativeWebView.cs index b5e6346..bfe711f 100644 --- a/NativeShell/Controls/NativeWebView.cs +++ b/NativeShell/Controls/NativeWebView.cs @@ -31,8 +31,22 @@ public NativeWebView() this.Clr = new GlobalClr(); Context["clr"] = Context.Marshal(Clr); + Context["serialize"] = Context.CreateFunction(1, (c, s) => { + try + { + var arg0 = s[0]; + var serialized = Clr.Serialize(arg0); + return Context.CreateString(serialized); + } catch (Exception error) + { + System.Diagnostics.Debug.WriteLine(error.ToString()); + return Context.CreateString("null"); + } + }, "serialize"); + Context["evalInPage"] = Context.CreateFunction(1, (c, s) => { - this.Eval(s.ToString()); + var script = s[0].ToString(); + this.Eval(script); return Context.Undefined; }, "sendToBrowser"); diff --git a/NativeShell/Core/GlobalClr.cs b/NativeShell/Core/GlobalClr.cs index b803191..9bd6640 100644 --- a/NativeShell/Core/GlobalClr.cs +++ b/NativeShell/Core/GlobalClr.cs @@ -21,6 +21,50 @@ public GlobalClr() return Type.GetType(typeName); } + public string Serialize(IJSValue value) + { + if (value.IsValueNull || value.IsUndefined) + { + return NullJson; + } + if (value.IsString) + { + return Serialize(value.ToString()!); + } + if (value.IsNumber) + { + return Serialize(value.DoubleValue!); + } + if (value.IsDate) + { + return Serialize(value.DateValue!); + } + if (value.IsBoolean) + { + return Serialize(value.BooleanValue!); + } + if (value.IsArray) + { + return Serialize(value.ToArray().Select((x) => SerializeAsync(x)).ToList()); + } + if (value.IsObject) + { + var list = new List(); + foreach (var item in value.Entries) + { + list.Add($"\"{item.Key}\": {SerializeAsync(item.Value)}"); + } + return "{" + string.Join(",", list) + "}"; + } + if (value.IsWrapped) + { + var v = value.Unwrap(); + throw new NotSupportedException($"You cannot transfer clr object to JavaScript"); + + } + return Serialize(value.ToString()); + } + public async Task SerializeAsync(IJSValue value) { if (value.IsValueNull || value.IsUndefined) diff --git a/NativeShell/Engine/JSContextExtensions.cs b/NativeShell/Engine/JSContextExtensions.cs index 3d39d44..efef536 100644 --- a/NativeShell/Engine/JSContextExtensions.cs +++ b/NativeShell/Engine/JSContextExtensions.cs @@ -460,10 +460,17 @@ public static IJSValue Marshal(this IJSContext context, object valueToCopy, Seri { if (valueToCopy == null) { - return null; + return context.Null; } if (valueToCopy is IJSValue jv) return jv; - var type = valueToCopy.GetType(); + + if (valueToCopy is Type type) + { + return context.CreateClass(type); + } + + type = valueToCopy.GetType(); + type = Nullable.GetUnderlyingType(type) ?? type; if (type.IsEnum) { diff --git a/NativeShell/NativeShell.csproj b/NativeShell/NativeShell.csproj index e966a4b..3698d35 100644 --- a/NativeShell/NativeShell.csproj +++ b/NativeShell/NativeShell.csproj @@ -33,8 +33,6 @@ - - all @@ -44,6 +42,8 @@ + + diff --git a/NativeShell/Resources/NativeShell.js b/NativeShell/Resources/NativeShell.js index 40c99b6..a7b5941 100644 --- a/NativeShell/Resources/NativeShell.js +++ b/NativeShell/Resources/NativeShell.js @@ -10,18 +10,18 @@ let result = ($code$).apply({ clr, evalInPage }, a); if (result && result.then) { result.then((r) => { - evalInPage(`window.nativeShell.on($rid$, ${JSON.stringify(r) || 1})`); + evalInPage(`window.nativeShell.on($rid$, ${serialize(r) || 1})`); }, (e) => { - evalInPage(`window.nativeShell.on($rid$, void 0, ${JSON.stringify(e.stack || e)})`); + evalInPage(`window.nativeShell.on($rid$, void 0, ${serialize(e.stack || e)})`); }); } else { setTimeout(() => - evalInPage(`window.nativeShell.on($rid$, ${JSON.stringify(r) || 1})`), + evalInPage(`window.nativeShell.on($rid$, ${serialize(result) || 1})`), 1); } } catch (error) { setTimeout(() => - evalInPage(`window.nativeShell.on($rid$, void 0, ${JSON.stringify(error.stack || error)})`), + evalInPage(`window.nativeShell.on($rid$, void 0, ${serialize(error.stack || error)})`), 1); } } diff --git a/NativeShellApp/App.xaml.cs b/NativeShellApp/App.xaml.cs index 5451766..a1c4a6b 100644 --- a/NativeShellApp/App.xaml.cs +++ b/NativeShellApp/App.xaml.cs @@ -11,7 +11,7 @@ public App() var mp = new NativeShellMainPage() { Url = "https://m.800casting.com/ProfileEditor/Agency" }; - mp.WebView.UserAgent = "800Casting-Hybrid-Mobile-App/1.0"; + mp.WebView.UserAgent = "Hybrid-Mobile-App/1.0 Android/1.1"; MainPage = mp; diff --git a/NativeShellApp/NativeShellApp.csproj b/NativeShellApp/NativeShellApp.csproj index e59918c..36b778b 100644 --- a/NativeShellApp/NativeShellApp.csproj +++ b/NativeShellApp/NativeShellApp.csproj @@ -53,6 +53,7 @@ + @@ -74,8 +75,12 @@ - - + + + + + + diff --git a/yantra b/yantra index 4ecaa82..b7a8061 160000 --- a/yantra +++ b/yantra @@ -1 +1 @@ -Subproject commit 4ecaa824b41a74928028ab81a06f2c3967589010 +Subproject commit b7a80610aa5b5e273cd722a5b9afc3b4e0f8a6a8