Verisure Deploy Pipeline

VerifiedCaution

Run the full deployment pipeline for the Verisure Italy Home Assistant integration: test, typecheck, lint, deploy via SSH to HAOS, restart, and smoke test.

Sby Skills Guide Bot
DevOpsAdvanced
7/23/2026
Claude Code
#home-assistant#deployment#ssh#smoke-test#pipeline

Recommended for

Automated summary

Automates the full deployment pipeline for a Verisure Italy Home Assistant integration: tests, typecheck, lint, SSH file transfer to HAOS, restart, and post-deploy verification.

Strengths

  • Chains blocking quality gates (pytest, pyright, ruff) before anything reaches production
  • Handles the two distinct deployment targets: integration files on HAOS and the pip-installed client library inside the Docker container
  • Waits for genuine Home Assistant availability by polling the HTTP API instead of an arbitrary sleep
  • Enforces a capture-and-restore protocol for alarm state and automations during live E2E cycles on a real panel

Limitations

  • Tightly coupled to one specific personal setup (host homeassistant, port 22222, HA_TOKEN) and not reusable as-is
  • The site-packages/python3.14 path is brittle and breaks on Home Assistant upgrades
  • Does not cover releasing (PyPI, GitHub tag), which is explicitly left manual
  • Relies on external project context (auto-memory project_ha_automations.md, scripts/smoke_test.sh) not included in the skill
When to use it

Use it when shipping a new build of the verisure_italy integration to a live Home Assistant instance and confirming it comes up cleanly.

When not to use it

Don't use it to cut a release, to work on a different integration, or when you lack SSH access to the target HAOS instance.

Security analysis

Caution
Quality score84/100

No exfiltration, obfuscated payloads, or destructive host-wide commands; every action targets the author's own HA instance for a legitimate deploy purpose. However the skill runs as root over SSH, overwrites files in place without backup, handles an HA bearer token, restarts a live system, and can leave a real alarm panel in the wrong armed state — powerful, blast-radius-heavy tooling that warrants a caution rating rather than safe.

Findings
  • •Uses SSH as root to the Home Assistant host (root@homeassistant -p 22222) and `docker exec` into the HA container to overwrite live integration and site-packages files with `cat >` — no backup or rollback path if a deploy is interrupted mid-way
  • •Overwrites a hardcoded interpreter path (/usr/local/lib/python3.14/site-packages/verisure_italy/) which can clobber or misplace files if the HA Python version changes
  • •`source .env` executes whatever shell content that file contains and pulls HA_TOKEN into the environment; the token is later passed on a command line and could be exposed via process listing/logs
  • •Restarts HA core (`ha core restart`) on a live home-automation system — disruptive to automations and any dependent services during the 30-60s window
  • •Directly mutates a real home alarm panel state (arm/disarm) against a live security system; a failure between capture and restore could leave the house disarmed
  • •Step 2 of the E2E protocol depends on an external auto-memory file (project_ha_automations.md) to know which automations to pause — if stale or missing, interfering automations may remain active
How this analysis is made

Examples

Deploy new integration version
Deploy the current verisure_italy integration to HAOS and run the full pipeline.
Verify fix on live instance
I fixed the arm/disarm bug — run the deploy pipeline with smoke test and check the logs for verisure_italy errors.
Safe E2E arm/disarm test
Run an end-to-end arm/disarm cycle against the live panel to verify the change, and restore the initial alarm state and my automations afterwards.

name: verisure-deploy description: Full deploy pipeline — test, typecheck, deploy to HAOS, smoke test

Run the full deployment pipeline. Abort on any failure — never continue past a red gate.

