diff --git a/.vscode/launch.json b/.vscode/launch.json
index 87b70a760..810f84749 100644
--- a/.vscode/launch.json
+++ b/.vscode/launch.json
@@ -9,7 +9,8 @@
                 "<node_internals>/**"
             ],
             "env": {
-                "TRILIUM_ENV": "dev"
+                "TRILIUM_ENV": "dev",
+                "TRILIUM_DATA_DIR": "./data"
             },
             "outputCapture": "std",
             "program": "${workspaceFolder}/src/www"
diff --git a/dump-db/package-lock.json b/dump-db/package-lock.json
index 9b98e2f3d..509017062 100644
--- a/dump-db/package-lock.json
+++ b/dump-db/package-lock.json
@@ -387,9 +387,12 @@
       }
     },
     "node_modules/minimist": {
-      "version": "1.2.5",
-      "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.5.tgz",
-      "integrity": "sha512-FM9nNUYrRBAELZQT3xeZQ7fmMOBg6nWNmJKTcgsJeaLstP/UODVpGsr5OhXhhXg6f+qtJ8uiZ+PUxkDWcgIXLw=="
+      "version": "1.2.7",
+      "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.7.tgz",
+      "integrity": "sha512-bzfL1YUZsP41gmu/qjrEk0Q6i2ix/cVeAhbCbqH9u3zYutS1cLg00qhrD0M2MVdCcx4Sc0UpP2eBWo9rotpq6g==",
+      "funding": {
+        "url": "https://github.com/sponsors/ljharb"
+      }
     },
     "node_modules/mkdirp-classic": {
       "version": "0.5.3",
@@ -1163,9 +1166,9 @@
       "integrity": "sha512-z0yWI+4FDrrweS8Zmt4Ej5HdJmky15+L2e6Wgn3+iK5fWzb6T3fhNFq2+MeTRb064c6Wr4N/wv0DzQTjNzHNGQ=="
     },
     "minimist": {
-      "version": "1.2.5",
-      "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.5.tgz",
-      "integrity": "sha512-FM9nNUYrRBAELZQT3xeZQ7fmMOBg6nWNmJKTcgsJeaLstP/UODVpGsr5OhXhhXg6f+qtJ8uiZ+PUxkDWcgIXLw=="
+      "version": "1.2.7",
+      "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.7.tgz",
+      "integrity": "sha512-bzfL1YUZsP41gmu/qjrEk0Q6i2ix/cVeAhbCbqH9u3zYutS1cLg00qhrD0M2MVdCcx4Sc0UpP2eBWo9rotpq6g=="
     },
     "mkdirp-classic": {
       "version": "0.5.3",
diff --git a/package-lock.json b/package-lock.json
index a5fa39b34..dbb36afca 100644
--- a/package-lock.json
+++ b/package-lock.json
@@ -1,20 +1,21 @@
 {
   "name": "trilium",
-  "version": "0.58.0-beta",
+  "version": "0.58.2-beta",
   "lockfileVersion": 2,
   "requires": true,
   "packages": {
     "": {
       "name": "trilium",
-      "version": "0.58.0-beta",
+      "version": "0.58.2-beta",
       "hasInstallScript": true,
       "license": "AGPL-3.0-only",
       "dependencies": {
+        "@braintree/sanitize-url": "^6.0.2",
         "@electron/remote": "2.0.9",
         "@excalidraw/excalidraw": "0.13.0",
         "archiver": "5.3.1",
         "async-mutex": "0.4.0",
-        "axios": "1.2.1",
+        "axios": "1.2.2",
         "better-sqlite3": "7.4.5",
         "chokidar": "3.5.3",
         "cls-hooked": "4.2.2",
@@ -115,6 +116,11 @@
         "node": ">=6.9.0"
       }
     },
+    "node_modules/@braintree/sanitize-url": {
+      "version": "6.0.2",
+      "resolved": "https://registry.npmjs.org/@braintree/sanitize-url/-/sanitize-url-6.0.2.tgz",
+      "integrity": "sha512-Tbsj02wXCbqGmzdnXNk0SOF19ChhRU70BsroIi4Pm6Ehp56in6vch94mfbdQ17DozxkL3BAVjbZ4Qc1a0HFRAg=="
+    },
     "node_modules/@develar/schema-utils": {
       "version": "2.6.5",
       "resolved": "https://registry.npmjs.org/@develar/schema-utils/-/schema-utils-2.6.5.tgz",
@@ -807,6 +813,64 @@
         "regenerator-runtime": "^0.13.3"
       }
     },
+    "node_modules/@jridgewell/gen-mapping": {
+      "version": "0.3.2",
+      "resolved": "https://registry.npmjs.org/@jridgewell/gen-mapping/-/gen-mapping-0.3.2.tgz",
+      "integrity": "sha512-mh65xKQAzI6iBcFzwv28KVWSmCkdRBWoOh+bYQGW3+6OZvbbN3TqMGo5hqYxQniRcH9F2VZIoJCm4pa3BPDK/A==",
+      "dev": true,
+      "dependencies": {
+        "@jridgewell/set-array": "^1.0.1",
+        "@jridgewell/sourcemap-codec": "^1.4.10",
+        "@jridgewell/trace-mapping": "^0.3.9"
+      },
+      "engines": {
+        "node": ">=6.0.0"
+      }
+    },
+    "node_modules/@jridgewell/resolve-uri": {
+      "version": "3.1.0",
+      "resolved": "https://registry.npmjs.org/@jridgewell/resolve-uri/-/resolve-uri-3.1.0.tgz",
+      "integrity": "sha512-F2msla3tad+Mfht5cJq7LSXcdudKTWCVYUgw6pLFOOHSTtZlj6SWNYAp+AhuqLmWdBO2X5hPrLcu8cVP8fy28w==",
+      "dev": true,
+      "engines": {
+        "node": ">=6.0.0"
+      }
+    },
+    "node_modules/@jridgewell/set-array": {
+      "version": "1.1.2",
+      "resolved": "https://registry.npmjs.org/@jridgewell/set-array/-/set-array-1.1.2.tgz",
+      "integrity": "sha512-xnkseuNADM0gt2bs+BvhO0p78Mk762YnZdsuzFV018NoG1Sj1SCQvpSqa7XUaTam5vAGasABV9qXASMKnFMwMw==",
+      "dev": true,
+      "engines": {
+        "node": ">=6.0.0"
+      }
+    },
+    "node_modules/@jridgewell/source-map": {
+      "version": "0.3.2",
+      "resolved": "https://registry.npmjs.org/@jridgewell/source-map/-/source-map-0.3.2.tgz",
+      "integrity": "sha512-m7O9o2uR8k2ObDysZYzdfhb08VuEml5oWGiosa1VdaPZ/A6QyPkAJuwN0Q1lhULOf6B7MtQmHENS743hWtCrgw==",
+      "dev": true,
+      "dependencies": {
+        "@jridgewell/gen-mapping": "^0.3.0",
+        "@jridgewell/trace-mapping": "^0.3.9"
+      }
+    },
+    "node_modules/@jridgewell/sourcemap-codec": {
+      "version": "1.4.14",
+      "resolved": "https://registry.npmjs.org/@jridgewell/sourcemap-codec/-/sourcemap-codec-1.4.14.tgz",
+      "integrity": "sha512-XPSJHWmi394fuUuzDnGz1wiKqWfo1yXecHQMRf2l6hztTO+nPru658AyDngaBe7isIxEkRsPR3FZh+s7iVa4Uw==",
+      "dev": true
+    },
+    "node_modules/@jridgewell/trace-mapping": {
+      "version": "0.3.17",
+      "resolved": "https://registry.npmjs.org/@jridgewell/trace-mapping/-/trace-mapping-0.3.17.tgz",
+      "integrity": "sha512-MCNzAp77qzKca9+W/+I0+sEpaUnZoeasnghNeVc41VZCEKaCH73Vq3BZZ/SzWIgrqE4H4ceI+p+b6C0mHf9T4g==",
+      "dev": true,
+      "dependencies": {
+        "@jridgewell/resolve-uri": "3.1.0",
+        "@jridgewell/sourcemap-codec": "1.4.14"
+      }
+    },
     "node_modules/@jsdoc/salty": {
       "version": "0.2.1",
       "resolved": "https://registry.npmjs.org/@jsdoc/salty/-/salty-0.2.1.tgz",
@@ -1877,9 +1941,9 @@
       "integrity": "sha512-ReZxvNHIOv88FlT7rxcXIIC0fPt4KZqZbOlivyWtXLt8ESx84zd3kMC6iK5jVeS2qt+g7ftS7ye4fi06X5rtRQ=="
     },
     "node_modules/axios": {
-      "version": "1.2.1",
-      "resolved": "https://registry.npmjs.org/axios/-/axios-1.2.1.tgz",
-      "integrity": "sha512-I88cFiGu9ryt/tfVEi4kX2SITsvDddTajXTOFmt2uK1ZVA8LytjtdeyefdQWEf5PU8w+4SSJDoYnggflB5tW4A==",
+      "version": "1.2.2",
+      "resolved": "https://registry.npmjs.org/axios/-/axios-1.2.2.tgz",
+      "integrity": "sha512-bz/J4gS2S3I7mpN/YZfGFTqhXTYzRho8Ay38w2otuuDR322KzFIWm/4W2K6gIwvWaws5n+mnb7D1lN9uD+QH6Q==",
       "dependencies": {
         "follow-redirects": "^1.15.0",
         "form-data": "^4.0.0",
@@ -6617,9 +6681,9 @@
       "dev": true
     },
     "node_modules/json-schema": {
-      "version": "0.2.3",
-      "resolved": "https://registry.npmjs.org/json-schema/-/json-schema-0.2.3.tgz",
-      "integrity": "sha1-tIDIkuWaLwWVTOcnvT8qTogvnhM="
+      "version": "0.4.0",
+      "resolved": "https://registry.npmjs.org/json-schema/-/json-schema-0.4.0.tgz",
+      "integrity": "sha512-es94M3nTIfsEPisRafak+HDLfHXnKBhV3vU5eqPcS3flIWqcxJWgXHXiey3YrpaNsanY5ei1VoYEbOzijuq9BA=="
     },
     "node_modules/json-schema-traverse": {
       "version": "0.4.1",
@@ -6652,17 +6716,17 @@
       }
     },
     "node_modules/jsprim": {
-      "version": "1.4.1",
-      "resolved": "https://registry.npmjs.org/jsprim/-/jsprim-1.4.1.tgz",
-      "integrity": "sha1-MT5mvB5cwG5Di8G3SZwuXFastqI=",
-      "engines": [
-        "node >=0.6.0"
-      ],
+      "version": "1.4.2",
+      "resolved": "https://registry.npmjs.org/jsprim/-/jsprim-1.4.2.tgz",
+      "integrity": "sha512-P2bSOMAc/ciLz6DzgjVlGJP9+BrJWu5UDGK70C2iweC5QBIeFf0ZXRvGjEj2uYgrY2MkAAhsSWHDWlFtEroZWw==",
       "dependencies": {
         "assert-plus": "1.0.0",
         "extsprintf": "1.3.0",
-        "json-schema": "0.2.3",
+        "json-schema": "0.4.0",
         "verror": "1.10.0"
+      },
+      "engines": {
+        "node": ">=0.6.0"
       }
     },
     "node_modules/junk": {
@@ -7315,9 +7379,9 @@
       }
     },
     "node_modules/nanoid": {
-      "version": "3.1.30",
-      "resolved": "https://registry.npmjs.org/nanoid/-/nanoid-3.1.30.tgz",
-      "integrity": "sha512-zJpuPDwOv8D2zq2WRoMe1HsfZthVewpel9CAvTfc/2mBD1uUT/agc5f7GHGWXlYkFvi1mVxe4IjvP2HNrop7nQ==",
+      "version": "3.3.1",
+      "resolved": "https://registry.npmjs.org/nanoid/-/nanoid-3.3.1.tgz",
+      "integrity": "sha512-n6Vs/3KGyxPQd6uO0eH4Bv0ojGSUvuLlIHtC3Y0kEO23YRge8H9x1GCzLn28YX0H66pMkxuaeESFq4tKISKwdw==",
       "bin": {
         "nanoid": "bin/nanoid.cjs"
       },
@@ -8487,9 +8551,9 @@
       }
     },
     "node_modules/request/node_modules/qs": {
-      "version": "6.5.2",
-      "resolved": "https://registry.npmjs.org/qs/-/qs-6.5.2.tgz",
-      "integrity": "sha512-N5ZAX4/LxJmF+7wN74pUD6qAh9/wnvdQcjq9TZjevvXzSUo7bfmw91saqMjzGS2xq91/odN2dW/WOl7qQHNDGA==",
+      "version": "6.5.3",
+      "resolved": "https://registry.npmjs.org/qs/-/qs-6.5.3.tgz",
+      "integrity": "sha512-qxXIEh4pCGfHICj1mAJQ2/2XVZkjCDTcEgfoSQxc/fYivUZxTkk7L3bDBJSoNrEzXI17oUO5Dp07ktqE5KzczA==",
       "engines": {
         "node": ">=0.6"
       }
@@ -9603,13 +9667,14 @@
       }
     },
     "node_modules/terser": {
-      "version": "5.10.0",
-      "resolved": "https://registry.npmjs.org/terser/-/terser-5.10.0.tgz",
-      "integrity": "sha512-AMmF99DMfEDiRJfxfY5jj5wNH/bYO09cniSqhfoyxc8sFoYIgkJy86G04UoZU5VjlpnplVu0K6Tx6E9b5+DlHA==",
+      "version": "5.16.1",
+      "resolved": "https://registry.npmjs.org/terser/-/terser-5.16.1.tgz",
+      "integrity": "sha512-xvQfyfA1ayT0qdK47zskQgRZeWLoOQ8JQ6mIgRGVNwZKdQMU+5FkCBjmv4QjcrTzyZquRw2FVtlJSRUmMKQslw==",
       "dev": true,
       "dependencies": {
+        "@jridgewell/source-map": "^0.3.2",
+        "acorn": "^8.5.0",
         "commander": "^2.20.0",
-        "source-map": "~0.7.2",
         "source-map-support": "~0.5.20"
       },
       "bin": {
@@ -9617,14 +9682,6 @@
       },
       "engines": {
         "node": ">=10"
-      },
-      "peerDependencies": {
-        "acorn": "^8.5.0"
-      },
-      "peerDependenciesMeta": {
-        "acorn": {
-          "optional": true
-        }
       }
     },
     "node_modules/terser-webpack-plugin": {
@@ -9667,15 +9724,6 @@
       "integrity": "sha512-GpVkmM8vF2vQUkj2LvZmD35JxeJOLCwJ9cUkugyk2nuhbv3+mJvpLYYt+0+USMxE+oj+ey/lJEnhZw75x/OMcQ==",
       "dev": true
     },
