Skip to content

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

26 Commits
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

render

English | Polski

CI Latest release Downloads

Latest downloads: macOS Apple Silicon · Windows x64 · Windows ARM64

Image-generation tools such as ComfyUI are extremely powerful, but producing a first image can mean choosing a backend, assembling nodes and workflows, configuring pipelines and model components, and understanding dozens of generation options. render was created to provide a simpler starting point: set up the engine, pull a compatible model, and generate an image from a prompt.

It is not intended to replace advanced visual tools. It deliberately offers a narrow, predictable CLI path — setuppullrun — that works locally or with a remote GPU server, without requiring a workflow to be designed first.

The current version can:

  • fetch a model catalog from the public ComfyUI-Manager registry;
  • install and update models from Hugging Face;
  • classify checkpoints, diffusion models, and supporting assets;
  • prevent LoRA, text encoder, ControlNet, and VAE files from being launched as standalone models;
  • generate images locally with sd-cli;
  • run a sequence of generations for multiple seeds;
  • embed the prompt and generation parameters in image metadata;
  • pass an optional negative prompt locally or to a remote server;
  • operate as an HTTP server and remote client;
  • cancel active remote inference when Ctrl+C is pressed.

Supported platforms

The CLI is written in Go 1.22. Automatic engine setup and execution are currently supported on:

  • macOS on Apple Silicon (darwin/arm64, Metal);
  • Windows (amd64 or arm64; Vulkan by default, with CPU and CUDA packages available as alternatives).

Linux does not yet have a backend configured in ResolveEngine or support in the setup command.

Quick start

From the repository directory:

go build -o render .
./render setup
./render list --only-runnable
./render pull sd_xl_base_1.0
./render run sd_xl_base_1.0 "photograph of a modern street in Warsaw"

On Windows:

go build -o render.exe .
.\render.exe setup
.\render.exe list --only-runnable
.\render.exe pull sd_xl_base_1.0
.\render.exe run sd_xl_base_1.0 "photograph of a modern street in Warsaw"

CLI commands

render setup
render help
render <command> --help
render version
render --version
render -v
render pull [--alias <filename>] <model-name|http(s)-url>
render run [options] <model-name-or-alias> "<prompt>"
render list [options] [filter]
render serve [port]
render <command> --remote <host:port> [options]

Running render without arguments prints a quick usage summary. Use render help, --help, or -h for the full reference, and render <command> --help for command-specific help.

render version, --version, and -v print version information. --verbose is a global option and can be placed before or after the command. By default, the CLI shows progress, warnings, cancellation messages, and final results. Verbose mode additionally prints native sd-cli output, remote connection banners, and HTTP access logs when running a server:

./render run --verbose sd_xl_base_1.0 "modern Warsaw street"
./render serve --verbose

Native engine output may contain the prompt and local file paths. Review it before sharing a verbose log publicly.

Model listing and classification

The local list command makes an anonymous HTTP GET request to the public ComfyUI-Manager manifest. Only entries with a public https://huggingface.co/... URL are added to the catalog. The application does not send a token or an Authorization header.

The upstream registry contains assets for many applications and pipelines. render list therefore applies a conservative compatibility allowlist before showing download candidates. A registry entry is marked RUNNABLE: YES only when it is a self-contained SD 1.x/1.5, SD 2.x, or SDXL checkpoint stored as .safetensors or .ckpt. This matches the application's current inference path, which supplies one model file to sd-cli using --model.

Compatibility at a glance:

Model or asset Listed by default Current support
Complete SD 1.x / SD 1.5 checkpoint Yes Supported
Complete SD 2.x checkpoint Yes Supported
Complete SDXL text-to-image checkpoint (including base or Turbo) Yes Supported
SDXL refiner, inpainting UNet, or unCLIP model No Requires a pipeline the application does not expose
FLUX, SD3, Stable Cascade, video, or other architecture No Not supported by the current single-file pipeline
LoRA, ControlNet, VAE, text encoder, AnimateDiff/motion model No Supporting component, not a standalone model
.gguf, .bin, .pth, .pt, archive, or unknown format No Not accepted as a standalone model by this integration

--all remains available for inspecting the unfiltered upstream catalog. It does not mean that every displayed entry can be run. --type likewise exposes all entries of a category for diagnostics.

./render list
./render list sdxl
./render list --installed
./render list --updatable
./render list --all
./render list --type checkpoint
./render list --type text-encoder
./render list --only-runnable

Listing options:

