IfcOpenShell 0.9.0: Your First Python Door Schedule and Fire-Rating Check
IfcOpenShell 0.9.0 rewrote its C++ core. Install it with pip, open any IFC, write a door schedule CSV and flag every door missing a FireRating in Python.
IfcOpenShell 0.9.0 is out. According to the IfcOpenShell v0.9.0 release notes on GitHub, it is “the last major stepping stone before IfcOpenShell version 1.0”. According to PyPI, the Python package ifcopenshell 0.9.0 was uploaded on 29 September 2026, and the headline release tag ifcopenshell-v0.9.0 followed on GitHub on 1 October 2026. Underneath, the community rebuilt the IFC data model and parser from the ground up. On top, the Python an architect actually types is still a handful of lines. The engine is new and the surface you touch is still small, so this is a good time to learn the basic moves.
Every Swiss office receives IFC files from the engineer, the facade consultant and the other architect on the Wettbewerb team. Most of those files get opened in a viewer, rotated and closed again. Nobody asks them a question, yet the answers are already in the file. Every door in it either carries a fire rating or it does not, and you can read all of them before your coffee goes cold.
What the community actually shipped
The IfcOpenShell release notes report, in their Highlights section, a ground-up rewrite of the C++ IFC data model and parser. This is the “v1.0 data model”: it is built on weak_ptr, has a plug-in architecture for schemas, geometry kernels and serializers, and supports lazy, paged parsing. The same Highlights list two new geometry kernels, Manifold and Passthrough, and Bonsai Viewer, a new GPU web and desktop viewer. Bonsai Viewer brings a .ifcview caching format, streaming, federation, measurement tools and a WebAssembly build. According to PyPI, precompiled wheels cover Python 3.10 through 3.15 under the LGPLv3+ licence. The official installation guide on docs.ifcopenshell.org reports the same Python 3.10–3.15 range and gives a single command: pip install ifcopenshell.
That one-line install rests on years of unglamorous work. Hundreds of people have contributed to IfcOpenShell. Among the core contributors visible on ifcopenshell.org are Dion Moult (the PyPI author of record), Thomas Krijnen (aothms on GitHub), Bruno Postle and Andrej730. Building a parser is half the job. The other half is turning it into a wheel that installs cleanly on an office laptop, with documented helpers in ifcopenshell.util and a viewer that runs in a browser, and that half is often the harder one. These maintainers are the reason a door schedule can start with pip.
Read one line before you write one
IFC is not a compiled format. It is plain text, standardised by buildingSMART International, and you can open it in Notepad. Here is an illustrative IFC4 door line of the kind an exporter writes:
#152=IFCDOOR('2O2Fr$t4X7Zf8NOew3FLOH',#5,'T02',$,$,#160,#170,$,2.1,0.9,.DOOR.,$,$);#152is the line’s local id. Other lines point at this door through it.'2O2Fr$t4X7Zf8NOew3FLOH'is the 22-character GlobalId, which stays stable across exports.#5points to the owner history (who created the element, and when).'T02'is the Name. The two$after it are an empty Description and an empty ObjectType.#160, #170point to the placement (where the door sits) and the geometry representation (what it looks like).2.1, 0.9are OverallHeight and OverallWidth, in the project’s units (2.1 m by 0.9 m here)..DOOR.is the PredefinedType enumeration.
Notice what is missing from that line: the fire rating. FireRating lives in a separate property set, Pset_DoorCommon, defined by buildingSMART International and linked to the door by a relationship elsewhere in the file. The script below follows that link for you.
←TODAY: IfcOpenShell 0.9.0 installs with one pip command on Python 3.10–3.15 and reads any IFC4 export.
→3012: The buildings still under repair in Zurich are the ones whose data was written in a format a stranger could read.
Fulcrum: An open text file only becomes infrastructure once ordinary practitioners query it, not just view it.
The Tool: IfcOpenShell is the free, LGPLv3+ toolkit for reading and writing IFC. It is maintained by an open community, and it powers Bonsai (the native-IFC add-on for Blender), IfcTester for IDS checks, and now Bonsai Viewer. For an architect it is worth an afternoon because it turns “the model we received” into data you can count, filter and send back.
Setup: Install Python 3.11 or newer from python.org. Then work inside a fresh virtual environment. If an older ifcopenshell is installed system-wide, Python can import that copy instead of the new one, and the venv rules this out.
mkdir ifc-doors && cd ifc-doors
python -m venv .venv
.venv\Scripts\activate # macOS/Linux: source .venv/bin/activate
pip install ifcopenshell==0.9.0
python -c "import ifcopenshell; print(ifcopenshell.version)"
# expected output: 0.9.0First steps:
- Take a real file: your office’s own IFC export, or any IFC4 file from a current project, whether it came out of an Archicad workflow or a consultant’s tool. Copy it into the folder.
- Save the following as
door_schedule.py. It opens the model, walks every door, readsPset_DoorCommonand the containing storey, and writes a CSV.
import csv, sys
import ifcopenshell
import ifcopenshell.util.element as ue
import ifcopenshell.util.selector as us
model = ifcopenshell.open(sys.argv[1], lazy=True)
print("Schema:", model.schema, "| ifcopenshell", ifcopenshell.version)
rows = []
for d in us.filter_elements(model, "IfcDoor"):
common = ue.get_psets(d).get("Pset_DoorCommon", {})
storey = ue.get_container(d)
rows.append({
"GlobalId": d.GlobalId,
"Name": d.Name,
"Storey": storey.Name if storey else "",
"Width_m": d.OverallWidth,
"FireRating": common.get("FireRating", ""),
"IsExternal": common.get("IsExternal", ""),
})
with open("door_schedule.csv", "w", newline="", encoding="utf-8") as fh:
w = csv.DictWriter(fh, fieldnames=list(rows[0]))
w.writeheader(); w.writerows(rows)
missing = [r["Name"] for r in rows if not r["FireRating"]]
print(f"{len(rows)} doors written; {len(missing)} without FireRating: {missing}")- Run
python door_schedule.py my_model.ifc, then opendoor_schedule.csvin Excel or LibreOffice. The PAZ research desk ran it on 2 October 2026, on Windows with ifcopenshell 0.9.0, against a three-door IFC4 test file. It produced a correct CSV and printed1 without FireRating: ['T02']. - Read the caveats before you trust the numbers.
OverallWidthfollows the file’s project units: metres in that test file, often millimetres in real exports.lazy=Trueis new in 0.9 and has so far only been tested on a small file.
The two helpers doing the real work are documented in the 0.9.0 API reference. According to the ifcopenshell.util.element docs, get_psets retrieves property sets with their properties’ names and values, and get_container returns the spatial structure container, which here is the storey. The same ifcopenshell.util helpers come back in IDS checking with IfcTester and inside Bonsai. That is why the Python track in the PAZ workshops starts from them rather than from syntax drills.
A limitation to keep in mind: the file only tells you what the exporter chose to write. A door without Pset_DoorCommon returns an empty dict, not an error, so “no rating” can mean the rating was never assigned or simply never exported. Either way, it is a question worth sending to the model owner, and now it comes with a GlobalId attached.
Atelier: For a small Zürich studio that coordinates on received IFCs, checking a model no longer requires an authoring seat or a specialist. It requires a venv and about thirty lines that a junior can read with an AI assistant at their side, and that changes who on the team is allowed to ask the model hard questions. Monday move: run door_schedule.py on the last IFC your office sent or received, and email the list of doors without a FireRating to whoever owns the model before the next coordination meeting.
Hack: Ask the selector for the doors that are missing a rating, in one filter string. According to the IfcOpenShell selector syntax docs, property filters take the form Pset.Prop=value, with the operators = != > >= < <= *= !*=. Comparing against NULL with = returns the elements that lack the property, and the docs’ own example uses the inverse, != NULL, to find the elements that have it. Five lines, no loop logic of your own:
import ifcopenshell
import ifcopenshell.util.selector as us
model = ifcopenshell.open("my_model.ifc")
for d in us.filter_elements(model, "IfcDoor, Pset_DoorCommon.FireRating = NULL"):
print(d.GlobalId, d.Name)When that works, try the stretch the docs hint at: swap IfcDoor for IfcWall and Pset_DoorCommon for Pset_WallCommon. The docs show IfcWall, Pset_WallCommon.ThermalTransmittance>1.5 as a U-value filter, which is handy whenever the energy consultant asks.
Learn-it:
- IfcOpenShell v0.9.0 release notes on GitHub. Read the Highlights section; the detail section below it is labelled AI-generated.
- IfcOpenShell-Python installation guide (0.9.0)
- Selector syntax: the filter language behind the Hack
- ifcopenshell.util.element API reference: get_psets, get_container and friends
- ifcopenshell 0.9.0 on PyPI
- A Momo note: keep the script in the project folder, next to the IFC it checked. Next year’s colleague will thank you.
A word from the late 2070s. The buildings that aged badly in my time were not the ugly ones. They were the ones nobody could repair, because the file describing them went dark along with its vendor. An IFC you can read in Notepad and query with LGPL code is the opposite of that. Getting into the habit of querying it now costs one afternoon.
Open the last IFC on your server and ask it which doors have no fire rating.
PAZ Kaffi · multidisciplinary editorial, led by PAZ Academy