Skip to content

API Token (machine-to-machine)

API Token cấp cho hệ thống máy (CRM backend, dialer engine, integration service) gọi API Zorio mà không gắn với phiên user. Phù hợp cho server-to-server traffic, cron job, microservice tích hợp.

Khác biệt với Bearer (phiên user) (user session)

Đặc điểmBearer (phiên user) (user)API Token (machine)
Gắn với user nào1 user cụ thể1 ứng dụng / service
Khi user logoutToken mất hiệu lựcVẫn sống
Khi user đổi mật khẩuCòn sốngCòn sống
Audit log ghi nhậnTheo user.usernameTheo tên ứng dụng
Phù hợp choApp có người dùng (frontend, mobile)Server-to-server / cron

TIP

Cả 2 dạng đều dùng header Authorization: Bearer <token> giống nhau — phân biệt qua cách cấp + audit log, không phải qua format token.

Tạo API Token

Chỉ admin được tạo

API Token chỉ admin của tài khoản tạo được — qua Admin Console. Không có endpoint API để tự tạo (tránh CRM tự nhân bản token).

Quy trình

  1. Vào Admin Console → Cài đặt → API Tokens.
  2. Chọn tab Machine Tokens (khác tab "User Tokens").
  3. Bấm Tạo Machine Token:
    • Tên — vd "CRM Salesforce Production", "Dialer Engine v2".
    • Permission scope — chọn permissions cụ thể (vd pbx_api_access, telesales_create_lead).
    • IP whitelist (tùy chọn) — chỉ chấp nhận request từ các IP cụ thể.
    • Expiration (tùy chọn) — auto-expire sau N ngày.
  4. Hệ thống sinh token → copy ngay 1 lần.

Dùng API Token

Giống Bearer (phiên user) — chỉ thêm header Authorization: Bearer <token> vào mọi request.

bash
curl -X POST 'https://app.zorio.vn/api/pbx/calls/click-to-call' \
  -H 'Authorization: Bearer <YOUR_MACHINE_TOKEN>' \
  -H 'Content-Type: application/json' \
  -H 'Accept: application/json' \
  -d '{"from_extension":"1001","to_phone":"0987654321"}'

Permission scope

API Token có scope hẹp hơn user — chỉ làm được thao tác trong danh sách permission đã chọn lúc tạo.

Ví dụ scope phổ biến:

ScopeCho phép
pbx_api_accessMọi endpoint /api/pbx/*
manage_caller_idsCRUD caller ID + groups
telesales_api_accessĐọc/ghi campaign + lead Telesales
autocall_api_accessĐọc/ghi campaign + lead AutoCall
view_all_cdrXem CDR toàn tài khoản
view_team_cdrChỉ xem CDR trong team

Endpoint kiểm tra permission của token hiện tại:

GET /api/auth/me
Authorization: Bearer <token>

Response 200 trả về permissions[] array.

IP whitelist

Khi tạo token với IP whitelist:

  • Mọi request từ IP không trong list → HTTP 403 với body { "message": "Forbidden: IP not whitelisted." }.
  • IP 0.0.0.0/0 = chấp nhận mọi IP (mặc định).
  • Hỗ trợ CIDR range (vd 203.0.113.0/24).

Lưu ý load balancer

Nếu app deploy sau LB / nginx proxy — Zorio đọc IP từ header X-Forwarded-For (chuỗi client, proxy1, proxy2). LB cần cấu hình forward đúng client IP.

Audit log

Mỗi request với API Token được log với:

FieldMô tả
token_nameTên token (vd "CRM Salesforce Production")
ipIP gửi request
endpointMethod + path
statusHTTP status response
atTimestamp

Truy cập tại Admin Console → Audit Log → API Token Activity.

Rotate token

Vì lý do bảo mật, rotate token định kỳ (khuyến nghị 90 ngày 1 lần):

  1. Vào Admin Console → API Tokens → bấm Rotate bên cạnh token.
  2. Hệ thống sinh token mới — copy.
  3. Update token mới vào ứng dụng (deploy code mới với token mới).
  4. Verify ứng dụng chạy OK với token mới.
  5. Revoke token cũ sau khi confirm.

Không xoay 2 token cùng lúc

Nếu app dùng nhiều token (vd LB → N replicas), rotate từng cái một, không đồng loạt, để có rollback path khi gặp lỗi.

Revoke

Token bị compromise hoặc không còn dùng — Admin Console → API Tokens → Revoke. Mọi request với token sau khi revoke → HTTP 401.

Revoke ngay khi nghi ngờ lộ

  • Code có token vô tình commit lên git public.
  • Server có token bị hack.
  • Nhân viên có quyền tạo token rời công ty.

Revoke ngay, không chờ điều tra. Tạo token mới + deploy.

Bổ sung token vào CI/CD

ToolCách lưu token
GitHub ActionsRepository secrets → ZORIO_API_TOKEN
GitLab CICI/CD Variables (Masked + Protected)
JenkinsCredentials → Secret Text
VaultPath secret/zorio/api-token → fetch lúc deploy
K8sSecret → mount vào env var pod

KHÔNG echo token ra log build. Tool CI thường có "masked output" — bật flag này.

Sample server-to-server (cron import lead)

js
// cron-job.js — chạy mỗi 5 phút
const axios = require('axios');

const api = axios.create({
  baseURL: 'https://app.zorio.vn/api',
  headers: {
    Authorization: 'Bearer ' + process.env.ZORIO_TOKEN,
    Accept: 'application/json',
    'Content-Type': 'application/json',
  },
  timeout: 30_000,
});

async function syncLeads() {
  const crmLeads = await fetchFromCRM();
  for (const lead of crmLeads) {
    try {
      await api.post(`/telesales/campaigns/${lead.campaign_id}/leads`, {
        phone: lead.phone,
        custom_fields: lead.fields,
      });
    } catch (err) {
      if (err.response?.status === 422) {
        console.error('Lead invalid:', lead, err.response.data.errors);
      } else {
        throw err;
      }
    }
  }
}

syncLeads().catch(console.error);

Tài liệu liên quan

Cấp phép theo điều khoản sử dụng của Zorio.