Troubleshooting
Solutions to common problems with Morgenruf. If your issue isn't listed here, open a discussion on GitHub.
Bot Not Responding to Slash Commands
This usually means Slack can't reach your bot's request URL. Check the following:
- Your bot process is running and listening on the configured port.
- The Request URL in your Slack app's Slash Commands settings matches the public URL of your deployment (e.g.
https://yourdomain.com/slack/events). - Your server's TLS certificate is valid β Slack requires HTTPS with a trusted certificate.
- No firewall or reverse proxy is blocking inbound requests from Slack's IP ranges.
You can verify reachability by running:
curl -X POST https://yourdomain.com/slack/events
bash
You should receive a 400 or 401 response (not a connection error).
Morgenruf must be invited to the channel before slash commands can be used there. In Slack, run:
/invite @Morgenruf
slack
If you're self-hosting, also verify that your Slack app manifest includes the commands scope and the correct slash command definition.
OAuth / Installation Errors
The redirect URI registered in your Slack app must exactly match the one used at runtime. In your Slack app settings under OAuth & Permissions β Redirect URLs, ensure the entry matches your APP_URL environment variable, including the path:
https://yourdomain.com/slack/oauth_redirect
example
Trailing slashes and HTTP vs HTTPS differences will cause a mismatch.
When a workspace reinstalls the app, Slack issues a new token and invalidates the old one. Morgenruf stores the latest token automatically during the OAuth callback. If you see invalid_auth errors:
- Remove Morgenruf from your workspace in Slack β Apps β Remove App.
- Reinstall via the "Add to Slack" button on morgenruf.dev (or your self-hosted install URL).
For self-hosted deployments, also verify the SLACK_CLIENT_ID and SLACK_CLIENT_SECRET environment variables match the credentials in your Slack app settings.
Database Connection Issues
Check that your DATABASE_URL environment variable is set and points to a reachable PostgreSQL instance:
postgresql://user:password@host:5432/morgenruf
example DATABASE_URL
Common causes:
- The database container hasn't finished starting up β add a
depends_onhealth check in yourdocker-compose.yml. - The hostname is incorrect β when using Docker Compose, use the service name (e.g.
db), notlocalhost. - The database user lacks the
CREATEprivilege needed for migrations.
Morgenruf runs database migrations automatically at startup. If migrations fail:
- Ensure the database exists before the app starts (create it with
createdb morgenrufor via your cloud provider). - Check the application logs for the specific SQL error β it usually points to a permission or version incompatibility.
- PostgreSQL 13 or newer is required.
To run migrations manually:
docker run --rm -e DATABASE_URL=... ghcr.io/morgenruf/morgenruf:latest migrate
bash
Standup Not Sending at Scheduled Time
The most common cause is a timezone misconfiguration. Verify:
- The workspace timezone in Dashboard β Settings is set to the correct IANA timezone (e.g.
America/New_York, notEST). - Individual members haven't set a personal timezone override that conflicts with expectations β they can check with the DM command:
timezone. - The server's system clock is accurate (run
datein the container to verify).
If no DMs were sent at all:
- Check that the standup is active in the dashboard β it may have been paused.
- Confirm the scheduled day is enabled (e.g. if today is Monday, verify Monday is checked under Active Days).
- If self-hosting, check that only one instance of the bot is running β multiple replicas can cause the scheduler to skip jobs. Use a single scheduler replica or a distributed lock (see the Self Hosting docs).
- Review application logs around the scheduled time for scheduler errors.
Celebrations
The reaction needs the reactions:write scope, and workspaces that installed Morgenruf before it existed have not granted it. The scope is optional, which is why the posts still go out.
- A workspace admin clicks Re-authorise Slack on the Celebrations page. Posts after that get the reaction.
- If you're self-hosting, add
reactions:writeto your Slack app's bot scopes first (see Upgrading to member profiles and Celebrations), then re-authorise.
Check the following:
- Celebrations is turned on, and a channel and a timezone are saved.
- @Morgenruf has been invited to the celebrations channel.
- The person has the date in their profile and has not ticked Don't celebrate me publicly.
- For an anniversary, the start date is at least a year ago.
- The day was not a day off. A celebration on a weekend or a listed holiday is posted on the last working day before it, so look there. The Coming up list on the Celebrations page shows which day each one is posted.
Dashboard Not Loading
Open the browser developer console (F12 β Console) and look for errors. Common causes:
- Content Security Policy (CSP) error: If you're running behind a reverse proxy, ensure it isn't injecting a CSP header that blocks the app's scripts.
- API 401 errors: Your session has expired. Log out and log back in via the Sign in with Slack button.
- API 500 errors: A backend error β check server logs for the root cause.
Only workspace admins and members added in Dashboard β Members can access the dashboard. If you're an admin and still see this error:
- Sign out and sign back in with Slack to refresh your session.
- Confirm you're signing in with the same Slack account that installed the app.
- If self-hosting, verify the
SESSION_SECRETenvironment variable is set and hasn't changed since installation.
Docker / Kubernetes Deployment Issues
Inspect the container logs to find the root cause:
# Docker
docker logs morgenruf --tail 50
# Kubernetes
kubectl logs deployment/morgenruf --tail 50
bash
Common causes:
- A required environment variable is missing β see Environment Variables for the full list.
- The database is unreachable at startup (see Database Connection Issues above).
- Port conflicts β ensure nothing else is bound to the same port on the host.
Check the pod events for scheduling or image-pull errors:
kubectl describe pod -l app.kubernetes.io/name=morgenruf
bash
Common causes:
- ImagePullBackOff: The image tag in your
values.yamldoesn't exist or the registry is unreachable. Useghcr.io/morgenruf/morgenruf:latestor a pinned version tag. - Pending / Insufficient resources: Your cluster doesn't have enough CPU or memory. Lower the resource requests in
values.yamlor add nodes. - Secret not found: If you're using Kubernetes Secrets for environment variables, verify the secret exists in the same namespace as the deployment.
See the Kubernetes / Helm docs for a full deployment walkthrough.
A 502 from the ingress means it can reach the service but not the pod. Verify:
- The pod is Running and its readiness probe is passing:
kubectl get pods. - The
ServicetargetPortmatches the port the app listens on (default3000). - If using TLS termination at the ingress, the backend service should target HTTP, not HTTPS.
Check ingress controller logs for more detail:
kubectl logs -n ingress-nginx deployment/ingress-nginx-controller --tail 50
bash
Still stuck? Open a discussion on GitHub or email hello@morgenruf.dev.