Auth

Login, refresh and logout endpoints for the HookSentry dashboard API — JWT access and refresh tokens.

See Authentication for how the returned tokens are used on every other endpoint.

Login

POST /api/v1/auth/login

Authenticates an existing user and returns a JWT access token (TTL 15 minutes) and a refresh token (TTL 7 days). The refresh token is stored in Redis; the access token is stateless, validated only by signature and expiration.

Auth: none

Body

FieldTypeRequiredDescription
emailstringYesUser email
passwordstringYesUser password
using var client = new HttpClient();

var response = await client.PostAsJsonAsync("https://api.hooksentry.com/api/v1/auth/login", new
{
    email = "owner@example.com",
    password = "SenhaSegura123!"
});

var auth = await response.Content.ReadFromJsonAsync<AuthResponse>();

record AuthResponse(string AccessToken, int ExpiresIn, string RefreshToken, DateTimeOffset ExpiresAt);

Return codes

  • 200 OK — authentication successful
  • 400 Bad Request — missing required fields or invalid email format
  • 401 Unauthorized — invalid credentials or inactive user
  • 429 Too Many Requests — rate limit exceeded (see Errors & Rate Limiting)
{
  "accessToken": "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9...",
  "expiresIn": 900,
  "refreshToken": "8f14e45fceea167a5a36dedd4bea2543...",
  "expiresAt": "2026-07-10T14:32:00.000Z"
}

Refresh token

POST /api/v1/auth/refresh

Exchanges an active refresh token for a new token pair. The provided refresh token is consumed atomically (single-use, via Redis GETDEL) — reusing it fails.

Auth: none

Body

FieldTypeRequiredDescription
refreshTokenstringYesRefresh token obtained at login or from a previous refresh
using var client = new HttpClient();

var response = await client.PostAsJsonAsync("https://api.hooksentry.com/api/v1/auth/refresh", new
{
    refreshToken
});

var auth = await response.Content.ReadFromJsonAsync<AuthResponse>();

Return codes

  • 200 OK — new tokens issued successfully
  • 400 Bad Request — required field missing
  • 401 Unauthorized — invalid, expired, or already-used refresh token
{
  "accessToken": "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9...",
  "expiresIn": 900,
  "refreshToken": "3c9d2b7e1a4f8c6d0e5b9a2f7c1d4e8b...",
  "expiresAt": "2026-07-10T14:47:00.000Z"
}

Logout

POST /api/v1/auth/logout

Removes the refresh token from Redis and immediately revokes the access token via a Redis denylist keyed by the token's jti. Any subsequent request with the same access token receives 401 Unauthorized.

Auth: Bearer token

Body

FieldTypeRequiredDescription
refreshTokenstringYesRefresh token to invalidate
var request = new HttpRequestMessage(HttpMethod.Post, "https://api.hooksentry.com/api/v1/auth/logout")
{
    Content = JsonContent.Create(new { refreshToken })
};
request.Headers.Authorization = new AuthenticationHeaderValue("Bearer", accessToken);

using var client = new HttpClient();
var response = await client.SendAsync(request);

Return codes

  • 204 No Content — logout successful
  • 400 Bad RequestrefreshToken missing
  • 401 Unauthorized — missing/invalid JWT, or the refresh token doesn't belong to the caller