379 lines
9.4 KiB
Markdown
379 lines
9.4 KiB
Markdown
# Gateway Management - Admin Interface
|
|
|
|
## Overview
|
|
|
|
The admin interface now includes complete gateway management functionality, allowing administrators to register new Android SMS gateway devices and manage existing ones.
|
|
|
|
## Features Added
|
|
|
|
### 1. Register New Gateway
|
|
|
|
**URL**: `/admin/gateways/new`
|
|
|
|
**Form Fields**:
|
|
- **Device ID** (required): Unique identifier for the gateway device
|
|
- **Gateway Name** (required): Friendly name for identification
|
|
- **Priority** (1-10): Priority level for message routing (higher priority = used first)
|
|
|
|
**Process**:
|
|
1. Admin fills out the registration form
|
|
2. System creates gateway record with status "offline"
|
|
3. System generates unique API key (format: `gw_live_...`)
|
|
4. Redirects to gateway details page showing the API key
|
|
|
|
### 2. Gateway Creation Success Page
|
|
|
|
After creating a gateway, the admin sees:
|
|
|
|
**Key Information Displayed**:
|
|
- ✅ Warning banner: "Save this API key now - you won't see it again!"
|
|
- ✅ Gateway API key in copy-to-clipboard format
|
|
- ✅ Gateway details (Device ID, Name, Priority, Status)
|
|
- ✅ Next steps instructions for configuring the Android app
|
|
|
|
**Copy to Clipboard**:
|
|
- Click button to copy API key
|
|
- Visual feedback (button turns green, shows "Copied!")
|
|
- API key displayed in terminal-style format (dark background, green text)
|
|
|
|
### 3. Gateway List Page
|
|
|
|
**URL**: `/admin/gateways`
|
|
|
|
**Features**:
|
|
- "Register New Gateway" button (top right)
|
|
- Table showing all gateways with:
|
|
- Name (clickable link to details)
|
|
- Device ID
|
|
- Status (Online/Offline with animated pulse for online)
|
|
- Active/Inactive status
|
|
- Priority level
|
|
- Today's message counts
|
|
- Total message counts
|
|
- Last heartbeat timestamp
|
|
- Created date
|
|
- Actions (View Details, Toggle Active)
|
|
|
|
### 4. Gateway Details Page (Existing Gateway)
|
|
|
|
**URL**: `/admin/gateways/:id`
|
|
|
|
**For existing gateways** (not newly created):
|
|
- Complete statistics dashboard
|
|
- Connection status indicators
|
|
- Message statistics (sent/received today and total)
|
|
- Recent messages table
|
|
- Device metadata (if available)
|
|
- Activate/Deactivate button
|
|
|
|
---
|
|
|
|
## API Key Security
|
|
|
|
### Key Generation
|
|
|
|
```ruby
|
|
# Format: gw_live_ + 64 character hex string
|
|
raw_key = "gw_live_#{SecureRandom.hex(32)}"
|
|
api_key_digest = Digest::SHA256.hexdigest(raw_key)
|
|
```
|
|
|
|
**Security Features**:
|
|
- Raw key shown only once during creation
|
|
- Stored as SHA256 hash in database
|
|
- Keys cannot be retrieved after creation
|
|
- Unique per gateway
|
|
|
|
### Session-Based Key Display
|
|
|
|
Similar to API key creation, gateway keys use session storage:
|
|
|
|
```ruby
|
|
# On create:
|
|
session[:new_gateway_id] = gateway.id
|
|
session[:new_gateway_raw_key] = raw_key
|
|
|
|
# On show:
|
|
if session[:new_gateway_id] == @gateway.id && session[:new_gateway_raw_key].present?
|
|
@raw_key = session[:new_gateway_raw_key]
|
|
@is_new = true
|
|
# Clear session immediately
|
|
session.delete(:new_gateway_id)
|
|
session.delete(:new_gateway_raw_key)
|
|
end
|
|
```
|
|
|
|
**Benefits**:
|
|
- Prevents accidental key exposure via URL
|
|
- One-time display only
|
|
- Secure redirect pattern
|
|
- No key in browser history
|
|
|
|
---
|
|
|
|
## Routes Added
|
|
|
|
```ruby
|
|
resources :gateways, only: [:index, :new, :create, :show] do
|
|
member do
|
|
post :toggle
|
|
end
|
|
end
|
|
```
|
|
|
|
**Available Routes**:
|
|
- `GET /admin/gateways` - List all gateways
|
|
- `GET /admin/gateways/new` - New gateway form
|
|
- `POST /admin/gateways` - Create gateway
|
|
- `GET /admin/gateways/:id` - View gateway details (or show new key)
|
|
- `POST /admin/gateways/:id/toggle` - Activate/deactivate gateway
|
|
|
|
---
|
|
|
|
## Controller Actions
|
|
|
|
### `new`
|
|
Renders the registration form with empty gateway object.
|
|
|
|
### `create`
|
|
```ruby
|
|
def create
|
|
@gateway = Gateway.new(
|
|
device_id: params[:gateway][:device_id],
|
|
name: params[:gateway][:name],
|
|
priority: params[:gateway][:priority] || 1,
|
|
status: "offline"
|
|
)
|
|
|
|
raw_key = @gateway.generate_api_key!
|
|
|
|
# Store in session
|
|
session[:new_gateway_id] = @gateway.id
|
|
session[:new_gateway_raw_key] = raw_key
|
|
|
|
redirect_to admin_gateway_path(@gateway)
|
|
end
|
|
```
|
|
|
|
**Error Handling**:
|
|
- Validates device_id uniqueness
|
|
- Validates required fields
|
|
- Shows error messages on form
|
|
- Logs errors for debugging
|
|
|
|
### `show`
|
|
Conditional rendering based on `@is_new`:
|
|
|
|
**If newly created**:
|
|
- Shows API key with copy button
|
|
- Shows basic gateway info
|
|
- Shows next steps instructions
|
|
- No statistics (gateway not connected yet)
|
|
|
|
**If existing gateway**:
|
|
- Shows full statistics dashboard
|
|
- Shows recent messages
|
|
- Shows device metadata
|
|
- Shows activate/deactivate controls
|
|
|
|
---
|
|
|
|
## Gateway Model
|
|
|
|
### Required Fields
|
|
```ruby
|
|
validates :device_id, presence: true, uniqueness: true
|
|
validates :api_key_digest, presence: true
|
|
validates :status, inclusion: { in: %w[online offline error] }
|
|
```
|
|
|
|
### Default Values
|
|
- `status`: "offline"
|
|
- `priority`: 1
|
|
- `active`: true
|
|
- `metadata`: {} (empty JSONB hash)
|
|
- Message counters: 0
|
|
|
|
### Methods
|
|
|
|
**`generate_api_key!`**:
|
|
```ruby
|
|
def generate_api_key!
|
|
raw_key = "gw_live_#{SecureRandom.hex(32)}"
|
|
self.api_key_digest = Digest::SHA256.hexdigest(raw_key)
|
|
save!
|
|
raw_key
|
|
end
|
|
```
|
|
|
|
**`online?`**:
|
|
Checks if gateway is truly online based on heartbeat:
|
|
```ruby
|
|
def online?
|
|
status == "online" && last_heartbeat_at.present? && last_heartbeat_at > 2.minutes.ago
|
|
end
|
|
```
|
|
|
|
---
|
|
|
|
## View Files Created/Modified
|
|
|
|
### New Files
|
|
- `app/views/admin/gateways/new.html.erb` - Registration form
|
|
|
|
### Modified Files
|
|
- `app/views/admin/gateways/index.html.erb` - Added "Register New Gateway" button
|
|
- `app/views/admin/gateways/show.html.erb` - Added conditional for new gateway display
|
|
|
|
---
|
|
|
|
## Usage Flow
|
|
|
|
### Registering a New Gateway
|
|
|
|
1. **Navigate to Gateways**
|
|
- Click "Gateways" in sidebar
|
|
- See list of existing gateways (if any)
|
|
|
|
2. **Start Registration**
|
|
- Click "Register New Gateway" button (top right)
|
|
- Form appears with 3 fields
|
|
|
|
3. **Fill Form**
|
|
- Device ID: `phone-samsung-001`
|
|
- Gateway Name: `Office Android Phone`
|
|
- Priority: `5` (1-10 scale)
|
|
|
|
4. **Submit**
|
|
- Click "Register Gateway" button
|
|
- System creates gateway and generates API key
|
|
|
|
5. **Save API Key**
|
|
- Warning shown: "Save this key now!"
|
|
- API key displayed: `gw_live_a6e2b250dade...`
|
|
- Click "Copy to Clipboard" button
|
|
- Key copied to clipboard
|
|
|
|
6. **Configure Android App**
|
|
- Follow "Next Steps" instructions
|
|
- Install Android SMS Gateway app
|
|
- Paste API key in app settings
|
|
- Start gateway service
|
|
|
|
7. **Verify Connection**
|
|
- Gateway appears "Offline" initially
|
|
- Once Android app connects, status changes to "Online"
|
|
- View gateway details to see statistics
|
|
|
|
---
|
|
|
|
## Next Steps Instructions (Shown on Success Page)
|
|
|
|
1. Copy the API key above using the "Copy to Clipboard" button
|
|
2. Install the Android SMS Gateway app on your device
|
|
3. Open the app and navigate to Settings
|
|
4. Paste the API key in the app's configuration
|
|
5. Save the configuration and start the gateway service
|
|
6. The gateway will appear as "Online" once it connects successfully
|
|
|
|
---
|
|
|
|
## Testing
|
|
|
|
### Console Test
|
|
```bash
|
|
bin/rails console
|
|
```
|
|
|
|
```ruby
|
|
# Create gateway
|
|
gateway = Gateway.new(
|
|
device_id: "test-001",
|
|
name: "Test Gateway",
|
|
priority: 3,
|
|
status: "offline"
|
|
)
|
|
|
|
# Generate API key
|
|
raw_key = gateway.generate_api_key!
|
|
puts "API Key: #{raw_key}"
|
|
|
|
# Verify
|
|
gateway.reload
|
|
puts "Gateway ID: #{gateway.id}"
|
|
puts "Device ID: #{gateway.device_id}"
|
|
puts "Key Digest: #{gateway.api_key_digest}"
|
|
```
|
|
|
|
### Browser Test
|
|
1. Start server: `bin/dev`
|
|
2. Visit: `http://localhost:3000/admin/login`
|
|
3. Login with admin credentials
|
|
4. Click "Gateways" in sidebar
|
|
5. Click "Register New Gateway"
|
|
6. Fill form and submit
|
|
7. Verify API key is displayed
|
|
8. Verify copy to clipboard works
|
|
9. Click "Back to Gateways"
|
|
10. Verify new gateway appears in list
|
|
|
|
---
|
|
|
|
## Integration with Android App
|
|
|
|
The gateway API key is used by the Android app to:
|
|
|
|
1. **Authenticate WebSocket Connection**
|
|
- Connect to: `ws://your-server.com/cable?api_key=gw_live_...`
|
|
- Connection class authenticates via `api_key_digest`
|
|
|
|
2. **Send Heartbeats**
|
|
- POST `/api/v1/gateway/heartbeat`
|
|
- Header: `Authorization: Bearer gw_live_...`
|
|
- Keeps gateway status "online"
|
|
|
|
3. **Report Received SMS**
|
|
- POST `/api/v1/gateway/sms/received`
|
|
- Header: `Authorization: Bearer gw_live_...`
|
|
- Sends inbound SMS to system
|
|
|
|
4. **Report Delivery Status**
|
|
- POST `/api/v1/gateway/sms/status`
|
|
- Header: `Authorization: Bearer gw_live_...`
|
|
- Updates message delivery status
|
|
|
|
---
|
|
|
|
## Security Considerations
|
|
|
|
### Production Checklist
|
|
- ✅ API keys are SHA256 hashed before storage
|
|
- ✅ Raw keys shown only once during creation
|
|
- ✅ Keys transmitted via session (not URL)
|
|
- ✅ Device ID uniqueness enforced
|
|
- ✅ CSRF protection enabled on all forms
|
|
- ⚠️ Ensure HTTPS in production (`config.force_ssl = true`)
|
|
- ⚠️ Secure WebSocket connections (wss://)
|
|
- ⚠️ Implement rate limiting on registration endpoint
|
|
|
|
### Recommended Practices
|
|
- Regularly audit gateway list
|
|
- Deactivate unused gateways
|
|
- Monitor heartbeat timestamps
|
|
- Alert on prolonged offline status
|
|
- Rotate keys if device is compromised
|
|
- Keep device firmware updated
|
|
|
|
---
|
|
|
|
## Summary
|
|
|
|
✅ **Complete Gateway Management**: Register, view, and manage SMS gateway devices
|
|
✅ **Secure API Key Generation**: One-time display with copy-to-clipboard
|
|
✅ **Professional UI**: Tailwind CSS styling with clear instructions
|
|
✅ **Session-Based Security**: Keys not exposed in URLs or browser history
|
|
✅ **Integration Ready**: Works with Android SMS Gateway app
|
|
✅ **Admin Controls**: Activate/deactivate, view statistics, monitor status
|
|
|
|
The admin interface now provides everything needed to manage SMS gateway devices from registration to monitoring!
|