Vision and Description of PostTradeEngine
1. Core Vision
To create a Dodd-Frank compliant, automated post-trade processing
system that eliminates manual intervention in swap trade reporting, ensuring
financial institutions meet regulatory requirements with zero operational delays.
2. Problem Statement
Financial institutions struggle with:
Manual swap reporting causing missed deadlines and regulatory
penalties
Fragmented systems for trade validation, LEI mapping, and SDR
submissions
Lack of real-time visibility into report statuses and compliance gaps
3. Solution Overview
PostTradeEngine delivers:
End-to-end automation from trade ingestion → validation → regulatory
reporting
Unified platform integrating FIX parsing, LEI management, and CFTC
XML generation
Real-time dashboard for compliance officers to monitor submissions
4. Key Functional Pillars
4.1 Trade Processing Automation
FIX 4.4 ingestion with syntax validation and checksum verification
Context-aware parsing for IRS/CDS/TRS instruments
Smart reconciliation between FIX messages and internal trade records
4.2 Regulatory Compliance Engine
UTI generation using timestamp-based unique identifiers
Static LEI mapping with MySQL/Redis fallback strategy
CFTC XML validation against published schemas
4.3 Resilient Submission Framework
Idempotent SDR submissions with exponential backoff retries
Dead letter queue for irrecoverable failures
Audit trails with IP/user-agent metadata
5. Technical Differentiation
Feature Innovation
MongoDB for trade flexibility + MySQL for ACID
Hybrid Storage
compliance
Event
Kafka-based immutable trade lifecycle tracking
Sourcing
Security Keycloak RBAC + field-level encryption
Deployment Docker-first architecture with dependency checks
6. User Experience Vision
For Traders
Real-time trade status with color-coded indicators:
jsx
Copy
Download
<StatusBadge
status={trade.doddFrank?.submissions[0]?.status || 'PENDING'}
/>
One-click drilldown to FIX message origins
For Compliance Officers
Submission heatmaps showing success/failure rates
Regulatory deadlines countdown timers
Bulk retry for failed reports
7. Data Integrity Framework
Guarantees:
Exactly-once processing via Kafka idempotent producer
Cryptographic verification of trade data integrity
8. Regulatory Alignment
Dodd-Frank Coverage Matrix
Requirement Implementation
UTI Generation Time-based UTI-YYYYMMDD-RAND6
LEI Inclusion Preloaded counterparty registry + Redis cache
PET Reporting CFTC XML v2.3 schema validation
30-day MongoDB retention + MySQL
Recordkeeping
archives
9. Evolution Roadmap
Phase 1 (MVP)
Core swap reporting for IRS/CDS/TRS
Static LEI mappings
Local Docker deployment
Phase 2 (V1.0)
Dynamic LEI validation via GLEIF API
SEC CAT reporting integration
Cloud deployment (AWS ECS)
Phase 3 (V2.0)
AI-powered anomaly detection
Blockchain-based audit trails
FedNow integration for settlements
10. Impact Vision
Operational Transformation
diff
Copy
Download
- Manual report preparation: 45 min/trade
+ Automated processing: 5 sec/trade
Compliance Benefits
100% on-time SDR submissions
Zero regulatory penalties
Automated audit documentation
11. Development Philosophy
1. Regulatory-First Design: Every component complies with CFTC
technical specifications
2. Shift-Left Security: Encryption, RBAC, and input validation at ingestion
point
3. Observability-Driven: Built-in Prometheus metrics and structured
logging
4. Academic Rigor: Test-driven development with 70% coverage mandate
12. End-State Vision
A self-healing, compliance-aware infrastructure where:
Trades auto-process within 5 seconds of execution
Compliance officers receive proactive alerts for anomalies
Regulatory updates deploy via automated schema migrations
Audit reports generate with single CLI command:
bash
Copy
Download
npm run audit-report --from 2025-01-01 --to 2025-06-30
This essay defines PostTradeEngine as more than software—it's a regulatory
compliance nervous system for modern financial institutions, transforming
post-trade operations from cost center to strategic advantage.
SRS
We are going to create a comprehensive SRS document for the PostTradeEngine
project. This document will include every detail necessary for development,
including purpose, scope, architecture, functional and non-functional
requirements, database schemas, workflows, security, deployment, testing, and
development plan.
Note: Since the project is now Docker-based without Kubernetes for the MVP,
we adjust accordingly.
Let's structure the SRS as follows:
1. Introduction
2. Overall Description
3. System Architecture
4. Functional Requirements
5. Non-Functional Requirements
6. Database Design
7. Workflows
8. Security Architecture
9. Deployment Strategy
10. Testing Approach
11. Development Plan
12. Appendices
We'll include detailed diagrams and explanations.
Due to the length, I'll break it into sections. Let's start.
Software Requirements Specification (SRS): PostTradeEngine
Version: 5.0 (Final Implementation)
Date: June 19, 2025
1. Introduction
1.1 Purpose
PostTradeEngine automates Dodd-Frank compliant post-trade processing for
Interest Rate Swaps (IRS), Credit Default Swaps (CDS), and Total Return
Swaps (TRS).
1.2 Scope
Included:
Trade ingestion via FIX 4.4
Core validation rules
Dodd-Frank XML reporting
Static LEI mapping
Docker-based deployment
Excluded:
Risk calculation
Reconciliation
Production monitoring
2. System Architecture
2.1 High-Level Architecture
2.2 Technology Stack
Component Technology Version
Backend Node.js 20.x
Messaging Apache Kafka 3.6
Component Technology Version
MongoDB 7.0
Databases
MySQL 8.0
Security Keycloak 24.0
Frontend React 18.2
Containerization Docker 24.0
3. Detailed Workflows
3.1 LEI Mapping Workflow
Implementation Location: src/dodd-frank-service/services/leiService.js
3.2 End-to-End Trade Flow
4. Database Schemas
4.1 MongoDB: Trades Collection
javascript
Copy
Download
// trades collection
{
_id: ObjectId("665f1c9a8d1e2f3a7c8b9d0a"),
tradeId: "TRD-20250619-001",
instrument: "IRS",
quantity: 1000000,
price: 2.5, // Interest rate %
counterparty: "GOLDMAN",
status: "REPORTED",
fixMessage: "8=FIX.4.4|35=D|...",
doddFrank: {
uti: "UTI-20250619-001-XYZ",
lei: "9845000D3E3D5F6B7A2A1",
submissions: [
{
timestamp: ISODate("2025-06-19T14:30:00Z"),
status: "SUCCESS",
sdrResponse: "REC-123456"
}
]
},
createdAt: ISODate("2025-06-19T14:25:00Z")
}
4.2 MySQL: Counterparty Registry
sql
Copy
Download
CREATE TABLE counterparties (
id VARCHAR(12) PRIMARY KEY COMMENT 'Short identifier',
legal_name VARCHAR(100) NOT NULL,
lei VARCHAR(20) UNIQUE NOT NULL COMMENT 'Legal Entity
Identifier',
last_updated TIMESTAMP DEFAULT CURRENT_TIMESTAMP
);
-- Initial Data
INSERT INTO counterparties (id, legal_name, lei) VALUES
('GOLDMAN', 'Goldman Sachs', '9845000D3E3D5F6B7A2A1'),
('JPMORGAN', 'JP Morgan', 'R0MUWSFPU8MPRO8K5P83'),
('BARCLAYS', 'Barclays Capital', 'G5GSEF7VJP5I7OUK5573');
5. Service Implementation Details
5.1 Dodd-Frank Service (Core Components)
File Structure:
text
Copy
Download
dodd-frank-service/
├── src/
│ ├── config/
│ │ └── index.js
│ ├── services/
│ │ ├── leiService.js # LEI mapping logic
│ │ ├── xmlGenerator.js # CFTC XML builder
│ │ └── sdrClient.js # SDR HTTP client
│ ├── utils/
│ │ ├── utiGenerator.js # UTI creation
│ │ └── retryHandler.js # Submission retries
│ ├── kafka/
│ │ └── consumer.js # Trade validation consumer
│ ├── app.js # Express server
│ └── server.js
├── docker/
│ └── Dockerfile
└── test/
├── unit/
│ └── leiService.test.js
└── integration/
└── sdrSubmission.test.js
Key Functions:
javascript
Copy
Download
// leiService.js
export const getLEI = async (counterpartyId) => {
// 1. Check MySQL first
const lei = await mysql.query(
'SELECT lei FROM counterparties WHERE id = ?',
[counterpartyId]
);
// 2. Fallback to Redis cache
if (!lei) {
return redis.hGet('lei_mappings', counterpartyId);
}
return lei;
};
// xmlGenerator.js
export const buildCFTCXML = (trade, lei) => `
<SwapReport xmlns="http://cftc.gov/dodd-frank">
<UTI>${trade.uti}</UTI>
<LEI>${lei}</LEI>
<ProductType>${trade.instrument}</ProductType>
<Notional>${trade.notional}</Notional>
<EffectiveDate>${formatDate(trade.effectiveDate)}</EffectiveDate>
</SwapReport>`;
6. Security Implementation
6.1 Keycloak Configuration
Realm Settings:
json
Copy
Download
{
"realm": "posttrade",
"clients": [
{
"clientId": "posttrade-engine",
"publicClient": false,
"redirectUris": ["http://localhost:3000/*"],
"webOrigins": ["+"],
"roles": ["compliance_officer", "trader"]
}
],
"users": [
{
"username": "compliance1",
"roles": ["compliance_officer"],
"credentials": [{ "type": "password", "value": "SecurePass123!" }]
}
]
}
6.2 RBAC Middleware
javascript
Copy
Download
// authorizationMiddleware.js
const authorize = (role) => (req, res, next) => {
const token = req.headers.authorization.split(' ')[1];
const payload = jwt.verify(token, process.env.JWT_SECRET);
if (!payload.realm_access.roles.includes(role)) {
return res.status(403).json({ error: 'Forbidden' });
}
next();
};
// Route protection
app.post('/reports', authorize('compliance_officer'), reportController.submit);
7. Deployment & Operations
7.1 Docker Compose Setup
docker-compose.yml:
yaml
Copy
Download
version: '3.8'
services:
mongodb:
image: mongo:7.0
ports:
- "27017:27017"
volumes:
- mongo_data:/data/db
mysql:
image: mysql:8.0
environment:
MYSQL_ROOT_PASSWORD: rootpass
MYSQL_DATABASE: posttrade
ports:
- "3306:3306"
volumes:
- ./sql/init.sql:/docker-entrypoint-initdb.d/init.sql
kafka:
image: confluentinc/cp-kafka:7.6.0
ports:
- "9092:9092"
environment:
KAFKA_NUM_PARTITIONS: 3
keycloak:
image: quay.io/keycloak/keycloak:24.0
ports:
- "8080:8080"
command: ["start-dev"]
volumes:
mongo_data:
7.2 Service Startup Sequence
bash
Copy
Download
# Start infrastructure
docker-compose up -d mongodb mysql kafka keycloak
# Initialize databases
docker exec -it mysql mysql -u root -p posttrade < init.sql
# Run services
docker build -t trade-ingestion ./trade-ingestion-service
docker run -d --name trade-ingestion trade-ingestion
docker build -t dodd-frank ./dodd-frank-service
docker run -d --name dodd-frank dodd-frank
# Start React UI
cd frontend && npm start
8. Testing Specifications
8.1 Critical Test Cases
ID Service Test Case Verification Method
TC- Trade
Malformed FIX message Verify NACK response
101 Ingestion
TC- Check MySQL rejects
Validation Unknown counterparty
201 table
TC-
Dodd-Frank LEI lookup failure Validate error handling
301
TC- Confirm retry
Dodd-Frank SDR timeout (504)
302 execution
TC- Unauthorized report
Security Check 403 response
401 submission
8.2 Sample Jest Test
javascript
Copy
Download
// leiService.test.js
describe('LEI Service', () => {
test('Returns LEI for valid counterparty', async () => {
await seedCounterparties(); // Test DB setup
const lei = await getLEI('GOLDMAN');
expect(lei).toBe('9845000D3E3D5F6B7A2A1');
});
test('Throws error for unknown counterparty', async () => {
await expect(getLEI('UNKNOWN_BANK'))
.rejects
.toThrow('LEI not found');
});
});
9. Development Roadmap
9.1 80-Day Implementation Plan
Timeline
9.2 Effort Allocation (120 Hours Total)
Phase Hours Activities
Infrastructure 20 Docker setup, DB config
Backend 50 Service development
Frontend 15 React dashboard
Testing 15 Unit + integration tests
Documentatio
20 SRS, API docs, runbooks
n
10. Appendices
10.1 FIX Message Specification
Supported Messages:
Type Description Fields
D (NewOrderSingle) New trade Symbol, Qty, Price
8 (ExecutionReport) Trade execution ExecID, LastQty
AE
Swap instrument SwapType, Notional
(TradeCaptureReport)
10.2 CFTC XML Schema
xml
Copy
Download
Run
<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema">
<xs:element name="SwapReport">
<xs:complexType>
<xs:sequence>
<xs:element name="UTI" type="xs:string" minOccurs="1"
maxOccurs="1"/>
<xs:element name="LEI" type="xs:string" minOccurs="1"
maxOccurs="1"/>
<xs:element name="ProductType" type="xs:string" minOccurs="1"
maxOccurs="1"/>
<xs:element name="Notional" type="xs:decimal" minOccurs="1"
maxOccurs="1"/>
</xs:sequence>
</xs:complexType>
</xs:element>
</xs:schema>
10.3 Environment Variables
dodd-frank-service/.env:
text
Copy
Download
KAFKA_BROKERS=localhost:9092
MYSQL_HOST=mysql
MYSQL_USER=root
MYSQL_PASSWORD=rootpass
SDR_ENDPOINT=http://sdr-emulator:3000/reports
MAX_RETRIES=3
11. Regulatory Compliance
Dodd-Frank MVP Coverage
Requirement Implementation Status
Swap Identification ✅ (IRS, CDS, TRS only)
UTI Generation ✅ (Time-based with randomness)
LEI Inclusion ✅ (Static mapping)
XML Reporting ✅ (Basic CFTC schema)
Submission
✅ (MongoDB audit trail)
Recordkeeping
Approvals
This SRS provides complete implementation details for PostTradeEngine MVP.
Signature: ________________________
Date: June 19, 2025
END OF DOCUMENT
Implementation Notes:
1. Start with infrastructure setup (docker-compose.yml)
2. Implement trade ingestion service first
3. Use init.sql to preload counterparty data
4. LEI mapping implemented in Dodd-Frank service
5. All Kafka topics must be created before service startup
6. Use REACT_APP_DUMMY_DATA=true for frontend testing
Critical Final Checklist Before Development
Ensure these specifications are fully addressed in your implementation
plan:
1. FIX Message Processing Details
Supported Tags:
python
Copy
Download
REQUIRED_TAGS = [11, 35, 38, 44, 54, 55] # ClOrdID, MsgType, OrderQty,
Price, Side, Symbol
SWAP_TAGS = [1151, 1152] # SwapType, Notional
Parser Edge Cases:
o Handle fragmented TCP packets (message reassembly)
o Validate checksum (Tag 10)
o Reject messages with missing required tags
2. Kafka Configuration Hardening
topic-config.yml:
yaml
Copy
Download
trade_ingested:
partitions: 3
replication: 1
retention: 24h
trade_validated:
partitions: 3
replication: 1
retention: 48h
Consumer Groups:
javascript
Copy
Download
// Dodd-Frank service consumer
const consumer = kafka.consumer({
groupId: 'df-reporting-group',
maxBytesPerPartition: 1048576 // 1MB
});
3. Dodd-Frank XML Validation
XML Schema Enforcement:
javascript
Copy
Download
// xmlValidator.js
const validateAgainstSchema = (xml) => {
const schema = `.../schemas/cftc.xsd`;
const result = libxml.validate(xml, schema);
if (!result.valid) throw new InvalidXMLError(result.errors);
};
Pre-Submission Checks:
1. UTI format regex: /^UTI-\d{8}-[A-Z0-9]{6}$/
2. LEI validity: Check digit verification (ISO 17442)
3. Notional value > $10M threshold
4. Error Handling Specifications
Error Classification:
Code Type Recovery Action
DF-101 LEI Missing Retry + Alert
DF-202 XML Invalid Manual Fix Required
DF-303 SDR Unavailable Exponential Backoff
Dead Letter Queue Implementation:
javascript
Copy
Download
producer.send({
topic: 'dodd_frank_dlq',
messages: [{ value: JSON.stringify(failedTrade) }]
});
5. Security Hardening
Field-Level Encryption:
javascript
Copy
Download
// MongoDB encryption schema
const encryptedSchema = new mongoose.Schema({
notional: {
type: String,
encrypt: {
keyId: process.env.AWS_KMS_KEY_ARN,
algorithm: 'AEAD_AES_256_CBC_HMAC_SHA_512'
}
}
});
API Security Headers:
nginx
Copy
Download
# API Gateway configuration
add_header Content-Security-Policy "default-src 'self'";
add_header X-Content-Type-Options "nosniff";
add_header Strict-Transport-Security "max-age=31536000;
includeSubDomains";
6. Startup Sequence Validation
Dependency Check Script:
bash
Copy
Download
#!/bin/bash
# pre-start.sh
check_service() {
nc -z $1 $2
return $?
}
check_service mongodb 27017 || exit 1
check_service mysql 3306 || exit 1
check_service kafka 9092 || exit 1
echo "All dependencies available"
Service Boot Order:
1. Databases (MongoDB, MySQL)
2. Kafka
3. Keycloak
4. Application Services
5. Frontend
7. Regulatory Metadata Extensions
Audit Trail Requirements:
javascript
Copy
Download
// Audit log entry
const auditEntry = {
event: 'REPORT_SUBMITTED',
user: req.user.id,
trade: tradeId,
timestamp: new Date(),
ip: req.ip,
userAgent: req.headers['user-agent']
};
Data Retention Policy:
sql
Copy
Download
-- MySQL archive procedure
CREATE EVENT purge_old_submissions
ON SCHEDULE EVERY 1 DAY
DO
DELETE FROM submissions
WHERE created_at < NOW() - INTERVAL 30 DAY;
8. Test Data Generation Specs
Realistic Swap Generator:
typescript
Copy
Download
const generateIRS = () => ({
instrument: 'IRS',
notional: 10_000_000 + Math.floor(Math.random() * 50_000_000),
fixedRate: 1.5 + (Math.random() * 5),
floatingIndex: 'SOFR',
effectiveDate: new Date(Date.now() + 86400000 * 2),
terminationDate: new Date(Date.now() + 86400000 * 365 * 5)
});
Negative Test Cases:
Counterparty with expired LEI
Swap with notional < $10M threshold
FIX message with invalid checksum
9. Monitoring and Alerting
Critical Metrics:
prometheus
Copy
Download
# Prometheus metrics
posttrade_submissions_total{status="success"}
posttrade_submissions_total{status="failed"}
posttrade_processing_latency_seconds
Alert Rules:
yaml
Copy
Download
groups:
- name: dodd-frank-alerts
rules:
- alert: SDRSubmissionFailure
expr: rate(posttrade_submissions_total{status="failed"}[5m]) > 0.2
labels:
severity: critical
10. Compliance Documentation
Report Generation Spec:
markdown
Copy
Download
# Dodd-Frank Report Metadata
- **Report Type**: Primary Economic Terms (PET)
- **Format**: XML (CFTC Technical Spec v2.3)
- **Transmission**: HTTPS POST
- **Deadline**: T+1 (Trade Date + 1 business day)
Audit Log Requirements:
1. LEI source verification records
2. UTI generation logs
3. XML schema validation results
4. SDR response receipts
Final Development Readiness Checklist:
1. Docker environments validated
2. Kafka topics created
3. DB schemas initialized (init.sql executed)
4. Keycloak realm configured
5. FIX simulator ready
6. SDR emulator endpoint deployed
7. Shared environment variables set
8. Log aggregation pipeline tested
Implementation Tip: Start with the Trade Ingestion Service first, then move
to validation, followed by Dodd-Frank reporting. Validate each service
independently before integrating with Kafka. Use docker-compose logs -f for
real-time debugging.
You now have a complete, production-grade specification set. The SRS contains
all necessary details to begin development immediately.