Initial commit: AutoTrader Marker Firefox extension
Mark AutoTrader listings as 'not wanted' on both search results and detail pages. Includes the unlisted signing / auto-update pipeline (web-ext + dist/updates.json polled by Firefox). Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
This commit is contained in:
Executable
+119
@@ -0,0 +1,119 @@
|
||||
#!/usr/bin/env bash
|
||||
# Release a new signed XPI, update dist/updates.json, and prepare a commit.
|
||||
# Requires: WEB_EXT_API_KEY, WEB_EXT_API_SECRET (AMO JWT credentials).
|
||||
#
|
||||
# Usage:
|
||||
# bin/release.sh patch # 0.1.0 -> 0.1.1
|
||||
# bin/release.sh minor # 0.1.0 -> 0.2.0
|
||||
# bin/release.sh major # 0.1.0 -> 1.0.0
|
||||
# bin/release.sh 1.2.3 # explicit version
|
||||
|
||||
set -euo pipefail
|
||||
|
||||
BUMP="${1:-patch}"
|
||||
REPO_ROOT="$(cd "$(dirname "$0")/.." && pwd)"
|
||||
cd "$REPO_ROOT"
|
||||
|
||||
ADDON_ID="autotrader-marker@tony.codes"
|
||||
RAW_BASE="https://git.nocker.cloud/tony/autotrader-marker/raw/branch/main/dist"
|
||||
|
||||
: "${WEB_EXT_API_KEY:?WEB_EXT_API_KEY is required (AMO JWT issuer)}"
|
||||
: "${WEB_EXT_API_SECRET:?WEB_EXT_API_SECRET is required (AMO JWT secret)}"
|
||||
|
||||
# --- Compute next version ---
|
||||
CURRENT=$(node -p "require('./manifest.json').version")
|
||||
if [[ "$BUMP" =~ ^[0-9]+\.[0-9]+\.[0-9]+$ ]]; then
|
||||
NEXT="$BUMP"
|
||||
else
|
||||
NEXT=$(node -e "
|
||||
const [maj,min,pat] = require('./manifest.json').version.split('.').map(Number);
|
||||
const bump = process.argv[1];
|
||||
let v;
|
||||
if (bump === 'major') v = [maj+1, 0, 0];
|
||||
else if (bump === 'minor') v = [maj, min+1, 0];
|
||||
else v = [maj, min, pat+1];
|
||||
console.log(v.join('.'));
|
||||
" "$BUMP")
|
||||
fi
|
||||
|
||||
echo "→ Bumping $CURRENT → $NEXT"
|
||||
|
||||
# --- Write version to manifest.json and package.json ---
|
||||
node -e "
|
||||
const fs = require('fs');
|
||||
for (const f of ['manifest.json','package.json']) {
|
||||
const j = JSON.parse(fs.readFileSync(f, 'utf8'));
|
||||
j.version = process.argv[1];
|
||||
fs.writeFileSync(f, JSON.stringify(j, null, 2) + '\n');
|
||||
}
|
||||
" "$NEXT"
|
||||
|
||||
# --- Sign via AMO ---
|
||||
ARTIFACTS_DIR="$REPO_ROOT/.web-ext-artifacts"
|
||||
rm -rf "$ARTIFACTS_DIR"
|
||||
mkdir -p "$ARTIFACTS_DIR"
|
||||
|
||||
echo "→ Signing via AMO (unlisted channel)"
|
||||
npx --yes web-ext sign \
|
||||
--source-dir="$REPO_ROOT" \
|
||||
--artifacts-dir="$ARTIFACTS_DIR" \
|
||||
--channel=unlisted \
|
||||
--api-key="$WEB_EXT_API_KEY" \
|
||||
--api-secret="$WEB_EXT_API_SECRET" \
|
||||
--ignore-files "node_modules/**" "dist/**" "bin/**" "package.json" "package-lock.json" "README.md" ".gitignore"
|
||||
|
||||
# --- Move signed XPI to dist/ with a predictable name ---
|
||||
SIGNED_XPI=$(find "$ARTIFACTS_DIR" -name '*.xpi' -type f | head -1)
|
||||
if [[ -z "$SIGNED_XPI" ]]; then
|
||||
echo "ERROR: no signed XPI produced — check AMO output above" >&2
|
||||
exit 1
|
||||
fi
|
||||
|
||||
TARGET="dist/autotrader-marker-$NEXT.xpi"
|
||||
mkdir -p dist
|
||||
cp "$SIGNED_XPI" "$TARGET"
|
||||
echo "→ Signed XPI: $TARGET"
|
||||
|
||||
# --- Regenerate dist/updates.json (keep all historical versions) ---
|
||||
node -e "
|
||||
const fs = require('fs');
|
||||
const path = 'dist/updates.json';
|
||||
const j = fs.existsSync(path) ? JSON.parse(fs.readFileSync(path, 'utf8')) : { addons: {} };
|
||||
const addonId = process.argv[1];
|
||||
const version = process.argv[2];
|
||||
const rawBase = process.argv[3];
|
||||
j.addons = j.addons || {};
|
||||
j.addons[addonId] = j.addons[addonId] || { updates: [] };
|
||||
const updates = j.addons[addonId].updates.filter(u => u.version !== version);
|
||||
updates.push({ version, update_link: rawBase + '/autotrader-marker-' + version + '.xpi' });
|
||||
// Sort ascending by semver (Firefox picks the highest applicable)
|
||||
updates.sort((a, b) => {
|
||||
const pa = a.version.split('.').map(Number);
|
||||
const pb = b.version.split('.').map(Number);
|
||||
for (let i = 0; i < 3; i++) if (pa[i] !== pb[i]) return pa[i] - pb[i];
|
||||
return 0;
|
||||
});
|
||||
j.addons[addonId].updates = updates;
|
||||
fs.writeFileSync(path, JSON.stringify(j, null, 2) + '\n');
|
||||
" "$ADDON_ID" "$NEXT" "$RAW_BASE"
|
||||
|
||||
echo "→ dist/updates.json updated"
|
||||
|
||||
# --- Summarise for the developer ---
|
||||
cat <<EOF
|
||||
|
||||
✔ Release $NEXT built and signed.
|
||||
|
||||
Next steps:
|
||||
1. Review the diff:
|
||||
git status
|
||||
git diff
|
||||
2. Commit and push:
|
||||
git add manifest.json package.json dist/
|
||||
git commit -m "Release v$NEXT"
|
||||
git push origin main
|
||||
3. Firefox will auto-update installed copies within ~24h
|
||||
(or via about:addons → gear → "Check for Updates").
|
||||
|
||||
Signed XPI: $TARGET
|
||||
EOF
|
||||
Reference in New Issue
Block a user