first commit

This commit is contained in:
Chris
2026-03-23 20:23:58 +08:00
commit 74d612aca1
3193 changed files with 692056 additions and 0 deletions

View File

@@ -0,0 +1,15 @@
API_BASE_URL=https://mktapi.ose.tw
ACCESS_TOKEN=
BASE_URL=
EXPERIMENT_ID=
EXPERIMENT_KEY=
VARIANT_ID=
VARIANT_KEY=
SITE_ID=
SITE_KEY=
PAGE_URL=
VISITOR_ID=visitor_001
ASSIGNMENT_SALT=runtime-smoke
RELEASE_ID=
RELEASE_VERSION=1
EDITOR_SESSION_ID=

View File

@@ -0,0 +1,23 @@
#!/usr/bin/env bash
set -euo pipefail
ROOT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")/.." && pwd)"
SOURCE_FILE="${ROOT_DIR}/scripts/.env.validation.example"
TARGET_FILE="${1:-}"
if [[ -z "${TARGET_FILE}" ]]; then
echo "Usage: bash scripts/bootstrap_validation_env.sh <target-env-file>"
echo "Example: bash scripts/bootstrap_validation_env.sh /tmp/mkt.validation.env"
exit 1
fi
if [[ -f "${TARGET_FILE}" ]]; then
echo "Target file already exists: ${TARGET_FILE}"
exit 1
fi
cp "${SOURCE_FILE}" "${TARGET_FILE}"
echo "Created validation env template:"
echo " ${TARGET_FILE}"

View File

@@ -0,0 +1,101 @@
#!/usr/bin/env bash
set -euo pipefail
ENV_FILE="${1:-}"
BATCH="${2:-all}"
if [[ -z "${ENV_FILE}" ]]; then
echo "Usage: bash scripts/check_validation_env.sh <env-file> [batch]"
exit 1
fi
if [[ ! -f "${ENV_FILE}" ]]; then
echo "Env file not found: ${ENV_FILE}"
exit 1
fi
set -a
# shellcheck disable=SC1090
source "${ENV_FILE}"
set +a
check_vars() {
local label="$1"
shift
local missing=()
local var_name value
for var_name in "$@"; do
value="${!var_name:-}"
if [[ -z "${value}" ]]; then
missing+=("${var_name}")
fi
done
if (( ${#missing[@]} > 0 )); then
echo ""
echo "[FAIL] ${label}"
printf ' - missing: %s\n' "${missing[@]}"
return 1
fi
echo ""
echo "[PASS] ${label}"
return 0
}
check_runtime_site() {
if [[ -z "${SITE_ID:-}" && -z "${SITE_KEY:-}" ]]; then
echo ""
echo "[FAIL] runtime smoke"
echo " - missing: SITE_ID or SITE_KEY"
return 1
fi
echo ""
echo "[PASS] runtime smoke site scope"
return 0
}
run_batch_check() {
local batch_name="$1"
local failed=0
case "${batch_name}" in
batch1|batch2)
check_vars "validation smoke" API_BASE_URL ACCESS_TOKEN || failed=1
;;
batch3)
check_vars "editor smoke" API_BASE_URL ACCESS_TOKEN VARIANT_ID BASE_URL || failed=1
;;
batch4)
check_vars "runtime smoke" API_BASE_URL PAGE_URL EXPERIMENT_ID EXPERIMENT_KEY VARIANT_ID VARIANT_KEY || failed=1
check_runtime_site || failed=1
;;
batch1-3)
run_batch_check batch1 || failed=1
run_batch_check batch3 || failed=1
;;
all)
run_batch_check batch1 || failed=1
run_batch_check batch3 || failed=1
run_batch_check batch4 || failed=1
;;
*)
echo "Unknown batch: ${batch_name}"
exit 1
;;
esac
return "${failed}"
}
if run_batch_check "${BATCH}"; then
echo ""
echo "Validation env check passed for '${BATCH}'."
else
echo ""
echo "Validation env check failed for '${BATCH}'."
exit 1
fi

View File

