Commit Graph
76 Commits
Author SHA1 Message Date
86314dc9d8 fix: avoid apt package when psycopg-binary is used (#379)
* feat: detect psycopg[binary] and skip apt packages

When using psycopg2-binary or psycopg[binary], the PostgreSQL client
libraries (libpq-dev, libpq5) are not needed because these variants
ship with pre-compiled binaries. This change:

- Adds usesBinaryPsycopg() to detect binary variants
- Updates usesPostgres() to return false when binary variants are used
- Skips libpq-dev (build) and libpq5 (runtime) apt package installation
- Adds comprehensive unit tests for binary psycopg detection

This reduces image size and build time for projects using binary variants.

* test: add psycopg[binary] integration test

Adds a dedicated test example for psycopg[binary] to verify that the
bracket syntax for optional dependencies is correctly detected. This
ensures the binary detection works for both psycopg2-binary and
psycopg[binary] variants.

Test coverage now includes:
- psycopg2-binary (existing python-system-deps example)
- psycopg[binary] (new python-psycopg-binary example)
- psycopg non-binary (existing python-latest-psycopg example)
- psycopg2 non-binary (existing python-django example)

* test: snapshot update

* test: add binary pyscogp test

* test: ensure libpq is installed for pyscog operation

* build: add helper for running the current dir tests

* test: check to make sure the libpg library is not installed when a binary postgres connection is requested

* test: update snapshot

---------

Co-authored-by: Hanzo Dev <[email protected]>
2026-01-15 11:32:30 -07:00
Jake RunzerandGitHub a1a8a4ac0c feat(python): detect python projects with start.py or bot.py (#416)
* feat(python): detect python projects with start.py or bot.py

Refactor Detect() to use getMainPythonFile() instead of duplicating
the sentinel file check. Add start.py to the list of recognized
Python entry files.

Add test case and example for bot.py-only detection.

Fixes PRO-4625

* update
2026-01-07 16:24:00 -05:00
cbdb236184 feat: automatic start command for fastapi applications, improved provider docs (#353)
* docs: update provider documentation with missing features

Added missing documentation for Node, Python, and Ruby providers:

Node.js:
- Added .node-version file support for version detection
- Documented Tanstack Start framework detection and caching
- Added Puppeteer system dependencies documentation
- Clarified React Router cache support

Python:
- Added FastHTML framework detection and start command
- Documented Flask with gunicorn start command
- Added FastAPI framework detection
- Documented additional main file names (app.py, bot.py, hello.py, server.py)
- Added pycairo system dependency documentation

Ruby:
- Documented Node.js integration for Ruby projects
- Added Bootsnap precompilation support documentation
- Documented Propshaft asset pipeline support
- Added local path dependencies support documentation
- Documented Bundler version auto-detection
- Added YJIT/rustc requirement for Ruby 3.2+
- Documented jemalloc performance optimization
- Updated Charlock Holmes dependencies to include full list

* docs: complete FastAPI documentation section

Clarify that FastAPI detection is for metadata only and doesn't provide
automatic start command configuration. Users should configure their own
production ASGI server.

* feat: add python-fastapi example project

Add example project demonstrating FastAPI with custom start command
configuration. This example shows how to configure FastAPI applications
that need explicit ASGI server configuration.

Features:
- Simple FastAPI app with root and health endpoints
- Uses uvicorn as the ASGI server
- Custom start command in railpack.json
- HTTP check test to verify the app runs correctly

* feat: add automatic FastAPI start command detection

Add automatic start command detection for FastAPI projects when uvicorn
is available as a dependency, similar to how Flask and FastHTML are
handled.

Changes:
- Add isFastapi() method to Python provider
- Automatically detect FastAPI + uvicorn and set start command
- Update StartCommandHelp to include FastAPI
- Refactor getRuntime() to use isFastapi() method for consistency

Example updates:
- Convert python-fastapi example to use uv package manager
- Remove railpack.json (no longer needed with automatic detection)
- Add pyproject.toml and uv.lock for dependency management

Documentation updates:
- Update FastAPI section to reflect automatic start command detection
- Clarify that uvicorn must be present as a dependency

* refactor: remove unused /health endpoint from FastAPI example

* test: update snapshot

---------

Co-authored-by: Hanzo Dev <[email protected]>
2025-11-23 07:54:54 -07:00
092b81dff2 refactor: replace HasMatch with HasFile for specific file paths (#347)
Replace fuzzy matching (HasMatch) with exact file path checks (HasFile)
in all providers where specific files are being checked. This prevents
false positives from glob pattern matching when checking for specific
file names.

Changes:
- PHP provider: index.php, composer.json, artisan
- Go provider: main.go, go.mod, go.work, go.sum, go.work.sum
- Ruby provider: Gemfile, rails, bin/rails, config/environment.rb,
  config.ru, Rakefile
- Node providers: package.json, lock files, config files for Vite,
  Astro, Angular, React Router
- Python providers: main.py, requirements.txt, pyproject.toml, Pipfile,
  poetry.lock, pdm.lock, uv.lock, manage.py
- Rust provider: Cargo.toml, src/main.rs, src/lib.rs
- Elixir provider: mix.exs
- Deno provider: deno.json, deno.jsonc, main.ts/js/mjs/mts
- Java providers: gradlew, mvnw, gradle/maven wrapper properties
- Staticfile provider: index.html, Staticfile config
- Core: template.go and mise_step_builder.go

Directory checks (e.g. src/bin, node_modules, public, script) continue
to use HasMatch as they need pattern/directory matching.

Co-authored-by: Hanzo Dev <[email protected]>
2025-11-23 07:49:16 -07:00
ac447bc76f fix: detect psycopg3 and add required apt packages (#350)
* feat: add psycopg (psycopg3) to postgres dependency detection

Added psycopg to the list of Python dependencies that trigger installation
of PostgreSQL libraries (libpq-dev for build, libpq5 for runtime).

While psycopg[binary] includes a bundled libpq, the base psycopg package
and psycopg[c] both require system libpq. Since we cannot determine which
variant is being used from dependency files, we conservatively install
libpq when any psycopg dependency is detected.

Also added integration test example for psycopg3 to verify the dependency
detection works correctly.

* chore: add tmp/ to .gitignore

* test: enhance psycopg3 example to test actual database connectivity

Updated the python-psycopg3 example to:
- Connect to a real PostgreSQL database
- Execute test queries to verify connectivity
- Use docker-compose.yml to provide postgres service for integration tests
- Assert on multiple output strings to verify full connection lifecycle

This provides a comprehensive test that psycopg can successfully use
the system libpq libraries to connect to and query PostgreSQL.

* test: upgrade psycopg3 example to Python 3.14 and assert major version

Updated the python-psycopg3 example to:
- Use Python 3.14 (latest stable release)
- Specify psycopg>=3.2,<4.0 to ensure psycopg3 is used
- Add runtime check that verifies psycopg major version is 3
- Update test assertion to match new output message

This ensures the test explicitly validates we're using psycopg3 (not
psycopg2) and tests compatibility with the latest Python version.

* refactor: convert python-psycopg3 example to use uv and latest Python

- Changed .python-version from 3.14 to "latest"
- Converted from pip to uv package manager
- Created pyproject.toml with psycopg>=3.2,<4.0 dependency
- Generated uv.lock for reproducible builds
- Removed requirements.txt
- Reverted .gitignore changes (removed tmp/)

* test: update snapshot

---------

Co-authored-by: Hanzo Dev <[email protected]>
2025-11-20 15:38:37 -07:00
Michael BiancoandGitHub 269d29f774 fix: allow node_modules removal in build phase (#259)
* test: test install in build phase

* fix: detect node_modules removal and avoid caching node_modules/.cache

* test: add new snapshot

* build: adding go debugging tool and helper task

* refactor: node_modules detection is working

* test: test install in build phase

* refactor: pull plan cleansing into a separate file

* refactor: ai cleanup

* refactor: move cleanse to the provider level, stubs for all providers

* refactor: move existing node cleanse logic to a provider-specific implementation

* test: snapshot update

* docs: why we need node cleanse operation

* docs: note on corepack

* docs: on cache handling of node_modules
2025-11-18 10:52:48 -07:00
Michael BiancoandGitHub cffe6f8ccb feat: mise idiomatic file parsing (#344)
* test: update snapshots

* feat: use mise parse idiomatic .python-version{s} file
2025-11-12 17:03:37 -07:00
c1252f9e52 feat: set pipx.uvx = true when pipx backend is used in Python provider (#324)
* feat: set pipx.uvx = true when pipx backend is used in Python provider

Add support for mise settings configuration and set pipx.uvx = true
when using pipx in the Python provider. This configures pipx to use
uvx as the backend, as documented at:
https://mise.jdx.dev/dev-tools/backends/pipx.html

Changes:
- Add Settings field to MiseConfig struct to support mise settings
- Update GenerateMiseToml to accept and write settings to TOML
- Add Settings map to MiseStepBuilder
- Set pipx.uvx = true in Python provider when pipx is used

* fix: move to ENV vs config

* test: snapshot update

* fix: remove mise settings completely

* docs: notes on tmp/ and ENV

---------

Co-authored-by: Hanzo Dev <[email protected]>
2025-11-11 11:56:14 -07:00
Jake RunzerandGitHub 30cb74c79c fix: disable Python compilation to avoid package incompatibility issues (#301)
* fix: disable Python compilation to avoid package incompatibility issues

* update python compile settings
2025-10-23 21:26:35 -04:00
Michael BiancoandGitHub b6c915006b fix: use default mise backend for uv (#260)
* fix: use default mise backends for python package management when possible

* test: snapshot update
2025-10-18 10:21:17 -06:00
Michael BiancoandGitHub 4cf15bc783 feat: use py package versions from any mise-supported version specification file (#261)
* test: add .tool-versions test

* feat: extract locally defined mise package versions

* test: .tool-versions unit tests

* docs: integration tests docs

* build: local mise config for less annoying warnings

* feat: pull python ecosystem versions from mise

* feat: internal support for extracting mise-specified package versions from app folder

* refactor: move mise package version methods into context

* test: snapshots

* test: multiple test.json expectation lines

this is using newly implemented multiple expectations syntax

* test: support multiple expectations per test.json entry, don't use additional non-deterministic contains to throw an error

* refactor: refine mise interface

* refactor: make mise versions easier for a provider to use

* test: snapshot update

* refactor: move mise local package logic to step builder

* test: move mise package version extraction to mise step builder tests

* refactor: move mise package into mise step builder
2025-10-01 07:14:27 -06:00
24f0a773d8 feat: dockerignore support (#263)
* test: dockerignore test project

* docs: claude.md update

* feat: parse dockerignore files

* fixup! feat: parse dockerignore files

* feat: use revised local layer

* feat: parse dockerfiles and pass includes/excludes to the local layer

* test: snapshot

* refactor: ai cleanup

* test: dockerignore parsing tests

* refactor: remove obvious comment

* test: dockerignore failure tests

* Apply suggestion from @coffee-cup

Co-authored-by: Jake Runzer <[email protected]>

* Apply suggestion from @coffee-cup

Co-authored-by: Jake Runzer <[email protected]>

* docs: always use App for fs ops

* refactor: pass App to dockerignore context instead of a path to the repo

* test: pass app to dockerignore

---------

Co-authored-by: Jake Runzer <[email protected]>
2025-09-24 16:11:40 -06:00
Jake RunzerandGitHub 6c1823f3e6 Update default versions for Go, Python, Ruby, and Rust providers (#267)
* update provider default versions

* update golang test
2025-09-16 16:53:26 -04:00
Michael BiancoandGitHub 08a32ea8cc fix: remove python3-dev apt package (#256)
* fix: remove python build packages

mise uses precompiled versions of python, so this shouldn't be needed

* test: snapshot update
2025-09-15 18:44:59 -06:00
Jake RunzerandGitHub 3b5ab60b7e Revert "fix: use default mise backends for python packages (#249)" (#252)
This reverts commit f15960d2f7.
2025-09-04 22:44:10 -04:00
Michael BiancoandGitHub f15960d2f7 fix: use default mise backends for python packages (#249)
* fix: use mise default backends for uv and other package manager installs

* test: update snapshots
2025-09-03 16:17:12 -06:00
Michael BiancoandGitHub 5af5eb5161 refactor: use consistent local layers entrypoint (#241)
* fix: show-plan not showing json output

regression from $schema addition

* refactor: all providers using a consistent local layer entrypoint

* refactor: add local filesystem through a consistent entrypoint

* fix: improved error message on invalid firstInput

* test: remove path argument from NewLocalLayer test

* test: failing workspace example with uv

* test: passing workspace example

* feat: detect uv workspaces

* test: add packaged uv example

* test: snapshot update
2025-09-03 10:39:48 -06:00
Jake RunzerandGitHub 43229e0c14 Use pipx:package pattern for Python package managers (#186)
* Use pipx:package pattern for Python package managers in mise

Install Python package managers (poetry, pdm, uv, pipenv) using the
pipx:package pattern through mise instead of separate pipx install commands.
This approach is more efficient and consistent.

* update python snapshots
2025-06-24 17:14:24 -04:00
Jake RunzerandGitHub 1e6c3535d9 support pycairo (#178)
* support pycairo

* merge pycairo example with system deps
2025-06-13 19:13:29 -04:00
Jake RunzerandGitHub 93951b63ec prefer python_full_version in Pipfile (#142)
* prefer `python_full_version` in `Pipfile`

* update php snapshot
2025-04-21 14:46:10 -04:00
Jake RunzerandGitHub a1b23c76b0 fix poetry env (#136) 2025-04-01 17:29:45 -04:00
Jake RunzerandGitHub 0a5fe7f6ad [Python] copy all files to build context if necessary (#135)
* [Python] copy all files to build context if necessary

* update snapshot tests
2025-04-01 15:38:32 -04:00
Jake RunzerandGitHub d8f31b4589 Custom config step deploy outputs (#118)
* rename plan inputs to layers and use deploy base layer

* runtime deps installed

* step builders can create multiple steps

* support config step deploy outputs

* optimize when we merge vs copy layers

* update snapshots

* validate the deploy layers

* fix tests

* dont add mise if no packages

* fix pruning for php

* update layer merging and snapshot tests

* dont include mise commands or variables if no packages

* update docs

* update snapshots and normalization

* add guide for adding custom steps

* support .node-version file

* fix compile errors

* update snapshot tests
2025-04-01 13:33:30 -04:00
Jake Runzer 208284f1a4 support python app.py and bot.py 2025-03-13 20:59:43 -04:00
Jake Runzer f5f2ece51a store python install artifcats on separate layer 2025-03-11 16:47:19 -04:00
Jake Runzer 464cad4d09 move utils to internal 2025-03-10 19:05:21 -04:00
Jake Runzer e250e55749 optimize providers for merging states 2025-03-08 14:03:32 -05:00
Jake Runzer be3cf8f6db add pipx bin dir to path before installing 2025-03-07 18:33:46 -05:00
Jake Runzer dbb5b897a9 parse semver version from text 2025-03-07 18:32:09 -05:00
Jake Runzer 5bb084e8f3 update snapshots 2025-03-07 17:36:52 -05:00
Jake Runzer 60fb412dc3 install mysql client python runtime 2025-03-07 17:34:46 -05:00
Jake Runzer 46a3de71bf fix poetry virtual env 2025-03-07 13:41:34 -05:00
Jake RunzerandGitHub 039c26c07e Merge pull request #79 from railwayapp/jr/python-fasthtml-flask-ootb-support
support for fasthtml and flask
2025-03-07 02:14:37 -05:00
Jake Runzer 10e3509a22 support for fasthtml and flask 2025-03-07 01:49:26 -05:00
Jake RunzerandGitHub 667d491ba7 Merge branch 'main' into jr/default-python-3.11 2025-03-07 01:23:14 -05:00
Jake Runzer 588b2f1231 default to python 3.11 for compatability 2025-03-07 00:33:59 -05:00
Jake Runzer f902eb48a1 remove commented out code 2025-03-07 00:33:07 -05:00
Jake Runzer 18a34613d7 use a virtual env for pip installs 2025-03-07 00:28:20 -05:00
Jake Runzer 4af1477f14 append global python-packages/bin path for pip 2025-03-04 22:52:30 -05:00
Jake Runzer d7cf9a4a5b python django and postgres support 2025-03-04 19:35:04 -05:00
Jake Runzer c21fc6f0c0 refactor python install planning 2025-03-04 18:28:18 -05:00
Jake Runzer 5c058e08a5 basic django support 2025-03-04 03:48:51 -05:00
Jake Runzer 4188f20e21 update language docs 2025-03-03 18:34:46 -05:00
Jake Runzer 2f12583c70 remove double pipenv commands 2025-02-28 13:40:16 -05:00
Jake Runzer 0f3b85fb13 start command and missing build plan errors 2025-02-27 21:47:21 -05:00
Jake Runzer 955bc6a511 logger for logs, warns, and errors 2025-02-27 20:17:07 -05:00
Jake Runzer 10f5ddd58f change how config is applied 2025-02-23 21:23:42 -05:00
Jake Runzer c39a419887 pipfile support 2025-02-23 18:49:15 -05:00
Jake Runzer 3ac7b84140 pdm support 2025-02-23 14:09:27 -05:00
Jake Runzer cefa9ec1cf python poetry 2025-02-22 11:55:21 -05:00