Steps

  1. Test suite: pytest tests/ -x -q — abort if any test fails.
  2. Type check: pyright verisure_italy/ custom_components/ — abort if any new errors.
  3. Lint: ruff check verisure_italy/ tests/ custom_components/ — abort on errors.
  4. Deploy integration files: push all integration Python files + manifest.json to HAOS via SSH pipe. Manifest is load-bearing — it carries the integration version + client library pin, so HACS and HA Dev Tools both show the deployed version correctly:
    for f in custom_components/verisure_italy/*.py custom_components/verisure_italy/manifest.json; do
      ssh root@homeassistant -p 22222 \
        "cat > /mnt/data/supervisor/homeassistant/custom_components/verisure_italy/$(basename $f)" \
        < "$f"
    done
    
  5. Deploy client library: the verisure_italy/ package is pip-installed inside the HA Docker container. Must deploy it separately — the integration imports it at runtime:
    for f in verisure_italy/*.py; do
      ssh root@homeassistant -p 22222 \
        "docker exec -i homeassistant sh -c 'cat > /usr/local/lib/python3.14/site-packages/verisure_italy/$(basename $f)'" \
        < "$f"
    done
    
    Note: The Python version path (3.14) may change with HA updates. If deploy fails with "No such file or directory", check the actual path with: ssh root@homeassistant -p 22222 "docker exec homeassistant python3 -c \"import verisure_italy; print(verisure_italy.__file__)\""
  6. Restart HA: ssh root@homeassistant -p 22222 "ha core restart" — returns immediately once the restart is scheduled; core takes ~30-60s to come back up.
  7. Wait until HA is up: do NOT hard-sleep. The Bash tool blocks long leading sleep N commands. ha core info returns info even while core is restarting, so poll the HTTP API instead — it only answers 200 once HA is fully booted:
    source .env
    until [ "$(curl -sf -o /dev/null -w '%{http_code}' \
      http://homeassistant:8123/api/ -H "Authorization: Bearer $HA_TOKEN")" = "200" ]; do
      sleep 3
    done
    
    Use this inside a plain Bash call (not Monitor) — it exits as soon as the API responds. You'll get a completion notification automatically.
  8. Smoke test: ./scripts/smoke_test.sh — abort if any entity/service missing.
  9. Log check: ssh root@homeassistant -p 22222 "docker logs homeassistant 2>&1 | grep -i verisure_italy | tail -20" — look for ERROR/WARNING.

On failure at any step: stop, show full error, do NOT proceed or auto-fix. On success: report all gates passed.

Deploy does NOT release. Releasing (PyPI + GitHub tag) is a separate manual step.

Live E2E cycle — state and automation restoration (MANDATORY)

If an end-to-end arm/disarm cycle is run against the live panel as part of verification (either within this skill or downstream in a plan like docs/plans/*.md), the panel's initial state and the user's automations must be restored afterwards. This is a real home alarm — leaving it in the wrong state is a security failure.

Protocol:

  1. Capture initial state before the first transition.
    source .env
    INITIAL=$(curl -s http://homeassistant:8123/api/states/alarm_control_panel.verisure_alarm \
      -H "Authorization: Bearer $HA_TOKEN" | python3 -c "import sys,json;print(json.load(sys.stdin)['state'])")
    echo "initial: $INITIAL"
    
  2. Pause automations that would interfere with deliberate mutations (auto-disarm, morning-disarm, actionable-disarm notification, etc.). List is in auto-memory project_ha_automations.md.
  3. Cycle through the planned transitions.
  4. Restore initial state. If INITIAL == armed_away, the last transition must be alarm_arm_away, not alarm_disarm. Never end the cycle on a different state than where you started.
  5. Re-enable automations paused in step 2.
  6. Verify: alarm_control_panel.verisure_alarm state equals INITIAL, and every paused automation is back to on.

Do not rely on a plan's default "cycle ends disarmed" template — patch the last transition to restore. If unsure what the initial state was, ASK the user before running the cycle.

From the file to a first result

The download contains exactly the content displayed on this page. This copy may differ from the latest version in the source repository.

View the source and supporting files

This download contains SKILL.md only. Any scripts, references, templates and dependencies are not included. Get the required files from the source, preserving their directory structure, before continuing.

1. Download the file

Download SKILL.md

From the root of a test project, save the file as .skill-downloads/verisure-deploy-pipeline-mrx3y00n/SKILL.md, or use the command below. This folder is for inspecting the skill before installation.

Command for macOS/Linux or WSL: requires a POSIX shell and curl. On Windows without WSL, use the download button and create the folder manually.

mkdir -p '.skill-downloads/verisure-deploy-pipeline-mrx3y00n' && curl --fail --show-error --location 'https://skills-guides.com/api/skills/verisure-deploy-pipeline-mrx3y00n/download' --output '.skill-downloads/verisure-deploy-pipeline-mrx3y00n/SKILL.md.part' && mv '.skill-downloads/verisure-deploy-pipeline-mrx3y00n/SKILL.md.part' '.skill-downloads/verisure-deploy-pipeline-mrx3y00n/SKILL.md'

2. Check prerequisites

Read SKILL.md before using it. If it references scripts or external services, inspect them and prepare the required access in your test environment.

No recognized prerequisites section in this file. This does not mean it is self-contained: libraries, tools and access requirements may be mentioned elsewhere in the content or source repository.

The platforms on this page are catalog indications. The paths below follow tool documentation; they do not prove this skill has been run in those tools. No minimum tool version is confirmed for this listing.

3. Load the skill

After inspection, copy the complete folder into your project using one of the commands below, then open a new tool session. The command stops if a folder with the same name already exists: compare the files before replacing it.

Claude Code
test -f '.skill-downloads/verisure-deploy-pipeline-mrx3y00n/SKILL.md' && test -s '.skill-downloads/verisure-deploy-pipeline-mrx3y00n/SKILL.md' && mkdir -p '.claude/skills' && test ! -e '.claude/skills/verisure-deploy' && cp -R '.skill-downloads/verisure-deploy-pipeline-mrx3y00n' '.claude/skills/verisure-deploy'

OpenSkills

OpenSkills must already be installed. The local install/read procedure is checked with OpenSkills 1.5.0, which requires Node.js ≥ 20.6.0. Catalog slugs are not resolved automatically.

Official OpenSkills installation
openskills install './.skill-downloads/verisure-deploy-pipeline-mrx3y00n'

openskills read 'verisure-deploy-pipeline-mrx3y00n'

Reading should display the installed file content and its base directory. It does not run the skill or install its dependencies.

For an agent that reads AGENTS.md, then sync the index. This command changes AGENTS.md: review the diff before using it.

openskills sync

Manual method or another tool: attach SKILL.md to a conversation, or open it in an agent that can read files. Include any required supporting resources. No universal folder is recognized by every tool.

4. Try a first task

Use a short, synthetic input: an API endpoint, a small document or an interface brief. In a new conversation, attach the file or give the agent its path, then adapt this request:

Read .skill-downloads/verisure-deploy-pipeline-mrx3y00n/SKILL.md and apply its instructions to this example: [describe a test input]. Identify any missing files, dependencies or access. Produce the result requested by the skill without inventing data or running unreviewed scripts.

Expected result: output matching the skill instructions, or a precise list of missing prerequisites. A read confirmation alone does not validate a first use. If an external resource is unavailable, that path remains untested.

Related skills