commit 1c82d159b8a3a344bfcfab207c1ae1c141201685 Author: Daniel Kluge Date: Sun Nov 6 19:28:31 2022 +0100 Initial commit diff --git a/.gitmodules b/.gitmodules new file mode 100644 index 0000000..80cb77c --- /dev/null +++ b/.gitmodules @@ -0,0 +1,3 @@ +[submodule "librespot-to-mqtt"] + path = librespot-to-mqtt + url = git@git.c0ntroller.de:c0ntroller/librespot-to-mqtt.git diff --git a/README.md b/README.md new file mode 100644 index 0000000..d2d9707 --- /dev/null +++ b/README.md @@ -0,0 +1,8 @@ +# Spoti-Pi + +1. Pi in zwei Netzwerke hängen + * `wpa_supplicant-wifi0.conf` und `wpa_supplicant-wifi1.conf` mit unterschiedlichen Netzwerken +2. Klonen mit `--recursive` +3. edit `secrets.mjs` in the `librespot-to-mqtt` directory +4. `sudo docker compose build` +4. `sudo docker compose up -d` diff --git a/docker-compose.yml b/docker-compose.yml new file mode 100644 index 0000000..530af6b --- /dev/null +++ b/docker-compose.yml @@ -0,0 +1,36 @@ +version: '3' + +volumes: + cache: + +services: + librespot: + image: librespot + build: + context: ./librespot + container_name: librespot + restart: unless-stopped + network_mode: host + volumes: + - ./librespot/config.toml:/app/config.toml + - cache:/app/cache + healthcheck: + test: ["CMD-SHELL", "wget http://localhost:24877/instance --no-verbose --tries=1 || exit 1"] + interval: 10s + timeout: 5s + retries: 5 + devices: + - /dev/snd:/dev/snd + + + librespot-to-mqtt: + image: librespot-to-mqtt + build: + context: ./librespot-to-mqtt + container_name: librespot-to-mqtt + restart: unless-stopped + network_mode: host + volumes: + - ./librespot-to-mqtt/secrets.mjs:/app/secrets.mjs + depends_on: + - librespot \ No newline at end of file diff --git a/librespot-to-mqtt b/librespot-to-mqtt new file mode 160000 index 0000000..729bdfc --- /dev/null +++ b/librespot-to-mqtt @@ -0,0 +1 @@ +Subproject commit 729bdfc1c3e469bbaac354c7bf4a85aadaff94f9 diff --git a/librespot/Dockerfile b/librespot/Dockerfile new file mode 100644 index 0000000..374d7ad --- /dev/null +++ b/librespot/Dockerfile @@ -0,0 +1,10 @@ +FROM arm64v8/eclipse-temurin:11-jre +WORKDIR /app +RUN mkdir -p cache +VOLUME /app/cache + +RUN apt-get update && apt-get install alsa-base alsa-utils -y && rm -rf /var/lib/apt/lists/* + +RUN wget https://github.com/librespot-org/librespot-java/releases/download/v1.6.2/librespot-api-1.6.2.jar + +CMD java -jar librespot-api-1.6.2.jar diff --git a/librespot/config.toml b/librespot/config.toml new file mode 100644 index 0000000..210663a --- /dev/null +++ b/librespot/config.toml @@ -0,0 +1,84 @@ +deviceId = "" ### Device ID (40 chars, leave empty for random) ### +deviceName = "Spoti-Pi Küche" ### Device name ### +deviceType = "AUTOMOBILE" ### Device type (COMPUTER, TABLET, SMARTPHONE, SPEAKER, TV, AVR, STB, AUDIO_DONGLE, GAME_CONSOLE, CAST_VIDEO, CAST_AUDIO, AUTOMOBILE, WEARABLE, UNKNOWN_SPOTIFY, CAR_THING, UNKNOWN) ### +preferredLocale = "de" ### Preferred locale ### +logLevel = "INFO" ### Log level (OFF, FATAL, ERROR, WARN, INFO, DEBUG, TRACE, ALL) ### + +[auth] ### Authentication ### +strategy = "ZEROCONF" # Strategy (USER_PASS, ZEROCONF, BLOB, FACEBOOK, STORED) +username = "" # Spotify username (BLOB, USER_PASS only) +password = "" # Spotify password (USER_PASS only) +blob = "" # Spotify authentication blob Base64-encoded (BLOB only) +storeCredentials = false # Whether to store reusable credentials on disk (not a plain password) +credentialsFile = "credentials.json" # Credentials file (JSON) + +[zeroconf] ### Zeroconf ### +listenPort = -1 # Listen on this TCP port (`-1` for random) +listenAll = true # Listen on all interfaces (overrides `zeroconf.interfaces`) +interfaces = "" # Listen on these interfaces (comma separated list of names) + +[cache] ### Cache ### +enabled = true # Cache enabled +dir = "./cache/" +doCleanUp = true + +[network] ### Network ### +connectionTimeout = 10 # If ping isn't received within this amount of seconds, reconnect + +[preload] ### Preload ### +enabled = true # Preload enabled + +[time] ### Time correction ### +synchronizationMethod = "NTP" # Time synchronization method (NTP, PING, MELODY, MANUAL) +manualCorrection = 0 # Manual time correction in millis + +[player] ### Player ### +autoplayEnabled = true # Autoplay similar songs when your music ends +preferredAudioQuality = "HIGH" # Preferred audio quality (NORMAL, HIGH, VERY_HIGH) +enableNormalisation = true # Whether to apply the Spotify loudness normalisation +normalisationPregain = +3.0 # Normalisation pregain in decibels (loud at +6, normal at +3, quiet at -5) +initialVolume = 65536 # Initial volume (0-65536) +volumeSteps = 512 # Number of volume notches +logAvailableMixers = true # Log available mixers +mixerSearchKeywords = "" # Mixer/backend search keywords (semicolon separated) +crossfadeDuration = 0 # Crossfade overlap time (in milliseconds) +output = "MIXER" # Audio output device (MIXER, PIPE, STDOUT, CUSTOM) +outputClass = "" # Audio output Java class name +releaseLineDelay = 20 # Release mixer line after set delay (in seconds) +pipe = "" # Output raw (signed) PCM to this file (`player.output` must be PIPE) +retryOnChunkError = true # Whether the player should retry fetching a chuck if it fails +metadataPipe = "" # Output metadata in Shairport Sync format (https://github.com/mikebrady/shairport-sync-metadata-reader) +bypassSinkVolume = false # Whether librespot-java should ignore volume events, sink volume is set to the max +localFilesPath = "" # Where librespot-java should search for local files + +[api] ### API ### +port = 24879 # API port (`api` module only) +host = "0.0.0.0" # API listen interface (`api` module only) + +[proxy] ### Proxy ### +enabled = false # Whether the proxy is enabled +type = "HTTP" # The proxy type (HTTP, SOCKS) +ssl = false # Connect to proxy using SSL (HTTP only) +address = "" # The proxy hostname +port = 0 # The proxy port +auth = false # Whether authentication is enabled on the server +username = "" # Basic auth username +password = "" # Basic auth password + +[shell] ### Shell ### +enabled = false # Shell events enabled +executeWithBash = true # Execute the command with `bash -c` +onContextChanged = "" +onTrackChanged = "" +onPlaybackEnded = "" +onPlaybackPaused = "" +onPlaybackResumed = "" +onTrackSeeked = "" +onMetadataAvailable = "" +onVolumeChanged = "" +onInactiveSession = "" +onPanicState = "" +onConnectionDropped = "" +onConnectionEstablished = "" +onStartedLoading = "" +onFinishedLoading = "" \ No newline at end of file