@ifc-lite/export 2.9.3 → 3.0.0
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/dist/csv-cell.d.ts +101 -0
- package/dist/csv-cell.d.ts.map +1 -0
- package/dist/csv-cell.js +90 -0
- package/dist/csv-cell.js.map +1 -0
- package/dist/demesh-session.d.ts.map +1 -1
- package/dist/demesh-session.js +2 -1
- package/dist/demesh-session.js.map +1 -1
- package/dist/effective-index.js +1 -1
- package/dist/index.d.ts +1 -0
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +9 -0
- package/dist/index.js.map +1 -1
- package/dist/lod1-generator.d.ts +0 -2
- package/dist/lod1-generator.d.ts.map +1 -1
- package/dist/lod1-generator.js +1 -1
- package/dist/lod1-generator.js.map +1 -1
- package/dist/merged-exporter.d.ts +3 -2
- package/dist/merged-exporter.d.ts.map +1 -1
- package/dist/merged-exporter.js +32 -44
- package/dist/merged-exporter.js.map +1 -1
- package/dist/parquet-exporter.js +2 -0
- package/dist/parquet-exporter.js.map +1 -1
- package/dist/reference-collector.d.ts +40 -17
- package/dist/reference-collector.d.ts.map +1 -1
- package/dist/reference-collector.js +89 -19
- package/dist/reference-collector.js.map +1 -1
- package/dist/schema-converter.d.ts.map +1 -1
- package/dist/schema-converter.js +27 -1
- package/dist/schema-converter.js.map +1 -1
- package/dist/source-ref-bounds.d.ts +16 -1
- package/dist/source-ref-bounds.d.ts.map +1 -1
- package/dist/source-ref-bounds.js +85 -0
- package/dist/source-ref-bounds.js.map +1 -1
- package/dist/step-attribute-mutations.d.ts +91 -0
- package/dist/step-attribute-mutations.d.ts.map +1 -0
- package/dist/step-attribute-mutations.js +302 -0
- package/dist/step-attribute-mutations.js.map +1 -0
- package/dist/step-collection.d.ts +55 -0
- package/dist/step-collection.d.ts.map +1 -0
- package/dist/step-collection.js +125 -0
- package/dist/step-collection.js.map +1 -0
- package/dist/step-export-contexts.d.ts +63 -0
- package/dist/step-export-contexts.d.ts.map +1 -0
- package/dist/step-export-contexts.js +51 -0
- package/dist/step-export-contexts.js.map +1 -0
- package/dist/step-export-types.d.ts +262 -0
- package/dist/step-export-types.d.ts.map +1 -0
- package/dist/step-export-types.js +22 -0
- package/dist/step-export-types.js.map +1 -0
- package/dist/step-exporter.d.ts +45 -398
- package/dist/step-exporter.d.ts.map +1 -1
- package/dist/step-exporter.js +145 -2033
- package/dist/step-exporter.js.map +1 -1
- package/dist/step-geometry-types.d.ts +19 -0
- package/dist/step-geometry-types.d.ts.map +1 -0
- package/dist/step-geometry-types.js +57 -0
- package/dist/step-geometry-types.js.map +1 -0
- package/dist/step-georeferencing.d.ts +58 -0
- package/dist/step-georeferencing.d.ts.map +1 -0
- package/dist/step-georeferencing.js +339 -0
- package/dist/step-georeferencing.js.map +1 -0
- package/dist/step-header.d.ts +43 -0
- package/dist/step-header.d.ts.map +1 -0
- package/dist/step-header.js +70 -0
- package/dist/step-header.js.map +1 -0
- package/dist/step-omission-predicates.d.ts +51 -0
- package/dist/step-omission-predicates.d.ts.map +1 -0
- package/dist/step-omission-predicates.js +268 -0
- package/dist/step-omission-predicates.js.map +1 -0
- package/dist/step-overlay-entities.d.ts +64 -0
- package/dist/step-overlay-entities.d.ts.map +1 -0
- package/dist/step-overlay-entities.js +119 -0
- package/dist/step-overlay-entities.js.map +1 -0
- package/dist/step-pass-builder.d.ts +44 -0
- package/dist/step-pass-builder.d.ts.map +1 -0
- package/dist/step-pass-builder.js +249 -0
- package/dist/step-pass-builder.js.map +1 -0
- package/dist/step-property-sets.d.ts +198 -0
- package/dist/step-property-sets.d.ts.map +1 -0
- package/dist/step-property-sets.js +842 -0
- package/dist/step-property-sets.js.map +1 -0
- package/dist/step-serialization.d.ts +16 -1
- package/dist/step-serialization.d.ts.map +1 -1
- package/dist/step-serialization.js +50 -3
- package/dist/step-serialization.js.map +1 -1
- package/dist/step-source-iteration.d.ts +95 -0
- package/dist/step-source-iteration.d.ts.map +1 -0
- package/dist/step-source-iteration.js +178 -0
- package/dist/step-source-iteration.js.map +1 -0
- package/package.json +7 -7
|
@@ -0,0 +1,249 @@
|
|
|
1
|
+
/* This Source Code Form is subject to the terms of the Mozilla Public
|
|
2
|
+
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
|
3
|
+
* file, You can obtain one at https://mozilla.org/MPL/2.0/. */
|
|
4
|
+
import { getEffectiveEntityIndex } from './effective-index.js';
|
|
5
|
+
import { createModificationLedger } from './delta-modification-ledger.js';
|
|
6
|
+
import { createSourceRefReader } from './source-ref-bounds.js';
|
|
7
|
+
import { buildStepHeader } from './step-header.js';
|
|
8
|
+
export function buildExportPass(input) {
|
|
9
|
+
const { dataStore, mutationView, isGeometryEntity, options, schema, sourceSchema, converting, applyMutations, excludeGeometry, sourceHeader, schemaToken, } = input;
|
|
10
|
+
const pass = {
|
|
11
|
+
entities: [],
|
|
12
|
+
newEntityCount: 0,
|
|
13
|
+
schema,
|
|
14
|
+
sourceSchema,
|
|
15
|
+
converting,
|
|
16
|
+
sourceHeader,
|
|
17
|
+
schemaToken,
|
|
18
|
+
overlayActive: !!mutationView && applyMutations,
|
|
19
|
+
// Built once entity counts are known, so the provenance item can report the
|
|
20
|
+
// actual modification count. See the two call sites (empty delta + final).
|
|
21
|
+
// Body lives in `step-header.ts` (#2475 header/assembly tail): the
|
|
22
|
+
// closure still has to be built here, because it closes over this
|
|
23
|
+
// call's own `options`/`sourceHeader`/`schemaToken`, and both call
|
|
24
|
+
// sites still read it as `pass.buildHeader`.
|
|
25
|
+
buildHeader: (modifications) => buildStepHeader(options, sourceHeader, schemaToken, modifications),
|
|
26
|
+
// The one authority for exists / class / deleted, overlay first and source
|
|
27
|
+
// buffer second. Every pass below asks this instead of `dataStore`,
|
|
28
|
+
// which answers only for the file as parsed (#2012).
|
|
29
|
+
effective: getEffectiveEntityIndex(dataStore, mutationView, applyMutations),
|
|
30
|
+
// Does this id belong to an entity the OVERLAY created (`createEntity` /
|
|
31
|
+
// `store.addEntity`) rather than to a record in the source buffer? Such an
|
|
32
|
+
// entity has no source bytes, so the source-iteration pass below never sees
|
|
33
|
+
// it and the new-entities pass at the end owns its line entirely (#2006).
|
|
34
|
+
isOverlayCreated: (entityId) => pass.effective.isOverlayCreated(entityId),
|
|
35
|
+
// Does this record describe a line this export can actually READ out of the
|
|
36
|
+
// source? One predicate for every byte-range gate below, so they cannot
|
|
37
|
+
// disagree — see `source-ref-bounds.ts` for the corrupt file the weaker
|
|
38
|
+
// "is there a source / does the ref claim bytes" pair let through (#2491).
|
|
39
|
+
isReadableSourceRef: createSourceRefReader(dataStore.source),
|
|
40
|
+
// Build visible-only closure if requested. Classification, the closure walk
|
|
41
|
+
// and the style pass all run over the EFFECTIVE index: an overlay-created
|
|
42
|
+
// product becomes a root by the same type rules as a parsed one, the walk
|
|
43
|
+
// follows its authored references into the geometry it alone owns, and a
|
|
44
|
+
// tombstoned entity is simply not there. Run over the source buffer, a
|
|
45
|
+
// created wall could never be a root and nothing referenced it, so
|
|
46
|
+
// `visibleOnly` wrote a file without it and said nothing (#2012).
|
|
47
|
+
//
|
|
48
|
+
// Computed here, ahead of the modification-count passes below, because
|
|
49
|
+
// `hasEmittableHostBytes` needs it: a source-backed host EXCLUDED by
|
|
50
|
+
// `visibleOnly` never gets its line written by the source-iteration pass
|
|
51
|
+
// either, so counting it as "modified" would make the header claim a
|
|
52
|
+
// change the DATA section does not contain (CodeRabbit finding on #2414).
|
|
53
|
+
allowedEntityIds: null,
|
|
54
|
+
// Populated alongside `allowedEntityIds` below. `getVisibleEntityIds`
|
|
55
|
+
// excludes a hidden PRODUCT's own line from the closure, but `IFCREL*` is
|
|
56
|
+
// an unconditional root a few lines down and its bytes are copied verbatim
|
|
57
|
+
// by the source-iteration pass — nothing there filters a `#N` the closure
|
|
58
|
+
// just excluded out of the relationship's own attribute list. Kept because
|
|
59
|
+
// the closure walk's `isRefExcludedDuringClosureWalk` needs a notion of
|
|
60
|
+
// "hidden" that does not read `allowedEntityIds` — the set that walk is
|
|
61
|
+
// producing (#2398). The two OUTPUT passes no longer read this directly:
|
|
62
|
+
// they filter on `isOmittedFromOutput`, which subsumes it via
|
|
63
|
+
// `allowedEntityIds`.
|
|
64
|
+
hiddenProductIds: null,
|
|
65
|
+
// A relationship can name an excluded entity two ways that have nothing
|
|
66
|
+
// to do with each other: a `visibleOnly` hidden PRODUCT (`hiddenProductIds`,
|
|
67
|
+
// below), and a TOMBSTONED one — `editor.removeEntity` on a related object
|
|
68
|
+
// named by a relationship the deletion sweep below does not reach (that
|
|
69
|
+
// sweep only withholds an `IfcRelDefinesByProperties` when EVERY related
|
|
70
|
+
// object is gone, and only for that one relationship class). Left alone, a
|
|
71
|
+
// relationship still naming a deleted entity ships the identical `#N` with
|
|
72
|
+
// no `#N=` line, on a path with no `visibleOnly` involved at all (#2398).
|
|
73
|
+
// `effective.isDeleted` answers for every id, not just a precomputed set,
|
|
74
|
+
// so this predicate covers both sources without a second exclusion set.
|
|
75
|
+
//
|
|
76
|
+
// Declared here, ahead of the closure walk below, and passed into
|
|
77
|
+
// `collectReferencedEntityIds` as its `isRefExcluded` — rather than the
|
|
78
|
+
// walk inventing its own `!entityIndex.has` proxy for "deleted" that could
|
|
79
|
+
// disagree on an id that never existed in the file at all
|
|
80
|
+
// (maintainer-found regression on #2637: such an id blocked the bridge but
|
|
81
|
+
// did not stop the relationship's own line from shipping, dropping a
|
|
82
|
+
// VISIBLE sibling's pset while adding a fresh dangling ref). A closure over
|
|
83
|
+
// `pass.hiddenProductIds`, not a value snapshot — correct because nothing
|
|
84
|
+
// reads it before the closure walk assigns it just below.
|
|
85
|
+
//
|
|
86
|
+
// ## Why this is NOT the predicate the OUTPUT-line filter uses
|
|
87
|
+
//
|
|
88
|
+
// The name says walk, and only walk. The two passes that write a
|
|
89
|
+
// relationship's line ask `isOmittedFromOutput` (further below, derived
|
|
90
|
+
// from `pass.willBeEmitted`), which is strictly stronger — it also answers
|
|
91
|
+
// for the closure, for an unreadable source ref and for a geometry
|
|
92
|
+
// exclusion.
|
|
93
|
+
//
|
|
94
|
+
// This one CANNOT be `willBeEmitted`, and the difference is structural
|
|
95
|
+
// rather than stylistic: `willBeEmitted`'s first act is to consult
|
|
96
|
+
// `allowedEntityIds`, and `allowedEntityIds` is precisely what the call
|
|
97
|
+
// below is computing. Wiring it in here is circular: it would answer "not
|
|
98
|
+
// in the closure" as `false` while the closure is still being built and
|
|
99
|
+
// `true` for the same id afterwards.
|
|
100
|
+
//
|
|
101
|
+
// That is a genuine departure from the contract #2637 was closed on —
|
|
102
|
+
// `reference-collector.ts` still documents the bridge as taking the
|
|
103
|
+
// caller's OWN output predicate, "not two expressions that happened to
|
|
104
|
+
// agree". It has an OBSERVABLE consequence, not just a naming one: for an
|
|
105
|
+
// unreadable source ref this admits, the walk bridges through a
|
|
106
|
+
// relationship the output then withholds, leaving the relationship's other
|
|
107
|
+
// target in the closure with nothing naming it — an orphan, pinned by
|
|
108
|
+
// `unreadable-ref-dangling.test.ts` ("walk and output predicates diverge").
|
|
109
|
+
// The reverse direction is closed: every id this excludes,
|
|
110
|
+
// `isOmittedFromOutput` excludes too, so the #2548 leak cannot return.
|
|
111
|
+
isRefExcludedDuringClosureWalk: (id) => (pass.hiddenProductIds !== null && pass.hiddenProductIds.has(id))
|
|
112
|
+
|| pass.effective.isDeleted(id),
|
|
113
|
+
// Will THIS entity's own line ever land in the file? The same byte-range
|
|
114
|
+
// test `willBeEmitted` uses (defined further below) and the source-
|
|
115
|
+
// iteration pass's own skip at `entityRef.byteLength === 0` — a source
|
|
116
|
+
// entity with no bytes (a point-cloud / GLB "entity" from
|
|
117
|
+
// `createSyntheticDataStore`, not an overlay-created one) never gets a
|
|
118
|
+
// defining line written, source-iteration or otherwise, so a pset/attribute
|
|
119
|
+
// edit against it must not count as a modification either: the header
|
|
120
|
+
// would describe a change the file does not contain (out-of-scope finding
|
|
121
|
+
// in #2398). Also excludes a source-backed host the visible-only closure
|
|
122
|
+
// above drops — same reasoning, different reason the line never lands.
|
|
123
|
+
//
|
|
124
|
+
// And, like `willBeEmitted` below, excludes a geometry-classified SOURCE
|
|
125
|
+
// host under `includeGeometry: false`: the source-iteration pass's own
|
|
126
|
+
// `isGeometryEntity` skip (further below) drops that line too, so this
|
|
127
|
+
// predicate must agree or a geometry entity's attribute edit inflates the
|
|
128
|
+
// count over an omitted line (CodeRabbit finding on #2414). Guarded by
|
|
129
|
+
// `!deltaOnly` for the same reason `willBeEmitted` is: under `deltaOnly`
|
|
130
|
+
// the source-iteration pass — and its geometry skip — never runs at all,
|
|
131
|
+
// so a source entity's line is assumed to already exist in the file being
|
|
132
|
+
// patched, geometry or not.
|
|
133
|
+
isGeometryExcluded: (entityId, recordType) => excludeGeometry
|
|
134
|
+
&& isGeometryEntity(pass.effective.effectiveType(entityId, recordType)),
|
|
135
|
+
hasEmittableHostBytes: (entityId) => {
|
|
136
|
+
if (pass.allowedEntityIds !== null && !pass.allowedEntityIds.has(entityId))
|
|
137
|
+
return false;
|
|
138
|
+
const ref = pass.effective.get(entityId);
|
|
139
|
+
// The ref must be READABLE, not merely non-empty: a range this source
|
|
140
|
+
// cannot address decodes to the empty string, which used to be pushed
|
|
141
|
+
// into the file as a blank line while everything generated FOR the host
|
|
142
|
+
// still named it (#2491).
|
|
143
|
+
if (!ref || !pass.isReadableSourceRef(ref))
|
|
144
|
+
return false;
|
|
145
|
+
if (options.deltaOnly !== true && pass.isGeometryExcluded(entityId, ref.type))
|
|
146
|
+
return false;
|
|
147
|
+
return true;
|
|
148
|
+
},
|
|
149
|
+
/**
|
|
150
|
+
* Will this id have a defining STEP line in the output at all?
|
|
151
|
+
*
|
|
152
|
+
* The predicate is #2030's, and it is the right one: the pset, quantity and
|
|
153
|
+
* type-owned passes below are built from unfiltered mutation history, and
|
|
154
|
+
* what each of them needs to know before emitting an
|
|
155
|
+
* `IFCRELDEFINESBYPROPERTIES` is not "was this deleted" or "is this hidden"
|
|
156
|
+
* but the general question those are two answers to. A relation naming an
|
|
157
|
+
* expressId that never gets written is a dangling reference and an invalid
|
|
158
|
+
* file, whichever route dropped the line.
|
|
159
|
+
*
|
|
160
|
+
* #2030 had to reach for four things to answer it — a tombstone probe, a
|
|
161
|
+
* visibility set, a byte-range test on `completeIndex`, and a `getNewEntity`
|
|
162
|
+
* fallback whose stated purpose was that `deleteEntity` FORGOT an
|
|
163
|
+
* overlay-created entity instead of tombstoning it, so `isDeleted` could not
|
|
164
|
+
* answer for one. That fallback was documented on main as a workaround for
|
|
165
|
+
* exactly the model-level defect this branch fixes: `deleteEntity` now
|
|
166
|
+
* tombstones as well as forgets, so the effective index answers existence
|
|
167
|
+
* for source and overlay ids alike and the workaround collapses into it.
|
|
168
|
+
*
|
|
169
|
+
* The overlay branch does NOT disappear with it, and the distinction matters:
|
|
170
|
+
* `isOverlayCreated` is still load-bearing here, because a live
|
|
171
|
+
* overlay-created entity has no source bytes and would fail the byte-range
|
|
172
|
+
* test that a source record passes. What the tombstone fix removed is the
|
|
173
|
+
* need for that branch to double as a deletion detector.
|
|
174
|
+
*
|
|
175
|
+
* Deliberately unchanged from #2030 for source records under `deltaOnly` /
|
|
176
|
+
* `exportPropertiesOnly`: the source-iteration pass is skipped wholesale in
|
|
177
|
+
* those modes, yet a source entity still answers true here. A delta is a
|
|
178
|
+
* patch against a file that already has the line, not a standalone model.
|
|
179
|
+
*/
|
|
180
|
+
willBeEmitted: (entityId) => {
|
|
181
|
+
if (pass.allowedEntityIds !== null && !pass.allowedEntityIds.has(entityId))
|
|
182
|
+
return false;
|
|
183
|
+
// Undefined for a tombstoned id and for one neither the file nor the
|
|
184
|
+
// session ever had — a stale mutation must not conjure a relation either.
|
|
185
|
+
const ref = pass.effective.get(entityId);
|
|
186
|
+
if (!ref)
|
|
187
|
+
return false;
|
|
188
|
+
// An overlay-created record carries the placeholder byte range and is
|
|
189
|
+
// written by the new-entities pass; a source record needs real bytes.
|
|
190
|
+
if (pass.effective.isOverlayCreated(entityId)) {
|
|
191
|
+
// The overlay new-entities pass applies its OWN `isGeometryEntity`
|
|
192
|
+
// filter unconditionally — deltaOnly or not (see the comment at that
|
|
193
|
+
// loop, further below) — so this branch mirrors it without the
|
|
194
|
+
// deltaOnly carve-out the source branch gets.
|
|
195
|
+
return !pass.isGeometryExcluded(entityId, ref.type);
|
|
196
|
+
}
|
|
197
|
+
// Same readability test as `hasEmittableHostBytes`, and for the reason
|
|
198
|
+
// that predicate names: a ref this source cannot address is not a line
|
|
199
|
+
// this export can write, so nothing may be generated naming it (#2491).
|
|
200
|
+
if (!pass.isReadableSourceRef(ref))
|
|
201
|
+
return false;
|
|
202
|
+
// Mirrors `hasEmittableHostBytes`: under `deltaOnly` the source-
|
|
203
|
+
// iteration pass — and its geometry skip — never runs, so a source
|
|
204
|
+
// entity's line is assumed to already exist in the file being patched.
|
|
205
|
+
if (options.deltaOnly === true)
|
|
206
|
+
return true;
|
|
207
|
+
return !pass.isGeometryExcluded(entityId, ref.type);
|
|
208
|
+
},
|
|
209
|
+
// Under `deltaOnly` a nomination only becomes a count once some pass has
|
|
210
|
+
// actually written content that delivers THAT KIND of edit for the host —
|
|
211
|
+
// see `delta-modification-ledger.ts` for why the two are not the same event
|
|
212
|
+
// in that mode, and why the pair is (entity, kind) rather than the entity
|
|
213
|
+
// (#2462).
|
|
214
|
+
modifications: createModificationLedger(options.deltaOnly === true),
|
|
215
|
+
/**
|
|
216
|
+
* Hosts whose in-place named-attribute edits a FULL export may count, per
|
|
217
|
+
* kind. Filled by the collection passes below and read by the two passes
|
|
218
|
+
* that write a rewritten source line — see `in-place-nomination.ts` for why
|
|
219
|
+
* the nomination waits for the rewrite in this mode and not under
|
|
220
|
+
* `deltaOnly` (#2483).
|
|
221
|
+
*/
|
|
222
|
+
inPlaceNominees: {
|
|
223
|
+
attribute: new Set(),
|
|
224
|
+
georeferencing: new Set(),
|
|
225
|
+
},
|
|
226
|
+
// Collect entities that need to be modified or created
|
|
227
|
+
modifiedEntities: new Set(),
|
|
228
|
+
modifiedAttributes: new Map(),
|
|
229
|
+
newPropertySets: [],
|
|
230
|
+
newQuantitySets: [],
|
|
231
|
+
typeOwnedPsetNamesByEntity: new Map(),
|
|
232
|
+
typeOwnedPsetIdsByEntity: new Map(),
|
|
233
|
+
rewrittenEntityIds: new Set(),
|
|
234
|
+
rewrittenEntityLines: new Map(),
|
|
235
|
+
/** HasPropertySets slot value for an OVERLAY-CREATED type object, applied
|
|
236
|
+
* by the new-entities pass (there is no source line to rewrite). */
|
|
237
|
+
overlayTypeOwnedPsets: new Map(),
|
|
238
|
+
// Track property set IDs and relationship IDs to skip
|
|
239
|
+
skipPropertySetIds: new Set(),
|
|
240
|
+
skipRelationshipIds: new Set(),
|
|
241
|
+
// Written by the georeferencing pass and read again by the final
|
|
242
|
+
// assembly, which is why they are pass state and not phase locals.
|
|
243
|
+
newGeorefLines: [],
|
|
244
|
+
warnings: [],
|
|
245
|
+
};
|
|
246
|
+
// The same object, deliberately. See the file header.
|
|
247
|
+
return pass;
|
|
248
|
+
}
|
|
249
|
+
//# sourceMappingURL=step-pass-builder.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"step-pass-builder.js","sourceRoot":"","sources":["../src/step-pass-builder.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,198 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* The property-set and quantity-set phases of `StepExporter.export()` (#2475
|
|
3
|
+
* steps 2b and 2c), and the type-object `HasPropertySets` rewrite that sits
|
|
4
|
+
* between them.
|
|
5
|
+
*
|
|
6
|
+
* ## Why one module, and why the rewrite is not its own function
|
|
7
|
+
*
|
|
8
|
+
* - `generatedTypeOwnedPsetIds` is written by the property-set generation loop
|
|
9
|
+
* and read by the rewrite loop. `ExportPass` documents it as the binding
|
|
10
|
+
* that "is read in one phase only", and it stays that way here precisely
|
|
11
|
+
* because both loops live inside
|
|
12
|
+
* {@link generatePropertyAndQuantitySetEntities}: it is a plain local, not a
|
|
13
|
+
* field on the pass and not an argument threaded between two functions.
|
|
14
|
+
* - {@link getTypeOwnedHasPropertySetIds} is the rewrite's own helper, but its
|
|
15
|
+
* only call site is the property-set COLLECTION loop, which fills
|
|
16
|
+
* `pass.typeOwnedPsetIdsByEntity` from its result.
|
|
17
|
+
* - `getPropertySetName` is called from the collection loop twice and from the
|
|
18
|
+
* rewrite once.
|
|
19
|
+
* - The three generation loops run pset → rewrite → qset, and `export()`
|
|
20
|
+
* flushes `pass.rewrittenEntityLines` (the rewrite's output) only after the
|
|
21
|
+
* qset loop. That order is load-bearing and is kept exactly as it was.
|
|
22
|
+
*
|
|
23
|
+
* ## What stayed behind, and why these two exports exist
|
|
24
|
+
*
|
|
25
|
+
* `retainSharedAtoms` belongs to neither phase and runs between them, so it
|
|
26
|
+
* stays on the exporter — which is why {@link getPropertyIdsInSet} is exported
|
|
27
|
+
* rather than module-private, the same shape step 2a used for
|
|
28
|
+
* `findLengthUnitReference`. {@link buildRelDefinesByPropertiesIndex} is
|
|
29
|
+
* exported for the mirror-image reason: the collection loops consume its
|
|
30
|
+
* `byEntity` half, but `export()` reads `relatedByRel` for the deleted-host
|
|
31
|
+
* relationship sweep, which is neither phase's work.
|
|
32
|
+
* `step-attribute-mutations.ts`'s `applySourceLineMutations` (moved off
|
|
33
|
+
* `StepExporter` by #2475's "remaining private helpers" step) is shared with
|
|
34
|
+
* the source-iteration pass, so it is injected on the context rather than
|
|
35
|
+
* imported directly.
|
|
36
|
+
*
|
|
37
|
+
* ## The state these phases cannot read off the pass
|
|
38
|
+
*
|
|
39
|
+
* {@link PropertySetContext}, following `step-georeferencing.ts:GeorefContext`.
|
|
40
|
+
* `allocateExpressId` is the exporter's own `nextExpressId++`: all six
|
|
41
|
+
* allocation sites in an export live in the two generators below, and the
|
|
42
|
+
* counter is shared with the georeferencing phase, so it is injected as a
|
|
43
|
+
* callback rather than hoisted onto the pass. The owner-history memos are
|
|
44
|
+
* injected BY REFERENCE and stay owned by the exporter, because their reset is
|
|
45
|
+
* an `export()`-level statement whose comment explains why they are per-export;
|
|
46
|
+
* storing them here would move that reset out of the method that documents it.
|
|
47
|
+
*
|
|
48
|
+
* Every helper below takes `ctx` FIRST; the two phase entry points take it
|
|
49
|
+
* LAST, as `applyGeoreferencingMutations` does. The split is not aesthetic —
|
|
50
|
+
* the two generators end in optional parameters, which a trailing `ctx` cannot
|
|
51
|
+
* follow.
|
|
52
|
+
*/
|
|
53
|
+
import type { IfcDataStore } from '@ifc-lite/parser';
|
|
54
|
+
import { EntityExtractor } from '@ifc-lite/parser';
|
|
55
|
+
import type { MutablePropertyView } from '@ifc-lite/mutations';
|
|
56
|
+
import { createSourceRefReader } from './source-ref-bounds.js';
|
|
57
|
+
import type { IfcSchemaVersion } from './schema-converter.js';
|
|
58
|
+
import type { ExportPass, SourceLineMutations, StepExportOptions } from './step-exporter.js';
|
|
59
|
+
/**
|
|
60
|
+
* The two owner-history memos the generators share, in one object so the
|
|
61
|
+
* exporter can hand them over by reference. Both are per-EXPORT rather than
|
|
62
|
+
* per-exporter; `StepExporter.export()` owns the reset and explains why.
|
|
63
|
+
*/
|
|
64
|
+
export interface OwnerHistoryCache {
|
|
65
|
+
/** Lazily-resolved fallback `#id` of an IfcOwnerHistory that survives the
|
|
66
|
+
* current export closure (or `$` when the file has none). */
|
|
67
|
+
fallbackRef: string | undefined;
|
|
68
|
+
/** Per-host cache of an element's own OwnerHistory ref (`#id` or null). */
|
|
69
|
+
readonly byEntity: Map<number, string | null>;
|
|
70
|
+
}
|
|
71
|
+
/**
|
|
72
|
+
* The exporter state these phases cannot read off the {@link ExportPass}.
|
|
73
|
+
*
|
|
74
|
+
* `isReadableSourceRef` is the exporter's OWN reader rather than the pass's:
|
|
75
|
+
* the byte readers below are also reached from
|
|
76
|
+
* {@link buildRelDefinesByPropertiesIndex} and from `retainSharedAtoms`,
|
|
77
|
+
* neither of which has a pass in hand. Both readers are built by
|
|
78
|
+
* `createSourceRefReader` over the same `dataStore.source`.
|
|
79
|
+
*/
|
|
80
|
+
export interface PropertySetContext {
|
|
81
|
+
readonly dataStore: IfcDataStore;
|
|
82
|
+
readonly entityExtractor: EntityExtractor | null;
|
|
83
|
+
readonly mutationView: MutablePropertyView | null;
|
|
84
|
+
readonly isReadableSourceRef: ReturnType<typeof createSourceRefReader>;
|
|
85
|
+
/** `() => this.nextExpressId++` on the exporter. */
|
|
86
|
+
readonly allocateExpressId: () => number;
|
|
87
|
+
readonly ownerHistory: OwnerHistoryCache;
|
|
88
|
+
/** `step-attribute-mutations.ts`'s `applySourceLineMutations`: the ONE
|
|
89
|
+
* pipeline the source-iteration pass and the type-object rewrite share, so
|
|
90
|
+
* it belongs to neither phase and is injected. */
|
|
91
|
+
readonly applySourceLineMutations: (expressId: number, entityText: string, recordType: string, attributeMutations: Map<string, string> | undefined, sourceSchema: IfcSchemaVersion, overlayActive: boolean, onRejected?: (attrName: string, value: string) => void) => SourceLineMutations;
|
|
92
|
+
}
|
|
93
|
+
/** The mutation groupings `export()` builds before the collection phase runs. */
|
|
94
|
+
export interface PropertyMutationGroups {
|
|
95
|
+
readonly entityPropMutations: Map<number, Set<string>>;
|
|
96
|
+
readonly entityQuantMutations: Map<number, Set<string>>;
|
|
97
|
+
readonly relDefinesByEntity: Map<number, Array<{
|
|
98
|
+
relId: number;
|
|
99
|
+
psetId: number;
|
|
100
|
+
}>>;
|
|
101
|
+
}
|
|
102
|
+
/**
|
|
103
|
+
* Build a one-shot reverse index of every IfcRelDefinesByProperties in
|
|
104
|
+
* the source: for each related entity, list the rels and property/quantity
|
|
105
|
+
* sets that reference it. Used by the export pre-pass so the per-entity
|
|
106
|
+
* "find owning rels" step is O(K) rather than O(N) per modified entity.
|
|
107
|
+
*
|
|
108
|
+
* `relatedByRel` is the same walk read the other way round, so the deleted-host
|
|
109
|
+
* sweep costs nothing extra.
|
|
110
|
+
*/
|
|
111
|
+
export declare function buildRelDefinesByPropertiesIndex(ctx: PropertySetContext): {
|
|
112
|
+
byEntity: Map<number, Array<{
|
|
113
|
+
relId: number;
|
|
114
|
+
psetId: number;
|
|
115
|
+
}>>;
|
|
116
|
+
relatedByRel: Map<number, number[]>;
|
|
117
|
+
};
|
|
118
|
+
/**
|
|
119
|
+
* The source STEP text of an entity's line, or `null` when there are no bytes
|
|
120
|
+
* to read.
|
|
121
|
+
*
|
|
122
|
+
* The byte check is on the RANGE, not on `dataStore.source`. `source` is a
|
|
123
|
+
* MANDATORY accessor — `EMPTY_SOURCE_BYTES` is how "this model kept no bytes"
|
|
124
|
+
* is spelled (server-parsed, synthetic, GLB and point-cloud stores all have
|
|
125
|
+
* one) — so the `!ctx.dataStore.source` guard the five readers below used to
|
|
126
|
+
* carry never fired. It was also redundant: a zero-length range decodes to
|
|
127
|
+
* `''`, which fails every regex those readers run, so they already answered
|
|
128
|
+
* "nothing" for a sourceless store. Scoping the check to the range is what
|
|
129
|
+
* makes the guard live without changing a single answer, the same shape and
|
|
130
|
+
* for the same reason as `reference-collector.ts` (#2339).
|
|
131
|
+
*
|
|
132
|
+
* An OVERLAY-created entity never reaches here: every caller resolves its id
|
|
133
|
+
* through `dataStore.entityIndex.byId`, which holds source records only
|
|
134
|
+
* (`effective-index.ts` synthesises the overlay refs on its own side and
|
|
135
|
+
* writes nothing back), so an overlay id is already `undefined` at the
|
|
136
|
+
* lookup and is served by the callers' documented "not a source record"
|
|
137
|
+
* path. That is why an early return is safe HERE and is NOT safe at the
|
|
138
|
+
* visible-only closure in `export` — see the comment there.
|
|
139
|
+
*
|
|
140
|
+
* ## Why `isReadableSourceRef` and not `byteLength === 0`
|
|
141
|
+
*
|
|
142
|
+
* An out-of-range ref does NOT degrade to "no match" here. `decodeUtf8`
|
|
143
|
+
* clamps the range it cannot address, and the clamped window is still a
|
|
144
|
+
* window over real file bytes — so these readers answer from somebody
|
|
145
|
+
* ELSE's record. `source-ref-bounds.ts` (#2491) carries the measured
|
|
146
|
+
* account of both shapes and of why "a clamped, empty decode already yields
|
|
147
|
+
* no match" is false; it is not restated here, because an argument kept in
|
|
148
|
+
* two files is an argument that has to stay true in two files.
|
|
149
|
+
*
|
|
150
|
+
* The consequence specific to THIS site is that the wrong answer is acted
|
|
151
|
+
* on. `retainSharedAtoms` un-skips every id `getPropertyIdsInSet` returns,
|
|
152
|
+
* so a member list read out of the wrong record un-skips the wrong atoms;
|
|
153
|
+
* and the source-iteration pass already refuses to emit a record whose ref
|
|
154
|
+
* fails `isReadableSourceRef` (see the `continue` in `export`), so before
|
|
155
|
+
* this gate these readers were making decisions on behalf of a container
|
|
156
|
+
* that the same export had decided not to write. Gating them on the same
|
|
157
|
+
* predicate is what makes the two passes agree.
|
|
158
|
+
*
|
|
159
|
+
* The degradation is the one the exporter already handles: a record with no
|
|
160
|
+
* emittable bytes, generating nothing and named by nothing. It costs one
|
|
161
|
+
* answer that used to be right by luck — an overrunning ref on the file's
|
|
162
|
+
* LAST record clamps back to exactly that record's text — but that record
|
|
163
|
+
* is one the emission pass drops anyway, so keeping the answer only kept
|
|
164
|
+
* the disagreement.
|
|
165
|
+
*/
|
|
166
|
+
export declare function entityLineText(ctx: PropertySetContext, entityId: number): string | null;
|
|
167
|
+
/**
|
|
168
|
+
* Get the name of a property set by parsing the entity
|
|
169
|
+
*/
|
|
170
|
+
export declare function getPropertySetName(ctx: PropertySetContext, psetId: number): string | null;
|
|
171
|
+
/**
|
|
172
|
+
* Get IDs of properties in a property set
|
|
173
|
+
*/
|
|
174
|
+
export declare function getPropertyIdsInSet(ctx: PropertySetContext, psetId: number): number[];
|
|
175
|
+
/**
|
|
176
|
+
* Collect what the overlay's property-set and quantity-set edits mean for this
|
|
177
|
+
* export: which sets to regenerate (`pass.newPropertySets` /
|
|
178
|
+
* `pass.newQuantitySets`), which source records to withhold
|
|
179
|
+
* (`pass.skipPropertySetIds` / `pass.skipRelationshipIds`), and which type
|
|
180
|
+
* objects need their `HasPropertySets` resolved later
|
|
181
|
+
* (`pass.typeOwnedPsetNamesByEntity`, `…IdsByEntity`, `pass.rewrittenEntityIds`).
|
|
182
|
+
*
|
|
183
|
+
* The caller owns the `mutationView && options.applyMutations !== false` gate;
|
|
184
|
+
* reaching here means overlay edits were both present and enabled.
|
|
185
|
+
*/
|
|
186
|
+
export declare function collectPropertyAndQuantitySetMutations(pass: ExportPass, options: StepExportOptions, groups: PropertyMutationGroups, ctx: PropertySetContext): void;
|
|
187
|
+
/**
|
|
188
|
+
* Write the generated property-set and quantity-set records into
|
|
189
|
+
* `pass.entities`, and point every affected type object's `HasPropertySets` at
|
|
190
|
+
* the property sets this export just generated.
|
|
191
|
+
*
|
|
192
|
+
* Three loops, in the order `export()` ran them, and the order is load-bearing:
|
|
193
|
+
* the rewrite reads `generatedTypeOwnedPsetIds` from the property-set loop, and
|
|
194
|
+
* the caller flushes `pass.rewrittenEntityLines` — this function's output —
|
|
195
|
+
* only after the quantity-set loop has run.
|
|
196
|
+
*/
|
|
197
|
+
export declare function generatePropertyAndQuantitySetEntities(pass: ExportPass, options: StepExportOptions, ctx: PropertySetContext): void;
|
|
198
|
+
//# sourceMappingURL=step-property-sets.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"step-property-sets.d.ts","sourceRoot":"","sources":["../src/step-property-sets.ts"],"names":[],"mappings":"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"}
|