kind: pipeline
type: docker
name: release

when:
  event: tag

steps:
  - name: version-check
    image: registry.niovi.voyage/harb/node-ci:latest
    when:
      event: tag
    commands:
      - |
          bash -c '
            set -euo pipefail
            git submodule update --init --recursive
          corepack enable
          yarn --cwd onchain/lib/uni-v3-lib install --frozen-lockfile
          export PATH=/root/.foundry/bin:$PATH
          forge build >/dev/null
            npm config set fund false
            npm config set audit false
            npm install --prefix kraiken-lib --no-audit --no-fund
            ./scripts/build-kraiken-lib.sh
            node <<\"NODE\"
            import fs from \"fs\";

            const sol = fs.readFileSync(\"onchain/src/Kraiken.sol\", \"utf8\");
            const lib = fs.readFileSync(\"kraiken-lib/src/version.ts\", \"utf8\");

            const contractVersionMatch = sol.match(/VERSION\\s*=\\s*(\\d+)/);
            if (!contractVersionMatch) {
              console.error(\"Unable to find VERSION constant in Kraiken.sol\");
              process.exit(1);
            }
            const contractVersion = Number(contractVersionMatch[1]);

            const libVersionMatch = lib.match(/KRAIKEN_LIB_VERSION\\s*=\\s*(\\d+)/);
            if (!libVersionMatch) {
              console.error(\"Unable to find KRAIKEN_LIB_VERSION in kraiken-lib/src/version.ts\");
              process.exit(1);
            }
            const libVersion = Number(libVersionMatch[1]);

            const compatMatch = lib.match(/COMPATIBLE_CONTRACT_VERSIONS\\s*=\\s*\\[([^\\]]*)\\]/);
            if (!compatMatch) {
              console.error(\"Unable to find COMPATIBLE_CONTRACT_VERSIONS in kraiken-lib/src/version.ts\");
              process.exit(1);
            }
            const compatibleVersions = compatMatch[1]
              .split(\",\")
              .map(v => v.trim())
              .filter(Boolean)
              .map(Number);

            if (contractVersion !== libVersion) {
              console.error(\"Contract VERSION (\" + contractVersion + \") and KRAIKEN_LIB_VERSION (\" + libVersion + \") differ\");
              process.exit(1);
            }
            if (!compatibleVersions.includes(contractVersion)) {
              console.error(\"Contract VERSION \" + contractVersion + \" missing from COMPATIBLE_CONTRACT_VERSIONS [\" + compatibleVersions.join(\", \") + \"]\");
              process.exit(1);
            }

            console.log(\"Version check passed for VERSION \" + contractVersion);
            NODE
          '

  - name: build-artifacts
    image: registry.niovi.voyage/harb/node-ci:latest
    depends_on:
      - version-check
    when:
      event: tag
    commands:
      - |
          bash -c '
            set -euo pipefail
            npm config set fund false
            npm config set audit false
          npm install --prefix kraiken-lib --no-audit --no-fund
          ./scripts/build-kraiken-lib.sh
          npm install --prefix landing --no-audit --no-fund
          npm install --prefix web-app --no-audit --no-fund
          npm install --prefix services/ponder --no-audit --no-fund
          npm install --prefix services/txnBot --no-audit --no-fund
          npm install --no-audit --no-fund
          export PATH=/root/.foundry/bin:$PATH
          forge --version
          (cd onchain && forge build)
            npm run build --prefix landing
            npm run build --prefix web-app
            npm run build --prefix services/ponder
            npm run build --prefix services/txnBot
            rm -rf release
            mkdir -p release/dist
            cp -r onchain/out release/dist/abi
            cp -r kraiken-lib/dist release/dist/kraiken-lib
            cp -r landing/dist release/dist/landing
            cp -r web-app/dist release/dist/web-app
            cp -r services/txnBot/dist release/dist/txn-bot
            if [ -d services/ponder/generated ]; then
              cp -r services/ponder/generated release/dist/ponder-generated
            fi
            tar -czf release-bundle.tgz -C release dist
          '

  - name: docker-publish
    image: registry.niovi.voyage/harb/playwright-ci:latest
    pull: true
    privileged: true
    depends_on:
      - build-artifacts
    when:
      event: tag
    environment:
      REGISTRY_SERVER:
        from_secret: registry_server
      REGISTRY_NAMESPACE:
        from_secret: registry_namespace
      REGISTRY_USERNAME:
        from_secret: registry_username
      REGISTRY_PASSWORD:
        from_secret: registry_password
    commands:
      - |
          bash -c '
            set -eo pipefail
            if [ -z "${CI_COMMIT_TAG:-}" ]; then
              echo "CI_COMMIT_TAG not set" >&2
              exit 1
            fi
            if [ -z "${REGISTRY_SERVER:-}" ] || [ -z "${REGISTRY_NAMESPACE:-}" ]; then
              echo "Registry server or namespace missing" >&2
              exit 1
            fi
            TAG=$(printf '%s' "$CI_COMMIT_TAG" | sed "s#^refs/tags/##")
            export TAG
            if [ -z "${COMPOSE_PROJECT_NAME:-}" ]; then
              COMPOSE_PROJECT_NAME=harb
            fi
            REGISTRY_ROOT="${REGISTRY_SERVER:-registry.niovi.voyage}"
            REGISTRY_NS="${REGISTRY_NAMESPACE:-harb}"
            REGISTRY_BASE="$REGISTRY_ROOT/$REGISTRY_NS"

            docker login "$REGISTRY_ROOT" -u "$REGISTRY_USERNAME" -p "$REGISTRY_PASSWORD"
            # Build and publish CI base images
            node_ci_tmp=harb-node-ci-build
            playwright_ci_tmp=harb-playwright-ci-build

            docker build -f docker/Dockerfile.node-ci -t "$node_ci_tmp" .
            docker tag "$node_ci_tmp" "$REGISTRY_BASE/node-ci:$TAG"
            docker push "$REGISTRY_BASE/node-ci:$TAG"
            docker tag "$REGISTRY_BASE/node-ci:$TAG" "$REGISTRY_BASE/node-ci:latest"
            docker push "$REGISTRY_BASE/node-ci:latest"

            docker build -f docker/Dockerfile.playwright-ci -t "$playwright_ci_tmp" .
            docker tag "$playwright_ci_tmp" "$REGISTRY_BASE/playwright-ci:$TAG"
            docker push "$REGISTRY_BASE/playwright-ci:$TAG"
            docker tag "$REGISTRY_BASE/playwright-ci:$TAG" "$REGISTRY_BASE/playwright-ci:latest"
            docker push "$REGISTRY_BASE/playwright-ci:latest"

            docker-compose build ponder webapp landing txn-bot
            for service in ponder webapp landing txn-bot; do
              image=$(docker image ls --filter "label=com.docker.compose.project=$COMPOSE_PROJECT_NAME" --filter "label=com.docker.compose.service=$service" --format "{{.Repository}}:{{ .Tag }}" | head -n1)
              if [ -z "$image" ]; then
                echo "Unable to find built image for $service" >&2
                exit 1
              fi
              target="$REGISTRY_BASE/$service"
              docker tag "$image" "$target:$TAG"
              docker push "$target:$TAG"
              docker tag "$target:$TAG" "$target:latest"
              docker push "$target:latest"
            done
          '
