Skip to content

Commit 604f51e

Browse files
Patras3claude
andcommitted
Release Camera Snapshot Processor 1.0.0
Professional Home Assistant integration for advanced camera snapshot processing with web-based configuration UI. Features: - Image processing: Flexible resize, crop, quality control (JPEG 1-100%) - Professional web UI: Live preview, interactive crop tool, tabbed configuration - Advanced overlays: Date/time stamps, custom text with HA templates - State icons: Multi-state rules with 7000+ MDI icons (CDN-powered) - Complex conditions: equals, contains, gt/lt, in list, etc. - Per-state customization: icons, text, colors, backgrounds - Real-time template rendering with error detection - Stream support: RTSP passthrough with credential sanitization - Performance: In-memory processing, font caching, zero disk I/O - Security: Daily CVE scans, CodeQL analysis, proper auth Tested with Home Assistant ≥ 2025.9.4, Python ≥ 3.11 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude <noreply@anthropic.com>
1 parent d88c636 commit 604f51e

47 files changed

Lines changed: 11854 additions & 2 deletions

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

.github/SECURITY.md

Lines changed: 109 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,109 @@
1+
# Security Policy
2+
3+
## Supported Versions
4+
5+
| Version | Supported |
6+
| ------- | ------------------ |
7+
| 0.9.x | :white_check_mark: |
8+
| < 0.9 | :x: |
9+
10+
## Security Model
11+
12+
**Important**: This integration relies primarily on **Home Assistant's security model**. Camera Snapshot Processor is a lightweight image processing layer that:
13+
14+
- Does not store credentials (Home Assistant does)
15+
- Does not handle authentication (Home Assistant does)
16+
- Does not expose additional network endpoints
17+
- Simply processes images from cameras already configured in Home Assistant
18+
19+
The main security is provided by Home Assistant itself. This integration is as secure as your Home Assistant installation.
20+
21+
## Reporting a Vulnerability
22+
23+
This is an open source hobby project maintained in spare time. If you find a security issue:
24+
25+
1. **For critical issues**: Use [GitHub Security Advisory](https://github.com/Patras3/camera-snapshot-processor/security/advisories/new)
26+
2. **For non-critical issues**: Regular [GitHub Issues](https://github.com/Patras3/camera-snapshot-processor/issues) are fine
27+
28+
### What to Include
29+
30+
- Description of the vulnerability
31+
- Steps to reproduce
32+
- Potential impact
33+
- Any suggested fixes (optional)
34+
35+
### Response Timeline
36+
37+
This is a hobby project, so:
38+
- **Response**: Best effort, when time allows
39+
- **Fixes**: Will be included in next scheduled release
40+
- **Critical CVEs**: May warrant immediate patch release if severe
41+
42+
We use automated tools (pip-audit, CodeQL, Dependabot) to catch known vulnerabilities, but fixes are released on a regular schedule rather than emergency basis (unless critical).
43+
44+
## Automated Security Scanning
45+
46+
While this is a hobby project, we still care about security:
47+
48+
- **pip-audit**: Daily scans for known CVEs in dependencies
49+
- **CodeQL**: Automated code analysis
50+
- **Dependabot**: Automatic PR for dependency updates
51+
52+
These tools catch issues automatically, but fixes are released on a normal schedule.
53+
54+
## Security Through Design
55+
56+
### Minimal Attack Surface
57+
58+
- **Only one dependency**: Pillow (Python Imaging Library)
59+
- No network listeners, no external services
60+
- No custom authentication or credential storage
61+
- Runs entirely within Home Assistant's security context
62+
63+
### Home Assistant Integration
64+
65+
This integration inherits Home Assistant's security:
66+
- **Authentication**: Handled by Home Assistant
67+
- **Credential Storage**: Home Assistant's encrypted database
68+
- **Template Execution**: Home Assistant's sandboxed template engine
69+
- **Network Security**: Home Assistant's web server and SSL
70+
71+
### What We Do
72+
73+
- ✅ Redact credentials from debug logs
74+
- ✅ Validate user inputs
75+
- ✅ Use minimal dependencies
76+
- ✅ Automated CVE scanning
77+
78+
### What Home Assistant Does
79+
80+
- 🔐 User authentication
81+
- 🔐 Credential encryption
82+
- 🔐 Template sandboxing
83+
- 🔐 HTTPS/SSL
84+
- 🔐 Access control
85+
86+
## Best Practices for Users
87+
88+
**Most important**: Keep Home Assistant updated!
89+
90+
Other tips:
91+
- Use strong camera passwords
92+
- Enable HTTPS on Home Assistant
93+
- Don't share RTSP URLs publicly
94+
- Review templates before adding them
95+
96+
## Known Design Choices
97+
98+
- **Stream URLs forwarded as-is**: Required for streaming to work
99+
- **Credentials in logs**: Automatically sanitized (shown as `***:***@`)
100+
- **Minimal validation**: Relies on Home Assistant's validation
101+
- **No caching**: Always fresh images, no stale data
102+
103+
## Contact
104+
105+
Found a bug or have a security concern?
106+
- [GitHub Issues](https://github.com/Patras3/camera-snapshot-processor/issues)
107+
- [GitHub Discussions](https://github.com/Patras3/camera-snapshot-processor/discussions)
108+
109+
Remember: This is a hobby project maintained in spare time. Be patient and kind! 😊

.github/dependabot.yml

Lines changed: 31 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,31 @@
1+
# Dependabot configuration for automatic dependency updates
2+
# https://docs.github.com/en/code-security/dependabot/dependabot-version-updates
3+
4+
version: 2
5+
updates:
6+
# Monitor GitHub Actions
7+
- package-ecosystem: "github-actions"
8+
directory: "/"
9+
schedule:
10+
interval: "weekly"
11+
commit-message:
12+
prefix: "ci"
13+
labels:
14+
- "dependencies"
15+
- "github-actions"
16+
17+
# Monitor Python dependencies
18+
# Note: Dependabot will look for requirements files
19+
- package-ecosystem: "pip"
20+
directory: "/"
21+
schedule:
22+
interval: "weekly"
23+
commit-message:
24+
prefix: "deps"
25+
labels:
26+
- "dependencies"
27+
- "python"
28+
# Only create PRs for security updates
29+
open-pull-requests-limit: 5
30+
reviewers:
31+
- "Patras3"

.github/workflows/codeql.yml

Lines changed: 42 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,42 @@
1+
name: CodeQL Security Analysis
2+
3+
on:
4+
push:
5+
branches: [ master, main ]
6+
pull_request:
7+
branches: [ master, main ]
8+
schedule:
9+
# Run weekly on Monday at midnight UTC
10+
- cron: '0 0 * * 1'
11+
12+
jobs:
13+
analyze:
14+
name: CodeQL Analysis
15+
runs-on: ubuntu-latest
16+
permissions:
17+
actions: read
18+
contents: read
19+
security-events: write
20+
21+
strategy:
22+
fail-fast: false
23+
matrix:
24+
language: [ 'python', 'javascript' ]
25+
26+
steps:
27+
- name: Checkout repository
28+
uses: actions/checkout@v4
29+
30+
- name: Initialize CodeQL
31+
uses: github/codeql-action/init@v3
32+
with:
33+
languages: ${{ matrix.language }}
34+
queries: security-and-quality
35+
36+
- name: Autobuild
37+
uses: github/codeql-action/autobuild@v3
38+
39+
- name: Perform CodeQL Analysis
40+
uses: github/codeql-action/analyze@v3
41+
with:
42+
category: "/language:${{ matrix.language }}"

.github/workflows/security.yml

Lines changed: 101 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,101 @@
1+
name: Security Scan
2+
3+
on:
4+
push:
5+
branches: [ master, main ]
6+
pull_request:
7+
branches: [ master, main ]
8+
schedule:
9+
# Run daily at 6 AM UTC
10+
- cron: '0 6 * * *'
11+
workflow_dispatch:
12+
13+
jobs:
14+
pip-audit:
15+
name: Scan Python Dependencies for CVEs
16+
runs-on: ubuntu-latest
17+
18+
steps:
19+
- name: Checkout code
20+
uses: actions/checkout@v4
21+
22+
- name: Set up Python
23+
uses: actions/setup-python@v5
24+
with:
25+
python-version: '3.11'
26+
27+
- name: Install pip-audit
28+
run: |
29+
python -m pip install --upgrade pip
30+
pip install pip-audit
31+
32+
- name: Create requirements file from manifest
33+
run: |
34+
# Extract requirements from manifest.json
35+
python -c "
36+
import json
37+
with open('custom_components/camera_snapshot_processor/manifest.json') as f:
38+
manifest = json.load(f)
39+
requirements = manifest.get('requirements', [])
40+
with open('requirements-manifest.txt', 'w') as f:
41+
for req in requirements:
42+
f.write(req + '\n')
43+
"
44+
echo "Requirements from manifest.json:"
45+
cat requirements-manifest.txt
46+
47+
- name: Run pip-audit on manifest requirements
48+
run: |
49+
pip-audit -r requirements-manifest.txt --desc --format json > audit-results.json || true
50+
51+
- name: Display audit results
52+
run: |
53+
if [ -f audit-results.json ]; then
54+
python -c "
55+
import json
56+
with open('audit-results.json') as f:
57+
results = json.load(f)
58+
59+
vulnerabilities = results.get('vulnerabilities', [])
60+
if vulnerabilities:
61+
print(f'❌ Found {len(vulnerabilities)} vulnerabilities:')
62+
for vuln in vulnerabilities:
63+
pkg = vuln.get('name', 'unknown')
64+
version = vuln.get('version', 'unknown')
65+
vuln_id = vuln.get('id', 'unknown')
66+
desc = vuln.get('description', 'No description')
67+
fixed = vuln.get('fix_versions', [])
68+
print(f' - {pkg} {version}: {vuln_id}')
69+
print(f' {desc}')
70+
if fixed:
71+
print(f' Fix: Upgrade to {fixed}')
72+
exit(1)
73+
else:
74+
print('✅ No vulnerabilities found!')
75+
"
76+
else
77+
echo "✅ No vulnerabilities found!"
78+
fi
79+
80+
- name: Upload audit results as artifact
81+
if: always()
82+
uses: actions/upload-artifact@v4
83+
with:
84+
name: security-audit-results
85+
path: audit-results.json
86+
retention-days: 30
87+
88+
dependency-review:
89+
name: Dependency Review
90+
runs-on: ubuntu-latest
91+
if: github.event_name == 'pull_request'
92+
93+
steps:
94+
- name: Checkout code
95+
uses: actions/checkout@v4
96+
97+
- name: Dependency Review
98+
uses: actions/dependency-review-action@v4
99+
with:
100+
fail-on-severity: moderate
101+
comment-summary-in-pr: true

.gitignore

Lines changed: 79 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,79 @@
1+
# Byte-compiled / optimized / DLL files
2+
__pycache__/
3+
*.py[cod]
4+
*$py.class
5+
6+
# C extensions
7+
*.so
8+
9+
# Distribution / packaging
10+
.Python
11+
build/
12+
develop-eggs/
13+
dist/
14+
downloads/
15+
eggs/
16+
.eggs/
17+
lib/
18+
lib64/
19+
parts/
20+
sdist/
21+
var/
22+
wheels/
23+
*.egg-info/
24+
.installed.cfg
25+
*.egg
26+
27+
# PyInstaller
28+
*.manifest
29+
*.spec
30+
31+
# Unit test / coverage reports
32+
htmlcov/
33+
.tox/
34+
.coverage
35+
.coverage.*
36+
.cache
37+
nosetests.xml
38+
coverage.xml
39+
*.cover
40+
.hypothesis/
41+
.pytest_cache/
42+
43+
# Environments
44+
.env
45+
.venv
46+
env/
47+
venv/
48+
ENV/
49+
env.bak/
50+
venv.bak/
51+
52+
# IDEs
53+
.idea/
54+
.vscode/
55+
.claude/
56+
*.swp
57+
*.swo
58+
*~
59+
.DS_Store
60+
61+
# Home Assistant
62+
home-assistant.log
63+
home-assistant_v2.db
64+
*.db-shm
65+
*.db-wal
66+
.storage/
67+
deps/
68+
tts/
69+
www/
70+
71+
# Drafts and work-in-progress documents
72+
drafts/
73+
74+
# Test environment
75+
test_config/*
76+
!test_config/configuration.yaml
77+
78+
# Test outputs
79+
test_icon_output.png

0 commit comments

Comments
 (0)