-    "node_modules/terser/node_modules/source-map": {
-      "version": "0.7.3",
-      "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.7.3.tgz",
-      "integrity": "sha512-CkCj6giN3S+n9qrYiBTX5gystlENnRW5jZeNLHpe6aue+SrHcG5VYwujhW9s4dY31mEGsxBDrHR6oI69fTXsaQ==",
-      "dev": true,
-      "engines": {
-        "node": ">= 8"
-      }
-    },
     "node_modules/timm": {
       "version": "1.7.1",
       "resolved": "https://registry.npmjs.org/timm/-/timm-1.7.1.tgz",
@@ -10552,6 +10600,11 @@
         "regenerator-runtime": "^0.13.4"
       }
     },
+    "@braintree/sanitize-url": {
+      "version": "6.0.2",
+      "resolved": "https://registry.npmjs.org/@braintree/sanitize-url/-/sanitize-url-6.0.2.tgz",
+      "integrity": "sha512-Tbsj02wXCbqGmzdnXNk0SOF19ChhRU70BsroIi4Pm6Ehp56in6vch94mfbdQ17DozxkL3BAVjbZ4Qc1a0HFRAg=="
+    },
     "@develar/schema-utils": {
       "version": "2.6.5",
       "resolved": "https://registry.npmjs.org/@develar/schema-utils/-/schema-utils-2.6.5.tgz",
@@ -11081,6 +11134,55 @@
         "regenerator-runtime": "^0.13.3"
       }
     },
