@cdklabs/cdk-construct-connect-datalake 0.0.12 → 0.0.14
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/.jsii +11 -11
- package/.jsii.tabl.json +1 -1
- package/lib/index.js +1 -1
- package/node_modules/@aws-sdk/client-cloudformation/README.md +1 -1
- package/node_modules/@aws-sdk/client-cloudformation/dist-types/CloudFormation.d.ts +1 -1
- package/node_modules/@aws-sdk/client-cloudformation/dist-types/CloudFormationClient.d.ts +1 -1
- package/node_modules/@aws-sdk/client-cloudformation/dist-types/index.d.ts +1 -1
- package/node_modules/@aws-sdk/client-cloudformation/dist-types/models/models_0.d.ts +1 -1
- package/node_modules/@aws-sdk/client-cloudformation/package.json +10 -10
- package/node_modules/@aws-sdk/client-connect/README.md +11 -6
- package/node_modules/@aws-sdk/client-connect/dist-cjs/schemas/schemas_0.js +74 -47
- package/node_modules/@aws-sdk/client-connect/dist-es/schemas/schemas_0.js +43 -16
- package/node_modules/@aws-sdk/client-connect/dist-types/Connect.d.ts +12 -7
- package/node_modules/@aws-sdk/client-connect/dist-types/ConnectClient.d.ts +12 -7
- package/node_modules/@aws-sdk/client-connect/dist-types/commands/CreateVocabularyCommand.d.ts +2 -1
- package/node_modules/@aws-sdk/client-connect/dist-types/commands/GetMetricDataV2Command.d.ts +2 -1
- package/node_modules/@aws-sdk/client-connect/dist-types/commands/SearchContactsCommand.d.ts +17 -0
- package/node_modules/@aws-sdk/client-connect/dist-types/commands/SearchPromptsCommand.d.ts +1 -2
- package/node_modules/@aws-sdk/client-connect/dist-types/commands/SearchQueuesCommand.d.ts +1 -2
- package/node_modules/@aws-sdk/client-connect/dist-types/index.d.ts +12 -7
- package/node_modules/@aws-sdk/client-connect/dist-types/models/models_0.d.ts +40 -37
- package/node_modules/@aws-sdk/client-connect/dist-types/models/models_1.d.ts +152 -59
- package/node_modules/@aws-sdk/client-connect/dist-types/models/models_2.d.ts +69 -63
- package/node_modules/@aws-sdk/client-connect/dist-types/models/models_3.d.ts +72 -16
- package/node_modules/@aws-sdk/client-connect/dist-types/schemas/schemas_0.d.ts +3 -0
- package/node_modules/@aws-sdk/client-connect/dist-types/ts3.4/commands/CreateVocabularyCommand.d.ts +2 -4
- package/node_modules/@aws-sdk/client-connect/dist-types/ts3.4/commands/GetMetricDataV2Command.d.ts +2 -4
- package/node_modules/@aws-sdk/client-connect/dist-types/ts3.4/commands/SearchPromptsCommand.d.ts +4 -2
- package/node_modules/@aws-sdk/client-connect/dist-types/ts3.4/commands/SearchQueuesCommand.d.ts +1 -2
- package/node_modules/@aws-sdk/client-connect/dist-types/ts3.4/models/models_0.d.ts +9 -10
- package/node_modules/@aws-sdk/client-connect/dist-types/ts3.4/models/models_1.d.ts +9 -10
- package/node_modules/@aws-sdk/client-connect/dist-types/ts3.4/models/models_2.d.ts +19 -15
- package/node_modules/@aws-sdk/client-connect/dist-types/ts3.4/models/models_3.d.ts +17 -1
- package/node_modules/@aws-sdk/client-connect/dist-types/ts3.4/schemas/schemas_0.d.ts +3 -0
- package/node_modules/@aws-sdk/client-connect/package.json +10 -10
- package/node_modules/@aws-sdk/client-glue/README.md +14 -0
- package/node_modules/@aws-sdk/client-glue/dist-cjs/index.js +44 -4
- package/node_modules/@aws-sdk/client-glue/dist-cjs/models/errors.js +16 -1
- package/node_modules/@aws-sdk/client-glue/dist-cjs/schemas/schemas_0.js +133 -51
- package/node_modules/@aws-sdk/client-glue/dist-es/Glue.js +4 -0
- package/node_modules/@aws-sdk/client-glue/dist-es/commands/GetDashboardUrlCommand.js +16 -0
- package/node_modules/@aws-sdk/client-glue/dist-es/commands/GetSessionEndpointCommand.js +16 -0
- package/node_modules/@aws-sdk/client-glue/dist-es/commands/index.js +2 -0
- package/node_modules/@aws-sdk/client-glue/dist-es/models/enums.js +14 -4
- package/node_modules/@aws-sdk/client-glue/dist-es/models/errors.js +14 -0
- package/node_modules/@aws-sdk/client-glue/dist-es/schemas/schemas_0.js +108 -26
- package/node_modules/@aws-sdk/client-glue/dist-types/Glue.d.ts +14 -0
- package/node_modules/@aws-sdk/client-glue/dist-types/GlueClient.d.ts +4 -2
- package/node_modules/@aws-sdk/client-glue/dist-types/commands/CreateSessionCommand.d.ts +5 -0
- package/node_modules/@aws-sdk/client-glue/dist-types/commands/GetDashboardUrlCommand.d.ts +93 -0
- package/node_modules/@aws-sdk/client-glue/dist-types/commands/GetMLTaskRunCommand.d.ts +1 -2
- package/node_modules/@aws-sdk/client-glue/dist-types/commands/GetSessionCommand.d.ts +1 -0
- package/node_modules/@aws-sdk/client-glue/dist-types/commands/GetSessionEndpointCommand.d.ts +101 -0
- package/node_modules/@aws-sdk/client-glue/dist-types/commands/GetTableCommand.d.ts +121 -0
- package/node_modules/@aws-sdk/client-glue/dist-types/commands/GetTableVersionCommand.d.ts +118 -0
- package/node_modules/@aws-sdk/client-glue/dist-types/commands/GetTableVersionsCommand.d.ts +118 -0
- package/node_modules/@aws-sdk/client-glue/dist-types/commands/GetTablesCommand.d.ts +119 -1
- package/node_modules/@aws-sdk/client-glue/dist-types/commands/GetUnfilteredTableMetadataCommand.d.ts +118 -0
- package/node_modules/@aws-sdk/client-glue/dist-types/commands/ListSessionsCommand.d.ts +1 -0
- package/node_modules/@aws-sdk/client-glue/dist-types/commands/RunStatementCommand.d.ts +6 -0
- package/node_modules/@aws-sdk/client-glue/dist-types/commands/SearchTablesCommand.d.ts +118 -0
- package/node_modules/@aws-sdk/client-glue/dist-types/commands/UpdateCrawlerScheduleCommand.d.ts +2 -1
- package/node_modules/@aws-sdk/client-glue/dist-types/commands/UpdateDataQualityRulesetCommand.d.ts +1 -1
- package/node_modules/@aws-sdk/client-glue/dist-types/commands/UpdateDatabaseCommand.d.ts +1 -1
- package/node_modules/@aws-sdk/client-glue/dist-types/commands/index.d.ts +2 -0
- package/node_modules/@aws-sdk/client-glue/dist-types/models/enums.d.ts +38 -12
- package/node_modules/@aws-sdk/client-glue/dist-types/models/errors.d.ts +17 -0
- package/node_modules/@aws-sdk/client-glue/dist-types/models/models_1.d.ts +41 -28
- package/node_modules/@aws-sdk/client-glue/dist-types/models/models_2.d.ts +156 -102
- package/node_modules/@aws-sdk/client-glue/dist-types/models/models_3.d.ts +107 -2
- package/node_modules/@aws-sdk/client-glue/dist-types/schemas/schemas_0.d.ts +9 -0
- package/node_modules/@aws-sdk/client-glue/dist-types/ts3.4/Glue.d.ts +34 -0
- package/node_modules/@aws-sdk/client-glue/dist-types/ts3.4/GlueClient.d.ts +12 -0
- package/node_modules/@aws-sdk/client-glue/dist-types/ts3.4/commands/GetDashboardUrlCommand.d.ts +52 -0
- package/node_modules/@aws-sdk/client-glue/dist-types/ts3.4/commands/GetMLTaskRunCommand.d.ts +1 -2
- package/node_modules/@aws-sdk/client-glue/dist-types/ts3.4/commands/GetSessionEndpointCommand.d.ts +53 -0
- package/node_modules/@aws-sdk/client-glue/dist-types/ts3.4/commands/UpdateCrawlerScheduleCommand.d.ts +2 -4
- package/node_modules/@aws-sdk/client-glue/dist-types/ts3.4/commands/UpdateDataQualityRulesetCommand.d.ts +1 -1
- package/node_modules/@aws-sdk/client-glue/dist-types/ts3.4/commands/UpdateDatabaseCommand.d.ts +1 -1
- package/node_modules/@aws-sdk/client-glue/dist-types/ts3.4/commands/index.d.ts +2 -0
- package/node_modules/@aws-sdk/client-glue/dist-types/ts3.4/models/enums.d.ts +19 -6
- package/node_modules/@aws-sdk/client-glue/dist-types/ts3.4/models/errors.d.ts +8 -0
- package/node_modules/@aws-sdk/client-glue/dist-types/ts3.4/models/models_1.d.ts +12 -7
- package/node_modules/@aws-sdk/client-glue/dist-types/ts3.4/models/models_2.d.ts +36 -23
- package/node_modules/@aws-sdk/client-glue/dist-types/ts3.4/models/models_3.d.ts +24 -1
- package/node_modules/@aws-sdk/client-glue/dist-types/ts3.4/schemas/schemas_0.d.ts +9 -0
- package/node_modules/@aws-sdk/client-glue/package.json +10 -10
- package/node_modules/@aws-sdk/client-lakeformation/package.json +10 -10
- package/node_modules/@aws-sdk/client-ram/package.json +10 -10
- package/node_modules/@aws-sdk/client-sts/package.json +12 -12
- package/node_modules/@aws-sdk/core/dist-cjs/index.js +47 -2291
- package/node_modules/@aws-sdk/core/dist-cjs/submodules/httpAuthSchemes/index.js +12 -6
- package/node_modules/@aws-sdk/core/dist-es/index.js +3 -3
- package/node_modules/@aws-sdk/core/dist-es/submodules/httpAuthSchemes/aws_sdk/AwsSdkSigV4ASigner.js +1 -0
- package/node_modules/@aws-sdk/core/dist-es/submodules/httpAuthSchemes/aws_sdk/AwsSdkSigV4Signer.js +11 -6
- package/node_modules/@aws-sdk/core/dist-types/index.d.ts +5 -5
- package/node_modules/@aws-sdk/core/dist-types/ts3.4/index.d.ts +5 -5
- package/node_modules/@aws-sdk/core/package.json +12 -12
- package/node_modules/@aws-sdk/credential-provider-env/package.json +7 -7
- package/node_modules/@aws-sdk/credential-provider-http/package.json +11 -10
- package/node_modules/@aws-sdk/credential-provider-ini/package.json +15 -15
- package/node_modules/@aws-sdk/credential-provider-login/package.json +8 -8
- package/node_modules/@aws-sdk/credential-provider-node/package.json +13 -13
- package/node_modules/@aws-sdk/credential-provider-process/package.json +7 -7
- package/node_modules/@aws-sdk/credential-provider-sso/dist-cjs/index.js +4 -1
- package/node_modules/@aws-sdk/credential-provider-sso/dist-es/resolveSSOCredentials.js +4 -1
- package/node_modules/@aws-sdk/credential-provider-sso/package.json +12 -10
- package/node_modules/@aws-sdk/credential-provider-web-identity/package.json +8 -8
- package/node_modules/@aws-sdk/nested-clients/dist-cjs/submodules/cognito-identity/index.js +99 -106
- package/node_modules/@aws-sdk/nested-clients/dist-cjs/submodules/signin/index.js +62 -120
- package/node_modules/@aws-sdk/nested-clients/dist-cjs/submodules/sso/index.js +55 -86
- package/node_modules/@aws-sdk/nested-clients/dist-cjs/submodules/sso-oidc/index.js +73 -104
- package/node_modules/@aws-sdk/nested-clients/dist-cjs/submodules/sts/index.js +102 -185
- package/node_modules/@aws-sdk/nested-clients/dist-es/submodules/cognito-identity/auth/httpAuthSchemeProvider.js +4 -5
- package/node_modules/@aws-sdk/nested-clients/dist-es/submodules/cognito-identity/endpoint/bdd.js +21 -57
- package/node_modules/@aws-sdk/nested-clients/dist-es/submodules/cognito-identity/runtimeConfig.browser.js +1 -2
- package/node_modules/@aws-sdk/nested-clients/dist-es/submodules/cognito-identity/runtimeConfig.js +2 -4
- package/node_modules/@aws-sdk/nested-clients/dist-es/submodules/cognito-identity/schemas/schemas_0.js +73 -41
- package/node_modules/@aws-sdk/nested-clients/dist-es/submodules/signin/auth/httpAuthSchemeProvider.js +4 -5
- package/node_modules/@aws-sdk/nested-clients/dist-es/submodules/signin/endpoint/bdd.js +20 -52
- package/node_modules/@aws-sdk/nested-clients/dist-es/submodules/signin/runtimeConfig.browser.js +1 -2
- package/node_modules/@aws-sdk/nested-clients/dist-es/submodules/signin/runtimeConfig.js +2 -4
- package/node_modules/@aws-sdk/nested-clients/dist-es/submodules/signin/schemas/schemas_0.js +36 -59
- package/node_modules/@aws-sdk/nested-clients/dist-es/submodules/sso/auth/httpAuthSchemeProvider.js +4 -5
- package/node_modules/@aws-sdk/nested-clients/dist-es/submodules/sso/endpoint/bdd.js +17 -45
- package/node_modules/@aws-sdk/nested-clients/dist-es/submodules/sso/runtimeConfig.browser.js +1 -2
- package/node_modules/@aws-sdk/nested-clients/dist-es/submodules/sso/runtimeConfig.js +2 -4
- package/node_modules/@aws-sdk/nested-clients/dist-es/submodules/sso/schemas/schemas_0.js +32 -32
- package/node_modules/@aws-sdk/nested-clients/dist-es/submodules/sso-oidc/auth/httpAuthSchemeProvider.js +4 -5
- package/node_modules/@aws-sdk/nested-clients/dist-es/submodules/sso-oidc/endpoint/bdd.js +17 -45
- package/node_modules/@aws-sdk/nested-clients/dist-es/submodules/sso-oidc/runtimeConfig.browser.js +1 -2
- package/node_modules/@aws-sdk/nested-clients/dist-es/submodules/sso-oidc/runtimeConfig.js +2 -4
- package/node_modules/@aws-sdk/nested-clients/dist-es/submodules/sso-oidc/schemas/schemas_0.js +50 -50
- package/node_modules/@aws-sdk/nested-clients/dist-es/submodules/sts/auth/httpAuthSchemeProvider.js +4 -5
- package/node_modules/@aws-sdk/nested-clients/dist-es/submodules/sts/defaultRoleAssumers.js +1 -1
- package/node_modules/@aws-sdk/nested-clients/dist-es/submodules/sts/endpoint/bdd.js +34 -96
- package/node_modules/@aws-sdk/nested-clients/dist-es/submodules/sts/runtimeConfig.browser.js +1 -2
- package/node_modules/@aws-sdk/nested-clients/dist-es/submodules/sts/runtimeConfig.js +3 -6
- package/node_modules/@aws-sdk/nested-clients/dist-es/submodules/sts/schemas/schemas_0.js +63 -80
- package/node_modules/@aws-sdk/nested-clients/package.json +11 -11
- package/node_modules/@aws-sdk/signature-v4-multi-region/package.json +10 -9
- package/node_modules/@aws-sdk/token-providers/package.json +8 -8
- package/node_modules/@aws-sdk/types/package.json +4 -4
- package/node_modules/@aws-sdk/util-locate-window/package.json +3 -3
- package/node_modules/{strnum → @aws-sdk/xml-builder/node_modules/strnum}/CHANGELOG.md +8 -0
- package/node_modules/{strnum → @aws-sdk/xml-builder/node_modules/strnum}/README.md +9 -0
- package/node_modules/{strnum → @aws-sdk/xml-builder/node_modules/strnum}/package.json +4 -1
- package/node_modules/{strnum → @aws-sdk/xml-builder/node_modules/strnum}/strnum.js +9 -1
- package/node_modules/@aws-sdk/xml-builder/package.json +4 -4
- package/node_modules/@nodable/entities/package.json +4 -1
- package/node_modules/@nodable/entities/src/EntityDecoder.js +104 -3
- package/node_modules/@nodable/entities/src/index.d.ts +77 -0
- package/node_modules/@nodable/entities/src/index.js +1 -1
- package/node_modules/@smithy/core/dist-cjs/index.js +13 -15
- package/node_modules/@smithy/core/dist-cjs/submodules/cbor/index.js +29 -31
- package/node_modules/@smithy/core/dist-cjs/submodules/checksum/index.browser.js +2 -4
- package/node_modules/@smithy/core/dist-cjs/submodules/checksum/index.js +7 -9
- package/node_modules/@smithy/core/dist-cjs/submodules/checksum/index.native.js +3 -5
- package/node_modules/@smithy/core/dist-cjs/submodules/client/index.js +22 -23
- package/node_modules/@smithy/core/dist-cjs/submodules/config/index.browser.js +10 -11
- package/node_modules/@smithy/core/dist-cjs/submodules/config/index.js +38 -39
- package/node_modules/@smithy/core/dist-cjs/submodules/config/index.native.js +10 -11
- package/node_modules/@smithy/core/dist-cjs/submodules/endpoints/index.browser.js +14 -17
- package/node_modules/@smithy/core/dist-cjs/submodules/endpoints/index.js +20 -23
- package/node_modules/@smithy/core/dist-cjs/submodules/event-streams/index.browser.js +9 -11
- package/node_modules/@smithy/core/dist-cjs/submodules/event-streams/index.js +11 -13
- package/node_modules/@smithy/core/dist-cjs/submodules/protocols/index.js +59 -60
- package/node_modules/@smithy/core/dist-cjs/submodules/retry/index.browser.js +26 -27
- package/node_modules/@smithy/core/dist-cjs/submodules/retry/index.js +28 -29
- package/node_modules/@smithy/core/dist-cjs/submodules/schema/index.js +5 -7
- package/node_modules/@smithy/core/dist-cjs/submodules/serde/index.browser.js +4 -6
- package/node_modules/@smithy/core/dist-cjs/submodules/serde/index.js +23 -25
- package/node_modules/@smithy/core/dist-cjs/submodules/serde/index.native.js +4 -6
- package/node_modules/@smithy/core/dist-cjs/submodules/transport/index.js +2 -4
- package/node_modules/@smithy/core/dist-es/legacy-root-exports/middleware-http-auth-scheme/httpAuthSchemeMiddleware.js +1 -1
- package/node_modules/@smithy/core/dist-es/legacy-root-exports/middleware-http-signing/httpSigningMiddleware.js +1 -1
- package/node_modules/@smithy/core/dist-es/submodules/cbor/SmithyRpcV2CborProtocol.js +1 -1
- package/node_modules/@smithy/core/dist-es/submodules/endpoints/middleware-endpoint/endpointMiddleware.js +1 -1
- package/node_modules/@smithy/core/dist-es/submodules/retry/middleware-retry/retry-pre-sra-deprecated/StandardRetryStrategy.js +2 -2
- package/node_modules/@smithy/core/dist-es/submodules/retry/util-retry/DefaultRateLimiter.js +1 -1
- package/node_modules/@smithy/core/dist-types/submodules/schema/TypeRegistry.d.ts +1 -1
- package/node_modules/@smithy/core/package.json +18 -17
- package/node_modules/@smithy/credential-provider-imds/dist-cjs/index.js +23 -24
- package/node_modules/@smithy/credential-provider-imds/dist-es/remoteProvider/httpRequest.js +2 -2
- package/node_modules/@smithy/credential-provider-imds/dist-es/remoteProvider/node-http.js +2 -0
- package/node_modules/@smithy/credential-provider-imds/dist-types/remoteProvider/httpRequest.d.ts +1 -1
- package/node_modules/@smithy/credential-provider-imds/dist-types/remoteProvider/node-http.d.ts +2 -0
- package/node_modules/@smithy/credential-provider-imds/package.json +7 -7
- package/node_modules/@smithy/fetch-http-handler/dist-cjs/index.js +6 -8
- package/node_modules/@smithy/fetch-http-handler/package.json +10 -10
- package/node_modules/@smithy/node-http-handler/dist-cjs/index.js +15 -15
- package/node_modules/@smithy/node-http-handler/dist-es/node-http-handler.js +7 -6
- package/node_modules/@smithy/node-http-handler/dist-es/node-http2-handler.js +2 -1
- package/node_modules/@smithy/node-http-handler/dist-es/node-http2.js +2 -0
- package/node_modules/@smithy/node-http-handler/dist-es/node-https.js +2 -0
- package/node_modules/@smithy/node-http-handler/dist-types/node-http-handler.d.ts +2 -2
- package/node_modules/@smithy/node-http-handler/dist-types/node-http2-handler.d.ts +1 -1
- package/node_modules/@smithy/node-http-handler/dist-types/node-http2.d.ts +2 -0
- package/node_modules/@smithy/node-http-handler/dist-types/node-https.d.ts +2 -0
- package/node_modules/@smithy/node-http-handler/package.json +8 -8
- package/node_modules/@smithy/signature-v4/dist-cjs/index.js +27 -29
- package/node_modules/@smithy/signature-v4/package.json +7 -7
- package/node_modules/@smithy/types/dist-cjs/index.js +23 -18
- package/node_modules/@smithy/types/package.json +10 -10
- package/node_modules/@types/aws-lambda/README.md +1 -1
- package/node_modules/@types/aws-lambda/package.json +3 -3
- package/node_modules/@types/aws-lambda/trigger/api-gateway-proxy.d.ts +2 -0
- package/node_modules/anynum/LICENSE +21 -0
- package/node_modules/anynum/README.md +142 -0
- package/node_modules/anynum/anynum.js +135 -0
- package/node_modules/anynum/digitTable.js +116 -0
- package/node_modules/anynum/package.json +42 -0
- package/node_modules/watchpack/README.md +9 -0
- package/node_modules/watchpack/lib/DirectoryWatcher.js +182 -25
- package/node_modules/watchpack/lib/index.js +55 -15
- package/node_modules/watchpack/lib/reducePlan.js +56 -35
- package/node_modules/watchpack/lib/util/globToRegExp.js +142 -0
- package/node_modules/watchpack/lib/watchEventSource.js +18 -10
- package/node_modules/watchpack/package.json +17 -23
- package/node_modules/watchpack/types/DirectoryWatcher.d.ts +2 -0
- package/node_modules/watchpack/types/index.d.ts +121 -113
- package/node_modules/watchpack/types/util/globToRegExp.d.ts +2 -0
- package/node_modules/watchpack/types/watchpack.d.ts +1 -1
- package/node_modules/which-typed-array/CHANGELOG.md +7 -0
- package/node_modules/which-typed-array/eslint.config.mjs +1 -0
- package/node_modules/which-typed-array/index.d.ts +22 -31
- package/node_modules/which-typed-array/index.js +36 -23
- package/node_modules/which-typed-array/package.json +4 -7
- package/package.json +14 -14
- package/node_modules/glob-to-regexp/.travis.yml +0 -4
- package/node_modules/glob-to-regexp/README.md +0 -75
- package/node_modules/glob-to-regexp/index.js +0 -130
- package/node_modules/glob-to-regexp/package.json +0 -23
- package/node_modules/glob-to-regexp/test.js +0 -235
- /package/node_modules/{strnum → @aws-sdk/xml-builder/node_modules/strnum}/LICENSE +0 -0
|
@@ -0,0 +1,135 @@
|
|
|
1
|
+
'use strict';
|
|
2
|
+
|
|
3
|
+
import { TABLE, TABLE_OFFSET, HIGH_MAP, NOT_DIGIT } from './digitTable.js';
|
|
4
|
+
|
|
5
|
+
const CHAR_0 = 48; // '0'.charCodeAt(0)
|
|
6
|
+
const CHAR_9 = 57; // '9'.charCodeAt(0)
|
|
7
|
+
const CHAR_MINUS = 45; // '-'.charCodeAt(0)
|
|
8
|
+
|
|
9
|
+
// Unicode minus/hyphen variants worth normalizing to ASCII '-' in numeric context:
|
|
10
|
+
// U+2212 MINUS SIGN − (mathematically correct minus)
|
|
11
|
+
// U+FF0D FULLWIDTH HYPHEN-MINUS - (Japanese fullwidth context)
|
|
12
|
+
// U+FE63 SMALL HYPHEN-MINUS ﹣ (small form variant)
|
|
13
|
+
//
|
|
14
|
+
// NOT normalized (deliberate):
|
|
15
|
+
// U+2013 EN DASH – (punctuation, not a numeric sign)
|
|
16
|
+
// U+2014 EM DASH — (punctuation)
|
|
17
|
+
// U+2010 HYPHEN ‐ (typographic hyphen)
|
|
18
|
+
//
|
|
19
|
+
// Rationale: only characters a human or locale formatter would plausibly use
|
|
20
|
+
// as a numeric minus sign are normalized. Dashes used for punctuation are left
|
|
21
|
+
// alone to avoid mangling non-numeric strings.
|
|
22
|
+
const MINUS_SET = new Set([0x2212, 0xFF0D, 0xFE63]);
|
|
23
|
+
|
|
24
|
+
/**
|
|
25
|
+
* Normalize all Unicode decimal digit characters in a string to ASCII (0-9),
|
|
26
|
+
* and normalize Unicode minus variants to ASCII '-' (U+002D).
|
|
27
|
+
*
|
|
28
|
+
* Non-digit, non-minus characters are passed through unchanged.
|
|
29
|
+
*
|
|
30
|
+
* Performance design:
|
|
31
|
+
* - Fast path: if the string has no convertible characters, return it unchanged
|
|
32
|
+
* (zero allocation).
|
|
33
|
+
* - BMP digits (0x0660..0xFFFF excl. surrogates): flat Uint8Array lookup (O(1)).
|
|
34
|
+
* - Supplementary plane digits (> 0xFFFF, encoded as surrogate pairs): Map lookup.
|
|
35
|
+
* - Minus variants: checked inline with a small fixed Set.
|
|
36
|
+
*
|
|
37
|
+
* @param {string} str
|
|
38
|
+
* @returns {string}
|
|
39
|
+
*/
|
|
40
|
+
function anynum(str) {
|
|
41
|
+
if (typeof str !== 'string') return str;
|
|
42
|
+
|
|
43
|
+
const len = str.length;
|
|
44
|
+
if (len === 0) return str;
|
|
45
|
+
|
|
46
|
+
// Scan for first character needing conversion.
|
|
47
|
+
// If none found, return original string (zero allocation).
|
|
48
|
+
let firstHit = -1;
|
|
49
|
+
|
|
50
|
+
for (let i = 0; i < len; i++) {
|
|
51
|
+
const cc = str.charCodeAt(i);
|
|
52
|
+
|
|
53
|
+
// ASCII digit or ASCII minus — already normalized, skip fast
|
|
54
|
+
if ((cc >= CHAR_0 && cc <= CHAR_9) || cc === CHAR_MINUS) continue;
|
|
55
|
+
|
|
56
|
+
// Below first unicode digit script — check minus variants only
|
|
57
|
+
if (cc < TABLE_OFFSET) {
|
|
58
|
+
if (MINUS_SET.has(cc)) { firstHit = i; break; }
|
|
59
|
+
continue;
|
|
60
|
+
}
|
|
61
|
+
|
|
62
|
+
// Surrogate pairs live in BMP range 0xD800-0xDFFF — check before TABLE
|
|
63
|
+
if (cc >= 0xD800 && cc <= 0xDBFF) {
|
|
64
|
+
if (i + 1 < len) {
|
|
65
|
+
const low = str.charCodeAt(i + 1);
|
|
66
|
+
if (low >= 0xDC00 && low <= 0xDFFF) {
|
|
67
|
+
const cp = 0x10000 + ((cc - 0xD800) << 10) + (low - 0xDC00);
|
|
68
|
+
if (HIGH_MAP.has(cp)) { firstHit = i; break; }
|
|
69
|
+
}
|
|
70
|
+
}
|
|
71
|
+
continue;
|
|
72
|
+
}
|
|
73
|
+
|
|
74
|
+
// BMP non-surrogate: flat table lookup; also check minus variants in this range
|
|
75
|
+
if (TABLE[cc - TABLE_OFFSET] !== NOT_DIGIT || MINUS_SET.has(cc)) {
|
|
76
|
+
firstHit = i;
|
|
77
|
+
break;
|
|
78
|
+
}
|
|
79
|
+
}
|
|
80
|
+
|
|
81
|
+
// Nothing to replace — return original, zero allocation
|
|
82
|
+
if (firstHit === -1) return str;
|
|
83
|
+
|
|
84
|
+
// Build result: copy unchanged prefix, then convert from firstHit onward
|
|
85
|
+
const chars = [];
|
|
86
|
+
|
|
87
|
+
if (firstHit > 0) chars.push(str.slice(0, firstHit));
|
|
88
|
+
|
|
89
|
+
for (let i = firstHit; i < len; i++) {
|
|
90
|
+
const cc = str.charCodeAt(i);
|
|
91
|
+
|
|
92
|
+
// ASCII digit or ASCII minus — pass through
|
|
93
|
+
if ((cc >= CHAR_0 && cc <= CHAR_9) || cc === CHAR_MINUS) {
|
|
94
|
+
chars.push(str[i]);
|
|
95
|
+
continue;
|
|
96
|
+
}
|
|
97
|
+
|
|
98
|
+
// Below TABLE_OFFSET — check minus variants, else pass through
|
|
99
|
+
if (cc < TABLE_OFFSET) {
|
|
100
|
+
chars.push(MINUS_SET.has(cc) ? '-' : str[i]);
|
|
101
|
+
continue;
|
|
102
|
+
}
|
|
103
|
+
|
|
104
|
+
// Surrogate pairs
|
|
105
|
+
if (cc >= 0xD800 && cc <= 0xDBFF) {
|
|
106
|
+
if (i + 1 < len) {
|
|
107
|
+
const low = str.charCodeAt(i + 1);
|
|
108
|
+
if (low >= 0xDC00 && low <= 0xDFFF) {
|
|
109
|
+
const cp = 0x10000 + ((cc - 0xD800) << 10) + (low - 0xDC00);
|
|
110
|
+
const d = HIGH_MAP.get(cp);
|
|
111
|
+
if (d !== undefined) {
|
|
112
|
+
chars.push(String.fromCharCode(d + 48));
|
|
113
|
+
i++; // consume low surrogate
|
|
114
|
+
continue;
|
|
115
|
+
}
|
|
116
|
+
}
|
|
117
|
+
}
|
|
118
|
+
chars.push(str[i]);
|
|
119
|
+
continue;
|
|
120
|
+
}
|
|
121
|
+
|
|
122
|
+
// BMP non-surrogate: flat table lookup + minus variants
|
|
123
|
+
if (MINUS_SET.has(cc)) {
|
|
124
|
+
chars.push('-');
|
|
125
|
+
continue;
|
|
126
|
+
}
|
|
127
|
+
const d = TABLE[cc - TABLE_OFFSET];
|
|
128
|
+
chars.push(d !== NOT_DIGIT ? String.fromCharCode(d + 48) : str[i]);
|
|
129
|
+
}
|
|
130
|
+
|
|
131
|
+
return chars.join('');
|
|
132
|
+
}
|
|
133
|
+
|
|
134
|
+
export { anynum };
|
|
135
|
+
export default anynum;
|
|
@@ -0,0 +1,116 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Flat lookup table: maps Unicode code point → ASCII digit (0-9).
|
|
3
|
+
* Only decimal digit characters (Unicode category Nd) are included.
|
|
4
|
+
*
|
|
5
|
+
* Strategy: Int32Array of size (maxCodePoint - minCodePoint + 1).
|
|
6
|
+
* Value 0xFF means "not a digit". Value 0-9 is the ASCII digit value.
|
|
7
|
+
* This gives O(1) lookup with no branching, no bisect, no loop.
|
|
8
|
+
*
|
|
9
|
+
* Memory: range is 0x0660 to 0x1FBF0 → ~129,936 entries × 1 byte = ~127 KB.
|
|
10
|
+
* Acceptable for a one-time init; lookup is a single array index.
|
|
11
|
+
*/
|
|
12
|
+
|
|
13
|
+
// All known Unicode Nd (decimal digit) script zero code points.
|
|
14
|
+
// Each script has exactly 10 consecutive digits: zero+0 .. zero+9.
|
|
15
|
+
const SCRIPT_ZEROS = [
|
|
16
|
+
// Basic Latin (ASCII) — included for completeness / pass-through
|
|
17
|
+
0x0030, // 0-9
|
|
18
|
+
|
|
19
|
+
// Arabic scripts
|
|
20
|
+
0x0660, // Arabic-Indic ٠١٢٣٤٥٦٧٨٩
|
|
21
|
+
0x06F0, // Extended Arabic-Indic (Urdu/Persian/Sindhi) ۰۱۲۳
|
|
22
|
+
|
|
23
|
+
// Indic scripts
|
|
24
|
+
0x0966, // Devanagari ०१२३४५६७८९
|
|
25
|
+
0x09E6, // Bengali ০১২৩৪৫৬৭৮৯
|
|
26
|
+
0x0A66, // Gurmukhi ੦੧੨੩੪੫੬੭੮੯
|
|
27
|
+
0x0AE6, // Gujarati ૦૧૨૩૪૫૬૭૮૯
|
|
28
|
+
0x0B66, // Odia ୦୧୨୩୪୫୬୭୮୯
|
|
29
|
+
0x0BE6, // Tamil ௦௧௨௩௪௫௬௭௮௯
|
|
30
|
+
0x0C66, // Telugu ౦౧౨౩౪౫౬౭౮౯
|
|
31
|
+
0x0CE6, // Kannada ೦೧೨೩೪೫೬೭೮೯
|
|
32
|
+
0x0D66, // Malayalam ൦൧൨൩൪൫൬൭൮൯
|
|
33
|
+
0x0DE6, // Sinhala Archaic ෦෧෨෩෪෫෬෭෮෯
|
|
34
|
+
|
|
35
|
+
// Southeast Asian scripts
|
|
36
|
+
0x0E50, // Thai ๐๑๒๓๔๕๖๗๘๙
|
|
37
|
+
0x0ED0, // Lao ໐໑໒໓໔໕໖໗໘໙
|
|
38
|
+
0x0F20, // Tibetan ༠༡༢༣༤༥༦༧༨༩
|
|
39
|
+
0x1040, // Myanmar ၀၁၂၃၄၅၆၇၈၉
|
|
40
|
+
0x1090, // Myanmar Shan ႐႑႒႓႔႕႖႗႘႙
|
|
41
|
+
0x17E0, // Khmer ០១២៣៤៥៦៧៨៩
|
|
42
|
+
0x1810, // Mongolian ᠐᠑᠒᠓᠔᠕᠖᠗᠘᠙
|
|
43
|
+
0x1946, // Limbu ᥆᥇᥈᥉᥊᥋᥌᥍᥎᥏
|
|
44
|
+
0x19D0, // New Tai Lue ᧐᧑᧒᧓᧔᧕᧖᧗᧘᧙
|
|
45
|
+
0x1A80, // Tai Tham Hora ᪀᪁᪂᪃᪄᪅᪆᪇᪈᪉
|
|
46
|
+
0x1A90, // Tai Tham Tham ᪐᪑᪒᪓᪔᪕᪖᪗᪘᪙
|
|
47
|
+
0x1B50, // Balinese ᭐᭑᭒᭓᭔᭕᭖᭗᭘᭙
|
|
48
|
+
0x1BB0, // Sundanese ᮰᮱᮲᮳᮴᮵᮶᮷᮸᮹
|
|
49
|
+
0x1C40, // Lepcha ᱀᱁᱂᱃᱄᱅᱆᱇᱈᱉
|
|
50
|
+
0x1C50, // Ol Chiki ᱐᱑᱒᱓᱔᱕᱖᱗᱘᱙
|
|
51
|
+
|
|
52
|
+
// Fullwidth (CJK context)
|
|
53
|
+
0xFF10, // Fullwidth 0123456789
|
|
54
|
+
|
|
55
|
+
// Mathematical digit variants (Unicode math block)
|
|
56
|
+
0x1D7CE, // Mathematical Bold
|
|
57
|
+
0x1D7D8, // Mathematical Double-Struck
|
|
58
|
+
0x1D7E2, // Mathematical Sans-Serif
|
|
59
|
+
0x1D7EC, // Mathematical Sans-Serif Bold
|
|
60
|
+
0x1D7F6, // Mathematical Monospace
|
|
61
|
+
|
|
62
|
+
// Other scripts
|
|
63
|
+
0x104A0, // Osmanya 𐒠𐒡𐒢𐒣𐒤𐒥𐒦𐒧𐒨𐒩
|
|
64
|
+
0x10D30, // Hanifi Rohingya 𐴰𐴱𐴲𐴳𐴴𐴵𐴶𐴷𐴸𐴹
|
|
65
|
+
0x11066, // Brahmi 𑁦𑁧𑁨𑁩𑁪𑁫𑁬𑁭𑁮𑁯
|
|
66
|
+
0x110F0, // Sora Sompeng 𑃰𑃱𑃲𑃳𑃴𑃵𑃶𑃷𑃸𑃹
|
|
67
|
+
0x11136, // Chakma 𑄶𑄷𑄸𑄹𑄺𑄻𑄼𑄽𑄾𑄿
|
|
68
|
+
0x111D0, // Sharada 𑇐𑇑𑇒𑇓𑇔𑇕𑇖𑇗𑇘𑇙
|
|
69
|
+
0x112F0, // Khudawadi 𑋰𑋱𑋲𑋳𑋴𑋵𑋶𑋷𑋸𑋹
|
|
70
|
+
0x11450, // Newa 𑑐𑑑𑑒𑑓𑑔𑑕𑑖𑑗𑑘𑑙
|
|
71
|
+
0x114D0, // Tirhuta 𑓐𑓑𑓒𑓓𑓔𑓕𑓖𑓗𑓘𑓙
|
|
72
|
+
0x11650, // Modi 𑙐𑙑𑙒𑙓𑙔𑙕𑙖𑙗𑙘𑙙
|
|
73
|
+
0x116C0, // Takri 𑛀𑛁𑛂𑛃𑛄𑛅𑛆𑛇𑛈𑛉
|
|
74
|
+
0x11730, // Ahom 𑜰𑜱𑜲𑜳𑜴𑜵𑜶𑜷𑜸𑜹
|
|
75
|
+
0x118E0, // Warang Citi 𑣠𑣡𑣢𑣣𑣤𑣥𑣦𑣧𑣨𑣩
|
|
76
|
+
0x11950, // Dives Akuru 𑥐𑥑𑥒𑥓𑥔𑥕𑥖𑥗𑥘𑥙
|
|
77
|
+
0x11BF0, // Khitan Small Script
|
|
78
|
+
0x11C50, // Bhaiksuki 𑱐𑱑𑱒𑱓𑱔𑱕𑱖𑱗𑱘𑱙
|
|
79
|
+
0x11D50, // Masaram Gondi 𑵐𑵑𑵒𑵓𑵔𑵕𑵖𑵗𑵘𑵙
|
|
80
|
+
0x11DA0, // Gunjala Gondi 𑶠𑶡𑶢𑶣𑶤𑶥𑶦𑶧𑶨𑶩
|
|
81
|
+
0x11F50, // Kawi 𑽐𑽑𑽒𑽓𑽔𑽕𑽖𑽗𑽘𑽙
|
|
82
|
+
0x16A60, // Mro 𖩠𖩡𖩢𖩣𖩤𖩥𖩦𖩧𖩨𖩩
|
|
83
|
+
0x16AC0, // Tangsa 𖫀𖫁𖫂𖫃𖫄𖫅𖫆𖫇𖫈𖫉
|
|
84
|
+
0x16B50, // Pahawh Hmong 𖭐𖭑𖭒𖭓𖭔𖭕𖭖𖭗𖭘𖭙
|
|
85
|
+
0x1E140, // Nyiakeng Puachue Hmong 𞅀𞅁𞅂𞅃𞅄𞅅𞅆𞅇𞅈𞅉
|
|
86
|
+
0x1E2F0, // Wancho 𞋰𞋱𞋲𞋳𞋴𞋵𞋶𞋷𞋸𞋹
|
|
87
|
+
0x1E4F0, // Nag Mundari 𞓰𞓱𞓲𞓳𞓴𞓵𞓶𞓷𞓸𞓹
|
|
88
|
+
0x1E950, // Adlam 𞥐𞥑𞥒𞥓𞥔𞥕𞥖𞥗𞥘𞥙
|
|
89
|
+
0x1FBF0, // Segmented digit symbols 🯰🯱🯲🯳🯴🯵🯶🯷🯸🯹
|
|
90
|
+
];
|
|
91
|
+
|
|
92
|
+
// Build a sparse Map for scripts above 0xFFFF (surrogate-pair range).
|
|
93
|
+
// These can't go into a flat Uint8Array indexed by code point efficiently.
|
|
94
|
+
const NOT_DIGIT = 0xFF;
|
|
95
|
+
const HIGH_MAP = new Map(); // codePoint → digit value (0-9)
|
|
96
|
+
|
|
97
|
+
const LOW_MAX = 0xFFFF;
|
|
98
|
+
const LOW_MIN = 0x0660; // first non-ASCII digit script
|
|
99
|
+
|
|
100
|
+
// Flat Uint8Array covering 0x0660 .. 0xFFFF
|
|
101
|
+
const TABLE_OFFSET = LOW_MIN;
|
|
102
|
+
const TABLE_SIZE = LOW_MAX - LOW_MIN + 1;
|
|
103
|
+
const TABLE = new Uint8Array(TABLE_SIZE).fill(NOT_DIGIT);
|
|
104
|
+
|
|
105
|
+
for (const zero of SCRIPT_ZEROS) {
|
|
106
|
+
for (let d = 0; d < 10; d++) {
|
|
107
|
+
const cp = zero + d;
|
|
108
|
+
if (cp <= LOW_MAX) {
|
|
109
|
+
TABLE[cp - TABLE_OFFSET] = d;
|
|
110
|
+
} else {
|
|
111
|
+
HIGH_MAP.set(cp, d);
|
|
112
|
+
}
|
|
113
|
+
}
|
|
114
|
+
}
|
|
115
|
+
|
|
116
|
+
export { TABLE, TABLE_OFFSET, HIGH_MAP, NOT_DIGIT };
|
|
@@ -0,0 +1,42 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "anynum",
|
|
3
|
+
"version": "1.0.0",
|
|
4
|
+
"description": "Normalize all Unicode decimal digits (Devanagari, Arabic, Thai, etc.) to ASCII numerals. Zero dependencies, performance-first.",
|
|
5
|
+
"type": "module",
|
|
6
|
+
"main": "./anynum.js",
|
|
7
|
+
"files": [
|
|
8
|
+
"anynum.js",
|
|
9
|
+
"digitTable.js",
|
|
10
|
+
"README.md"
|
|
11
|
+
],
|
|
12
|
+
"scripts": {
|
|
13
|
+
"test": "jasmine tests/anynum.test.js",
|
|
14
|
+
"bench": "node test/bench.js"
|
|
15
|
+
},
|
|
16
|
+
"keywords": [
|
|
17
|
+
"unicode",
|
|
18
|
+
"digits",
|
|
19
|
+
"normalize",
|
|
20
|
+
"devanagari",
|
|
21
|
+
"arabic",
|
|
22
|
+
"hindi",
|
|
23
|
+
"japanese",
|
|
24
|
+
"indic",
|
|
25
|
+
"asian",
|
|
26
|
+
"math",
|
|
27
|
+
"numerals",
|
|
28
|
+
"strnum"
|
|
29
|
+
],
|
|
30
|
+
"repository": {
|
|
31
|
+
"type": "git",
|
|
32
|
+
"url": "https://github.com/NaturalIntelligence/anynum"
|
|
33
|
+
},
|
|
34
|
+
"author": "Amit Gupta (https://solothought.work/)",
|
|
35
|
+
"license": "MIT",
|
|
36
|
+
"funding": [
|
|
37
|
+
{
|
|
38
|
+
"type": "github",
|
|
39
|
+
"url": "https://github.com/sponsors/NaturalIntelligence"
|
|
40
|
+
}
|
|
41
|
+
]
|
|
42
|
+
}
|
|
@@ -131,3 +131,12 @@ const fileTimesOld = wp.getTimes();
|
|
|
131
131
|
// this include timestamps from files not directly watched
|
|
132
132
|
// key: absolute path, value: timestamp as number
|
|
133
133
|
```
|
|
134
|
+
|
|
135
|
+
## Environment variables
|
|
136
|
+
|
|
137
|
+
- `WATCHPACK_POLLING`: when set, overrides the `poll` option (see above).
|
|
138
|
+
- `WATCHPACK_RETRIES`: number of times to retry `fs.lstat` when it returns
|
|
139
|
+
`EBUSY` (default: `3`). Useful on Windows where anti-virus scanners,
|
|
140
|
+
indexers or editors briefly lock files — without retries watchpack would
|
|
141
|
+
see a spurious `remove` and stop tracking the file. Set to `0` or
|
|
142
|
+
`"false"` to disable retrying.
|
|
@@ -28,13 +28,28 @@ let FS_ACCURACY = 2000;
|
|
|
28
28
|
const IS_OSX = require("os").platform() === "darwin";
|
|
29
29
|
const IS_WIN = require("os").platform() === "win32";
|
|
30
30
|
|
|
31
|
-
const { WATCHPACK_POLLING } = process.env;
|
|
31
|
+
const { WATCHPACK_POLLING, WATCHPACK_RETRIES } = process.env;
|
|
32
32
|
const FORCE_POLLING =
|
|
33
33
|
// @ts-expect-error avoid additional checks
|
|
34
34
|
`${+WATCHPACK_POLLING}` === WATCHPACK_POLLING
|
|
35
35
|
? +WATCHPACK_POLLING
|
|
36
36
|
: Boolean(WATCHPACK_POLLING) && WATCHPACK_POLLING !== "false";
|
|
37
37
|
|
|
38
|
+
// Number of retries (and delay between retries, in ms) when an fs operation
|
|
39
|
+
// returns EBUSY. EBUSY is transient on Windows when an AV scanner, indexer,
|
|
40
|
+
// or another process briefly locks a file; retrying avoids incorrectly
|
|
41
|
+
// reporting the file as removed (see webpack/watchpack#223, #44).
|
|
42
|
+
//
|
|
43
|
+
// Configurable via `WATCHPACK_RETRIES` env var: an integer >= 0, or "false"
|
|
44
|
+
// to disable retries entirely. Unset / invalid values fall back to 3.
|
|
45
|
+
const BUSY_RETRIES = (() => {
|
|
46
|
+
if (WATCHPACK_RETRIES === undefined) return 3;
|
|
47
|
+
if (WATCHPACK_RETRIES === "false") return 0;
|
|
48
|
+
const n = Number(WATCHPACK_RETRIES);
|
|
49
|
+
return Number.isFinite(n) && n >= 0 ? Math.floor(n) : 3;
|
|
50
|
+
})();
|
|
51
|
+
const BUSY_RETRY_DELAY = 100;
|
|
52
|
+
|
|
38
53
|
/**
|
|
39
54
|
* @param {string} str string
|
|
40
55
|
* @returns {string} lower cased string
|
|
@@ -77,6 +92,38 @@ function ensureFsAccuracy(mtime) {
|
|
|
77
92
|
else if (FS_ACCURACY > 1000 && mtime % 1000 !== 0) FS_ACCURACY = 1000;
|
|
78
93
|
}
|
|
79
94
|
|
|
95
|
+
/**
|
|
96
|
+
* Call `fs.lstat` with retries on EBUSY. Transient EBUSY errors are common
|
|
97
|
+
* on Windows when another process (AV scanner, indexer, editor) holds an
|
|
98
|
+
* open handle on the file. See webpack/watchpack#223, #44.
|
|
99
|
+
*
|
|
100
|
+
* The retry count is taken from the `WATCHPACK_RETRIES` env var (default
|
|
101
|
+
* 3, set to "0" or "false" to disable retrying). The hot path is a single
|
|
102
|
+
* `fs.lstat` call with one inline callback; the timer and the recursive
|
|
103
|
+
* call are only scheduled when an EBUSY is actually observed.
|
|
104
|
+
* @param {string} target target path
|
|
105
|
+
* @param {{ closed: boolean }} watcher owning watcher (checked between retries)
|
|
106
|
+
* @param {(err: NodeJS.ErrnoException | null, stats: import("fs").Stats) => void} callback callback
|
|
107
|
+
* @param {number=} remaining retries remaining (defaults to `BUSY_RETRIES`)
|
|
108
|
+
*/
|
|
109
|
+
function lstatWithRetry(target, watcher, callback, remaining = BUSY_RETRIES) {
|
|
110
|
+
fs.lstat(target, (err, stats) => {
|
|
111
|
+
if (
|
|
112
|
+
err &&
|
|
113
|
+
/** @type {NodeJS.ErrnoException} */ (err).code === "EBUSY" &&
|
|
114
|
+
remaining > 0 &&
|
|
115
|
+
!watcher.closed
|
|
116
|
+
) {
|
|
117
|
+
setTimeout(
|
|
118
|
+
() => lstatWithRetry(target, watcher, callback, remaining - 1),
|
|
119
|
+
BUSY_RETRY_DELAY,
|
|
120
|
+
);
|
|
121
|
+
return;
|
|
122
|
+
}
|
|
123
|
+
callback(err, stats);
|
|
124
|
+
});
|
|
125
|
+
}
|
|
126
|
+
|
|
80
127
|
/**
|
|
81
128
|
* @typedef {object} FileWatcherEvents
|
|
82
129
|
* @property {(type: EventType) => void} initial-missing initial missing event
|
|
@@ -167,6 +214,8 @@ class DirectoryWatcher extends EventEmitter {
|
|
|
167
214
|
this.filesWithoutCase = new Map();
|
|
168
215
|
/** @type {Map<string, Watcher<DirectoryWatcherEvents> | boolean>} */
|
|
169
216
|
this.directories = new Map();
|
|
217
|
+
/** @type {Map<string, Watcher<FileWatcherEvents>>} */
|
|
218
|
+
this._symlinkTargetWatchers = new Map();
|
|
170
219
|
this.lastWatchEvent = 0;
|
|
171
220
|
this.initialScan = true;
|
|
172
221
|
this.ignored = options.ignored || (() => false);
|
|
@@ -427,6 +476,10 @@ class DirectoryWatcher extends EventEmitter {
|
|
|
427
476
|
(watcher).close();
|
|
428
477
|
this.directories.set(directory, true);
|
|
429
478
|
}
|
|
479
|
+
for (const w of this._symlinkTargetWatchers.values()) {
|
|
480
|
+
w.close();
|
|
481
|
+
}
|
|
482
|
+
this._symlinkTargetWatchers.clear();
|
|
430
483
|
}
|
|
431
484
|
}
|
|
432
485
|
}
|
|
@@ -550,7 +603,7 @@ class DirectoryWatcher extends EventEmitter {
|
|
|
550
603
|
const checkStats = () => {
|
|
551
604
|
if (this.closed) return;
|
|
552
605
|
this._activeEvents.set(filename, false);
|
|
553
|
-
|
|
606
|
+
lstatWithRetry(target, this, (err, stats) => {
|
|
554
607
|
if (this.closed) return;
|
|
555
608
|
if (this._activeEvents.get(filename) === true) {
|
|
556
609
|
process.nextTick(checkStats);
|
|
@@ -559,6 +612,9 @@ class DirectoryWatcher extends EventEmitter {
|
|
|
559
612
|
this._activeEvents.delete(filename);
|
|
560
613
|
// ENOENT happens when the file/directory doesn't exist
|
|
561
614
|
// EPERM happens when the containing directory doesn't exist
|
|
615
|
+
// EBUSY happens when another process has the file locked (e.g.
|
|
616
|
+
// Windows AV scanner). lstatWithRetry already retried before
|
|
617
|
+
// giving up here.
|
|
562
618
|
if (err) {
|
|
563
619
|
if (
|
|
564
620
|
err.code !== "ENOENT" &&
|
|
@@ -575,6 +631,13 @@ class DirectoryWatcher extends EventEmitter {
|
|
|
575
631
|
}
|
|
576
632
|
this.lastWatchEvent = Date.now();
|
|
577
633
|
if (!stats) {
|
|
634
|
+
// On EBUSY we keep the tracked state: the file is likely still
|
|
635
|
+
// there and a later event or scan will reconcile. Emitting a
|
|
636
|
+
// remove here would make the watch appear to stop after a
|
|
637
|
+
// transient lock (webpack/watchpack#223, #44).
|
|
638
|
+
if (err && err.code === "EBUSY" && BUSY_RETRIES > 0) {
|
|
639
|
+
return;
|
|
640
|
+
}
|
|
578
641
|
this.setMissing(target, false, eventType);
|
|
579
642
|
} else if (stats.isDirectory()) {
|
|
580
643
|
this.setDirectory(target, +stats.birthtime || 1, false, eventType);
|
|
@@ -724,7 +787,20 @@ class DirectoryWatcher extends EventEmitter {
|
|
|
724
787
|
fs.readdir(this.path, (err, items) => {
|
|
725
788
|
if (this.closed) return;
|
|
726
789
|
if (err) {
|
|
727
|
-
|
|
790
|
+
// Mirror the lstat error handling below: treat permission /
|
|
791
|
+
// invalid-argument / no-device errors on the directory itself
|
|
792
|
+
// as removed rather than logging "Watchpack Error (initial
|
|
793
|
+
// scan)". These surface for unreadable mounts (WSL `/mnt/c`,
|
|
794
|
+
// fuse mounts), unmounted devices (`/efi`), and libuv's
|
|
795
|
+
// post-Node 22.17 `EINVAL` on protected Windows paths
|
|
796
|
+
// (see #187).
|
|
797
|
+
if (
|
|
798
|
+
err.code === "ENOENT" ||
|
|
799
|
+
err.code === "EPERM" ||
|
|
800
|
+
err.code === "EACCES" ||
|
|
801
|
+
err.code === "ENODEV" ||
|
|
802
|
+
(err.code === "EINVAL" && IS_WIN)
|
|
803
|
+
) {
|
|
728
804
|
this.onDirectoryRemoved("scan readdir failed");
|
|
729
805
|
} else {
|
|
730
806
|
this.onScanError(err);
|
|
@@ -801,7 +877,7 @@ class DirectoryWatcher extends EventEmitter {
|
|
|
801
877
|
}
|
|
802
878
|
});
|
|
803
879
|
for (const itemPath of itemPaths) {
|
|
804
|
-
|
|
880
|
+
lstatWithRetry(itemPath, this, (err2, stats) => {
|
|
805
881
|
if (this.closed) return;
|
|
806
882
|
if (err2) {
|
|
807
883
|
if (
|
|
@@ -809,39 +885,115 @@ class DirectoryWatcher extends EventEmitter {
|
|
|
809
885
|
err2.code === "EPERM" ||
|
|
810
886
|
err2.code === "EACCES" ||
|
|
811
887
|
err2.code === "EBUSY" ||
|
|
888
|
+
err2.code === "ENODEV" ||
|
|
812
889
|
// TODO https://github.com/libuv/libuv/pull/4566
|
|
813
890
|
(err2.code === "EINVAL" && IS_WIN)
|
|
814
891
|
) {
|
|
815
|
-
|
|
892
|
+
// readdir saw the entry but we can't stat it due to a
|
|
893
|
+
// transient lock — keep the previously-known entry instead
|
|
894
|
+
// of incorrectly flagging it as missing.
|
|
895
|
+
if (
|
|
896
|
+
!(
|
|
897
|
+
err2.code === "EBUSY" &&
|
|
898
|
+
BUSY_RETRIES > 0 &&
|
|
899
|
+
this.files.has(itemPath)
|
|
900
|
+
)
|
|
901
|
+
) {
|
|
902
|
+
this.setMissing(itemPath, initial, `scan (${err2.code})`);
|
|
903
|
+
}
|
|
816
904
|
} else {
|
|
817
905
|
this.onScanError(err2);
|
|
818
906
|
}
|
|
819
907
|
itemFinished();
|
|
820
908
|
return;
|
|
821
909
|
}
|
|
822
|
-
|
|
823
|
-
|
|
824
|
-
|
|
910
|
+
/**
|
|
911
|
+
* @param {string | null} realPath resolved real path for an outside-dir symlink target
|
|
912
|
+
*/
|
|
913
|
+
const apply = (realPath) => {
|
|
914
|
+
if (stats.isFile() || stats.isSymbolicLink()) {
|
|
915
|
+
if (stats.mtime) ensureFsAccuracy(+stats.mtime);
|
|
916
|
+
this.setFileTime(
|
|
917
|
+
itemPath,
|
|
918
|
+
+stats.mtime || +stats.ctime || 1,
|
|
919
|
+
initial,
|
|
920
|
+
true,
|
|
921
|
+
"scan (file)",
|
|
922
|
+
);
|
|
923
|
+
if (realPath && !this._symlinkTargetWatchers.has(itemPath)) {
|
|
924
|
+
const w = this.watcherManager.watchFile(realPath, Date.now());
|
|
925
|
+
if (w) {
|
|
926
|
+
w.on("change", (mtime, type, wInitial) => {
|
|
927
|
+
if (wInitial) return;
|
|
928
|
+
this.setFileTime(itemPath, mtime, false, false, type);
|
|
929
|
+
});
|
|
930
|
+
this._symlinkTargetWatchers.set(itemPath, w);
|
|
931
|
+
}
|
|
932
|
+
}
|
|
933
|
+
} else if (
|
|
934
|
+
stats.isDirectory() &&
|
|
935
|
+
(!initial || !this.directories.has(itemPath))
|
|
936
|
+
) {
|
|
937
|
+
this.setDirectory(
|
|
938
|
+
itemPath,
|
|
939
|
+
+stats.birthtime || 1,
|
|
940
|
+
initial,
|
|
941
|
+
"scan (dir)",
|
|
942
|
+
);
|
|
825
943
|
}
|
|
826
|
-
|
|
827
|
-
|
|
828
|
-
|
|
829
|
-
|
|
830
|
-
|
|
831
|
-
|
|
832
|
-
);
|
|
833
|
-
} else if (
|
|
834
|
-
stats.isDirectory() &&
|
|
835
|
-
(!initial || !this.directories.has(itemPath))
|
|
944
|
+
itemFinished();
|
|
945
|
+
};
|
|
946
|
+
if (
|
|
947
|
+
this.options.followSymlinks &&
|
|
948
|
+
this.nestedWatching &&
|
|
949
|
+
stats.isSymbolicLink()
|
|
836
950
|
) {
|
|
837
|
-
|
|
838
|
-
|
|
839
|
-
|
|
840
|
-
|
|
841
|
-
|
|
842
|
-
|
|
951
|
+
fs.realpath(itemPath, (err3, realPath) => {
|
|
952
|
+
if (this.closed) return;
|
|
953
|
+
if (
|
|
954
|
+
err3 ||
|
|
955
|
+
!realPath ||
|
|
956
|
+
withoutCase(path.dirname(realPath)) === withoutCase(this.path)
|
|
957
|
+
) {
|
|
958
|
+
apply(null);
|
|
959
|
+
return;
|
|
960
|
+
}
|
|
961
|
+
// Cycle protection: when the symlink's target is the symlink
|
|
962
|
+
// path itself or one of its ancestors, descending would
|
|
963
|
+
// create an unbounded chain of `DirectoryWatcher`s as we walk
|
|
964
|
+
// back into territory we are already watching. Treat the
|
|
965
|
+
// symlink as a plain entry instead so the symlink itself is
|
|
966
|
+
// still tracked but no recursion happens.
|
|
967
|
+
const rel = path.relative(realPath, itemPath);
|
|
968
|
+
if (!path.isAbsolute(rel) && !rel.startsWith("..")) {
|
|
969
|
+
apply(null);
|
|
970
|
+
return;
|
|
971
|
+
}
|
|
972
|
+
fs.stat(realPath, (err4, targetStats) => {
|
|
973
|
+
if (this.closed) return;
|
|
974
|
+
if (err4 || !targetStats) {
|
|
975
|
+
apply(null);
|
|
976
|
+
} else if (targetStats.isFile()) {
|
|
977
|
+
apply(realPath);
|
|
978
|
+
} else if (targetStats.isDirectory()) {
|
|
979
|
+
// Treat a symlink whose target is a directory as a
|
|
980
|
+
// nested watched directory so files inside the target
|
|
981
|
+
// propagate change events to the symlink path.
|
|
982
|
+
this.setDirectory(
|
|
983
|
+
itemPath,
|
|
984
|
+
+targetStats.birthtime || +stats.birthtime || 1,
|
|
985
|
+
initial,
|
|
986
|
+
"scan (dir)",
|
|
987
|
+
);
|
|
988
|
+
itemFinished();
|
|
989
|
+
} else {
|
|
990
|
+
apply(null);
|
|
991
|
+
}
|
|
992
|
+
});
|
|
993
|
+
});
|
|
994
|
+
return;
|
|
843
995
|
}
|
|
844
|
-
|
|
996
|
+
apply(null);
|
|
845
997
|
});
|
|
846
998
|
}
|
|
847
999
|
itemFinished();
|
|
@@ -939,6 +1091,7 @@ class DirectoryWatcher extends EventEmitter {
|
|
|
939
1091
|
}
|
|
940
1092
|
|
|
941
1093
|
close() {
|
|
1094
|
+
if (this.closed) return;
|
|
942
1095
|
this.closed = true;
|
|
943
1096
|
this.initialScan = false;
|
|
944
1097
|
if (this.watcher) {
|
|
@@ -952,6 +1105,10 @@ class DirectoryWatcher extends EventEmitter {
|
|
|
952
1105
|
}
|
|
953
1106
|
this.directories.clear();
|
|
954
1107
|
}
|
|
1108
|
+
for (const w of this._symlinkTargetWatchers.values()) {
|
|
1109
|
+
w.close();
|
|
1110
|
+
}
|
|
1111
|
+
this._symlinkTargetWatchers.clear();
|
|
955
1112
|
if (this.parentWatcher) {
|
|
956
1113
|
this.parentWatcher.close();
|
|
957
1114
|
this.parentWatcher = null;
|