acrylblends 0.6.2 → 0.6.4
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +5 -1
- package/docs/framework/README.md +3 -2
- package/docs/framework/UPSTREAM.md +1 -1
- package/docs/framework/cordis/acryl-in-a-cordis-app.md +6 -0
- package/docs/framework/getting-started/basic.md +1 -0
- package/docs/framework/getting-started/desktop.md +41 -0
- package/docs/framework/guides/jsx-dom.md +0 -3
- package/docs/framework/guides/jsx.md +24 -3
- package/docs/framework/helpers/css.md +0 -3
- package/docs/framework/helpers/ssg.md +3 -6
- package/docs/framework/middleware/builtin/jsx-renderer.md +0 -3
- package/docs/framework/upstream.json +3 -3
- package/lib/accepts.d.ts +1 -1
- package/lib/acryl-base.d.ts +1 -1
- package/lib/adapter.d.ts +1 -1
- package/lib/{app-BdrVHBlJ.d.ts → app-D8riatvv.d.ts} +1 -1
- package/lib/base-BpQy2Rk7.d.ts +783 -0
- package/lib/base-ddiVmiE7.js +721 -0
- package/lib/basic-auth.d.ts +1 -1
- package/lib/bearer-auth.d.ts +1 -1
- package/lib/body-limit.d.ts +1 -1
- package/lib/cache.d.ts +1 -1
- package/lib/cache.js +4 -4
- package/lib/{client-BHTr318g.js → client-DDLXwhBo.js} +2 -125
- package/lib/client.d.ts +2 -2
- package/lib/client.js +2 -1
- package/lib/combine.d.ts +1 -1
- package/lib/common-D8Z4JRCw.d.ts +46 -0
- package/lib/components-0o0CBYNv.js +268 -0
- package/lib/components-DdI7-ns7.js +24 -0
- package/lib/compress.d.ts +1 -1
- package/lib/conninfo.d.ts +2 -2
- package/lib/constants-BR9jM9BC.js +9 -0
- package/lib/{context-B5Y1lLha.d.ts → context-DS3fYyG-.d.ts} +2 -2
- package/lib/context-DxFdY_un.d.ts +250 -0
- package/lib/context-storage.d.ts +1 -1
- package/lib/{cookie-D9_nQbsM.d.ts → cookie-CCelEqky.d.ts} +1 -1
- package/lib/cookie.d.ts +3 -3
- package/lib/cors.d.ts +1 -1
- package/lib/csrf.d.ts +1 -1
- package/lib/css-D2jb7X8b.js +320 -0
- package/lib/css.d.ts +82 -0
- package/lib/css.js +134 -0
- package/lib/dev.d.ts +2 -2
- package/lib/etag.d.ts +1 -1
- package/lib/factory.d.ts +2 -2
- package/lib/hooks-BMw6BAyP.js +762 -0
- package/lib/html-SllAe0YT.d.ts +46 -0
- package/lib/html.d.ts +1 -1
- package/lib/{index-m12zcmph.d.ts → index-Bb7YJKCq.d.ts} +3 -3
- package/lib/{index-Kqou8Fjh.d.ts → index-BvFh1Gfx.d.ts} +2 -2
- package/lib/index-C850MeBA.d.ts +94 -0
- package/lib/{index-DtEoak1i.d.ts → index-CTy4N7ng.d.ts} +2 -2
- package/lib/index.d.ts +4 -4
- package/lib/ip-restriction.d.ts +2 -2
- package/lib/jsx/dom/client.d.ts +30 -0
- package/lib/jsx/dom/client.js +49 -0
- package/lib/jsx/dom/css.d.ts +84 -0
- package/lib/jsx/dom/css.js +2 -0
- package/lib/jsx/dom/jsx-dev-runtime.d.ts +3 -0
- package/lib/jsx/dom/jsx-dev-runtime.js +2 -0
- package/lib/jsx/dom/jsx-runtime.d.ts +3 -0
- package/lib/jsx/dom/jsx-runtime.js +2 -0
- package/lib/jsx/dom/server.d.ts +105 -0
- package/lib/jsx/dom/server.js +37 -0
- package/lib/jsx/dom.d.ts +5 -0
- package/lib/jsx/dom.js +74 -0
- package/lib/jsx/jsx-dev-runtime.d.ts +6 -0
- package/lib/jsx/jsx-dev-runtime.js +14 -0
- package/lib/jsx/jsx-runtime.d.ts +10 -0
- package/lib/jsx/jsx-runtime.js +30 -0
- package/lib/jsx/streaming.d.ts +2 -0
- package/lib/jsx/streaming.js +2 -0
- package/lib/jsx-dev-runtime-B22O-Npk.d.ts +7 -0
- package/lib/jsx-dev-runtime-D18Y35TI.js +354 -0
- package/lib/jsx-renderer.d.ts +75 -0
- package/lib/jsx-renderer.js +99 -0
- package/lib/jsx-runtime-BVVgDSdq.d.ts +1 -0
- package/lib/jsx.d.ts +3 -0
- package/lib/jsx.js +47 -0
- package/lib/jwk.d.ts +4 -4
- package/lib/{jwt-BA65QhnJ.d.ts → jwt-BARhotDz.d.ts} +1 -1
- package/lib/jwt.d.ts +4 -4
- package/lib/language.d.ts +1 -1
- package/lib/logger.d.ts +1 -1
- package/lib/loopback-only.d.ts +1 -1
- package/lib/method-not-allowed.d.ts +2 -2
- package/lib/method-override.d.ts +2 -2
- package/lib/mount.d.ts +1 -1
- package/lib/node-server/conninfo.d.ts +1 -1
- package/lib/node-server/serve-static.d.ts +1 -1
- package/lib/node-server/serve-static.js +1 -1
- package/lib/node-server.d.ts +1 -1
- package/lib/node-server.js +1 -1
- package/lib/powered-by.d.ts +1 -1
- package/lib/pretty-json.d.ts +1 -1
- package/lib/proxy.d.ts +1 -1
- package/lib/quick.d.ts +1 -1
- package/lib/request-id.d.ts +1 -1
- package/lib/request.d.ts +1 -1
- package/lib/route.d.ts +1 -1
- package/lib/schema-validator.d.ts +1 -1
- package/lib/secure-headers.d.ts +1 -1
- package/lib/{serve-static-Dw_m6KxR.js → serve-static-B14MF1Va.js} +2 -0
- package/lib/serve-static.d.ts +1 -1
- package/lib/ssg-BwjcA-Ge.js +389 -0
- package/lib/ssg.d.ts +156 -0
- package/lib/ssg.js +2 -0
- package/lib/streaming.d.ts +1 -1
- package/lib/testing.d.ts +4 -4
- package/lib/testing.js +1 -1
- package/lib/timeout.d.ts +1 -1
- package/lib/timing.d.ts +1 -1
- package/lib/tiny.d.ts +1 -1
- package/lib/trailing-slash.d.ts +1 -1
- package/lib/{types-ZM9gIiKh.d.ts → types-Dv_nV2cv.d.ts} +1 -1
- package/lib/{types-D9DEXMjE.d.ts → types-Lqx5BxQF.d.ts} +8 -1
- package/lib/{types-Bd29gh2o.d.ts → types-zNxyEpG2.d.ts} +3 -3
- package/lib/types.d.ts +1 -1
- package/lib/utils/body.d.ts +1 -1
- package/lib/utils/cookie.d.ts +1 -1
- package/lib/utils/crypto.d.ts +1 -1
- package/lib/utils/html.d.ts +1 -45
- package/lib/utils/ipaddr.d.ts +1 -1
- package/lib/utils/jwt.d.ts +1 -1
- package/lib/utils/types.d.ts +2 -2
- package/lib/utils-Cx61GFMC.js +125 -0
- package/lib/validator.d.ts +2 -2
- package/lib/ws.d.ts +1 -1
- package/package.json +53 -1
- package/plugins/acryl-inspect/upstream.json +1 -1
- package/plugins/acryl-node-server/upstream.json +1 -1
- package/plugins/acryl-router/src/core/helper/css/common.ts +337 -0
- package/plugins/acryl-router/src/core/helper/css/index.ts +262 -0
- package/plugins/acryl-router/src/core/helper/ssg/index.ts +14 -0
- package/plugins/acryl-router/src/core/helper/ssg/middleware.ts +83 -0
- package/plugins/acryl-router/src/core/helper/ssg/plugins.ts +72 -0
- package/plugins/acryl-router/src/core/helper/ssg/ssg.ts +471 -0
- package/plugins/acryl-router/src/core/helper/ssg/utils.ts +118 -0
- package/plugins/acryl-router/src/core/jsx/base.ts +490 -0
- package/plugins/acryl-router/src/core/jsx/children.ts +20 -0
- package/plugins/acryl-router/src/core/jsx/components.ts +257 -0
- package/plugins/acryl-router/src/core/jsx/constants.ts +6 -0
- package/plugins/acryl-router/src/core/jsx/context.ts +266 -0
- package/plugins/acryl-router/src/core/jsx/dom/client.ts +89 -0
- package/plugins/acryl-router/src/core/jsx/dom/components.ts +39 -0
- package/plugins/acryl-router/src/core/jsx/dom/context.ts +52 -0
- package/plugins/acryl-router/src/core/jsx/dom/css.ts +263 -0
- package/plugins/acryl-router/src/core/jsx/dom/hooks/index.ts +91 -0
- package/plugins/acryl-router/src/core/jsx/dom/index.ts +170 -0
- package/plugins/acryl-router/src/core/jsx/dom/intrinsic-element/components.ts +438 -0
- package/plugins/acryl-router/src/core/jsx/dom/jsx-dev-runtime.ts +23 -0
- package/plugins/acryl-router/src/core/jsx/dom/jsx-runtime.ts +8 -0
- package/plugins/acryl-router/src/core/jsx/dom/render.ts +879 -0
- package/plugins/acryl-router/src/core/jsx/dom/server.ts +76 -0
- package/plugins/acryl-router/src/core/jsx/dom/utils.ts +7 -0
- package/plugins/acryl-router/src/core/jsx/hooks/index.ts +437 -0
- package/plugins/acryl-router/src/core/jsx/index.ts +115 -0
- package/plugins/acryl-router/src/core/jsx/intrinsic-element/common.ts +23 -0
- package/plugins/acryl-router/src/core/jsx/intrinsic-element/components.ts +210 -0
- package/plugins/acryl-router/src/core/jsx/intrinsic-elements.ts +938 -0
- package/plugins/acryl-router/src/core/jsx/jsx-dev-runtime.ts +26 -0
- package/plugins/acryl-router/src/core/jsx/jsx-runtime.ts +51 -0
- package/plugins/acryl-router/src/core/jsx/streaming.ts +231 -0
- package/plugins/acryl-router/src/core/jsx/types.ts +41 -0
- package/plugins/acryl-router/src/core/jsx/utils.ts +202 -0
- package/plugins/acryl-router/src/core/middleware/cache/index.ts +4 -4
- package/plugins/acryl-router/src/core/middleware/jsx-renderer/index.ts +162 -0
- package/plugins/acryl-router/src/core/utils/types.ts +6 -0
- package/plugins/acryl-router/src/helpers/index.ts +2 -0
- package/plugins/acryl-router/src/middleware/index.ts +1 -0
- package/plugins/acryl-router/upstream.json +3 -3
- package/plugins/acryl-router-http/upstream.json +1 -1
- package/plugins/acryl-state/upstream.json +1 -1
- package/plugins/desktop/upstream.json +1 -1
- package/plugins/desktop-web/upstream.json +1 -1
- package/plugins/extensions/resolve.ts +4 -0
- package/plugins/save/plugin.json +1 -1
- package/shared/AGENTS.core.md +4 -0
- package/templates/agent/tsconfig.json +7 -1
- package/templates/todo/upstream.json +1 -1
- package/plugins/acryl-inspect/tests/report.spec.ts +0 -69
- package/plugins/acryl-inspect/tests/service.spec.ts +0 -121
- package/plugins/acryl-node-server/tests/adapter/app.ts +0 -76
- package/plugins/acryl-node-server/tests/adapter/assets/.static/plain.txt +0 -1
- package/plugins/acryl-node-server/tests/adapter/assets/favicon.ico +0 -0
- package/plugins/acryl-node-server/tests/adapter/assets/secret.txt +0 -1
- package/plugins/acryl-node-server/tests/adapter/assets/static/acryl.html +0 -1
- package/plugins/acryl-node-server/tests/adapter/assets/static/admin/secret.txt +0 -1
- package/plugins/acryl-node-server/tests/adapter/assets/static/data.json +0 -5
- package/plugins/acryl-node-server/tests/adapter/assets/static/extensionless +0 -1
- package/plugins/acryl-node-server/tests/adapter/assets/static/foo..bar.txt +0 -0
- package/plugins/acryl-node-server/tests/adapter/assets/static/index.html +0 -1
- package/plugins/acryl-node-server/tests/adapter/assets/static/plain.txt +0 -1
- package/plugins/acryl-node-server/tests/adapter/assets/static-with-context-path/plain.txt +0 -1
- package/plugins/acryl-node-server/tests/adapter/assets/static-with-precompressed/hello.bin +0 -1
- package/plugins/acryl-node-server/tests/adapter/assets/static-with-precompressed/hello.bin.br +0 -1
- package/plugins/acryl-node-server/tests/adapter/assets/static-with-precompressed/hello.txt +0 -1
- package/plugins/acryl-node-server/tests/adapter/assets/static-with-precompressed/hello.txt.br +0 -1
- package/plugins/acryl-node-server/tests/adapter/assets/static-with-precompressed/hello.txt.zst +0 -1
- package/plugins/acryl-node-server/tests/adapter/conninfo.test.ts +0 -34
- package/plugins/acryl-node-server/tests/adapter/content-length.test.ts +0 -248
- package/plugins/acryl-node-server/tests/adapter/early-hints.test.ts +0 -457
- package/plugins/acryl-node-server/tests/adapter/fixtures/keys/agent1-cert.pem +0 -23
- package/plugins/acryl-node-server/tests/adapter/fixtures/keys/agent1-key.pem +0 -27
- package/plugins/acryl-node-server/tests/adapter/headers.test.ts +0 -252
- package/plugins/acryl-node-server/tests/adapter/helpers/request.ts +0 -190
- package/plugins/acryl-node-server/tests/adapter/listener.test.ts +0 -727
- package/plugins/acryl-node-server/tests/adapter/request-client-disconnect.test.ts +0 -189
- package/plugins/acryl-node-server/tests/adapter/request.test.ts +0 -1230
- package/plugins/acryl-node-server/tests/adapter/response.test.ts +0 -285
- package/plugins/acryl-node-server/tests/adapter/serve-static.test.ts +0 -849
- package/plugins/acryl-node-server/tests/adapter/server-socket.test.ts +0 -790
- package/plugins/acryl-node-server/tests/adapter/server.test.ts +0 -1312
- package/plugins/acryl-node-server/tests/adapter/setup.ts +0 -16
- package/plugins/acryl-node-server/tests/adapter/url.test.ts +0 -76
- package/plugins/acryl-node-server/tests/adapter/utils/response.test.ts +0 -23
- package/plugins/acryl-node-server/tests/adapter/utils/stream.test.ts +0 -75
- package/plugins/acryl-node-server/tests/adapter/utils.test.ts +0 -235
- package/plugins/acryl-node-server/tests/adapter/websocket.test.ts +0 -260
- package/plugins/acryl-node-server/tests/server.spec.ts +0 -141
- package/plugins/acryl-router/src/core/app.test.ts +0 -3833
- package/plugins/acryl-router/src/core/client/client.test.ts +0 -2313
- package/plugins/acryl-router/src/core/client/types.test.ts +0 -149
- package/plugins/acryl-router/src/core/client/utils.test.ts +0 -405
- package/plugins/acryl-router/src/core/compose.test.ts +0 -751
- package/plugins/acryl-router/src/core/context.test.ts +0 -629
- package/plugins/acryl-router/src/core/helper/accepts/accepts.test.ts +0 -344
- package/plugins/acryl-router/src/core/helper/adapter/index.test.ts +0 -55
- package/plugins/acryl-router/src/core/helper/cookie/index.test.ts +0 -510
- package/plugins/acryl-router/src/core/helper/dev/index.test.ts +0 -181
- package/plugins/acryl-router/src/core/helper/factory/index.test.ts +0 -434
- package/plugins/acryl-router/src/core/helper/html/index.test.ts +0 -78
- package/plugins/acryl-router/src/core/helper/proxy/index.test.ts +0 -356
- package/plugins/acryl-router/src/core/helper/route/index.test.ts +0 -259
- package/plugins/acryl-router/src/core/helper/streaming/stream.test.ts +0 -128
- package/plugins/acryl-router/src/core/helper/streaming/text.test.ts +0 -34
- package/plugins/acryl-router/src/core/helper/testing/index.test.ts +0 -42
- package/plugins/acryl-router/src/core/helper/websocket/index.test.ts +0 -124
- package/plugins/acryl-router/src/core/http-exception.test.ts +0 -45
- package/plugins/acryl-router/src/core/middleware/basic-auth/index.test.ts +0 -434
- package/plugins/acryl-router/src/core/middleware/bearer-auth/index.test.ts +0 -1018
- package/plugins/acryl-router/src/core/middleware/body-limit/index.test.ts +0 -273
- package/plugins/acryl-router/src/core/middleware/cache/index.test.ts +0 -1211
- package/plugins/acryl-router/src/core/middleware/combine/index.test.ts +0 -355
- package/plugins/acryl-router/src/core/middleware/compress/index.test.ts +0 -535
- package/plugins/acryl-router/src/core/middleware/context-storage/index.test.ts +0 -43
- package/plugins/acryl-router/src/core/middleware/cors/index.test.ts +0 -532
- package/plugins/acryl-router/src/core/middleware/csrf/index.test.ts +0 -534
- package/plugins/acryl-router/src/core/middleware/etag/digest.test.ts +0 -21
- package/plugins/acryl-router/src/core/middleware/etag/index.test.ts +0 -503
- package/plugins/acryl-router/src/core/middleware/ip-restriction/index.test.ts +0 -217
- package/plugins/acryl-router/src/core/middleware/jwk/index.test.ts +0 -1135
- package/plugins/acryl-router/src/core/middleware/jwk/keys.test.json +0 -48
- package/plugins/acryl-router/src/core/middleware/jwt/index.test.ts +0 -802
- package/plugins/acryl-router/src/core/middleware/language/index.test.ts +0 -552
- package/plugins/acryl-router/src/core/middleware/logger/index.test.ts +0 -204
- package/plugins/acryl-router/src/core/middleware/method-not-allowed/index.test.ts +0 -292
- package/plugins/acryl-router/src/core/middleware/method-override/index.test.ts +0 -221
- package/plugins/acryl-router/src/core/middleware/mount/index.test.ts +0 -334
- package/plugins/acryl-router/src/core/middleware/powered-by/index.test.ts +0 -37
- package/plugins/acryl-router/src/core/middleware/pretty-json/index.test.ts +0 -218
- package/plugins/acryl-router/src/core/middleware/request-id/index.test.ts +0 -168
- package/plugins/acryl-router/src/core/middleware/secure-headers/index.test.ts +0 -671
- package/plugins/acryl-router/src/core/middleware/serve-static/index.test.ts +0 -450
- package/plugins/acryl-router/src/core/middleware/serve-static/path.test.ts +0 -50
- package/plugins/acryl-router/src/core/middleware/timeout/index.test.ts +0 -70
- package/plugins/acryl-router/src/core/middleware/timing/index.test.ts +0 -310
- package/plugins/acryl-router/src/core/middleware/trailing-slash/index.test.ts +0 -381
- package/plugins/acryl-router/src/core/preset/quick.test.ts +0 -42
- package/plugins/acryl-router/src/core/preset/tiny.test.ts +0 -42
- package/plugins/acryl-router/src/core/request.test.ts +0 -751
- package/plugins/acryl-router/src/core/router/common.case.test.ts +0 -1132
- package/plugins/acryl-router/src/core/router/linear-router/router.test.ts +0 -80
- package/plugins/acryl-router/src/core/router/pattern-router/router.test.ts +0 -46
- package/plugins/acryl-router/src/core/router/reg-exp-router/prepared-router.test.ts +0 -154
- package/plugins/acryl-router/src/core/router/reg-exp-router/router.test.ts +0 -265
- package/plugins/acryl-router/src/core/router/smart-router/router.test.ts +0 -13
- package/plugins/acryl-router/src/core/router/trie-router/node.test.ts +0 -896
- package/plugins/acryl-router/src/core/router/trie-router/router.test.ts +0 -8
- package/plugins/acryl-router/src/core/types.test.ts +0 -4134
- package/plugins/acryl-router/src/core/utils/accept.test.ts +0 -299
- package/plugins/acryl-router/src/core/utils/basic-auth.test.ts +0 -56
- package/plugins/acryl-router/src/core/utils/body.test.ts +0 -496
- package/plugins/acryl-router/src/core/utils/buffer.test.ts +0 -147
- package/plugins/acryl-router/src/core/utils/color.test.ts +0 -23
- package/plugins/acryl-router/src/core/utils/concurrent.test.ts +0 -69
- package/plugins/acryl-router/src/core/utils/cookie.test.ts +0 -460
- package/plugins/acryl-router/src/core/utils/crypto.test.ts +0 -43
- package/plugins/acryl-router/src/core/utils/encode.test.ts +0 -61
- package/plugins/acryl-router/src/core/utils/filepath.test.ts +0 -78
- package/plugins/acryl-router/src/core/utils/html.test.ts +0 -16
- package/plugins/acryl-router/src/core/utils/ipaddr.test.ts +0 -149
- package/plugins/acryl-router/src/core/utils/jwt/jwa.test.ts +0 -86
- package/plugins/acryl-router/src/core/utils/jwt/jwt.test.ts +0 -1788
- package/plugins/acryl-router/src/core/utils/mime.test.ts +0 -64
- package/plugins/acryl-router/src/core/utils/stream.test.ts +0 -212
- package/plugins/acryl-router/src/core/utils/types.test.ts +0 -295
- package/plugins/acryl-router/src/core/utils/url.test.ts +0 -384
- package/plugins/acryl-router/src/core/validator/utils.test.ts +0 -82
- package/plugins/acryl-router/src/core/validator/validator.test.ts +0 -1488
- package/plugins/acryl-router/tests/docs-examples.spec.ts +0 -152
- package/plugins/acryl-router/tests/live-install.spec.ts +0 -64
- package/plugins/acryl-router/tests/loader.spec.ts +0 -72
- package/plugins/acryl-router/tests/loopback-only.spec.ts +0 -80
- package/plugins/acryl-router/tests/no-dom/consumer.ts +0 -11
- package/plugins/acryl-router/tests/no-dom/tsconfig.json +0 -13
- package/plugins/acryl-router/tests/service.spec.ts +0 -426
- package/plugins/acryl-router/tests/shadow-state.spec.ts +0 -79
- package/plugins/acryl-router-http/tests/adapter.spec.ts +0 -174
- package/plugins/acryl-router-http/tests/stream.spec.ts +0 -133
- package/plugins/acryl-router-http/tests/surfaces.spec.ts +0 -101
- package/plugins/acryl-state/src/react.ts +0 -11
- package/plugins/acryl-state/tests/cell.spec.ts +0 -71
- package/plugins/acryl-state/tests/react.spec.ts +0 -39
- package/plugins/acryl-state/tests/service.spec.ts +0 -132
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* @module
|
|
3
|
+
* This module provides Acryl's JSX dev runtime.
|
|
4
|
+
*/
|
|
5
|
+
|
|
6
|
+
import type { HtmlEscapedString } from '../utils/html.ts'
|
|
7
|
+
import { jsxFn } from './base.ts'
|
|
8
|
+
import type { JSXNode } from './base.ts'
|
|
9
|
+
export { Fragment } from './base.ts'
|
|
10
|
+
export type { JSX } from './base.ts'
|
|
11
|
+
|
|
12
|
+
export function jsxDEV(
|
|
13
|
+
tag: string | Function,
|
|
14
|
+
props: Record<string, unknown>,
|
|
15
|
+
key?: string
|
|
16
|
+
): JSXNode {
|
|
17
|
+
let node: JSXNode
|
|
18
|
+
if (!props || !('children' in props)) {
|
|
19
|
+
node = jsxFn(tag, props, [])
|
|
20
|
+
} else {
|
|
21
|
+
const children = props.children as string | HtmlEscapedString
|
|
22
|
+
node = Array.isArray(children) ? jsxFn(tag, props, children) : jsxFn(tag, props, [children])
|
|
23
|
+
}
|
|
24
|
+
node.key = key
|
|
25
|
+
return node
|
|
26
|
+
}
|
|
@@ -0,0 +1,51 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* @module
|
|
3
|
+
* This module provides Acryl's JSX runtime.
|
|
4
|
+
*/
|
|
5
|
+
|
|
6
|
+
export { jsxDEV as jsx, Fragment } from './jsx-dev-runtime.ts'
|
|
7
|
+
export { jsxDEV as jsxs } from './jsx-dev-runtime.ts'
|
|
8
|
+
export type { JSX } from './jsx-dev-runtime.ts'
|
|
9
|
+
import { html, raw } from '../helper/html/index.ts'
|
|
10
|
+
import type { HtmlEscapedString, StringBuffer, HtmlEscaped } from '../utils/html.ts'
|
|
11
|
+
import { escapeToBuffer, stringBufferToString } from '../utils/html.ts'
|
|
12
|
+
import { isValidAttributeName, styleObjectForEach } from './utils.ts'
|
|
13
|
+
|
|
14
|
+
export { html as jsxTemplate }
|
|
15
|
+
|
|
16
|
+
export const jsxAttr = (
|
|
17
|
+
key: string,
|
|
18
|
+
v: string | Promise<string> | Record<string, string | number | null | undefined | boolean>
|
|
19
|
+
): HtmlEscapedString | Promise<HtmlEscapedString> => {
|
|
20
|
+
if (!isValidAttributeName(key)) {
|
|
21
|
+
return raw('')
|
|
22
|
+
}
|
|
23
|
+
const buffer: StringBuffer = [`${key}="`] as StringBuffer
|
|
24
|
+
if (key === 'style' && typeof v === 'object') {
|
|
25
|
+
// object to style strings
|
|
26
|
+
let styleStr = ''
|
|
27
|
+
styleObjectForEach(v as Record<string, string | number>, (property, value) => {
|
|
28
|
+
if (value != null) {
|
|
29
|
+
styleStr += `${styleStr ? ';' : ''}${property}:${value}`
|
|
30
|
+
}
|
|
31
|
+
})
|
|
32
|
+
escapeToBuffer(styleStr, buffer)
|
|
33
|
+
buffer[0] += '"'
|
|
34
|
+
} else if (typeof v === 'string') {
|
|
35
|
+
escapeToBuffer(v, buffer)
|
|
36
|
+
buffer[0] += '"'
|
|
37
|
+
} else if (v === null || v === undefined) {
|
|
38
|
+
return raw('')
|
|
39
|
+
} else if (typeof v === 'number' || (v as unknown as HtmlEscaped).isEscaped) {
|
|
40
|
+
buffer[0] += `${v}"`
|
|
41
|
+
} else if (v instanceof Promise) {
|
|
42
|
+
buffer.unshift('"', v)
|
|
43
|
+
} else {
|
|
44
|
+
escapeToBuffer(v.toString(), buffer)
|
|
45
|
+
buffer[0] += '"'
|
|
46
|
+
}
|
|
47
|
+
|
|
48
|
+
return buffer.length === 1 ? raw(buffer[0]) : stringBufferToString(buffer, undefined)
|
|
49
|
+
}
|
|
50
|
+
|
|
51
|
+
export const jsxEscape = (value: string) => value
|
|
@@ -0,0 +1,231 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* @module
|
|
3
|
+
* This module enables JSX to supports streaming Response.
|
|
4
|
+
*/
|
|
5
|
+
|
|
6
|
+
import { raw } from '../helper/html/index.ts'
|
|
7
|
+
import { HtmlEscapedCallbackPhase, resolveCallback } from '../utils/html.ts'
|
|
8
|
+
import type { HtmlEscapedString } from '../utils/html.ts'
|
|
9
|
+
import type { Child, FC, PropsWithChildren, Context as JSXContext } from './index.ts'
|
|
10
|
+
import { isUntrustedObject, JSXNode, renderChildren, renderUntrustedObject } from './base.ts'
|
|
11
|
+
import { childrenToString } from './components.ts'
|
|
12
|
+
import { DOM_RENDERER, DOM_STASH } from './constants.ts'
|
|
13
|
+
import { captureRenderContext, createContext, useContext } from './context.ts'
|
|
14
|
+
import { Suspense as SuspenseDomRenderer } from './dom/components.ts'
|
|
15
|
+
import { buildDataStack } from './dom/render.ts'
|
|
16
|
+
import type { HasRenderToDom, NodeObject } from './dom/render.ts'
|
|
17
|
+
|
|
18
|
+
/**
|
|
19
|
+
* Used to specify nonce for scripts generated by `Suspense` and `ErrorBoundary`.
|
|
20
|
+
*
|
|
21
|
+
* @example
|
|
22
|
+
* ```tsx
|
|
23
|
+
* <StreamingContext.Provider value={{ scriptNonce: 'test-nonce' }}>
|
|
24
|
+
* <Suspense fallback={<p>Loading...</p>}>
|
|
25
|
+
* <Content />
|
|
26
|
+
* </Suspense>
|
|
27
|
+
* </StreamingContext.Provider>
|
|
28
|
+
* ```
|
|
29
|
+
*/
|
|
30
|
+
export const StreamingContext: JSXContext<{ scriptNonce: string } | null> = createContext<{
|
|
31
|
+
scriptNonce: string
|
|
32
|
+
} | null>(null)
|
|
33
|
+
|
|
34
|
+
let suspenseCounter = 0
|
|
35
|
+
|
|
36
|
+
const serializeBoundaryChild = (child: Child): string | Promise<string> =>
|
|
37
|
+
typeof child === 'string' || Array.isArray(child)
|
|
38
|
+
? renderChildren([child])
|
|
39
|
+
: child == null || typeof child === 'boolean'
|
|
40
|
+
? ''
|
|
41
|
+
: isUntrustedObject(child)
|
|
42
|
+
? renderUntrustedObject(child)
|
|
43
|
+
: child.toString()
|
|
44
|
+
|
|
45
|
+
/**
|
|
46
|
+
* @experimental
|
|
47
|
+
* `Suspense` is an experimental feature.
|
|
48
|
+
* The API might be changed.
|
|
49
|
+
*/
|
|
50
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
51
|
+
export const Suspense: FC<PropsWithChildren<{ fallback: any }>> = async ({
|
|
52
|
+
children,
|
|
53
|
+
fallback,
|
|
54
|
+
}) => {
|
|
55
|
+
if (!Array.isArray(children)) {
|
|
56
|
+
children = [children]
|
|
57
|
+
}
|
|
58
|
+
|
|
59
|
+
const nonce = useContext(StreamingContext)?.scriptNonce
|
|
60
|
+
|
|
61
|
+
let resArray: HtmlEscapedString[] | Promise<HtmlEscapedString[]>[] = []
|
|
62
|
+
|
|
63
|
+
// for use() hook
|
|
64
|
+
const stackNode = { [DOM_STASH]: [0, []] } as unknown as NodeObject
|
|
65
|
+
const popNodeStack = () => {
|
|
66
|
+
buildDataStack.pop()
|
|
67
|
+
}
|
|
68
|
+
|
|
69
|
+
try {
|
|
70
|
+
stackNode[DOM_STASH][0] = 0
|
|
71
|
+
buildDataStack.push([[], stackNode])
|
|
72
|
+
resArray = children.map(serializeBoundaryChild) as HtmlEscapedString[]
|
|
73
|
+
} catch (e) {
|
|
74
|
+
if (e instanceof Promise) {
|
|
75
|
+
// Capture before deferring: on the fallback path the render context is
|
|
76
|
+
// observable here but not in the `.then()` below.
|
|
77
|
+
const resume = captureRenderContext()
|
|
78
|
+
resArray = [
|
|
79
|
+
e.then(() =>
|
|
80
|
+
resume(() => {
|
|
81
|
+
stackNode[DOM_STASH][0] = 0
|
|
82
|
+
buildDataStack.push([[], stackNode])
|
|
83
|
+
return childrenToString(children as Child[]).finally(popNodeStack)
|
|
84
|
+
})
|
|
85
|
+
),
|
|
86
|
+
] as Promise<HtmlEscapedString[]>[]
|
|
87
|
+
} else {
|
|
88
|
+
throw e
|
|
89
|
+
}
|
|
90
|
+
} finally {
|
|
91
|
+
popNodeStack()
|
|
92
|
+
}
|
|
93
|
+
|
|
94
|
+
if (resArray.some((res) => (res as {}) instanceof Promise)) {
|
|
95
|
+
const index = suspenseCounter++
|
|
96
|
+
const fallbackStr = await (typeof fallback === 'string' || Array.isArray(fallback)
|
|
97
|
+
? renderChildren([fallback])
|
|
98
|
+
: isUntrustedObject(fallback)
|
|
99
|
+
? renderUntrustedObject(fallback)
|
|
100
|
+
: fallback.toString())
|
|
101
|
+
return raw(`<template id="H:${index}"></template>${fallbackStr}<!--/$-->`, [
|
|
102
|
+
...(fallbackStr.callbacks || []),
|
|
103
|
+
({ phase, buffer, context }) => {
|
|
104
|
+
if (phase === HtmlEscapedCallbackPhase.BeforeStream) {
|
|
105
|
+
return
|
|
106
|
+
}
|
|
107
|
+
return Promise.all(resArray).then(async (htmlArray) => {
|
|
108
|
+
htmlArray = htmlArray.flat()
|
|
109
|
+
const content = htmlArray.join('')
|
|
110
|
+
if (buffer) {
|
|
111
|
+
buffer[0] = buffer[0].replace(
|
|
112
|
+
new RegExp(`<template id="H:${index}"></template>.*?<!--/\\$-->`, 's'),
|
|
113
|
+
() => content
|
|
114
|
+
)
|
|
115
|
+
}
|
|
116
|
+
let html = buffer
|
|
117
|
+
? ''
|
|
118
|
+
: `<template data-acryl-target="H:${index}">${content}</template><script${
|
|
119
|
+
nonce ? ` nonce="${nonce}"` : ''
|
|
120
|
+
}>
|
|
121
|
+
((d,c,n) => {
|
|
122
|
+
c=d.currentScript.previousSibling
|
|
123
|
+
d=d.getElementById('H:${index}')
|
|
124
|
+
if(!d)return
|
|
125
|
+
do{n=d.nextSibling;n.remove()}while(n.nodeType!=8||n.nodeValue!='/$')
|
|
126
|
+
d.replaceWith(c.content)
|
|
127
|
+
})(document)
|
|
128
|
+
</script>`
|
|
129
|
+
|
|
130
|
+
const callbacks = htmlArray
|
|
131
|
+
.map((html) => (html as HtmlEscapedString).callbacks || [])
|
|
132
|
+
.flat()
|
|
133
|
+
if (!callbacks.length) {
|
|
134
|
+
return html
|
|
135
|
+
}
|
|
136
|
+
|
|
137
|
+
if (phase === HtmlEscapedCallbackPhase.Stream) {
|
|
138
|
+
html = await resolveCallback(html, HtmlEscapedCallbackPhase.BeforeStream, true, context)
|
|
139
|
+
}
|
|
140
|
+
|
|
141
|
+
return raw(html, callbacks)
|
|
142
|
+
})
|
|
143
|
+
},
|
|
144
|
+
])
|
|
145
|
+
} else {
|
|
146
|
+
return raw(resArray.join(''))
|
|
147
|
+
}
|
|
148
|
+
}
|
|
149
|
+
;(Suspense as HasRenderToDom)[DOM_RENDERER] = SuspenseDomRenderer
|
|
150
|
+
|
|
151
|
+
const textEncoder = new TextEncoder()
|
|
152
|
+
/**
|
|
153
|
+
* @experimental
|
|
154
|
+
* `renderToReadableStream()` is an experimental feature.
|
|
155
|
+
* The API might be changed.
|
|
156
|
+
*/
|
|
157
|
+
export const renderToReadableStream = (
|
|
158
|
+
content: HtmlEscapedString | JSXNode | Promise<HtmlEscapedString>,
|
|
159
|
+
onError: (e: unknown) => string | void = console.trace
|
|
160
|
+
): ReadableStream<Uint8Array> => {
|
|
161
|
+
let cancelled = false
|
|
162
|
+
const reader = new ReadableStream<Uint8Array>({
|
|
163
|
+
async start(controller) {
|
|
164
|
+
try {
|
|
165
|
+
if (content instanceof JSXNode) {
|
|
166
|
+
// aJSXNode.toString() returns a string or Promise<string> and string is already escaped
|
|
167
|
+
content = content.toString() as HtmlEscapedString | Promise<HtmlEscapedString>
|
|
168
|
+
}
|
|
169
|
+
const context = typeof content === 'object' ? content : {}
|
|
170
|
+
const resolved = await resolveCallback(
|
|
171
|
+
content,
|
|
172
|
+
HtmlEscapedCallbackPhase.BeforeStream,
|
|
173
|
+
true,
|
|
174
|
+
context
|
|
175
|
+
)
|
|
176
|
+
if (!cancelled) {
|
|
177
|
+
controller.enqueue(textEncoder.encode(resolved))
|
|
178
|
+
}
|
|
179
|
+
|
|
180
|
+
let resolvedCount = 0
|
|
181
|
+
const callbacks: Promise<void>[] = []
|
|
182
|
+
const then = (promise: Promise<string>) => {
|
|
183
|
+
callbacks.push(
|
|
184
|
+
promise
|
|
185
|
+
.catch((err) => {
|
|
186
|
+
console.log(err)
|
|
187
|
+
onError(err)
|
|
188
|
+
return ''
|
|
189
|
+
})
|
|
190
|
+
.then(async (res) => {
|
|
191
|
+
res = await resolveCallback(
|
|
192
|
+
res,
|
|
193
|
+
HtmlEscapedCallbackPhase.BeforeStream,
|
|
194
|
+
true,
|
|
195
|
+
context
|
|
196
|
+
)
|
|
197
|
+
;(res as HtmlEscapedString).callbacks
|
|
198
|
+
?.map((c) => c({ phase: HtmlEscapedCallbackPhase.Stream, context }))
|
|
199
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
200
|
+
.filter<Promise<string>>(Boolean as any)
|
|
201
|
+
.forEach(then)
|
|
202
|
+
resolvedCount++
|
|
203
|
+
if (!cancelled) {
|
|
204
|
+
controller.enqueue(textEncoder.encode(res))
|
|
205
|
+
}
|
|
206
|
+
})
|
|
207
|
+
)
|
|
208
|
+
}
|
|
209
|
+
;(resolved as HtmlEscapedString).callbacks
|
|
210
|
+
?.map((c) => c({ phase: HtmlEscapedCallbackPhase.Stream, context }))
|
|
211
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
212
|
+
.filter<Promise<string>>(Boolean as any)
|
|
213
|
+
.forEach(then)
|
|
214
|
+
while (resolvedCount !== callbacks.length) {
|
|
215
|
+
await Promise.all(callbacks)
|
|
216
|
+
}
|
|
217
|
+
} catch (e) {
|
|
218
|
+
// maybe the connection was closed
|
|
219
|
+
onError(e)
|
|
220
|
+
}
|
|
221
|
+
|
|
222
|
+
if (!cancelled) {
|
|
223
|
+
controller.close()
|
|
224
|
+
}
|
|
225
|
+
},
|
|
226
|
+
cancel() {
|
|
227
|
+
cancelled = true
|
|
228
|
+
},
|
|
229
|
+
})
|
|
230
|
+
return reader
|
|
231
|
+
}
|
|
@@ -0,0 +1,41 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* All types exported from "acryl-router/jsx" are in this file.
|
|
3
|
+
*/
|
|
4
|
+
import type { Child, JSXNode } from './base.ts'
|
|
5
|
+
import type { JSX } from './intrinsic-elements.ts'
|
|
6
|
+
import type { DomEvent } from '../utils/types.ts'
|
|
7
|
+
|
|
8
|
+
export type { Child, JSXNode, FC } from './base.ts'
|
|
9
|
+
export type { RefObject } from './hooks/index.ts'
|
|
10
|
+
export type { Context } from './context.ts'
|
|
11
|
+
|
|
12
|
+
export type PropsWithChildren<P = unknown> = P & { children?: Child | undefined }
|
|
13
|
+
export type CSSProperties = JSX.CSSProperties
|
|
14
|
+
|
|
15
|
+
/**
|
|
16
|
+
* React types
|
|
17
|
+
*/
|
|
18
|
+
|
|
19
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
20
|
+
type ReactElement<P = any, T = string | Function> = JSXNode & {
|
|
21
|
+
type: T
|
|
22
|
+
props: P
|
|
23
|
+
key: string | null
|
|
24
|
+
}
|
|
25
|
+
type ReactNode = ReactElement | string | number | boolean | null | undefined
|
|
26
|
+
type ComponentClass<_P = {}, _S = {}> = unknown
|
|
27
|
+
|
|
28
|
+
export type { ReactElement, ReactNode, ComponentClass }
|
|
29
|
+
|
|
30
|
+
export type Event = globalThis.Event
|
|
31
|
+
export type MouseEvent = DomEvent<'MouseEvent'>
|
|
32
|
+
export type KeyboardEvent = DomEvent<'KeyboardEvent'>
|
|
33
|
+
export type FocusEvent = DomEvent<'FocusEvent'>
|
|
34
|
+
export type ClipboardEvent = DomEvent<'ClipboardEvent'>
|
|
35
|
+
export type InputEvent = DomEvent<'InputEvent'>
|
|
36
|
+
export type PointerEvent = DomEvent<'PointerEvent'>
|
|
37
|
+
export type TouchEvent = DomEvent<'TouchEvent'>
|
|
38
|
+
export type WheelEvent = DomEvent<'WheelEvent'>
|
|
39
|
+
export type AnimationEvent = DomEvent<'AnimationEvent'>
|
|
40
|
+
export type TransitionEvent = DomEvent<'TransitionEvent'>
|
|
41
|
+
export type DragEvent = DomEvent<'DragEvent'>
|
|
@@ -0,0 +1,202 @@
|
|
|
1
|
+
const normalizeElementKeyMap: Map<string, string> = new Map([
|
|
2
|
+
['className', 'class'],
|
|
3
|
+
['htmlFor', 'for'],
|
|
4
|
+
['crossOrigin', 'crossorigin'],
|
|
5
|
+
['httpEquiv', 'http-equiv'],
|
|
6
|
+
['itemProp', 'itemprop'],
|
|
7
|
+
['fetchPriority', 'fetchpriority'],
|
|
8
|
+
['noModule', 'nomodule'],
|
|
9
|
+
['formAction', 'formaction'],
|
|
10
|
+
])
|
|
11
|
+
export const normalizeIntrinsicElementKey = (key: string): string =>
|
|
12
|
+
normalizeElementKeyMap.get(key) || key
|
|
13
|
+
|
|
14
|
+
// eslint-disable-next-line no-control-regex
|
|
15
|
+
const invalidAttributeNameCharRe = /[\s"'<>/=`\\\x00-\x1f\x7f-\x9f]/
|
|
16
|
+
const validAttributeNameCache = new Set<string>()
|
|
17
|
+
const validAttributeNameCacheMax = 1024
|
|
18
|
+
// reject HTML parser-control tag starters ('!' for comments/doctype, '?' for
|
|
19
|
+
// processing instructions) in addition to the shared invalid-char set
|
|
20
|
+
// eslint-disable-next-line no-control-regex
|
|
21
|
+
const invalidTagNameCharRe = /^[!?]|[\s"'<>/=`\\\x00-\x1f\x7f-\x9f]/
|
|
22
|
+
const validTagNameCache = new Set<unknown>()
|
|
23
|
+
const validTagNameCacheMax = 256
|
|
24
|
+
|
|
25
|
+
const cacheValidName = (cache: Set<unknown>, max: number, name: string): void => {
|
|
26
|
+
if (cache.size >= max) {
|
|
27
|
+
cache.clear()
|
|
28
|
+
}
|
|
29
|
+
cache.add(name)
|
|
30
|
+
}
|
|
31
|
+
|
|
32
|
+
export const isValidTagName = (name: unknown): name is string => {
|
|
33
|
+
if (validTagNameCache.has(name)) {
|
|
34
|
+
return true
|
|
35
|
+
}
|
|
36
|
+
if (typeof name !== 'string') {
|
|
37
|
+
return false
|
|
38
|
+
}
|
|
39
|
+
if (name.length === 0) {
|
|
40
|
+
return true
|
|
41
|
+
}
|
|
42
|
+
if (invalidTagNameCharRe.test(name)) {
|
|
43
|
+
return false
|
|
44
|
+
}
|
|
45
|
+
cacheValidName(validTagNameCache, validTagNameCacheMax, name)
|
|
46
|
+
return true
|
|
47
|
+
}
|
|
48
|
+
|
|
49
|
+
export const isValidAttributeName = (name: string): boolean => {
|
|
50
|
+
if (validAttributeNameCache.has(name)) {
|
|
51
|
+
return true
|
|
52
|
+
}
|
|
53
|
+
const len = name.length
|
|
54
|
+
if (len === 0) {
|
|
55
|
+
return false
|
|
56
|
+
}
|
|
57
|
+
for (let i = 0; i < len; i++) {
|
|
58
|
+
const c = name.charCodeAt(i)
|
|
59
|
+
if (
|
|
60
|
+
!(
|
|
61
|
+
(c >= 0x61 && c <= 0x7a) || // a-z
|
|
62
|
+
(c >= 0x41 && c <= 0x5a) || // A-Z
|
|
63
|
+
(c >= 0x30 && c <= 0x39) || // 0-9
|
|
64
|
+
c === 0x2d || // -
|
|
65
|
+
c === 0x5f || // _
|
|
66
|
+
c === 0x2e || // .
|
|
67
|
+
c === 0x3a // :
|
|
68
|
+
)
|
|
69
|
+
) {
|
|
70
|
+
// non-fast-path character found — fall back to regex for the full name
|
|
71
|
+
if (!invalidAttributeNameCharRe.test(name)) {
|
|
72
|
+
cacheValidName(validAttributeNameCache, validAttributeNameCacheMax, name)
|
|
73
|
+
return true
|
|
74
|
+
} else {
|
|
75
|
+
return false
|
|
76
|
+
}
|
|
77
|
+
}
|
|
78
|
+
}
|
|
79
|
+
cacheValidName(validAttributeNameCache, validAttributeNameCacheMax, name)
|
|
80
|
+
return true
|
|
81
|
+
}
|
|
82
|
+
|
|
83
|
+
// eslint-disable-next-line no-control-regex
|
|
84
|
+
const invalidStylePropertyNameCharRe = /[\s"'():;\\/\[\]{}\x00-\x1f\x7f-\x9f]/
|
|
85
|
+
const validStylePropertyNameCache = new Set<string>()
|
|
86
|
+
const validStylePropertyNameCacheMax = 1024
|
|
87
|
+
|
|
88
|
+
const isValidStylePropertyName = (name: string): boolean => {
|
|
89
|
+
if (validStylePropertyNameCache.has(name)) {
|
|
90
|
+
return true
|
|
91
|
+
}
|
|
92
|
+
const len = name.length
|
|
93
|
+
if (len === 0) {
|
|
94
|
+
return false
|
|
95
|
+
}
|
|
96
|
+
for (let i = 0; i < len; i++) {
|
|
97
|
+
const c = name.charCodeAt(i)
|
|
98
|
+
if (
|
|
99
|
+
!(
|
|
100
|
+
(c >= 0x61 && c <= 0x7a) || // a-z
|
|
101
|
+
(c >= 0x41 && c <= 0x5a) || // A-Z
|
|
102
|
+
(c >= 0x30 && c <= 0x39) || // 0-9
|
|
103
|
+
c === 0x2d || // -
|
|
104
|
+
c === 0x5f // _
|
|
105
|
+
)
|
|
106
|
+
) {
|
|
107
|
+
// non-fast-path character found — fall back to regex for the full name
|
|
108
|
+
if (!invalidStylePropertyNameCharRe.test(name)) {
|
|
109
|
+
cacheValidName(validStylePropertyNameCache, validStylePropertyNameCacheMax, name)
|
|
110
|
+
return true
|
|
111
|
+
} else {
|
|
112
|
+
return false
|
|
113
|
+
}
|
|
114
|
+
}
|
|
115
|
+
}
|
|
116
|
+
cacheValidName(validStylePropertyNameCache, validStylePropertyNameCacheMax, name)
|
|
117
|
+
return true
|
|
118
|
+
}
|
|
119
|
+
|
|
120
|
+
const unsafeStyleValueCharRe = /[;"'\\/\[\](){}]/
|
|
121
|
+
|
|
122
|
+
const hasUnsafeStyleValue = (value: string): boolean => {
|
|
123
|
+
if (!unsafeStyleValueCharRe.test(value)) {
|
|
124
|
+
return false
|
|
125
|
+
}
|
|
126
|
+
|
|
127
|
+
let quote = 0
|
|
128
|
+
const blockStack: number[] = []
|
|
129
|
+
for (let i = 0, len = value.length; i < len; i++) {
|
|
130
|
+
const c = value.charCodeAt(i)
|
|
131
|
+
if (c === 0x5c) {
|
|
132
|
+
if (i === len - 1) {
|
|
133
|
+
return true
|
|
134
|
+
}
|
|
135
|
+
i++
|
|
136
|
+
} else if (quote !== 0) {
|
|
137
|
+
if (c === 0x0a || c === 0x0c || c === 0x0d) {
|
|
138
|
+
return true
|
|
139
|
+
}
|
|
140
|
+
if (c === quote) {
|
|
141
|
+
quote = 0
|
|
142
|
+
}
|
|
143
|
+
} else if (c === 0x2f && value.charCodeAt(i + 1) === 0x2a) {
|
|
144
|
+
const end = value.indexOf('*/', i + 2)
|
|
145
|
+
if (end === -1) {
|
|
146
|
+
return true
|
|
147
|
+
}
|
|
148
|
+
i = end + 1
|
|
149
|
+
} else if (c === 0x22 || c === 0x27) {
|
|
150
|
+
quote = c
|
|
151
|
+
} else if (c === 0x28) {
|
|
152
|
+
blockStack.push(0x29)
|
|
153
|
+
} else if (c === 0x5b) {
|
|
154
|
+
blockStack.push(0x5d)
|
|
155
|
+
} else if (c === 0x7b || c === 0x7d) {
|
|
156
|
+
return true
|
|
157
|
+
} else if (c === 0x29 || c === 0x5d) {
|
|
158
|
+
if (blockStack[blockStack.length - 1] !== c) {
|
|
159
|
+
return true
|
|
160
|
+
}
|
|
161
|
+
blockStack.pop()
|
|
162
|
+
} else if (c === 0x3b && blockStack.length === 0) {
|
|
163
|
+
return true
|
|
164
|
+
}
|
|
165
|
+
}
|
|
166
|
+
return quote !== 0 || blockStack.length !== 0
|
|
167
|
+
}
|
|
168
|
+
|
|
169
|
+
export const styleObjectForEach = (
|
|
170
|
+
style: Record<string, unknown>,
|
|
171
|
+
fn: (key: string, value: string | null) => void
|
|
172
|
+
): void => {
|
|
173
|
+
for (const [k, v] of Object.entries(style)) {
|
|
174
|
+
const key =
|
|
175
|
+
k[0] === '-' || !/[A-Z]/.test(k)
|
|
176
|
+
? k // a CSS variable or a lowercase only property
|
|
177
|
+
: k.replace(/[A-Z]/g, (m) => `-${m.toLowerCase()}`) // a camelCase property. convert to kebab-case
|
|
178
|
+
if (!isValidStylePropertyName(key)) {
|
|
179
|
+
continue
|
|
180
|
+
}
|
|
181
|
+
if (v == null) {
|
|
182
|
+
fn(key, null)
|
|
183
|
+
continue
|
|
184
|
+
}
|
|
185
|
+
let value: string
|
|
186
|
+
if (typeof v === 'number') {
|
|
187
|
+
value = !key.match(
|
|
188
|
+
/^(?:a|border-im|column(?:-c|s)|flex(?:$|-[^b])|grid-(?!.*gap)(?:ar|[^a])|font-w|li|or|sca|st|ta|wido|z)|ty$/
|
|
189
|
+
)
|
|
190
|
+
? `${v}px`
|
|
191
|
+
: `${v}`
|
|
192
|
+
} else if (typeof v === 'string') {
|
|
193
|
+
if (hasUnsafeStyleValue(v)) {
|
|
194
|
+
continue
|
|
195
|
+
}
|
|
196
|
+
value = v
|
|
197
|
+
} else {
|
|
198
|
+
continue
|
|
199
|
+
}
|
|
200
|
+
fn(key, value)
|
|
201
|
+
}
|
|
202
|
+
}
|
|
@@ -17,10 +17,10 @@ const defaultCacheableStatusCodes: ReadonlyArray<StatusCode> = [200]
|
|
|
17
17
|
const defaultMaxQueryBodySize = 64 * 1024
|
|
18
18
|
|
|
19
19
|
const cacheKeyPath = '/.acryl-router/cache'
|
|
20
|
-
const cacheKeyParameter = '
|
|
21
|
-
const cacheMethodKeyParameter = '
|
|
22
|
-
const queryDigestKeyParameter = '
|
|
23
|
-
const cacheVaryKeyParameter = '
|
|
20
|
+
const cacheKeyParameter = '__acryl_cache_key'
|
|
21
|
+
const cacheMethodKeyParameter = '__acryl_cache_method'
|
|
22
|
+
const queryDigestKeyParameter = '__acryl_query_digest'
|
|
23
|
+
const cacheVaryKeyParameter = '__acryl_cache_vary'
|
|
24
24
|
|
|
25
25
|
type CacheKeyRequest =
|
|
26
26
|
| { method: 'GET' }
|