Skip to main content

woodwright

A semantic CAD library for woodworking. You describe furniture the way a woodworker thinks about it: boards with named sides, and the joints between them. woodwright works out the joinery, the cut sizes and where every part goes, and produces 3D models (STEP, STL), drawings (SVG) and cut lists.

It is built on build123d. This is an early alpha: the API will still change.

A chair drawn by woodwright The chair taken apart, showing its tenons and mortises
A chair with mortise-and-tenon joints, assembled and exploded: projects.chair in the example library. Every tenon and mortise is derived from the joints between the parts.

Getting started without programming

You don't need to know Python to try woodwright: one small program, uv, installs it with everything it needs, and you then type a few commands.

  1. Open a terminal: Terminal on macOS (in Applications / Utilities), PowerShell on Windows (from the Start menu), any terminal on Linux.

  2. Install uv by pasting this line into it and pressing Enter.

    • macOS and Linux:
      curl -LsSf https://astral.sh/uv/install.sh | sh
      
    • Windows:
      powershell -ExecutionPolicy ByPass -c "irm https://astral.sh/uv/install.ps1 | iex"
      

    Then close the terminal and open a new one.

  3. List the examples, from single joints to whole projects (the first run downloads Python and woodwright, which takes a minute):

    uvx --python 3.14 woodwright list
    
  4. Export one, e.g. a small cabinet door:

    uvx --python 3.14 woodwright export projects.cabinet_door
    

    This makes a folder output/projects/cabinet_door in the folder the terminal is in (your home folder, unless you moved with cd). In it:

    • cut_list.txt – each part with its size and its cuts (tenons, mortises, grooves...), a plain text file;
    • .svg drawings of the whole thing, an exploded view and each part – open them in a web browser;
    • .stl 3D models of the whole thing and each part – open them in any online STL viewer;
    • assembled.step – the 3D model for CAD programs such as the free FreeCAD, which opens the .stl files too.
  5. Make your own: in a plain text editor (TextEdit set to plain text, Notepad, ...) write a file my_door.py with the sizes you want:

    from woodwright.examples import projects
    
    door = projects.cabinet_door(height=700, width=450)
    

    and export it, in the folder where you saved it:

    uvx --python 3.14 woodwright export my_door.py
    

    The results are in output/my_door/door. What each example can change (sizes, stock thickness...) is listed at the top of its code in the example library; copying an example's code into your file is the way on to your own designs.

To update woodwright later, write woodwright@latest instead of woodwright once. If you use an AI coding assistant (e.g. Claude Code), you can also ask it to do all of this for you.

Installation

pip install woodwright  # or: uv add woodwright

Requires Python 3.14. The woodwright command lists and exports the examples and your own design files (woodwright --help). Source: https://github.com/bzamecnik/woodwright

Quickstart

A rail tenoned into a stile. You give the design dimensions and the joint; the tenon, the mortise, the rail's cut length and its placement are derived.

from pathlib import Path

import woodwright as ww
from woodwright.export import export_model

oak = ww.Stock.board(thickness=20, species="oak")

frame = ww.Assembly("corner", root_location=ww.orient(right_end=ww.UP, back_edge=ww.RIGHT))
stile = frame.add(ww.Board("stile", oak, length=600, width=60))
rail = frame.add(ww.Board("rail", oak, length=300, width=60))  # shoulder to shoulder
frame.join(ww.MortiseTenon(tenon=rail.left_end, mortise=stile.back_edge))

model = frame.resolve()
print(model.cut_list())
export_model(model, Path("output/corner"))  # STEP, STL, SVG views, cut list
stile  600 x 60 x 20 mm  oak
       - mortise 50 x 8 mm, 42 deep, in stile.back_edge
rail   340 x 60 x 20 mm  oak
       - tenon 50 x 8 mm, 40 long, on rail.left_end

