Initial commit

This commit is contained in:
Mike Cifelli 2022-12-26 17:03:35 -05:00
commit 1ce1081375
7 changed files with 193 additions and 0 deletions

6
.gitignore vendored Normal file
View File

@ -0,0 +1,6 @@
__pycache__/
*.swp
*.tmp
garage.cfg
www/*
!www/.gitkeep

47
README.md Normal file
View File

@ -0,0 +1,47 @@
# garage
## Dependencies
```
sudo raspi-config nonint do_spi 0
sudo apt install python3-pip python3-dev python3-spidev
sudo pip3 install unicornhathd
```
## Configuration
```
cp garage.sample.cfg garage.cfg
```
## Installation
```
sudo ./install
```
## Output
By default output will be in `/var/log/syslog`.
A separate log file can be used by creating `/etc/rsyslog.d/30-garage.conf` containing:
```
if $programname == 'garage' then /var/log/garage.log
& stop
```
and then restart the rsyslog service:
```
sudo systemctl restart rsyslog
```
This log file can be rotated by creating `/etc/logrotate.d/garage` containing:
```
/var/log/garage.log
{
rotate 14
daily
create
missingok
notifempty
compress
delaycompress
postrotate
/usr/lib/rsyslog/rsyslog-rotate
endscript
}
```

82
garage.py Normal file
View File

@ -0,0 +1,82 @@
import json
import sys
from configparser import ConfigParser
from gpio import Button
from signal import pause
from signal import signal
from signal import SIGTERM
from threading import Lock
state = {"east-door": "opened", "west-door": "opened"}
threadLock = Lock()
stateFile = 'www/garage.json'
def main():
signal(SIGTERM, cleanExit())
config = ConfigParser()
config.read('garage.cfg')
eastPin = config['garage'].getint('east-pin')
westPin = config['garage'].getint('west-pin')
# eastUri = config['push'].getint('east-uri')
# westUri = config['push'].getint('west-uri')
persistState()
eastButton = Button(eastPin)
westButton = Button(westPin)
pause()
def eastDoorOpened():
try:
threadLock.aquire()
state["east-door"] = "opened"
persistState()
finally:
threadLock.release()
def eastDoorClosed():
try:
threadLock.aquire()
state["east-door"] = "closed"
persistState()
finally:
threadLock.release()
def westDoorOpened():
try:
threadLock.aquire()
state["west-door"] = "opened"
persistState()
finally:
threadLock.release()
def westDoorClosed():
try:
threadLock.aquire()
state["west-door"] = "closed"
persistState()
finally:
threadLock.release()
def persistState():
with open(stateFile, 'w') as file:
json.dump(state, file)
def cleanExit():
def _exit_(signum, frame):
sys.exit(0)
return _exit_
if __name__ == '__main__':
main()

7
garage.sample.cfg Normal file
View File

@ -0,0 +1,7 @@
[garage]
east-pin=1
west-pin=1
[push]
east-uri=uri
west-uri=uri

15
garage.service Normal file
View File

@ -0,0 +1,15 @@
[Unit]
Description=Garage
After=multi.user.target
[Service]
Type=simple
KillMode=mixed
WorkingDirectory=$workingDirectory
ExecStart=$execStart
Restart=on-failure
SyslogIdentifier=garage
User=$user
[Install]
WantedBy=multi-user.target

36
install Executable file
View File

@ -0,0 +1,36 @@
#! /usr/bin/env python3
import os
import sys
from string import Template
from subprocess import check_call
from subprocess import check_output
EXEC = 'garage.py'
SERVICE = 'garage.service'
SYSTEM_DIR = '/etc/systemd/system'
CURRENT_DIR = os.path.dirname(os.path.realpath(__file__))
SERVICE_TEMPLATE = os.path.join(CURRENT_DIR, SERVICE)
SERVICE_FILE = os.path.join(SYSTEM_DIR, SERVICE)
PYTHON = sys.executable
EXEC_START = f'{PYTHON} {EXEC}'
USER = check_output(['logname']).decode('utf-8').strip()
with open(SERVICE_TEMPLATE) as f:
serviceTemplate = Template(f.read())
serviceFile = serviceTemplate.substitute(
workingDirectory=CURRENT_DIR,
execStart=EXEC_START,
user=USER
)
with open(SERVICE_FILE, 'w') as f:
f.write(serviceFile)
check_call(['systemctl', 'daemon-reload'])
check_call(['systemctl', 'enable', '--no-pager', SERVICE])
check_call(['systemctl', 'restart', '--no-pager', SERVICE])
check_call(['systemctl', 'status', '--no-pager', SERVICE])

0
www/.gitkeep Normal file
View File