Skip to main content

Documentation Index

Fetch the complete documentation index at: https://mintlify.com/astrxnomo/tourify/llms.txt

Use this file to discover all available pages before exploring further.

Tourify authenticates mobile clients with Laravel Sanctum opaque bearer tokens. This page explains how tokens are issued, how to include them in requests, their lifetime, and how to revoke them.

How It Works

Tourify’s API is protected by Laravel Sanctum using opaque, plain-text bearer tokens. The model is fully stateless from the API’s perspective:
  • Tokens are generated server-side and returned once — the server does not store the plain-text value.
  • The client is responsible for persisting the token securely and sending it on every protected request.
  • Each call to /api/auth/register or /api/auth/login creates a new, independent token — a user can hold multiple active tokens simultaneously (one per device or session).
  • Tokens have no expiration by default (expiration: null in config/sanctum.php). They remain valid until explicitly revoked via logout.
On mobile, store the token with Expo SecureStore — the Tourify app already does this. SecureStore encrypts values at rest using the device’s secure enclave, making it significantly safer than AsyncStorage.

Obtaining a Token

Both the register and login endpoints return identical response shapes: a user object and a plain-text token string. Save the token immediately after receiving it.
1

Register a new account

POST /api/auth/register
name
string
required
The user’s full display name. Maximum 255 characters.
email
string
required
A valid, unique email address.
password
string
required
Minimum 8 characters.
password_confirmation
string
required
Must match password exactly.
Request
curl -X POST http://localhost:8000/api/auth/register \
  -H "Content-Type: application/json" \
  -H "Accept: application/json" \
  -d '{
    "name": "María García",
    "email": "maria@example.com",
    "password": "securepassword",
    "password_confirmation": "securepassword"
  }'
Response 201 Created
{
  "user": {
    "id": 1,
    "name": "María García",
    "email": "maria@example.com",
    "role_id": 2,
    "push_token": null,
    "created_at": "2024-06-01T10:00:00.000000Z",
    "updated_at": "2024-06-01T10:00:00.000000Z"
  },
  "token": "1|aBcDeFgHiJkLmNoPqRsTuVwXyZ1234567890abcdef"
}
2

Log in to an existing account

POST /api/auth/login
email
string
required
The account’s registered email address.
password
string
required
The account password.
Request
curl -X POST http://localhost:8000/api/auth/login \
  -H "Content-Type: application/json" \
  -H "Accept: application/json" \
  -d '{
    "email": "maria@example.com",
    "password": "securepassword"
  }'
Response 200 OK
{
  "user": {
    "id": 1,
    "name": "María García",
    "email": "maria@example.com",
    "role_id": 2,
    "push_token": null,
    "created_at": "2024-06-01T10:00:00.000000Z",
    "updated_at": "2024-06-01T10:00:00.000000Z"
  },
  "token": "2|xYzAbCdEfGhIjKlMnOpQrStUvWxYz0987654321fedcba"
}
If credentials are incorrect, the API returns HTTP 422 with errors.email set to "Las credenciales no son correctas.".
3

Store the token on the client

Save the token string to secure storage immediately after a successful register or login response. In the Tourify Expo app, this is handled with expo-secure-store:
import * as SecureStore from 'expo-secure-store';

await SecureStore.setItemAsync('auth_token', token);

Using the Token in Requests

Include the token as a Bearer credential in the Authorization header of every request to a protected endpoint:
Authorization: Bearer {your-token}
The header must be present on every request — the API is fully stateless and does not use cookies or sessions for mobile clients.

Complete Example: Login → Authenticated Request

The following shell script logs in, captures the token from the JSON response, then calls the protected GET /api/auth/me endpoint to retrieve the authenticated user’s profile.
# Step 1: Log in and extract the token
TOKEN=$(curl -s -X POST http://localhost:8000/api/auth/login \
  -H "Content-Type: application/json" \
  -H "Accept: application/json" \
  -d '{"email":"maria@example.com","password":"securepassword"}' \
  | grep -o '"token":"[^"]*"' \
  | cut -d'"' -f4)

echo "Token: $TOKEN"

# Step 2: Call a protected endpoint using the token
curl -X GET http://localhost:8000/api/auth/me \
  -H "Accept: application/json" \
  -H "Authorization: Bearer $TOKEN"
Response 200 OK
{
  "id": 1,
  "name": "María García",
  "email": "maria@example.com",
  "role_id": 2,
  "push_token": null,
  "created_at": "2024-06-01T10:00:00.000000Z",
  "updated_at": "2024-06-01T10:00:00.000000Z",
  "role": {
    "id": 2,
    "name": "user"
  }
}
GET /api/auth/me returns the authenticated user with their role relationship eager-loaded.

Multiple Tokens Per User

Every call to /api/auth/register or /api/auth/login issues a brand-new token — it does not invalidate previous tokens. This allows a single user to be logged in on multiple devices at the same time, each holding its own independent token.
Device A  →  login  →  token_A  (valid)
Device B  →  login  →  token_B  (valid, independent of token_A)

Token Lifetime

Tokens do not expire automaticallyexpiration is set to null in config/sanctum.php. A token remains valid indefinitely until it is explicitly revoked by calling POST /api/auth/logout with that token in the Authorization header.

Revoking a Token (Logout)

POST /api/auth/logout deletes only the current access token (the one attached to the incoming request). Other tokens belonging to the same user on other devices are not affected.
curl -X POST http://localhost:8000/api/auth/logout \
  -H "Accept: application/json" \
  -H "Authorization: Bearer 2|xYzAbCdEfGhIjKlMnOpQrStUvWxYz0987654321fedcba"
Response 200 OK
{
  "message": "Sesión cerrada correctamente."
}
After logout, discard the token from client storage:
import * as SecureStore from 'expo-secure-store';

await SecureStore.deleteItemAsync('auth_token');

Error Responses

If the bearer token is missing, invalid, or has been revoked, every protected endpoint returns HTTP 401 Unauthenticated:
{
  "message": "Unauthenticated."
}
When you receive a 401, prompt the user to log in again and replace the stored token.

Response Fields Reference

user
object
The authenticated user object returned by /api/auth/register, /api/auth/login, and /api/auth/me.
token
string
Opaque plain-text Sanctum bearer token. Include this value in the Authorization: Bearer {token} header on all subsequent protected requests. Not returned by GET /api/auth/me.

Build docs developers (and LLMs) love