Discord Bot API
The Discord Bot API powers the MyNATCA Discord integration, handling member verification, role management, and real-time Discord operations. This API enables seamless integration between NATCA membership data and Discord community features.
Base URLs
Production: https://discord.mynatca.org/api
Staging: https://discord-staging.natca.org/api
Development: http://localhost:3003/apiAuthentication
Service Authentication
# Service-to-service authentication for Discord operations
curl -H "Authorization: Bearer <service_token>" \
https://discord.mynatca.org/api/members/123456User Authentication
# User authentication with Auth0 JWT for verification
curl -H "Authorization: Bearer <auth0_jwt_token>" \
https://discord.mynatca.org/api/verify/complete/abc123Webhook Authentication
# Webhook authentication for event notifications
curl -H "X-Webhook-Secret: <webhook_secret>" \
-X POST https://discord.mynatca.org/api/webhooks/member-updateVerification Endpoints
Start Verification Flow
Initiate the Discord account verification process for a NATCA member.
POST /api/verify/start
Content-Type: application/json
{
"discord_id": "123456789012345678",
"discord_username": "username#1234",
"member_number": "123456"
}Response (200 OK):
{
"success": true,
"verification_id": "550e8400-e29b-41d4-a716-446655440000",
"verification_url": "https://discord.mynatca.org/verify/550e8400-e29b-41d4-a716-446655440000",
"expires_at": "2023-01-01T01:30:00.000Z"
}Response (400 Bad Request):
{
"success": false,
"error": "MEMBER_NOT_FOUND",
"message": "Member number 123456 not found or inactive"
}Get Verification Status
Check the current status of a verification process.
GET /api/verify/status/{verification_id}Response (200 OK):
{
"success": true,
"verification": {
"id": "550e8400-e29b-41d4-a716-446655440000",
"status": "pending",
"discord_id": "123456789012345678",
"discord_username": "username#1234",
"member_number": "123456",
"created_at": "2023-01-01T01:00:00.000Z",
"expires_at": "2023-01-01T01:30:00.000Z"
}
}Complete Verification
Complete the verification process by linking Auth0 account.
POST /api/verify/complete/{verification_id}
Content-Type: application/json
Authorization: Bearer <auth0_jwt_token>
{
"auth0_user_id": "auth0|64a1b2c3d4e5f6789012"
}Response (200 OK):
{
"success": true,
"member": {
"member_number": "123456",
"first_name": "John",
"last_name": "Doe",
"facility_code": "ZTL",
"region_code": "ASO",
"positions": [
{
"position_type": "facrep",
"facility_code": "ZTL"
}
]
},
"discord_roles_assigned": ["NATCA Member", "FacRep"]
}Member Management Endpoints
Get Member Information
Retrieve member information for Discord integration.
GET /api/members/{member_number}
Authorization: Bearer <auth0_jwt_token>Response (200 OK):
{
"success": true,
"member": {
"member_number": "123456",
"first_name": "John",
"last_name": "Doe",
"email": "john.doe@example.com",
"facility_code": "ZTL",
"facility_name": "Atlanta TRACON",
"region_code": "ASO",
"region_name": "Air Safety Organization",
"member_type_id": 6,
"member_type": "Current Member",
"discord_id": "123456789012345678",
"discord_username": "username#1234",
"auth0_user_id": "auth0|64a1b2c3d4e5f6789012",
"verified_at": "2023-01-01T01:00:00.000Z",
"created_at": "2023-01-01T00:00:00.000Z",
"updated_at": "2023-01-01T01:00:00.000Z"
}
}Update Member Discord Link
Update Discord account information for a member.
PUT /api/members/{member_number}/discord
Content-Type: application/json
Authorization: Bearer <service_token>
{
"discord_id": "123456789012345678",
"discord_username": "username#1234"
}Response (200 OK):
{
"success": true,
"message": "Discord link updated successfully"
}Get Member Positions
Retrieve member positions for role assignment.
GET /api/members/{member_number}/positions
Authorization: Bearer <auth0_jwt_token>Response (200 OK):
{
"success": true,
"positions": [
{
"id": 1,
"position_type": "facrep",
"facility_code": "ZTL",
"facility_name": "Atlanta TRACON",
"start_date": "2023-01-01",
"end_date": null,
"active": true
}
]
}Discord Integration Endpoints
Assign Discord Roles
Assign Discord roles based on member data and positions.
POST /api/discord/roles/assign
Content-Type: application/json
Authorization: Bearer <service_token>
{
"discord_id": "123456789012345678",
"member_number": "123456"
}Response (200 OK):
{
"success": true,
"roles_assigned": ["NATCA Member", "FacRep"],
"nickname_set": "John Doe"
}Refresh Discord Roles
Update Discord roles based on current member data.
POST /api/discord/roles/refresh
Content-Type: application/json
Authorization: Bearer <service_token>
{
"discord_id": "123456789012345678"
}Response (200 OK):
{
"success": true,
"roles_added": ["Committee Member"],
"roles_removed": ["FacRep"],
"nickname_updated": true
}Administrative Endpoints
Manual Verification
Manually verify a member (admin only).
POST /api/admin/verify/manual
Content-Type: application/json
Authorization: Bearer <admin_jwt_token>
{
"member_number": "123456",
"discord_id": "123456789012345678",
"admin_user_id": "auth0|admin123"
}Response (200 OK):
{
"success": true,
"verification_completed": true,
"auth0_user_created": true,
"discord_roles_assigned": ["NATCA Member", "FacRep"]
}Get Verification Statistics
Administrative statistics for verification processes.
GET /api/admin/stats/verification
Authorization: Bearer <admin_jwt_token>Response (200 OK):
{
"success": true,
"stats": {
"total_members": 5000,
"verified_members": 3500,
"pending_verifications": 25,
"verification_rate": 0.70,
"daily_verifications": 15,
"weekly_verifications": 105
}
}Webhook Endpoints
Member Update Webhook
Receive notifications when member data is updated.
POST /api/webhooks/member-update
Content-Type: application/json
X-Webhook-Secret: <webhook_secret>
{
"event": "member.updated",
"timestamp": "2023-01-01T12:00:00.000Z",
"data": {
"member_number": "123456",
"discord_id": "123456789012345678",
"facility_code": "ZTL",
"first_name": "John",
"last_name": "Doe",
"positions": [
{
"position_type": "facrep",
"facility_code": "ZTL"
}
]
}
}Response (200 OK):
{
"success": true,
"processed": true,
"roles_updated": true
}Role Assignment Webhook
Trigger role assignment for a Discord user.
POST /api/webhooks/assign-roles
Content-Type: application/json
X-Webhook-Secret: <webhook_secret>
{
"discord_id": "123456789012345678",
"member_number": "123456"
}Rate Limiting
Current Limits
- Discord Bot API: 100 requests/minute per service
- User verification: 10 requests/minute per user
- Administrative operations: 500 requests/minute per admin
Response Headers
X-RateLimit-Limit: 100
X-RateLimit-Remaining: 87
X-RateLimit-Reset: 1640995200
X-RateLimit-Window: 60Error Handling
Standard Error Format
{
"success": false,
"error": "DISCORD_USER_NOT_FOUND",
"message": "Discord user ID 123456789012345678 not found in server",
"details": {
"discord_id": "123456789012345678",
"server_id": "987654321098765432",
"suggestion": "Ensure user has joined the Discord server"
},
"timestamp": "2023-01-01T12:00:00.000Z",
"request_id": "req_550e8400-e29b-41d4"
}Common Error Codes
Verification Errors
- MEMBER_NOT_FOUND - NATCA member number not found
- DISCORD_USER_NOT_FOUND - Discord user not found in server
- VERIFICATION_EXPIRED - Verification link has expired
- ALREADY_VERIFIED - Member is already verified
Discord Errors
- ROLE_ASSIGNMENT_FAILED - Unable to assign Discord roles
- NICKNAME_UPDATE_FAILED - Unable to update Discord nickname
- INSUFFICIENT_PERMISSIONS - Bot lacks required Discord permissions
- SERVER_UNAVAILABLE - Discord server is temporarily unavailable
Authentication Errors
- INVALID_TOKEN - JWT token is invalid or expired
- MISSING_PERMISSIONS - User lacks required permissions
- WEBHOOK_SIGNATURE_INVALID - Webhook signature verification failed
Implementation Examples
Bot Command Integration
// Discord bot command for starting verification
client.on('interactionCreate', async interaction => {
if (interaction.commandName === 'register') {
const memberNumber = interaction.options.getString('member_number');
const response = await fetch('https://discord.mynatca.org/api/verify/start', {
method: 'POST',
headers: {
'Authorization': `Bearer ${process.env.SERVICE_TOKEN}`,
'Content-Type': 'application/json'
},
body: JSON.stringify({
discord_id: interaction.user.id,
discord_username: interaction.user.tag,
member_number: memberNumber
})
});
const result = await response.json();
if (result.success) {
await interaction.reply({
content: `Verification started! Please visit: ${result.verification_url}`,
ephemeral: true
});
} else {
await interaction.reply({
content: `Verification failed: ${result.message}`,
ephemeral: true
});
}
}
});Webhook Handler
// Express webhook handler for member updates
app.post('/api/webhooks/member-update', express.json(), async (req, res) => {
const signature = req.headers['x-webhook-secret'];
// Verify webhook signature
if (!verifyWebhookSignature(req.body, signature, process.env.WEBHOOK_SECRET)) {
return res.status(401).json({ error: 'Invalid signature' });
}
const { event, data } = req.body;
try {
if (event === 'member.updated') {
await webhookHandler.handleMemberUpdate(data);
}
res.json({ success: true, processed: true });
} catch (error) {
console.error('Webhook processing error:', error);
res.status(500).json({ error: 'Processing failed' });
}
});Role Management
// Update member roles based on position changes
async function updateMemberRoles(memberId, positions) {
const response = await fetch('https://discord.mynatca.org/api/discord/roles/refresh', {
method: 'POST',
headers: {
'Authorization': `Bearer ${process.env.SERVICE_TOKEN}`,
'Content-Type': 'application/json'
},
body: JSON.stringify({
discord_id: memberId
})
});
const result = await response.json();
if (result.success) {
console.log('Roles updated:', result.roles_added, result.roles_removed);
} else {
console.error('Role update failed:', result.message);
}
}Best Practices
Verification Flow
- Validate member numbers before starting verification
- Handle expired verifications gracefully
- Provide clear error messages to users
- Log verification attempts for audit purposes
Role Management
- Batch role updates when possible to reduce API calls
- Handle Discord permission errors appropriately
- Sync roles regularly to maintain consistency
- Monitor role assignment failures and alert administrators
Webhook Security
- Always verify webhook signatures to ensure authenticity
- Implement idempotency for webhook processing
- Handle webhook delivery failures with retry logic
- Monitor webhook health and delivery success rates
Error Handling
- Implement exponential backoff for rate-limited requests
- Cache member data to reduce duplicate API calls
- Handle Discord API outages gracefully
- Provide meaningful error messages to end users
The Discord Bot API enables seamless integration between NATCA membership and Discord community features, providing automated verification and role management for thousands of members.