What's there so far:

  • Cuts: grooves, dados and rabbets (through or stopped), mortises, slot mortises, tenons (haunched, mitred, chamfered, multiple side by side or across the thickness, wedged), tongues, dovetail tongues and laps, chamfers, mitres (across the face, the edge, or along the grain), tapers.
  • Joints: butt (also turned at an angle); dado, rabbet, groove and tongue and groove housings (also stopped); mortise and tenon (blind, through, stub, haunched, mitred, with mitred shoulders, multiple, wedged, tusk); loose tenons and loose tongues; bridles (L and T); half laps (plain, dovetailed, mitred), cross laps, mitred face tenons; box joints; sliding, through, half-blind, mitred-corner and blind mitred dovetails; mitre corners and splices; table-top buttons.

Example library

woodwright.examples holds over ninety examples, from single cuts through joints to projects: a try square, a mallet, a bookshelf, a dovetailed drawer with a bottom, a dining table, a side table, a chair, a step stool seat, ledged and frame-and-panel doors, a small glazed cabinet door.

woodwright list
woodwright export projects.chair --out output

The design ideas are in docs/vision.md and docs/plan.md.

Development

Install the environment and dependencies:

uv sync
pre-commit install  # ruff lint + format on commit

Optionally, for notebooks with an interactive 3D viewer:

uv sync --group notebook
uv run jupyter lab

Run the tests and the linters:

uv run pytest
uv run ruff format
uv run ruff check --fix

License

MIT License.

Credits

  • Ideas and guidance: Bohumír Zámečník
  • Most of the implementation: Claude Code (Opus 5.5)

Metadata

Release files for woodwright 0.3.0

For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.

Source distribution (sdist)

Source distribution for woodwright 0.3.0
File Size Uploaded Provenance
woodwright-0.3.0.tar.gz 141.5 kB Without provenance Details

Built distribution (wheel)

Table of built distributions (wheels) for woodwright 0.3.0
File Interpreter ABI Platform
woodwright-0.3.0-py3-none-any.whl Python 3 none any Details

Total release size: 223.9 kB

Release files / woodwright-0.3.0.tar.gz

Download URL woodwright-0.3.0.tar.gz
Size 141.5 kB
Tags Source
SHA-256 checksum
How to use checksums
e637899421d9fd5d8e458c10a1f9ebabd4028893f9d96de5fb5e77247466aa63
BLAKE2b-256 checksum
How to use checksums
27a89268eee47cc1fe79cd6cc2ce9e549057168280a5a36a32ad9076e3ce5bae
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via uv/0.13.1 {"installer":{"name":"uv","version":"0.13.1","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"macOS","version":null,"id":null,"libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":null}

Release files / woodwright-0.3.0-py3-none-any.whl

Download URL woodwright-0.3.0-py3-none-any.whl
Size 82.5 kB
Tags Python 3
SHA-256 checksum
How to use checksums
5f5b5d93423423b04c4bebc666e04f42bf1544d1260601751ae3c5874a769dbd
BLAKE2b-256 checksum
How to use checksums
fe36bf1ffeeebdea90aa67879c62eb6d6bfcf7ea32c34cb415981c3f2fb61d34
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via uv/0.13.1 {"installer":{"name":"uv","version":"0.13.1","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"macOS","version":null,"id":null,"libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":null}

Security for woodwright 0.3.0

Provenance

Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.

No provenance found

None of the files in this release were uploaded with provenance metadata.

A note on package security

PyPI is a repository for distributing packages, not a service for auditing them. While third-party security researchers and our staff do their best to detect and remove malicious packages, PyPI cannot guarantee the quality, security or suitability of any given package.

Anthropic, PBC Visionary sponsor Bloomberg Visionary sponsor Hudson River Trading Visionary sponsor Meta Visionary sponsor NVIDIA Visionary sponsor Microsoft Sustainability sponsor Depot Continuous Integration AWS Cloud computing and Security Sponsor Datadog Monitoring Fastly CDN Google Download Analytics Sentry Error logging StatusPage Status page