diff --git a/.github/workflows/publish-container.yml b/.github/workflows/publish-container.yml new file mode 100644 index 00000000..926a2a7d --- /dev/null +++ b/.github/workflows/publish-container.yml @@ -0,0 +1,88 @@ +name: Publish container image + +on: + pull_request: + paths: + - Dockerfile + - .github/workflows/publish-container.yml + release: + types: + - published + workflow_dispatch: + inputs: + mws_version: + description: Published @tiddlywiki/mws version to package + required: true + type: string + +env: + REGISTRY: ghcr.io + IMAGE_NAME: ${{ github.repository }} + +permissions: + contents: read + +jobs: + build: + if: github.event_name == 'pull_request' + runs-on: ubuntu-latest + + steps: + - name: Check out repository + uses: actions/checkout@v4 + + - name: Set up Docker Buildx + uses: docker/setup-buildx-action@v3 + + - name: Build container image + uses: docker/build-push-action@v6 + with: + context: . + push: false + + publish: + if: github.event_name == 'release' || github.event_name == 'workflow_dispatch' + runs-on: ubuntu-latest + permissions: + contents: read + packages: write + + steps: + - name: Check out release source + uses: actions/checkout@v4 + with: + ref: ${{ github.event.release.tag_name || github.sha }} + + - name: Resolve published MWS version + id: version + env: + INPUT_VERSION: ${{ inputs.mws_version }} + RELEASE_TAG: ${{ github.event.release.tag_name }} + run: | + version="${INPUT_VERSION:-${RELEASE_TAG#v}}" + test -n "$version" + test "$(npm view "@tiddlywiki/mws@$version" version)" = "$version" + echo "value=$version" >> "$GITHUB_OUTPUT" + + - name: Log in to the Container registry + uses: docker/login-action@v3 + with: + registry: ${{ env.REGISTRY }} + username: ${{ github.actor }} + password: ${{ secrets.GITHUB_TOKEN }} + + - name: Extract container metadata + id: meta + uses: docker/metadata-action@v5 + with: + images: ${{ env.REGISTRY }}/${{ env.IMAGE_NAME }} + tags: type=raw,value=${{ steps.version.outputs.value }} + + - name: Build and publish container image + uses: docker/build-push-action@v6 + with: + context: . + push: true + build-args: MWS_VERSION=${{ steps.version.outputs.value }} + tags: ${{ steps.meta.outputs.tags }} + labels: ${{ steps.meta.outputs.labels }} diff --git a/Dockerfile b/Dockerfile index 84fe325e..b01dad11 100644 --- a/Dockerfile +++ b/Dockerfile @@ -1,15 +1,20 @@ # Use Node.js 22 Alpine image FROM node:22-alpine -# Set working directory +# The data-folder format is independent from the MWS package version. This +# matches create-package/files/package.json, which is the template used by +# `npm init @tiddlywiki/mws`. +ARG MWS_VERSION=0.2.4 WORKDIR /data +RUN echo '{"name":"@tiddlywiki/mws-instance","private":true,"version":"0.2.0","scripts":{"start":"mws listen --listener"}}' > package.json -# Create instance package.json that references MWS -RUN echo '{"name":"@tiddlywiki/mws-instance","private":true,"version":"0.1.0","scripts":{"start":"mws listen --listener"}}' > package.json - -# Install TiddlyWiki and MultiWikiServer from npm -# Using --omit=dev to keep image smaller -RUN npm install --save-exact tiddlywiki@latest @tiddlywiki/mws@latest +# Install the published MWS package for the target container platform. The +# build tools are only needed when a native dependency has no prebuilt binary. +# The create script then downloads TiddlyWiki with `mws update-tiddlywiki`. +RUN apk add --no-cache --virtual .build-deps python3 make g++ \ + && npm install --save-exact "@tiddlywiki/mws@${MWS_VERSION}" \ + && npm exec mws update-tiddlywiki \ + && apk del .build-deps # Expose default MWS port EXPOSE 8080