Complete Implementation Guide
Step-by-step walkthrough for implementing the complete BigCity Rewards API integration, from initial setup to voucher redemption.
Table of Contents
Prerequisites
Required Information
- Company secret key for authentication
- BigCity API base URL:
https://api.bigcity.in/v1 - Customer data (mobile number, name, email)
- Order/purchase data with SKUs
Development Environment
- HTTPS capability for secure API calls
- JSON parsing libraries
- HTTP client (curl, axios, requests, etc.)
- Error handling framework
- Logging capability
Implementation Steps
Company Authentication
POST /v1/company/authPurpose: Authenticate your company to access the BigCity rewards platform.
Test Command
curl -X POST https://api.bigcity.in/v1/company/auth \
-H "Authorization: Required" \
-H "Content-Type: application/json" \
-d '{"secret": "your_company_secret_key"}'
Expected Response
{
"vendor_id": 1,
"vendor_name": "YourCompany",
"auth_token": "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9...",
"token_expiry": "2025-10-14 13:47:16",
"state": "Active"
}
Get Available Rewards
GET /v1/bigcity/rewardsPurpose: Retrieve the list of available rewards and denominations.
Test Command
curl -X GET https://api.bigcity.in/v1/bigcity/rewards \
-H "Authorization: Bearer YOUR_COMPANY_TOKEN"
Expected Response
[
{
"id": 1,
"denomination_value": "10",
"status": 1,
"qty": "0",
"skus": "Product-SKU\tVariant-Info"
}
]
Customer Authentication
POST /v1/customer/authPurpose: Authenticate individual customers to enable order creation.
Test Command
curl -X POST https://api.bigcity.in/v1/customer/auth \
-H "Authorization: Bearer YOUR_COMPANY_TOKEN" \
-H "Content-Type: application/json" \
-d '{
"customer_name": "John Doe",
"customer_mobile": "1234567890",
"customer_email": "john@example.com"
}'
Expected Response
{
"customer_id": 1,
"customer_token": "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9...",
"token_expiry": "2025-10-14 14:31:35"
}
Create Redemption Order
POST /v1/bigcity/redeemptiononskusPurpose: Process customer purchases and generate reward vouchers.
Test Command
curl -X POST https://api.bigcity.in/v1/bigcity/redeemptiononskus \
-H "Authorization: Bearer YOUR_CUSTOMER_TOKEN" \
-H "Content-Type: application/json" \
-d '{
"order_timestamp": "2025-10-13T15:42:36-04:00",
"order_total": 1500,
"order_items": 3,
"line_items": [
{
"order_id": "ORD-001234",
"SKU": "SKU1",
"qty": 1
}
]
}'
Expected Response
{
"id": 45654654654,
"order_id": "ORD-001234",
"state": "success",
"vouchers": [
{
"voucher_code": "BCP123456",
"pin": "1234",
"validity": "2024-03-26"
}
],
"redemption_url": "https://bigcity.in/redeem"
}
Complete Code Examples
#!/usr/bin/env python3
"""
BigCity Rewards API - Complete Implementation Example
"""
import requests
import json
from datetime import datetime, timezone
from typing import Dict, List, Optional
import logging
# Configure logging
logging.basicConfig(level=logging.INFO)
logger = logging.getLogger(__name__)
class BigCityRewardsAPI:
def __init__(self, company_secret: str):
self.base_url = "https://api.bigcity.in/v1"
self.company_secret = company_secret
self.company_token = None
self.session = requests.Session()
self.session.timeout = 30
def authenticate_company(self) -> str:
"""Step 1: Authenticate company and get company token"""
logger.info("๐ข Authenticating company...")
response = self.session.post(
f"{self.base_url}/company/auth",
headers={
"Authorization": "Required",
"Content-Type": "application/json"
},
json={"secret": self.company_secret}
)
if response.status_code == 200:
auth_data = response.json()
self.company_token = auth_data["auth_token"]
logger.info(f"โ
Company authenticated successfully. Vendor ID: {auth_data['vendor_id']}")
return self.company_token
else:
error_msg = f"Company authentication failed: {response.text}"
logger.error(error_msg)
raise Exception(error_msg)
def get_rewards(self) -> List[Dict]:
"""Step 2: Get available rewards"""
if not self.company_token:
raise Exception("Company not authenticated. Call authenticate_company() first.")
logger.info("๐ Fetching available rewards...")
response = self.session.get(
f"{self.base_url}/bigcity/rewards",
headers={
"Authorization": f"Bearer {self.company_token}",
"Content-Type": "application/json"
}
)
if response.status_code == 200:
rewards = response.json()
active_rewards = [r for r in rewards if r['status'] == 1]
logger.info(f"โ
Found {len(active_rewards)} active rewards out of {len(rewards)} total")
return rewards
else:
error_msg = f"Failed to get rewards: {response.text}"
logger.error(error_msg)
raise Exception(error_msg)
def authenticate_customer(self, customer_data: Dict) -> str:
"""Step 3: Authenticate customer and get customer token"""
if not self.company_token:
raise Exception("Company not authenticated. Call authenticate_company() first.")
logger.info(f"๐ค Authenticating customer: {customer_data.get('customer_name', 'Unknown')}")
response = self.session.post(
f"{self.base_url}/customer/auth",
headers={
"Authorization": f"Bearer {self.company_token}",
"Content-Type": "application/json"
},
json=customer_data
)
if response.status_code == 200:
auth_data = response.json()
logger.info(f"โ
Customer authenticated. Customer ID: {auth_data['customer_id']}")
return auth_data["customer_token"]
else:
error_msg = f"Customer authentication failed: {response.text}"
logger.error(error_msg)
raise Exception(error_msg)
def create_redemption_order(self, customer_token: str, order_data: Dict) -> Dict:
"""Step 4: Create redemption order and generate vouchers"""
logger.info(f"๐ฆ Creating redemption order: {order_data['line_items'][0]['order_id']}")
response = self.session.post(
f"{self.base_url}/bigcity/redeemptiononskus",
headers={
"Authorization": f"Bearer {customer_token}",
"Content-Type": "application/json"
},
json=order_data
)
if response.status_code == 200:
result = response.json()
logger.info(f"โ
Order created successfully. Generated {len(result.get('vouchers', []))} vouchers")
return result
else:
error_msg = f"Order creation failed: {response.text}"
logger.error(error_msg)
raise Exception(error_msg)
def complete_rewards_workflow(company_secret: str, customer_data: Dict, cart_items: List[Dict]) -> Dict:
"""
Complete end-to-end rewards workflow
Args:
company_secret: Company authentication secret
customer_data: Customer information (name, mobile, email)
cart_items: List of purchased items with SKU and quantity
Returns:
Dict containing vouchers and redemption information
"""
try:
# Initialize API client
api = BigCityRewardsAPI(company_secret)
# Step 1: Company Authentication
company_token = api.authenticate_company()
# Step 2: Get Available Rewards (for reference/validation)
rewards = api.get_rewards()
logger.info(f"๐ Available reward denominations: {[r['denomination_value'] for r in rewards if r['status'] == 1]}")
# Step 3: Customer Authentication
customer_token = api.authenticate_customer(customer_data)
# Step 4: Prepare Order Data
order_total = sum(item['price'] * item['quantity'] for item in cart_items)
order_id = f"ORD-{datetime.now().strftime('%Y%m%d')}-{hash(str(cart_items)) % 100000:05d}"
order_data = {
"order_timestamp": datetime.now(timezone.utc).isoformat(),
"order_total": order_total,
"order_items": len(cart_items),
"line_items": [
{
"order_id": order_id,
"SKU": item['sku'],
"qty": item['quantity']
}
for item in cart_items
]
}
# Step 5: Create Redemption Order
result = api.create_redemption_order(customer_token, order_data)
return {
'success': True,
'order_id': order_id,
'redemption_result': result,
'customer_data': customer_data,
'order_summary': {
'total_amount': order_total,
'items_count': len(cart_items),
'vouchers_generated': len(result.get('vouchers', []))
}
}
except Exception as e:
logger.error(f"โ Workflow failed: {e}")
return {
'success': False,
'error': str(e),
'step_failed': 'See logs for details'
}
# Example Usage
def main():
# Configuration
COMPANY_SECRET = "your_company_secret_here"
# Customer information
customer_data = {
"customer_name": "Alice Johnson",
"customer_mobile": "9876543210",
"customer_email": "alice@example.com"
}
# Shopping cart (example purchase)
cart_items = [
{'sku': 'NUTRI-SEEDS-1200', 'quantity': 2, 'price': 25.00},
{'sku': 'NUTRI-OATS-MULTI', 'quantity': 1, 'price': 15.00},
{'sku': 'NUTRI-HERBS-800', 'quantity': 1, 'price': 30.00}
]
# Execute complete workflow
result = complete_rewards_workflow(COMPANY_SECRET, customer_data, cart_items)
if result['success']:
print("๐ Rewards processing completed successfully!")
print(f"\n๐ Order Summary:")
print(f" Order ID: {result['order_id']}")
print(f" Customer: {customer_data['customer_name']}")
print(f" Total Amount: ${result['order_summary']['total_amount']:.2f}")
print(f" Items: {result['order_summary']['items_count']}")
print(f" Vouchers Generated: {result['order_summary']['vouchers_generated']}")
# Display vouchers
vouchers = result['redemption_result']['vouchers']
print(f"\n๐ซ Generated Vouchers:")
for i, voucher in enumerate(vouchers, 1):
print(f" Voucher {i}:")
print(f" Code: {voucher['voucher_code']}")
print(f" PIN: {voucher.get('pin', 'N/A')}")
print(f" Valid until: {voucher['validity']}")
print(f"\n๐ Redemption URL: {result['redemption_result']['redemption_url']}")
else:
print("โ Rewards processing failed!")
print(f"Error: {result['error']}")
if __name__ == "__main__":
main()
const axios = require('axios');
class BigCityRewardsWorkflow {
constructor(companySecret) {
this.baseUrl = 'https://api.bigcity.in/v1';
this.companySecret = companySecret;
this.companyToken = null;
// Configure axios defaults
this.client = axios.create({
timeout: 30000,
headers: {
'Content-Type': 'application/json'
}
});
}
async authenticateCompany() {
console.log('๐ข Authenticating company...');
try {
const response = await this.client.post(`${this.baseUrl}/company/auth`,
{ secret: this.companySecret },
{
headers: { 'Authorization': 'Required' }
}
);
this.companyToken = response.data.auth_token;
console.log(`โ
Company authenticated. Vendor: ${response.data.vendor_name}`);
return this.companyToken;
} catch (error) {
console.error('โ Company authentication failed:', error.response?.data || error.message);
throw error;
}
}
async getRewards() {
if (!this.companyToken) {
throw new Error('Company not authenticated');
}
console.log('๐ Fetching available rewards...');
try {
const response = await this.client.get(`${this.baseUrl}/bigcity/rewards`, {
headers: { 'Authorization': `Bearer ${this.companyToken}` }
});
const activeRewards = response.data.filter(r => r.status === 1);
console.log(`โ
Found ${activeRewards.length} active rewards`);
return response.data;
} catch (error) {
console.error('โ Failed to get rewards:', error.response?.data || error.message);
throw error;
}
}
async authenticateCustomer(customerData) {
if (!this.companyToken) {
throw new Error('Company not authenticated');
}
console.log(`๐ค Authenticating customer: ${customerData.customer_name}`);
try {
const response = await this.client.post(`${this.baseUrl}/customer/auth`,
customerData,
{
headers: { 'Authorization': `Bearer ${this.companyToken}` }
}
);
console.log(`โ
Customer authenticated. ID: ${response.data.customer_id}`);
return response.data.customer_token;
} catch (error) {
console.error('โ Customer authentication failed:', error.response?.data || error.message);
throw error;
}
}
async createRedemptionOrder(customerToken, orderData) {
console.log(`๐ฆ Creating redemption order: ${orderData.line_items[0].order_id}`);
try {
const response = await this.client.post(`${this.baseUrl}/bigcity/redeemptiononskus`,
orderData,
{
headers: { 'Authorization': `Bearer ${customerToken}` }
}
);
const result = response.data;
console.log(`โ
Order created. State: ${result.state}, Vouchers: ${result.vouchers?.length || 0}`);
return result;
} catch (error) {
console.error('โ Order creation failed:', error.response?.data || error.message);
throw error;
}
}
generateOrderId() {
const timestamp = new Date().toISOString().slice(0, 10).replace(/-/g, '');
const random = Math.random().toString(36).substr(2, 8).toUpperCase();
return `ORD-${timestamp}-${random}`;
}
async processCompleteWorkflow(customerData, cartItems) {
try {
// Step 1: Company Authentication
await this.authenticateCompany();
// Step 2: Get Rewards (optional, for validation)
const rewards = await this.getRewards();
// Step 3: Customer Authentication
const customerToken = await this.authenticateCustomer(customerData);
// Step 4: Prepare Order Data
const orderId = this.generateOrderId();
const orderTotal = cartItems.reduce((total, item) =>
total + (item.price * item.quantity), 0
);
const orderData = {
order_timestamp: new Date().toISOString(),
order_total: orderTotal,
order_items: cartItems.length,
line_items: cartItems.map(item => ({
order_id: orderId,
SKU: item.sku,
qty: item.quantity
}))
};
// Step 5: Create Redemption Order
const redemptionResult = await this.createRedemptionOrder(customerToken, orderData);
return {
success: true,
orderId,
customer: customerData,
orderSummary: {
totalAmount: orderTotal,
itemsCount: cartItems.length,
vouchersGenerated: redemptionResult.vouchers?.length || 0
},
vouchers: redemptionResult.vouchers,
redemptionUrl: redemptionResult.redemption_url,
howToAvail: redemptionResult.how_to_avail,
terms: redemptionResult.terms
};
} catch (error) {
return {
success: false,
error: error.message,
timestamp: new Date().toISOString()
};
}
}
}
// Usage Example
async function runExample() {
const api = new BigCityRewardsWorkflow('your_company_secret_here');
const customerData = {
customer_name: "Bob Wilson",
customer_mobile: "5551234567",
customer_email: "bob@example.com"
};
const cartItems = [
{ sku: 'NUTRI-SEEDS-1200', quantity: 1, price: 25.00 },
{ sku: 'NUTRI-OATS-MULTI', quantity: 2, price: 15.00 }
];
const result = await api.processCompleteWorkflow(customerData, cartItems);
if (result.success) {
console.log('\n๐ Workflow completed successfully!');
console.log(`Order ID: ${result.orderId}`);
console.log(`Customer: ${result.customer.customer_name}`);
console.log(`Total: $${result.orderSummary.totalAmount}`);
console.log(`Vouchers: ${result.orderSummary.vouchersGenerated}`);
if (result.vouchers && result.vouchers.length > 0) {
console.log('\n๐ซ Voucher Details:');
result.vouchers.forEach((voucher, index) => {
console.log(` ${index + 1}. Code: ${voucher.voucher_code}`);
console.log(` PIN: ${voucher.pin || 'N/A'}`);
console.log(` Valid until: ${voucher.validity}`);
});
}
console.log(`\n๐ Redeem at: ${result.redemptionUrl}`);
} else {
console.error('\nโ Workflow failed:', result.error);
}
}
// Run the example
runExample().catch(console.error);
companySecret = $companySecret;
}
public function authenticateCompany() {
echo "๐ข Authenticating company...\n";
$curl = curl_init();
curl_setopt_array($curl, [
CURLOPT_URL => $this->baseUrl . '/company/auth',
CURLOPT_RETURNTRANSFER => true,
CURLOPT_POST => true,
CURLOPT_HTTPHEADER => [
'Authorization: Required',
'Content-Type: application/json'
],
CURLOPT_POSTFIELDS => json_encode(['secret' => $this->companySecret]),
CURLOPT_TIMEOUT => 30
]);
$response = curl_exec($curl);
$httpCode = curl_getinfo($curl, CURLINFO_HTTP_CODE);
curl_close($curl);
if ($httpCode === 200) {
$authData = json_decode($response, true);
$this->companyToken = $authData['auth_token'];
echo "โ
Company authenticated. Vendor: {$authData['vendor_name']}\n";
return $this->companyToken;
} else {
throw new Exception("Company authentication failed: $response");
}
}
public function processCompleteWorkflow($customerData, $cartItems) {
try {
// Step 1: Company Authentication
$companyToken = $this->authenticateCompany();
// Step 2: Get Rewards
$rewards = $this->getRewards();
// Step 3: Customer Authentication
$customerToken = $this->authenticateCustomer($customerData);
// Step 4: Prepare Order Data
$orderTotal = array_sum(array_map(fn($item) => $item['price'] * $item['quantity'], $cartItems));
$orderId = 'ORD-' . date('Ymd') . '-' . strtoupper(substr(uniqid(), -8));
$orderData = [
'order_timestamp' => date('c'), // ISO 8601
'order_total' => $orderTotal,
'order_items' => count($cartItems),
'line_items' => array_map(fn($item) => [
'order_id' => $orderId,
'SKU' => $item['sku'],
'qty' => $item['quantity']
], $cartItems)
];
// Step 5: Create Redemption Order
$result = $this->createRedemptionOrder($customerToken, $orderData);
return [
'success' => true,
'order_id' => $orderId,
'redemption_result' => $result,
'customer_data' => $customerData,
'order_summary' => [
'total_amount' => $orderTotal,
'items_count' => count($cartItems),
'vouchers_generated' => count($result['vouchers'] ?? [])
]
];
} catch (Exception $e) {
echo "โ Workflow failed: " . $e->getMessage() . "\n";
return [
'success' => false,
'error' => $e->getMessage()
];
}
}
}
Testing Guide
Unit Testing Example
import unittest
from unittest.mock import patch, Mock
class TestBigCityWorkflow(unittest.TestCase):
def setUp(self):
self.api = BigCityRewardsAPI('test_secret')
@patch('requests.Session.post')
def test_company_authentication_success(self, mock_post):
# Mock successful response
mock_response = Mock()
mock_response.status_code = 200
mock_response.json.return_value = {
'vendor_id': 1,
'auth_token': 'test_token',
'vendor_name': 'Test Company'
}
mock_post.return_value = mock_response
token = self.api.authenticate_company()
self.assertEqual(token, 'test_token')
self.assertEqual(self.api.company_token, 'test_token')
@patch('requests.Session.post')
def test_company_authentication_failure(self, mock_post):
# Mock failed response
mock_response = Mock()
mock_response.status_code = 400
mock_response.text = 'Invalid secret'
mock_post.return_value = mock_response
with self.assertRaises(Exception):
self.api.authenticate_company()
if __name__ == '__main__':
unittest.main()
Integration Test Script
#!/bin/bash
# Integration test script
set -e
echo "๐งช Running BigCity API Integration Tests"
# Test 1: Company Authentication
echo "Test 1: Company Authentication"
COMPANY_RESPONSE=$(curl -s -X POST https://api.bigcity.in/v1/company/auth \
-H "Authorization: Required" \
-H "Content-Type: application/json" \
-d '{"secret": "test_secret"}')
COMPANY_TOKEN=$(echo $COMPANY_RESPONSE | jq -r '.auth_token')
echo "Company Token: ${COMPANY_TOKEN:0:20}..."
# Test 2: Rewards List
echo "Test 2: Get Rewards"
REWARDS_RESPONSE=$(curl -s -X GET https://api.bigcity.in/v1/bigcity/rewards \
-H "Authorization: Bearer $COMPANY_TOKEN")
REWARDS_COUNT=$(echo $REWARDS_RESPONSE | jq '. | length')
echo "Available Rewards: $REWARDS_COUNT"
# Test 3: Customer Authentication
echo "Test 3: Customer Authentication"
CUSTOMER_RESPONSE=$(curl -s -X POST https://api.bigcity.in/v1/customer/auth \
-H "Authorization: Bearer $COMPANY_TOKEN" \
-H "Content-Type: application/json" \
-d '{
"customer_name": "Test Customer",
"customer_mobile": "1234567890",
"customer_email": "test@example.com"
}')
CUSTOMER_TOKEN=$(echo $CUSTOMER_RESPONSE | jq -r '.customer_token')
echo "Customer Token: ${CUSTOMER_TOKEN:0:20}..."
# Test 4: Create Order
echo "Test 4: Create Redemption Order"
ORDER_RESPONSE=$(curl -s -X POST https://api.bigcity.in/v1/bigcity/redeemptiononskus \
-H "Authorization: Bearer $CUSTOMER_TOKEN" \
-H "Content-Type: application/json" \
-d '{
"order_timestamp": "'$(date -u +%Y-%m-%dT%H:%M:%S-00:00)'",
"order_total": 100,
"order_items": 1,
"line_items": [
{
"order_id": "TEST-'$(date +%s)'",
"SKU": "TEST-SKU",
"qty": 1
}
]
}')
ORDER_STATE=$(echo $ORDER_RESPONSE | jq -r '.state')
VOUCHER_COUNT=$(echo $ORDER_RESPONSE | jq '.vouchers | length')
echo "Order State: $ORDER_STATE"
echo "Vouchers Generated: $VOUCHER_COUNT"
echo "โ
All tests completed successfully!"
Health Check Implementation
def health_check():
"""Check if BigCity API is accessible"""
try:
response = requests.get("https://api.bigcity.in/health", timeout=5)
return response.status_code == 200
except:
return False
if not health_check():
print("โ ๏ธ BigCity API is not accessible")
Production Checklist
Security Requirements
- Company secrets stored securely (environment variables)
- HTTPS enforced for all API calls
- Token storage encrypted
- Input validation implemented
- Rate limiting handled
- Error logging without sensitive data
Error Handling
- Network timeout handling
- Retry logic with exponential backoff
- Graceful degradation for API failures
- User-friendly error messages
- Comprehensive logging
Performance Optimization
- Connection pooling implemented
- Token caching with expiry management
- Request/response compression
- Monitoring and alerting
- Load testing completed
Data Management
- Voucher storage system
- Order tracking database
- Customer data privacy compliance
- Backup and recovery procedures
Troubleshooting
"Could not authenticate you" (400)
Cause: Invalid company secret
Solution: Verify secret key and company account status
"Invalid customer token" (401)
Cause: Expired or malformed customer token
Solution: Re-authenticate customer
"Validation Failed" (422)
Cause: Missing or invalid request parameters
Solution: Validate request format and required fields
Empty vouchers array
Cause: No matching rewards for provided SKUs
Solution: Check SKU mapping in rewards list
Rate limiting (429)
Cause: Too many requests
Solution: Implement proper rate limiting and retry logic
Best Practices Summary
Authentication Management
- Cache tokens with proper expiry handling
- Implement automatic token refresh
- Use secure storage for secrets
- Monitor authentication failures
Order Processing
- Validate data before API calls
- Generate unique order IDs
- Handle partial failures gracefully
- Store order history for debugging
Voucher Management
- Store voucher details securely
- Implement expiry notifications
- Provide clear redemption instructions
- Track voucher usage analytics
Error Recovery
- Implement comprehensive retry logic
- Log errors with sufficient context
- Provide meaningful user feedback
- Monitor API health continuously