diff --git a/deploy-compose.sh b/deploy-compose.sh new file mode 100755 index 0000000..ec7e799 --- /dev/null +++ b/deploy-compose.sh @@ -0,0 +1,31 @@ +#!/bin/bash + +# Deploy docker-compose.prod.yml to strato_1 server + +TARGET_HOST="strato_1" +TARGET_DIR="/opt/stacks/wetter" +TARGET_FILE="compose.yml" +SOURCE_FILE="docker-compose.prod.yml" + +echo "Deploying ${SOURCE_FILE} to ${TARGET_HOST}:${TARGET_DIR}/${TARGET_FILE}..." + +# Check if source file exists +if [ ! -f "${SOURCE_FILE}" ]; then + echo "Error: ${SOURCE_FILE} not found!" + exit 1 +fi + +# Remove old compose.yml on target if it exists +echo "Removing old ${TARGET_FILE} on ${TARGET_HOST}..." +ssh "${TARGET_HOST}" "rm -f ${TARGET_DIR}/${TARGET_FILE}" + +# Copy the file +echo "Copying ${SOURCE_FILE} to ${TARGET_HOST}..." +scp "${SOURCE_FILE}" "${TARGET_HOST}:${TARGET_DIR}/${TARGET_FILE}" + +if [ $? -eq 0 ]; then + echo "✓ Successfully deployed ${TARGET_FILE} to ${TARGET_HOST}:${TARGET_DIR}/" +else + echo "✗ Deployment failed!" + exit 1 +fi diff --git a/docker-compose.prod.yml b/docker-compose.prod.yml index 8486575..0e0f9f7 100644 --- a/docker-compose.prod.yml +++ b/docker-compose.prod.yml @@ -32,6 +32,7 @@ services: - internal - proxy labels: + - "com.centurylinklabs.watchtower.enable=true" - "traefik.enable=true" - "traefik.docker.network=dockge_default" - "traefik.http.routers.wetterstation-collector.rule=Host(`stwwetter.fuerst-stuttgart.de`) && PathPrefix(`/collector`)" @@ -57,6 +58,7 @@ services: - internal - proxy labels: + - "com.centurylinklabs.watchtower.enable=true" - "traefik.enable=true" - "traefik.docker.network=dockge_default" - "traefik.http.routers.wetterstation-api.rule=Host(`stwwetter.fuerst-stuttgart.de`) && PathPrefix(`/api`)" @@ -77,6 +79,7 @@ services: - internal - proxy labels: + - "com.centurylinklabs.watchtower.enable=true" - "traefik.enable=true" - "traefik.docker.network=dockge_default" - "traefik.http.routers.wetterstation.rule=Host(`stwwetter.fuerst-stuttgart.de`)" @@ -85,6 +88,21 @@ services: - "traefik.http.routers.wetterstation.tls.certresolver=letsencrypt" - "traefik.http.services.wetterstation.loadbalancer.server.port=80" + watchtower: + image: containrrr/watchtower:latest + container_name: wetterstation_watchtower + restart: unless-stopped + volumes: + - /var/run/docker.sock:/var/run/docker.sock + environment: + - WATCHTOWER_CLEANUP=true + - WATCHTOWER_LABEL_ENABLE=true + - WATCHTOWER_INCLUDE_RESTARTING=true + - WATCHTOWER_POLL_INTERVAL=300 + - TZ=Europe/Berlin + networks: + - internal + volumes: postgres_data: name: wetterstation_postgres_data_prod diff --git a/frontend/src/components/WeatherDashboard.css b/frontend/src/components/WeatherDashboard.css index 07935e0..573249a 100644 --- a/frontend/src/components/WeatherDashboard.css +++ b/frontend/src/components/WeatherDashboard.css @@ -65,3 +65,46 @@ color: #666; font-weight: 500; } + +.dashboard-footer { + margin-top: 2rem; + padding-top: 1rem; +} + +.footer-divider { + border: none; + border-top: 1px solid #ccc; + margin: 0 0 1rem 0; +} + +.footer-credits { + display: flex; + justify-content: space-between; + align-items: center; + font-size: 0.85rem; + color: #666; + margin-bottom: 0.75rem; +} + +.footer-left { + text-align: left; +} + +.footer-right { + text-align: right; +} + +.footer-sponsor { + text-align: center; + font-size: 0.85rem; + color: #666; +} + +.footer-sponsor a { + color: #0066cc; + text-decoration: none; +} + +.footer-sponsor a:hover { + text-decoration: underline; +} diff --git a/frontend/src/components/WeatherDashboard.jsx b/frontend/src/components/WeatherDashboard.jsx index 725dd77..1687ad1 100644 --- a/frontend/src/components/WeatherDashboard.jsx +++ b/frontend/src/components/WeatherDashboard.jsx @@ -426,6 +426,18 @@ const WeatherDashboard = ({ data }) => { + + {/* Footer */} +