Option Description
--all Shows the full upstream catalog, including incompatible assets.
--type <category> Filters by model category.
--only-runnable Shows standalone checkpoints only.
--installed, -i Shows models present in the local manifest.
--updatable, -u Shows installed models for which the registry has a newer version.
[filter] An optional single text filter.

Supported categories are CHECKPOINT, DIFFUSION_MODEL, TEXT_ENCODER, LORA, CONTROLNET, VAE, and the technical category UNKNOWN. The table contains these columns:

STATUS | MODEL NAME | CATEGORY | RUNNABLE | SIZE | VERSION

RUNNABLE values mean:

  • YES — a compatible complete checkpoint that can be passed to sd-cli;
  • PARTIAL — a standalone diffusion component, such as a FLUX GGUF, that requires a separate text encoder and VAE;
  • NO — a supporting or unrecognized asset.

Classification uses application metadata, registry data, the filename, and — for local Safetensors files — keys found in the file header. Older manifests without classification fields remain supported.

By default, download candidates are limited to RUNNABLE: YES, while every installed model remains visible as part of the local or remote inventory. Consequently an installed PARTIAL or NO entry is shown, but the same entry is not offered as an available download. --only-runnable limits both groups to YES; --all or an explicit --type exposes incompatible downloads too.

The check intentionally favors false negatives over multi-gigabyte downloads that cannot run. Registry metadata cannot prove that every tensor inside a remote file is valid, so Safetensors downloaded from a direct URL are inspected before being recorded. A newer engine may support more architectures, but they remain hidden until the application exposes the command-line components required to run them.

The table prefers the local file size, then the registry value. If neither is available, it makes an anonymous HTTP HEAD request with a one-second timeout. Long model names and versions are truncated to keep terminal columns aligned.

The registry response is cached in cache/remote_models.json. If the registry is unavailable, the application prints a warning and uses the latest valid cache. The registry download timeout is five seconds.

Downloading and updating models

./render pull <alias|name|filename>
./render pull "https://civitai.com/api/download/models/12345"
./render pull --alias realvisxl_v4.safetensors \
  "https://huggingface.co/user/repository/resolve/main/model.safetensors"

pull first looks for an exact alias, name, or filename. A partial match is accepted only when it identifies a single entry; otherwise, the CLI displays a list of suggestions.

If the argument starts with http:// or https://, pull downloads it directly without consulting the application registry. The destination filename is selected in this order: --alias, the response's Content-Disposition filename, the final URL after redirects, and the original URL. An alias without an extension inherits the detected extension. Unsafe paths are rejected.

The file is downloaded to models/<filename>.tmp and then moved into place. An interrupted download can be resumed with an HTTP Range request. If the server does not honor Range, the download safely restarts from the beginning. An up-to-date model is not downloaded again, while an older version is replaced. The progress display includes transferred bytes, percentage, transfer rate, elapsed time, and estimated time remaining; the same output is streamed by a remote server.

After a direct download, Safetensors metadata is read from the JSON header without loading tensor data. The application detects the category, runnability, and model family (SD1.5, SDXL, FLUX, and other recognized families). An invalid file advertised as .safetensors is rejected instead of being registered as a checkpoint.

After a successful installation, models/installed.json stores the name, alias, version, filename, installation time, category, runnability, and required components, among other fields.

Generating images

./render run <alias|name|filename> "<prompt>"
./render run --negative-prompt "blurry, artifacts, text" \
  sd_xl_base_1.0 "modern Warsaw street"
./render run --steps 30 --cfg-scale 7 --width 1024 --height 1024 \
  --vae-tiling --seed 849204912 sd_xl_base_1.0 "modern Warsaw street"
./render run -s 101,202,303 sd_xl_base_1.0 "modern Warsaw street"

run options:

Option Short Description
--negative-prompt <text> -n Optional concepts and defects to avoid.
--steps <n> Number of steps; must be positive.
--cfg-scale <n> -c CFG scale; must be non-negative.
--width <px> -W Image width; must be positive.
--height <px> -H Image height; must be positive.
`--vae-tiling[=true false]`
--seed <n[,n...]> -s One seed or a comma-separated list without spaces.

A model can be selected by its exact name, alias, filename, or filename without the extension recorded in installed.json.

Before starting the backend, the application validates the model category:

  • CHECKPOINT is allowed to run;
  • TEXT_ENCODER, LORA, CONTROLNET, VAE, and UNKNOWN produce a clear error before the C++ process starts;
  • DIFFUSION_MODEL produces a message explaining that a text encoder and VAE are required.

The current version cannot yet assemble a complete pipeline from a separate diffusion model, T5/CLIP encoder, and VAE.

