Full-Stack Quickstart
Purpose: Show the recommended setup for most teams.
Use this when: You have frontend code and backend code.
Do not use this when: You only have a backend or selected Frontend or mobile app for a public client with no backend exchange.
Backend required: Yes.
Allowed runtimes: Browser + backend, mobile + backend.
Required credentials: A Backend/server app from Developer Console, with its pre-live client_id in the frontend and its pre-live client_id plus one-time client_secret in the backend.
Minimal import: @quranjs/api/public in frontend, @quranjs/api/server in backend.
Frontend
import { createPublicClient } from "@quranjs/api/public";
export const authClient = createPublicClient({
clientId: "your-client-id",
clientType: "confidential-proxy",
services: {
gatewayUrl: "https://apis-prelive.quran.foundation",
oauth2BaseUrl: "https://prelive-oauth2.quran.foundation",
},
});
Backend
import { createServerClient } from "@quranjs/api/server";
export const apiClient = createServerClient({
clientId: process.env.QF_CLIENT_ID!,
clientSecret: process.env.QF_CLIENT_SECRET!,
services: {
gatewayUrl: "https://apis-prelive.quran.foundation",
oauth2BaseUrl: "https://prelive-oauth2.quran.foundation",
},
});
Both clients explicitly use pre-live so they match a newly created Console app. After production permissions are granted, switch the frontend and backend Client IDs, the backend secret, and both service URLs to production together.
Short Flow
- Frontend creates the authorize URL and sends the user to Quran Foundation login.
- Frontend receives the authorization code.
- Frontend sends
code + code_verifier + redirect_urito the backend. - Backend exchanges the code.
- Backend calls Content or approved User APIs as needed. Search calls require separate Search permission in Developer Console.
Think of it like this:
- The frontend starts login with PKCE.
- The backend does the secret parts.
- The backend keeps the session.
- The frontend never sees
client_secret.
Content and Search can still keep working even if the user session expires, because they use a separate app token. User APIs use the signed-in user's token, so they may need refresh sooner.
For serious multi-instance production deployments, keep the user session in a shared server-side store such as Redis. Edge or serverless frontends still typically need a backend or BFF layer for confidential token exchange and session management.
For a fuller reference, use the standalone quran-oauth2-sdk-e2e-example repo. It acts as a broader interactive playground with a same-origin React SPA shell over an Express backend/BFF, and demonstrates login, refresh, logout, app-authenticated search, server-side Quran content reads, notes, bookmarks, collections, and QuranReflect calls in one place.