nsarrazin commited on
Commit
7a99944
·
unverified ·
1 Parent(s): 911e941

Improve sanitization of model output (#1341)

Browse files

* Improve sanitization of model output

* make it compatible with SSR

* fix formatting issues

package-lock.json CHANGED
@@ -59,6 +59,7 @@
59
  "@sveltejs/adapter-node": "^1.3.1",
60
  "@sveltejs/kit": "^1.30.4",
61
  "@tailwindcss/typography": "^0.5.9",
 
62
  "@types/express": "^4.17.21",
63
  "@types/js-yaml": "^4.0.9",
64
  "@types/jsdom": "^21.1.1",
@@ -68,9 +69,11 @@
68
  "@types/uuid": "^9.0.8",
69
  "@typescript-eslint/eslint-plugin": "^6.x",
70
  "@typescript-eslint/parser": "^6.x",
 
71
  "eslint": "^8.28.0",
72
  "eslint-config-prettier": "^8.5.0",
73
  "eslint-plugin-svelte": "^2.30.0",
 
74
  "js-yaml": "^4.1.0",
75
  "minimist": "^1.2.8",
76
  "prettier": "^2.8.0",
@@ -3460,6 +3463,16 @@
3460
  "integrity": "sha512-COUnqfB2+ckwXXSFInsFdOAWQzCCx+a5hq2ruyj+Vjund94RJQd4LG2u9hnvJrTgunKAaax7ancBYlDrNYxA0g==",
3461
  "dev": true
3462
  },
 
 
 
 
 
 
 
 
 
 
3463
  "node_modules/@types/estree": {
3464
  "version": "1.0.5",
3465
  "resolved": "https://registry.npmjs.org/@types/estree/-/estree-1.0.5.tgz",
@@ -3678,6 +3691,13 @@
3678
  "integrity": "sha512-Q5vtl1W5ue16D+nIaW8JWebSSraJVlK+EthKn7e7UcD4KWsaSJ8BqGPXNaPghgtcn/fhvrN17Tv8ksUsQpiplw==",
3679
  "dev": true
3680
  },
 
 
 
 
 
 
 
3681
  "node_modules/@types/uuid": {
3682
  "version": "9.0.8",
3683
  "resolved": "https://registry.npmjs.org/@types/uuid/-/uuid-9.0.8.tgz",
@@ -5350,6 +5370,13 @@
5350
  "url": "https://github.com/fb55/domhandler?sponsor=1"
5351
  }
5352
  },
 
 
 
 
 
 
 
5353
  "node_modules/domutils": {
5354
  "version": "3.1.0",
5355
  "resolved": "https://registry.npmjs.org/domutils/-/domutils-3.1.0.tgz",
@@ -6890,6 +6917,223 @@
6890
  "integrity": "sha512-RHxMLp9lnKHGHRng9QFhRCMbYAcVpn69smSGcq3f36xjgVVWThj4qqLbTLlq7Ssj8B+fIQ1EuCEGI2lKsyQeIw==",
6891
  "dev": true
6892
  },
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
6893
  "node_modules/jiti": {
6894
  "version": "1.21.0",
6895
  "resolved": "https://registry.npmjs.org/jiti/-/jiti-1.21.0.tgz",
@@ -7809,9 +8053,10 @@
7809
  }
7810
  },
7811
  "node_modules/nwsapi": {
7812
- "version": "2.2.4",
7813
- "resolved": "https://registry.npmjs.org/nwsapi/-/nwsapi-2.2.4.tgz",
7814
- "integrity": "sha512-NHj4rzRo0tQdijE9ZqAx6kYDcoRwYwSYzCA8MY3JzfxlrvEU0jhnhJT9BhqhJs7I/dKcrDm6TyulaRqZPIhN5g=="
 
7815
  },
7816
  "node_modules/object-assign": {
7817
  "version": "4.1.1",
@@ -8906,9 +9151,10 @@
8906
  }