@@ -0,0 +1,102 @@
#!/usr/bin/env bash
set -euo pipefail
API_BASE_URL="${API_BASE_URL:-}"
ACCESS_TOKEN="${ACCESS_TOKEN:-}"
VARIANT_ID="${VARIANT_ID:-}"
BASE_URL="${BASE_URL:-}"
if [[ -z "${API_BASE_URL}" ]]; then
echo "Missing API_BASE_URL"
exit 1
fi
if [[ -z "${ACCESS_TOKEN}" ]]; then
echo "Missing ACCESS_TOKEN"
exit 1
fi
if [[ -z "${VARIANT_ID}" ]]; then
echo "Missing VARIANT_ID"
exit 1
fi
if [[ -z "${BASE_URL}" ]]; then
echo "Missing BASE_URL"
exit 1
fi
AUTH_HEADER="Authorization: Bearer ${ACCESS_TOKEN}"
CONTENT_HEADER="Content-Type: application/json"
echo ""
echo "== Create Editor Session =="
curl --silent --show-error --fail \
-X POST \
-H "${AUTH_HEADER}" \
-H "${CONTENT_HEADER}" \
-d "{
\"variant_id\": \"${VARIANT_ID}\",
\"base_url\": \"${BASE_URL}\",
\"mode\": \"edit\"
}" \
"${API_BASE_URL}/api/editor/sessions"
echo ""
echo ""
echo "== Load Variant Changes =="
curl --silent --show-error --fail \
-H "${AUTH_HEADER}" \
"${API_BASE_URL}/api/editor/variants/${VARIANT_ID}/changes"
echo ""
echo ""
echo "== Save Variant Changes =="
curl --silent --show-error --fail \
-X PUT \
-H "${AUTH_HEADER}" \
-H "${CONTENT_HEADER}" \
-d "{
\"items\": [
{
\"change_type\": \"replace_text\",
\"selector_type\": \"css\",
\"selector_value\": \"h1\",
\"sort_order\": 0,
\"enabled\": true,
\"payload\": {
\"text\": \"Smoke Test Heading\"
}
}
]
}" \
"${API_BASE_URL}/api/editor/variants/${VARIANT_ID}/changes"
echo ""
echo ""
echo "== Build Preview =="
curl --silent --show-error --fail \
-X POST \
-H "${AUTH_HEADER}" \
-H "${CONTENT_HEADER}" \
-d "{
\"variant_id\": \"${VARIANT_ID}\",
\"items\": [
{
\"change_type\": \"replace_text\",
\"selector_type\": \"css\",
\"selector_value\": \"h1\",
\"sort_order\": 0,
\"enabled\": true,
\"payload\": {
\"text\": \"Smoke Test Heading\"
}
}
]
}" \
"${API_BASE_URL}/api/editor/previews/build"
echo ""
echo ""
echo "Editor smoke test completed."

View File

