Port Allocation
Stackie automatically assigns host ports to each block’s services so they
don’t collide. Ports are persisted between runs — restarting a stack
gives you the same ports unless a conflict forces reallocation.
How It Works
On first stackie up, Stackie picks free ephemeral ports (32768-65535)
for every block service and saves them to ~/.stackie/stacks/{stack}/ports.lock.
On subsequent runs, Stackie bind-tests every saved port. If all are still
free, they are reused. If any are taken, all ports are reallocated together
to keep cross-block references consistent.
no yes yes no Expose stable service ports
Stackie flowchart: #stackie-mermaid-0{font-family:Inter Variable,Inter,ui-sans-serif,system-ui,-apple-system,BlinkMacSystemFont,Segoe UI,sans-serif;font-size:16px;fill:#f8fafc;}@keyframes edge-animation-frame{from{stroke-dashoffset:0;}}@keyframes dash{to{stroke-dashoffset:0;}}#stackie-mermaid-0 .edge-animation-slow{stroke-dasharray:9,5!important;stroke-dashoffset:900;animation:dash 50s linear infinite;stroke-linecap:round;}#stackie-mermaid-0 .edge-animation-fast{stroke-dasharray:9,5!important;stroke-dashoffset:900;animation:dash 20s linear infinite;stroke-linecap:round;}#stackie-mermaid-0 .error-icon{fill:#111827;}#stackie-mermaid-0 .error-text{fill:#f8fafc;stroke:#f8fafc;}#stackie-mermaid-0 .edge-thickness-normal{stroke-width:1px;}#stackie-mermaid-0 .edge-thickness-thick{stroke-width:3.5px;}#stackie-mermaid-0 .edge-pattern-solid{stroke-dasharray:0;}#stackie-mermaid-0 .edge-thickness-invisible{stroke-width:0;fill:none;}#stackie-mermaid-0 .edge-pattern-dashed{stroke-dasharray:3;}#stackie-mermaid-0 .edge-pattern-dotted{stroke-dasharray:2;}#stackie-mermaid-0 .marker{fill:#facc15;stroke:#facc15;}#stackie-mermaid-0 .marker.cross{stroke:#facc15;}#stackie-mermaid-0 svg{font-family:Inter Variable,Inter,ui-sans-serif,system-ui,-apple-system,BlinkMacSystemFont,Segoe UI,sans-serif;font-size:16px;}#stackie-mermaid-0 p{margin:0;}#stackie-mermaid-0 .label{font-family:Inter Variable,Inter,ui-sans-serif,system-ui,-apple-system,BlinkMacSystemFont,Segoe UI,sans-serif;color:#f8fafc;}#stackie-mermaid-0 .cluster-label text{fill:#f8fafc;}#stackie-mermaid-0 .cluster-label span{color:#f8fafc;}#stackie-mermaid-0 .cluster-label span p{background-color:transparent;}#stackie-mermaid-0 .label text,#stackie-mermaid-0 span{fill:#f8fafc;color:#f8fafc;}#stackie-mermaid-0 .node rect,#stackie-mermaid-0 .node circle,#stackie-mermaid-0 .node ellipse,#stackie-mermaid-0 .node polygon,#stackie-mermaid-0 .node path{fill:#1f2937;stroke:#facc15;stroke-width:1px;}#stackie-mermaid-0 .rough-node .label text,#stackie-mermaid-0 .node .label text,#stackie-mermaid-0 .image-shape .label,#stackie-mermaid-0 .icon-shape .label{text-anchor:middle;}#stackie-mermaid-0 .node .katex path{fill:#000;stroke:#000;stroke-width:1px;}#stackie-mermaid-0 .rough-node .label,#stackie-mermaid-0 .node .label,#stackie-mermaid-0 .image-shape .label,#stackie-mermaid-0 .icon-shape .label{text-align:center;}#stackie-mermaid-0 .node.clickable{cursor:pointer;}#stackie-mermaid-0 .root .anchor path{fill:#facc15!important;stroke-width:0;stroke:#facc15;}#stackie-mermaid-0 .arrowheadPath{fill:rgba(255, 255, 255, 0);}#stackie-mermaid-0 .edgePath .path{stroke:#facc15;stroke-width:1px;}#stackie-mermaid-0 .flowchart-link{stroke:#facc15;fill:none;}#stackie-mermaid-0 .edgeLabel{background-color:#171717;text-align:center;}#stackie-mermaid-0 .edgeLabel p{background-color:#171717;}#stackie-mermaid-0 .edgeLabel rect{opacity:0.5;background-color:#171717;fill:#171717;}#stackie-mermaid-0 .labelBkg{background-color:rgba(23, 23, 23, 0.5);}#stackie-mermaid-0 .cluster rect{fill:#111827;stroke:#2dd4bf;stroke-width:1px;}#stackie-mermaid-0 .cluster text{fill:#f8fafc;}#stackie-mermaid-0 .cluster span{color:#f8fafc;}#stackie-mermaid-0 div.mermaidTooltip{position:absolute;text-align:center;max-width:200px;padding:2px;font-family:Inter Variable,Inter,ui-sans-serif,system-ui,-apple-system,BlinkMacSystemFont,Segoe UI,sans-serif;font-size:12px;background:#111827;border:1px solid #2dd4bf;border-radius:2px;pointer-events:none;z-index:100;}#stackie-mermaid-0 .flowchartTitleText{text-anchor:middle;font-size:18px;fill:#f8fafc;}#stackie-mermaid-0 rect.text{fill:none;stroke-width:0;}#stackie-mermaid-0 .icon-shape,#stackie-mermaid-0 .image-shape{background-color:#171717;text-align:center;}#stackie-mermaid-0 .icon-shape p,#stackie-mermaid-0 .image-shape p{background-color:#171717;padding:2px;}#stackie-mermaid-0 .icon-shape .label rect,#stackie-mermaid-0 .image-shape .label rect{opacity:0.5;background-color:#171717;fill:#171717;}#stackie-mermaid-0 .label-icon{display:inline-block;height:1em;overflow:visible;vertical-align:-0.125em;}#stackie-mermaid-0 .node .label-icon path{fill:currentColor;stroke:revert;stroke-width:revert;}#stackie-mermaid-0 .node .neo-node{stroke:#facc15;}#stackie-mermaid-0 [data-look="neo"].node rect,#stackie-mermaid-0 [data-look="neo"].cluster rect,#stackie-mermaid-0 [data-look="neo"].node polygon{stroke:url(#stackie-mermaid-0-gradient);filter:drop-shadow( 1px 2px 2px rgba(185,185,185,1));}#stackie-mermaid-0 [data-look="neo"].swimlane.cluster rect{filter:none;}#stackie-mermaid-0 [data-look="neo"].node path{stroke:url(#stackie-mermaid-0-gradient);stroke-width:1px;}#stackie-mermaid-0 [data-look="neo"].node .outer-path{filter:drop-shadow( 1px 2px 2px rgba(185,185,185,1));}#stackie-mermaid-0 [data-look="neo"].node .neo-line path{stroke:#facc15;filter:none;}#stackie-mermaid-0 [data-look="neo"].node circle{stroke:url(#stackie-mermaid-0-gradient);filter:drop-shadow( 1px 2px 2px rgba(185,185,185,1));}#stackie-mermaid-0 [data-look="neo"].node circle .state-start{fill:#000000;}#stackie-mermaid-0 [data-look="neo"].icon-shape .icon{fill:url(#stackie-mermaid-0-gradient);filter:drop-shadow( 1px 2px 2px rgba(185,185,185,1));}#stackie-mermaid-0 [data-look="neo"].icon-shape .icon-neo path{stroke:url(#stackie-mermaid-0-gradient);filter:drop-shadow( 1px 2px 2px rgba(185,185,185,1));}#stackie-mermaid-0 :root{--mermaid-font-family:Inter Variable,Inter,ui-sans-serif,system-ui,-apple-system,BlinkMacSystemFont,Segoe UI,sans-serif;}, yes, stackie up, ports.lock, exists?. Use horizontal scrolling when the full diagram is wider than the visible frame. Generated from Stackie public documentation source.
Pinning a Port
To lock a service to a specific port, set it in your stack file:
my-project :
blocks :
stackie.postgres :
serves :
PORT :
port : 5432
Any port below the ephemeral range (< 32768) and above zero is treated
as pinned — it is never reallocated and always overrides the lock file.
Port 0 means “let Stackie pick for me” (the default).
Blast Radius
The ports.lock file only stores port numbers — no secrets. Deleting or
corrupting it causes a fresh allocation on the next stackie up but does
not affect running processes.