8907
  },
8908
  "node_modules/punycode": {
8909
- "version": "2.3.0",
8910
- "resolved": "https://registry.npmjs.org/punycode/-/punycode-2.3.0.tgz",
8911
- "integrity": "sha512-rRV+zQD8tVFys26lAGR9WUuS4iUAngJScM+ZRSKtvl5tKeZ2t5bvdNFdNHBW9FWR4guGHlgmsZ1G7BSm2wTbuA==",
 
8912
  "engines": {
8913
  "node": ">=6"
8914
  }
@@ -10391,9 +10637,10 @@
10391
  }
10392
  },
10393
  "node_modules/tough-cookie": {
10394
- "version": "4.1.3",
10395
- "resolved": "https://registry.npmjs.org/tough-cookie/-/tough-cookie-4.1.3.tgz",
10396
- "integrity": "sha512-aX/y5pVRkfRnfmuX+OdbSdXvPe6ieKX/G2s7e98f4poJHnqH3281gDPm/metm6E/WRamfx7WC4HUqkWHfQHprw==",
 
10397
  "dependencies": {
10398
  "psl": "^1.1.33",
10399
  "punycode": "^2.1.1",
 
59
  "@sveltejs/adapter-node": "^1.3.1",
60
  "@sveltejs/kit": "^1.30.4",
61
  "@tailwindcss/typography": "^0.5.9",
62
+ "@types/dompurify": "^3.0.5",
63
  "@types/express": "^4.17.21",
64
  "@types/js-yaml": "^4.0.9",
65
  "@types/jsdom": "^21.1.1",
 
69
  "@types/uuid": "^9.0.8",
70
  "@typescript-eslint/eslint-plugin": "^6.x",
71
  "@typescript-eslint/parser": "^6.x",
72
+ "dompurify": "^3.1.6",
73
  "eslint": "^8.28.0",
74
  "eslint-config-prettier": "^8.5.0",
75
  "eslint-plugin-svelte": "^2.30.0",
76
+ "isomorphic-dompurify": "^2.13.0",
77
  "js-yaml": "^4.1.0",
78
  "minimist": "^1.2.8",
79
  "prettier": "^2.8.0",
 
3463
  "integrity": "sha512-COUnqfB2+ckwXXSFInsFdOAWQzCCx+a5hq2ruyj+Vjund94RJQd4LG2u9hnvJrTgunKAaax7ancBYlDrNYxA0g==",
3464
  "dev": true
3465
  },
3466
+ "node_modules/@types/dompurify": {
3467
+ "version": "3.0.5",
3468
+ "resolved": "https://registry.npmjs.org/@types/dompurify/-/dompurify-3.0.5.tgz",
3469
+ "integrity": "sha512-1Wg0g3BtQF7sSb27fJQAKck1HECM6zV1EB66j8JH9i3LCjYabJa0FSdiSgsD5K/RbrsR0SiraKacLB+T8ZVYAg==",
3470
+ "dev": true,
3471
+ "license": "MIT",
3472
+ "dependencies": {
3473
+ "@types/trusted-types": "*"
3474
+ }
3475
+ },
3476
  "node_modules/@types/estree": {
3477
  "version": "1.0.5",
3478
  "resolved": "https://registry.npmjs.org/@types/estree/-/estree-1.0.5.tgz",
 
3691
  "integrity": "sha512-Q5vtl1W5ue16D+nIaW8JWebSSraJVlK+EthKn7e7UcD4KWsaSJ8BqGPXNaPghgtcn/fhvrN17Tv8ksUsQpiplw==",
3692
  "dev": true
3693
  },
3694
+ "node_modules/@types/trusted-types": {
3695
+ "version": "2.0.7",
3696
+ "resolved": "https://registry.npmjs.org/@types/trusted-types/-/trusted-types-2.0.7.tgz",
3697
+ "integrity": "sha512-ScaPdn1dQczgbl0QFTeTOmVHFULt394XJgOQNoyVhZ6r2vLnMLJfBPd53SB52T/3G36VI1/g2MZaX0cwDuXsfw==",
3698
+ "dev": true,
3699
+ "license": "MIT"
3700
+ },
3701
  "node_modules/@types/uuid": {
3702
  "version": "9.0.8",
3703
  "resolved": "https://registry.npmjs.org/@types/uuid/-/uuid-9.0.8.tgz",
 
5370
  "url": "https://github.com/fb55/domhandler?sponsor=1"
5371
  }
5372
  },