@@ -0,0 +1,148 @@
#!/usr/bin/env bash
set -euo pipefail
BATCH="${1:-all}"
ENV_FILE="${2:-}"
ROOT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")/.." && pwd)"
load_env_file() {
local env_file="$1"
if [[ -z "${env_file}" ]]; then
return 0
fi
if [[ ! -f "${env_file}" ]]; then
echo "Env file not found: ${env_file}"
exit 1
fi
set -a
# shellcheck disable=SC1090
source "${env_file}"
set +a
}
check_required_vars() {
local batch_name="$1"
shift
local missing=()
local var_name value
for var_name in "$@"; do
value="${!var_name:-}"
if [[ -z "${value}" ]]; then
missing+=("${var_name}")
fi
done
if (( ${#missing[@]} > 0 )); then
echo ""
echo "Missing required env for ${batch_name}:"
printf ' - %s\n' "${missing[@]}"
echo ""
echo "Tip:"
echo " Copy scripts/.env.validation.example and fill the required values."
exit 1
fi
}
run_validation_smoke() {
check_required_vars "validation smoke" API_BASE_URL ACCESS_TOKEN
echo ""
echo ">>> Batch 1 / Batch 2: validation_smoke_test.sh"
bash "${ROOT_DIR}/scripts/validation_smoke_test.sh"
}
run_editor_smoke() {
check_required_vars "editor smoke" API_BASE_URL ACCESS_TOKEN VARIANT_ID BASE_URL
echo ""
echo ">>> Batch 3: editor_smoke_test.sh"
bash "${ROOT_DIR}/scripts/editor_smoke_test.sh"
}
run_runtime_smoke() {
check_required_vars \
"runtime smoke" \
API_BASE_URL \
PAGE_URL \
EXPERIMENT_ID \
EXPERIMENT_KEY \
VARIANT_ID \
VARIANT_KEY
if [[ -z "${SITE_ID:-}" && -z "${SITE_KEY:-}" ]]; then
echo ""
echo "Missing required env for runtime smoke:"
echo " - SITE_ID or SITE_KEY"
echo ""
echo "Tip:"
echo " Provide at least one of SITE_ID / SITE_KEY in your validation env."
exit 1
fi
echo ""
echo ">>> Batch 4: runtime_smoke_test.sh"
bash "${ROOT_DIR}/scripts/runtime_smoke_test.sh"
}
print_usage() {
cat <<'EOF'
Usage:
bash scripts/run_validation_batch.sh <batch> [env-file]
Available batch values:
batch1 Run health/auth smoke
batch2 Run admin data smoke
batch3 Run editor smoke
batch4 Run runtime smoke
batch1-3 Run batch1 + batch2 + batch3
all Run batch1 + batch2 + batch3 + batch4
Recommended:
1. copy scripts/.env.validation.example to your own env file
2. fill real staging values
3. run batch1-3 first
4. pass the env file path as the second argument
EOF
}
load_env_file "${ENV_FILE}"
case "${BATCH}" in
batch1)
run_validation_smoke
;;
batch2)
run_validation_smoke
;;
batch3)
run_editor_smoke
;;
batch4)
run_runtime_smoke
;;
batch1-3)
run_validation_smoke
run_editor_smoke
;;
all)
run_validation_smoke
run_editor_smoke
run_runtime_smoke
;;
help|-h|--help)
print_usage
exit 0
;;
*)
echo "Unknown batch: ${BATCH}"
echo ""
print_usage
exit 1
;;
esac
echo ""
echo "Validation batch '${BATCH}' completed."

View File

