RSS Reader using AT Protocol rssbase.io
feed atom rss reader atproto social
2

Configure Feed

Select the types of activity you want to include in your feed.

fix ci by adding docker?

+441 -26
+408
.tangled/workflow.schema.json
··· 1 + { 2 + "$schema": "http://json-schema.org/draft-07/schema#", 3 + "$id": "https://rssbase.io/schemas/tangled-workflow.schema.json", 4 + "title": "Tangled Spindle workflow", 5 + "description": "Local JSON Schema for Tangled CI / Spindle workflow files under .tangled/workflows/*.yml. Based on https://docs.tangled.org/spindles.", 6 + "type": "object", 7 + "additionalProperties": false, 8 + "required": ["when", "engine"], 9 + "properties": { 10 + "when": { 11 + "title": "Trigger conditions", 12 + "description": "Defines when the workflow runs. Each condition can match events, branches, and/or tags.", 13 + "type": "array", 14 + "minItems": 1, 15 + "items": { "$ref": "#/definitions/trigger" }, 16 + "defaultSnippets": [ 17 + { 18 + "label": "push/manual on main + PR to main", 19 + "body": [ 20 + { "event": ["push", "manual"], "branch": ["main"] }, 21 + { "event": ["pull_request"], "branch": ["main"] } 22 + ] 23 + }, 24 + { 25 + "label": "tag push", 26 + "body": [ 27 + { "event": ["push"], "tag": ["v*"] } 28 + ] 29 + } 30 + ] 31 + }, 32 + "engine": { 33 + "title": "Execution engine", 34 + "description": "The Spindle engine used to run the workflow.", 35 + "type": "string", 36 + "enum": ["microvm", "nixery"] 37 + }, 38 + "clone": { 39 + "title": "Clone options", 40 + "description": "Controls how the repository is cloned before workflow steps run.", 41 + "type": "object", 42 + "additionalProperties": false, 43 + "properties": { 44 + "skip": { 45 + "description": "Skip cloning the repository. Default: false.", 46 + "type": "boolean", 47 + "default": false 48 + }, 49 + "depth": { 50 + "description": "Number of commits to fetch. Default: 1.", 51 + "type": "integer", 52 + "minimum": 0, 53 + "default": 1 54 + }, 55 + "submodules": { 56 + "description": "Recursively fetch git submodules. Default: false.", 57 + "type": "boolean", 58 + "default": false 59 + } 60 + }, 61 + "defaultSnippets": [ 62 + { 63 + "label": "default clone options", 64 + "body": { "skip": false, "depth": 1, "submodules": false } 65 + } 66 + ] 67 + }, 68 + "environment": { 69 + "title": "Workflow environment variables", 70 + "description": "Public environment variables available throughout the workflow. Do not put secrets here; use Tangled repository secrets.", 71 + "$ref": "#/definitions/environment" 72 + }, 73 + "steps": { 74 + "title": "Workflow steps", 75 + "description": "Commands to run in order. Commands run in a Bash shell.", 76 + "type": "array", 77 + "items": { "$ref": "#/definitions/step" }, 78 + "defaultSnippets": [ 79 + { 80 + "label": "single command step", 81 + "body": [ 82 + { "name": "$1", "command": "$2" } 83 + ] 84 + }, 85 + { 86 + "label": "multi-line Bash step", 87 + "body": [ 88 + { "name": "$1", "command": "set -euo pipefail\n$2" } 89 + ] 90 + } 91 + ] 92 + }, 93 + "dependencies": { 94 + "title": "Dependencies", 95 + "description": "For microvm: a flat list of packages/flakeref#attrs. For nixery: a map of registry refs to package lists.", 96 + "oneOf": [ 97 + { "$ref": "#/definitions/microvmDependencies" }, 98 + { "$ref": "#/definitions/nixeryDependencies" } 99 + ] 100 + }, 101 + "image": { 102 + "title": "microVM image", 103 + "description": "microVM image name. Examples: nixos, alpine. Available images depend on the Spindle operator; if omitted, the operator default is used.", 104 + "type": "string", 105 + "examples": ["nixos", "alpine"], 106 + "defaultSnippets": [ 107 + { "label": "nixos", "body": "nixos" }, 108 + { "label": "alpine", "body": "alpine" } 109 + ] 110 + }, 111 + "registry": { 112 + "title": "microVM flake registry aliases", 113 + "description": "Remaps flake references for microVM NixOS images, similar to `nix registry`.", 114 + "type": "object", 115 + "additionalProperties": { 116 + "type": "string", 117 + "description": "Flake reference, e.g. github:nixos/nixpkgs/nixos-unstable." 118 + }, 119 + "defaultSnippets": [ 120 + { 121 + "label": "pin nixpkgs to unstable", 122 + "body": { "nixpkgs": "github:nixos/nixpkgs/nixos-unstable" } 123 + } 124 + ] 125 + }, 126 + "caches": { 127 + "title": "microVM Nix binary caches", 128 + "description": "Map of Nix binary cache URL to trusted public key. Used by microVM NixOS images.", 129 + "type": "object", 130 + "additionalProperties": { 131 + "type": "string", 132 + "description": "Trusted public key for this binary cache." 133 + }, 134 + "defaultSnippets": [ 135 + { 136 + "label": "nix-community Cachix", 137 + "body": { 138 + "https://nix-community.cachix.org": "nix-community.cachix.org-1:mB9FSh9qf2dCimDSUo8Zy7bkq5CX+/rkCWyvRCYg3Fs=" 139 + } 140 + } 141 + ] 142 + }, 143 + "services": { 144 + "title": "microVM NixOS services.* configuration", 145 + "description": "Passed through to NixOS as services.* for microVM NixOS images. `true` is shorthand for `.enable = true` where an enable option exists.", 146 + "type": "object", 147 + "additionalProperties": { "$ref": "#/definitions/nixosValue" }, 148 + "defaultSnippets": [ 149 + { 150 + "label": "PostgreSQL service", 151 + "body": { 152 + "postgresql": { 153 + "enable": true, 154 + "ensureDatabases": ["spindle-workflow"], 155 + "ensureUsers": [ 156 + { "name": "spindle-workflow", "ensureDBOwnership": true } 157 + ] 158 + } 159 + } 160 + } 161 + ] 162 + }, 163 + "virtualisation": { 164 + "title": "microVM NixOS virtualisation.* configuration", 165 + "description": "Passed through to NixOS as virtualisation.* for microVM NixOS images. `true` is shorthand for `.enable = true` where an enable option exists.", 166 + "type": "object", 167 + "additionalProperties": { "$ref": "#/definitions/nixosValue" }, 168 + "defaultSnippets": [ 169 + { 170 + "label": "enable Docker", 171 + "body": { "docker": true } 172 + } 173 + ] 174 + } 175 + }, 176 + "allOf": [ 177 + { 178 + "if": { 179 + "properties": { "engine": { "const": "microvm" } }, 180 + "required": ["engine"] 181 + }, 182 + "then": { 183 + "properties": { 184 + "dependencies": { "$ref": "#/definitions/microvmDependencies" } 185 + } 186 + } 187 + }, 188 + { 189 + "if": { 190 + "properties": { "engine": { "const": "nixery" } }, 191 + "required": ["engine"] 192 + }, 193 + "then": { 194 + "properties": { 195 + "dependencies": { "$ref": "#/definitions/nixeryDependencies" } 196 + }, 197 + "not": { 198 + "anyOf": [ 199 + { "required": ["image"] }, 200 + { "required": ["registry"] }, 201 + { "required": ["caches"] }, 202 + { "required": ["services"] }, 203 + { "required": ["virtualisation"] } 204 + ] 205 + } 206 + } 207 + } 208 + ], 209 + "defaultSnippets": [ 210 + { 211 + "label": "microVM NixOS workflow", 212 + "body": { 213 + "when": [ 214 + { "event": ["push", "manual"], "branch": ["main"] }, 215 + { "event": ["pull_request"], "branch": ["main"] } 216 + ], 217 + "engine": "microvm", 218 + "image": "nixos", 219 + "dependencies": ["devenv"], 220 + "steps": [ 221 + { "name": "Run checks", "command": "devenv shell check" } 222 + ] 223 + } 224 + }, 225 + { 226 + "label": "microVM Alpine workflow", 227 + "body": { 228 + "when": [ 229 + { "event": ["push", "pull_request"], "branch": ["main"] } 230 + ], 231 + "engine": "microvm", 232 + "image": "alpine", 233 + "steps": [ 234 + { "name": "Install dependencies", "command": "apk add --no-cache go" }, 235 + { "name": "Check formatting", "command": "test -z $(gofmt -l .)" } 236 + ] 237 + } 238 + }, 239 + { 240 + "label": "nixery workflow", 241 + "body": { 242 + "when": [ 243 + { "event": ["push", "manual"], "branch": ["main", "develop"] }, 244 + { "event": ["pull_request"], "branch": ["main"] } 245 + ], 246 + "engine": "nixery", 247 + "clone": { "skip": false, "depth": 1, "submodules": false }, 248 + "dependencies": { 249 + "nixpkgs": ["nodejs", "go"] 250 + }, 251 + "steps": [ 252 + { "name": "Build backend", "command": "go build" }, 253 + { "name": "Build frontend", "command": "npm run build" } 254 + ] 255 + } 256 + } 257 + ], 258 + "definitions": { 259 + "trigger": { 260 + "type": "object", 261 + "additionalProperties": false, 262 + "required": ["event"], 263 + "properties": { 264 + "event": { 265 + "description": "Events that can trigger this condition.", 266 + "type": "array", 267 + "minItems": 1, 268 + "uniqueItems": true, 269 + "items": { 270 + "type": "string", 271 + "enum": ["push", "pull_request", "manual"] 272 + } 273 + }, 274 + "branch": { 275 + "description": "Branch patterns. For push, matches pushed branches. For pull_request, matches target branches. No effect for manual. Supports * and ** globs.", 276 + "$ref": "#/definitions/patternList" 277 + }, 278 + "tag": { 279 + "description": "Tag patterns for push events. No effect for pull_request or manual. Supports * and ** globs.", 280 + "$ref": "#/definitions/patternList" 281 + } 282 + }, 283 + "allOf": [ 284 + { 285 + "if": { 286 + "properties": { 287 + "event": { "contains": { "const": "push" } } 288 + }, 289 + "required": ["event"] 290 + }, 291 + "then": { 292 + "anyOf": [ 293 + { "required": ["branch"] }, 294 + { "required": ["tag"] } 295 + ] 296 + } 297 + } 298 + ], 299 + "defaultSnippets": [ 300 + { 301 + "label": "push to main", 302 + "body": { "event": ["push"], "branch": ["main"] } 303 + }, 304 + { 305 + "label": "pull request to main", 306 + "body": { "event": ["pull_request"], "branch": ["main"] } 307 + }, 308 + { 309 + "label": "manual", 310 + "body": { "event": ["manual"] } 311 + }, 312 + { 313 + "label": "push tag v*", 314 + "body": { "event": ["push"], "tag": ["v*"] } 315 + } 316 + ] 317 + }, 318 + "patternList": { 319 + "type": "array", 320 + "minItems": 1, 321 + "items": { "type": "string" } 322 + }, 323 + "environment": { 324 + "type": "object", 325 + "additionalProperties": { 326 + "type": "string" 327 + }, 328 + "propertyNames": { 329 + "pattern": "^[A-Za-z_][A-Za-z0-9_]*$" 330 + }, 331 + "defaultSnippets": [ 332 + { 333 + "label": "common environment", 334 + "body": { 335 + "NODE_ENV": "production" 336 + } 337 + } 338 + ] 339 + }, 340 + "step": { 341 + "type": "object", 342 + "additionalProperties": false, 343 + "required": ["name", "command"], 344 + "properties": { 345 + "name": { 346 + "description": "Human-readable step name shown in workflow runs.", 347 + "type": "string" 348 + }, 349 + "command": { 350 + "description": "Bash command to run for this step.", 351 + "type": "string" 352 + }, 353 + "environment": { 354 + "description": "Public environment variables for this step only. Do not put secrets here; use Tangled repository secrets.", 355 + "$ref": "#/definitions/environment" 356 + } 357 + } 358 + }, 359 + "microvmDependencies": { 360 + "description": "microVM dependencies: a flat list of packages available to every step. Bare names resolve from nixpkgs; flakeref#attr is also supported.", 361 + "type": "array", 362 + "items": { 363 + "type": "string", 364 + "examples": ["go", "pnpm", "pkg-config", "openssl", "github:nixos/nixpkgs#hello"] 365 + } 366 + }, 367 + "nixeryDependencies": { 368 + "description": "Nixery dependencies: map registry references to package lists.", 369 + "type": "object", 370 + "minProperties": 1, 371 + "additionalProperties": { 372 + "type": "array", 373 + "items": { "type": "string" } 374 + }, 375 + "defaultSnippets": [ 376 + { 377 + "label": "nixpkgs packages", 378 + "body": { "nixpkgs": ["nodejs", "go"] } 379 + }, 380 + { 381 + "label": "unstable package", 382 + "body": { "nixpkgs/nixpkgs-unstable": ["bun"] } 383 + }, 384 + { 385 + "label": "custom registry", 386 + "body": { "git+https://tangled.org/@example.com/my_pkg": ["my_pkg"] } 387 + } 388 + ] 389 + }, 390 + "nixosValue": { 391 + "description": "Arbitrary NixOS option value used under services.* or virtualisation.*.", 392 + "anyOf": [ 393 + { "type": "boolean" }, 394 + { "type": "string" }, 395 + { "type": "number" }, 396 + { "type": "null" }, 397 + { 398 + "type": "array", 399 + "items": { "$ref": "#/definitions/nixosValue" } 400 + }, 401 + { 402 + "type": "object", 403 + "additionalProperties": { "$ref": "#/definitions/nixosValue" } 404 + } 405 + ] 406 + } 407 + } 408 + }
+22 -22
.tangled/workflows/build.yml
··· 1 + # yaml-language-server: $schema=../workflow.schema.json 2 + 1 3 when: 2 4 - event: ["push", "manual"] 3 5 branch: ["main"] ··· 6 8 7 9 engine: microvm 8 10 image: nixos 11 + dependencies: 12 + - devenv 13 + caches: 14 + https://rssbase.cachix.org: rssbase.cachix.org-1:M6FSdZTOB35gaghrEhEML1s8n1jsH3hCKIXo/CcWEGc= 15 + virtualisation: 16 + docker: true 9 17 10 18 clone: 11 19 skip: false 12 20 depth: 1 13 - 14 - dependencies: 15 - - devenv 16 21 17 22 steps: 18 23 - name: "Initialize devenv" 19 24 command: devenv shell true 20 25 21 - - name: "Build production image with Dagger" 22 - command: DAGGER_NO_NAG=1 devenv shell dagger call application build-prod sync 23 - 24 - - name: "Build production image with Docker Compose" 25 - command: | 26 - devenv shell -- bash -c ' 27 - set -euo pipefail 28 - cd application 29 - export APP_SECRET="${APP_SECRET:-ci-app-secret}" 30 - export CADDY_MERCURE_JWT_SECRET="${CADDY_MERCURE_JWT_SECRET:-ci-mercure-secret}" 31 - docker-compose -f compose.yaml -f compose.prod.yaml build --pull 32 - ' 26 + - name: "Build docker image" 27 + command: DAGGER_NO_NAG=1 devenv shell dagger call application build-prod export-image --name app-php-prod:latest 33 28 34 - - name: "Start production services and smoke test" 29 + - name: "Start docker container and smoke test" 35 30 command: | 36 31 devenv shell -- bash -c ' 37 32 set -euo pipefail 38 - cd application 33 + export DOCKER_BUILDKIT=1 34 + export COMPOSE_DOCKER_CLI_BUILD=1 39 35 export APP_SECRET="${APP_SECRET:-ci-app-secret}" 40 36 export CADDY_MERCURE_JWT_SECRET="${CADDY_MERCURE_JWT_SECRET:-ci-mercure-secret}" 41 - trap "docker-compose -f compose.yaml -f compose.prod.yaml down --volumes --remove-orphans" EXIT 42 - docker-compose -f compose.yaml -f compose.prod.yaml down --volumes --remove-orphans 43 - docker-compose -f compose.yaml -f compose.prod.yaml up --wait --wait-timeout 120 --no-build -d 44 - curl -v --fail-with-body http://localhost 45 - curl -vI --insecure --fail-with-body "https://localhost/.well-known/mercure?topic=test" 37 + export HTTP_PORT="${HTTP_PORT:-8080}" 38 + export HTTPS_PORT="${HTTPS_PORT:-8443}" 39 + export HTTP3_PORT="${HTTP3_PORT:-8443}" 40 + export COMPOSE_FILE="application/compose.yaml:application/compose.prod.yaml" 41 + trap "docker-compose down --volumes --remove-orphans" EXIT 42 + docker-compose down --volumes --remove-orphans 43 + docker-compose up --wait --wait-timeout 120 --no-build -d 44 + curl -v --fail-with-body "http://localhost:${HTTP_PORT}" 45 + curl -vI --insecure --fail-with-body "https://localhost:${HTTPS_PORT}/.well-known/mercure?topic=test" 46 46 '
+9 -4
.tangled/workflows/check.yml
··· 1 + # yaml-language-server: $schema=../workflow.schema.json 2 + 1 3 when: 2 4 - event: ["push", "manual"] 3 5 branch: ["main"] ··· 6 8 7 9 engine: microvm 8 10 image: nixos 11 + dependencies: 12 + - devenv 13 + caches: 14 + https://rssbase.cachix.org: rssbase.cachix.org-1:M6FSdZTOB35gaghrEhEML1s8n1jsH3hCKIXo/CcWEGc= 15 + virtualisation: 16 + docker: true 9 17 10 18 clone: 11 19 skip: false 12 20 depth: 1 13 21 14 - dependencies: 15 - - devenv 16 - 17 22 steps: 18 23 - name: "Initialize devenv" 19 24 command: devenv shell true 20 25 21 - - name: "Run Dagger checks" 26 + - name: "Run checks" 22 27 command: DAGGER_NO_NAG=1 devenv shell dagger check
+2
devenv.nix
··· 11 11 { 12 12 # https://devenv.sh/packages/ 13 13 packages = [ 14 + pkgs.docker-buildx # BuildKit builder for CI image builds 14 15 pkgs.docker-compose # used by application 15 16 dagger # dagger CLI dev build (until 1.0) 16 17 pkgs.skills # used to manage .agents/skills ··· 21 22 enterShell = devenvSummary { 22 23 title = "RSSBase devenv:"; 23 24 rows = [ 25 + { pkg = pkgs.docker-buildx; } 24 26 { pkg = pkgs.docker-compose; } 25 27 { pkg = dagger; } 26 28 { pkg = pkgs.skills; }