2 min read

STEP to STL: How to batch convert STEP files to STL files with Python and Docker

I had a project recently, where I had to make a data pipeline for all files coming from a PDM (Product Data Management) system. The engineering and documentation teams used the PDM system to update revisions or add revisions of 3D files and product documentation. My data pipeline had to retrieve the latest revisions of all the approved files and transfer them to a customer/distributor portal, where it could be downloaded or viewed. The problem with STEP files are, that they are not really that web-friendly. I wanted some way to also display a preview of the STEP file of the product via the web portal.

I searched for some batch 3D convert solutions, but all of them are either part of a full-blown CAD-Suite, or some one-by-one online converter. Then I came across a free solution called FreeCAD. I tested it out on both Windows and Linux, and wanted to containerize it to make it part of my data scheduling jobs. Luckily there's already a Docker image available, which I just used, together with a little bit of python to convert the 3D STEP files to STL files.

python
step_to_stl.py
from pathlib import Path
import FreeCAD
import Part
import Mesh
import sys
def get_files(path, extensions):
all_files = []
for ext in extensions:
all_files.extend(path.glob(ext))
return all_files
path = Path.cwd().joinpath('convert')
stepfiles = get_files(path, ('*.[sS][tT][eE][pP]', '*.[sS][tT][pP]'))
stlfiles = get_files(path, ('*.[sS][tT][lL]',))
if not stepfiles:
print("No step files found in the given folder")
sys.exit()
stlstems = [i.stem for i in stlfiles]
processfiles = [i for i in stepfiles if i.stem not in stlstems]
print("Processing files:")
for f in processfiles:
print(f.name)
filename = f'{f.parent}/{f.name}'
shape = Part.Shape()
shape.read(filename)
doc = App.newDocument('Doc')
pf = doc.addObject("Part::Feature", "STEPpreview")
pf.Shape = shape
stl = f'{f.parent}/{f.stem}.stl'
Mesh.export([pf], stl)
print(f'{f.stem}.stl Generated')

Nothing fancy. We are simply listing the STEP files in the directory with pathlib, and using the FreeCAD library to import each STEP file and export a STL file.

To make it easy to use, we could also make a docker-compose file

yml
version: '3.9'
services:
converter:
image: amrit3701/freecad-cli:latest
volumes:
- ./convert:/app/convert
- ./step_to_stl.py:/app/step_to_stl.py
working_dir: /app
command: [python3, step_to_stl.py]

and execute with docker-compose up

Or just run it with docker

bash
docker run -v $PWD/convert:/app/convert -v $PWD/step_to_stl.py:/app/step_to_stl.py -w /app amrit3701/freecad-cli:latest python3 step_to_stl.py

If you just want to get the full source code, it's available on my Github.

© 2022 Jacques du Preez. All rights reserved.