Published: Jun 3, 2025 by Isaac Johnson
Today I want to dig into two Open-Source apps that have been on my list: Fider and AudioBookshelf.
Fider is a Feedback + Voting site. It sort of reminds me of Digg from back in the day. The idea is people can drop suggestions and then also vote. Everyone is gated by an email to limit spam. We’ll try setting this up on Docker as well as Kubernetes. I’ll even cover OAuth setup with Google.
Audioshelf is a self-hosted Audiobook and Podcast server. It is not for music, so we can set that aside for now. We’ll set this up in Docker (for good reasons) and sort out Books and Podcasts (and music, in a way).
Fider
Back in Jan, I saw this Marius post on Fider which is a simple containerized feedback system.
In the Docker install steps we can see a simple Docker compose file
services:
db:
restart: always
image: postgres:17
volumes:
- /var/fider/pg_data:/var/lib/postgresql/data
environment:
POSTGRES_USER: fider
POSTGRES_PASSWORD: s0m3g00dp4ssw0rd
app:
restart: always
image: getfider/fider:stable
ports:
- "80:3000"
environment:
# Public Host Name
BASE_URL: http://localhost
# Connection string to the PostgreSQL database
DATABASE_URL: postgres://fider:s0m3g00dp4ssw0rd@db:5432/fider?sslmode=disable
# Generate a secure secret, for example using https://jwtsecret.com
JWT_SECRET: VERY_STRONG_SECRET_SHOULD_BE_USED_HERE
# From which account e-mails will be sent
EMAIL_NOREPLY: noreply@yourdomain.com
###
# EMAIL
# Either EMAIL_MAILGUN_* or EMAIL_SMTP_*, EMAIL_AWSSES_* or EMAIL_RESEND_* is required
###
# EMAIL_MAILGUN_API: key-yourkeygoeshere
# EMAIL_MAILGUN_DOMAIN: yourdomain.com
# EMAIL_MAILGUN_REGION: US
# EMAIL_SMTP_HOST: smtp.yourdomain.com
# EMAIL_SMTP_PORT: 587
# EMAIL_SMTP_USERNAME: user@yourdomain.com
# EMAIL_SMTP_PASSWORD: s0m3p4ssw0rd
# EMAIL_SMTP_ENABLE_STARTTLS: 'true'
# EMAIL_AWSSES_REGION: us-east-1
# EMAIL_AWSSES_ACCESS_KEY_ID: youraccesskeygoeshere
# EMAIL_AWSSES_SECRET_ACCESS_KEY: yoursecretkeygoeshere
# EMAIL_RESEND_API: resend-api-key
Here I’ll use a Resend sender
builder@LuiGi:~/Workspaces/fiderApp$ cat ./docker-compose.yml
services:
db:
restart: always
image: postgres:17
volumes:
- /home/builder/Workspaces/fiderApp/pg_data:/var/lib/postgresql/data
environment:
POSTGRES_USER: fider
POSTGRES_PASSWORD: s0m3g00dp4ssw0rd
app:
restart: always
image: getfider/fider:stable
ports:
- "8844:3000"
environment:
# Public Host Name
BASE_URL: http://localhost:8844
# Connection string to the PostgreSQL database
DATABASE_URL: postgres://fider:s0m3g00dp4ssw0rd@db:5432/fider?sslmode=disable
# Generate a secure secret, for example using https://jwtsecret.com
JWT_SECRET: VERY_STRONG_SECRET_SHOULD_BE_USED_HERE
# From which account e-mails will be sent
EMAIL_NOREPLY: isaac@steeped.space
EMAIL_RESEND_API: re_xxxxxxxxxxxxxxxxxxxxxxxx
I see it launch but the app keeps crashing looking for an SMTP variable
builder@LuiGi:~/Workspaces/fiderApp$ docker compose up
[+] Running 28/28
✔ app Pulled 18.1s
✔ 6e909acdb790 Pull complete 12.2s
✔ d5b5f7131ee0 Pull complete 12.5s
✔ de3223de4c07 Pull complete 12.6s
✔ 9d21d4a801d9 Pull complete 12.7s
✔ b7fe34b6c18a Pull complete 12.8s
✔ b644702da688 Pull complete 12.8s
✔ 4da2d0a291ce Pull complete 12.9s
✔ 1d4cef4462a8 Pull complete 15.6s
✔ 87c2e062905e Pull complete 15.7s
✔ 800fb5df1c38 Pull complete 15.8s
✔ e9f9de74aa60 Pull complete 15.8s
✔ e49a90a7cdb7 Pull complete 15.9s
✔ db Pulled 104.5s
✔ 61320b01ae5e Pull complete 19.8s
✔ 3db9b37be7c3 Pull complete 19.9s
✔ e9a82aed48d7 Pull complete 20.1s
✔ 7c852ebdd63e Pull complete 20.2s
✔ 28708ff4e046 Pull complete 21.7s
✔ 6ce13d85dabe Pull complete 21.8s
✔ bd1fa28722bb Pull complete 21.9s
✔ 410cd7ec9a40 Pull complete 21.9s
✔ 475b0e32b814 Pull complete 101.8s
✔ e7aba16d6a5e Pull complete 101.9s
✔ 89ba8b615fa9 Pull complete 101.9s
✔ 82697a7976df Pull complete 102.0s
✔ 7e11eb1421f3 Pull complete 102.1s
✔ 2bb588ce4e67 Pull complete 102.1s
[+] Running 3/3
✔ Network fiderapp_default Created 0.1s
✔ Container fiderapp-db-1 Created 0.3s
✔ Container fiderapp-app-1 Created 0.3s
Attaching to app-1, db-1
db-1 | The files belonging to this database system will be owned by user "postgres".
db-1 | This user must also own the server process.
db-1 |
db-1 | The database cluster will be initialized with locale "en_US.utf8".
db-1 | The default database encoding has accordingly been set to "UTF8".
db-1 | The default text search configuration will be set to "english".
db-1 |
db-1 | Data page checksums are disabled.
db-1 |
db-1 | fixing permissions on existing directory /var/lib/postgresql/data ... ok
db-1 | creating subdirectories ... ok
db-1 | selecting dynamic shared memory implementation ... posix
db-1 | selecting default "max_connections" ... 100
app-1 | panic: could not find environment variable named 'EMAIL_SMTP_HOST'
app-1 |
app-1 | goroutine 1 [running]:
app-1 | github.com/getfider/fider/app/pkg/env.mustBeSet({0x1c1f3b5, 0xf})
db-1 | selecting default "shared_buffers" ... 128MB
app-1 | /server/app/pkg/env/env.go:205 +0x85
app-1 | github.com/getfider/fider/app/pkg/env.Reload()
app-1 | /server/app/pkg/env/env.go:190 +0x246
app-1 | github.com/getfider/fider/app/pkg/env.init.0()
app-1 | /server/app/pkg/env/env.go:146 +0xf
db-1 | selecting default time zone ... Etc/UTC
db-1 | creating configuration files ... ok
db-1 | running bootstrap script ... ok
db-1 | performing post-bootstrap initialization ... ok
app-1 exited with code 0
db-1 | syncing data to disk ... ok
db-1 |
db-1 |
db-1 | Success. You can now start the database server using:
db-1 |
db-1 | pg_ctl -D /var/lib/postgresql/data -l logfile start
db-1 |
db-1 | initdb: warning: enabling "trust" authentication for local connections
db-1 | initdb: hint: You can change this by editing pg_hba.conf or using the option -A, or --auth-local and --auth-host, the next time you run initdb.
db-1 | waiting for server to start....2025-05-31 13:26:01.395 UTC [50] LOG: starting PostgreSQL 17.5 (Debian 17.5-1.pgdg120+1) on x86_64-pc-linux-gnu, compiled by gcc (Debian 12.2.0-14) 12.2.0, 64-bit
db-1 | 2025-05-31 13:26:01.400 UTC [50] LOG: listening on Unix socket "/var/run/postgresql/.s.PGSQL.5432"
db-1 | 2025-05-31 13:26:01.419 UTC [53] LOG: database system was shut down at 2025-05-31 13:25:58 UTC
db-1 | 2025-05-31 13:26:01.427 UTC [50] LOG: database system is ready to accept connections
db-1 | done
db-1 | server started
db-1 | CREATE DATABASE
db-1 |
db-1 |
db-1 | /usr/local/bin/docker-entrypoint.sh: ignoring /docker-entrypoint-initdb.d/*
db-1 |
db-1 | waiting for server to shut down....2025-05-31 13:26:01.586 UTC [50] LOG: received fast shutdown request
db-1 | 2025-05-31 13:26:01.596 UTC [50] LOG: aborting any active transactions
db-1 | 2025-05-31 13:26:01.598 UTC [50] LOG: background worker "logical replication launcher" (PID 56) exited with exit code 1
db-1 | 2025-05-31 13:26:01.600 UTC [51] LOG: shutting down
db-1 | 2025-05-31 13:26:01.606 UTC [51] LOG: checkpoint starting: shutdown immediate
app-1 | panic: could not find environment variable named 'EMAIL_SMTP_HOST'
app-1 |
app-1 | goroutine 1 [running]:
app-1 | github.com/getfider/fider/app/pkg/env.mustBeSet({0x1c1f3b5, 0xf})
app-1 | /server/app/pkg/env/env.go:205 +0x85
app-1 | github.com/getfider/fider/app/pkg/env.Reload()
app-1 | /server/app/pkg/env/env.go:190 +0x246
app-1 | github.com/getfider/fider/app/pkg/env.init.0()
app-1 | /server/app/pkg/env/env.go:146 +0xf
app-1 | panic: could not find environment variable named 'EMAIL_SMTP_HOST'
app-1 |
app-1 | goroutine 1 [running]:
app-1 | github.com/getfider/fider/app/pkg/env.mustBeSet({0x1c1f3b5, 0xf})
app-1 exited with code 2
app-1 | /server/app/pkg/env/env.go:205 +0x85
app-1 | github.com/getfider/fider/app/pkg/env.Reload()
app-1 | /server/app/pkg/env/env.go:190 +0x246
app-1 | github.com/getfider/fider/app/pkg/env.init.0()
app-1 | /server/app/pkg/env/env.go:146 +0xf
app-1 | panic: could not find environment variable named 'EMAIL_SMTP_HOST'
app-1 |
app-1 | goroutine 1 [running]:
app-1 | github.com/getfider/fider/app/pkg/env.mustBeSet({0x1c1f3b5, 0xf})
app-1 | /server/app/pkg/env/env.go:205 +0x85
app-1 | github.com/getfider/fider/app/pkg/env.Reload()
app-1 | /server/app/pkg/env/env.go:190 +0x246
app-1 | github.com/getfider/fider/app/pkg/env.init.0()
app-1 | /server/app/pkg/env/env.go:146 +0xf
db-1 | 2025-05-31 13:26:02.143 UTC [51] LOG: checkpoint complete: wrote 921 buffers (5.6%); 0 WAL file(s) added, 0 removed, 0 recycled; write=0.027 s, sync=0.494 s, total=0.544 s; sync files=301, longest=0.010 s, average=0.002 s; distance=4238 kB, estimate=4238 kB; lsn=0/1908970, redo lsn=0/1908970
db-1 | 2025-05-31 13:26:02.148 UTC [50] LOG: database system is shut down
db-1 | done
db-1 | server stopped
db-1 |
db-1 | PostgreSQL init process complete; ready for start up.
db-1 |
db-1 | 2025-05-31 13:26:02.223 UTC [1] LOG: starting PostgreSQL 17.5 (Debian 17.5-1.pgdg120+1) on x86_64-pc-linux-gnu, compiled by gcc (Debian 12.2.0-14) 12.2.0, 64-bit
db-1 | 2025-05-31 13:26:02.265 UTC [1] LOG: listening on IPv4 address "0.0.0.0", port 5432
db-1 | 2025-05-31 13:26:02.265 UTC [1] LOG: listening on IPv6 address "::", port 5432
db-1 | 2025-05-31 13:26:02.282 UTC [1] LOG: listening on Unix socket "/var/run/postgresql/.s.PGSQL.5432"
db-1 | 2025-05-31 13:26:02.301 UTC [66] LOG: database system was shut down at 2025-05-31 13:26:02 UTC
db-1 | 2025-05-31 13:26:02.312 UTC [1] LOG: database system is ready to accept connections
app-1 exited with code 2
app-1 | panic: could not find environment variable named 'EMAIL_SMTP_HOST'
app-1 |
app-1 | goroutine 1 [running]:
app-1 | github.com/getfider/fider/app/pkg/env.mustBeSet({0x1c1f3b5, 0xf})
I filled out the SMTP settings for resend form and it worked.
This time it worked to launch
builder@LuiGi:~/Workspaces/fiderApp$ docker compose up
[+] Running 2/2
✔ Container fiderapp-app-1 Recreated 0.1s
✔ Container fiderapp-db-1 Created 0.0s
Attaching to app-1, db-1
db-1 |
db-1 | PostgreSQL Database directory appears to contain a database; Skipping initialization
db-1 |
db-1 | 2025-05-31 13:36:13.482 UTC [1] LOG: starting PostgreSQL 17.5 (Debian 17.5-1.pgdg120+1) on x86_64-pc-linux-gnu, compiled by gcc (Debian 12.2.0-14) 12.2.0, 64-bit
db-1 | 2025-05-31 13:36:13.482 UTC [1] LOG: listening on IPv4 address "0.0.0.0", port 5432
db-1 | 2025-05-31 13:36:13.482 UTC [1] LOG: listening on IPv6 address "::", port 5432
app-1 | INFO [2025-05-31T13:36:13Z] [MIGRATE] Running migrations...
db-1 | 2025-05-31 13:36:13.494 UTC [1] LOG: listening on Unix socket "/var/run/postgresql/.s.PGSQL.5432"
app-1 | INFO [2025-05-31T13:36:13Z] [MIGRATE] Found total of 74 migration files.
db-1 | 2025-05-31 13:36:13.505 UTC [29] LOG: database system was shut down at 2025-05-31 13:34:22 UTC
db-1 | 2025-05-31 13:36:13.506 UTC [30] FATAL: the database system is starting up
app-1 | ERROR [2025-05-31T13:36:13Z] [MIGRATE] Error Trace:
db-1 | 2025-05-31 13:36:13.506 UTC [31] FATAL: the database system is starting up
app-1 | - failed to get last migration record (app/pkg/dbx/migrate.go:57)
db-1 | 2025-05-31 13:36:13.507 UTC [32] FATAL: the database system is starting up
app-1 | - pq: the database system is starting up
db-1 | 2025-05-31 13:36:13.519 UTC [1] LOG: database system is ready to accept connections
app-1 exited with code 0
db-1 | 2025-05-31 13:36:16.656 UTC [36] ERROR: relation "logs" does not exist at character 13
db-1 | 2025-05-31 13:36:16.656 UTC [36] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
db-1 | 2025-05-31 13:36:16.657 UTC [37] ERROR: relation "logs" does not exist at character 13
db-1 | 2025-05-31 13:36:16.657 UTC [37] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
db-1 | 2025-05-31 13:36:16.667 UTC [37] ERROR: relation "schema_migrations" does not exist at character 21
db-1 | 2025-05-31 13:36:16.667 UTC [37] STATEMENT: SELECT version FROM schema_migrations LIMIT 1
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Current version is 0
db-1 | 2025-05-31 13:36:16.667 UTC [37] ERROR: relation "logs" does not exist at character 13
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201701261850 (201701261850_create_tenants.up.sql)
db-1 | 2025-05-31 13:36:16.667 UTC [37] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
db-1 | 2025-05-31 13:36:16.667 UTC [36] ERROR: relation "logs" does not exist at character 13
db-1 | 2025-05-31 13:36:16.667 UTC [36] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201701281131 (201701281131_rename_domain.up.sql)
db-1 | 2025-05-31 13:36:16.682 UTC [36] ERROR: relation "logs" does not exist at character 13
db-1 | 2025-05-31 13:36:16.682 UTC [36] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201702072040 (201702072040_create_ideas.up.sql)
db-1 | 2025-05-31 13:36:16.686 UTC [37] ERROR: relation "logs" does not exist at character 13
db-1 | 2025-05-31 13:36:16.686 UTC [37] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201702251213 (201702251213_create_users.up.sql)
db-1 | 2025-05-31 13:36:16.693 UTC [36] ERROR: relation "logs" does not exist at character 13
db-1 | 2025-05-31 13:36:16.693 UTC [36] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201702251620 (201702251620_add_tenant_cname.up.sql)
db-1 | 2025-05-31 13:36:16.698 UTC [36] ERROR: relation "logs" does not exist at character 13
db-1 | 2025-05-31 13:36:16.698 UTC [36] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201703172030 (201703172030_add_ideas_userid.up.sql)
db-1 | 2025-05-31 13:36:16.701 UTC [37] ERROR: relation "logs" does not exist at character 13
db-1 | 2025-05-31 13:36:16.701 UTC [37] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201703172115 (201703172115_remove_col_defaults.up.sql)
db-1 | 2025-05-31 13:36:16.705 UTC [36] ERROR: relation "logs" does not exist at character 13
db-1 | 2025-05-31 13:36:16.705 UTC [36] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201703240709 (201703240709_remove_col_tenants.up.sql)
db-1 | 2025-05-31 13:36:16.709 UTC [37] ERROR: relation "logs" does not exist at character 13
db-1 | 2025-05-31 13:36:16.709 UTC [37] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201703240710 (201703240710_create_comments.up.sql)
db-1 | 2025-05-31 13:36:16.713 UTC [36] ERROR: relation "logs" does not exist at character 13
db-1 | 2025-05-31 13:36:16.713 UTC [36] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201703310824 (201703310824_remove_col_user_providers.up.sql)
db-1 | 2025-05-31 13:36:16.719 UTC [37] ERROR: relation "logs" does not exist at character 13
db-1 | 2025-05-31 13:36:16.719 UTC [37] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201703310857 (201703310857_add_tenant_to_users.up.sql)
db-1 | 2025-05-31 13:36:16.722 UTC [37] ERROR: relation "logs" does not exist at character 13
db-1 | 2025-05-31 13:36:16.722 UTC [37] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201704101854 (201704101854_add_ideas_number.up.sql)
db-1 | 2025-05-31 13:36:16.727 UTC [36] ERROR: relation "logs" does not exist at character 13
db-1 | 2025-05-31 13:36:16.727 UTC [36] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201704112003 (201704112003_add_role_users.up.sql)
db-1 | 2025-05-31 13:36:16.732 UTC [36] ERROR: relation "logs" does not exist at character 13
db-1 | 2025-05-31 13:36:16.732 UTC [36] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201704181821 (201704181821_add_supporters.up.sql)
db-1 | 2025-05-31 13:36:16.735 UTC [37] ERROR: relation "logs" does not exist at character 13
db-1 | 2025-05-31 13:36:16.735 UTC [37] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201705132054 (201705132054_add_idea_status.up.sql)
db-1 | 2025-05-31 13:36:16.740 UTC [37] ERROR: relation "logs" does not exist at character 13
db-1 | 2025-05-31 13:36:16.740 UTC [37] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201705191854 (201705191854_add_idea_slug.up.sql)
db-1 | 2025-05-31 13:36:16.744 UTC [37] ERROR: relation "logs" does not exist at character 13
db-1 | 2025-05-31 13:36:16.744 UTC [37] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201705202300 (201705202300_add_idea_response.up.sql)
db-1 | 2025-05-31 13:36:16.747 UTC [36] ERROR: relation "logs" does not exist at character 13
db-1 | 2025-05-31 13:36:16.747 UTC [36] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201707081055 (201707081055_set_cname_null.up.sql)
db-1 | 2025-05-31 13:36:16.751 UTC [36] ERROR: relation "logs" does not exist at character 13
db-1 | 2025-05-31 13:36:16.751 UTC [36] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201707261949 (201707261949_set_cname_empty.up.sql)
db-1 | 2025-05-31 13:36:16.757 UTC [37] ERROR: relation "logs" does not exist at character 13
db-1 | 2025-05-31 13:36:16.757 UTC [37] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201707271826 (201707271826_new_tenant_settings.up.sql)
db-1 | 2025-05-31 13:36:16.761 UTC [37] ERROR: relation "logs" does not exist at character 13
db-1 | 2025-05-31 13:36:16.761 UTC [37] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201709081837 (201709081837_create_email_verifications.up.sql)
db-1 | 2025-05-31 13:36:16.766 UTC [36] ERROR: relation "logs" does not exist at character 13
db-1 | 2025-05-31 13:36:16.766 UTC [36] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201709091228 (201709091228_create_email_verification_key_index.up.sql)
db-1 | 2025-05-31 13:36:16.771 UTC [37] ERROR: relation "logs" does not exist at character 13
db-1 | 2025-05-31 13:36:16.771 UTC [37] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201709141944 (201709141944_rename_email_verification.up.sql)
db-1 | 2025-05-31 13:36:16.775 UTC [37] ERROR: relation "logs" does not exist at character 13
db-1 | 2025-05-31 13:36:16.775 UTC [37] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201709241236 (201709241236_add_tenant_status.up.sql)
db-1 | 2025-05-31 13:36:16.779 UTC [37] ERROR: relation "logs" does not exist at character 13
db-1 | 2025-05-31 13:36:16.779 UTC [37] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201709241254 (201709241254_add_signin_request_name_expires_on.up.sql)
db-1 | 2025-05-31 13:36:16.782 UTC [36] ERROR: relation "logs" does not exist at character 13
db-1 | 2025-05-31 13:36:16.782 UTC [36] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201711152138 (201711152138_create_tags.up.sql)
db-1 | 2025-05-31 13:36:16.787 UTC [36] ERROR: relation "logs" does not exist at character 13
db-1 | 2025-05-31 13:36:16.787 UTC [36] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201711181740 (201711181740_create_uniq_indexes.up.sql)
db-1 | 2025-05-31 13:36:16.794 UTC [37] ERROR: relation "logs" does not exist at character 13
db-1 | 2025-05-31 13:36:16.794 UTC [37] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201712061924 (201712061924_unique_email.up.sql)
db-1 | 2025-05-31 13:36:16.798 UTC [36] ERROR: relation "logs" does not exist at character 13
db-1 | 2025-05-31 13:36:16.798 UTC [36] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201712131842 (201712131842_unique_slug.up.sql)
db-1 | 2025-05-31 13:36:16.804 UTC [37] ERROR: relation "logs" does not exist at character 13
db-1 | 2025-05-31 13:36:16.804 UTC [37] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201801031643 (201801031643_original_id.up.sql)
db-1 | 2025-05-31 13:36:16.808 UTC [36] ERROR: relation "logs" does not exist at character 13
db-1 | 2025-05-31 13:36:16.808 UTC [36] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201801152006 (201801152006_rename_signin_requests.up.sql)
db-1 | 2025-05-31 13:36:16.811 UTC [37] ERROR: relation "logs" does not exist at character 13
db-1 | 2025-05-31 13:36:16.811 UTC [37] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201801152017 (201801152017_add_kind_email_verification.up.sql)
db-1 | 2025-05-31 13:36:16.815 UTC [36] ERROR: relation "logs" does not exist at character 13
db-1 | 2025-05-31 13:36:16.815 UTC [36] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201802061858 (201802061858_create_notification_tables.up.sql)
db-1 | 2025-05-31 13:36:16.819 UTC [37] ERROR: relation "logs" does not exist at character 13
db-1 | 2025-05-31 13:36:16.819 UTC [37] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201802071816 (201802071816_seed_subscribers_table.up.sql)
db-1 | 2025-05-31 13:36:16.825 UTC [36] ERROR: relation "logs" does not exist at character 13
db-1 | 2025-05-31 13:36:16.825 UTC [36] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201802231910 (201802231910_add_pg_trgm.up.sql)
db-1 | 2025-05-31 13:36:16.829 UTC [37] ERROR: relation "logs" does not exist at character 13
db-1 | 2025-05-31 13:36:16.829 UTC [37] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201802241348 (201802241348_create_webnotification_tables.up.sql)
db-1 | 2025-05-31 13:36:16.849 UTC [36] ERROR: relation "logs" does not exist at character 13
db-1 | 2025-05-31 13:36:16.849 UTC [36] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201803011831 (201803011831_add_tenant_id_everywhere.up.sql)
db-1 | 2025-05-31 13:36:16.855 UTC [37] ERROR: relation "logs" does not exist at character 13
db-1 | 2025-05-31 13:36:16.855 UTC [37] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201803110836 (201803110836_edit_comment_columns.up.sql)
db-1 | 2025-05-31 13:36:16.875 UTC [36] ERROR: relation "logs" does not exist at character 13
db-1 | 2025-05-31 13:36:16.875 UTC [36] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201804091842 (201804091842_add_is_private.up.sql)
db-1 | 2025-05-31 13:36:16.879 UTC [37] ERROR: relation "logs" does not exist at character 13
db-1 | 2025-05-31 13:36:16.879 UTC [37] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201805061319 (201805061319_create_uploads.up.sql)
db-1 | 2025-05-31 13:36:16.883 UTC [36] ERROR: relation "logs" does not exist at character 13
db-1 | 2025-05-31 13:36:16.883 UTC [36] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201805070759 (201805070759_add_logo_id.up.sql)
db-1 | 2025-05-31 13:36:16.889 UTC [37] ERROR: relation "logs" does not exist at character 13
db-1 | 2025-05-31 13:36:16.889 UTC [37] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201805162034 (201805162034_add_custom_css.up.sql)
db-1 | 2025-05-31 13:36:16.895 UTC [36] ERROR: relation "logs" does not exist at character 13
db-1 | 2025-05-31 13:36:16.895 UTC [36] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201805230000 (201805230000_drop_supporters_column.up.sql)
db-1 | 2025-05-31 13:36:16.899 UTC [37] ERROR: relation "logs" does not exist at character 13
db-1 | 2025-05-31 13:36:16.899 UTC [37] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201805261834 (201805261834_add_user_status.up.sql)
db-1 | 2025-05-31 13:36:16.904 UTC [36] ERROR: relation "logs" does not exist at character 13
db-1 | 2025-05-31 13:36:16.904 UTC [36] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201806191904 (201806191904_create_logs.sql)
db-1 | 2025-05-31 13:36:16.909 UTC [36] ERROR: relation "logs" does not exist at character 13
db-1 | 2025-05-31 13:36:16.909 UTC [36] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201807122132 (201807122132_create_oauth_providers.sql)
db-1 | 2025-05-31 13:36:16.913 UTC [36] ERROR: column "created_at" of relation "logs" does not exist at character 37
db-1 | 2025-05-31 13:36:16.913 UTC [36] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201808152020 (201808152020_rename_idea_post.sql)
db-1 | 2025-05-31 13:36:16.919 UTC [37] ERROR: column "created_at" of relation "logs" does not exist at character 37
db-1 | 2025-05-31 13:36:16.919 UTC [37] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201808181931 (201808181931_add_api_key_users.sql)
db-1 | 2025-05-31 13:36:16.926 UTC [36] ERROR: column "created_at" of relation "logs" does not exist at character 37
db-1 | 2025-05-31 13:36:16.926 UTC [36] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201808192103 (201808192103_increase_key_size.sql)
db-1 | 2025-05-31 13:36:16.932 UTC [36] ERROR: column "created_at" of relation "logs" does not exist at character 37
db-1 | 2025-05-31 13:36:16.932 UTC [36] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201808291958 (201808291958_rename_support_vote.sql)
db-1 | 2025-05-31 13:36:16.937 UTC [37] ERROR: column "created_at" of relation "logs" does not exist at character 37
db-1 | 2025-05-31 13:36:16.937 UTC [37] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201809262108 (201809262108_rename_datetime_fields.sql)
db-1 | 2025-05-31 13:36:16.942 UTC [36] ERROR: column "created_at" of relation "logs" does not exist at character 37
db-1 | 2025-05-31 13:36:16.942 UTC [36] STATEMENT: INSERT INTO logs (tag, level, text, created_at, properties) VALUES ($1, $2, $3, $4, $5)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201810022329 (201810022329_add_events.sql)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201810152035 (201810152035_add_comment_deleted.sql)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201811071547 (201811071547_increase_link_size.sql)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201812102208 (201812102208_create_blob_table.sql)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201812171813 (201812171813_migrate_to_blobs.sql)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201812201644 (201812201644_migrate_autocert_to_blobs.sql)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201812230904 (201812230904_user_avatar_type.sql)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201901042021 (201901042021_create_tenants_billing.sql)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201901072106 (201901072106_recreate_post_slug_index.sql)
app-1 | INFO [2025-05-31T13:36:16Z] [MIGRATE] Running Version: 201901130830 (201901130830_attachments.sql)
app-1 | INFO [2025-05-31T13:36:17Z] [MIGRATE] Running Version: 201904022134 (201904022134_lowercase_emails.sql)
app-1 | INFO [2025-05-31T13:36:17Z] [MIGRATE] Running Version: 201904091921 (201904091921_fix_api_users_role.sql)
app-1 | INFO [2025-05-31T13:36:17Z] [MIGRATE] Running Version: 202105161823 (202105161823_create_indexes.sql)
app-1 | INFO [2025-05-31T13:36:17Z] [MIGRATE] Running Version: 202107031320 (202107031320_add_locale_field.sql)
app-1 | INFO [2025-05-31T13:36:17Z] [MIGRATE] Running Version: 202107211126 (202107211126_added_allowing_email_auth.sql)
app-1 | INFO [2025-05-31T13:36:17Z] [MIGRATE] Running Version: 202108092243 (202108092243_create_webhooks.sql)
app-1 | INFO [2025-05-31T13:36:17Z] [MIGRATE] Running Version: 202109052023 (202109052023_email_supressed_at.sql)
app-1 | INFO [2025-05-31T13:36:17Z] [MIGRATE] Running Version: 202109072130 (202109072130_paddle_fields.sql)
app-1 | INFO [2025-05-31T13:36:17Z] [MIGRATE] Running Version: 202109272130 (202109272130_system_settings.sql)
app-1 | INFO [2025-05-31T13:36:17Z] [MIGRATE] Running Version: 202205082055 (202205082055_trusted_provider.sql)
app-1 | INFO [2025-05-31T13:36:17Z] [MIGRATE] Running Version: 202406111146 (202406111146_add_posts_user_id_index.sql)
app-1 | INFO [2025-05-31T13:36:17Z] [MIGRATE] Running Version: 202410122105 (202410122105_create_reactions_up.sql)
app-1 | INFO [2025-05-31T13:36:17Z] [MIGRATE] Running Version: 202503202000 (202503202000_mentions_notifications.sql)
app-1 | INFO [2025-05-31T13:36:17Z] [MIGRATE] 74 migrations have been applied.
app-1 | INFO [2025-05-31T13:36:17Z] [WEB] Application is starting
app-1 | INFO [2025-05-31T13:36:17Z] [WEB] Version: 0.22.0-0ea0031a87fe8a2927b4ba6b2967d93bd605c331
app-1 | INFO [2025-05-31T13:36:17Z] [WEB] Environment: production
app-1 | INFO [2025-05-31T13:36:17Z] [WEB] http server started on :3000
app-1 | INFO [2025-05-31T13:36:17Z] [BGW] Starting worker 6.
app-1 | INFO [2025-05-31T13:36:17Z] [BGW] Starting worker 11.
app-1 | INFO [2025-05-31T13:36:17Z] [BGW] Starting worker 1.
app-1 | INFO [2025-05-31T13:36:17Z] [BGW] Starting worker 5.
app-1 | INFO [2025-05-31T13:36:17Z] [BGW] Starting worker 0.
app-1 | INFO [2025-05-31T13:36:17Z] [BGW] Starting worker 2.
app-1 | INFO [2025-05-31T13:36:17Z] [BGW] Starting worker 14.
app-1 | INFO [2025-05-31T13:36:17Z] [BGW] Starting worker 4.
app-1 | INFO [2025-05-31T13:36:17Z] [BGW] Starting worker 7.
app-1 | INFO [2025-05-31T13:36:17Z] [BGW] Starting worker 13.
app-1 | INFO [2025-05-31T13:36:17Z] [BGW] Starting worker 15.
app-1 | INFO [2025-05-31T13:36:17Z] [BGW] Starting worker 12.
app-1 | INFO [2025-05-31T13:36:17Z] [BGW] Starting worker 8.
app-1 | INFO [2025-05-31T13:36:17Z] [BGW] Starting worker 3.
app-1 | INFO [2025-05-31T13:36:17Z] [BGW] Starting worker 10.
app-1 | INFO [2025-05-31T13:36:17Z] [BGW] Starting worker 9.
I can now view the signup page
Be aware that for initial signup it wants to verify your email (which seems silly for the admin user)
At first, I thought I might be stuck as the email did not come through.
Perhaps resend doe not like the from and to addresses to be the same. I certainly didn’t get a forward to my gmail.
That said, I could view the logs in Resend to find the validation URL:
I did a quick scan of settings before moving on and noted that if I take this to production, I can use some IdP’s like Google
I’ll try making a suggestion
I now have a suggestion visible
I now have a couple posts
An incognito window does show that they are public (but one cannot vote without logging in)
This might be a challenge as the sign in just sends emails
Helm
As I’m having troubles with the container so perhaps I’ll have more luck with the Fider helm charts
$ helm repo add fider https://getfider.github.io/helm
"fider" has been added to your repositories
$ helm search repo fider
NAME CHART VERSION APP VERSION DESCRIPTION
fider/fider 0.0.6 0.25.0 An open platform to collect and prioritize feed...
fider/postgresql 12.6.4 15.3.0 PostgreSQL (Postgres) is an open source object-...
We can look at the values in the chart
I can start with a quick install to see what it creates
$ helm install myfider -n fider --set postgresql.enabled=true fider/fider
NAME: myfider
LAST DEPLOYED: Mon Jun 2 21:15:37 2025
NAMESPACE: fider
STATUS: deployed
REVISION: 1
NOTES:
1. Get the application URL by running these commands:
export POD_NAME=$(kubectl get pods --namespace fider -l "app.kubernetes.io/name=fider,app.kubernetes.io/instance=myfider" -o jsonpath="{.items[0].metadata.name}")
export CONTAINER_PORT=$(kubectl get pod --namespace fider $POD_NAME -o jsonpath="{.spec.containers[0].ports[0].containerPort}")
echo "Visit http://127.0.0.1:8080 to use your application"
kubectl --namespace fider port-forward $POD_NAME 8080:$CONTAINER_PORT
$ kubectl get po -n fider
NAME READY STATUS RESTARTS AGE
myfider-6df6556897-sjzs8 0/1 Init:0/1 0 11s
myfider-postgresql-0 0/1 ContainerCreating 0 11s
the first thing I noticed is the dbchecker was failing and it seems to do with a wrong PSQL service name
2025-06-03T02:17:28Z INF [PostgreSQL] Checking the postgresql-service:5432 ...
2025-06-03T02:17:28Z ERR Expectation failed error="failed to establish a connection to the postgresql server, caused by: dial tcp: lookup postgresql-service on 10.43.0.10:53: no such host" dsn=postgres://fider:s0m3g00dp4ssw0rd@postgresql-service:5432/fider?sslmode=disable
2025-06-03T02:17:29Z INF [PostgreSQL] Checking the postgresql-service:5432 ...
2025-06-03T02:17:29Z ERR Expectation failed error="failed to establish a connection to the postgresql server, caused by: dial tcp: lookup postgresql-service on 10.43.0.10:53: no such host" dsn=postgres://fider:s0m3g00dp4ssw0rd@postgresql-service:5432/fider?sslmode=disable
builder@LuiGi:~/Workspaces/jekyll-blog$ kubectl get svc -n fider
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
myfider-postgresql-hl ClusterIP None <none> 5432/TCP 2m3s
myfider ClusterIP 10.43.83.15 <none> 3000/TCP,4000/TCP 2m3s
myfider-postgresql ClusterIP 10.43.139.150 <none> 5432/TCP 2m3s
I fixed that and added values for SendGrid email
$ helm upgrade --install myfider -n fider -f ./values.yaml fider/fider
Release "myfider" has been upgraded. Happy Helming!
NAME: myfider
LAST DEPLOYED: Mon Jun 2 21:26:52 2025
NAMESPACE: fider
STATUS: deployed
REVISION: 2
NOTES:
1. Get the application URL by running these commands:
export POD_NAME=$(kubectl get pods --namespace fider -l "app.kubernetes.io/name=fider,app.kubernetes.io/instance=myfider" -o jsonpath="{.items[0].metadata.name}")
export CONTAINER_PORT=$(kubectl get pod --namespace fider $POD_NAME -o jsonpath="{.spec.containers[0].ports[0].containerPort}")
echo "Visit http://127.0.0.1:8080 to use your application"
kubectl --namespace fider port-forward $POD_NAME 8080:$CONTAINER_PORT
So we could create an ingress, I made a new A record
$ az account set --subscription "Pay-As-You-Go" && az network dns record-set a add-record -g idjdnsrg -z tpk.pw -a 75.73.224.240 -n fider
{
"ARecords": [
{
"ipv4Address": "75.73.224.240"
}
],
"TTL": 3600,
"etag": "61f9f4b8-8462-458f-806b-007de99bd520",
"fqdn": "fider.tpk.pw.",
"id": "/subscriptions/d955c0ba-13dc-44cf-a29a-8fed74cbb22d/resourceGroups/idjdnsrg/providers/Microsoft.Network/dnszones/tpk.pw/A/fider",
"name": "fider",
"provisioningState": "Succeeded",
"resourceGroup": "idjdnsrg",
"targetResource": {},
"trafficManagementProfile": {},
"type": "Microsoft.Network/dnszones/A"
}
I then setup the ingress and applied
builder@LuiGi:~/Workspaces/jekyll-blog$ helm upgrade --install myfider -n fider -f ./values.yaml fider/fider
Release "myfider" has been upgraded. Happy Helming!
NAME: myfider
LAST DEPLOYED: Mon Jun 2 21:43:57 2025
NAMESPACE: fider
STATUS: deployed
REVISION: 7
NOTES:
1. Get the application URL by running these commands:
https://fider.tpk.pw/
builder@LuiGi:~/Workspaces/jekyll-blog$ kubectl get ingress -n fider
NAME CLASS HOSTS ADDRESS PORTS AGE
myfider <none> fider.tpk.pw 80, 443 72s
builder@LuiGi:~/Workspaces/jekyll-blog$ kubectl get cert -n fider
NAME READY SECRET AGE
fider-tls False fider-tls 79s
builder@LuiGi:~/Workspaces/jekyll-blog$ kubectl get cert -n fider
NAME READY SECRET AGE
fider-tls True fider-tls 95s
builder@LuiGi:~/Workspaces/jekyll-blog
I can now signup using the URL https://fider.tpk.pw/
I fired up the signup
This time I had no issues getting the email
I can now add suggestions
I can customize it a bit
Oauth
Let’s add google login as by defualt, no OAuth providers are setup
We first go to Google Credentials to create a new credential
We’ll create a new “OAuth client ID”
We’ll add a new Web client and the OAuth call back to <site>/oauth/google/callback
This should return a Client ID and Secret we’ll need to put into Fider
I’ll now want to add these Env vars via Helm
OAUTH_GOOGLE_CLIENTID: Client ID given by Google
OAUTH_GOOGLE_SECRET: Client Secret given by Google
I can do it with a few quick commands locally:
builder@DESKTOP-QADGF36:~$ helm list -n fider
NAME NAMESPACE REVISION UPDATED STATUS CHART APP VERSION
myfider fider 7 2025-06-02 21:43:57.622777665 -0500 CDT deployed fider-0.0.6 0.25.0
builder@DESKTOP-QADGF36:~$ helm get values myfider -n fider -o yaml > fider.values.yaml
builder@DESKTOP-QADGF36:~$ helm get values myfider -n fider -o yaml > fider.values.yaml.bak
builder@DESKTOP-QADGF36:~$ vi fider.values.yaml
builder@DESKTOP-QADGF36:~$ diff fider.values.yaml fider.values.yaml.bak
42,45d41
< - name: OAUTH_GOOGLE_CLIENTID
< value: 511842454269-8mis7mvs0vfa91mid2n2lq1gsdl1eclo.apps.googleusercontent.com
< - name: OAUTH_GOOGLE_SECRET
< value: GOxxxxxxxxxxxxxxxxxxxxxxxxxxx
builder@DESKTOP-QADGF36:~$ helm repo add fider https://getfider.github.io/helm
"fider" has been added to your repositories
builder@DESKTOP-QADGF36:~$ helm upgrade myfider -n fider -f ./fider.values.yaml fider/fider
Release "myfider" has been upgraded. Happy Helming!
NAME: myfider
LAST DEPLOYED: Tue Jun 3 06:24:17 2025
NAMESPACE: fider
STATUS: deployed
REVISION: 8
NOTES:
1. Get the application URL by running these commands:
https://fider.tpk.pw/
I did not even have to re-login - can now see Google enabled
A quick test proves it works
I’ve now loaded it with some options. I welcome you to go to https://fider.tpk.pw/ to add new ones or vote on them. If Fider turns into spam, then I’ll lock it down more.
AudioBookshelf
I listen to AudioBooks from time to time - most often with Audible for which I have a pretty extensive collection. In fact, just yesterday I picked up the latest Stephen King. But I find dancing between devices a bit challenging.
Audioshelf is a self-hosted Audiobook and Podcast server. Frankly this solves two problems at once (as my ancient Doggcatcher app I don’t think is updated anymore).
The Docker compose steps are pretty easy
services:
audiobookshelf:
image: ghcr.io/advplyr/audiobookshelf:latest
ports:
- 13378:80
volumes:
- </path/to/audiobooks>:/audiobooks
- </path/to/podcasts>:/podcasts
- </path/to/config>:/config
- </path/to/metadata>:/metadata
environment:
- TZ=America/Toronto
I initially planned to convert this to Helm to run in Kubernetes, but I think docker might work best as i can mount the volume on the NAS
builder@builder-T100:~$ sudo mkdir /mnt/sassynassymusic
builder@builder-T100:~$ sudo vi /etc/fstab
builder@builder-T100:~$ cat /etc/fstab | tail -n 1
192.168.1.129:/volume1/music /mnt/sassynassymusic nfs auto,nofail,noatime,nolock,intr,tcp,actimeo=1800 0 0
builder@builder-T100:~$ sudo mount -a
builder@builder-T100:~$ ls /mnt/sassynassymusic/Audiobooks/
@eaDir eatthatfrog_berrettkoehler humbleconsulting humbleleadership long-distanceteammate
I’ll make some local dirs and open them up for podcasts, config and metadata
builder@builder-T100:~/AudioBookshelf$ ls -ltra
total 24
-rw-rw-r-- 1 builder builder 324 Jun 3 07:26 docker-compose.yml
drwxrwxr-x 2 builder builder 4096 Jun 3 07:26 podcasts
drwxr-xr-x 87 builder builder 4096 Jun 3 07:27 ..
drwxrwxr-x 2 builder builder 4096 Jun 3 07:27 config
drwxrwxr-x 2 builder builder 4096 Jun 3 07:27 metadata
drwxrwxr-x 5 builder builder 4096 Jun 3 07:27 .
builder@builder-T100:~/AudioBookshelf$ chmod 777 podcasts/
builder@builder-T100:~/AudioBookshelf$ chmod 777 config/
builder@builder-T100:~/AudioBookshelf$ chmod 777 metadata/
We can now see a docker compose YAML that uses the NAS mount for the AudioBooks but some local folders for the rest
builder@builder-T100:~/AudioBookshelf$ cat ./docker-compose.yml
services:
audiobookshelf:
image: ghcr.io/advplyr/audiobookshelf:latest
ports:
- 13378:80
volumes:
- /mnt/sassynassymusic/Audiobooks:/audiobooks
- /home/builder/AudioBookshelf/podcasts:/podcasts
- /home/builder/AudioBookshelf/config:/config
- /home/builder/AudioBookshelf/metadata:/metadata
environment:
- TZ=America/Chicago
I can now start it up (interactively)
builder@builder-T100:~/AudioBookshelf$ docker compose up
[+] Running 10/10
✔ audiobookshelf 9 layers [⣿⣿⣿⣿⣿⣿⣿⣿⣿] 0B/0B Pulled 6.1s
✔ fe07684b16b8 Pull complete 0.7s
✔ 50e3d90b6378 Pull complete 2.4s
✔ de1f569a8696 Pull complete 2.5s
✔ a35ae40f249e Pull complete 2.5s
✔ fee7fee3e86b Pull complete 3.4s
✔ dfa18c41c46b Pull complete 3.5s
✔ b14f4aee86e0 Pull complete 3.6s
✔ fdf0bf560042 Pull complete 4.8s
✔ 8dc553bc5569 Pull complete 4.8s
[+] Building 0.0s (0/0)
[+] Running 2/2
✔ Network audiobookshelf_default Created 0.1s
✔ Container audiobookshelf-audiobookshelf-1 Created 0.5s
Attaching to audiobookshelf-audiobookshelf-1
audiobookshelf-audiobookshelf-1 | Running in production mode.
audiobookshelf-audiobookshelf-1 | Options: CONFIG_PATH=/config, METADATA_PATH=/metadata, PORT=80, HOST=undefined, SOURCE=docker, ROUTER_BASE_PATH=/audiobookshelf
audiobookshelf-audiobookshelf-1 | [2025-06-03 07:29:10.382] INFO: === Starting Server ===
audiobookshelf-audiobookshelf-1 | [2025-06-03 07:29:10.384] INFO: [Server] Init v2.24.0
audiobookshelf-audiobookshelf-1 | [2025-06-03 07:29:10.384] INFO: [Server] Node.js Version: v20.19.2
audiobookshelf-audiobookshelf-1 | [2025-06-03 07:29:10.385] INFO: [Server] Platform: linux
audiobookshelf-audiobookshelf-1 | [2025-06-03 07:29:10.385] INFO: [Server] Arch: x64
audiobookshelf-audiobookshelf-1 | [2025-06-03 07:29:10.392] INFO: [Database] absdatabase.sqlite not found at /config/absdatabase.sqlite
audiobookshelf-audiobookshelf-1 | [2025-06-03 07:29:10.392] INFO: [Database] Initializing db at "/config/absdatabase.sqlite"
audiobookshelf-audiobookshelf-1 | [2025-06-03 07:29:10.418] INFO: [Database] Loading extension /usr/local/lib/nusqlite3/libnusqlite3.so
audiobookshelf-audiobookshelf-1 | [2025-06-03 07:29:10.419] INFO: [Database] Successfully loaded extension /usr/local/lib/nusqlite3/libnusqlite3.so
audiobookshelf-audiobookshelf-1 | [2025-06-03 07:29:10.419] INFO: [Database] Db supports unaccent and unicode foldings
audiobookshelf-audiobookshelf-1 | [2025-06-03 07:29:10.420] INFO: [Database] Db connection was successful
audiobookshelf-audiobookshelf-1 | [2025-06-03 07:29:10.620] INFO: [MigrationManager] Database is new. Skipping migrations.
audiobookshelf-audiobookshelf-1 | [2025-06-03 07:29:11.005] INFO: [Database] Db initialized with models: user, library, libraryFolder, book, podcast, podcastEpisode, libraryItem, mediaProgress, series, bookSeries, author, bookAuthor, collection, collectionBook, playlist, playlistMediaItem, device, playbackSession, feed, feedEpisode, setting, customMetadataProvider, mediaItemShare
audiobookshelf-audiobookshelf-1 | [2025-06-03 07:29:11.006] INFO: [Database] Adding trigger update_library_items_title
audiobookshelf-audiobookshelf-1 | [2025-06-03 07:29:11.011] INFO: [Database] Adding trigger update_library_items_title_ignore_prefix
audiobookshelf-audiobookshelf-1 | [2025-06-03 07:29:11.018] INFO: [Database] Adding trigger update_library_items_title_from_podcasts_title
audiobookshelf-audiobookshelf-1 | [2025-06-03 07:29:11.024] INFO: [Database] Adding trigger update_library_items_title_ignore_prefix_from_podcasts_title_ignore_prefix
audiobookshelf-audiobookshelf-1 | [2025-06-03 07:29:11.031] INFO: [Database] Adding trigger update_library_items_author_names_on_book_authors_insert
audiobookshelf-audiobookshelf-1 | [2025-06-03 07:29:11.037] INFO: [Database] Adding trigger update_library_items_author_names_on_book_authors_delete
audiobookshelf-audiobookshelf-1 | [2025-06-03 07:29:11.043] INFO: [Database] Adding trigger update_library_items_author_names_on_authors_update
audiobookshelf-audiobookshelf-1 | [2025-06-03 07:29:11.079] INFO: [Database] running ANALYZE
audiobookshelf-audiobookshelf-1 | [2025-06-03 07:29:11.084] INFO: [Database] ANALYZE completed
audiobookshelf-audiobookshelf-1 | [2025-06-03 07:29:11.086] INFO: [LogManager] Init current daily log filename: 2025-06-03.txt
audiobookshelf-audiobookshelf-1 | [2025-06-03 07:29:11.114] INFO: [BackupManager] 0 Backups Found
audiobookshelf-audiobookshelf-1 | [2025-06-03 07:29:11.115] INFO: [BackupManager] Auto Backups are disabled
audiobookshelf-audiobookshelf-1 | [2025-06-03 07:29:11.134] INFO: Listening on port :80
The first page has configure (note: i did not change my zoom level, it just uses rather small fonts)
I’m now at the main dashboard
I’ll add my Audiobooks first.
I then clicked scan
I was a bit worried as these were from a Humble Bundle I got a while back and came down as mp3 files not m4b or any other “book” format.
But as we see, it did find them just fine
Playing from the web browser was fine, but would it pick up where i left off if I switched to the phone?
Indeed it picked right back up.
I stopped then started the Docker service in daemon mode
builder@builder-T100:~/AudioBookshelf$ docker compose up -d
[+] Building 0.0s (0/0)
[+] Running 1/1
✔ Container audiobookshelf-audiobookshelf-1 Started 0.5s
I want to expose this externally so first I need a DNS record
$ az account set --subscription "Pay-As-You-Go" && az network dns record-set a add-record -g idjdnsrg -z tpk.pw -a 75.73.224.240 -n audioshelf
{
"ARecords": [
{
"ipv4Address": "75.73.224.240"
}
],
"TTL": 3600,
"etag": "a49e0012-e016-4851-9c43-7b80929bc704",
"fqdn": "audioshelf.tpk.pw.",
"id": "/subscriptions/d955c0ba-13dc-44cf-a29a-8fed74cbb22d/resourceGroups/idjdnsrg/providers/Microsoft.Network/dnszones/tpk.pw/A/audioshelf",
"name": "audioshelf",
"provisioningState": "Succeeded",
"resourceGroup": "idjdnsrg",
"targetResource": {},
"trafficManagementProfile": {},
"type": "Microsoft.Network/dnszones/A"
}
Then I just need an Endpoint, Service and Ingress to expose it externally
$ cat audioshelf.yaml
apiVersion: v1
kind: Endpoints
metadata:
name: audioshelf-external-ip
subsets:
- addresses:
- ip: 192.168.1.100
ports:
- name: audioshelfint
port: 13378
protocol: TCP
---
apiVersion: v1
kind: Service
metadata:
name: audioshelf-external-ip
spec:
clusterIP: None
clusterIPs:
- None
internalTrafficPolicy: Cluster
ipFamilies:
- IPv4
- IPv6
ipFamilyPolicy: RequireDualStack
ports:
- name: audioshelf
port: 80
protocol: TCP
targetPort: 13378
sessionAffinity: None
type: ClusterIP
---
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
annotations:
cert-manager.io/cluster-issuer: azuredns-tpkpw
ingress.kubernetes.io/ssl-redirect: "true"
kubernetes.io/ingress.class: nginx
kubernetes.io/tls-acme: "true"
nginx.ingress.kubernetes.io/proxy-read-timeout: "3600"
nginx.ingress.kubernetes.io/proxy-send-timeout: "3600"
nginx.org/websocket-services: audioshelf-external-ip
generation: 1
name: audioshelfingress
spec:
rules:
- host: audioshelf.tpk.pw
http:
paths:
- backend:
service:
name: audioshelf-external-ip
port:
number: 80
path: /
pathType: ImplementationSpecific
tls:
- hosts:
- audioshelf.tpk.pw
secretName: audioshelf-tls
$ kubectl apply -f ./audioshelf.yaml
endpoints/audioshelf-external-ip created
service/audioshelf-external-ip created
ingress.networking.k8s.io/audioshelfingress created
I can now login using the URL
Podcasts
Let’s add a new Podcast library
I added several, but no episodes showed up.
When I got back to the UI, I realized it, by default, sets it to find new episodes newer than the moment you add (namely, only future episodes).
I moved it back by a few days in the Episodes tab then could find new episodes
Now I can see one to play
Like this:
One of my favourites from DJ Hex, which my primary coding music, DNB Dojo stopped updating a couple of years ago but he keeps his feed up. I set it to download all the episodes as I just like to listen at random
A quick note: if we add books to a network share, we’ll want to go to the library to “scan” to find them
I found a few classic Sci-fi books to add to my collection of business books on libvox which has free public domain books read by volunteers.
Stats
The app has various stats and metrics for those interested; such as top authors and largest items
I can make user accounts and even set whether they can access explicit content (which would be good for my kiddos)
Summary
We set up Fider, first on docker then on Kubernetes. I spent a bit more time than I hoped trying to get Docker to work - I suspect now it might have just been an old image. Once in Kubernetes, it worked like a charm (using Sendgrid).
I then moved on to AudioBookshelf which was very easy to setup in Docker. They have docs for Docker, Linux, Windows and more. My only challenge was really figuring out how the episodes of podcasts worked. I thought that it would show the last 5 or so but instead it just, by default, shows future episodes. Once I sorted that, it worked great. It also works fantastic for audiobooks. I’ll have to check this more as I commute.
I don’t think I’ll ditch my local Doggcatcher app though because one really good use for an Android app is when i have low/no bandwidth. This means I’ll likely go back to the local app for remote camping (BWCA), airplane and kids sports practices (some of the regional pools are like faraday cages for signal).
Hopefully you found something interesting… and for the time being (unless it gets spammed too hard), please use my Fider (fider.tpk.pw) to provide ideas/suggestions if you have any. If there ends up being a desire for podcasts or YouTube videos, I can always go that direction.