Skip to main content

onescad

Bundle an OpenSCAD model into one self-contained, Customizer-ready .scad file.

uvx onescad model.scad -o dist/model.scad

The bundle renders identically to the source, keeps the Customizer's parameters, groups, and widgets, and carries the license text of every file it takes code from. Python 3.11 or newer; no runtime dependencies.

Usage

onescad INPUT -o OUTPUT [-L DIR]... [--minify] [--verify] [--version]
Option Meaning
INPUT The model's .scad file.
-o, --output The bundle to write. Parent directories are created.
-L, --library DIR A directory to search for include and use; repeatable.
--minify Strip comments and indentation after the Customizer parameters.
--verify Render the source and the bundle with openscad and compare them.
--version Print the version.

Warnings print to stderr as onescad: warning: <message>. Errors print as onescad: <message>.

Exit code Meaning
0 The bundle was written (and verified, with --verify).
1 The bundle could not be built or verified.
2 Usage error.

Search path

include and use are resolved in this order: the including file's directory, each -L directory, each OPENSCADPATH entry, then OpenSCAD's user library directory (~/Documents/OpenSCAD/libraries on macOS, %USERPROFILE%\Documents\OpenSCAD\libraries on Windows, ~/.local/share/OpenSCAD/libraries elsewhere). OpenSCAD's installation library (for example MCAD) is not searched; put it on -L or OPENSCADPATH. A missing file is an error that lists the directories searched.

What gets bundled

The output has these parts, in order:

  1. A header of // comments:
    • the onescad version, marked as generated;
    • the source path relative to its git root, the remote as an https URL, and the commit, with +dirty when tracked files have uncommitted changes (omitted outside a git work tree with a commit);
    • the main file's leading comment;
    • the fonts named by font= strings, the files read by import() or surface(), and a note naming the presets file, when they apply;
    • for each license file covering code that was kept, its directory and its text verbatim. The license file is the nearest LICENSE*, LICENCE*, or COPYING* in an ancestor directory of each source file.
  2. The Customizer parameters, hoisted to the top.
  3. A /* [Hidden] */ marker, so nothing after it appears in the Customizer.
  4. Each used file's definitions, dependencies first, each preceded by a // onescad: <path> marker and the file's leading comment.
  5. The main file, with its included files spliced in.

--minify removes comments, blank lines, and indentation from parts 4 and 5, keeping one line break where the source had any; on BOSL2 it cuts the bundle by about two thirds. The header and the Customizer parameters are kept, so the licenses and the Customizer's descriptions survive. Identifiers are not renamed.

The output has no timestamps, so the same input gives byte-identical output.

Definitions that the model never reaches are dropped. A definition is renamed (name__1) when keeping its name would capture a different reference, as when a library wraps a builtin it later overrides.

Presets

If model.json sits next to model.scad, onescad copies it verbatim to the output's name with a .json extension (dist/model.json for -o dist/model.scad). OpenSCAD loads presets only from a .json beside the .scad, so keep the two together. A warning names each preset key that is not a Customizer parameter of the bundle.

Verification

--verify needs openscad on PATH. It compares the source with the bundle on:

  • the CSG of the default parameters and of every preset;
  • the ECHO lines, after undoing renames;
  • the Customizer parameter set (-o x.param, ignoring title).

The bundle renders with OPENSCADPATH unset and an empty HOME, which proves it is self-contained. text() fonts are not compared. Verifying needs an OpenSCAD that can export param (the 2026.09 snapshots do; 2021.01 is untested).

Limitations

  • The Customizer is emulated, not run. A model whose parameter assignment reads a name before that name's first assignment cannot be hoisted; onescad stops with an error.
  • A top-level $ variable in a used file, conflicting definitions that cannot be renamed, and a rename that would split a call's possible targets are errors.
  • A top-level variable in a used file is evaluated once in the bundle, not on every call as OpenSCAD does; onescad warns.
  • import() and surface() still read their files at render time; onescad warns and lists them in the header. Relative paths then resolve against wherever the bundle is rendered.
  • Fonts are not embedded; the header lists those that font= names.
  • A model's license text appears in the header only when a license file covers its source. onescad warns about each source file with none.

License

MIT. See LICENSE. Bundles carry the licenses of their inputs; check them before redistributing.

Metadata

Release files for onescad 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 onescad 0.3.0
File Size Uploaded
onescad-0.3.0.tar.gz 336.6 kB Details

Built distribution (wheel)

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

Total release size: 374.0 kB

Release files / onescad-0.3.0.tar.gz

Download URL onescad-0.3.0.tar.gz
Size 336.6 kB
Tags Source
SHA-256 checksum
How to use checksums
60928aa58333c08b1af5a06bc780f01cd17504d4781b4fd3664850ae4f37612a
BLAKE2b-256 checksum
How to use checksums
1d026f694424bc58eaa1643e76a83fefba0fc226b323522aeff8c4733877a122
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
Yes
Uploaded via twine/7.0.0 CPython/3.13.14

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.

PyPI Publish Attestation

PyPI verified that this artifact, at this checksum, originated from the publisher listed below.

Signed by GitHub Actions, verified by PyPI on Oct 5, 2026.

Transparency log

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

Download URL onescad-0.3.0-py3-none-any.whl
Size 37.4 kB
Tags Python 3
SHA-256 checksum
How to use checksums
7f659ffb490473fb81b49e7b85e01f6edb07e7e440382caf044fb36e057bb364
BLAKE2b-256 checksum
How to use checksums
7764f9191a4db805f8e8f88e4eddb14e3b9c7fb107d927416bb5192cbe458e68
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
Yes
Uploaded via twine/7.0.0 CPython/3.13.14

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.

PyPI Publish Attestation

PyPI verified that this artifact, at this checksum, originated from the publisher listed below.

Signed by GitHub Actions, verified by PyPI on Oct 5, 2026.

Transparency log

Release history Release notifications | RSS feed

This release

0.3.0 This release

2 release files

0.2.0

2 release files

0.1.0

2 release files

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