+    "@jridgewell/gen-mapping": {
+      "version": "0.3.2",
+      "resolved": "https://registry.npmjs.org/@jridgewell/gen-mapping/-/gen-mapping-0.3.2.tgz",
+      "integrity": "sha512-mh65xKQAzI6iBcFzwv28KVWSmCkdRBWoOh+bYQGW3+6OZvbbN3TqMGo5hqYxQniRcH9F2VZIoJCm4pa3BPDK/A==",
+      "dev": true,
+      "requires": {
+        "@jridgewell/set-array": "^1.0.1",
+        "@jridgewell/sourcemap-codec": "^1.4.10",
+        "@jridgewell/trace-mapping": "^0.3.9"
+      }
+    },
+    "@jridgewell/resolve-uri": {
+      "version": "3.1.0",
+      "resolved": "https://registry.npmjs.org/@jridgewell/resolve-uri/-/resolve-uri-3.1.0.tgz",
+      "integrity": "sha512-F2msla3tad+Mfht5cJq7LSXcdudKTWCVYUgw6pLFOOHSTtZlj6SWNYAp+AhuqLmWdBO2X5hPrLcu8cVP8fy28w==",
+      "dev": true
+    },
+    "@jridgewell/set-array": {
+      "version": "1.1.2",
+      "resolved": "https://registry.npmjs.org/@jridgewell/set-array/-/set-array-1.1.2.tgz",
+      "integrity": "sha512-xnkseuNADM0gt2bs+BvhO0p78Mk762YnZdsuzFV018NoG1Sj1SCQvpSqa7XUaTam5vAGasABV9qXASMKnFMwMw==",
+      "dev": true
+    },
+    "@jridgewell/source-map": {
+      "version": "0.3.2",
+      "resolved": "https://registry.npmjs.org/@jridgewell/source-map/-/source-map-0.3.2.tgz",
+      "integrity": "sha512-m7O9o2uR8k2ObDysZYzdfhb08VuEml5oWGiosa1VdaPZ/A6QyPkAJuwN0Q1lhULOf6B7MtQmHENS743hWtCrgw==",
+      "dev": true,
+      "requires": {
+        "@jridgewell/gen-mapping": "^0.3.0",
+        "@jridgewell/trace-mapping": "^0.3.9"
+      }
+    },
+    "@jridgewell/sourcemap-codec": {
+      "version": "1.4.14",
+      "resolved": "https://registry.npmjs.org/@jridgewell/sourcemap-codec/-/sourcemap-codec-1.4.14.tgz",
+      "integrity": "sha512-XPSJHWmi394fuUuzDnGz1wiKqWfo1yXecHQMRf2l6hztTO+nPru658AyDngaBe7isIxEkRsPR3FZh+s7iVa4Uw==",
+      "dev": true
+    },
+    "@jridgewell/trace-mapping": {
+      "version": "0.3.17",
+      "resolved": "https://registry.npmjs.org/@jridgewell/trace-mapping/-/trace-mapping-0.3.17.tgz",
+      "integrity": "sha512-MCNzAp77qzKca9+W/+I0+sEpaUnZoeasnghNeVc41VZCEKaCH73Vq3BZZ/SzWIgrqE4H4ceI+p+b6C0mHf9T4g==",
+      "dev": true,
+      "requires": {
+        "@jridgewell/resolve-uri": "3.1.0",
+        "@jridgewell/sourcemap-codec": "1.4.14"
+      }
+    },
     "@jsdoc/salty": {
       "version": "0.2.1",
       "resolved": "https://registry.npmjs.org/@jsdoc/salty/-/salty-0.2.1.tgz",
@@ -11984,9 +12086,9 @@
       "integrity": "sha512-ReZxvNHIOv88FlT7rxcXIIC0fPt4KZqZbOlivyWtXLt8ESx84zd3kMC6iK5jVeS2qt+g7ftS7ye4fi06X5rtRQ=="
     },
     "axios": {
-      "version": "1.2.1",
-      "resolved": "https://registry.npmjs.org/axios/-/axios-1.2.1.tgz",
-      "integrity": "sha512-I88cFiGu9ryt/tfVEi4kX2SITsvDddTajXTOFmt2uK1ZVA8LytjtdeyefdQWEf5PU8w+4SSJDoYnggflB5tW4A==",
+      "version": "1.2.2",
+      "resolved": "https://registry.npmjs.org/axios/-/axios-1.2.2.tgz",
+      "integrity": "sha512-bz/J4gS2S3I7mpN/YZfGFTqhXTYzRho8Ay38w2otuuDR322KzFIWm/4W2K6gIwvWaws5n+mnb7D1lN9uD+QH6Q==",
       "requires": {
         "follow-redirects": "^1.15.0",
         "form-data": "^4.0.0",
@@ -15619,9 +15721,9 @@
       "dev": true
     },
     "json-schema": {
-      "version": "0.2.3",
-      "resolved": "https://registry.npmjs.org/json-schema/-/json-schema-0.2.3.tgz",
-      "integrity": "sha1-tIDIkuWaLwWVTOcnvT8qTogvnhM="
+      "version": "0.4.0",
+      "resolved": "https://registry.npmjs.org/json-schema/-/json-schema-0.4.0.tgz",
+      "integrity": "sha512-es94M3nTIfsEPisRafak+HDLfHXnKBhV3vU5eqPcS3flIWqcxJWgXHXiey3YrpaNsanY5ei1VoYEbOzijuq9BA=="
     },
     "json-schema-traverse": {
       "version": "0.4.1",
@@ -15648,13 +15750,13 @@
       }
     },
     "jsprim": {
-      "version": "1.4.1",
-      "resolved": "https://registry.npmjs.org/jsprim/-/jsprim-1.4.1.tgz",
-      "integrity": "sha1-MT5mvB5cwG5Di8G3SZwuXFastqI=",
+      "version": "1.4.2",
+      "resolved": "https://registry.npmjs.org/jsprim/-/jsprim-1.4.2.tgz",
+      "integrity": "sha512-P2bSOMAc/ciLz6DzgjVlGJP9+BrJWu5UDGK70C2iweC5QBIeFf0ZXRvGjEj2uYgrY2MkAAhsSWHDWlFtEroZWw==",
       "requires": {
         "assert-plus": "1.0.0",
         "extsprintf": "1.3.0",
-        "json-schema": "0.2.3",
+        "json-schema": "0.4.0",
         "verror": "1.10.0"
       }
     },
