banners-api.md
Banners API
Dynamic banners for the homepage carousel/slider. Banners can be scheduled to appear at specific times.
Client API
Get active banners
GET /client/v1/banners/
Returns a list of all currently active banners, ordered by displayOrder (ascending). Use this to render the homepage banner carousel.
Response 200 OK
[
{
"id": "xYz123",
"name": "Summer Campaign",
"image": "https://example.com/banner-desktop.jpg",
"mobileImage": "https://example.com/banner-mobile.jpg",
"link": "https://example.com/promo"
}
]
| Field | Type | Description |
|---|---|---|
id |
string | Banner ID |
name |
string | Banner name (for display or accessibility) |
image |
string | Desktop/web banner image URL |
mobileImage |
string | Mobile banner image URL |
link |
string? | Click-through URL. null if no action on click |
Notes:
- The response is an array. Render all items in a carousel/slider, in the order returned.
- If
linkis not null, the banner should be clickable and navigate to that URL. - If the array is empty, hide the banner section.
- The API handles scheduling server-side; the client always receives only the banners that should be visible right now.
Admin API
All admin endpoints require the admin authorization header.
Create a banner
POST /admin/v1/banners
Request body:
{
"name": "Summer Campaign",
"image": "https://example.com/banner-desktop.jpg",
"mobileImage": "https://example.com/banner-mobile.jpg",
"link": "https://example.com/promo",
"isActive": true,
"activeFrom": "2026-06-01T00:00:00Z",
"activeUntil": "2026-06-30T23:59:59Z",
"displayOrder": 1
}
| Field | Type | Required | Description |
|---|---|---|---|
name |
string | yes | Banner name |
image |
string | yes | Desktop image URL |
mobileImage |
string | yes | Mobile image URL |
link |
string? | no | Click-through URL |
isActive |
boolean | yes | Whether this banner is enabled |
activeFrom |
datetime? | no | Schedule start (UTC). null = no start restriction |
activeUntil |
datetime? | no | Schedule end (UTC). null = no end restriction |
displayOrder |
integer | yes | Sort order in the carousel. Lower number = shown first |
Response: 200 OK with AdminBannerDto (see below).
List all banners
GET /admin/v1/banners?page=1&pageSize=20
Response: 200 OK
{
"items": [ /* AdminBannerDto[] */ ],
"totalCount": 5
}
Get a single banner
GET /admin/v1/banners/{id}
Response: 200 OK with AdminBannerDto.
Update a banner
PUT /admin/v1/banners/{id}
Same body as create, plus id in the body matching the URL param.
Delete a banner
DELETE /admin/v1/banners/{id}
Response: 200 OK with true/false.
AdminBannerDto
{
"id": "xYz123",
"name": "Summer Campaign",
"image": "https://example.com/banner-desktop.jpg",
"mobileImage": "https://example.com/banner-mobile.jpg",
"link": "https://example.com/promo",
"isActive": true,
"activeFrom": "2026-06-01T00:00:00Z",
"activeUntil": "2026-06-30T23:59:59Z",
"displayOrder": 1,
"createdAt": "2026-04-01T10:00:00Z",
"updatedAt": "2026-04-01T10:00:00Z",
"createdBy": null,
"updatedBy": null
}
Scheduling logic
A banner appears in the client response when all of the following are true:
isActiveistrueactiveFromisnullor current time >=activeFromactiveUntilisnullor current time <activeUntil
| Scenario | isActive |
activeFrom |
activeUntil |
|---|---|---|---|
| Always visible | true |
null |
null |
| Visible after a date | true |
2026-06-01T00:00Z |
null |
| Visible until a date | true |
null |
2026-06-30T23:59Z |
| Scheduled window | true |
2026-06-01T00:00Z |
2026-06-30T23:59Z |
| Manually disabled | false |
any | any |