Building and CI
This page shows how to automate Markspresso builds, with a concrete example using GitHub Actions and GitHub Pages.
Basic build recap
Locally, you build your site from the project root with:
lucli markspresso build --clean
By default this renders Markdown from content/ into HTML under public/, and copies any assets from assets/.
For CI you typically want to:
- Run the same
buildcommand on every push (often only onmain) - Publish the
public/directory as your site output
GitHub Pages with GitHub Actions
The typical pattern is:
- Commit your Markspresso site into a GitHub repository
- Configure GitHub Pages to serve from a branch or from the GitHub Actions build output
- Add a GitHub Actions workflow that runs
lucli markspresso buildand uploadspublic/
1. Choose a Pages "source"
In your repository settings under Pages, choose a source. Two common options are:
- Deploy from a branch – e.g. branch
gh-pages, folder/. - GitHub Actions – recommended when you want a dedicated workflow to control the build.
The examples below assume you select GitHub Actions and let the workflow publish your site.
2. Example GitHub Actions workflow (using the LuCLI Docker image)
This repository ships with a ready-to-use workflow at .github/workflows/markspresso-pages.yml that runs everything inside a LuCLI Docker image. A simplified version looks like:
name: Build and deploy Markspresso site
on:
push:
branches: [ main ]
workflow_dispatch:
permissions:
contents: read
pages: write
id-token: write
concurrency:
group: "pages"
cancel-in-progress: true
jobs:
build:
name: Build static site
runs-on: ubuntu-latest
# Run all steps inside a LuCLI Docker image
container:
image: markdrew/lucli:latest
steps:
- name: Check out repository
uses: actions/checkout@v4
- name: Install Markspresso
run: lucli module install markspresso
- name: Build Markspresso site
run: |
# If your site lives in a subdirectory, cd into it first
# cd path/to/site-root
lucli markspresso build clean
- name: Upload Pages artifact
uses: actions/upload-pages-artifact@v3
with:
# Point this at your Markspresso output directory.
# In this docs site we build into `docs/`.
path: docs
deploy:
name: Deploy to GitHub Pages
needs: build
runs-on: ubuntu-latest
environment:
name: github-pages
url: ${{ steps.deployment.outputs.page_url }}
steps:
- name: Deploy
id: deployment
uses: actions/deploy-pages@v4
Key points:
- The whole job runs inside the
markdrew/lucli:latestcontainer, so you don’t have to install Java or LuCLI manually. - Markspresso itself is installed with
lucli module install markspressoinside the container. lucli markspresso build cleanperforms the site build; adjust the command or add flags as needed.- The
pathpassed toupload-pages-artifactmust match your configured output directory (for many sites this will bepublic/, for this docs site it isdocs/).
Once this workflow is committed and GitHub Pages is configured to use GitHub Actions, every push to main will rebuild and redeploy your Markspresso site.
Customizing for your project
You can adapt the example to your needs:
- Change the trigger (e.g. run only on tags, or on pushes to a
docsbranch). - Add a matrix build if you want to test multiple Java/Lucee versions.
- Run extra checks before deploy, such as link checking or custom scripts.
The important part is that CI runs lucli markspresso build from the site root and publishes the resulting public/ directory.