@@ -16167,9 +16269,9 @@
       }
     },
     "nanoid": {
-      "version": "3.1.30",
-      "resolved": "https://registry.npmjs.org/nanoid/-/nanoid-3.1.30.tgz",
-      "integrity": "sha512-zJpuPDwOv8D2zq2WRoMe1HsfZthVewpel9CAvTfc/2mBD1uUT/agc5f7GHGWXlYkFvi1mVxe4IjvP2HNrop7nQ=="
+      "version": "3.3.1",
+      "resolved": "https://registry.npmjs.org/nanoid/-/nanoid-3.3.1.tgz",
+      "integrity": "sha512-n6Vs/3KGyxPQd6uO0eH4Bv0ojGSUvuLlIHtC3Y0kEO23YRge8H9x1GCzLn28YX0H66pMkxuaeESFq4tKISKwdw=="
     },
     "napi-build-utils": {
       "version": "1.0.2",
@@ -17082,9 +17184,9 @@
       },
       "dependencies": {
         "qs": {
-          "version": "6.5.2",
-          "resolved": "https://registry.npmjs.org/qs/-/qs-6.5.2.tgz",
-          "integrity": "sha512-N5ZAX4/LxJmF+7wN74pUD6qAh9/wnvdQcjq9TZjevvXzSUo7bfmw91saqMjzGS2xq91/odN2dW/WOl7qQHNDGA=="
+          "version": "6.5.3",
+          "resolved": "https://registry.npmjs.org/qs/-/qs-6.5.3.tgz",
+          "integrity": "sha512-qxXIEh4pCGfHICj1mAJQ2/2XVZkjCDTcEgfoSQxc/fYivUZxTkk7L3bDBJSoNrEzXI17oUO5Dp07ktqE5KzczA=="
         },
         "tough-cookie": {
           "version": "2.5.0",
@@ -17946,13 +18048,14 @@
       }
     },
     "terser": {
-      "version": "5.10.0",
-      "resolved": "https://registry.npmjs.org/terser/-/terser-5.10.0.tgz",
-      "integrity": "sha512-AMmF99DMfEDiRJfxfY5jj5wNH/bYO09cniSqhfoyxc8sFoYIgkJy86G04UoZU5VjlpnplVu0K6Tx6E9b5+DlHA==",
+      "version": "5.16.1",
+      "resolved": "https://registry.npmjs.org/terser/-/terser-5.16.1.tgz",
+      "integrity": "sha512-xvQfyfA1ayT0qdK47zskQgRZeWLoOQ8JQ6mIgRGVNwZKdQMU+5FkCBjmv4QjcrTzyZquRw2FVtlJSRUmMKQslw==",
       "dev": true,
       "requires": {
+        "@jridgewell/source-map": "^0.3.2",
+        "acorn": "^8.5.0",
         "commander": "^2.20.0",
-        "source-map": "~0.7.2",
         "source-map-support": "~0.5.20"
       },
       "dependencies": {
@@ -17961,12 +18064,6 @@
           "resolved": "https://registry.npmjs.org/commander/-/commander-2.20.3.tgz",
           "integrity": "sha512-GpVkmM8vF2vQUkj2LvZmD35JxeJOLCwJ9cUkugyk2nuhbv3+mJvpLYYt+0+USMxE+oj+ey/lJEnhZw75x/OMcQ==",
           "dev": true
-        },
-        "source-map": {
-          "version": "0.7.3",
-          "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.7.3.tgz",
-          "integrity": "sha512-CkCj6giN3S+n9qrYiBTX5gystlENnRW5jZeNLHpe6aue+SrHcG5VYwujhW9s4dY31mEGsxBDrHR6oI69fTXsaQ==",
-          "dev": true
         }
       }
     },