5373
+ "node_modules/dompurify": {
5374
+ "version": "3.1.6",
5375
+ "resolved": "https://registry.npmjs.org/dompurify/-/dompurify-3.1.6.tgz",
5376
+ "integrity": "sha512-cTOAhc36AalkjtBpfG6O8JimdTMWNXjiePT2xQH/ppBGi/4uIpmj8eKyIkMJErXWARyINV/sB38yf8JCLF5pbQ==",
5377
+ "dev": true,
5378
+ "license": "(MPL-2.0 OR Apache-2.0)"
5379
+ },
5380
  "node_modules/domutils": {
5381
  "version": "3.1.0",
5382
  "resolved": "https://registry.npmjs.org/domutils/-/domutils-3.1.0.tgz",
 
6917
  "integrity": "sha512-RHxMLp9lnKHGHRng9QFhRCMbYAcVpn69smSGcq3f36xjgVVWThj4qqLbTLlq7Ssj8B+fIQ1EuCEGI2lKsyQeIw==",
6918
  "dev": true
6919
  },
6920
+ "node_modules/isomorphic-dompurify": {
6921
+ "version": "2.13.0",
6922
+ "resolved": "https://registry.npmjs.org/isomorphic-dompurify/-/isomorphic-dompurify-2.13.0.tgz",
6923
+ "integrity": "sha512-jVxFnyOiA3fKPkteQjfIogww9T/BIX1Basuwt5D50MB3Sqvki9yBNq96ICLHpbiDY79jc6RC555DeBbTCt6i6A==",
6924
+ "dev": true,
6925
+ "license": "MIT",
6926
+ "dependencies": {
6927
+ "@types/dompurify": "^3.0.5",
6928
+ "dompurify": "^3.1.6",
6929
+ "jsdom": "^24.1.0"
6930
+ },
6931
+ "engines": {
6932
+ "node": ">=18"
6933
+ }
6934
+ },
6935
+ "node_modules/isomorphic-dompurify/node_modules/agent-base": {
6936
+ "version": "7.1.1",
6937
+ "resolved": "https://registry.npmjs.org/agent-base/-/agent-base-7.1.1.tgz",
6938
+ "integrity": "sha512-H0TSyFNDMomMNJQBn8wFV5YC/2eJ+VXECwOadZJT554xP6cODZHPX3H9QMQECxvrgiSOP1pHjy1sMWQVYJOUOA==",
6939
+ "dev": true,
6940
+ "license": "MIT",
6941
+ "dependencies": {
6942
+ "debug": "^4.3.4"
6943
+ },
6944
+ "engines": {
6945
+ "node": ">= 14"
6946
+ }
6947
+ },
6948
+ "node_modules/isomorphic-dompurify/node_modules/cssstyle": {
6949
+ "version": "4.0.1",
6950
+ "resolved": "https://registry.npmjs.org/cssstyle/-/cssstyle-4.0.1.tgz",
6951
+ "integrity": "sha512-8ZYiJ3A/3OkDd093CBT/0UKDWry7ak4BdPTFP2+QEP7cmhouyq/Up709ASSj2cK02BbZiMgk7kYjZNS4QP5qrQ==",
6952
+ "dev": true,
6953
+ "license": "MIT",
6954
+ "dependencies": {
6955
+ "rrweb-cssom": "^0.6.0"
6956
+ },
6957
+ "engines": {
6958
+ "node": ">=18"
6959
+ }
6960
+ },
6961
+ "node_modules/isomorphic-dompurify/node_modules/data-urls": {
6962
+ "version": "5.0.0",
6963
+ "resolved": "https://registry.npmjs.org/data-urls/-/data-urls-5.0.0.tgz",
6964
+ "integrity": "sha512-ZYP5VBHshaDAiVZxjbRVcFJpc+4xGgT0bK3vzy1HLN8jTO975HEbuYzZJcHoQEY5K1a0z8YayJkyVETa08eNTg==",
6965
+ "dev": true,
6966
+ "license": "MIT",
6967
+ "dependencies": {
6968
+ "whatwg-mimetype": "^4.0.0",
6969
+ "whatwg-url": "^14.0.0"
6970
+ },
6971
+ "engines": {
6972
+ "node": ">=18"
6973
+ }
6974
+ },
6975
+ "node_modules/isomorphic-dompurify/node_modules/html-encoding-sniffer": {
6976
+ "version": "4.0.0",
6977
+ "resolved": "https://registry.npmjs.org/html-encoding-sniffer/-/html-encoding-sniffer-4.0.0.tgz",
6978
+ "integrity": "sha512-Y22oTqIU4uuPgEemfz7NDJz6OeKf12Lsu+QC+s3BVpda64lTiMYCyGwg5ki4vFxkMwQdeZDl2adZoqUgdFuTgQ==",
6979
+ "dev": true,
6980
+ "license": "MIT",
6981
+ "dependencies": {
6982
+ "whatwg-encoding": "^3.1.1"
6983
+ },
6984
+ "engines": {
6985
+ "node": ">=18"
6986
+ }
6987
+ },
6988
+ "node_modules/isomorphic-dompurify/node_modules/http-proxy-agent": {
6989
+ "version": "7.0.2",
6990
+ "resolved": "https://registry.npmjs.org/http-proxy-agent/-/http-proxy-agent-7.0.2.tgz",
6991
+ "integrity": "sha512-T1gkAiYYDWYx3V5Bmyu7HcfcvL7mUrTWiM6yOfa3PIphViJ/gFPbvidQ+veqSOHci/PxBcDabeUNCzpOODJZig==",
6992
+ "dev": true,
6993
+ "license": "MIT",
6994
+ "dependencies": {
6995
+ "agent-base": "^7.1.0",
6996
+ "debug": "^4.3.4"
6997
+ },
6998
+ "engines": {
6999
+ "node": ">= 14"
7000
+ }
7001
+ },
7002
+ "node_modules/isomorphic-dompurify/node_modules/https-proxy-agent": {
7003
+ "version": "7.0.5",
7004
+ "resolved": "https://registry.npmjs.org/https-proxy-agent/-/https-proxy-agent-7.0.5.tgz",
7005
+ "integrity": "sha512-1e4Wqeblerz+tMKPIq2EMGiiWW1dIjZOksyHWSUm1rmuvw/how9hBHZ38lAGj5ID4Ik6EdkOw7NmWPy6LAwalw==",
7006
+ "dev": true,
7007
+ "license": "MIT",
7008
+ "dependencies": {
7009
+ "agent-base": "^7.0.2",
7010
+ "debug": "4"
7011
+ },
7012
+ "engines": {
7013
+ "node": ">= 14"
7014
+ }
7015
+ },
7016
+ "node_modules/isomorphic-dompurify/node_modules/jsdom": {
7017
+ "version": "24.1.0",
7018
+ "resolved": "https://registry.npmjs.org/jsdom/-/jsdom-24.1.0.tgz",
7019
+ "integrity": "sha512-6gpM7pRXCwIOKxX47cgOyvyQDN/Eh0f1MeKySBV2xGdKtqJBLj8P25eY3EVCWo2mglDDzozR2r2MW4T+JiNUZA==",
7020
+ "dev": true,
7021
+ "license": "MIT",
7022
+ "dependencies": {
7023
+ "cssstyle": "^4.0.1",
7024
+ "data-urls": "^5.0.0",
7025
+ "decimal.js": "^10.4.3",
7026
+ "form-data": "^4.0.0",
7027
+ "html-encoding-sniffer": "^4.0.0",
7028
+ "http-proxy-agent": "^7.0.2",
7029
+ "https-proxy-agent": "^7.0.4",
7030
+ "is-potential-custom-element-name": "^1.0.1",
7031
+ "nwsapi": "^2.2.10",
7032
+ "parse5": "^7.1.2",
7033
+ "rrweb-cssom": "^0.7.0",
7034
+ "saxes": "^6.0.0",
7035
+ "symbol-tree": "^3.2.4",
7036
+ "tough-cookie": "^4.1.4",
7037
+ "w3c-xmlserializer": "^5.0.0",
7038
+ "webidl-conversions": "^7.0.0",
7039
+ "whatwg-encoding": "^3.1.1",
7040
+ "whatwg-mimetype": "^4.0.0",
7041
+ "whatwg-url": "^14.0.0",
7042
+ "ws": "^8.17.0",
7043
+ "xml-name-validator": "^5.0.0"
7044
+ },
7045
+ "engines": {
7046
+ "node": ">=18"
7047
+ },
7048
+ "peerDependencies": {
7049
+ "canvas": "^2.11.2"
7050
+ },
7051
+ "peerDependenciesMeta": {
7052
+ "canvas": {
7053
+ "optional": true
7054
+ }
7055
+ }
7056
+ },
7057
+ "node_modules/isomorphic-dompurify/node_modules/jsdom/node_modules/rrweb-cssom": {
7058
+ "version": "0.7.1",
7059
+ "resolved": "https://registry.npmjs.org/rrweb-cssom/-/rrweb-cssom-0.7.1.tgz",
7060
+ "integrity": "sha512-TrEMa7JGdVm0UThDJSx7ddw5nVm3UJS9o9CCIZ72B1vSyEZoziDqBYP3XIoi/12lKrJR8rE3jeFHMok2F/Mnsg==",
7061
+ "dev": true,
7062
+ "license": "MIT"
7063
+ },
7064
+ "node_modules/isomorphic-dompurify/node_modules/tr46": {
7065
+ "version": "5.0.0",
7066
+ "resolved": "https://registry.npmjs.org/tr46/-/tr46-5.0.0.tgz",
7067
+ "integrity": "sha512-tk2G5R2KRwBd+ZN0zaEXpmzdKyOYksXwywulIX95MBODjSzMIuQnQ3m8JxgbhnL1LeVo7lqQKsYa1O3Htl7K5g==",
7068
+ "dev": true,
7069
+ "license": "MIT",
7070
+ "dependencies": {
7071
+ "punycode": "^2.3.1"
7072
+ },
7073
+ "engines": {
7074
+ "node": ">=18"
7075
+ }
7076
+ },
7077
+ "node_modules/isomorphic-dompurify/node_modules/w3c-xmlserializer": {
7078
+ "version": "5.0.0",
7079
+ "resolved": "https://registry.npmjs.org/w3c-xmlserializer/-/w3c-xmlserializer-5.0.0.tgz",
7080
+ "integrity": "sha512-o8qghlI8NZHU1lLPrpi2+Uq7abh4GGPpYANlalzWxyWteJOCsr/P+oPBA49TOLu5FTZO4d3F9MnWJfiMo4BkmA==",
7081
+ "dev": true,
7082
+ "license": "MIT",
7083
+ "dependencies": {
7084
+ "xml-name-validator": "^5.0.0"
7085
+ },
7086
+ "engines": {
7087
+ "node": ">=18"
7088
+ }
7089
+ },
7090
+ "node_modules/isomorphic-dompurify/node_modules/whatwg-encoding": {
7091
+ "version": "3.1.1",
7092
+ "resolved": "https://registry.npmjs.org/whatwg-encoding/-/whatwg-encoding-3.1.1.tgz",
7093
+ "integrity": "sha512-6qN4hJdMwfYBtE3YBTTHhoeuUrDBPZmbQaxWAqSALV/MeEnR5z1xd8UKud2RAkFoPkmB+hli1TZSnyi84xz1vQ==",
7094
+ "dev": true,
7095
+ "license": "MIT",
7096
+ "dependencies": {
7097
+ "iconv-lite": "0.6.3"
7098
+ },
7099
+ "engines": {
7100
+ "node": ">=18"
7101
+ }
7102
+ },
7103
+ "node_modules/isomorphic-dompurify/node_modules/whatwg-mimetype": {
7104
+ "version": "4.0.0",
7105
+ "resolved": "https://registry.npmjs.org/whatwg-mimetype/-/whatwg-mimetype-4.0.0.tgz",
7106
+ "integrity": "sha512-QaKxh0eNIi2mE9p2vEdzfagOKHCcj1pJ56EEHGQOVxp8r9/iszLUUV7v89x9O1p/T+NlTM5W7jW6+cz4Fq1YVg==",
7107
+ "dev": true,
7108
+ "license": "MIT",
7109
+ "engines": {
7110
+ "node": ">=18"
7111
+ }
7112
+ },
7113
+ "node_modules/isomorphic-dompurify/node_modules/whatwg-url": {
7114
+ "version": "14.0.0",
7115
+ "resolved": "https://registry.npmjs.org/whatwg-url/-/whatwg-url-14.0.0.tgz",
7116
+ "integrity": "sha512-1lfMEm2IEr7RIV+f4lUNPOqfFL+pO+Xw3fJSqmjX9AbXcXcYOkCe1P6+9VBZB6n94af16NfZf+sSk0JCBZC9aw==",
7117
+ "dev": true,
7118
+ "license": "MIT",
7119
+ "dependencies": {
7120
+ "tr46": "^5.0.0",
7121
+ "webidl-conversions": "^7.0.0"
7122
+ },
7123
+ "engines": {
7124
+ "node": ">=18"
7125
+ }
7126
+ },
7127
+ "node_modules/isomorphic-dompurify/node_modules/xml-name-validator": {
7128
+ "version": "5.0.0",
7129
+ "resolved": "https://registry.npmjs.org/xml-name-validator/-/xml-name-validator-5.0.0.tgz",
7130
+ "integrity": "sha512-EvGK8EJ3DhaHfbRlETOWAS5pO9MZITeauHKJyb8wyajUfQUenkIg2MvLDTZ4T/TgIcm3HU0TFBgWWboAZ30UHg==",
7131
+ "dev": true,
7132
+ "license": "Apache-2.0",
7133
+ "engines": {
7134
+ "node": ">=18"
7135
+ }
7136
+ },
7137
  "node_modules/jiti": {
7138
  "version": "1.21.0",
7139
  "resolved": "https://registry.npmjs.org/jiti/-/jiti-1.21.0.tgz",
 
8053
  }
