tractatus/scripts/deploy-governance-files.sh
TheFlow ac2db33732 fix(submissions): restructure Economist package and fix article display
- Create Economist SubmissionTracking package correctly:
  * mainArticle = full blog post content
  * coverLetter = 216-word SIR— letter
  * Links to blog post via blogPostId
- Archive 'Letter to The Economist' from blog posts (it's the cover letter)
- Fix date display on article cards (use published_at)
- Target publication already displaying via blue badge

Database changes:
- Make blogPostId optional in SubmissionTracking model
- Economist package ID: 68fa85ae49d4900e7f2ecd83
- Le Monde package ID: 68fa2abd2e6acd5691932150

Next: Enhanced modal with tabs, validation, export

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-10-24 08:47:42 +13:00

147 lines
4.7 KiB
Bash
Executable file

#!/bin/bash
# Tractatus Governance Files Deployment Script
# Syncs .claude/ directory files to production
set -e
# Colors for output
RED='\033[0;31m'
GREEN='\033[0;32m'
YELLOW='\033[1;33m'
NC='\033[0m' # No Color
# Configuration
SSH_KEY="$HOME/.ssh/tractatus_deploy"
REMOTE_USER="ubuntu"
REMOTE_HOST="vps-93a693da.vps.ovh.net"
REMOTE_PATH="/var/www/tractatus"
LOCAL_CLAUDE_DIR=".claude"
echo -e "${YELLOW}━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━${NC}"
echo -e "${YELLOW} TRACTATUS GOVERNANCE FILES DEPLOYMENT${NC}"
echo -e "${YELLOW}━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━${NC}"
echo ""
# Check if .claude directory exists
if [ ! -d "$LOCAL_CLAUDE_DIR" ]; then
echo -e "${RED}✗ Error: .claude directory not found${NC}"
exit 1
fi
echo -e "${GREEN}[1/4] PRE-DEPLOYMENT CHECKS${NC}"
echo ""
# Check for instruction-history.json
if [ ! -f "$LOCAL_CLAUDE_DIR/instruction-history.json" ]; then
echo -e "${RED}✗ Error: instruction-history.json not found${NC}"
exit 1
fi
echo -e "${GREEN}✓ instruction-history.json found${NC}"
# Get file info
FILE_SIZE=$(du -h "$LOCAL_CLAUDE_DIR/instruction-history.json" | cut -f1)
INSTRUCTION_COUNT=$(node -e "
const fs = require('fs');
const data = JSON.parse(fs.readFileSync('$LOCAL_CLAUDE_DIR/instruction-history.json', 'utf8'));
const active = data.instructions.filter(i => i.active !== false).length;
console.log(active);
")
echo -e "${GREEN}✓ File size: $FILE_SIZE${NC}"
echo -e "${GREEN}✓ Active instructions: $INSTRUCTION_COUNT${NC}"
echo ""
# Check SSH connection
echo -e "${GREEN}[2/4] CHECKING CONNECTION${NC}"
echo ""
if ! ssh -i "$SSH_KEY" -o ConnectTimeout=5 "${REMOTE_USER}@${REMOTE_HOST}" "echo 'Connection OK'" 2>/dev/null; then
echo -e "${RED}✗ Error: Cannot connect to production server${NC}"
exit 1
fi
echo -e "${GREEN}✓ SSH connection successful${NC}"
echo ""
# Show what will be deployed
echo -e "${GREEN}[3/4] FILES TO DEPLOY${NC}"
echo ""
echo " Source: $LOCAL_CLAUDE_DIR/"
echo " Destination: ${REMOTE_USER}@${REMOTE_HOST}:${REMOTE_PATH}/.claude/"
echo ""
echo " Files:"
echo " - instruction-history.json ($FILE_SIZE, $INSTRUCTION_COUNT rules)"
echo " - session-state.json (if exists)"
echo " - token-checkpoints.json (if exists)"
echo " - metrics/ (if exists)"
echo " - backups/ (if exists)"
echo ""
# Confirmation
read -p "Continue with deployment? (yes/NO): " confirm
if [ "$confirm" != "yes" ]; then
echo -e "${YELLOW}Deployment cancelled${NC}"
exit 0
fi
echo ""
echo -e "${GREEN}[4/4] DEPLOYING${NC}"
echo ""
# Create backup on production first
echo "Creating backup on production..."
ssh -i "$SSH_KEY" "${REMOTE_USER}@${REMOTE_HOST}" "
cd $REMOTE_PATH/.claude
if [ -f instruction-history.json ]; then
cp instruction-history.json instruction-history.json.backup-\$(date +%Y%m%d-%H%M%S)
echo '✓ Backup created'
fi
"
# Deploy files
echo "Deploying governance files..."
rsync -avz --progress \
-e "ssh -i $SSH_KEY" \
--exclude='*.log' \
--exclude='temp/' \
"$LOCAL_CLAUDE_DIR/" \
"${REMOTE_USER}@${REMOTE_HOST}:${REMOTE_PATH}/.claude/"
echo ""
# Verify deployment
echo "Verifying deployment..."
REMOTE_COUNT=$(ssh -i "$SSH_KEY" "${REMOTE_USER}@${REMOTE_HOST}" "
cd $REMOTE_PATH
node -e \"
const fs = require('fs');
const data = JSON.parse(fs.readFileSync('.claude/instruction-history.json', 'utf8'));
const active = data.instructions.filter(i => i.active !== false).length;
console.log(active);
\"
")
if [ "$REMOTE_COUNT" = "$INSTRUCTION_COUNT" ]; then
echo -e "${GREEN}✓ Verification successful${NC}"
echo -e "${GREEN} Local: $INSTRUCTION_COUNT active rules${NC}"
echo -e "${GREEN} Remote: $REMOTE_COUNT active rules${NC}"
else
echo -e "${YELLOW}⚠ Warning: Count mismatch${NC}"
echo -e "${YELLOW} Local: $INSTRUCTION_COUNT active rules${NC}"
echo -e "${YELLOW} Remote: $REMOTE_COUNT active rules${NC}"
fi
echo ""
echo -e "${GREEN}━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━${NC}"
echo -e "${GREEN} DEPLOYMENT COMPLETE${NC}"
echo -e "${GREEN}━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━${NC}"
echo ""
echo "Next steps:"
echo "1. Run sync on production:"
echo " ssh -i $SSH_KEY ${REMOTE_USER}@${REMOTE_HOST} 'cd $REMOTE_PATH && node scripts/sync-instructions-to-db.js --force'"
echo ""
echo "2. Verify sync health:"
echo " curl -s https://agenticgovernance.digital/health"
echo ""