Default parameters

  • models whose names contain turbo or lightning: 4 steps and CFG 1.0;
  • other models: 20 steps and CFG 7.0;
  • SDXL: 1024x1024 with VAE tiling enabled;
  • other models: 512x512 with VAE tiling disabled;
  • sampler: euler for FLUX/SD3/Wan families, euler_a otherwise;
  • seed: a random nine-digit value if --seed is omitted or negative.

Explicit options always take precedence over defaults.

Multiple seeds

--seed 101,202,303 runs three sequential generations with the same model, positive prompt, negative prompt, and remaining parameters. Before each generation, the CLI prints:

[1/3] Generating image for seed = 101...

Each result is stored in a separate file named as follows:

YYYYMMDD_HHMMSS_<short-model>_s<seed>.png

For example: 20260803_153012_sdxl_s849204912.png.

Output files and metadata

The run command currently writes PNG images to the output/ directory next to models/. After inference, the application preserves the parameters chunk produced by stable-diffusion.cpp and adds:

  • ImageDescription / XPTitle — the prompt;
  • UserComment / XPComment — model, steps, CFG, seed, sampler, and the negative prompt when provided;
  • Software / XPAuthorrender;
  • PNG text fields Title, Description, Comment, Software, and Author.

XP fields and UserComment use UTF-16LE, so non-ASCII characters display correctly in places such as Windows Properties → Details. The internal metadata writer also supports JPEG (APP1/Exif) and WebP (EXIF/VP8X), although the current run command requests PNG output from the backend.

Engine setup and selection

./render setup

On macOS, setup requires Apple Silicon. It downloads the Darwin ARM64 archive from the latest stable-diffusion.cpp release, verifies SHA-256 when a digest is published, and installs sd-cli with its libraries as bin/sd-cli-darwin.

On Windows, the command selects an archive for the current architecture and backend. The default backend is Vulkan:

$env:RENDER_WIN_BACKEND = "cuda12" # e.g. vulkan, cpu, cuda12
.\render.exe setup

If the engine file already exists, setup does not download it again. On macOS, the engine can also be built locally:

./scripts/build-engine-mac.sh

During run, the application first checks the shared RENDER_BINARY environment variable, then the platform-specific variable, and finally the default path next to the executable.

Server mode and remote client

Start the server with the serve command:

./render serve
./render serve 8080

Stop the server with Ctrl+C. In an interactive terminal you can also type q and press Enter. Shutdown first waits briefly for active HTTP requests and then closes any remaining connections.

Caution

The server is not secured: it has no authentication, authorization, or TLS. The default address :11434 may make it reachable from other machines on the network. Anyone who can connect can inspect installed models, ask the server to download arbitrary HTTP(S) URLs, install the engine, start resource-heavy generation jobs, and cancel active jobs. Never expose it directly to the public internet. Use it only on a trusted private network, restrict access with a firewall or bind it to localhost (render serve 127.0.0.1:11434), or place it behind a reverse proxy that provides TLS and authentication. Enable remote access only when you understand and accept these risks.

Endpoints:

Method and path Description
GET /api/list Returns the server's available catalog and installed models.
POST /api/pull Downloads a model; progress is streamed as SSE.
POST /api/run Generates one PNG for one seed.
POST /api/cancel Cancels the active job identified by job_id.
POST /api/setup Installs the engine; progress is streamed as SSE.

POST /api/run returns image/png or, after CLI content negotiation, multipart/mixed containing progress messages followed by the final PNG. The server passes the cancelled context to exec.CommandContext, which terminates the active sd-cli process. Its optional JSON field negative_prompt maps to the native sd-cli --negative-prompt argument.

Remote client examples:

./render list --remote 192.168.1.50:11434
./render pull --remote 192.168.1.50:11434 sd_xl_base_1.0
./render pull --remote 192.168.1.50:11434 --alias custom.safetensors \
  "https://civitai.com/api/download/models/12345"
./render run --remote 192.168.1.50:11434 --steps 30 \
  --seed 101,202,303 sd_xl_base_1.0 "modern Warsaw street"

In remote mode, the client coordinates the seed list: it sends a separate /api/run request for every seed and saves every PNG locally. Each request has a random job_id. Ctrl+C sends /api/cancel with a short timeout, terminates the active server process, skips remaining seeds, and exits the client with code 130.

