diff --git a/Browser/Adapters/CefBrowserComponent.cs b/Browser/Adapters/CefBrowserComponent.cs
index 69d7edb9..1c472cca 100644
--- a/Browser/Adapters/CefBrowserComponent.cs
+++ b/Browser/Adapters/CefBrowserComponent.cs
@@ -96,10 +96,6 @@ public void AttachBridgeObject(string name, object bridge) {
 			browser.JavascriptObjectRepository.Register(name, bridge, isAsync: true, BindingOptions.DefaultBinder);
 		}
 
-		public void RunFunction(string name, params object[] args) {
-			browser.BrowserCore.ExecuteScriptAsync(name, args);
-		}
-
 		public void RunScript(string identifier, string script) {
 			using IFrame frame = browser.GetMainFrame();
 			frame.ExecuteJavaScriptAsync(script, identifier, 1);
diff --git a/lib/TweetLib.Browser/Interfaces/IScriptExecutor.cs b/lib/TweetLib.Browser/Interfaces/IScriptExecutor.cs
index da73347e..d48765f7 100644
--- a/lib/TweetLib.Browser/Interfaces/IScriptExecutor.cs
+++ b/lib/TweetLib.Browser/Interfaces/IScriptExecutor.cs
@@ -1,6 +1,58 @@
-namespace TweetLib.Browser.Interfaces {
+using System;
+using System.Globalization;
+using System.Text;
+
+namespace TweetLib.Browser.Interfaces {
 	public interface IScriptExecutor {
-		void RunFunction(string name, params object[] args);
 		void RunScript(string identifier, string script);
 	}
+	
+	public static class ScriptExecutorExtensions {
+		public static void RunFunction(this IScriptExecutor executor, string name, params object?[] args) {
+			executor.RunScript("about:blank", GenerateJavaScriptFunctionCall(name, args));
+		}
+		
+		private static string GenerateJavaScriptFunctionCall(string name, object?[] args) {
+			var builder = new StringBuilder();
+			builder.Append(name);
+			builder.Append('(');
+
+			for (var index = 0; index < args.Length; index++) {
+				var obj = args[index];
+
+				switch (obj) {
+					case null:
+						builder.Append("null");
+						break;
+
+					case bool b:
+						builder.Append(b.ToString().ToLowerInvariant());
+						break;
+
+					case sbyte or byte or short or ushort or int or uint or long or ulong or float or double or decimal:
+						builder.Append(Convert.ToString(obj, CultureInfo.InvariantCulture));
+						break;
+
+					default:
+						var str = obj.ToString() ?? string.Empty;
+						var escaped = str.Replace("\\", "\\\\")
+						                 .Replace("'", "\\'")
+						                 .Replace("\t", "\\t")
+						                 .Replace("\r", "\\r")
+						                 .Replace("\n", "\\n");
+
+						builder.Append('\'');
+						builder.Append(escaped);
+						builder.Append('\'');
+						break;
+				}
+
+				if (index < args.Length - 1) {
+					builder.Append(',');
+				}
+			}
+
+			return builder.Append(");").ToString();
+		}
+	}
 }