8054
  },
8055
  "node_modules/nwsapi": {
8056
+ "version": "2.2.12",
8057
+ "resolved": "https://registry.npmjs.org/nwsapi/-/nwsapi-2.2.12.tgz",
8058
+ "integrity": "sha512-qXDmcVlZV4XRtKFzddidpfVP4oMSGhga+xdMc25mv8kaLUHtgzCDhUxkrN8exkGdTlLNaXj7CV3GtON7zuGZ+w==",
8059
+ "license": "MIT"
8060
  },
8061
  "node_modules/object-assign": {
8062
  "version": "4.1.1",
 
9151
  }
9152
  },
9153
  "node_modules/punycode": {
9154
+ "version": "2.3.1",
9155
+ "resolved": "https://registry.npmjs.org/punycode/-/punycode-2.3.1.tgz",
9156
+ "integrity": "sha512-vYt7UD1U9Wg6138shLtLOvdAu+8DsC/ilFtEVHcH+wydcSpNE20AfSOduf6MkRFahL5FY7X1oU7nKVZFtfq8Fg==",
9157
+ "license": "MIT",
9158
  "engines": {
9159
  "node": ">=6"
9160
  }
 
10637
  }
10638
  },
10639
  "node_modules/tough-cookie": {
10640
+ "version": "4.1.4",
10641
+ "resolved": "https://registry.npmjs.org/tough-cookie/-/tough-cookie-4.1.4.tgz",
10642
+ "integrity": "sha512-Loo5UUvLD9ScZ6jh8beX1T6sO1w2/MpCRpEP7V280GKMVUQ0Jzar2U3UJPsrdbziLEMMhu3Ujnq//rhiFuIeag==",
10643
+ "license": "BSD-3-Clause",
10644
  "dependencies": {
10645
  "psl": "^1.1.33",
10646
  "punycode": "^2.1.1",
package.json CHANGED
@@ -22,6 +22,7 @@
22
  "@sveltejs/adapter-node": "^1.3.1",
23
  "@sveltejs/kit": "^1.30.4",
24
  "@tailwindcss/typography": "^0.5.9",
 
25
  "@types/express": "^4.17.21",
26
  "@types/js-yaml": "^4.0.9",
27
  "@types/jsdom": "^21.1.1",
@@ -31,9 +32,11 @@
31
  "@types/uuid": "^9.0.8",
32
  "@typescript-eslint/eslint-plugin": "^6.x",
33
  "@typescript-eslint/parser": "^6.x",
 
34
  "eslint": "^8.28.0",
35
  "eslint-config-prettier": "^8.5.0",
36
  "eslint-plugin-svelte": "^2.30.0",
 
37
  "js-yaml": "^4.1.0",
38
  "minimist": "^1.2.8",
39
  "prettier": "^2.8.0",
 
22
  "@sveltejs/adapter-node": "^1.3.1",
23
  "@sveltejs/kit": "^1.30.4",
24
  "@tailwindcss/typography": "^0.5.9",
25
+ "@types/dompurify": "^3.0.5",
26
  "@types/express": "^4.17.21",
27
  "@types/js-yaml": "^4.0.9",
28
  "@types/jsdom": "^21.1.1",
 
32
  "@types/uuid": "^9.0.8",
33
  "@typescript-eslint/eslint-plugin": "^6.x",
34
  "@typescript-eslint/parser": "^6.x",
35
+ "dompurify": "^3.1.6",
36
  "eslint": "^8.28.0",
37
  "eslint-config-prettier": "^8.5.0",
38
  "eslint-plugin-svelte": "^2.30.0",
39
+ "isomorphic-dompurify": "^2.13.0",
40
  "js-yaml": "^4.1.0",
41
  "minimist": "^1.2.8",
42
  "prettier": "^2.8.0",
src/lib/components/CodeBlock.svelte CHANGED
@@ -1,6 +1,7 @@
1
  <script lang="ts">
2
  import { afterUpdate } from "svelte";
3
  import CopyToClipBoardBtn from "./CopyToClipBoardBtn.svelte";
 
4
 
5
  export let code = "";
6
  export let lang = "";
@@ -19,8 +20,9 @@
19
  <!-- eslint-disable svelte/no-at-html-tags -->
20
  <pre
21
  class="scrollbar-custom overflow-auto px-5 scrollbar-thumb-gray-500 hover:scrollbar-thumb-gray-400 dark:scrollbar-thumb-white/10 dark:hover:scrollbar-thumb-white/20"><code
22
- class="language-{lang}">{@html highlightedCode || code.replaceAll("<", "&lt;")}</code
23
- ></pre>
 
24
  <CopyToClipBoardBtn
25
  classNames="absolute top-2 right-2 invisible opacity-0 group-hover:visible group-hover:opacity-100"
26
  value={code}
 
1
  <script lang="ts">
2
  import { afterUpdate } from "svelte";
3
  import CopyToClipBoardBtn from "./CopyToClipBoardBtn.svelte";
4
+ import DOMPurify from "isomorphic-dompurify";
5
 
6
  export let code = "";
7
  export let lang = "";
 
20
  <!-- eslint-disable svelte/no-at-html-tags -->
21
  <pre
22
  class="scrollbar-custom overflow-auto px-5 scrollbar-thumb-gray-500 hover:scrollbar-thumb-gray-400 dark:scrollbar-thumb-white/10 dark:hover:scrollbar-thumb-white/20"><code
23
+ class="language-{lang}"
24
+ >{@html DOMPurify.sanitize(highlightedCode || code.replaceAll("<", "&lt;"))}
25
+ </code></pre>
26
  <CopyToClipBoardBtn
27
  classNames="absolute top-2 right-2 invisible opacity-0 group-hover:visible group-hover:opacity-100"
28
  value={code}
src/lib/components/chat/ChatMessage.svelte CHANGED
@@ -33,6 +33,7 @@
33
  import Modal from "../Modal.svelte";
34
  import ToolUpdate from "./ToolUpdate.svelte";
35
  import { useSettingsStore } from "$lib/stores/settings";
 
36
 
37
  function sanitizeMd(md: string) {
38
  let ret = md
@@ -53,6 +54,7 @@
53
 
54
  return ret;
55
  }
 
56
  function unsanitizeMd(md: string) {
57
  return md.replaceAll("&lt;", "<");
58
  }
@@ -106,11 +108,10 @@
106
  marked.use(
107
  markedKatex({
108
  throwOnError: false,
109
- // output: "html",
110
  })
111
  );
112
 
113
- $: tokens = marked.lexer(sanitizeMd(message.content));
114
 
115
  $: emptyLoad =
116
  !message.content && (webSearchIsDone || (searchUpdates && searchUpdates.length === 0));
@@ -303,8 +304,10 @@
303
  {#if token.type === "code"}
304
  <CodeBlock lang={token.lang} code={unsanitizeMd(token.text)} />
305
  {:else}
306
- <!-- eslint-disable-next-line svelte/no-at-html-tags -->
307
- {@html marked.parse(token.raw, options)}
 
 
308
  {/if}
309
  {/each}
310
  </div>
 
33
  import Modal from "../Modal.svelte";
34
  import ToolUpdate from "./ToolUpdate.svelte";
35
  import { useSettingsStore } from "$lib/stores/settings";
36
+ import DOMPurify from "isomorphic-dompurify";
37
 
38
  function sanitizeMd(md: string) {
39
  let ret = md
 
54
 
55
  return ret;
56
  }
57
+
58
  function unsanitizeMd(md: string) {
59
  return md.replaceAll("&lt;", "<");
60
  }
 
108
  marked.use(
109
  markedKatex({
110
  throwOnError: false,
 
111
  })
112
  );
113
 
114
+ $: tokens = marked.lexer(sanitizeMd(message.content ?? ""));
115
 
116
  $: emptyLoad =
117
  !message.content && (webSearchIsDone || (searchUpdates && searchUpdates.length === 0));
 
304
  {#if token.type === "code"}
305
  <CodeBlock lang={token.lang} code={unsanitizeMd(token.text)} />
306
  {:else}
307
+ {#await marked.parse(token.raw, options) then parsed}
308
+ <!-- eslint-disable-next-line svelte/no-at-html-tags -->
309
+ {@html DOMPurify.sanitize(parsed)}
310
+ {/await}
311
  {/if}
312
  {/each}
313
  </div>