@@ -0,0 +1,166 @@
#!/usr/bin/env bash
set -euo pipefail
API_BASE_URL="${API_BASE_URL:-}"
SITE_ID="${SITE_ID:-}"
SITE_KEY="${SITE_KEY:-}"
EXPERIMENT_ID="${EXPERIMENT_ID:-}"
EXPERIMENT_KEY="${EXPERIMENT_KEY:-}"
VARIANT_ID="${VARIANT_ID:-}"
VARIANT_KEY="${VARIANT_KEY:-}"
VISITOR_ID="${VISITOR_ID:-visitor_001}"
PAGE_URL="${PAGE_URL:-}"
ASSIGNMENT_SALT="${ASSIGNMENT_SALT:-runtime-smoke}"
RELEASE_ID="${RELEASE_ID:-}"
RELEASE_VERSION="${RELEASE_VERSION:-1}"
if [[ -z "${API_BASE_URL}" ]]; then
echo "Missing API_BASE_URL"
exit 1
fi
if [[ -z "${SITE_ID}" && -z "${SITE_KEY}" ]]; then
echo "Missing SITE_ID or SITE_KEY"
exit 1
fi
if [[ -z "${PAGE_URL}" ]]; then
echo "Missing PAGE_URL"
exit 1
fi
if [[ -z "${EXPERIMENT_ID}" || -z "${EXPERIMENT_KEY}" ]]; then
echo "Missing EXPERIMENT_ID or EXPERIMENT_KEY"
exit 1
fi
if [[ -z "${VARIANT_ID}" || -z "${VARIANT_KEY}" ]]; then
echo "Missing VARIANT_ID or VARIANT_KEY"
exit 1
fi
CONTENT_HEADER="Content-Type: application/json"
EXPERIMENT_JSON="$(cat <<EOF
{
"experiment_id": "${EXPERIMENT_ID}",
"experiment_key": "${EXPERIMENT_KEY}",
"status": "running",
"site_key": "${SITE_KEY}",
"assignment_salt": "${ASSIGNMENT_SALT}",
"release_id": "${RELEASE_ID}",
"release_version": ${RELEASE_VERSION},
"payload": {
"operations": [
{
"selector_type": "css",
"selector_value": "h1",
"action": "replace_text",
"payload": {
"text": "Smoke Test Runtime Heading"
}
}
]
},
"variants": [
{
"id": "${VARIANT_ID}",
"variant_key": "${VARIANT_KEY}",
"traffic_weight": 50,
"is_control": false
},
{
"id": "${VARIANT_ID}_control",
"variant_key": "control",
"traffic_weight": 50,
"is_control": true
}
]
}
EOF
)"
echo ""
echo "== Runtime Bootstrap =="
curl --silent --show-error --fail \
-X POST \
-H "${CONTENT_HEADER}" \
-d "{
\"site_id\": \"${SITE_ID}\",
\"site_key\": \"${SITE_KEY}\",
\"url\": \"${PAGE_URL}\",
\"visitor_id\": \"${VISITOR_ID}\",
\"user_agent\": \"Mozilla/5.0\"
}" \
"${API_BASE_URL}/api/runtime/bootstrap"
echo ""
echo ""
echo "== Runtime Assign =="
curl --silent --show-error --fail \
-X POST \
-H "${CONTENT_HEADER}" \
-d "{
\"visitor_id\": \"${VISITOR_ID}\",
\"experiment\": ${EXPERIMENT_JSON}
}" \
"${API_BASE_URL}/api/runtime/assign"
echo ""
echo ""
echo "== Runtime Payload =="
curl --silent --show-error --fail \
-X POST \
-H "${CONTENT_HEADER}" \
-d "{
\"visitor_id\": \"${VISITOR_ID}\",
\"experiment\": ${EXPERIMENT_JSON}
}" \
"${API_BASE_URL}/api/runtime/payload"
echo ""
echo ""
echo "== Runtime Impression Event =="
curl --silent --show-error --fail \
-X POST \
-H "${CONTENT_HEADER}" \
-d "{
\"site_id\": \"${SITE_ID}\",
\"site_key\": \"${SITE_KEY}\",
\"experiment_id\": \"${EXPERIMENT_ID}\",
\"experiment_key\": \"${EXPERIMENT_KEY}\",
\"variant_id\": \"${VARIANT_ID}\",
\"variant_key\": \"${VARIANT_KEY}\",
\"visitor_id\": \"${VISITOR_ID}\",
\"event_name\": \"experiment_impression\",
\"payload\": {
\"page\": \"${PAGE_URL}\"
}
}" \
"${API_BASE_URL}/api/runtime/events/impression"
echo ""
echo ""
echo "== Runtime Conversion Event =="
curl --silent --show-error --fail \
-X POST \
-H "${CONTENT_HEADER}" \
-d "{
\"site_id\": \"${SITE_ID}\",
\"site_key\": \"${SITE_KEY}\",
\"experiment_id\": \"${EXPERIMENT_ID}\",
\"experiment_key\": \"${EXPERIMENT_KEY}\",
\"variant_id\": \"${VARIANT_ID}\",
\"variant_key\": \"${VARIANT_KEY}\",
\"visitor_id\": \"${VISITOR_ID}\",
\"event_name\": \"experiment_conversion\",
\"payload\": {
\"page\": \"${PAGE_URL}\"
}
}" \
"${API_BASE_URL}/api/runtime/events/conversion"
echo ""
echo ""
echo "Runtime smoke test completed."

View File