The server address can also be set with RENDER_HOST; an explicit --remote takes precedence. Remote list uses the server's online catalog and installation manifest, so the normal compatibility, --installed, and --updatable filters work the same way as in local mode. If the registry is unavailable, the server uses its latest valid cache and the client prints a warning. Models installed from a direct URL or another source remain visible even when they have no matching online-catalog entry. New clients remain compatible with older installed-only servers.

With --verbose, the server logs the start and end of every request to stderr, including method, endpoint, client address, status, byte count, and duration. Prompt content is not logged. Because the API can download arbitrary HTTP(S) URLs and has no authentication, it must only be exposed to trusted clients.

Files and configuration

Typical data layout next to the application:

bin/                         sd-cli binary and libraries
cache/remote_models.json     latest valid model-catalog cache
models/installed.json        local installation manifest
models/*                     downloaded model files
output/*.png                 generated images

Important environment variables:

Variable Description
RENDER_MANIFEST Explicit path to installed.json.
RENDER_REGISTRY_CACHE Explicit path to the online catalog cache.
RENDER_HOST Default remote-client address.
RENDER_BINARY Shared path to an existing sd-cli.
RENDER_DARWIN_BINARY Engine path on macOS.
RENDER_WIN_BINARY Engine path on Windows.
RENDER_WIN_BACKEND Windows package backend; vulkan by default.
RENDER_DARWIN_DOWNLOAD_URL Direct URL of the macOS archive.
RENDER_WIN_DOWNLOAD_URL Direct URL of the Windows archive.
RENDER_WINDOWS_DOWNLOAD_URL Legacy alias for the Windows archive URL.
RENDER_RELEASES_API_URL Alternative GitHub Releases API endpoint.

Relative paths stored in the manifest are resolved against the directory that contains installed.json. Default locations are based on the current directory or the location of the running binary; in custom environments, setting RENDER_MANIFEST explicitly is recommended.

Building and testing

go build -trimpath -ldflags=-s -o render .
go test ./...
go vet ./...

A local build reports the dev version and, when available, its Git revision. Set the release version at build time without changing the source:

go build -trimpath -ldflags "-s -X render/cmd.Version=v0.1.0" -o render .
./render --version

Tests cover CLI parsing, model classification, downloads, inference, PNG/JPEG/WebP metadata, the HTTP API, multiple seeds, Ctrl+C, and remote process cancellation. Run client and server concurrency tests with:

go test -race ./client ./cmd ./server

Continuous integration and releases

GitHub Actions runs go vet, the complete test suite, and macOS/Windows build checks for every push and pull request targeting main.

Pushing a tag whose name starts with v creates a corresponding GitHub Release with downloadable files:

  • render-darwin-arm64 for macOS on Apple Silicon;
  • render-windows-amd64.exe for 64-bit Intel/AMD Windows;
  • render-windows-arm64.exe for Windows on ARM;
  • checksums.txt with SHA-256 checksums.

The release version is taken directly from the Git tag, embedded in every executable, and displayed by render --version. Release tags must start with v; following Semantic Versioning is recommended, for example v0.1.0.

The recommended way to publish a release is the release helper:

./scripts/release.sh         # interactive menu
./scripts/release.sh patch   # v0.1.0 -> v0.1.1
./scripts/release.sh minor   # v0.1.1 -> v0.2.0
./scripts/release.sh major   # v0.2.0 -> v1.0.0
./scripts/release.sh v1.2.0  # explicit version

When run without an argument, the script displays a numbered menu for choosing patch, minor, major, an explicit version, or cancellation. The script requires a clean main branch, fetches origin/main and all tags, checks that the local and remote branches match, verifies that the new version is greater than the latest release, shows the included commits, and asks for confirmation before creating and pushing an annotated tag. Pass --yes after the version to skip the confirmation prompt.

To create a release manually, perform the same checks and push an annotated tag:

git switch main
git pull --ff-only origin main
git tag -a v0.1.1 -m "render v0.1.1"
git push origin v0.1.1

Pushing the tag starts the Release workflow. If verification and all builds succeed, GitHub Actions creates the release, generates release notes, and attaches the macOS and Windows executables with their SHA-256 checksums. Follow the run in GitHub Actions and download the finished files from GitHub Releases. Published version tags should not be reused; create a new version tag for every release.

About

Render is a lightweight, easy-to-use CLI and local server for generating AI images. Run Stable Diffusion (SD 1.5, SDXL) and FLUX models locally with simple commands like pull and run. Powered by Vulkan acceleration and GGUF support for ultra-fast performance. Think Ollama, but for local image generation.

Topics

Resources

Stars

0 stars

Watchers

0 watching

Forks

Releases

Packages

Contributors

Languages