Expand description
Domain-format exporters for ifc-lite.
Phase 1: HBJSON (Honeybee energy-model) room export — the analytic, watertight IFC→Ladybug bridge. Apertures/doors/shades and a glTF migration follow.
This is the Rust source of truth; CLI / SDK / wasm become thin callers (mirroring how
geometry already flows through ifc-lite-wasm).
Modules§
- csv_
cell - The single CSV cell escaper for this crate — RFC 4180 quoting plus the
CWE-1236 formula-injection guard, pinned to the TypeScript half by
tests/csv_cell_parity.rs. THE CSV cell escaper for this repository’s Rust. - rooted_
type - Schema-driven
IfcRootrootedness check, extracted as a standalone unit. - source_
header - Read the ISO 10303-21
HEADERsection of a source file into the structured form the writer needs to round-trip header fidelity.
Structs§
- Attr
Mutation - A single root-attribute edit: replace the top-level attribute at
indexof entityexpress_idwithvalue(already STEP-serialized, e.g.'New Name'or$). This is the wasm-bridge form of aMutablePropertyViewUPDATE_ATTRIBUTE mutation. - Authored
Quantity - An IFC-authored physical simple quantity, with its two source entity IDs.
- Authored
Quantity Analysis - Observations keyed by product STEP ID.
product_countcounts IFC product entities, not represented solids or physical parts. - Authored
Rebar Attribute - One explicitly authored EXPRESS attribute, keyed by its exact name.
- Copy
OnWrite Mutation - Replace one attribute of a record that other records share, by copying the record and repointing a single referrer at the copy.
- CsvOptions
- Options for CSV export.
- Decoded
Entity - Decoded IFC entity.
attributesis behind anArcso cloning aDecodedEntity(the decoder clones on every cache insert AND every cache hit) is a refcount bump, not a deep clone of the attribute tree. Attributes are never mutated after construction, so sharing is sound and byte-identical. - Derived
Quantity - A source parameter or nominal measurement, never a final cut-product takeoff.
- Dfjson
Options - Options for DFJSON (Dragonfly) export.
- Dfjson
Stats - Coverage stats for a DFJSON export.
- Entity
Row - One exportable entity row.
- Export
Model - The full extracted model.
- Georef
Mutations StepExportOptions.georefMutations: partialProjectedCRS/MapConversionedits. Each member is kept as its JSON value so an explicitnullstays distinguishable from an absent key, which the TypeScript exporter tests with!== undefined.- GlbSize
Projection - Projected size of the single-GLB export for a model, computed from pass 1
only (no output allocation) — issue #1516. A caller uses it to pick single
GLB vs multi-buffer glTF (
export_gltf_streaming) WITHOUT the historical “attempt the GLB, catch the 4 GiB panic, re-run as multi-buffer” dance. - Gltf
Buffer - One finished external buffer of a multi-buffer glTF export.
- Gltf
Options - Options for glTF/GLB export.
- Gltf
Stats - Coverage stats for a GLB export.
- Hbjson
Options - Options for HBJSON export.
- Hbjson
Stats - Coverage stats for an HBJSON export.
- Ifc5
Options - Options for IFC5/IFCX export.
- Json
LdOptions - Options for JSON-LD export.
- Json
Options - Options for JSON export.
- KmzOptions
- Options for KMZ export.
- Land
XmlTerrain Export - The LandXML document plus what it contains.
- Land
XmlTerrain Options - How the document is written.
#[non_exhaustive]: build it withLandXmlTerrainOptions::newand set the fields you need, so a later option is not a breaking change. - Land
XmlTerrain Refusal - The selection is not an authored triangulated terrain, or its georeferencing (map conversion, CRS, units) is missing or ambiguous. The reason names the product or attribute, so a caller can show it verbatim.
- Land
XmlTerrain Surface - One written
<Surface>, for the caller to report. - LogExport
Stats - What a mutation-log export reports beyond
StepStats. - LogMutation
- One
Mutationrecord. Values are kept as JSON because that is what they are on the wire:PropertyValueisstring | number | boolean | null | PropertyValue[], and a positional value may carry the{ real }/{ typed }write markers. - LogNew
Entity NewEntity: an entity the session created, asgetNewEntities()returns it.attributesis the positional STEP argument list in theIfcAttributeValueshape ("#42"for a reference,".AREA."for an enum,"$"for unset,{ "real": 5 }for a forced REAL).- MapConversion
Entity Patch - A complete replacement or newly allocated STEP entity. IDs let the host exporter settle its existing modification ledger without counting edits twice.
- MapConversion
Normalization Plan - Atomic plan applied to the already mutation-resolved export pass. Warnings mean no geometry/context patches were produced; upload must refuse them.
- Merged
Model - A single input model for
export_merged_models. - Merged
Options - Options for merged export.
- Merged
Stats - Coverage stats for a merged export.
- Model
- The top-level Honeybee model.
- Model
Options - What the export should resolve beyond the attributes it always reads.
- Mutation
Log - What
exportMutations()returns, plus the two members above. - ObjOptions
- Options for OBJ export.
- ObjStats
- Coverage stats for an OBJ export.
- Placement
- A product’s placement, composed from its
IfcLocalPlacementchain. - Product
Quantities - One actual product occurrence; no row here represents a type product.
- Product
Quantity Analysis - Authored observations and nominal source estimates for one IFC product.
- Prop
Mutation - A property create/update: attach (or overwrite)
prop_nameinpset_nameonexpress_idwithvalue— the STEP-serialized nominal value, e.g.IFCLABEL('2HR')orIFCREAL(42.). The wasm-bridge form of aMutablePropertyViewCREATE/UPDATE_PROPERTY. Synthesizes freshIfcPropertySingleValue/IfcPropertySet/IfcRelDefinesByPropertiesentities appended to DATA (new psets; merge-into-existing is a follow-on). - Prop
Value - A single property value (
IfcPropertySingleValueand friends). - Property
Set - A named property set (
IfcPropertySet). - Quantity
Analysis - Product and unique geometric source counts are different, especially for maps.
- Quantity
Conflict - Same named authored occurrence and type quantity disagree in value or unit.
- Quantity
Set - A named quantity set (
IfcElementQuantity). - Quantity
Source Occurrence - One use of a source solid by a product. Repeated map uses remain separate.
- Quantity
Unit - Resolved IFC unit, including an explicit quantity override when supplied.
- Quantity
Value - A single physical quantity (
IfcQuantityLength/Area/Volume/…). - Rebar
Fabrication Check - One requested comparison, including the source identity and absent-value reason.
- Rebar
Fabrication Policy - Caller-selected SI comparisons.
Nonemeans the check was not requested. - Rebar
Fabrication Policy Error - Rebar
Fabrication Report - A geometric precheck only. Even all passing checks do not establish a physical bar count, material, process, cutting length, or code compliance.
- Rebar
Preflight Comparison - One measured comparison. Segment index is absent for the whole directrix.
- Rebar
Preflight Error - Invalid caller-supplied fabrication threshold.
- Rebar
Preflight Limits - Project-specific limits in SI metres. No default fabrication code is implied.
- Rebar
Preflight Report - Source geometry assessment. A skipped sweep has unavailable comparisons.
- Rebar
Schedule - Occurrence-keyed schedule inputs.
physical_bar_countis deliberately absent: IFC permits one entity to represent multiple manufactured bars. - Rebar
Schedule Row - One IFC
IfcReinforcingBarentity, including bars without analytic geometry. - Rebar
Sweep - One represented swept-disk source. This is not a physical bar count.
- Relationships
- Relationships resolved from one pass over the file.
- Step
Counters StepStats’ counters, carried over for a caller that reads them.- Step
Options - Options for STEP export.
- Step
Stats - Coverage stats for a STEP export.
- Unit
Scales - The file’s unit scales, resolved exactly once per parse.
- UsdOptions
- Options for USD (USDA) export.
Enums§
- Altitude
Mode - KML
<altitudeMode>— how Google Earth interprets the model’saltitude. - Attribute
Value - IFC entity attribute value
- Authored
Rebar Value - Authored IFC value. Measures retain the file value and an SI conversion.
- Container
Merge Strategy - Strategy for matching a later model’s
IfcSite/IfcBuildingonto the first. - CsvMode
- Which CSV view to emit.
- Export
Error - A failure the caller must handle; completion of a
try_export_*function implies a non-empty artifact. - IfcType
- IFC Entity Types
- Land
XmlLinear Unit - The length unit the document is written in (#7618). Coordinates are computed in metres and converted once, at write time.
- Mutation
Kind Mutation['type'].- Rebar
Fabrication Check Status - Rebar
Schedule Fabrication Error - Rebar
Schedule Preflight Error - Failure to validate caller thresholds or existing sweep-check tolerances.
- Rebar
Source - Where a schema-declared value was authored. An occurrence wins a conflict.
- Storey
Merge Strategy - Strategy for matching a later model’s
IfcBuildingStoreyonto the first. - Tessellation
Quality - Detail level for geometry tessellation, selectable by consumers.
- Unit
Reconciliation - How to reconcile models whose length unit differs from the first model’s.
Functions§
- analyze_
authored_ quantities - Read authored quantities without meshing.
idsrestricts emitted product rows; an empty set emits none. Relationship fan-out and quantity lists have explicit work budgets and report refusal rather than truncating silently. - analyze_
quantities - Join three canonical opt-in analytic views with exact authored observations.
idsselects actual product occurrences; an empty set returns no rows. Source measurements are nominal and intentionally never summed into a product material quantity, cutting length, or physical-part count. - build_
entity_ index - Build an entity index from content.
- build_
export_ model - Build the export model from raw IFC/STEP bytes.
- build_
export_ model_ with_ options build_export_modelwith options. Same memory caveat: this collects.- build_
rebar_ schedule - Build an occurrence-aware schedule without tessellating. The optional ID set
filters
IfcReinforcingBaroccurrence IDs; an empty set returns no rows. Geometric findings concern source paths, not bending-code compliance. - build_
rebar_ schedule_ with_ fabrication_ precheck - Compare only the caller’s requested SI constraints against represented
source geometry. The outcome is always
precheck_only. - build_
rebar_ schedule_ with_ preflight - Build a schedule with caller-supplied geometric fabrication comparisons. Results do not certify a cutting length or code compliance.
- deterministic_
global_ id - Deterministic 22-char GlobalId from an arbitrary seed. A faithful port of
@ifc-lite/parser’sdeterministicGlobalId(four independent 32-bit rolling hashes cross-mixed into a 128-bit state, stamped MSB-first as2 + 21*6bits) so a merged file re-stamped natively carries the same ids the JS path would. - entity_
count - Count the entities in a STEP/IFC byte buffer in
O(scan)time andO(1)memory — no entity index, no per-type map. - escape_
step_ string - The STEP string-literal escaper;
escape’s docs say why it is public. Escape a STEP string literal body: double the apostrophe and reverse solidus, and encode any character outside the basic graphic range as its\X2\/\X4\control directive — never a raw byte — since ISO 10303-21 6.3.3.4 restricts a literal’s plain-text bytes to 32-126. buildingSMART’s IFC string-encoding guidance states the same for IFC2X3/IFC4/IFC4X3: a character outside decimal 32-126 “has to be encoded” (e.g. ‘Ä’ as\X2\00C4\X0\). A reader that treats the file’s bytes as ISO-8859-1 — the byte encoding the base standard and most real consumers assume — turns a raw UTF-8 multi-byte sequence into mojibake or a broken parse; this exact writer shape is a reported, reproduced defect in real IFC tooling (IfcOpenShell#699/#1016; files rejected by Solibri). - export_
csv - Export the requested CSV view from raw IFC bytes.
- export_
dfjson - Export the
IfcSpacevolumes incontent(raw IFC/STEP bytes) as a Dragonfly DFJSON string. Each space becomes an extrudedRoom2D(floor polygon + heights) grouped into stories — the simpler Ladybug target for mostly-vertical-wall models. - export_
dfjson_ with_ stats - Like
export_dfjsonbut also returns coverage stats. - export_
glb_ from_ meshes - Assemble a GLB from already-produced meshes (the viewer’s MeshData — no re-meshing).
Per mesh
i:vertex_counts[i]vertices +index_counts[i]indices, taken in order from the concatenatedpositions/normals/indices;colorsis RGBA per mesh,originsis xyz per mesh,express_idslabels each mesh. Indices are per-mesh LOCAL. Callers pass exactly the meshes they want emitted (visibility filtering is theirs). - export_
gltf_ streaming - Export a model as a multi-buffer glTF: the
.gltfJSON (returned) plus one or more external.binbuffers, each kept underchunk_capbytes (well below the 4 GiB glTF limit), so a model of ANY size loads as one logical model. Each finished buffer is handed tosinkand dropped, so peak memory is ~one chunk, not the whole model — this is the path for models too large for a single GLB (try_export_glb*stays the smaller-model path). Compose withGltfOptions.quantizeto shrink first. - export_
gltf_ streaming_ with_ index - Like
export_gltf_streamingbut reuses a pre-built entity index instead of scanningcontentagain on EACH of its two passes. A caller that already built the index — e.g. to share with the attribute pass (crate::stream_export_model_with_index) — passes it here to remove the redundant SIMD scans on the large models this path targets (#1516).indexMUST come frombuild_entity_indexover the samecontent; output is byte-identical toexport_gltf_streaming. - export_
hbjson - Export the
IfcSpacevolumes incontent(raw IFC/STEP bytes) as an HBJSON string. - export_
hbjson_ with_ stats - Like
export_hbjsonbut also returns coverage stats (so callers can report how many spaces were skipped instead of silently truncating). - export_
ifc5 - Export the model in
contentas an IFCX (IFC5) document string. - export_
json - Export the model as a JSON array string.
- export_
jsonld - Export the model as a JSON-LD document string.
- export_
jsonld_ with_ filter - Export JSON-LD with an explicit null-vs-empty isolation filter.
- export_
merged - Merge
models(raw IFC byte slices) into one STEP/IFC string. Convenience wrapper overexport_merged_modelsthat exports each model in full. - export_
merged_ models - Merge several parsed models into one STEP/IFC string, honoring per-model visibility, spatial-merge strategies, and unit reconciliation.
- export_
merged_ models_ with_ logs export_merged_modelswith a mutation log per model (logs[i]formodels[i];None, a missing entry or an empty log leaves the model as it is). Errs, writing nothing, when a model’s log cannot be applied (seeexport_step_with_log).- export_
merged_ with_ stats - Like
export_mergedbut also returns coverage stats. - export_
obj - Export the render geometry in
content(raw IFC/STEP bytes) as a Wavefront OBJ string. - export_
obj_ with_ stats - Like
export_objbut also returns coverage stats. - export_
step - Export the parsed model in
contentas a STEP/IFC string. - export_
step_ json - Export STEP from raw bytes + a JSON mutation payload (the wasm bridge form of a
MutablePropertyViewdiff). - export_
step_ to_ writer export_step_with_stats, writing as it goes instead of returning the file. The two cannot drift: that one is this one writing into aVec.- export_
step_ with_ log - Export
contentwith the edits inlogapplied, as a string. - export_
step_ with_ log_ to_ writer export_step_with_log, writing as it goes. The source is read, never copied: memory beyond the record index grows with the EDITS (the lines they change, the records they generate), not with the file.- export_
step_ with_ stats - Like
export_stepbut also returns coverage stats. - export_
usd - Export the model in
content(raw IFC/STEP bytes) as a.usda(ASCII USD) string. - ifc_
angle_ to_ kml_ heading - Convert the IFC angle-to-grid-north (counter-clockwise from map east, via the
IfcMapConversionX-axis abscissa/ordinate) into a KML<Model><Orientation><heading>, a clockwise rotation of a model whose local X-axis starts pointing east. Returns0when either component is absent. KML heading is not a compass bearing: atheading = 0the X-axis already points east (KML’s baseline), and rotating clockwise byheadingmoves it to true bearing90 + heading, so reaching bearingBtakesB - 90(mod 360). - leading_
rooted_ global_ id - The leading GlobalId of a raw STEP entity line, classified by TYPE (not just
the 22-char shape): reads the type from the line and applies the rooted-entity
rule, so a non-rooted entity leading with a 22-char charset Name (e.g. an
IfcColourRgb) is not counted as a rooted GlobalId. For callers that only have raw text — the merge harness and duplicate-GlobalId diagnostics — and want the same classification the merge itself uses. - padded_
type_ universe - Every
(from, to, SOURCE TYPE)this module pads, for the cross-language parity gate to re-derive its required-coverage set from rather than trust a count floor (rust/export/tests/schema_upconvert_parity.rs). - plan_
map_ conversion_ normalization - Plan a standards-valid, uniform 3D
IfcMapConversioncompatibility export. Default STEP export never calls this. For project unit u metres, physical similarity s = MapScale/u, and native map affine A = [Rs,T/u], emit P_new = APS^-1 and representation scale S=s. Therefore P_newS=A*P, while logical placement origins also represent the same physical map point. The neutral remaining conversion is offsets 0, axes identity, Scale=u. - project_
glb_ size - Project the single-GLB size for
contentfrom pass 1 only — the world AABB + per-mesh byte sizes the bounded assembler already computes — WITHOUT meshing twice or allocating the output (#1516). Lets a caller pick single GLB vs multi-buffer glTF up front. Meshes the model once (the price of an exact size). - project_
glb_ size_ with_ index - Shared-index
project_glb_size(seetry_export_glb_streaming_bounded_with_index). - relationships
- Resolve the relationships in
content. - stream_
export_ model - Stream one
EntityRowperIfcProductoccurrence, in file order, invokingffor each row and then dropping it. - stream_
export_ model_ with_ index - Like
stream_export_modelbut reuses a pre-built entity index. A caller also running the geometry pass (crate::try_export_glb_with_stats_with_index) over the same bytes builds the index once with [build_entity_index] and shares it across both, skipping the duplicate scan.entity_indexMUST be built from the samecontent; output is identical tostream_export_model. Returns the model’sUnitScales, so a caller consuming attribute values can interpret them without a second pass over the file: the scales are resolved from the decoder this function already builds. - stream_
export_ model_ with_ options stream_export_model_with_index, plus the decoded entity behind each row and whateverModelOptionsasked to resolve.- try_
export_ collada_ from_ meshes - Build a Google-Earth-compatible COLLADA 1.4.1
.daefrom already-produced (Y-up) meshes, flattened into parallel arrays exactly likeexport_glb_from_meshes. Per meshi:vertex_counts[i]vertices +index_counts[i]indices taken in order from the concatenatedpositions/normals/indices;colorsis RGBA per mesh,originsxyz per mesh (world = origin + position). Returns the.daebytes (UTF-8 XML). - try_
export_ glb - Export the render geometry in
contentas a binary GLB. - try_
export_ glb_ from_ meshes - Fail-closed
export_glb_from_meshes: validates the per-meshvertex_counts/index_counts(and normals) against the flattened buffers, and the index VALUES against the vertex counts, BEFORE assembling. ReturnsExportError::MalformedMeshInputwhen a declared vertex/index count runs past the end ofpositions/indices, anindex_countsentry is missing,normalsis empty or too short to cover every emitted vertex, or an index names a vertex its own mesh does not have — instead of silently dropping the un-backed meshes (which the infallible variant does — a valid GLB missing part of the model, reported as success) or copying the out-of-range index straight into the BIN chunk. Prefer this at any boundary where the counts and buffers come from separate sources (the wasm FFI). - try_
export_ glb_ streaming_ bounded - Bounded-memory single-GLB export: two passes over the deterministic mesh
stream (
retain_emitted_meshes: false, peak input = one batch). - try_
export_ glb_ streaming_ bounded_ with_ index - Like
try_export_glb_streaming_boundedbut reuses a pre-built entity index instead of scanningcontentagain on EACH of the two passes — for a caller that already built it (e.g. to share withcrate::stream_export_model_with_index), removing the redundant SIMD scans on the large models this path targets (#1516).indexMUST come frombuild_entity_indexover the samecontent; output is byte-identical. - try_
export_ glb_ with_ stats - Like
try_export_glbbut also returns coverage stats. Meshes the model from bytes. - try_
export_ glb_ with_ stats_ with_ index - Like
try_export_glb_with_statsbut reuses a pre-built entity index — for a caller that also runs the attribute pass (crate::stream_export_model_with_index) over the same bytes,build_entity_indexonce and share it across both.indexMUST be built from the samecontent; output is byte-identical totry_export_glb_with_statsbelow the streaming threshold. NOTE: this path always uses the in-memory assembler (the bounded two-pass path rebuilds its own index per pass and cannot reuse this one); a native caller that needs bounded memory on a large model should calltry_export_glb_streaming_bounded_with_indexdirectly. - try_
export_ kmz_ collada_ from_ meshes - Build a Google-Earth-ready KMZ (
doc.kml+model.dae) directly from the viewer’s already-produced (Y-up) meshes, the working path (#1427). The model is embedded as COLLADA (the only<Model>format Google Earth loads), with emission-lit, double-sided materials andclampToGroundplacement. Mesh arrays matchcrate::try_export_collada_from_meshes/export_glb_from_meshes. - try_
export_ landxml_ terrain - Export the selected terrain products of
content(IFC STEP bytes) as one LandXML 1.2 document, one<Surface>per product in selection order.
Type Aliases§
- Entity
Index - Pre-built entity index type