Gifable is a self hostable gif library manager.
- Add gifs to your library with searchable comments.
- Find your perfect gif quickly.
- Upload gifs to your S3 compatible bucket.
- Works with javascript disabled.
- Keyboard / accessibility friendly.
- Matrix Federation - Share GIFs with Matrix clients (Element, Gomuks, etc.) using MXC URIs.
Gifable is available as a docker image.
docker pull ghcr.io/pietvanzoen/gifable:latestTo run the image first setup your configuration. Copy the .env.example and update as needed.
curl https://raw.githubusercontent.com/pietvanzoen/gifable/main/.env.example -o .envThen run the image using --env-file flag. You'll also want to attach a volume for the database so it is persisted between runs. In this example we're using a directory /data to store the database file. You don't need to create the file, the app will create one if it doesn't exist.
docker run -d \
--name gifable \
--env-file=$PWD/.env \
-v $PWD/data:/data \
-e DATABASE_URL="file:/data/gifable.db" \
ghcr.io/pietvanzoen/gifable:latestGifable supports multiple database providers:
- SQLite (default) - Perfect for single-server deployments and development
- PostgreSQL - Recommended for production, especially with managed services like Digital Ocean
See docs/database-providers.md for detailed configuration instructions, migration guides, and best practices.
-
Update
prisma/schema.prisma:datasource db { provider = "postgresql" url = env("DATABASE_URL") }
-
Set your DATABASE_URL in
.env:DATABASE_URL="postgresql://user:password@host:5432/gifable?sslmode=require" -
Run migrations:
npx prisma migrate deploy
Important: Keep prisma/schema.prisma as SQLite during migration. The script connects to both databases independently.
# Make sure schema.prisma still has provider = "sqlite"
SQLITE_URL="file:./dev.db" POSTGRES_URL="postgresql://user:password@host:5432/gifable?sslmode=require" npm run migrate:sqlite-to-postgres
# After successful migration, update schema.prisma to:
# provider = "postgresql"
# Then update your .env DATABASE_URL and run:
npx prisma generateSee the database providers documentation for detailed instructions.
See .env.example for all available configuration options.
Gifable supports Matrix federation, allowing Matrix clients to use your GIFs via MXC URIs (mxc://). This enables seamless integration with Matrix messaging platforms like Element, Gomuks, FluffyChat, and more.
- Your Gifable instance acts as a Matrix media server
- Public media can be referenced using
mxc://your-domain.com/media-idURIs - Matrix homeservers fetch media via standard Matrix endpoints
- No duplicates - the same GIF = the same MXC URI across all Matrix rooms
- Homeservers cache media and can independently manage cleanup
-
Set your public domain in
.env:APP_URL=https://gifs.example.com
-
Ensure media is public - Only public media is accessible via federation
-
That's it! Matrix endpoints are automatically available:
/.well-known/matrix/server- Server discovery/_matrix/media/v3/download/{serverName}/{mediaId}- Media downloads/_matrix/media/v3/thumbnail/{serverName}/{mediaId}- Thumbnails
Generate MXC URIs in your code:
import { getMxcUri } from "~/utils/media.server";
const mxcUri = getMxcUri(mediaId);
// Returns: "mxc://gifs.example.com/abc-123-def"Test your Matrix federation setup:
# Run the test script
APP_URL=http://localhost:3000 TEST_MEDIA_ID=your-media-id ./scripts/test-matrix-federation.sh
# Or test manually
curl https://gifs.example.com/.well-known/matrix/serverFor detailed documentation, see:
- docs/matrix-federation.md - Complete guide
- docs/matrix-federation-testing.md - Testing instructions