Courses API Documentation
The Courses API is a production-grade B2B REST API that delivers course, skill, role, and YouTube reel data to external clients. It is split into two surfaces: a Public REST API authenticated via shared credentials, and a Web Admin Panel protected by session auth.
All public endpoints are reachable under /api/v1/ and accept JSON request bodies. Every protected call requires your client_id and api_key.
Base URL
All API requests should be made to:https://api.WorkFence.ioAuthentication
The Courses API uses a shared-secret model. There is no OAuth or JWT — every protected request must include two fields in the POST body.
Credential Fields
| Field | Type | Description |
|---|---|---|
| client_id | string (UUID) | Issued by your admin. Uniquely identifies your organisation. |
| api_key | string (32 chars) | Issued alongside your client_id. Regeneratable from the dashboard. |
Validation Flow
The ValidateClientMiddleware runs these checks in order before your request reaches any handler:
- Both
client_idandapi_keymust be present → 401 if missing. client_idis looked up (5-minute cache) → 401 if not found.- Client status must be
active→ 401 if inactive. api_keymust match the stored value → 401 if wrong.- If a domain restriction is set, the
Originheader is checked → 401 on mismatch.
{
"success": false,
"message": "Invalid API key. Regenerate your key from the dashboard."
}Base URL
https://api.WorkFence.io/api/v1All public API endpoints are prefixed with /api/v1. The admin panel lives separately under /admin and is not accessible via API credentials.
Making Your First Request
The quickest way to verify your credentials is to search a single skill. The endpoint returns courses mapped to that skill, sorted by relevance.
- Obtain your
client_idandapi_keyfrom the admin panel. - Send a POST request to
/api/v1/skills. - Include your credentials and a skill slug in the JSON body.
- Check the
successfield in the response.
Request
curl -X POST https://api.WorkFence.io/api/v1/skills \
-H "Content-Type: application/json" \
-d '{
"client_id": "550e8400-e29b-41d4-a716-446655440000",
"api_key": "sk_live_xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx",
"skill": "javascript",
"level": "Beginner",
"language": "en"
}'Response
{
"success": true,
"skill": "javascript",
"total_courses": 48,
"result_count": 24,
"courses": [
{
"course_id": "yt_dQw4w9WgXcQ",
"course_title": "JavaScript Full Course for Beginners",
"course_url": "https://www.youtube.com/watch?v=dQw4w9WgXcQ",
"level": "Beginner",
"average_rating": 4.8,
"total_rating": 12400,
"base_language": "en",
"course_duration": "4h 32m",
"learners_count": 380000,
"view_count": 2100000,
"source": "YouTube"
}
]
}Request Headers
| Header | Value | Required | Description |
|---|---|---|---|
| Content-Type | application/json | Yes | All request bodies must be JSON-encoded. |
| Accept | application/json | No | Recommended. Ensures JSON error responses. |
| Origin | https://yourapp.com | Conditional | Required if your client has domain restrictions enabled. |
Request Parameters
Parameters for POST /api/v1/skills — the primary endpoint. Other endpoints follow the same credential pattern with endpoint-specific fields documented below.
| Name | Type | Required | Description |
|---|---|---|---|
client_id | string (UUID) | Required | Your client UUID issued from the admin panel. |
api_key | string | Required | 32-character API key. Regeneratable from the dashboard. |
skill | string | Required | Skill slug in lowercase (e.g. "javascript", "python"). |
level | string | Optional | Filter by difficulty: "Beginner", "Intermediate", or "Advanced". |
language | string | Optional | ISO language code to filter by base language (e.g. "en"). |