@naman_deep_singh/communication-core 1.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +345 -0
- package/dist/cjs/abstract/BaseCircuitBreaker.js +253 -0
- package/dist/cjs/abstract/BaseClient.js +298 -0
- package/dist/cjs/abstract/BaseCompressionManager.js +377 -0
- package/dist/cjs/abstract/BaseConnectionPool.js +543 -0
- package/dist/cjs/abstract/BaseInterceptor.js +235 -0
- package/dist/cjs/abstract/BaseLoadBalancer.js +269 -0
- package/dist/cjs/abstract/BaseProtocol.js +269 -0
- package/dist/cjs/abstract/BaseRetryStrategy.js +255 -0
- package/dist/cjs/abstract/BaseSerializer.js +341 -0
- package/dist/cjs/abstract/BaseServiceDiscoverer.js +254 -0
- package/dist/cjs/abstract/BaseTimeoutManager.js +295 -0
- package/dist/cjs/abstract/index.js +25 -0
- package/dist/cjs/errors/CircuitBreakerError.js +16 -0
- package/dist/cjs/errors/CommunicationError.js +15 -0
- package/dist/cjs/errors/ConnectionError.js +15 -0
- package/dist/cjs/errors/DiscoveryError.js +15 -0
- package/dist/cjs/errors/LoadBalancerError.js +15 -0
- package/dist/cjs/errors/ProtocolError.js +15 -0
- package/dist/cjs/errors/RetryError.js +16 -0
- package/dist/cjs/errors/SerializationError.js +15 -0
- package/dist/cjs/errors/ServiceUnavailableError.js +15 -0
- package/dist/cjs/errors/TimeoutError.js +16 -0
- package/dist/cjs/errors/communicationErrorCodes.js +35 -0
- package/dist/cjs/errors/index.js +31 -0
- package/dist/cjs/index.js +38 -0
- package/dist/cjs/interfaces/CircuitBreaker.interface.js +6 -0
- package/dist/cjs/interfaces/Client.interface.js +6 -0
- package/dist/cjs/interfaces/Compression.interface.js +6 -0
- package/dist/cjs/interfaces/ConnectionPool.interface.js +6 -0
- package/dist/cjs/interfaces/Interceptor.interface.js +6 -0
- package/dist/cjs/interfaces/LoadBalancer.interface.js +2 -0
- package/dist/cjs/interfaces/Protocol.interface.js +6 -0
- package/dist/cjs/interfaces/RetryStrategy.interface.js +6 -0
- package/dist/cjs/interfaces/Serializer.interface.js +2 -0
- package/dist/cjs/interfaces/ServiceDiscovery.interface.js +6 -0
- package/dist/cjs/interfaces/Timeout.interface.js +6 -0
- package/dist/cjs/interfaces/index.js +6 -0
- package/dist/cjs/types/config.js +6 -0
- package/dist/cjs/types/events.js +6 -0
- package/dist/cjs/types/index.js +6 -0
- package/dist/cjs/types/request.js +6 -0
- package/dist/cjs/types/response.js +6 -0
- package/dist/cjs/types/service.js +6 -0
- package/dist/cjs/utils.js +200 -0
- package/dist/esm/abstract/BaseCircuitBreaker.js +249 -0
- package/dist/esm/abstract/BaseClient.js +294 -0
- package/dist/esm/abstract/BaseCompressionManager.js +373 -0
- package/dist/esm/abstract/BaseConnectionPool.js +539 -0
- package/dist/esm/abstract/BaseInterceptor.js +231 -0
- package/dist/esm/abstract/BaseLoadBalancer.js +265 -0
- package/dist/esm/abstract/BaseProtocol.js +265 -0
- package/dist/esm/abstract/BaseRetryStrategy.js +251 -0
- package/dist/esm/abstract/BaseSerializer.js +337 -0
- package/dist/esm/abstract/BaseServiceDiscoverer.js +250 -0
- package/dist/esm/abstract/BaseTimeoutManager.js +291 -0
- package/dist/esm/abstract/index.js +11 -0
- package/dist/esm/errors/CircuitBreakerError.js +12 -0
- package/dist/esm/errors/CommunicationError.js +11 -0
- package/dist/esm/errors/ConnectionError.js +11 -0
- package/dist/esm/errors/DiscoveryError.js +11 -0
- package/dist/esm/errors/LoadBalancerError.js +11 -0
- package/dist/esm/errors/ProtocolError.js +11 -0
- package/dist/esm/errors/RetryError.js +12 -0
- package/dist/esm/errors/SerializationError.js +11 -0
- package/dist/esm/errors/ServiceUnavailableError.js +11 -0
- package/dist/esm/errors/TimeoutError.js +12 -0
- package/dist/esm/errors/communicationErrorCodes.js +32 -0
- package/dist/esm/errors/index.js +17 -0
- package/dist/esm/index.js +18 -0
- package/dist/esm/interfaces/CircuitBreaker.interface.js +5 -0
- package/dist/esm/interfaces/Client.interface.js +5 -0
- package/dist/esm/interfaces/Compression.interface.js +5 -0
- package/dist/esm/interfaces/ConnectionPool.interface.js +5 -0
- package/dist/esm/interfaces/Interceptor.interface.js +5 -0
- package/dist/esm/interfaces/LoadBalancer.interface.js +1 -0
- package/dist/esm/interfaces/Protocol.interface.js +5 -0
- package/dist/esm/interfaces/RetryStrategy.interface.js +5 -0
- package/dist/esm/interfaces/Serializer.interface.js +1 -0
- package/dist/esm/interfaces/ServiceDiscovery.interface.js +5 -0
- package/dist/esm/interfaces/Timeout.interface.js +5 -0
- package/dist/esm/interfaces/index.js +5 -0
- package/dist/esm/types/config.js +5 -0
- package/dist/esm/types/events.js +5 -0
- package/dist/esm/types/index.js +5 -0
- package/dist/esm/types/request.js +5 -0
- package/dist/esm/types/response.js +5 -0
- package/dist/esm/types/service.js +5 -0
- package/dist/esm/utils.js +193 -0
- package/dist/types/abstract/BaseCircuitBreaker.d.ts +167 -0
- package/dist/types/abstract/BaseClient.d.ts +197 -0
- package/dist/types/abstract/BaseCompressionManager.d.ts +180 -0
- package/dist/types/abstract/BaseConnectionPool.d.ts +210 -0
- package/dist/types/abstract/BaseInterceptor.d.ts +150 -0
- package/dist/types/abstract/BaseLoadBalancer.d.ts +167 -0
- package/dist/types/abstract/BaseProtocol.d.ts +163 -0
- package/dist/types/abstract/BaseRetryStrategy.d.ts +130 -0
- package/dist/types/abstract/BaseSerializer.d.ts +181 -0
- package/dist/types/abstract/BaseServiceDiscoverer.d.ts +161 -0
- package/dist/types/abstract/BaseTimeoutManager.d.ts +145 -0
- package/dist/types/abstract/index.d.ts +11 -0
- package/dist/types/errors/CircuitBreakerError.d.ts +8 -0
- package/dist/types/errors/CommunicationError.d.ts +10 -0
- package/dist/types/errors/ConnectionError.d.ts +9 -0
- package/dist/types/errors/DiscoveryError.d.ts +9 -0
- package/dist/types/errors/LoadBalancerError.d.ts +9 -0
- package/dist/types/errors/ProtocolError.d.ts +9 -0
- package/dist/types/errors/RetryError.d.ts +11 -0
- package/dist/types/errors/SerializationError.d.ts +9 -0
- package/dist/types/errors/ServiceUnavailableError.d.ts +12 -0
- package/dist/types/errors/TimeoutError.d.ts +11 -0
- package/dist/types/errors/communicationErrorCodes.d.ts +27 -0
- package/dist/types/errors/index.d.ts +11 -0
- package/dist/types/index.d.ts +13 -0
- package/dist/types/interfaces/CircuitBreaker.interface.d.ts +150 -0
- package/dist/types/interfaces/Client.interface.d.ts +153 -0
- package/dist/types/interfaces/Compression.interface.d.ts +190 -0
- package/dist/types/interfaces/ConnectionPool.interface.d.ts +191 -0
- package/dist/types/interfaces/Interceptor.interface.d.ts +220 -0
- package/dist/types/interfaces/LoadBalancer.interface.d.ts +153 -0
- package/dist/types/interfaces/Protocol.interface.d.ts +117 -0
- package/dist/types/interfaces/RetryStrategy.interface.d.ts +160 -0
- package/dist/types/interfaces/Serializer.interface.d.ts +176 -0
- package/dist/types/interfaces/ServiceDiscovery.interface.d.ts +189 -0
- package/dist/types/interfaces/Timeout.interface.d.ts +135 -0
- package/dist/types/interfaces/index.d.ts +15 -0
- package/dist/types/types/config.d.ts +540 -0
- package/dist/types/types/events.d.ts +204 -0
- package/dist/types/types/index.d.ts +9 -0
- package/dist/types/types/request.d.ts +143 -0
- package/dist/types/types/response.d.ts +155 -0
- package/dist/types/types/service.d.ts +279 -0
- package/dist/types/utils.d.ts +179 -0
- package/package.json +88 -0
package/README.md
ADDED
|
@@ -0,0 +1,345 @@
|
|
|
1
|
+
# @naman_deep_singh/communication-core
|
|
2
|
+
|
|
3
|
+
> Core interfaces and abstract classes for building a comprehensive service-to-service communication layer in TypeScript
|
|
4
|
+
|
|
5
|
+
## Overview
|
|
6
|
+
|
|
7
|
+
This package provides the foundational interfaces, abstract base classes, types, and utilities needed to build a complete microservices communication ecosystem. It serves as the architectural foundation for 5 specialized subpackages that handle different aspects of service communication.
|
|
8
|
+
|
|
9
|
+
## Features
|
|
10
|
+
|
|
11
|
+
- 🔌 **Protocol Abstraction**: Unified interface for HTTP, gRPC, WebSocket protocols
|
|
12
|
+
- 🛡️ **Resilience Patterns**: Circuit breaker and retry strategy interfaces
|
|
13
|
+
- 🔍 **Service Discovery**: Dynamic service location and health monitoring
|
|
14
|
+
- ⚖️ **Load Balancing**: Traffic distribution strategies
|
|
15
|
+
- 🎯 **Unified Client**: Composable client that orchestrates all components
|
|
16
|
+
- 🔧 **Connection Pooling**: Built-in connection management with health checks
|
|
17
|
+
- 📊 **Observability**: Metrics, events, and health monitoring
|
|
18
|
+
- 🚦 **Interceptors**: Request/response middleware system
|
|
19
|
+
- ⚡ **TypeScript First**: Full type safety with strict import/export patterns
|
|
20
|
+
|
|
21
|
+
## Installation
|
|
22
|
+
|
|
23
|
+
```bash
|
|
24
|
+
npm install @naman_deep_singh/communication-core
|
|
25
|
+
```
|
|
26
|
+
|
|
27
|
+
## Core Interfaces
|
|
28
|
+
|
|
29
|
+
### Communication Protocols
|
|
30
|
+
- **`IProtocol`**: Base interface for all communication protocols
|
|
31
|
+
- **`IConnectionPool`**: Connection pooling and lifecycle management
|
|
32
|
+
- **`IInterceptor`**: Request/response middleware
|
|
33
|
+
|
|
34
|
+
### Resilience & Reliability
|
|
35
|
+
- **`ICircuitBreaker`**: Circuit breaker pattern for fault tolerance
|
|
36
|
+
- **`IRetryStrategy`**: Configurable retry mechanisms with backoff
|
|
37
|
+
|
|
38
|
+
### Service Discovery & Load Balancing
|
|
39
|
+
- **`IServiceDiscoverer`**: Dynamic service instance discovery
|
|
40
|
+
- **`ILoadBalanceStrategy`**: Traffic distribution algorithms
|
|
41
|
+
|
|
42
|
+
### Client Orchestration
|
|
43
|
+
- **`IClient`**: Main client interface that composes all components
|
|
44
|
+
- **`IClientFactory`**: Factory for creating and managing client instances
|
|
45
|
+
|
|
46
|
+
## Abstract Base Classes
|
|
47
|
+
|
|
48
|
+
These classes provide common functionality and enforce consistent patterns:
|
|
49
|
+
|
|
50
|
+
### Protocol Layer
|
|
51
|
+
- **`BaseProtocol`**: Common protocol functionality (connection pooling, metrics, error handling)
|
|
52
|
+
- **`BaseConnectionPool`**: Connection lifecycle, health checks, and resource management
|
|
53
|
+
|
|
54
|
+
### Service Discovery
|
|
55
|
+
- **`BaseServiceDiscoverer`**: Caching, health monitoring, and event-driven updates
|
|
56
|
+
|
|
57
|
+
## Type System
|
|
58
|
+
|
|
59
|
+
### Core Types
|
|
60
|
+
- **`Request/Response`**: Standardized request/response objects
|
|
61
|
+
- **`ServiceInstance`**: Service endpoint representation
|
|
62
|
+
- **`ClientConfig`**: Comprehensive client configuration
|
|
63
|
+
- **`ConnectionPoolConfig`**: Connection pool settings
|
|
64
|
+
|
|
65
|
+
### Configuration Types
|
|
66
|
+
- **`ProtocolConfig`**: Protocol-specific settings
|
|
67
|
+
- **`CircuitBreakerConfig`**: Circuit breaker thresholds and timeouts
|
|
68
|
+
- **`RetryConfig`**: Retry policies and backoff strategies
|
|
69
|
+
- **`LoadBalancerConfig`**: Load balancing algorithms and weights
|
|
70
|
+
|
|
71
|
+
### Error Handling
|
|
72
|
+
- **`CommunicationError`**: Base error class with error codes and context
|
|
73
|
+
- **`ConnectionError`**: Connection-specific errors
|
|
74
|
+
- **`TimeoutError`**: Request timeout errors
|
|
75
|
+
- **`ServiceUnavailableError`**: Service discovery errors
|
|
76
|
+
|
|
77
|
+
## Subpackage Architecture
|
|
78
|
+
|
|
79
|
+
This core package enables building 5 specialized subpackages:
|
|
80
|
+
|
|
81
|
+
### 1. **@naman_deep_singh/communication-protocols**
|
|
82
|
+
|
|
83
|
+
**Purpose**: Protocol-specific implementations (HTTP, gRPC, WebSocket)
|
|
84
|
+
|
|
85
|
+
```
|
|
86
|
+
communication-protocols/
|
|
87
|
+
├── src/
|
|
88
|
+
│ ├── http/
|
|
89
|
+
│ │ ├── HttpProtocol.ts # extends BaseProtocol
|
|
90
|
+
│ │ ├── HttpConnectionPool.ts # extends BaseConnectionPool
|
|
91
|
+
│ │ └── HttpInterceptor.ts # implements IInterceptor
|
|
92
|
+
│ ├── grpc/
|
|
93
|
+
│ │ ├── GrpcProtocol.ts # extends BaseProtocol
|
|
94
|
+
│ │ ├── GrpcConnectionPool.ts # extends BaseConnectionPool
|
|
95
|
+
│ │ └── GrpcInterceptor.ts # implements IInterceptor
|
|
96
|
+
│ ├── websocket/
|
|
97
|
+
│ │ ├── WebSocketProtocol.ts # extends BaseProtocol
|
|
98
|
+
│ │ ├── WebSocketConnectionPool.ts
|
|
99
|
+
│ │ └── WebSocketInterceptor.ts
|
|
100
|
+
│ └── index.ts
|
|
101
|
+
├── package.json
|
|
102
|
+
└── README.md
|
|
103
|
+
```
|
|
104
|
+
|
|
105
|
+
**Key Dependencies**: `axios`, `@grpc/grpc-js`, `ws`
|
|
106
|
+
|
|
107
|
+
**Usage**:
|
|
108
|
+
```typescript
|
|
109
|
+
import { HttpProtocol } from '@naman_deep_singh/communication-protocols/http';
|
|
110
|
+
import { GrpcProtocol } from '@naman_deep_singh/communication-protocols/grpc';
|
|
111
|
+
```
|
|
112
|
+
|
|
113
|
+
### 2. **@naman_deep_singh/communication-resilience**
|
|
114
|
+
|
|
115
|
+
**Purpose**: Fault tolerance patterns (Circuit Breaker, Retry Strategies)
|
|
116
|
+
|
|
117
|
+
```
|
|
118
|
+
communication-resilience/
|
|
119
|
+
├── src/
|
|
120
|
+
│ ├── circuit-breaker/
|
|
121
|
+
│ │ ├── CircuitBreakerImpl.ts # implements ICircuitBreaker
|
|
122
|
+
│ │ ├── CircuitBreakerState.ts # State management
|
|
123
|
+
│ │ └── CircuitBreakerMetrics.ts # Failure tracking
|
|
124
|
+
│ ├── retry/
|
|
125
|
+
│ │ ├── ExponentialBackoffRetry.ts # implements IRetryStrategy
|
|
126
|
+
│ │ ├── LinearBackoffRetry.ts # implements IRetryStrategy
|
|
127
|
+
│ │ ├── FixedDelayRetry.ts # implements IRetryStrategy
|
|
128
|
+
│ │ └── JitterRetry.ts # implements IRetryStrategy
|
|
129
|
+
│ ├── policies/
|
|
130
|
+
│ │ ├── RetryPolicy.ts
|
|
131
|
+
│ │ └── CircuitBreakerPolicy.ts
|
|
132
|
+
│ └── index.ts
|
|
133
|
+
├── package.json
|
|
134
|
+
└── README.md
|
|
135
|
+
```
|
|
136
|
+
|
|
137
|
+
**Usage**:
|
|
138
|
+
```typescript
|
|
139
|
+
import { CircuitBreakerImpl } from '@naman_deep_singh/communication-resilience/circuit-breaker';
|
|
140
|
+
import { ExponentialBackoffRetry } from '@naman_deep_singh/communication-resilience/retry';
|
|
141
|
+
```
|
|
142
|
+
|
|
143
|
+
### 3. **@naman_deep_singh/communication-discovery**
|
|
144
|
+
|
|
145
|
+
**Purpose**: Service discovery implementations (Consul, etcd, Kubernetes)
|
|
146
|
+
|
|
147
|
+
```
|
|
148
|
+
communication-discovery/
|
|
149
|
+
├── src/
|
|
150
|
+
│ ├── consul/
|
|
151
|
+
│ │ ├── ConsulServiceDiscoverer.ts # extends BaseServiceDiscoverer
|
|
152
|
+
│ │ ├── ConsulHealthChecker.ts
|
|
153
|
+
│ │ └── ConsulWatcher.ts
|
|
154
|
+
│ ├── etcd/
|
|
155
|
+
│ │ ├── EtcdServiceDiscoverer.ts # extends BaseServiceDiscoverer
|
|
156
|
+
│ │ ├── EtcdHealthChecker.ts
|
|
157
|
+
│ │ └── EtcdWatcher.ts
|
|
158
|
+
│ ├── kubernetes/
|
|
159
|
+
│ │ ├── K8sServiceDiscoverer.ts # extends BaseServiceDiscoverer
|
|
160
|
+
│ │ ├── K8sHealthChecker.ts
|
|
161
|
+
│ │ └── K8sWatcher.ts
|
|
162
|
+
│ ├── static/
|
|
163
|
+
│ │ └── StaticServiceDiscoverer.ts # For testing/development
|
|
164
|
+
│ └── index.ts
|
|
165
|
+
├── package.json
|
|
166
|
+
└── README.md
|
|
167
|
+
```
|
|
168
|
+
|
|
169
|
+
**Key Dependencies**: `consul`, `etcd3`, `@kubernetes/client-node`
|
|
170
|
+
|
|
171
|
+
**Usage**:
|
|
172
|
+
```typescript
|
|
173
|
+
import { ConsulServiceDiscoverer } from '@naman_deep_singh/communication-discovery/consul';
|
|
174
|
+
import { K8sServiceDiscoverer } from '@naman_deep_singh/communication-discovery/kubernetes';
|
|
175
|
+
```
|
|
176
|
+
|
|
177
|
+
### 4. **@naman_deep_singh/communication-load-balancing**
|
|
178
|
+
|
|
179
|
+
**Purpose**: Load balancing strategies for traffic distribution
|
|
180
|
+
|
|
181
|
+
```
|
|
182
|
+
communication-load-balancing/
|
|
183
|
+
├── src/
|
|
184
|
+
│ ├── strategies/
|
|
185
|
+
│ │ ├── RoundRobinStrategy.ts # implements ILoadBalanceStrategy
|
|
186
|
+
│ │ ├── WeightedRoundRobinStrategy.ts # implements ILoadBalanceStrategy
|
|
187
|
+
│ │ ├── LeastConnectionsStrategy.ts # implements ILoadBalanceStrategy
|
|
188
|
+
│ │ ├── RandomStrategy.ts # implements ILoadBalanceStrategy
|
|
189
|
+
│ │ └── ConsistentHashStrategy.ts # implements ILoadBalanceStrategy
|
|
190
|
+
│ ├── health/
|
|
191
|
+
│ │ ├── HealthAwareLoadBalancer.ts
|
|
192
|
+
│ │ └── HealthScorer.ts
|
|
193
|
+
│ ├── metrics/
|
|
194
|
+
│ │ ├── LoadBalancerMetrics.ts
|
|
195
|
+
│ │ └── ConnectionTracker.ts
|
|
196
|
+
│ └── index.ts
|
|
197
|
+
├── package.json
|
|
198
|
+
└── README.md
|
|
199
|
+
```
|
|
200
|
+
|
|
201
|
+
**Usage**:
|
|
202
|
+
```typescript
|
|
203
|
+
import { RoundRobinStrategy } from '@naman_deep_singh/communication-load-balancing/strategies';
|
|
204
|
+
import { WeightedRoundRobinStrategy } from '@naman_deep_singh/communication-load-balancing/strategies';
|
|
205
|
+
```
|
|
206
|
+
|
|
207
|
+
### 5. **@naman_deep_singh/communication-client**
|
|
208
|
+
|
|
209
|
+
**Purpose**: Unified client that orchestrates all components
|
|
210
|
+
|
|
211
|
+
```
|
|
212
|
+
communication-client/
|
|
213
|
+
├── src/
|
|
214
|
+
│ ├── client/
|
|
215
|
+
│ │ ├── CommunicationClient.ts # implements IClient
|
|
216
|
+
│ │ ├── ClientFactory.ts # implements IClientFactory
|
|
217
|
+
│ │ └── ClientBuilder.ts # Fluent builder pattern
|
|
218
|
+
│ ├── pipeline/
|
|
219
|
+
│ │ ├── RequestPipeline.ts
|
|
220
|
+
│ │ ├── ResponsePipeline.ts
|
|
221
|
+
│ │ └── InterceptorChain.ts
|
|
222
|
+
│ ├── middleware/
|
|
223
|
+
│ │ ├── LoggingInterceptor.ts
|
|
224
|
+
│ │ ├── MetricsInterceptor.ts
|
|
225
|
+
│ │ ├── TracingInterceptor.ts
|
|
226
|
+
│ │ └── AuthInterceptor.ts
|
|
227
|
+
│ ├── events/
|
|
228
|
+
│ │ ├── ClientEventEmitter.ts
|
|
229
|
+
│ │ └── ClientEvents.ts
|
|
230
|
+
│ └── index.ts
|
|
231
|
+
├── package.json
|
|
232
|
+
└── README.md
|
|
233
|
+
```
|
|
234
|
+
|
|
235
|
+
**Usage**:
|
|
236
|
+
```typescript
|
|
237
|
+
import { CommunicationClient, ClientBuilder } from '@naman_deep_singh/communication-client';
|
|
238
|
+
|
|
239
|
+
// Fluent builder pattern
|
|
240
|
+
const client = new ClientBuilder()
|
|
241
|
+
.withProtocol(new HttpProtocol())
|
|
242
|
+
.withServiceDiscovery(new ConsulServiceDiscoverer(consulConfig))
|
|
243
|
+
.withLoadBalancer(new RoundRobinStrategy())
|
|
244
|
+
.withCircuitBreaker(new CircuitBreakerImpl(cbConfig))
|
|
245
|
+
.withRetryStrategy(new ExponentialBackoffRetry(retryConfig))
|
|
246
|
+
.build('user-service');
|
|
247
|
+
```
|
|
248
|
+
|
|
249
|
+
## Development Roadmap
|
|
250
|
+
|
|
251
|
+
### Phase 1: Protocols Foundation (Week 1-2)
|
|
252
|
+
- Implement `HttpProtocol` with connection pooling
|
|
253
|
+
- Add basic interceptor support
|
|
254
|
+
- Create comprehensive tests
|
|
255
|
+
|
|
256
|
+
### Phase 2: Resilience Layer (Week 3)
|
|
257
|
+
- Implement `CircuitBreakerImpl` with state management
|
|
258
|
+
- Add `ExponentialBackoffRetry` strategy
|
|
259
|
+
- Integration testing with HTTP protocol
|
|
260
|
+
|
|
261
|
+
### Phase 3: Service Discovery (Week 4)
|
|
262
|
+
- Implement `ConsulServiceDiscoverer`
|
|
263
|
+
- Add health checking and caching
|
|
264
|
+
- Event-driven service updates
|
|
265
|
+
|
|
266
|
+
### Phase 4: Load Balancing (Week 5)
|
|
267
|
+
- Implement `RoundRobinStrategy`
|
|
268
|
+
- Add health-aware load balancing
|
|
269
|
+
- Performance benchmarking
|
|
270
|
+
|
|
271
|
+
### Phase 5: Client Orchestration (Week 6)
|
|
272
|
+
- Create unified `CommunicationClient`
|
|
273
|
+
- Implement request pipeline
|
|
274
|
+
- End-to-end integration testing
|
|
275
|
+
|
|
276
|
+
## Usage Example
|
|
277
|
+
|
|
278
|
+
```typescript
|
|
279
|
+
import {
|
|
280
|
+
IClient,
|
|
281
|
+
IProtocol,
|
|
282
|
+
IServiceDiscoverer,
|
|
283
|
+
ILoadBalanceStrategy,
|
|
284
|
+
ICircuitBreaker,
|
|
285
|
+
IRetryStrategy
|
|
286
|
+
} from '@naman_deep_singh/communication-core';
|
|
287
|
+
|
|
288
|
+
// This core package provides the contracts
|
|
289
|
+
// Implementations come from subpackages:
|
|
290
|
+
|
|
291
|
+
// From communication-protocols
|
|
292
|
+
const protocol: IProtocol = new HttpProtocol({
|
|
293
|
+
timeout: 5000,
|
|
294
|
+
maxConnections: 100
|
|
295
|
+
});
|
|
296
|
+
|
|
297
|
+
// From communication-discovery
|
|
298
|
+
const discovery: IServiceDiscoverer = new ConsulServiceDiscoverer({
|
|
299
|
+
host: 'localhost',
|
|
300
|
+
port: 8500
|
|
301
|
+
});
|
|
302
|
+
|
|
303
|
+
// From communication-load-balancing
|
|
304
|
+
const loadBalancer: ILoadBalanceStrategy = new RoundRobinStrategy();
|
|
305
|
+
|
|
306
|
+
// From communication-resilience
|
|
307
|
+
const circuitBreaker: ICircuitBreaker = new CircuitBreakerImpl({
|
|
308
|
+
failureThreshold: 5,
|
|
309
|
+
timeout: 60000
|
|
310
|
+
});
|
|
311
|
+
|
|
312
|
+
// From communication-client
|
|
313
|
+
const client: IClient = new CommunicationClient({
|
|
314
|
+
serviceName: 'user-service',
|
|
315
|
+
protocol,
|
|
316
|
+
serviceDiscoverer: discovery,
|
|
317
|
+
loadBalancer,
|
|
318
|
+
circuitBreaker
|
|
319
|
+
});
|
|
320
|
+
|
|
321
|
+
// Make requests
|
|
322
|
+
const response = await client.call('/users/123');
|
|
323
|
+
```
|
|
324
|
+
|
|
325
|
+
## Key Benefits
|
|
326
|
+
|
|
327
|
+
- **🔧 Modular Architecture**: Use only the components you need
|
|
328
|
+
- **🔄 Consistent Patterns**: All implementations follow the same interfaces
|
|
329
|
+
- **🧪 Easy Testing**: Mock interfaces for comprehensive unit testing
|
|
330
|
+
- **📈 Extensible**: Add new protocols/strategies without breaking changes
|
|
331
|
+
- **⚡ Performance**: Built-in connection pooling and caching
|
|
332
|
+
- **🛡️ Reliable**: Circuit breakers and retry mechanisms
|
|
333
|
+
- **📊 Observable**: Built-in metrics and event system
|
|
334
|
+
|
|
335
|
+
## Contributing
|
|
336
|
+
|
|
337
|
+
This package follows strict TypeScript patterns:
|
|
338
|
+
- No wildcard exports (except root index)
|
|
339
|
+
- Type keyword for all type imports
|
|
340
|
+
- .js extensions in imports
|
|
341
|
+
- Barrel exports in all directories
|
|
342
|
+
|
|
343
|
+
## License
|
|
344
|
+
|
|
345
|
+
MIT
|
|
@@ -0,0 +1,253 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
/**
|
|
3
|
+
* Abstract base circuit breaker implementation
|
|
4
|
+
* @packageDocumentation
|
|
5
|
+
*/
|
|
6
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
7
|
+
exports.BaseCircuitBreaker = void 0;
|
|
8
|
+
/**
|
|
9
|
+
* Abstract base circuit breaker implementation
|
|
10
|
+
* Provides common functionality for all circuit breaker implementations
|
|
11
|
+
*/
|
|
12
|
+
class BaseCircuitBreaker {
|
|
13
|
+
/**
|
|
14
|
+
* Create a new base circuit breaker instance
|
|
15
|
+
* @param name Circuit breaker name
|
|
16
|
+
* @param config Circuit breaker configuration
|
|
17
|
+
*/
|
|
18
|
+
constructor(name, config) {
|
|
19
|
+
/** Current state */
|
|
20
|
+
this.state = 'closed';
|
|
21
|
+
/** Failure count */
|
|
22
|
+
this.failureCount = 0;
|
|
23
|
+
/** Success count */
|
|
24
|
+
this.successCount = 0;
|
|
25
|
+
/** Circuit breaker statistics */
|
|
26
|
+
this.stats = {
|
|
27
|
+
totalExecutions: 0,
|
|
28
|
+
totalSuccesses: 0,
|
|
29
|
+
totalFailures: 0,
|
|
30
|
+
successRate: 0,
|
|
31
|
+
failureRate: 0,
|
|
32
|
+
totalTimeOpen: 0,
|
|
33
|
+
totalTimeClosed: 0,
|
|
34
|
+
lastStateChange: Date.now(),
|
|
35
|
+
};
|
|
36
|
+
/** Time when current state was entered */
|
|
37
|
+
this.stateEnteredTime = Date.now();
|
|
38
|
+
this.name = name;
|
|
39
|
+
this.config = { ...config };
|
|
40
|
+
this.initialize();
|
|
41
|
+
}
|
|
42
|
+
/**
|
|
43
|
+
* Initialize circuit breaker
|
|
44
|
+
*/
|
|
45
|
+
initialize() {
|
|
46
|
+
// Can be overridden by subclasses
|
|
47
|
+
}
|
|
48
|
+
/**
|
|
49
|
+
* Check if circuit breaker should allow execution
|
|
50
|
+
* @returns True if execution is allowed
|
|
51
|
+
*/
|
|
52
|
+
shouldAllowExecution() {
|
|
53
|
+
switch (this.state) {
|
|
54
|
+
case 'closed':
|
|
55
|
+
return true;
|
|
56
|
+
case 'open':
|
|
57
|
+
if (this.nextResetTime && Date.now() >= this.nextResetTime) {
|
|
58
|
+
this.transitionToHalfOpen();
|
|
59
|
+
return true;
|
|
60
|
+
}
|
|
61
|
+
return false;
|
|
62
|
+
case 'half-open':
|
|
63
|
+
return this.failureCount < (this.config.halfOpenMaxAttempts || 1);
|
|
64
|
+
default:
|
|
65
|
+
return false;
|
|
66
|
+
}
|
|
67
|
+
}
|
|
68
|
+
/**
|
|
69
|
+
* Transition circuit breaker to closed state
|
|
70
|
+
*/
|
|
71
|
+
transitionToClosed() {
|
|
72
|
+
const previousState = this.state;
|
|
73
|
+
this.state = 'closed';
|
|
74
|
+
this.failureCount = 0;
|
|
75
|
+
this.successCount = 0;
|
|
76
|
+
this.nextResetTime = undefined;
|
|
77
|
+
this.updateStateTime(previousState);
|
|
78
|
+
this.onStateChange('closed', previousState);
|
|
79
|
+
}
|
|
80
|
+
/**
|
|
81
|
+
* Transition circuit breaker to open state
|
|
82
|
+
* @param error Optional error that caused the transition
|
|
83
|
+
*/
|
|
84
|
+
transitionToOpen(error) {
|
|
85
|
+
const previousState = this.state;
|
|
86
|
+
this.state = 'open';
|
|
87
|
+
this.nextResetTime = Date.now() + (this.config.resetTimeout || 30000);
|
|
88
|
+
this.updateStateTime(previousState);
|
|
89
|
+
this.onStateChange('open', previousState, error);
|
|
90
|
+
}
|
|
91
|
+
/**
|
|
92
|
+
* Transition circuit breaker to half-open state
|
|
93
|
+
*/
|
|
94
|
+
transitionToHalfOpen() {
|
|
95
|
+
const previousState = this.state;
|
|
96
|
+
this.state = 'half-open';
|
|
97
|
+
this.failureCount = 0;
|
|
98
|
+
this.successCount = 0;
|
|
99
|
+
this.updateStateTime(previousState);
|
|
100
|
+
this.onStateChange('half-open', previousState);
|
|
101
|
+
}
|
|
102
|
+
/**
|
|
103
|
+
* Update state timing statistics
|
|
104
|
+
* @param previousState Previous state
|
|
105
|
+
*/
|
|
106
|
+
updateStateTime(previousState) {
|
|
107
|
+
const now = Date.now();
|
|
108
|
+
const timeInState = now - this.stateEnteredTime;
|
|
109
|
+
if (previousState === 'open') {
|
|
110
|
+
this.stats.totalTimeOpen += timeInState;
|
|
111
|
+
}
|
|
112
|
+
else if (previousState === 'closed') {
|
|
113
|
+
this.stats.totalTimeClosed += timeInState;
|
|
114
|
+
}
|
|
115
|
+
this.stateEnteredTime = now;
|
|
116
|
+
this.stats.lastStateChange = now;
|
|
117
|
+
}
|
|
118
|
+
/**
|
|
119
|
+
* Hook for state changes
|
|
120
|
+
* @param newState New state
|
|
121
|
+
* @param previousState Previous state
|
|
122
|
+
* @param error Optional error that caused state change
|
|
123
|
+
*/
|
|
124
|
+
onStateChange(newState, previousState, error) {
|
|
125
|
+
// Can be overridden by subclasses
|
|
126
|
+
// Emit events, log, etc.
|
|
127
|
+
}
|
|
128
|
+
/**
|
|
129
|
+
* Check if failure threshold is reached
|
|
130
|
+
* @returns True if failure threshold reached
|
|
131
|
+
*/
|
|
132
|
+
isFailureThresholdReached() {
|
|
133
|
+
return this.failureCount >= (this.config.failureThreshold || 5);
|
|
134
|
+
}
|
|
135
|
+
/**
|
|
136
|
+
* Check if success threshold is reached
|
|
137
|
+
* @returns True if success threshold reached
|
|
138
|
+
*/
|
|
139
|
+
isSuccessThresholdReached() {
|
|
140
|
+
return this.successCount >= (this.config.successThreshold || 1);
|
|
141
|
+
}
|
|
142
|
+
/**
|
|
143
|
+
* Manually trip the circuit breaker to open state
|
|
144
|
+
* @param error Error that caused the trip
|
|
145
|
+
*/
|
|
146
|
+
trip(error) {
|
|
147
|
+
this.transitionToOpen(error);
|
|
148
|
+
}
|
|
149
|
+
/**
|
|
150
|
+
* Manually reset the circuit breaker to closed state
|
|
151
|
+
*/
|
|
152
|
+
reset() {
|
|
153
|
+
this.transitionToClosed();
|
|
154
|
+
}
|
|
155
|
+
/**
|
|
156
|
+
* Check if circuit breaker is currently open
|
|
157
|
+
*/
|
|
158
|
+
isOpen() {
|
|
159
|
+
return this.state === 'open';
|
|
160
|
+
}
|
|
161
|
+
/**
|
|
162
|
+
* Check if circuit breaker is currently closed
|
|
163
|
+
*/
|
|
164
|
+
isClosed() {
|
|
165
|
+
return this.state === 'closed';
|
|
166
|
+
}
|
|
167
|
+
/**
|
|
168
|
+
* Check if circuit breaker is in half-open state
|
|
169
|
+
*/
|
|
170
|
+
isHalfOpen() {
|
|
171
|
+
return this.state === 'half-open';
|
|
172
|
+
}
|
|
173
|
+
/**
|
|
174
|
+
* Record a successful execution
|
|
175
|
+
*/
|
|
176
|
+
recordSuccess() {
|
|
177
|
+
this.successCount++;
|
|
178
|
+
this.lastSuccessTime = Date.now();
|
|
179
|
+
this.stats.totalSuccesses++;
|
|
180
|
+
if (this.state === 'half-open' && this.isSuccessThresholdReached()) {
|
|
181
|
+
this.transitionToClosed();
|
|
182
|
+
}
|
|
183
|
+
}
|
|
184
|
+
/**
|
|
185
|
+
* Record a failed execution
|
|
186
|
+
* @param error Error that occurred
|
|
187
|
+
*/
|
|
188
|
+
recordFailure(error) {
|
|
189
|
+
this.failureCount++;
|
|
190
|
+
this.lastFailureTime = Date.now();
|
|
191
|
+
this.stats.totalFailures++;
|
|
192
|
+
if (this.state === 'half-open') {
|
|
193
|
+
this.transitionToOpen(error);
|
|
194
|
+
}
|
|
195
|
+
else if (this.state === 'closed' && this.isFailureThresholdReached()) {
|
|
196
|
+
this.transitionToOpen(error);
|
|
197
|
+
}
|
|
198
|
+
}
|
|
199
|
+
/**
|
|
200
|
+
* Get circuit breaker statistics
|
|
201
|
+
*/
|
|
202
|
+
getStats() {
|
|
203
|
+
const total = this.stats.totalSuccesses + this.stats.totalFailures;
|
|
204
|
+
return {
|
|
205
|
+
...this.stats,
|
|
206
|
+
successRate: total > 0 ? this.stats.totalSuccesses / total : 0,
|
|
207
|
+
failureRate: total > 0 ? this.stats.totalFailures / total : 0,
|
|
208
|
+
};
|
|
209
|
+
}
|
|
210
|
+
/**
|
|
211
|
+
* Reset circuit breaker statistics
|
|
212
|
+
*/
|
|
213
|
+
resetStats() {
|
|
214
|
+
this.stats = {
|
|
215
|
+
totalExecutions: 0,
|
|
216
|
+
totalSuccesses: 0,
|
|
217
|
+
totalFailures: 0,
|
|
218
|
+
successRate: 0,
|
|
219
|
+
failureRate: 0,
|
|
220
|
+
totalTimeOpen: 0,
|
|
221
|
+
totalTimeClosed: 0,
|
|
222
|
+
lastStateChange: Date.now(),
|
|
223
|
+
};
|
|
224
|
+
}
|
|
225
|
+
/**
|
|
226
|
+
* Update circuit breaker configuration
|
|
227
|
+
* @param config New configuration
|
|
228
|
+
*/
|
|
229
|
+
updateConfig(config) {
|
|
230
|
+
this.config = { ...this.config, ...config };
|
|
231
|
+
}
|
|
232
|
+
/**
|
|
233
|
+
* Health check for the circuit breaker
|
|
234
|
+
*/
|
|
235
|
+
healthCheck() {
|
|
236
|
+
const healthy = this.state === 'closed' || this.state === 'half-open';
|
|
237
|
+
return {
|
|
238
|
+
healthy,
|
|
239
|
+
state: this.state,
|
|
240
|
+
message: healthy ? 'Circuit breaker is operational' : 'Circuit breaker is open',
|
|
241
|
+
details: {
|
|
242
|
+
name: this.name,
|
|
243
|
+
failureCount: this.failureCount,
|
|
244
|
+
successCount: this.successCount,
|
|
245
|
+
lastFailureTime: this.lastFailureTime,
|
|
246
|
+
lastSuccessTime: this.lastSuccessTime,
|
|
247
|
+
nextResetTime: this.nextResetTime,
|
|
248
|
+
config: this.config,
|
|
249
|
+
},
|
|
250
|
+
};
|
|
251
|
+
}
|
|
252
|
+
}
|
|
253
|
+
exports.BaseCircuitBreaker = BaseCircuitBreaker;
|