@itwin/core-quantity 5.10.0-dev.5 → 5.10.0-dev.7
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/CHANGELOG.md +17 -1
- package/lib/cjs/BasicUnitsProvider.js.map +1 -1
- package/lib/cjs/CompositeUnitsProvider.js.map +1 -1
- package/lib/cjs/Constants.js.map +1 -1
- package/lib/cjs/Exception.js.map +1 -1
- package/lib/cjs/FormatSpecHandle.d.ts +9 -10
- package/lib/cjs/FormatSpecHandle.d.ts.map +1 -1
- package/lib/cjs/FormatSpecHandle.js +17 -35
- package/lib/cjs/FormatSpecHandle.js.map +1 -1
- package/lib/cjs/Formatter/Format.js.map +1 -1
- package/lib/cjs/Formatter/FormatEnums.js.map +1 -1
- package/lib/cjs/Formatter/Formatter.js.map +1 -1
- package/lib/cjs/Formatter/FormatterSpec.js.map +1 -1
- package/lib/cjs/Formatter/FormattingReadyCollector.js.map +1 -1
- package/lib/cjs/Formatter/Interfaces.d.ts +1 -1
- package/lib/cjs/Formatter/Interfaces.js.map +1 -1
- package/lib/cjs/Interfaces.js.map +1 -1
- package/lib/cjs/Parser.js.map +1 -1
- package/lib/cjs/ParserSpec.js.map +1 -1
- package/lib/cjs/Quantity.js.map +1 -1
- package/lib/cjs/QuantityLoggerCategory.js.map +1 -1
- package/lib/cjs/SerializedUnitSchema.js.map +1 -1
- package/lib/cjs/Unit.js.map +1 -1
- package/lib/cjs/UnitConversion/Graph.js.map +1 -1
- package/lib/cjs/UnitConversion/Parser.js.map +1 -1
- package/lib/cjs/UnitConversion/UnitConversion.js.map +1 -1
- package/lib/cjs/UnitConversion/UnitDefinitionResolver.js.map +1 -1
- package/lib/cjs/UnitConversion/nameUtils.js.map +1 -1
- package/lib/cjs/core-quantity.js.map +1 -1
- package/lib/cjs/internal/cross-package.js.map +1 -1
- package/lib/esm/BasicUnitsProvider.js.map +1 -1
- package/lib/esm/CompositeUnitsProvider.js.map +1 -1
- package/lib/esm/Constants.js.map +1 -1
- package/lib/esm/Exception.js.map +1 -1
- package/lib/esm/FormatSpecHandle.d.ts +9 -10
- package/lib/esm/FormatSpecHandle.d.ts.map +1 -1
- package/lib/esm/FormatSpecHandle.js +17 -35
- package/lib/esm/FormatSpecHandle.js.map +1 -1
- package/lib/esm/Formatter/Format.js.map +1 -1
- package/lib/esm/Formatter/FormatEnums.js.map +1 -1
- package/lib/esm/Formatter/Formatter.js.map +1 -1
- package/lib/esm/Formatter/FormatterSpec.js.map +1 -1
- package/lib/esm/Formatter/FormattingReadyCollector.js.map +1 -1
- package/lib/esm/Formatter/Interfaces.d.ts +1 -1
- package/lib/esm/Formatter/Interfaces.js.map +1 -1
- package/lib/esm/Interfaces.js.map +1 -1
- package/lib/esm/Parser.js.map +1 -1
- package/lib/esm/ParserSpec.js.map +1 -1
- package/lib/esm/Quantity.js.map +1 -1
- package/lib/esm/QuantityLoggerCategory.js.map +1 -1
- package/lib/esm/SerializedUnitSchema.js.map +1 -1
- package/lib/esm/Unit.js.map +1 -1
- package/lib/esm/UnitConversion/Graph.js.map +1 -1
- package/lib/esm/UnitConversion/Parser.js.map +1 -1
- package/lib/esm/UnitConversion/UnitConversion.js.map +1 -1
- package/lib/esm/UnitConversion/UnitDefinitionResolver.js.map +1 -1
- package/lib/esm/UnitConversion/nameUtils.js.map +1 -1
- package/lib/esm/core-quantity.js.map +1 -1
- package/lib/esm/internal/cross-package.js.map +1 -1
- package/package.json +4 -4
package/CHANGELOG.md
CHANGED
|
@@ -1,6 +1,22 @@
|
|
|
1
1
|
# Change Log - @itwin/core-quantity
|
|
2
2
|
|
|
3
|
-
This log was last generated on
|
|
3
|
+
This log was last generated on Tue, 05 May 2026 17:44:54 GMT and should not be manually modified.
|
|
4
|
+
|
|
5
|
+
## 5.9.1
|
|
6
|
+
Tue, 05 May 2026 17:43:30 GMT
|
|
7
|
+
|
|
8
|
+
_Version update only_
|
|
9
|
+
|
|
10
|
+
## 5.9.0
|
|
11
|
+
Mon, 04 May 2026 16:32:08 GMT
|
|
12
|
+
|
|
13
|
+
### Minor changes
|
|
14
|
+
|
|
15
|
+
- Add Units namespace with typed constants, findPersistenceUnitForPhenomenon helper, and impliedUnitSystem to FormatsChangedArgs.
|
|
16
|
+
|
|
17
|
+
### Updates
|
|
18
|
+
|
|
19
|
+
- Added BasicUnitsProvider (bundled BIS units), createUnitsProvider factory, and CreateUnitsProviderOptions interface. Added UnitConversion math, parseDefinition, and Graph utilities (moved from ecschema-metadata). Added SerializedUnitSchema types and UnitDefinitionResolver.
|
|
4
20
|
|
|
5
21
|
## 5.8.4
|
|
6
22
|
Thu, 23 Apr 2026 18:05:14 GMT
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"BasicUnitsProvider.js","sourceRoot":"","sources":["../../src/BasicUnitsProvider.ts"],"names":[],"mappings":"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","sourcesContent":["/*---------------------------------------------------------------------------------------------\n* Copyright (c) Bentley Systems, Incorporated. All rights reserved.\n* See LICENSE.md in the project root for license terms and full copyright notice.\n*--------------------------------------------------------------------------------------------*/\nimport { UnitConversionInvert, type UnitConversionProps, type UnitProps, type UnitsProvider } from \"./Interfaces\";\nimport type { SerializedInvertedUnit, SerializedUnit, SerializedUnitSchema } from \"./SerializedUnitSchema\";\nimport { type ResolvedUnit, UnitDefinitionResolver } from \"./UnitConversion/UnitDefinitionResolver\";\nimport { qualifyItemName } from \"./UnitConversion/nameUtils\";\nimport { BadUnit } from \"./Unit\";\n\ninterface IndexedUnit {\n readonly props: UnitProps;\n readonly resolved: ResolvedUnit;\n}\n\ninterface InvertedEntry {\n readonly props: UnitProps;\n readonly invertsUnitName: string;\n}\n\n/** Immutable lookup indexes resolved from the bundled Units.json. */\ninterface ResolvedState {\n readonly nameMap: Map<string, IndexedUnit>;\n readonly labelMap: Map<string, IndexedUnit[]>;\n readonly phenomenonMap: Map<string, IndexedUnit[]>;\n readonly invertedUnits: Map<string, InvertedEntry>;\n readonly schemaName: string;\n}\n\n// Module-level cache: the unit data is derived deterministically from the bundled Units.json\n// asset, so the resolved indexes are effectively an immutable constant. Caching at module\n// scope avoids redundant work when multiple BasicUnitsProvider instances are created (e.g.\n// in tests or when composed inside CompositeUnitsProvider).\n// The JSON is loaded lazily via dynamic import() on first use, keeping the module footprint\n// near-zero until a provider method is actually called.\nlet _resolvePromise: Promise<ResolvedState> | undefined;\nlet _permanentError: Error | undefined;\n\nasync function resolveState(): Promise<ResolvedState> {\n if (_permanentError !== undefined) {\n throw _permanentError;\n }\n if (!_resolvePromise) {\n _resolvePromise = _buildState().catch((err) => {\n _permanentError = err instanceof Error ? err : new Error(String(err));\n _resolvePromise = undefined;\n throw _permanentError;\n });\n }\n return _resolvePromise;\n}\n\n/** @internal — test use only. Resets the module-level lazy cache. */\nexport function _testResetUnitsCache(): void {\n _resolvePromise = undefined;\n _permanentError = undefined;\n}\n\nasync function _buildState(): Promise<ResolvedState> {\n const { default: schema } = await import(\"./assets/Units.json\");\n\n const nameMap = new Map<string, IndexedUnit>();\n const labelMap = new Map<string, IndexedUnit[]>();\n const phenomenonMap = new Map<string, IndexedUnit[]>();\n const invertedUnits = new Map<string, InvertedEntry>();\n\n const s = schema as SerializedUnitSchema;\n const resolver = new UnitDefinitionResolver(s);\n const resolved = resolver.resolveAll();\n\n for (const [name, entry] of resolved) {\n const item = s.items[name] as SerializedUnit;\n const phenomenon = item.phenomenon;\n const unitSystem = item.unitSystem;\n\n const fullName = `${s.name}.${name}`;\n const props: UnitProps = {\n name: fullName,\n label: entry.label,\n phenomenon,\n isValid: true,\n system: unitSystem,\n };\n\n const indexed: IndexedUnit = { props, resolved: entry };\n\n nameMap.set(fullName, indexed);\n const lowerLabel = entry.label.toLowerCase();\n const byLabel = labelMap.get(lowerLabel) ?? [];\n byLabel.push(indexed);\n labelMap.set(lowerLabel, byLabel);\n\n const byPhen = phenomenonMap.get(phenomenon) ?? [];\n byPhen.push(indexed);\n phenomenonMap.set(phenomenon, byPhen);\n }\n\n // Handle InvertedUnit items — must run after nameMap is fully populated above because\n // invertedSource lookup requires the inverted unit's target to already be in nameMap.\n for (const [name, item] of Object.entries(s.items)) {\n if (item.schemaItemType !== \"InvertedUnit\") {\n continue;\n }\n const inv: SerializedInvertedUnit = item;\n const fullName = `${s.name}.${name}`;\n const invertsName = qualifyItemName(inv.invertsUnit, s.name);\n const unitSystem = inv.unitSystem;\n\n const invertedSource = nameMap.get(invertsName);\n const phenomenon = invertedSource?.props.phenomenon ?? \"\";\n\n const props: UnitProps = {\n name: fullName,\n label: inv.label ?? name,\n phenomenon,\n isValid: true,\n system: unitSystem,\n };\n\n invertedUnits.set(fullName, { props, invertsUnitName: invertsName });\n\n if (invertedSource) {\n const indexed: IndexedUnit = {\n props,\n resolved: { ...invertedSource.resolved, name: fullName, label: props.label, unitSystem },\n };\n nameMap.set(fullName, indexed);\n\n const lowerLabel = props.label.toLowerCase();\n const byLabel = labelMap.get(lowerLabel) ?? [];\n byLabel.push(indexed);\n labelMap.set(lowerLabel, byLabel);\n\n const byPhen = phenomenonMap.get(phenomenon) ?? [];\n byPhen.push(indexed);\n phenomenonMap.set(phenomenon, byPhen);\n }\n }\n\n return { nameMap, labelMap, phenomenonMap, invertedUnits, schemaName: s.name };\n}\n\n/**\n * A `UnitsProvider` backed by the full BIS `Units.ecschema.json` bundled as a JSON asset.\n *\n * The ~90 KB bundled JSON is loaded lazily via dynamic `import()` on the first provider method\n * call and cached at module scope — construction is essentially free, and multiple instances\n * share the same immutable lookup indexes.\n *\n * This is the zero-dependency default for backends, tools, and any frontend that doesn't need\n * iModel overrides. Equivalent to calling `createUnitsProvider()` with no arguments.\n *\n * @see createUnitsProvider for layering schema-defined units on top of basic BIS units.\n * @beta\n */\nexport class BasicUnitsProvider implements UnitsProvider {\n\n // ── UnitsProvider implementation ─────────────────────────────────────\n\n /** Find a unit by its display label, optionally filtering by schema name, phenomenon, and unit system.\n * @param unitLabel - The display label to search for (case-insensitive).\n * @param schemaName - Optional schema name filter. Returns `BadUnit` if provided and not `\"Units\"`.\n * @param phenomenon - Optional phenomenon filter (e.g. `\"Units.LENGTH\"`).\n * @param unitSystem - Optional unit system filter (e.g. `\"Units.METRIC\"`).\n * @returns The matching `UnitProps`, or a `BadUnit` if no match is found.\n */\n public async findUnit(unitLabel: string, schemaName?: string, phenomenon?: string, unitSystem?: string): Promise<UnitProps> {\n const state = await resolveState();\n if (schemaName && schemaName !== state.schemaName) {\n return new BadUnit();\n }\n const candidates = state.labelMap.get(unitLabel.toLowerCase());\n if (!candidates || candidates.length === 0) {\n return new BadUnit();\n }\n\n for (const c of candidates) {\n if (phenomenon && c.props.phenomenon !== phenomenon) {\n continue;\n }\n if (unitSystem && c.props.system !== unitSystem) {\n continue;\n }\n return c.props;\n }\n\n return new BadUnit();\n }\n\n /** Return all units belonging to the given phenomenon (unit family).\n * @param phenomenon - The phenomenon full name (e.g. `\"Units.LENGTH\"`).\n * @returns An array of matching `UnitProps`, or an empty array if none.\n */\n public async getUnitsByFamily(phenomenon: string): Promise<UnitProps[]> {\n const state = await resolveState();\n const entries = state.phenomenonMap.get(phenomenon);\n return entries ? entries.map((e) => e.props) : [];\n }\n\n /** Find a unit by its fully-qualified name (e.g. `\"Units.M\"`).\n * @param unitName - The qualified unit name.\n * @returns The matching `UnitProps`, or a `BadUnit` if not found.\n */\n public async findUnitByName(unitName: string): Promise<UnitProps> {\n const state = await resolveState();\n const entry = state.nameMap.get(unitName);\n return entry ? entry.props : new BadUnit();\n }\n\n /** Compute the conversion factors from `fromUnit` to `toUnit`.\n * Handles normal units, inverted units, and mixed (inverted ↔ non-inverted) conversions.\n * @param fromUnit - The source unit.\n * @param toUnit - The target unit.\n * @returns A `UnitConversionProps` with `factor`, `offset`, and optionally `inversion` and `error`.\n */\n public async getConversion(fromUnit: UnitProps, toUnit: UnitProps): Promise<UnitConversionProps> {\n const state = await resolveState();\n const from = state.nameMap.get(fromUnit.name);\n const to = state.nameMap.get(toUnit.name);\n\n if (!from || !to) {\n return { factor: 1.0, offset: 0.0, error: true };\n }\n\n const fromInverted = state.invertedUnits.get(fromUnit.name);\n const toInverted = state.invertedUnits.get(toUnit.name);\n\n const fromPhenomenon = fromInverted\n ? state.nameMap.get(fromInverted.invertsUnitName)?.props.phenomenon\n : from.props.phenomenon;\n const toPhenomenon = toInverted\n ? state.nameMap.get(toInverted.invertsUnitName)?.props.phenomenon\n : to.props.phenomenon;\n if (fromPhenomenon !== toPhenomenon) {\n return { factor: 1.0, offset: 0.0, error: true };\n }\n\n if (fromInverted && toInverted) {\n const innerFrom = state.nameMap.get(fromInverted.invertsUnitName);\n const innerTo = state.nameMap.get(toInverted.invertsUnitName);\n if (innerFrom && innerTo) {\n const c = innerFrom.resolved.conversion.inverse().compose(innerTo.resolved.conversion);\n return { factor: c.factor, offset: c.offset };\n }\n }\n\n if (fromInverted) {\n const innerFrom = state.nameMap.get(fromInverted.invertsUnitName);\n if (innerFrom) {\n const c = innerFrom.resolved.conversion.inverse().compose(to.resolved.conversion);\n return { factor: c.factor, offset: c.offset, inversion: UnitConversionInvert.InvertPreConversion };\n }\n }\n\n if (toInverted) {\n const innerTo = state.nameMap.get(toInverted.invertsUnitName);\n if (innerTo) {\n const c = from.resolved.conversion.inverse().compose(innerTo.resolved.conversion);\n return { factor: c.factor, offset: c.offset, inversion: UnitConversionInvert.InvertPostConversion };\n }\n }\n\n const conv = from.resolved.conversion.inverse().compose(to.resolved.conversion);\n return { factor: conv.factor, offset: conv.offset };\n }\n}\n"]}
|
|
1
|
+
{"version":3,"file":"BasicUnitsProvider.js","sourceRoot":"","sources":["../../src/BasicUnitsProvider.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;AAqDA,oDAGC;AAxDD;;;+FAG+F;AAC/F,6CAAkH;AAElH,oFAAoG;AACpG,0DAA6D;AAC7D,iCAAiC;AAqBjC,6FAA6F;AAC7F,0FAA0F;AAC1F,2FAA2F;AAC3F,4DAA4D;AAC5D,4FAA4F;AAC5F,wDAAwD;AACxD,IAAI,eAAmD,CAAC;AACxD,IAAI,eAAkC,CAAC;AAEvC,KAAK,UAAU,YAAY;IACzB,IAAI,eAAe,KAAK,SAAS,EAAE,CAAC;QAClC,MAAM,eAAe,CAAC;IACxB,CAAC;IACD,IAAI,CAAC,eAAe,EAAE,CAAC;QACrB,eAAe,GAAG,WAAW,EAAE,CAAC,KAAK,CAAC,CAAC,GAAG,EAAE,EAAE;YAC5C,eAAe,GAAG,GAAG,YAAY,KAAK,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,IAAI,KAAK,CAAC,MAAM,CAAC,GAAG,CAAC,CAAC,CAAC;YACtE,eAAe,GAAG,SAAS,CAAC;YAC5B,MAAM,eAAe,CAAC;QACxB,CAAC,CAAC,CAAC;IACL,CAAC;IACD,OAAO,eAAe,CAAC;AACzB,CAAC;AAED,qEAAqE;AACrE,SAAgB,oBAAoB;IAClC,eAAe,GAAG,SAAS,CAAC;IAC5B,eAAe,GAAG,SAAS,CAAC;AAC9B,CAAC;AAED,KAAK,UAAU,WAAW;IACxB,MAAM,EAAE,OAAO,EAAE,MAAM,EAAE,GAAG,wDAAa,qBAAqB,GAAC,CAAC;IAEhE,MAAM,OAAO,GAAG,IAAI,GAAG,EAAuB,CAAC;IAC/C,MAAM,QAAQ,GAAG,IAAI,GAAG,EAAyB,CAAC;IAClD,MAAM,aAAa,GAAG,IAAI,GAAG,EAAyB,CAAC;IACvD,MAAM,aAAa,GAAG,IAAI,GAAG,EAAyB,CAAC;IAEvD,MAAM,CAAC,GAAG,MAA8B,CAAC;IACzC,MAAM,QAAQ,GAAG,IAAI,+CAAsB,CAAC,CAAC,CAAC,CAAC;IAC/C,MAAM,QAAQ,GAAG,QAAQ,CAAC,UAAU,EAAE,CAAC;IAEvC,KAAK,MAAM,CAAC,IAAI,EAAE,KAAK,CAAC,IAAI,QAAQ,EAAE,CAAC;QACrC,MAAM,IAAI,GAAG,CAAC,CAAC,KAAK,CAAC,IAAI,CAAmB,CAAC;QAC7C,MAAM,UAAU,GAAG,IAAI,CAAC,UAAU,CAAC;QACnC,MAAM,UAAU,GAAG,IAAI,CAAC,UAAU,CAAC;QAEnC,MAAM,QAAQ,GAAG,GAAG,CAAC,CAAC,IAAI,IAAI,IAAI,EAAE,CAAC;QACrC,MAAM,KAAK,GAAc;YACvB,IAAI,EAAE,QAAQ;YACd,KAAK,EAAE,KAAK,CAAC,KAAK;YAClB,UAAU;YACV,OAAO,EAAE,IAAI;YACb,MAAM,EAAE,UAAU;SACnB,CAAC;QAEF,MAAM,OAAO,GAAgB,EAAE,KAAK,EAAE,QAAQ,EAAE,KAAK,EAAE,CAAC;QAExD,OAAO,CAAC,GAAG,CAAC,QAAQ,EAAE,OAAO,CAAC,CAAC;QAC/B,MAAM,UAAU,GAAG,KAAK,CAAC,KAAK,CAAC,WAAW,EAAE,CAAC;QAC7C,MAAM,OAAO,GAAG,QAAQ,CAAC,GAAG,CAAC,UAAU,CAAC,IAAI,EAAE,CAAC;QAC/C,OAAO,CAAC,IAAI,CAAC,OAAO,CAAC,CAAC;QACtB,QAAQ,CAAC,GAAG,CAAC,UAAU,EAAE,OAAO,CAAC,CAAC;QAElC,MAAM,MAAM,GAAG,aAAa,CAAC,GAAG,CAAC,UAAU,CAAC,IAAI,EAAE,CAAC;QACnD,MAAM,CAAC,IAAI,CAAC,OAAO,CAAC,CAAC;QACrB,aAAa,CAAC,GAAG,CAAC,UAAU,EAAE,MAAM,CAAC,CAAC;IACxC,CAAC;IAED,sFAAsF;IACtF,sFAAsF;IACtF,KAAK,MAAM,CAAC,IAAI,EAAE,IAAI,CAAC,IAAI,MAAM,CAAC,OAAO,CAAC,CAAC,CAAC,KAAK,CAAC,EAAE,CAAC;QACnD,IAAI,IAAI,CAAC,cAAc,KAAK,cAAc,EAAE,CAAC;YAC3C,SAAS;QACX,CAAC;QACD,MAAM,GAAG,GAA2B,IAAI,CAAC;QACzC,MAAM,QAAQ,GAAG,GAAG,CAAC,CAAC,IAAI,IAAI,IAAI,EAAE,CAAC;QACrC,MAAM,WAAW,GAAG,IAAA,2BAAe,EAAC,GAAG,CAAC,WAAW,EAAE,CAAC,CAAC,IAAI,CAAC,CAAC;QAC7D,MAAM,UAAU,GAAG,GAAG,CAAC,UAAU,CAAC;QAElC,MAAM,cAAc,GAAG,OAAO,CAAC,GAAG,CAAC,WAAW,CAAC,CAAC;QAChD,MAAM,UAAU,GAAG,cAAc,EAAE,KAAK,CAAC,UAAU,IAAI,EAAE,CAAC;QAE1D,MAAM,KAAK,GAAc;YACvB,IAAI,EAAE,QAAQ;YACd,KAAK,EAAE,GAAG,CAAC,KAAK,IAAI,IAAI;YACxB,UAAU;YACV,OAAO,EAAE,IAAI;YACb,MAAM,EAAE,UAAU;SACnB,CAAC;QAEF,aAAa,CAAC,GAAG,CAAC,QAAQ,EAAE,EAAE,KAAK,EAAE,eAAe,EAAE,WAAW,EAAE,CAAC,CAAC;QAErE,IAAI,cAAc,EAAE,CAAC;YACnB,MAAM,OAAO,GAAgB;gBAC3B,KAAK;gBACL,QAAQ,EAAE,EAAE,GAAG,cAAc,CAAC,QAAQ,EAAE,IAAI,EAAE,QAAQ,EAAE,KAAK,EAAE,KAAK,CAAC,KAAK,EAAE,UAAU,EAAE;aACzF,CAAC;YACF,OAAO,CAAC,GAAG,CAAC,QAAQ,EAAE,OAAO,CAAC,CAAC;YAE/B,MAAM,UAAU,GAAG,KAAK,CAAC,KAAK,CAAC,WAAW,EAAE,CAAC;YAC7C,MAAM,OAAO,GAAG,QAAQ,CAAC,GAAG,CAAC,UAAU,CAAC,IAAI,EAAE,CAAC;YAC/C,OAAO,CAAC,IAAI,CAAC,OAAO,CAAC,CAAC;YACtB,QAAQ,CAAC,GAAG,CAAC,UAAU,EAAE,OAAO,CAAC,CAAC;YAElC,MAAM,MAAM,GAAG,aAAa,CAAC,GAAG,CAAC,UAAU,CAAC,IAAI,EAAE,CAAC;YACnD,MAAM,CAAC,IAAI,CAAC,OAAO,CAAC,CAAC;YACrB,aAAa,CAAC,GAAG,CAAC,UAAU,EAAE,MAAM,CAAC,CAAC;QACxC,CAAC;IACH,CAAC;IAED,OAAO,EAAE,OAAO,EAAE,QAAQ,EAAE,aAAa,EAAE,aAAa,EAAE,UAAU,EAAE,CAAC,CAAC,IAAI,EAAE,CAAC;AACjF,CAAC;AAED;;;;;;;;;;;;GAYG;AACH,MAAa,kBAAkB;IAE7B,wEAAwE;IAExE;;;;;;OAMG;IACI,KAAK,CAAC,QAAQ,CAAC,SAAiB,EAAE,UAAmB,EAAE,UAAmB,EAAE,UAAmB;QACpG,MAAM,KAAK,GAAG,MAAM,YAAY,EAAE,CAAC;QACnC,IAAI,UAAU,IAAI,UAAU,KAAK,KAAK,CAAC,UAAU,EAAE,CAAC;YAClD,OAAO,IAAI,cAAO,EAAE,CAAC;QACvB,CAAC;QACD,MAAM,UAAU,GAAG,KAAK,CAAC,QAAQ,CAAC,GAAG,CAAC,SAAS,CAAC,WAAW,EAAE,CAAC,CAAC;QAC/D,IAAI,CAAC,UAAU,IAAI,UAAU,CAAC,MAAM,KAAK,CAAC,EAAE,CAAC;YAC3C,OAAO,IAAI,cAAO,EAAE,CAAC;QACvB,CAAC;QAED,KAAK,MAAM,CAAC,IAAI,UAAU,EAAE,CAAC;YAC3B,IAAI,UAAU,IAAI,CAAC,CAAC,KAAK,CAAC,UAAU,KAAK,UAAU,EAAE,CAAC;gBACpD,SAAS;YACX,CAAC;YACD,IAAI,UAAU,IAAI,CAAC,CAAC,KAAK,CAAC,MAAM,KAAK,UAAU,EAAE,CAAC;gBAChD,SAAS;YACX,CAAC;YACD,OAAO,CAAC,CAAC,KAAK,CAAC;QACjB,CAAC;QAED,OAAO,IAAI,cAAO,EAAE,CAAC;IACvB,CAAC;IAED;;;OAGG;IACI,KAAK,CAAC,gBAAgB,CAAC,UAAkB;QAC9C,MAAM,KAAK,GAAG,MAAM,YAAY,EAAE,CAAC;QACnC,MAAM,OAAO,GAAG,KAAK,CAAC,aAAa,CAAC,GAAG,CAAC,UAAU,CAAC,CAAC;QACpD,OAAO,OAAO,CAAC,CAAC,CAAC,OAAO,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC;IACpD,CAAC;IAED;;;OAGG;IACI,KAAK,CAAC,cAAc,CAAC,QAAgB;QAC1C,MAAM,KAAK,GAAG,MAAM,YAAY,EAAE,CAAC;QACnC,MAAM,KAAK,GAAG,KAAK,CAAC,OAAO,CAAC,GAAG,CAAC,QAAQ,CAAC,CAAC;QAC1C,OAAO,KAAK,CAAC,CAAC,CAAC,KAAK,CAAC,KAAK,CAAC,CAAC,CAAC,IAAI,cAAO,EAAE,CAAC;IAC7C,CAAC;IAED;;;;;OAKG;IACI,KAAK,CAAC,aAAa,CAAC,QAAmB,EAAE,MAAiB;QAC/D,MAAM,KAAK,GAAG,MAAM,YAAY,EAAE,CAAC;QACnC,MAAM,IAAI,GAAG,KAAK,CAAC,OAAO,CAAC,GAAG,CAAC,QAAQ,CAAC,IAAI,CAAC,CAAC;QAC9C,MAAM,EAAE,GAAG,KAAK,CAAC,OAAO,CAAC,GAAG,CAAC,MAAM,CAAC,IAAI,CAAC,CAAC;QAE1C,IAAI,CAAC,IAAI,IAAI,CAAC,EAAE,EAAE,CAAC;YACjB,OAAO,EAAE,MAAM,EAAE,GAAG,EAAE,MAAM,EAAE,GAAG,EAAE,KAAK,EAAE,IAAI,EAAE,CAAC;QACnD,CAAC;QAED,MAAM,YAAY,GAAG,KAAK,CAAC,aAAa,CAAC,GAAG,CAAC,QAAQ,CAAC,IAAI,CAAC,CAAC;QAC5D,MAAM,UAAU,GAAG,KAAK,CAAC,aAAa,CAAC,GAAG,CAAC,MAAM,CAAC,IAAI,CAAC,CAAC;QAExD,MAAM,cAAc,GAAG,YAAY;YACjC,CAAC,CAAC,KAAK,CAAC,OAAO,CAAC,GAAG,CAAC,YAAY,CAAC,eAAe,CAAC,EAAE,KAAK,CAAC,UAAU;YACnE,CAAC,CAAC,IAAI,CAAC,KAAK,CAAC,UAAU,CAAC;QAC1B,MAAM,YAAY,GAAG,UAAU;YAC7B,CAAC,CAAC,KAAK,CAAC,OAAO,CAAC,GAAG,CAAC,UAAU,CAAC,eAAe,CAAC,EAAE,KAAK,CAAC,UAAU;YACjE,CAAC,CAAC,EAAE,CAAC,KAAK,CAAC,UAAU,CAAC;QACxB,IAAI,cAAc,KAAK,YAAY,EAAE,CAAC;YACpC,OAAO,EAAE,MAAM,EAAE,GAAG,EAAE,MAAM,EAAE,GAAG,EAAE,KAAK,EAAE,IAAI,EAAE,CAAC;QACnD,CAAC;QAED,IAAI,YAAY,IAAI,UAAU,EAAE,CAAC;YAC/B,MAAM,SAAS,GAAG,KAAK,CAAC,OAAO,CAAC,GAAG,CAAC,YAAY,CAAC,eAAe,CAAC,CAAC;YAClE,MAAM,OAAO,GAAG,KAAK,CAAC,OAAO,CAAC,GAAG,CAAC,UAAU,CAAC,eAAe,CAAC,CAAC;YAC9D,IAAI,SAAS,IAAI,OAAO,EAAE,CAAC;gBACzB,MAAM,CAAC,GAAG,SAAS,CAAC,QAAQ,CAAC,UAAU,CAAC,OAAO,EAAE,CAAC,OAAO,CAAC,OAAO,CAAC,QAAQ,CAAC,UAAU,CAAC,CAAC;gBACvF,OAAO,EAAE,MAAM,EAAE,CAAC,CAAC,MAAM,EAAE,MAAM,EAAE,CAAC,CAAC,MAAM,EAAE,CAAC;YAChD,CAAC;QACH,CAAC;QAED,IAAI,YAAY,EAAE,CAAC;YACjB,MAAM,SAAS,GAAG,KAAK,CAAC,OAAO,CAAC,GAAG,CAAC,YAAY,CAAC,eAAe,CAAC,CAAC;YAClE,IAAI,SAAS,EAAE,CAAC;gBACd,MAAM,CAAC,GAAG,SAAS,CAAC,QAAQ,CAAC,UAAU,CAAC,OAAO,EAAE,CAAC,OAAO,CAAC,EAAE,CAAC,QAAQ,CAAC,UAAU,CAAC,CAAC;gBAClF,OAAO,EAAE,MAAM,EAAE,CAAC,CAAC,MAAM,EAAE,MAAM,EAAE,CAAC,CAAC,MAAM,EAAE,SAAS,EAAE,iCAAoB,CAAC,mBAAmB,EAAE,CAAC;YACrG,CAAC;QACH,CAAC;QAED,IAAI,UAAU,EAAE,CAAC;YACf,MAAM,OAAO,GAAG,KAAK,CAAC,OAAO,CAAC,GAAG,CAAC,UAAU,CAAC,eAAe,CAAC,CAAC;YAC9D,IAAI,OAAO,EAAE,CAAC;gBACZ,MAAM,CAAC,GAAG,IAAI,CAAC,QAAQ,CAAC,UAAU,CAAC,OAAO,EAAE,CAAC,OAAO,CAAC,OAAO,CAAC,QAAQ,CAAC,UAAU,CAAC,CAAC;gBAClF,OAAO,EAAE,MAAM,EAAE,CAAC,CAAC,MAAM,EAAE,MAAM,EAAE,CAAC,CAAC,MAAM,EAAE,SAAS,EAAE,iCAAoB,CAAC,oBAAoB,EAAE,CAAC;YACtG,CAAC;QACH,CAAC;QAED,MAAM,IAAI,GAAG,IAAI,CAAC,QAAQ,CAAC,UAAU,CAAC,OAAO,EAAE,CAAC,OAAO,CAAC,EAAE,CAAC,QAAQ,CAAC,UAAU,CAAC,CAAC;QAChF,OAAO,EAAE,MAAM,EAAE,IAAI,CAAC,MAAM,EAAE,MAAM,EAAE,IAAI,CAAC,MAAM,EAAE,CAAC;IACtD,CAAC;CACF;AA9GD,gDA8GC","sourcesContent":["/*---------------------------------------------------------------------------------------------\r\n* Copyright (c) Bentley Systems, Incorporated. All rights reserved.\r\n* See LICENSE.md in the project root for license terms and full copyright notice.\r\n*--------------------------------------------------------------------------------------------*/\r\nimport { UnitConversionInvert, type UnitConversionProps, type UnitProps, type UnitsProvider } from \"./Interfaces\";\r\nimport type { SerializedInvertedUnit, SerializedUnit, SerializedUnitSchema } from \"./SerializedUnitSchema\";\r\nimport { type ResolvedUnit, UnitDefinitionResolver } from \"./UnitConversion/UnitDefinitionResolver\";\r\nimport { qualifyItemName } from \"./UnitConversion/nameUtils\";\r\nimport { BadUnit } from \"./Unit\";\r\n\r\ninterface IndexedUnit {\r\n readonly props: UnitProps;\r\n readonly resolved: ResolvedUnit;\r\n}\r\n\r\ninterface InvertedEntry {\r\n readonly props: UnitProps;\r\n readonly invertsUnitName: string;\r\n}\r\n\r\n/** Immutable lookup indexes resolved from the bundled Units.json. */\r\ninterface ResolvedState {\r\n readonly nameMap: Map<string, IndexedUnit>;\r\n readonly labelMap: Map<string, IndexedUnit[]>;\r\n readonly phenomenonMap: Map<string, IndexedUnit[]>;\r\n readonly invertedUnits: Map<string, InvertedEntry>;\r\n readonly schemaName: string;\r\n}\r\n\r\n// Module-level cache: the unit data is derived deterministically from the bundled Units.json\r\n// asset, so the resolved indexes are effectively an immutable constant. Caching at module\r\n// scope avoids redundant work when multiple BasicUnitsProvider instances are created (e.g.\r\n// in tests or when composed inside CompositeUnitsProvider).\r\n// The JSON is loaded lazily via dynamic import() on first use, keeping the module footprint\r\n// near-zero until a provider method is actually called.\r\nlet _resolvePromise: Promise<ResolvedState> | undefined;\r\nlet _permanentError: Error | undefined;\r\n\r\nasync function resolveState(): Promise<ResolvedState> {\r\n if (_permanentError !== undefined) {\r\n throw _permanentError;\r\n }\r\n if (!_resolvePromise) {\r\n _resolvePromise = _buildState().catch((err) => {\r\n _permanentError = err instanceof Error ? err : new Error(String(err));\r\n _resolvePromise = undefined;\r\n throw _permanentError;\r\n });\r\n }\r\n return _resolvePromise;\r\n}\r\n\r\n/** @internal — test use only. Resets the module-level lazy cache. */\r\nexport function _testResetUnitsCache(): void {\r\n _resolvePromise = undefined;\r\n _permanentError = undefined;\r\n}\r\n\r\nasync function _buildState(): Promise<ResolvedState> {\r\n const { default: schema } = await import(\"./assets/Units.json\");\r\n\r\n const nameMap = new Map<string, IndexedUnit>();\r\n const labelMap = new Map<string, IndexedUnit[]>();\r\n const phenomenonMap = new Map<string, IndexedUnit[]>();\r\n const invertedUnits = new Map<string, InvertedEntry>();\r\n\r\n const s = schema as SerializedUnitSchema;\r\n const resolver = new UnitDefinitionResolver(s);\r\n const resolved = resolver.resolveAll();\r\n\r\n for (const [name, entry] of resolved) {\r\n const item = s.items[name] as SerializedUnit;\r\n const phenomenon = item.phenomenon;\r\n const unitSystem = item.unitSystem;\r\n\r\n const fullName = `${s.name}.${name}`;\r\n const props: UnitProps = {\r\n name: fullName,\r\n label: entry.label,\r\n phenomenon,\r\n isValid: true,\r\n system: unitSystem,\r\n };\r\n\r\n const indexed: IndexedUnit = { props, resolved: entry };\r\n\r\n nameMap.set(fullName, indexed);\r\n const lowerLabel = entry.label.toLowerCase();\r\n const byLabel = labelMap.get(lowerLabel) ?? [];\r\n byLabel.push(indexed);\r\n labelMap.set(lowerLabel, byLabel);\r\n\r\n const byPhen = phenomenonMap.get(phenomenon) ?? [];\r\n byPhen.push(indexed);\r\n phenomenonMap.set(phenomenon, byPhen);\r\n }\r\n\r\n // Handle InvertedUnit items — must run after nameMap is fully populated above because\r\n // invertedSource lookup requires the inverted unit's target to already be in nameMap.\r\n for (const [name, item] of Object.entries(s.items)) {\r\n if (item.schemaItemType !== \"InvertedUnit\") {\r\n continue;\r\n }\r\n const inv: SerializedInvertedUnit = item;\r\n const fullName = `${s.name}.${name}`;\r\n const invertsName = qualifyItemName(inv.invertsUnit, s.name);\r\n const unitSystem = inv.unitSystem;\r\n\r\n const invertedSource = nameMap.get(invertsName);\r\n const phenomenon = invertedSource?.props.phenomenon ?? \"\";\r\n\r\n const props: UnitProps = {\r\n name: fullName,\r\n label: inv.label ?? name,\r\n phenomenon,\r\n isValid: true,\r\n system: unitSystem,\r\n };\r\n\r\n invertedUnits.set(fullName, { props, invertsUnitName: invertsName });\r\n\r\n if (invertedSource) {\r\n const indexed: IndexedUnit = {\r\n props,\r\n resolved: { ...invertedSource.resolved, name: fullName, label: props.label, unitSystem },\r\n };\r\n nameMap.set(fullName, indexed);\r\n\r\n const lowerLabel = props.label.toLowerCase();\r\n const byLabel = labelMap.get(lowerLabel) ?? [];\r\n byLabel.push(indexed);\r\n labelMap.set(lowerLabel, byLabel);\r\n\r\n const byPhen = phenomenonMap.get(phenomenon) ?? [];\r\n byPhen.push(indexed);\r\n phenomenonMap.set(phenomenon, byPhen);\r\n }\r\n }\r\n\r\n return { nameMap, labelMap, phenomenonMap, invertedUnits, schemaName: s.name };\r\n}\r\n\r\n/**\r\n * A `UnitsProvider` backed by the full BIS `Units.ecschema.json` bundled as a JSON asset.\r\n *\r\n * The ~90 KB bundled JSON is loaded lazily via dynamic `import()` on the first provider method\r\n * call and cached at module scope — construction is essentially free, and multiple instances\r\n * share the same immutable lookup indexes.\r\n *\r\n * This is the zero-dependency default for backends, tools, and any frontend that doesn't need\r\n * iModel overrides. Equivalent to calling `createUnitsProvider()` with no arguments.\r\n *\r\n * @see createUnitsProvider for layering schema-defined units on top of basic BIS units.\r\n * @beta\r\n */\r\nexport class BasicUnitsProvider implements UnitsProvider {\r\n\r\n // ── UnitsProvider implementation ─────────────────────────────────────\r\n\r\n /** Find a unit by its display label, optionally filtering by schema name, phenomenon, and unit system.\r\n * @param unitLabel - The display label to search for (case-insensitive).\r\n * @param schemaName - Optional schema name filter. Returns `BadUnit` if provided and not `\"Units\"`.\r\n * @param phenomenon - Optional phenomenon filter (e.g. `\"Units.LENGTH\"`).\r\n * @param unitSystem - Optional unit system filter (e.g. `\"Units.METRIC\"`).\r\n * @returns The matching `UnitProps`, or a `BadUnit` if no match is found.\r\n */\r\n public async findUnit(unitLabel: string, schemaName?: string, phenomenon?: string, unitSystem?: string): Promise<UnitProps> {\r\n const state = await resolveState();\r\n if (schemaName && schemaName !== state.schemaName) {\r\n return new BadUnit();\r\n }\r\n const candidates = state.labelMap.get(unitLabel.toLowerCase());\r\n if (!candidates || candidates.length === 0) {\r\n return new BadUnit();\r\n }\r\n\r\n for (const c of candidates) {\r\n if (phenomenon && c.props.phenomenon !== phenomenon) {\r\n continue;\r\n }\r\n if (unitSystem && c.props.system !== unitSystem) {\r\n continue;\r\n }\r\n return c.props;\r\n }\r\n\r\n return new BadUnit();\r\n }\r\n\r\n /** Return all units belonging to the given phenomenon (unit family).\r\n * @param phenomenon - The phenomenon full name (e.g. `\"Units.LENGTH\"`).\r\n * @returns An array of matching `UnitProps`, or an empty array if none.\r\n */\r\n public async getUnitsByFamily(phenomenon: string): Promise<UnitProps[]> {\r\n const state = await resolveState();\r\n const entries = state.phenomenonMap.get(phenomenon);\r\n return entries ? entries.map((e) => e.props) : [];\r\n }\r\n\r\n /** Find a unit by its fully-qualified name (e.g. `\"Units.M\"`).\r\n * @param unitName - The qualified unit name.\r\n * @returns The matching `UnitProps`, or a `BadUnit` if not found.\r\n */\r\n public async findUnitByName(unitName: string): Promise<UnitProps> {\r\n const state = await resolveState();\r\n const entry = state.nameMap.get(unitName);\r\n return entry ? entry.props : new BadUnit();\r\n }\r\n\r\n /** Compute the conversion factors from `fromUnit` to `toUnit`.\r\n * Handles normal units, inverted units, and mixed (inverted ↔ non-inverted) conversions.\r\n * @param fromUnit - The source unit.\r\n * @param toUnit - The target unit.\r\n * @returns A `UnitConversionProps` with `factor`, `offset`, and optionally `inversion` and `error`.\r\n */\r\n public async getConversion(fromUnit: UnitProps, toUnit: UnitProps): Promise<UnitConversionProps> {\r\n const state = await resolveState();\r\n const from = state.nameMap.get(fromUnit.name);\r\n const to = state.nameMap.get(toUnit.name);\r\n\r\n if (!from || !to) {\r\n return { factor: 1.0, offset: 0.0, error: true };\r\n }\r\n\r\n const fromInverted = state.invertedUnits.get(fromUnit.name);\r\n const toInverted = state.invertedUnits.get(toUnit.name);\r\n\r\n const fromPhenomenon = fromInverted\r\n ? state.nameMap.get(fromInverted.invertsUnitName)?.props.phenomenon\r\n : from.props.phenomenon;\r\n const toPhenomenon = toInverted\r\n ? state.nameMap.get(toInverted.invertsUnitName)?.props.phenomenon\r\n : to.props.phenomenon;\r\n if (fromPhenomenon !== toPhenomenon) {\r\n return { factor: 1.0, offset: 0.0, error: true };\r\n }\r\n\r\n if (fromInverted && toInverted) {\r\n const innerFrom = state.nameMap.get(fromInverted.invertsUnitName);\r\n const innerTo = state.nameMap.get(toInverted.invertsUnitName);\r\n if (innerFrom && innerTo) {\r\n const c = innerFrom.resolved.conversion.inverse().compose(innerTo.resolved.conversion);\r\n return { factor: c.factor, offset: c.offset };\r\n }\r\n }\r\n\r\n if (fromInverted) {\r\n const innerFrom = state.nameMap.get(fromInverted.invertsUnitName);\r\n if (innerFrom) {\r\n const c = innerFrom.resolved.conversion.inverse().compose(to.resolved.conversion);\r\n return { factor: c.factor, offset: c.offset, inversion: UnitConversionInvert.InvertPreConversion };\r\n }\r\n }\r\n\r\n if (toInverted) {\r\n const innerTo = state.nameMap.get(toInverted.invertsUnitName);\r\n if (innerTo) {\r\n const c = from.resolved.conversion.inverse().compose(innerTo.resolved.conversion);\r\n return { factor: c.factor, offset: c.offset, inversion: UnitConversionInvert.InvertPostConversion };\r\n }\r\n }\r\n\r\n const conv = from.resolved.conversion.inverse().compose(to.resolved.conversion);\r\n return { factor: conv.factor, offset: conv.offset };\r\n }\r\n}\r\n"]}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"CompositeUnitsProvider.js","sourceRoot":"","sources":["../../src/CompositeUnitsProvider.ts"],"names":[],"mappings":"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","sourcesContent":["/*---------------------------------------------------------------------------------------------\n* Copyright (c) Bentley Systems, Incorporated. All rights reserved.\n* See LICENSE.md in the project root for license terms and full copyright notice.\n*--------------------------------------------------------------------------------------------*/\nimport { BasicUnitsProvider } from \"./BasicUnitsProvider\";\nimport type { UnitConversionProps, UnitProps, UnitsProvider } from \"./Interfaces\";\nimport { BadUnit } from \"./Unit\";\n\n/**\n * Options for [[createUnitsProvider]].\n * @beta\n */\nexport interface CreateUnitsProviderOptions {\n /**\n * A `UnitsProvider` consulted before the basic BIS units (e.g. a `SchemaUnitProvider`\n * for an open iModel's `SchemaContext`). When omitted, the returned provider behaves\n * exactly like `new BasicUnitsProvider()`.\n */\n primary?: UnitsProvider;\n\n /**\n * Controls which provider is consulted first and wins ties.\n * - `\"preferSchema\"` (default): `primary` is authoritative; bundled BIS units are fallback.\n * - `\"preferBundled\"`: bundled BIS units win; `primary` is consulted only for units not in\n * the bundled set. Use when the iModel's schema may be stale.\n *\n * Affects `findUnit`, `findUnitByName`, and `getConversion` (first-consulted wins or\n * falls through). `getUnitsByFamily` always merges both providers — the first-consulted\n * provider wins name collisions.\n *\n * Has no effect when `primary` is omitted — the returned provider is a plain `BasicUnitsProvider`.\n */\n bisUnitsPolicy?: \"preferSchema\" | \"preferBundled\";\n}\n\n/**\n * Returns a `UnitsProvider` that layers the basic BIS units under (or over) an optional\n * `primary` provider. Typical use: layer an iModel's schema units on top of the bundled\n * defaults from `@itwin/core-quantity`.\n *\n * Precedence rules:\n * - When `primary` is supplied and `bisUnitsPolicy` is `\"preferSchema\"` (the default): `primary` wins;\n * basic BIS units fill any gaps where `primary` returns an invalid unit or throws.\n * - When `bisUnitsPolicy` is `\"preferBundled\"`: basic BIS units win; `primary` is consulted only when the\n * basic provider can't answer.\n * - `getUnitsByFamily` always merges results from both providers, deduplicated by\n * `UnitProps.name` (fully-qualified). The first-consulted provider wins ties.\n * - When no `primary` is supplied, the returned provider is exactly `new BasicUnitsProvider()`\n * (no wrapper), preserving `instanceof` checks and keeping the hot path fast.\n *\n * @beta\n */\nexport function createUnitsProvider(options: CreateUnitsProviderOptions = {}): UnitsProvider {\n const basic = new BasicUnitsProvider();\n const primary = options.primary;\n // NOTE: returns BasicUnitsProvider directly when no primary is provided.\n // QuantityFormatter.resetToUseInternalUnitsProvider uses instanceof BasicUnitsProvider to detect this.\n // If this fast-path is ever wrapped (e.g. for telemetry), that guard must be updated.\n if (!primary) {\n return basic;\n }\n\n const providers = options.bisUnitsPolicy === \"preferBundled\" ? [basic, primary] : [primary, basic];\n return new CompositeUnitsProvider(providers);\n}\n\nclass CompositeUnitsProvider implements UnitsProvider {\n constructor(private readonly _providers: UnitsProvider[]) {}\n\n public async findUnit(label: string, schemaName?: string, phenomenon?: string, unitSystem?: string): Promise<UnitProps> {\n for (let i = 0; i < this._providers.length - 1; i++) {\n const hit = await tryFind(async () => this._providers[i].findUnit(label, schemaName, phenomenon, unitSystem));\n if (hit?.isValid) {\n return hit;\n }\n }\n return tryFind(async () => this._providers[this._providers.length - 1].findUnit(label, schemaName, phenomenon, unitSystem)).then((hit) => hit ?? new BadUnit());\n }\n\n public async findUnitByName(name: string): Promise<UnitProps> {\n for (let i = 0; i < this._providers.length - 1; i++) {\n const hit = await tryFind(async () => this._providers[i].findUnitByName(name));\n if (hit?.isValid) {\n return hit;\n }\n }\n return tryFind(async () => this._providers[this._providers.length - 1].findUnitByName(name)).then((hit) => hit ?? new BadUnit());\n }\n\n public async getUnitsByFamily(phenomenon: string): Promise<UnitProps[]> {\n const seen = new Set<string>();\n const out: UnitProps[] = [];\n // Query all providers in parallel; process results in declaration order to honour precedence.\n const results = await Promise.all(this._providers.map(async (p) => tryList(async () => p.getUnitsByFamily(phenomenon))));\n for (const units of results) {\n for (const u of units) {\n if (!seen.has(u.name)) {\n seen.add(u.name);\n out.push(u);\n }\n }\n }\n return out;\n }\n\n public async getConversion(from: UnitProps, to: UnitProps): Promise<UnitConversionProps> {\n for (let i = 0; i < this._providers.length - 1; i++) {\n try {\n const result = await this._providers[i].getConversion(from, to);\n if (!result.error) {\n return result;\n }\n } catch { /* fall through to next provider */ }\n }\n try {\n return await this._providers[this._providers.length - 1].getConversion(from, to);\n } catch {\n return { factor: 1.0, offset: 0.0, error: true };\n }\n }\n}\n\nasync function tryFind(fn: () => Promise<UnitProps>): Promise<UnitProps | undefined> {\n try { return await fn(); } catch { return undefined; }\n}\n\nasync function tryList(fn: () => Promise<UnitProps[]>): Promise<UnitProps[]> {\n try { return await fn(); } catch { return []; }\n}\n"]}
|
|
1
|
+
{"version":3,"file":"CompositeUnitsProvider.js","sourceRoot":"","sources":["../../src/CompositeUnitsProvider.ts"],"names":[],"mappings":"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","sourcesContent":["/*---------------------------------------------------------------------------------------------\r\n* Copyright (c) Bentley Systems, Incorporated. All rights reserved.\r\n* See LICENSE.md in the project root for license terms and full copyright notice.\r\n*--------------------------------------------------------------------------------------------*/\r\nimport { BasicUnitsProvider } from \"./BasicUnitsProvider\";\r\nimport type { UnitConversionProps, UnitProps, UnitsProvider } from \"./Interfaces\";\r\nimport { BadUnit } from \"./Unit\";\r\n\r\n/**\r\n * Options for [[createUnitsProvider]].\r\n * @beta\r\n */\r\nexport interface CreateUnitsProviderOptions {\r\n /**\r\n * A `UnitsProvider` consulted before the basic BIS units (e.g. a `SchemaUnitProvider`\r\n * for an open iModel's `SchemaContext`). When omitted, the returned provider behaves\r\n * exactly like `new BasicUnitsProvider()`.\r\n */\r\n primary?: UnitsProvider;\r\n\r\n /**\r\n * Controls which provider is consulted first and wins ties.\r\n * - `\"preferSchema\"` (default): `primary` is authoritative; bundled BIS units are fallback.\r\n * - `\"preferBundled\"`: bundled BIS units win; `primary` is consulted only for units not in\r\n * the bundled set. Use when the iModel's schema may be stale.\r\n *\r\n * Affects `findUnit`, `findUnitByName`, and `getConversion` (first-consulted wins or\r\n * falls through). `getUnitsByFamily` always merges both providers — the first-consulted\r\n * provider wins name collisions.\r\n *\r\n * Has no effect when `primary` is omitted — the returned provider is a plain `BasicUnitsProvider`.\r\n */\r\n bisUnitsPolicy?: \"preferSchema\" | \"preferBundled\";\r\n}\r\n\r\n/**\r\n * Returns a `UnitsProvider` that layers the basic BIS units under (or over) an optional\r\n * `primary` provider. Typical use: layer an iModel's schema units on top of the bundled\r\n * defaults from `@itwin/core-quantity`.\r\n *\r\n * Precedence rules:\r\n * - When `primary` is supplied and `bisUnitsPolicy` is `\"preferSchema\"` (the default): `primary` wins;\r\n * basic BIS units fill any gaps where `primary` returns an invalid unit or throws.\r\n * - When `bisUnitsPolicy` is `\"preferBundled\"`: basic BIS units win; `primary` is consulted only when the\r\n * basic provider can't answer.\r\n * - `getUnitsByFamily` always merges results from both providers, deduplicated by\r\n * `UnitProps.name` (fully-qualified). The first-consulted provider wins ties.\r\n * - When no `primary` is supplied, the returned provider is exactly `new BasicUnitsProvider()`\r\n * (no wrapper), preserving `instanceof` checks and keeping the hot path fast.\r\n *\r\n * @beta\r\n */\r\nexport function createUnitsProvider(options: CreateUnitsProviderOptions = {}): UnitsProvider {\r\n const basic = new BasicUnitsProvider();\r\n const primary = options.primary;\r\n // NOTE: returns BasicUnitsProvider directly when no primary is provided.\r\n // QuantityFormatter.resetToUseInternalUnitsProvider uses instanceof BasicUnitsProvider to detect this.\r\n // If this fast-path is ever wrapped (e.g. for telemetry), that guard must be updated.\r\n if (!primary) {\r\n return basic;\r\n }\r\n\r\n const providers = options.bisUnitsPolicy === \"preferBundled\" ? [basic, primary] : [primary, basic];\r\n return new CompositeUnitsProvider(providers);\r\n}\r\n\r\nclass CompositeUnitsProvider implements UnitsProvider {\r\n constructor(private readonly _providers: UnitsProvider[]) {}\r\n\r\n public async findUnit(label: string, schemaName?: string, phenomenon?: string, unitSystem?: string): Promise<UnitProps> {\r\n for (let i = 0; i < this._providers.length - 1; i++) {\r\n const hit = await tryFind(async () => this._providers[i].findUnit(label, schemaName, phenomenon, unitSystem));\r\n if (hit?.isValid) {\r\n return hit;\r\n }\r\n }\r\n return tryFind(async () => this._providers[this._providers.length - 1].findUnit(label, schemaName, phenomenon, unitSystem)).then((hit) => hit ?? new BadUnit());\r\n }\r\n\r\n public async findUnitByName(name: string): Promise<UnitProps> {\r\n for (let i = 0; i < this._providers.length - 1; i++) {\r\n const hit = await tryFind(async () => this._providers[i].findUnitByName(name));\r\n if (hit?.isValid) {\r\n return hit;\r\n }\r\n }\r\n return tryFind(async () => this._providers[this._providers.length - 1].findUnitByName(name)).then((hit) => hit ?? new BadUnit());\r\n }\r\n\r\n public async getUnitsByFamily(phenomenon: string): Promise<UnitProps[]> {\r\n const seen = new Set<string>();\r\n const out: UnitProps[] = [];\r\n // Query all providers in parallel; process results in declaration order to honour precedence.\r\n const results = await Promise.all(this._providers.map(async (p) => tryList(async () => p.getUnitsByFamily(phenomenon))));\r\n for (const units of results) {\r\n for (const u of units) {\r\n if (!seen.has(u.name)) {\r\n seen.add(u.name);\r\n out.push(u);\r\n }\r\n }\r\n }\r\n return out;\r\n }\r\n\r\n public async getConversion(from: UnitProps, to: UnitProps): Promise<UnitConversionProps> {\r\n for (let i = 0; i < this._providers.length - 1; i++) {\r\n try {\r\n const result = await this._providers[i].getConversion(from, to);\r\n if (!result.error) {\r\n return result;\r\n }\r\n } catch { /* fall through to next provider */ }\r\n }\r\n try {\r\n return await this._providers[this._providers.length - 1].getConversion(from, to);\r\n } catch {\r\n return { factor: 1.0, offset: 0.0, error: true };\r\n }\r\n }\r\n}\r\n\r\nasync function tryFind(fn: () => Promise<UnitProps>): Promise<UnitProps | undefined> {\r\n try { return await fn(); } catch { return undefined; }\r\n}\r\n\r\nasync function tryList(fn: () => Promise<UnitProps[]>): Promise<UnitProps[]> {\r\n try { return await fn(); } catch { return []; }\r\n}\r\n"]}
|
package/lib/cjs/Constants.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"Constants.js","sourceRoot":"","sources":["../../src/Constants.ts"],"names":[],"mappings":";AAAA;;;+FAG+F;;;AAE/F,yDAAyD;AAEzD;;GAEG;AACH,MAAa,iBAAiB;IACrB,MAAM,CAAU,UAAU,GAAG,EAAE,CAAC;IAChC,MAAM,CAAU,UAAU,GAAG,EAAE,CAAC;IAChC,MAAM,CAAU,WAAW,GAAG,EAAE,CAAC;IACjC,MAAM,CAAU,SAAS,GAAG,EAAE,CAAC;IAC/B,MAAM,CAAU,UAAU,GAAG,EAAE,CAAC;IAChC,MAAM,CAAU,WAAW,GAAG,EAAE,CAAC;IACjC,MAAM,CAAU,UAAU,GAAG,EAAE,CAAC;IAChC,MAAM,CAAU,mBAAmB,GAAG,IAAI,CAAC;IAC3C,MAAM,CAAU,mBAAmB,GAAG,IAAI,CAAC;IAC3C,MAAM,CAAU,gBAAgB,GAAG,GAAG,CAAC;IACvC,MAAM,CAAU,aAAa,GAAG,GAAG,CAAC;IACpC,MAAM,CAAU,kBAAkB,GAAG,GAAG,CAAC;IACzC,MAAM,CAAU,eAAe,GAAG,EAAE,CAAC;IACrC,MAAM,CAAU,eAAe,GAAG,EAAE,CAAC;IACrC,MAAM,CAAU,YAAY,GAAG,EAAE,CAAC;IAClC,MAAM,CAAU,YAAY,GAAG,GAAG,CAAC;IAClC,MAAM,CAAC,yBAAyB,GAAG,EAAE,CAAC;IACtC,MAAM,CAAC,0BAA0B,GAAG,EAAE,CAAC;IAE/C,2DAA2D;IACpD,MAAM,KAAK,8BAA8B;QAC9C,IAAI,iBAAiB,CAAC,yBAAyB,CAAC,MAAM,GAAG,CAAC;YACxD,OAAO,iBAAiB,CAAC,yBAAyB,CAAC;QAErD,iBAAiB,CAAC,yBAAyB,GAAG,GAAG,CAAC;QAClD,MAAM,OAAO,GAAG,CAAC,UAAU,CAAC,CAAC,cAAc,EAAE,CAAC,KAAK,CAAC,WAAW,CAAC,CAAC;QACjE,IAAI,OAAO,IAAI,OAAO,CAAC,MAAM,GAAG,CAAC;YAC/B,iBAAiB,CAAC,yBAAyB,GAAG,OAAO,CAAC,CAAC,CAAC,CAAC;QAE3D,OAAO,iBAAiB,CAAC,yBAAyB,CAAC;IACrD,CAAC;IAED,4DAA4D;IACrD,MAAM,KAAK,+BAA+B;QAC/C,IAAI,iBAAiB,CAAC,0BAA0B,CAAC,MAAM,GAAG,CAAC;YACzD,OAAO,iBAAiB,CAAC,0BAA0B,CAAC;QAEtD,iBAAiB,CAAC,0BAA0B,GAAG,GAAG,CAAC;QACnD,MAAM,OAAO,GAAG,CAAC,UAAU,CAAC,CAAC,cAAc,EAAE,CAAC,KAAK,CAAC,WAAW,CAAC,CAAC;QACjE,IAAI,OAAO,IAAI,OAAO,CAAC,MAAM,GAAG,CAAC,IAAI,OAAO,CAAC,CAAC,CAAC,KAAK,EAAE;YACpD,iBAAiB,CAAC,0BAA0B,GAAG,OAAO,CAAC,CAAC,CAAC,CAAC;QAE5D,OAAO,iBAAiB,CAAC,0BAA0B,CAAC;IACtD,CAAC;;AA5CH,8CA6CC","sourcesContent":["/*---------------------------------------------------------------------------------------------\n* Copyright (c) Bentley Systems, Incorporated. All rights reserved.\n* See LICENSE.md in the project root for license terms and full copyright notice.\n*--------------------------------------------------------------------------------------------*/\n\n/* eslint-disable @typescript-eslint/naming-convention */\n\n/** Constants used internally for both formatting and parsing.\n * @internal\n */\nexport class QuantityConstants {\n public static readonly CHAR_COMMA = 44;\n public static readonly CHAR_SPACE = 32;\n public static readonly CHAR_NUMBER = 35;\n public static readonly CHAR_PLUS = 43;\n public static readonly CHAR_MINUS = 45;\n public static readonly CHAR_PERIOD = 46;\n public static readonly CHAR_SLASH = 47;\n public static readonly CHAR_DIVISION_SLASH = 8725;\n public static readonly CHAR_FRACTION_SLASH = 8260;\n public static readonly CHAR_ONE_QUARTER = 188;\n public static readonly CHAR_ONE_HALF = 189;\n public static readonly CHAR_THREE_QUARTER = 190;\n public static readonly CHAR_DIGIT_ZERO = 48;\n public static readonly CHAR_DIGIT_NINE = 57;\n public static readonly CHAR_UPPER_E = 69;\n public static readonly CHAR_LOWER_E = 101;\n private static _LOCALE_DECIMAL_SEPARATOR = \"\";\n private static _LOCALE_THOUSAND_SEPARATOR = \"\";\n\n /** Return the decimal separator for the current locale. */\n public static get LocaleSpecificDecimalSeparator(): string {\n if (QuantityConstants._LOCALE_DECIMAL_SEPARATOR.length > 0)\n return QuantityConstants._LOCALE_DECIMAL_SEPARATOR;\n\n QuantityConstants._LOCALE_DECIMAL_SEPARATOR = \".\";\n const matches = (12345.6789).toLocaleString().match(/345(.*)67/);\n if (matches && matches.length > 1)\n QuantityConstants._LOCALE_DECIMAL_SEPARATOR = matches[1];\n\n return QuantityConstants._LOCALE_DECIMAL_SEPARATOR;\n }\n\n /** Return the thousand separator for the current locale. */\n public static get LocaleSpecificThousandSeparator(): string {\n if (QuantityConstants._LOCALE_THOUSAND_SEPARATOR.length > 0)\n return QuantityConstants._LOCALE_THOUSAND_SEPARATOR;\n\n QuantityConstants._LOCALE_THOUSAND_SEPARATOR = \",\";\n const matches = (12345.6789).toLocaleString().match(/12(.*)345/);\n if (matches && matches.length > 1 && matches[1] !== \"\")\n QuantityConstants._LOCALE_THOUSAND_SEPARATOR = matches[1];\n\n return QuantityConstants._LOCALE_THOUSAND_SEPARATOR;\n }\n}\n"]}
|
|
1
|
+
{"version":3,"file":"Constants.js","sourceRoot":"","sources":["../../src/Constants.ts"],"names":[],"mappings":";AAAA;;;+FAG+F;;;AAE/F,yDAAyD;AAEzD;;GAEG;AACH,MAAa,iBAAiB;IACrB,MAAM,CAAU,UAAU,GAAG,EAAE,CAAC;IAChC,MAAM,CAAU,UAAU,GAAG,EAAE,CAAC;IAChC,MAAM,CAAU,WAAW,GAAG,EAAE,CAAC;IACjC,MAAM,CAAU,SAAS,GAAG,EAAE,CAAC;IAC/B,MAAM,CAAU,UAAU,GAAG,EAAE,CAAC;IAChC,MAAM,CAAU,WAAW,GAAG,EAAE,CAAC;IACjC,MAAM,CAAU,UAAU,GAAG,EAAE,CAAC;IAChC,MAAM,CAAU,mBAAmB,GAAG,IAAI,CAAC;IAC3C,MAAM,CAAU,mBAAmB,GAAG,IAAI,CAAC;IAC3C,MAAM,CAAU,gBAAgB,GAAG,GAAG,CAAC;IACvC,MAAM,CAAU,aAAa,GAAG,GAAG,CAAC;IACpC,MAAM,CAAU,kBAAkB,GAAG,GAAG,CAAC;IACzC,MAAM,CAAU,eAAe,GAAG,EAAE,CAAC;IACrC,MAAM,CAAU,eAAe,GAAG,EAAE,CAAC;IACrC,MAAM,CAAU,YAAY,GAAG,EAAE,CAAC;IAClC,MAAM,CAAU,YAAY,GAAG,GAAG,CAAC;IAClC,MAAM,CAAC,yBAAyB,GAAG,EAAE,CAAC;IACtC,MAAM,CAAC,0BAA0B,GAAG,EAAE,CAAC;IAE/C,2DAA2D;IACpD,MAAM,KAAK,8BAA8B;QAC9C,IAAI,iBAAiB,CAAC,yBAAyB,CAAC,MAAM,GAAG,CAAC;YACxD,OAAO,iBAAiB,CAAC,yBAAyB,CAAC;QAErD,iBAAiB,CAAC,yBAAyB,GAAG,GAAG,CAAC;QAClD,MAAM,OAAO,GAAG,CAAC,UAAU,CAAC,CAAC,cAAc,EAAE,CAAC,KAAK,CAAC,WAAW,CAAC,CAAC;QACjE,IAAI,OAAO,IAAI,OAAO,CAAC,MAAM,GAAG,CAAC;YAC/B,iBAAiB,CAAC,yBAAyB,GAAG,OAAO,CAAC,CAAC,CAAC,CAAC;QAE3D,OAAO,iBAAiB,CAAC,yBAAyB,CAAC;IACrD,CAAC;IAED,4DAA4D;IACrD,MAAM,KAAK,+BAA+B;QAC/C,IAAI,iBAAiB,CAAC,0BAA0B,CAAC,MAAM,GAAG,CAAC;YACzD,OAAO,iBAAiB,CAAC,0BAA0B,CAAC;QAEtD,iBAAiB,CAAC,0BAA0B,GAAG,GAAG,CAAC;QACnD,MAAM,OAAO,GAAG,CAAC,UAAU,CAAC,CAAC,cAAc,EAAE,CAAC,KAAK,CAAC,WAAW,CAAC,CAAC;QACjE,IAAI,OAAO,IAAI,OAAO,CAAC,MAAM,GAAG,CAAC,IAAI,OAAO,CAAC,CAAC,CAAC,KAAK,EAAE;YACpD,iBAAiB,CAAC,0BAA0B,GAAG,OAAO,CAAC,CAAC,CAAC,CAAC;QAE5D,OAAO,iBAAiB,CAAC,0BAA0B,CAAC;IACtD,CAAC;;AA5CH,8CA6CC","sourcesContent":["/*---------------------------------------------------------------------------------------------\r\n* Copyright (c) Bentley Systems, Incorporated. All rights reserved.\r\n* See LICENSE.md in the project root for license terms and full copyright notice.\r\n*--------------------------------------------------------------------------------------------*/\r\n\r\n/* eslint-disable @typescript-eslint/naming-convention */\r\n\r\n/** Constants used internally for both formatting and parsing.\r\n * @internal\r\n */\r\nexport class QuantityConstants {\r\n public static readonly CHAR_COMMA = 44;\r\n public static readonly CHAR_SPACE = 32;\r\n public static readonly CHAR_NUMBER = 35;\r\n public static readonly CHAR_PLUS = 43;\r\n public static readonly CHAR_MINUS = 45;\r\n public static readonly CHAR_PERIOD = 46;\r\n public static readonly CHAR_SLASH = 47;\r\n public static readonly CHAR_DIVISION_SLASH = 8725;\r\n public static readonly CHAR_FRACTION_SLASH = 8260;\r\n public static readonly CHAR_ONE_QUARTER = 188;\r\n public static readonly CHAR_ONE_HALF = 189;\r\n public static readonly CHAR_THREE_QUARTER = 190;\r\n public static readonly CHAR_DIGIT_ZERO = 48;\r\n public static readonly CHAR_DIGIT_NINE = 57;\r\n public static readonly CHAR_UPPER_E = 69;\r\n public static readonly CHAR_LOWER_E = 101;\r\n private static _LOCALE_DECIMAL_SEPARATOR = \"\";\r\n private static _LOCALE_THOUSAND_SEPARATOR = \"\";\r\n\r\n /** Return the decimal separator for the current locale. */\r\n public static get LocaleSpecificDecimalSeparator(): string {\r\n if (QuantityConstants._LOCALE_DECIMAL_SEPARATOR.length > 0)\r\n return QuantityConstants._LOCALE_DECIMAL_SEPARATOR;\r\n\r\n QuantityConstants._LOCALE_DECIMAL_SEPARATOR = \".\";\r\n const matches = (12345.6789).toLocaleString().match(/345(.*)67/);\r\n if (matches && matches.length > 1)\r\n QuantityConstants._LOCALE_DECIMAL_SEPARATOR = matches[1];\r\n\r\n return QuantityConstants._LOCALE_DECIMAL_SEPARATOR;\r\n }\r\n\r\n /** Return the thousand separator for the current locale. */\r\n public static get LocaleSpecificThousandSeparator(): string {\r\n if (QuantityConstants._LOCALE_THOUSAND_SEPARATOR.length > 0)\r\n return QuantityConstants._LOCALE_THOUSAND_SEPARATOR;\r\n\r\n QuantityConstants._LOCALE_THOUSAND_SEPARATOR = \",\";\r\n const matches = (12345.6789).toLocaleString().match(/12(.*)345/);\r\n if (matches && matches.length > 1 && matches[1] !== \"\")\r\n QuantityConstants._LOCALE_THOUSAND_SEPARATOR = matches[1];\r\n\r\n return QuantityConstants._LOCALE_THOUSAND_SEPARATOR;\r\n }\r\n}\r\n"]}
|
package/lib/cjs/Exception.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"Exception.js","sourceRoot":"","sources":["../../src/Exception.ts"],"names":[],"mappings":";AAAA;;;+FAG+F;AAC/F;;GAEG;;;AAEH,sDAA2D;AAE3D;;;GAGG;AACH,IAAY,cAaX;AAbD,WAAY,cAAc;IACxB,qFAA4B,CAAA;IAC5B,yDAAW,CAAA;IACX,qEAAqC,CAAA;IACrC,2FAAgD,CAAA;IAChD,qGAAqD,CAAA;IACrD,mGAAoD,CAAA;IACpD,2GAAwD,CAAA;IACxD,qEAAqC,CAAA;IACrC,uHAA8D,CAAA;IAC9D,6EAAyC,CAAA;IACzC,6FAAiD,CAAA;IACjD,yEAAwC,CAAA;AAC1C,CAAC,EAbW,cAAc,8BAAd,cAAc,QAazB;AAED;;GAEG;AACH,MAAa,aAAc,SAAQ,2BAAY;IACD;IAA5C,YAA4C,WAAmB,EAAE,OAAgB;QAC/E,KAAK,CAAC,WAAW,EAAE,OAAO,CAAC,CAAC;QADc,gBAAW,GAAX,WAAW,CAAQ;QAE7D,IAAA,qBAAM,EAAC,WAAW,KAAK,cAAc,CAAC,OAAO,EAAE,OAAO,CAAC,CAAC;IAC1D,CAAC;CACF;AALD,sCAKC","sourcesContent":["/*---------------------------------------------------------------------------------------------\n* Copyright (c) Bentley Systems, Incorporated. All rights reserved.\n* See LICENSE.md in the project root for license terms and full copyright notice.\n*--------------------------------------------------------------------------------------------*/\n/** @packageDocumentation\n * @module Quantity\n */\n\nimport { assert, BentleyError } from \"@itwin/core-bentley\";\n\n/**\n * Status codes used during Quantity parsing and formatting processing.\n * @beta\n */\nexport enum QuantityStatus {\n QUANTITY_ERROR_BASE = 0x88DF,\n Success = 0,\n InvalidJson = QUANTITY_ERROR_BASE + 1,\n InvalidCompositeFormat = QUANTITY_ERROR_BASE + 2,\n UnableToGenerateParseTokens = QUANTITY_ERROR_BASE + 3,\n NoValueOrUnitFoundInString = QUANTITY_ERROR_BASE + 4,\n UnitLabelSuppliedButNotMatched = QUANTITY_ERROR_BASE + 5,\n UnknownUnit = QUANTITY_ERROR_BASE + 6,\n UnableToConvertParseTokensToQuantity = QUANTITY_ERROR_BASE + 7,\n UnsupportedUnit = QUANTITY_ERROR_BASE + 8,\n MissingRequiredProperty = QUANTITY_ERROR_BASE + 9,\n InvertingZero = QUANTITY_ERROR_BASE + 10,\n}\n\n/** The error type thrown by this module. See [[QuantityStatus]] for `errorNumber` values.\n * @beta\n */\nexport class QuantityError extends BentleyError {\n public constructor(public override readonly errorNumber: number, message?: string) {\n super(errorNumber, message);\n assert(errorNumber !== QuantityStatus.Success, message);\n }\n}\n"]}
|
|
1
|
+
{"version":3,"file":"Exception.js","sourceRoot":"","sources":["../../src/Exception.ts"],"names":[],"mappings":";AAAA;;;+FAG+F;AAC/F;;GAEG;;;AAEH,sDAA2D;AAE3D;;;GAGG;AACH,IAAY,cAaX;AAbD,WAAY,cAAc;IACxB,qFAA4B,CAAA;IAC5B,yDAAW,CAAA;IACX,qEAAqC,CAAA;IACrC,2FAAgD,CAAA;IAChD,qGAAqD,CAAA;IACrD,mGAAoD,CAAA;IACpD,2GAAwD,CAAA;IACxD,qEAAqC,CAAA;IACrC,uHAA8D,CAAA;IAC9D,6EAAyC,CAAA;IACzC,6FAAiD,CAAA;IACjD,yEAAwC,CAAA;AAC1C,CAAC,EAbW,cAAc,8BAAd,cAAc,QAazB;AAED;;GAEG;AACH,MAAa,aAAc,SAAQ,2BAAY;IACD;IAA5C,YAA4C,WAAmB,EAAE,OAAgB;QAC/E,KAAK,CAAC,WAAW,EAAE,OAAO,CAAC,CAAC;QADc,gBAAW,GAAX,WAAW,CAAQ;QAE7D,IAAA,qBAAM,EAAC,WAAW,KAAK,cAAc,CAAC,OAAO,EAAE,OAAO,CAAC,CAAC;IAC1D,CAAC;CACF;AALD,sCAKC","sourcesContent":["/*---------------------------------------------------------------------------------------------\r\n* Copyright (c) Bentley Systems, Incorporated. All rights reserved.\r\n* See LICENSE.md in the project root for license terms and full copyright notice.\r\n*--------------------------------------------------------------------------------------------*/\r\n/** @packageDocumentation\r\n * @module Quantity\r\n */\r\n\r\nimport { assert, BentleyError } from \"@itwin/core-bentley\";\r\n\r\n/**\r\n * Status codes used during Quantity parsing and formatting processing.\r\n * @beta\r\n */\r\nexport enum QuantityStatus {\r\n QUANTITY_ERROR_BASE = 0x88DF,\r\n Success = 0,\r\n InvalidJson = QUANTITY_ERROR_BASE + 1,\r\n InvalidCompositeFormat = QUANTITY_ERROR_BASE + 2,\r\n UnableToGenerateParseTokens = QUANTITY_ERROR_BASE + 3,\r\n NoValueOrUnitFoundInString = QUANTITY_ERROR_BASE + 4,\r\n UnitLabelSuppliedButNotMatched = QUANTITY_ERROR_BASE + 5,\r\n UnknownUnit = QUANTITY_ERROR_BASE + 6,\r\n UnableToConvertParseTokensToQuantity = QUANTITY_ERROR_BASE + 7,\r\n UnsupportedUnit = QUANTITY_ERROR_BASE + 8,\r\n MissingRequiredProperty = QUANTITY_ERROR_BASE + 9,\r\n InvertingZero = QUANTITY_ERROR_BASE + 10,\r\n}\r\n\r\n/** The error type thrown by this module. See [[QuantityStatus]] for `errorNumber` values.\r\n * @beta\r\n */\r\nexport class QuantityError extends BentleyError {\r\n public constructor(public override readonly errorNumber: number, message?: string) {\r\n super(errorNumber, message);\r\n assert(errorNumber !== QuantityStatus.Success, message);\r\n }\r\n}\r\n"]}
|
|
@@ -9,22 +9,20 @@ import type { UnitSystemKey } from "./Interfaces";
|
|
|
9
9
|
* @internal
|
|
10
10
|
*/
|
|
11
11
|
export interface FormatSpecHandleArgs extends FormattingSpecArgs {
|
|
12
|
-
/** The provider that supplies spec lookups
|
|
12
|
+
/** The provider that supplies current formatting spec lookups. */
|
|
13
13
|
provider: FormattingSpecProvider;
|
|
14
14
|
}
|
|
15
|
-
/** A
|
|
16
|
-
*
|
|
15
|
+
/** A handle to formatting and parsing specs for a specific KoQ and persistence unit.
|
|
16
|
+
* Reads the current specs from the provider on access. Use [[QuantityFormatter.getFormatSpecHandle]]
|
|
17
17
|
* to create instances.
|
|
18
18
|
*
|
|
19
19
|
* When formatting is not yet ready, [[format]] returns a `value.toString()` fallback.
|
|
20
|
-
*
|
|
20
|
+
* Dispose the handle when it is no longer needed to invalidate it.
|
|
21
21
|
*
|
|
22
22
|
* @beta
|
|
23
23
|
*/
|
|
24
24
|
export declare class FormatSpecHandle implements Disposable {
|
|
25
|
-
private
|
|
26
|
-
private _parserSpec;
|
|
27
|
-
private _removeListener;
|
|
25
|
+
private _disposed;
|
|
28
26
|
private readonly _provider;
|
|
29
27
|
private readonly _koqName;
|
|
30
28
|
private readonly _persistenceUnit;
|
|
@@ -47,10 +45,11 @@ export declare class FormatSpecHandle implements Disposable {
|
|
|
47
45
|
* @returns The formatted string.
|
|
48
46
|
*/
|
|
49
47
|
format(value: number): string;
|
|
50
|
-
/**
|
|
51
|
-
* Idempotent and safe to call
|
|
48
|
+
/** Invalidate this handle.
|
|
49
|
+
* Idempotent and safe to call multiple times.
|
|
50
|
+
* No additional teardown is required because the handle owns no external resources.
|
|
52
51
|
*/
|
|
53
52
|
[Symbol.dispose](): void;
|
|
54
|
-
private
|
|
53
|
+
private _getEntry;
|
|
55
54
|
}
|
|
56
55
|
//# sourceMappingURL=FormatSpecHandle.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"FormatSpecHandle.d.ts","sourceRoot":"","sources":["../../src/FormatSpecHandle.ts"],"names":[],"mappings":"AAKA;;GAEG;AAEH,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,2BAA2B,CAAC;AAC/D,OAAO,KAAK,EAAE,kBAAkB,EAAuB,sBAAsB,EAAE,MAAM,wBAAwB,CAAC;AAC9G,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,cAAc,CAAC;AAC/C,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,cAAc,CAAC;AAElD;;GAEG;AACH,MAAM,WAAW,oBAAqB,SAAQ,kBAAkB;IAC9D,
|
|
1
|
+
{"version":3,"file":"FormatSpecHandle.d.ts","sourceRoot":"","sources":["../../src/FormatSpecHandle.ts"],"names":[],"mappings":"AAKA;;GAEG;AAEH,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,2BAA2B,CAAC;AAC/D,OAAO,KAAK,EAAE,kBAAkB,EAAuB,sBAAsB,EAAE,MAAM,wBAAwB,CAAC;AAC9G,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,cAAc,CAAC;AAC/C,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,cAAc,CAAC;AAElD;;GAEG;AACH,MAAM,WAAW,oBAAqB,SAAQ,kBAAkB;IAC9D,kEAAkE;IAClE,QAAQ,EAAE,sBAAsB,CAAC;CAClC;AAED;;;;;;;;GAQG;AACH,qBAAa,gBAAiB,YAAW,UAAU;IACjD,OAAO,CAAC,SAAS,CAAS;IAC1B,OAAO,CAAC,QAAQ,CAAC,SAAS,CAAyB;IACnD,OAAO,CAAC,QAAQ,CAAC,QAAQ,CAAS;IAClC,OAAO,CAAC,QAAQ,CAAC,gBAAgB,CAAS;IAC1C,OAAO,CAAC,QAAQ,CAAC,OAAO,CAA4B;IAEpD,gBAAgB;gBACJ,IAAI,EAAE,oBAAoB;IAOtC,4CAA4C;IAC5C,IAAW,OAAO,IAAI,MAAM,CAA0B;IAEtD,oDAAoD;IACpD,IAAW,eAAe,IAAI,MAAM,CAAkC;IAEtE,sFAAsF;IACtF,IAAW,MAAM,IAAI,aAAa,GAAG,SAAS,CAAyB;IAEvE,iEAAiE;IACjE,IAAW,aAAa,IAAI,aAAa,GAAG,SAAS,CAA4C;IAEjG,8DAA8D;IAC9D,IAAW,UAAU,IAAI,UAAU,GAAG,SAAS,CAAyC;IAExF;;;;OAIG;IACI,MAAM,CAAC,KAAK,EAAE,MAAM,GAAG,MAAM;IAOpC;;;OAGG;IACI,CAAC,MAAM,CAAC,OAAO,CAAC,IAAI,IAAI;IAI/B,OAAO,CAAC,SAAS;CAUlB"}
|
|
@@ -5,19 +5,17 @@
|
|
|
5
5
|
*--------------------------------------------------------------------------------------------*/
|
|
6
6
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
7
7
|
exports.FormatSpecHandle = void 0;
|
|
8
|
-
/** A
|
|
9
|
-
*
|
|
8
|
+
/** A handle to formatting and parsing specs for a specific KoQ and persistence unit.
|
|
9
|
+
* Reads the current specs from the provider on access. Use [[QuantityFormatter.getFormatSpecHandle]]
|
|
10
10
|
* to create instances.
|
|
11
11
|
*
|
|
12
12
|
* When formatting is not yet ready, [[format]] returns a `value.toString()` fallback.
|
|
13
|
-
*
|
|
13
|
+
* Dispose the handle when it is no longer needed to invalidate it.
|
|
14
14
|
*
|
|
15
15
|
* @beta
|
|
16
16
|
*/
|
|
17
17
|
class FormatSpecHandle {
|
|
18
|
-
|
|
19
|
-
_parserSpec;
|
|
20
|
-
_removeListener;
|
|
18
|
+
_disposed = false;
|
|
21
19
|
_provider;
|
|
22
20
|
_koqName;
|
|
23
21
|
_persistenceUnit;
|
|
@@ -28,10 +26,6 @@ class FormatSpecHandle {
|
|
|
28
26
|
this._koqName = args.name;
|
|
29
27
|
this._persistenceUnit = args.persistenceUnitName;
|
|
30
28
|
this._system = args.system;
|
|
31
|
-
this._removeListener = args.provider.onFormattingReady.addListener(() => {
|
|
32
|
-
this._refresh();
|
|
33
|
-
});
|
|
34
|
-
this._refresh();
|
|
35
29
|
}
|
|
36
30
|
/** The KoQ name this handle is keyed to. */
|
|
37
31
|
get koqName() { return this._koqName; }
|
|
@@ -40,47 +34,35 @@ class FormatSpecHandle {
|
|
|
40
34
|
/** The unit system this handle is pinned to, or `undefined` for the active system. */
|
|
41
35
|
get system() { return this._system; }
|
|
42
36
|
/** The current FormatterSpec, or undefined if not yet loaded. */
|
|
43
|
-
get formatterSpec() { return this.
|
|
37
|
+
get formatterSpec() { return this._getEntry()?.formatterSpec; }
|
|
44
38
|
/** The current ParserSpec, or undefined if not yet loaded. */
|
|
45
|
-
get parserSpec() { return this.
|
|
39
|
+
get parserSpec() { return this._getEntry()?.parserSpec; }
|
|
46
40
|
/** Format a quantity value using the current spec.
|
|
47
41
|
* If the formatter is not yet ready, returns `value.toString()` as a fallback.
|
|
48
42
|
* @param value - The numeric value to format.
|
|
49
43
|
* @returns The formatted string.
|
|
50
44
|
*/
|
|
51
45
|
format(value) {
|
|
52
|
-
|
|
46
|
+
const formatterSpec = this.formatterSpec;
|
|
47
|
+
if (!formatterSpec)
|
|
53
48
|
return value.toString();
|
|
54
|
-
return this._provider.formatQuantity(value,
|
|
49
|
+
return this._provider.formatQuantity(value, formatterSpec);
|
|
55
50
|
}
|
|
56
|
-
/**
|
|
57
|
-
* Idempotent and safe to call
|
|
51
|
+
/** Invalidate this handle.
|
|
52
|
+
* Idempotent and safe to call multiple times.
|
|
53
|
+
* No additional teardown is required because the handle owns no external resources.
|
|
58
54
|
*/
|
|
59
55
|
[Symbol.dispose]() {
|
|
60
|
-
|
|
61
|
-
this._removeListener();
|
|
62
|
-
this._removeListener = undefined;
|
|
63
|
-
}
|
|
64
|
-
this._formatterSpec = undefined;
|
|
65
|
-
this._parserSpec = undefined;
|
|
56
|
+
this._disposed = true;
|
|
66
57
|
}
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
const entry = this._provider.getSpecsByNameAndUnit({
|
|
58
|
+
_getEntry() {
|
|
59
|
+
if (this._disposed)
|
|
60
|
+
return undefined;
|
|
61
|
+
return this._provider.getSpecsByNameAndUnit({
|
|
72
62
|
name: this._koqName,
|
|
73
63
|
persistenceUnitName: this._persistenceUnit,
|
|
74
64
|
system: this._system,
|
|
75
65
|
});
|
|
76
|
-
if (entry) {
|
|
77
|
-
this._formatterSpec = entry.formatterSpec;
|
|
78
|
-
this._parserSpec = entry.parserSpec;
|
|
79
|
-
}
|
|
80
|
-
else {
|
|
81
|
-
this._formatterSpec = undefined;
|
|
82
|
-
this._parserSpec = undefined;
|
|
83
|
-
}
|
|
84
66
|
}
|
|
85
67
|
}
|
|
86
68
|
exports.FormatSpecHandle = FormatSpecHandle;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"FormatSpecHandle.js","sourceRoot":"","sources":["../../src/FormatSpecHandle.ts"],"names":[],"mappings":";AAAA;;;+FAG+F;;;AAmB/F;;;;;;;;GAQG;AACH,MAAa,gBAAgB;IACnB,
|
|
1
|
+
{"version":3,"file":"FormatSpecHandle.js","sourceRoot":"","sources":["../../src/FormatSpecHandle.ts"],"names":[],"mappings":";AAAA;;;+FAG+F;;;AAmB/F;;;;;;;;GAQG;AACH,MAAa,gBAAgB;IACnB,SAAS,GAAG,KAAK,CAAC;IACT,SAAS,CAAyB;IAClC,QAAQ,CAAS;IACjB,gBAAgB,CAAS;IACzB,OAAO,CAA4B;IAEpD,gBAAgB;IAChB,YAAY,IAA0B;QACpC,IAAI,CAAC,SAAS,GAAG,IAAI,CAAC,QAAQ,CAAC;QAC/B,IAAI,CAAC,QAAQ,GAAG,IAAI,CAAC,IAAI,CAAC;QAC1B,IAAI,CAAC,gBAAgB,GAAG,IAAI,CAAC,mBAAmB,CAAC;QACjD,IAAI,CAAC,OAAO,GAAG,IAAI,CAAC,MAAM,CAAC;IAC7B,CAAC;IAED,4CAA4C;IAC5C,IAAW,OAAO,KAAa,OAAO,IAAI,CAAC,QAAQ,CAAC,CAAC,CAAC;IAEtD,oDAAoD;IACpD,IAAW,eAAe,KAAa,OAAO,IAAI,CAAC,gBAAgB,CAAC,CAAC,CAAC;IAEtE,sFAAsF;IACtF,IAAW,MAAM,KAAgC,OAAO,IAAI,CAAC,OAAO,CAAC,CAAC,CAAC;IAEvE,iEAAiE;IACjE,IAAW,aAAa,KAAgC,OAAO,IAAI,CAAC,SAAS,EAAE,EAAE,aAAa,CAAC,CAAC,CAAC;IAEjG,8DAA8D;IAC9D,IAAW,UAAU,KAA6B,OAAO,IAAI,CAAC,SAAS,EAAE,EAAE,UAAU,CAAC,CAAC,CAAC;IAExF;;;;OAIG;IACI,MAAM,CAAC,KAAa;QACzB,MAAM,aAAa,GAAG,IAAI,CAAC,aAAa,CAAC;QACzC,IAAI,CAAC,aAAa;YAChB,OAAO,KAAK,CAAC,QAAQ,EAAE,CAAC;QAC1B,OAAO,IAAI,CAAC,SAAS,CAAC,cAAc,CAAC,KAAK,EAAE,aAAa,CAAC,CAAC;IAC7D,CAAC;IAED;;;OAGG;IACI,CAAC,MAAM,CAAC,OAAO,CAAC;QACrB,IAAI,CAAC,SAAS,GAAG,IAAI,CAAC;IACxB,CAAC;IAEO,SAAS;QACf,IAAI,IAAI,CAAC,SAAS;YAChB,OAAO,SAAS,CAAC;QAEnB,OAAO,IAAI,CAAC,SAAS,CAAC,qBAAqB,CAAC;YAC1C,IAAI,EAAE,IAAI,CAAC,QAAQ;YACnB,mBAAmB,EAAE,IAAI,CAAC,gBAAgB;YAC1C,MAAM,EAAE,IAAI,CAAC,OAAO;SACrB,CAAC,CAAC;IACL,CAAC;CACF;AA5DD,4CA4DC","sourcesContent":["/*---------------------------------------------------------------------------------------------\r\n* Copyright (c) Bentley Systems, Incorporated. All rights reserved.\r\n* See LICENSE.md in the project root for license terms and full copyright notice.\r\n*--------------------------------------------------------------------------------------------*/\r\n\r\n/** @packageDocumentation\r\n * @module Quantity\r\n */\r\n\r\nimport type { FormatterSpec } from \"./Formatter/FormatterSpec\";\r\nimport type { FormattingSpecArgs, FormattingSpecEntry, FormattingSpecProvider } from \"./Formatter/Interfaces\";\r\nimport type { ParserSpec } from \"./ParserSpec\";\r\nimport type { UnitSystemKey } from \"./Interfaces\";\r\n\r\n/** Arguments for constructing a [[FormatSpecHandle]].\r\n * @internal\r\n */\r\nexport interface FormatSpecHandleArgs extends FormattingSpecArgs {\r\n /** The provider that supplies current formatting spec lookups. */\r\n provider: FormattingSpecProvider;\r\n}\r\n\r\n/** A handle to formatting and parsing specs for a specific KoQ and persistence unit.\r\n * Reads the current specs from the provider on access. Use [[QuantityFormatter.getFormatSpecHandle]]\r\n * to create instances.\r\n *\r\n * When formatting is not yet ready, [[format]] returns a `value.toString()` fallback.\r\n * Dispose the handle when it is no longer needed to invalidate it.\r\n *\r\n * @beta\r\n */\r\nexport class FormatSpecHandle implements Disposable {\r\n private _disposed = false;\r\n private readonly _provider: FormattingSpecProvider;\r\n private readonly _koqName: string;\r\n private readonly _persistenceUnit: string;\r\n private readonly _system: UnitSystemKey | undefined;\r\n\r\n /** @internal */\r\n constructor(args: FormatSpecHandleArgs) {\r\n this._provider = args.provider;\r\n this._koqName = args.name;\r\n this._persistenceUnit = args.persistenceUnitName;\r\n this._system = args.system;\r\n }\r\n\r\n /** The KoQ name this handle is keyed to. */\r\n public get koqName(): string { return this._koqName; }\r\n\r\n /** The persistence unit this handle is keyed to. */\r\n public get persistenceUnit(): string { return this._persistenceUnit; }\r\n\r\n /** The unit system this handle is pinned to, or `undefined` for the active system. */\r\n public get system(): UnitSystemKey | undefined { return this._system; }\r\n\r\n /** The current FormatterSpec, or undefined if not yet loaded. */\r\n public get formatterSpec(): FormatterSpec | undefined { return this._getEntry()?.formatterSpec; }\r\n\r\n /** The current ParserSpec, or undefined if not yet loaded. */\r\n public get parserSpec(): ParserSpec | undefined { return this._getEntry()?.parserSpec; }\r\n\r\n /** Format a quantity value using the current spec.\r\n * If the formatter is not yet ready, returns `value.toString()` as a fallback.\r\n * @param value - The numeric value to format.\r\n * @returns The formatted string.\r\n */\r\n public format(value: number): string {\r\n const formatterSpec = this.formatterSpec;\r\n if (!formatterSpec)\r\n return value.toString();\r\n return this._provider.formatQuantity(value, formatterSpec);\r\n }\r\n\r\n /** Invalidate this handle.\r\n * Idempotent and safe to call multiple times.\r\n * No additional teardown is required because the handle owns no external resources.\r\n */\r\n public [Symbol.dispose](): void {\r\n this._disposed = true;\r\n }\r\n\r\n private _getEntry(): FormattingSpecEntry | undefined {\r\n if (this._disposed)\r\n return undefined;\r\n\r\n return this._provider.getSpecsByNameAndUnit({\r\n name: this._koqName,\r\n persistenceUnitName: this._persistenceUnit,\r\n system: this._system,\r\n });\r\n }\r\n}\r\n"]}
|