@@ -0,0 +1,33 @@
#!/usr/bin/env bash
set -euo pipefail
ROOT_DIR="$(cd "$(dirname "$0")/.." && pwd)"
FRONTEND_DIR="$ROOT_DIR/frontend"
DEFAULT_HOST="127.0.0.1"
DEFAULT_PORT="3000"
HOST="${1:-$DEFAULT_HOST}"
PORT="${2:-$DEFAULT_PORT}"
cd "$FRONTEND_DIR"
mkdir -p env
if [ ! -f "env/.env.local" ]; then
cat > "env/.env.local" <<'EOF'
VITE_DIRECTUS_BASE_URL=https://mktcms.ose.tw
VITE_MKTAPI_BASE_URL=http://127.0.0.1:8000
VITE_DIRECTUS_DEBUG_TOKEN=
_API_URL=https://mktcms.ose.tw
_API_TOKEN=
EOF
fi
echo "Starting frontend dev server..."
echo " host: $HOST"
echo " port: $PORT"
echo " env : $FRONTEND_DIR/env/.env.local"
npm run dev -- --host "$HOST" --port "$PORT"

View File

@@ -0,0 +1,27 @@
#!/usr/bin/env bash
set -euo pipefail
BATCH="${1:-batch1-3}"
ENV_FILE="${2:-}"
ROOT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")/.." && pwd)"
if [[ "${BATCH}" == "help" || "${BATCH}" == "-h" || "${BATCH}" == "--help" ]]; then
echo "Usage: bash scripts/start_validation.sh <batch> <env-file>"
echo "Example: bash scripts/start_validation.sh batch1-3 path/to/your.validation.env"
exit 0
fi
if [[ -z "${ENV_FILE}" ]]; then
echo "Usage: bash scripts/start_validation.sh <batch> <env-file>"
echo "Example: bash scripts/start_validation.sh batch1-3 path/to/your.validation.env"
exit 1
fi
echo ""
echo "== Step 1: Validation Env Check =="
bash "${ROOT_DIR}/scripts/check_validation_env.sh" "${ENV_FILE}" "${BATCH}"
echo ""
echo "== Step 2: Run Validation Batch =="
bash "${ROOT_DIR}/scripts/run_validation_batch.sh" "${BATCH}" "${ENV_FILE}"

View File

@@ -0,0 +1,73 @@
#!/usr/bin/env bash
set -euo pipefail
API_BASE_URL="${API_BASE_URL:-}"
ACCESS_TOKEN="${ACCESS_TOKEN:-}"
EXPERIMENT_ID="${EXPERIMENT_ID:-}"
if [[ -z "${API_BASE_URL}" ]]; then
echo "Missing API_BASE_URL"
echo "Example: API_BASE_URL=https://mktapi.ose.tw"
exit 1
fi
if [[ -z "${ACCESS_TOKEN}" ]]; then
echo "Missing ACCESS_TOKEN"
echo "Example: ACCESS_TOKEN=<mkt_access_token>"
exit 1
fi
AUTH_HEADER="Authorization: Bearer ${ACCESS_TOKEN}"
echo ""
echo "== Health =="
curl --silent --show-error --fail \
"${API_BASE_URL}/health"
echo ""
echo ""
echo "== Readiness =="
curl --silent --show-error --fail \
"${API_BASE_URL}/health/ready"
echo ""
echo ""
echo "== Auth / Me =="
curl --silent --show-error --fail \
-H "${AUTH_HEADER}" \
"${API_BASE_URL}/api/auth/me"
echo ""
echo ""
echo "== Experiments =="
curl --silent --show-error --fail \
-H "${AUTH_HEADER}" \
"${API_BASE_URL}/api/admin/experiments"
if [[ -n "${EXPERIMENT_ID}" ]]; then
echo ""
echo ""
echo "== Experiment Detail =="
curl --silent --show-error --fail \
-H "${AUTH_HEADER}" \
"${API_BASE_URL}/api/admin/experiments/${EXPERIMENT_ID}"
echo ""
echo ""
echo "== Variants By Experiment =="
curl --silent --show-error --fail \
-H "${AUTH_HEADER}" \
"${API_BASE_URL}/api/admin/variants?experiment_id=${EXPERIMENT_ID}"
echo ""
echo ""
echo "== Releases By Experiment =="
curl --silent --show-error --fail \
-H "${AUTH_HEADER}" \
"${API_BASE_URL}/api/admin/releases?experiment_id=${EXPERIMENT_ID}"
fi
echo ""
echo ""
echo "Smoke test completed."