diff --git a/package.json b/package.json
index 51eedb719..efa080246 100644
--- a/package.json
+++ b/package.json
@@ -2,7 +2,7 @@
   "name": "trilium",
   "productName": "Trilium Notes",
   "description": "Trilium Notes",
-  "version": "0.58.2-beta",
+  "version": "0.58.3-beta",
   "license": "AGPL-3.0-only",
   "main": "electron.js",
   "bin": {
@@ -17,10 +17,10 @@
     "start-server-no-dir": "cross-env TRILIUM_ENV=dev node ./src/www",
     "start-electron": "cross-env TRILIUM_DATA_DIR=./data TRILIUM_ENV=dev electron --inspect=5858 .",
     "start-electron-no-dir": "cross-env TRILIUM_ENV=dev electron --inspect=5858 .",
-    "switch-server": "rm -r ./node_modules/better-sqlite3 && npm install",
-    "switch-electron": "rm -r ./node_modules/better-sqlite3 && npm install && ./node_modules/.bin/electron-rebuild",
-    "build-backend-docs": "rm -r ./docs/backend_api && ./node_modules/.bin/jsdoc -c jsdoc-conf.json -d ./docs/backend_api src/becca/entities/*.js src/services/backend_script_api.js src/services/sql.js",
-    "build-frontend-docs": "rm -r ./docs/frontend_api && ./node_modules/.bin/jsdoc -c jsdoc-conf.json -d ./docs/frontend_api src/public/app/entities/*.js src/public/app/services/frontend_script_api.js src/public/app/widgets/collapsible_widget.js",
+    "switch-server": "rm -rf ./node_modules/better-sqlite3 && npm install",
+    "switch-electron": "rm -rf ./node_modules/better-sqlite3 && npm install && ./node_modules/.bin/electron-rebuild",
+    "build-backend-docs": "rm -rf ./docs/backend_api && ./node_modules/.bin/jsdoc -c jsdoc-conf.json -d ./docs/backend_api src/becca/entities/*.js src/services/backend_script_api.js src/services/sql.js",
+    "build-frontend-docs": "rm -rf ./docs/frontend_api && ./node_modules/.bin/jsdoc -c jsdoc-conf.json -d ./docs/frontend_api src/public/app/entities/*.js src/public/app/services/frontend_script_api.js src/public/app/widgets/collapsible_widget.js",
     "build-docs": "npm run build-backend-docs && npm run build-frontend-docs",
     "webpack": "npx webpack -c webpack-desktop.config.js && npx webpack -c webpack-mobile.config.js && npx webpack -c webpack-setup.config.js",
     "test-jasmine": "jasmine",
@@ -29,6 +29,7 @@
     "postinstall": "rimraf ./node_modules/canvas"
   },
   "dependencies": {
+    "@braintree/sanitize-url": "^6.0.2",
     "@electron/remote": "2.0.9",
     "@excalidraw/excalidraw": "0.13.0",
     "archiver": "5.3.1",
diff --git a/src/public/app/menus/tree_context_menu.js b/src/public/app/menus/tree_context_menu.js
index 98ebebadc..52300b962 100644
--- a/src/public/app/menus/tree_context_menu.js
+++ b/src/public/app/menus/tree_context_menu.js
@@ -32,7 +32,7 @@ export default class TreeContextMenu {
         const isHoisted = note.noteId === appContext.tabManager.getActiveContext().hoistedNoteId;
         const parentNote = isNotRoot ? await froca.getNote(branch.parentNoteId) : null;
 
-        // some actions don't support multi-note so they are disabled when notes are selected
+        // some actions don't support multi-note, so they are disabled when notes are selected
         // the only exception is when the only selected note is the one that was right-clicked, then
         // it's clear what the user meant to do.
         const selNodes = this.treeWidget.getSelectedNodes();
diff --git a/src/public/app/services/froca.js b/src/public/app/services/froca.js
index 2526c648b..0019b0bd8 100644
--- a/src/public/app/services/froca.js
+++ b/src/public/app/services/froca.js
@@ -216,7 +216,7 @@ class Froca {
     getNotesFromCache(noteIds, silentNotFoundError = false) {
         return noteIds.map(noteId => {
             if (!this.notes[noteId] && !silentNotFoundError) {
-                console.trace(`Can't find note "${noteId}"`);
+                console.trace(`Can't find note '${noteId}'`);
 
                 return null;
             }
@@ -235,7 +235,7 @@ class Froca {
 
         return noteIds.map(noteId => {
             if (!this.notes[noteId] && !silentNotFoundError) {
-                console.trace(`Can't find note "${noteId}"`);
+                console.trace(`Can't find note '${noteId}'`);
 
                 return null;
             } else {
@@ -285,7 +285,7 @@ class Froca {
     getBranch(branchId, silentNotFoundError = false) {
         if (!(branchId in this.branches)) {
             if (!silentNotFoundError) {
-                logError(`Not existing branch ${branchId}`);
+                logError(`Not existing branch '${branchId}'`);
             }
         }
         else {
@@ -295,13 +295,13 @@ class Froca {
 
     async getBranchId(parentNoteId, childNoteId) {
         if (childNoteId === 'root') {
-            return 'root';
+            return 'none_root';
         }
 
         const child = await this.getNote(childNoteId);
 
         if (!child) {
-            logError(`Could not find branchId for parent=${parentNoteId}, child=${childNoteId} since child does not exist`);
+            logError(`Could not find branchId for parent '${parentNoteId}', child '${childNoteId}' since child does not exist`);
 
             return null;
         }
@@ -318,9 +318,9 @@ class Froca {
                 .then(row => new NoteComplement(row))
                 .catch(e => console.error(`Cannot get note complement for note '${noteId}'`));
 
-            // we don't want to keep large payloads forever in memory so we clean that up quite quickly
+            // we don't want to keep large payloads forever in memory, so we clean that up quite quickly
             // this cache is more meant to share the data between different components within one business transaction (e.g. loading of the note into the tab context and all the components)
-            // this is also a work around for missing invalidation after change
+            // this is also a workaround for missing invalidation after change
             this.noteComplementPromises[noteId].then(
                 () => setTimeout(() => this.noteComplementPromises[noteId] = null, 1000)
             );
diff --git a/src/public/app/widgets/note_detail.js b/src/public/app/widgets/note_detail.js
index 274e82fa9..4907b6076 100644
--- a/src/public/app/widgets/note_detail.js
+++ b/src/public/app/widgets/note_detail.js
@@ -320,8 +320,6 @@ export default class NoteDetailWidget extends NoteContextAwareWidget {
                 && attributeService.isAffecting(attr, this.note));
 
             if (label || relation) {
-                console.log("OOOO");
-
                 // probably incorrect event
                 // calling this.refresh() is not enough since the event needs to be propagated to children as well
                 this.triggerEvent('noteTypeMimeChanged', {noteId: this.noteId});
diff --git a/src/routes/api/clipper.js b/src/routes/api/clipper.js
index fc3fcbdc4..9755462f2 100644
--- a/src/routes/api/clipper.js
+++ b/src/routes/api/clipper.js
@@ -14,8 +14,8 @@ const Attribute = require('../../becca/entities/attribute');
 const htmlSanitizer = require('../../services/html_sanitizer');
 const {formatAttrForSearch} = require("../../services/attribute_formatter");
 
-function findClippingNote(todayNote, pageUrl) {
-    const notes = todayNote.searchNotesInSubtree(
+function findClippingNote(clipperInboxNote, pageUrl) {
+    const notes = clipperInboxNote.searchNotesInSubtree(
         formatAttrForSearch({
             type: 'label',
             name: "pageUrl",
@@ -47,6 +47,7 @@ function addClipping(req) {
 
     const clipperInbox = getClipperInboxNote();
 
+    pageUrl = htmlSanitizer.sanitizeUrl(pageUrl);
     let clippingNote = findClippingNote(clipperInbox, pageUrl);
 
     if (!clippingNote) {
@@ -57,8 +58,6 @@ function addClipping(req) {
             type: 'text'
         }).note;
 
-        pageUrl = htmlSanitizer.sanitize(pageUrl);
-
         clippingNote.setLabel('clipType', 'clippings');
         clippingNote.setLabel('pageUrl', pageUrl);
         clippingNote.setLabel('iconClass', 'bx bx-globe');
@@ -96,7 +95,7 @@ function createNote(req) {
     note.setLabel('clipType', clipType);
 
     if (pageUrl) {
-        pageUrl = htmlSanitizer.sanitize(pageUrl);
+        pageUrl = htmlSanitizer.sanitizeUrl(pageUrl);
 
         note.setLabel('pageUrl', pageUrl);
         note.setLabel('iconClass', 'bx bx-globe');
diff --git a/src/routes/api/export.js b/src/routes/api/export.js
index 365c7e185..6294f2f25 100644
--- a/src/routes/api/export.js
+++ b/src/routes/api/export.js
@@ -13,7 +13,7 @@ function exportBranch(req, res) {
     const branch = becca.getBranch(branchId);
 
     if (!branch) {
-        const message = `Cannot export branch ${branchId} since it does not exist.`;
+        const message = `Cannot export branch '${branchId}' since it does not exist.`;
         log.error(message);
 
         res.setHeader("Content-Type", "text/plain")
diff --git a/src/services/build.js b/src/services/build.js
index 7461d1158..76698bb1a 100644
--- a/src/services/build.js
+++ b/src/services/build.js
@@ -1 +1 @@
-module.exports = { buildDate:"2022-12-29T00:12:54+01:00", buildRevision: "d36cf47974cd8bc6bd45c1da774a9a55d45f998e" };
+module.exports = { buildDate:"2023-01-04T22:36:31+01:00", buildRevision: "3a5fa2954dea0ff2ecdce9a28b3bb01f039d314d" };
diff --git a/src/services/html_sanitizer.js b/src/services/html_sanitizer.js
index c675c428a..32b275d17 100644
--- a/src/services/html_sanitizer.js
+++ b/src/services/html_sanitizer.js
@@ -1,4 +1,5 @@
 const sanitizeHtml = require('sanitize-html');
+const sanitizeUrl = require('@braintree/sanitize-url').sanitizeUrl;
 
 // intended mainly as protection against XSS via import
 // secondarily it (partly) protects against "CSS takeover"
@@ -50,5 +51,6 @@ function sanitize(dirtyHtml) {
 }
 
 module.exports = {
-    sanitize
+    sanitize,
+    sanitizeUrl
 };