Book of Mormon 365 API Documentation
Build mobile apps and integrations using our REST API. Track daily scripture reading habits, manage goals, and access community features programmatically.
Getting Started
Base URL
https://bookofmormon365.com/api
Authentication
Most API endpoints require authentication using Bearer tokens. For mobile apps, obtain tokens through the authentication endpoints below. Web users can also generate tokens from their profile page.
Authorization: Bearer your_api_token_here
Response Format
All responses are JSON with a status field matching the HTTP status code:
{ "status": 200, "data": { ... } }
{ "status": 400, "error": "Description of what went wrong" }
Rate Limiting
API requests are subject to reasonable rate limits to ensure service quality. If you exceed limits, you'll receive a 429 Too Many Requests
response.
HTTP Status Codes
200
- Success201
- Created (successful POST)400
- Bad Request (invalid input)401
- Unauthorized (missing/invalid token)403
- Forbidden (valid token, insufficient permissions)404
- Not Found (endpoint or resource doesn't exist)405
- Method Not Allowed (wrong HTTP method)409
- Conflict (duplicate resource)422
- Unprocessable Entity (validation failed)429
- Too Many Requests (rate limited)500
- Internal Server Error
Public Endpoints
These endpoints don't require authentication.
GET /api/status
Check API health and get basic information.
{ "status": 200, "app": "Book of Mormon 365 API", "version": 1, "time": "2024-01-15T10:30:00+00:00" }
GET /api/leaderboard
Get community leaderboards for motivation and competition.
Query Parameters:
type
- Leaderboard type:longest_streak
,current_streak
,total_days
(default: longest_streak)limit
- Number of results (1-50, default: 10)
GET /api/leaderboard?type=current_streak&limit=5
{ "status": 200, "leaderboard": [ { "display_name": "john_doe", "metric": 45 }, ... ] }
Privacy Note:
The leaderboard uses display names (usernames when available, otherwise email) to protect user privacy while maintaining community features.
Authentication Endpoints
These endpoints handle user authentication for mobile apps. No Bearer token required.
POST /api/auth/register
Create a new user account.
{ "email": "user@example.com", "username": "john_doe", "password": "securepassword123" }
{ "status": 201, "message": "Account created successfully.", "user": { "id": 123, "username": "john_doe", "email": "user@example.com", "created_at": "2024-01-15T10:30:00+00:00", "passkey_set_at": null }, "token": "api_token_here", "token_id": 456, "expires_at": null }
Validation Rules:
- Email must be valid format
- Username: letters, numbers, hyphens, underscores only
- Password: minimum 8 characters
- Email and username must be unique
POST /api/auth/login
Login with username/email and password.
{ "identifier": "john_doe", // email or username "password": "securepassword123" }
{ "status": 200, "message": "Login successful.", "user": { "id": 123, "username": "john_doe", "email": "user@example.com", "created_at": "2024-01-15T10:30:00+00:00", "passkey_set_at": "2024-01-10T15:20:00+00:00" }, "token": "api_token_here", "token_id": 456, "expires_at": null }
POST /api/auth/passkey-login-options
Get WebAuthn options for passkey login.
{ "identifier": "john_doe" // email or username }
{ "status": 200, "options": { "challenge": "base64_challenge", "timeout": 60000, "rpId": "bookofmormon365.com", // ... other WebAuthn options }, "user_id": 123 }
POST /api/auth/passkey-login
Complete passkey login with WebAuthn credential.
{ "user_id": 123, "credential": { "id": "credential_id", "rawId": "base64_raw_id", "response": { "authenticatorData": "base64_data", "clientDataJSON": "base64_json", "signature": "base64_signature" }, "type": "public-key" } }
{ "status": 200, "message": "Passkey login successful.", "user": { /* same as login */ }, "token": "api_token_here", "token_id": 456, "expires_at": null }
POST /api/auth/refresh-token
Refresh API token (requires current valid token).
Authorization: Bearer current_token
{ "token_id": 456 // optional: ID of token to revoke }
{ "status": 200, "message": "Token refreshed successfully.", "token": "new_api_token_here", "token_id": 789, "expires_at": null }
POST /api/auth/logout
Logout and revoke API token.
Authorization: Bearer token_to_revoke
{ "token_id": 456 // optional: specific token ID to revoke }
{ "status": 200, "message": "Logged out successfully." }
馃摫 Mobile Implementation Notes:
- Token Storage: Store tokens securely (iOS Keychain, Android Keystore)
- Passkey Support: Use platform WebAuthn APIs (iOS: ASAuthorization, Android: FIDO2)
- Offline Handling: Cache user data and sync when connection restored
- Token Lifecycle: Tokens don't expire but can be revoked; implement refresh logic
Authenticated Endpoints
These endpoints require a valid API token in the Authorization header.
GET /api/profile
Get current user's profile information.
{ "status": 200, "user": { "id": 123, "username": "john_doe", "created_at": "2024-01-01T00:00:00+00:00", "passkey_set_at": "2024-01-15T12:00:00+00:00" } }
Privacy Note:
User emails are not exposed through the API to protect privacy. Use the username field for display purposes.
GET /api/stats
Get comprehensive reading statistics for the authenticated user.
{ "status": 200, "stats": { "total_days": 156, "first_day": "2023-06-01", "last_day": "2024-01-15", "longest_streak": 45, "current_streak": 7, "longest_break": 3 } }
GET /api/logs
Retrieve recent reading logs with optional notes.
Query Parameters:
limit
- Number of logs to return (1-100, default: 30)
{ "status": 200, "logs": [ { "reading_date": "2024-01-15", "notes": "Read 1 Nephi 1-3. Great insights about faith.", "created_at": "2024-01-15T08:00:00+00:00" }, ... ] }
POST /api/logs
Log a day of scripture reading. This is the core action for tracking daily habits.
{ "reading_date": "2024-01-15", "notes": "Optional notes about today's reading" }
Validation:
- Date must be in YYYY-MM-DD format
- Notes are optional and limited to 1000 characters
- Logging the same date twice will update the notes
- This automatically updates streak calculations and goal progress
{ "status": 201, "message": "Reading logged.", "reading_date": "2024-01-15" }
DELETE /api/logs/{date}
Remove a reading log entry.
DELETE /api/logs/2024-01-15
{ "status": 200, "message": "Reading removed.", "reading_date": "2024-01-15" }
GET /api/goals
Get both active streak and completion goals for the authenticated user.
{ "status": 200, "streak_goal": { "id": 456, "user_id": 123, "target_days": 30, "start_date": "2024-01-01", "goal_type": "streak", "active": true, "created_at": "2024-01-01T00:00:00+00:00", "achieved_at": null, "completed_days": 14, "percentage": 46, "achieved": false }, "completion_goal": { "id": 457, "user_id": 123, "goal_type": "completion", "completion_target_date": "2024-12-31", "start_date": "2024-01-15", "active": true, "created_at": "2024-01-15T00:00:00+00:00", "achieved_at": null, "total_verses_completed": 1177, "total_verses": 6609, "completion_percentage": 17.81, "section_progress": [...], "chapters_remaining": 194, "days_remaining": 95, "chapters_per_day": 2.04, "verses_remaining": 5432, "verses_per_day": 57.18, "achieved": false } }
Returns null
for either goal type if no active goal exists.
POST /api/goals
Create a new reading goal. Supports both streak goals and completion goals.
Create Streak Goal:
{ "goal_type": "streak", "target_days": 30 }
Create Completion Goal:
{ "goal_type": "completion", "target_date": "2024-12-31" }
{ "status": 201, "goal": { "id": 458, "user_id": 123, "target_days": 30, "start_date": "2024-01-15", "goal_type": "streak", "active": true, "created_at": "2024-01-15T10:00:00+00:00", "achieved_at": null, "completed_days": 0, "percentage": 0, "achieved": false } }
Validation:
- Streak Goals:
target_days
must be between 7 and 1000 - Completion Goals:
target_date
must be in YYYY-MM-DD format and in the future goal_type
must be either "streak" or "completion"
GET /api/books
Get all Book of Mormon books with chapter counts. Useful for building reading progress interfaces.
{ "status": 200, "books": [ { "id": 1, "book_name": "1-nephi", "display_name": "1 Nephi", "chapter_count": 22, "book_order": 1 }, { "id": 2, "book_name": "2-nephi", "display_name": "2 Nephi", "chapter_count": 33, "book_order": 2 }, ... ] }
GET /api/progress
Get detailed Book of Mormon reading progress for the authenticated user.
{ "status": 200, "progress": [ { "book_name": "1-nephi", "display_name": "1 Nephi", "chapter_count": 22, "chapters_completed": 15, "completed_chapters": [1, 2, 3, 4, 5, 7, 8, 9, 12, 13, 14, 15, 18, 20, 22] }, { "book_name": "2-nephi", "display_name": "2 Nephi", "chapter_count": 33, "chapters_completed": 8, "completed_chapters": [1, 2, 3, 5, 9, 11, 25, 31] }, ... ] }
POST /api/progress
Log reading progress for a specific book, chapter, and optionally verse. Also creates a daily reading log entry for streak tracking.
{ "book_name": "1-nephi", "chapter": 3, "verse": 7, "notes": "Great insights about following the Lord's commandments" }
{ "status": 201, "message": "Reading progress logged.", "book_name": "1-nephi", "chapter": 3, "verse": 7 }
Parameters:
book_name
- Required. Use the book_name from /api/books (e.g., "1-nephi", "alma")chapter
- Required. Chapter number (must be >= 1)verse
- Optional. Specific verse number (must be >= 1 if provided)notes
- Optional. Reading notes (max 1000 characters)
Behavior:
- Automatically creates a daily reading log entry for streak tracking
- Updates completion goal progress if user has an active completion goal
- Prevents duplicate entries for the same book/chapter/verse on the same day
Bulk Progress Update:
{ "bulk_update": true, "progress_data": { "1-nephi": 22, "2-nephi": 15, "jacob": 7, "alma": 30 } }
{ "status": 201, "message": "Bulk reading progress updated.", "books_updated": 4 }
Bulk Update Notes: Use the bulk_update: true
flag with progress_data
object where keys are book names and values are chapter counts completed. This efficiently updates multiple books at once.
POST /api/mark-all-read
Mark all chapters in the Book of Mormon as read. This is a shortcut for users who have already completed the book.
{}
{ "status": 201, "message": "All chapters marked as read. Congratulations on completing the Book of Mormon!", "total_chapters": 239 }
Behavior:
- Marks all 239 chapters across all 15 books as completed
- Creates a daily reading log entry for streak tracking
- Updates completion goal progress to 100%
- Useful for users migrating from other tracking systems
Mobile App Implementation Guide
Core Features to Implement
- Authentication Flow - Direct users to the web app for login/registration and API token generation
- Daily Reading Tracker - Simple interface to log today's reading with optional notes
- Detailed Progress Tracking - Book/chapter/verse specific reading progress with Book of Mormon completion tracking
- Progress Dashboard - Display current streak, total days, and both goal types with progress
- Dual Goal Management - Allow users to set and track both streak goals and completion goals
- Book of Mormon Interface - Navigate through all 15 books with chapter selection for detailed progress logging
- Reading History - Show recent reading logs and detailed chapter progress
- Community Features - Display leaderboards for motivation
Recommended App Flow
- Onboarding - Explain the dual goal system (streaks + completion) and direct to web registration
- Token Setup - Guide users to get their API token from their profile
- Goal Creation - Help users set up both streak and completion goals
- Daily Check-in - Choose between simple reading log or detailed book/chapter progress
- Progress View - Visual streak counter, completion percentage, and daily targets
- Book Navigation - Browse through Book of Mormon books with chapter-by-chapter progress
- Motivation - Show leaderboards and personal stats
Data Sync Strategy
- Cache API responses for offline viewing
- Sync both simple reading logs and detailed progress when connectivity is available
- Cache Book of Mormon structure (/api/books) for offline book/chapter selection
- Handle conflicts by preferring server data
- Refresh leaderboards, stats, and goal progress periodically
- Sync completion goal targets and daily reading calculations
Push Notifications
Consider implementing daily reminders to encourage consistent reading habits. The API doesn't currently support push notifications, but you can implement local notifications for:
- Daily reading reminders with suggested chapters based on completion goals
- Streak milestone celebrations
- Completion goal progress milestones (25%, 50%, 75%)
- Daily target reminders ("Read 2.5 chapters today to stay on track")
- Goal completion notifications for both streak and completion achievements
Security & Privacy
Data Privacy
- No Email Exposure - User emails are never exposed through the API to protect privacy
- Display Names - Leaderboards and profiles use usernames when available
- User Isolation - Users can only access their own data through authenticated endpoints
- Input Validation - All inputs are validated and sanitized
Best Practices
- Secure Token Storage - Store API tokens securely in your app (keychain/secure storage)
- Rate Limiting - Be respectful with API usage and implement client-side rate limiting
- Data Validation - Always validate data on the client side before sending to API
- Error Handling - Implement proper error handling for all API responses
Mobile App Integration Examples
iOS Swift Example
struct LoginRequest: Codable { let identifier: String let password: String } struct User: Codable { let id: Int let username: String let email: String let created_at: String let passkey_set_at: String? } struct LoginResponse: Codable { let status: Int let message: String let user: User let token: String let token_id: Int } func login(identifier: String, password: String) async throws -> LoginResponse { let url = URL(string: "https://bookofmormon365.com/api/auth/login")! var request = URLRequest(url: url) request.httpMethod = "POST" request.setValue("application/json", forHTTPHeaderField: "Content-Type") let loginData = LoginRequest(identifier: identifier, password: password) request.httpBody = try JSONEncoder().encode(loginData) let (data, _) = try await URLSession.shared.data(for: request) return try JSONDecoder().decode(LoginResponse.self, from: data) }
Android Kotlin Example
data class LoginRequest( val identifier: String, val password: String ) data class LoginResponse( val status: Int, val message: String, val user: User, val token: String, val token_id: Int ) interface BookOfMormonApi { @POST("auth/login") suspend fun login(@Body request: LoginRequest): Response<LoginResponse> @GET("profile") suspend fun getProfile(@Header("Authorization") token: String): Response<ProfileResponse> @POST("logs") suspend fun logReading(@Header("Authorization") token: String, @Body request: LogRequest): Response<LogResponse> } class ApiClient { private val api = Retrofit.Builder() .baseUrl("https://bookofmormon365.com/api/") .addConverterFactory(GsonConverterFactory.create()) .build() .create(BookOfMormonApi::class.java) suspend fun login(identifier: String, password: String): LoginResponse? { val response = api.login(LoginRequest(identifier, password)) return if (response.isSuccessful) response.body() else null } }
React Native Example
class BookOfMormonClient { constructor(baseUrl = 'https://bookofmormon365.com/api') { this.baseUrl = baseUrl; this.token = null; } async login(identifier, password) { const response = await fetch(`${this.baseUrl}/auth/login`, { method: 'POST', headers: { 'Content-Type': 'application/json', }, body: JSON.stringify({ identifier, password }), }); const data = await response.json(); if (data.status === 200) { this.token = data.token; // Store token securely await AsyncStorage.setItem('bom365_token', data.token); } return data; } async logReading(date, notes = null) { const response = await fetch(`${this.baseUrl}/logs`, { method: 'POST', headers: { 'Content-Type': 'application/json', 'Authorization': `Bearer ${this.token}`, }, body: JSON.stringify({ reading_date: date, notes }), }); return await response.json(); } }
Support and Feedback
Questions or need help building your integration? Contact us or open an issue in our repository.