@elench/testkit 0.1.10 → 0.1.11

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "@elench/testkit",
3
- "version": "0.1.10",
4
- "description": "CLI for running k6 tests against real, ephemeral infrastructure",
3
+ "version": "0.1.11",
4
+ "description": "CLI for running manifest-defined local test suites across k6 and Playwright",
5
5
  "type": "module",
6
6
  "bin": {
7
7
  "testkit": "bin/testkit.mjs"
@@ -9,7 +9,8 @@
9
9
  "files": [
10
10
  "bin/",
11
11
  "lib/",
12
- "infra/",
12
+ "infra/neon-up.sh",
13
+ "infra/neon-down.sh",
13
14
  "vendor/"
14
15
  ],
15
16
  "dependencies": {
@@ -1,23 +0,0 @@
1
- #!/usr/bin/env bash
2
- # Ensures the Fly app exists, creating it if necessary.
3
- # Idempotent — safe to call on every run.
4
- # Requires: FLY_APP, FLY_ORG
5
- set -eo pipefail
6
-
7
- export PATH="$PATH:/snap/bin:$HOME/.fly/bin"
8
-
9
- FLY_APP="${FLY_APP:?FLY_APP required}"
10
- FLY_ORG="${FLY_ORG:?FLY_ORG required}"
11
-
12
- if fly status --app "$FLY_APP" >/dev/null 2>&1; then
13
- echo "Fly app '$FLY_APP' already exists"
14
- else
15
- echo "Creating Fly app '$FLY_APP' in org '$FLY_ORG'..."
16
- fly apps create "$FLY_APP" --org "$FLY_ORG"
17
-
18
- # Allocate IPs so *.fly.dev DNS resolves
19
- fly ips allocate-v4 --shared --app "$FLY_APP"
20
- fly ips allocate-v6 --app "$FLY_APP"
21
-
22
- echo "Fly app '$FLY_APP' created"
23
- fi
@@ -1,55 +0,0 @@
1
- #!/usr/bin/env bash
2
- # Builds Docker image from current source and pushes to Fly registry.
3
- # Requires: FLY_APP, FLY_ORG, Docker, fly CLI
4
- set -eo pipefail
5
-
6
- export PATH="$PATH:/snap/bin:$HOME/.fly/bin"
7
-
8
- STATE_DIR="${STATE_DIR:-.state}"
9
- API_DIR="$(cd "${API_DIR:?API_DIR required — set to the product directory}" && pwd)"
10
- DOCKERFILE_DIR="$(cd "${DOCKERFILE_DIR:-$API_DIR}" && pwd)"
11
- FLY_APP="${FLY_APP:?FLY_APP required}"
12
-
13
- SHORT_SHA=$(git -C "$API_DIR" rev-parse --short HEAD)
14
- IMAGE="registry.fly.io/$FLY_APP:testkit-$SHORT_SHA"
15
-
16
- # Warn if working tree is dirty (image will include uncommitted changes
17
- # but tag references HEAD)
18
- if ! git -C "$API_DIR" diff --quiet 2>/dev/null; then
19
- echo "WARNING: uncommitted changes will be included in the build"
20
- fi
21
-
22
- mkdir -p "$STATE_DIR"
23
-
24
- # Skip if image tag unchanged (same commit, clean tree)
25
- if [ -f "$STATE_DIR/fly_image" ]; then
26
- STORED_IMAGE=$(cat "$STATE_DIR/fly_image")
27
- if [ "$STORED_IMAGE" = "$IMAGE" ] && git -C "$API_DIR" diff --quiet 2>/dev/null; then
28
- echo "Image $IMAGE unchanged — skipping build"
29
- exit 0
30
- fi
31
- fi
32
-
33
- # Skip if image already exists in registry (e.g. built by a previous run without state)
34
- if git -C "$API_DIR" diff --quiet 2>/dev/null; then
35
- fly auth docker 2>/dev/null
36
- if docker manifest inspect "$IMAGE" >/dev/null 2>&1; then
37
- echo "Image $IMAGE already in registry — skipping build"
38
- echo "$IMAGE" > "$STATE_DIR/fly_image"
39
- exit 0
40
- fi
41
- fi
42
-
43
- # Ensure the Fly app exists (registry requires it)
44
- SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
45
- bash "$SCRIPT_DIR/fly-app-ensure.sh"
46
-
47
- echo "Building image: $IMAGE"
48
- docker build -t "$IMAGE" -f "$DOCKERFILE_DIR/Dockerfile" "$API_DIR"
49
-
50
- echo "Pushing to Fly registry..."
51
- fly auth docker
52
- docker push "$IMAGE"
53
-
54
- echo "$IMAGE" > "$STATE_DIR/fly_image"
55
- echo "Image ready: $IMAGE"
@@ -1,21 +0,0 @@
1
- #!/usr/bin/env bash
2
- # Destroys the Fly machine permanently (use fly-down.sh for stop/reuse)
3
- # Requires: FLY_APP
4
- set -eo pipefail
5
-
6
- export PATH="$PATH:/snap/bin:$HOME/.fly/bin"
7
-
8
- STATE_DIR="${STATE_DIR:-.state}"
9
- FLY_APP="${FLY_APP:?FLY_APP required}"
10
-
11
- if [ ! -f "$STATE_DIR/fly_machine_id" ]; then
12
- echo "No Fly machine to destroy"
13
- exit 0
14
- fi
15
-
16
- MACHINE_ID=$(cat "$STATE_DIR/fly_machine_id")
17
- echo "Destroying Fly machine: $MACHINE_ID"
18
- fly machines stop "$MACHINE_ID" --app "$FLY_APP" 2>/dev/null || true
19
- fly machines destroy "$MACHINE_ID" --app "$FLY_APP" --force 2>/dev/null || true
20
- rm -f "$STATE_DIR/fly_machine_id"
21
- echo "Fly machine destroyed"
package/infra/fly-down.sh DELETED
@@ -1,19 +0,0 @@
1
- #!/usr/bin/env bash
2
- # Stops the Fly machine (preserves it for reuse on next run)
3
- # Requires: FLY_APP
4
- set -eo pipefail
5
-
6
- export PATH="$PATH:/snap/bin:$HOME/.fly/bin"
7
-
8
- STATE_DIR="${STATE_DIR:-.state}"
9
- FLY_APP="${FLY_APP:?FLY_APP required}"
10
-
11
- if [ ! -f "$STATE_DIR/fly_machine_id" ]; then
12
- echo "No Fly machine to stop"
13
- exit 0
14
- fi
15
-
16
- MACHINE_ID=$(cat "$STATE_DIR/fly_machine_id")
17
- echo "Stopping Fly machine: $MACHINE_ID"
18
- fly machines stop "$MACHINE_ID" --app "$FLY_APP" 2>/dev/null || true
19
- echo "Fly machine stopped (preserved for next run)"
package/infra/fly-up.sh DELETED
@@ -1,142 +0,0 @@
1
- #!/usr/bin/env bash
2
- # Ensures a Fly machine is running with the correct env vars and image.
3
- # Reuses an existing stopped machine if available; creates a new one if not.
4
- # Requires: FLY_APP, FLY_REGION
5
- # Image required only for --build or new machines (FLY_IMAGE / FLY_IMAGE_DEFAULT / .state/fly_image)
6
- # Optional: DB_URL_ENV_NAME (default: DATABASE_URL), FLY_PORT, FLY_ENV_FILE
7
- set -eo pipefail
8
-
9
- export PATH="$PATH:/snap/bin:$HOME/.fly/bin"
10
-
11
- STATE_DIR="${STATE_DIR:-.state}"
12
- FLY_APP="${FLY_APP:?FLY_APP required}"
13
- FLY_REGION="${FLY_REGION:-lhr}"
14
-
15
- # Ensure the Fly app exists (idempotent — creates on first run)
16
- SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
17
- bash "$SCRIPT_DIR/fly-app-ensure.sh"
18
-
19
- # Resolve image if available (not required yet — may not be needed for reuse)
20
- if [ -z "$FLY_IMAGE" ] && [ -f "$STATE_DIR/fly_image" ]; then
21
- FLY_IMAGE="$(cat "$STATE_DIR/fly_image")"
22
- fi
23
- FLY_IMAGE="${FLY_IMAGE:-$FLY_IMAGE_DEFAULT}"
24
-
25
- if [ ! -f "$STATE_DIR/database_url" ]; then
26
- echo "ERROR: No database_url — run neon-up.sh first"
27
- exit 1
28
- fi
29
- DATABASE_URL=$(cat "$STATE_DIR/database_url")
30
-
31
- DB_URL_ENV_NAME="${DB_URL_ENV_NAME:-DATABASE_URL}"
32
- FLY_PORT="${FLY_PORT:-443:3000/tcp:tls:http}"
33
-
34
- # Load target-specific env args (sets FLY_ENV_ARGS array)
35
- FLY_ENV_ARGS=()
36
- if [ -n "$FLY_ENV_FILE" ] && [ -f "$FLY_ENV_FILE" ]; then
37
- # shellcheck disable=SC1090
38
- source "$FLY_ENV_FILE"
39
- fi
40
-
41
- MACHINE_ID=""
42
-
43
- # ── 1. Try state file ────────────────────────────────────────────────────
44
- if [ -f "$STATE_DIR/fly_machine_id" ]; then
45
- EXISTING_ID=$(cat "$STATE_DIR/fly_machine_id")
46
- if fly machines status "$EXISTING_ID" --app "$FLY_APP" >/dev/null 2>&1; then
47
- MACHINE_ID="$EXISTING_ID"
48
- else
49
- echo "Stored machine $EXISTING_ID gone — will discover or create"
50
- rm -f "$STATE_DIR/fly_machine_id"
51
- fi
52
- fi
53
-
54
- # ── 2. Discover existing machine on the app ──────────────────────────────
55
- if [ -z "$MACHINE_ID" ]; then
56
- DISCOVERED_ID=$(fly machines list --app "$FLY_APP" --json 2>/dev/null \
57
- | jq -r '.[0].id // empty')
58
- if [ -n "$DISCOVERED_ID" ]; then
59
- MACHINE_ID="$DISCOVERED_ID"
60
- echo "Discovered existing machine: $MACHINE_ID"
61
- fi
62
- fi
63
-
64
- # ── 3. Update and start existing machine ─────────────────────────────────
65
- if [ -n "$MACHINE_ID" ]; then
66
- echo "Reusing machine $MACHINE_ID — updating config"
67
-
68
- # Build update args array: always update DATABASE_URL + target env
69
- UPDATE_ARGS=(--env "$DB_URL_ENV_NAME=$DATABASE_URL" "${FLY_ENV_ARGS[@]}")
70
-
71
- # Only update image if one was provided (--build was used)
72
- if [ -n "$FLY_IMAGE" ]; then
73
- UPDATE_ARGS+=(--image "$FLY_IMAGE")
74
- fi
75
-
76
- fly machines update "$MACHINE_ID" --app "$FLY_APP" \
77
- "${UPDATE_ARGS[@]}" \
78
- --yes 2>&1
79
-
80
- # Start if not already running (update may auto-restart)
81
- fly machines start "$MACHINE_ID" --app "$FLY_APP" 2>/dev/null || true
82
- fly machines wait "$MACHINE_ID" --app "$FLY_APP" --state started --wait-timeout 60s
83
-
84
- echo "$MACHINE_ID" > "$STATE_DIR/fly_machine_id"
85
- fi
86
-
87
- # ── 4. Create new machine if needed ──────────────────────────────────────
88
- if [ -z "$MACHINE_ID" ]; then
89
- # Image is required for new machines
90
- FLY_IMAGE="${FLY_IMAGE:?FLY_IMAGE required — run with --build or set FLY_IMAGE}"
91
-
92
- echo "Creating Fly machine (app: $FLY_APP, region: $FLY_REGION)"
93
-
94
- if ! RESULT=$(fly machines run "$FLY_IMAGE" \
95
- --app "$FLY_APP" \
96
- --region "$FLY_REGION" \
97
- --vm-memory 512 \
98
- --autostop=stop \
99
- --env "$DB_URL_ENV_NAME=$DATABASE_URL" \
100
- "${FLY_ENV_ARGS[@]}" \
101
- --port "$FLY_PORT" \
102
- 2>&1); then
103
- echo "ERROR: fly machines run failed:"
104
- echo "$RESULT"
105
- exit 1
106
- fi
107
-
108
- echo "$RESULT"
109
-
110
- MACHINE_ID=$(echo "$RESULT" | grep 'Machine ID:' | awk '{print $3}')
111
- if [ -z "$MACHINE_ID" ]; then
112
- echo "ERROR: Could not extract machine ID from output"
113
- exit 1
114
- fi
115
-
116
- echo "Waiting for machine $MACHINE_ID to start..."
117
- fly machines wait "$MACHINE_ID" --app "$FLY_APP" --state started --wait-timeout 60s
118
- fi
119
-
120
- echo "$MACHINE_ID" > "$STATE_DIR/fly_machine_id"
121
-
122
- # Ephemeral machines aren't publicly DNS-routable by ID.
123
- # Route via the app hostname with fly-force-instance-id header.
124
- HOSTNAME="https://$FLY_APP.fly.dev"
125
- echo "$HOSTNAME" > "$STATE_DIR/fly_hostname"
126
-
127
- # Wait for app to become reachable (new apps need DNS propagation)
128
- echo "Waiting for $HOSTNAME to become reachable..."
129
- for i in $(seq 1 30); do
130
- if curl -sf --max-time 5 -o /dev/null "$HOSTNAME/health" \
131
- -H "fly-force-instance-id: $MACHINE_ID" 2>/dev/null; then
132
- echo "App reachable after ${i}s"
133
- break
134
- fi
135
- if [ "$i" -eq 30 ]; then
136
- echo "WARNING: App not reachable after 30s — DNS may still be propagating"
137
- fi
138
- sleep 1
139
- done
140
-
141
- echo "Fly machine ready: $MACHINE_ID"
142
- echo "Hostname: $HOSTNAME (routed via fly-force-instance-id header)"