onecore 0.5.17 → 0.6.1
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 +400 -1
- package/package.json +1 -1
- package/src/cache.ts +8 -7
- package/src/formatter.ts +6 -1
- package/src/index.ts +5 -2
- package/src/io.ts +24 -0
- package/src/job.ts +172 -0
- package/src/location.ts +0 -22
- package/src/logger.ts +26 -1
- package/src/model.ts +22 -135
- package/src/mq.ts +4 -5
- package/src/validator.ts +5 -3
- package/src/video.ts +0 -3
package/README.md
CHANGED
|
@@ -1 +1,400 @@
|
|
|
1
|
-
# onecore
|
|
1
|
+
# onecore
|
|
2
|
+
|
|
3
|
+
> The shared foundation for the Core TS ecosystem.
|
|
4
|
+
|
|
5
|
+
`onecore` provides the common contracts, metadata model, and reusable application-layer base classes used throughout the Core TS ecosystem.
|
|
6
|
+
|
|
7
|
+
It allows libraries such as **sql-core**, **mysql2-core**, **postgres-kit**, **mongodb-kit**, **validation-core**, **cache-plus**, **redis-plus**, **message-processing**, **nats-plus**, **redis-messaging**, **rabbitmq-transport**, **logger-core**, and **health-service** to work together through a unified API.
|
|
8
|
+
|
|
9
|
+
## Features
|
|
10
|
+
|
|
11
|
+
* Common interfaces for enterprise applications
|
|
12
|
+
* Unified metadata model (`Attribute`)
|
|
13
|
+
* Reusable CRUD and Search use-case base classes
|
|
14
|
+
* Zero-cost abstractions through TypeScript interfaces
|
|
15
|
+
* Tree-shakeable architecture
|
|
16
|
+
* Works in both backend and frontend applications
|
|
17
|
+
* No framework dependency
|
|
18
|
+
* Fully written in TypeScript
|
|
19
|
+
|
|
20
|
+
---
|
|
21
|
+
|
|
22
|
+
# Installation
|
|
23
|
+
|
|
24
|
+
```bash
|
|
25
|
+
npm install onecore
|
|
26
|
+
```
|
|
27
|
+
|
|
28
|
+
---
|
|
29
|
+
|
|
30
|
+
# Why onecore?
|
|
31
|
+
|
|
32
|
+
Enterprise applications often use many infrastructure libraries.
|
|
33
|
+
|
|
34
|
+
For example:
|
|
35
|
+
|
|
36
|
+
* Database
|
|
37
|
+
* Validation
|
|
38
|
+
* Cache
|
|
39
|
+
* Message Queue
|
|
40
|
+
* Logging
|
|
41
|
+
* Health Check
|
|
42
|
+
* Import/Export
|
|
43
|
+
|
|
44
|
+
Without a shared foundation, every library exposes its own interfaces and metadata.
|
|
45
|
+
|
|
46
|
+
```text
|
|
47
|
+
Repository (sql)
|
|
48
|
+
Validator (validation)
|
|
49
|
+
Producer (mq)
|
|
50
|
+
Logger (logger)
|
|
51
|
+
Cache (cache)
|
|
52
|
+
```
|
|
53
|
+
|
|
54
|
+
`onecore` provides a single common language for the entire ecosystem.
|
|
55
|
+
|
|
56
|
+
```ts
|
|
57
|
+
import {
|
|
58
|
+
Repository,
|
|
59
|
+
Validator,
|
|
60
|
+
Producer,
|
|
61
|
+
CachePort,
|
|
62
|
+
Logger,
|
|
63
|
+
HealthChecker
|
|
64
|
+
} from "onecore";
|
|
65
|
+
```
|
|
66
|
+
|
|
67
|
+
Applications only depend on **onecore**, while implementation libraries implement these contracts.
|
|
68
|
+
|
|
69
|
+
---
|
|
70
|
+
|
|
71
|
+
# Ecosystem
|
|
72
|
+
|
|
73
|
+
```
|
|
74
|
+
Applications
|
|
75
|
+
┌───────────────────────────────────────────────────────────────┐
|
|
76
|
+
│ │
|
|
77
|
+
│ React Apps • REST APIs • Microservices • Workers • CLI │
|
|
78
|
+
│ │
|
|
79
|
+
└───────────────────────────────────────────────────────────────┘
|
|
80
|
+
▲
|
|
81
|
+
│
|
|
82
|
+
Reusable Use Cases (Optional)
|
|
83
|
+
CRUD • Search • View • Generic Services
|
|
84
|
+
▲
|
|
85
|
+
│
|
|
86
|
+
┌─────────────────────────────────────────────────────────────────────────────────┐
|
|
87
|
+
│ onecore │
|
|
88
|
+
│ │
|
|
89
|
+
│ • Common Interfaces │
|
|
90
|
+
│ • Unified Attribute Metadata │
|
|
91
|
+
│ • Locale & Currency │
|
|
92
|
+
│ • Shared Models │
|
|
93
|
+
│ • Reusable Service Layer │
|
|
94
|
+
└─────────────────────────────────────────────────────────────────────────────────┘
|
|
95
|
+
▲ ▲ ▲ ▲ ▲
|
|
96
|
+
│ │ │ │ │
|
|
97
|
+
│ │ │ │ │
|
|
98
|
+
┌────────────────┐ ┌────────────────┐ ┌──────────────────┐ ┌────────────────┐ ┌────────────────┐
|
|
99
|
+
│ Database │ │ Validation │ │ Messaging │ │ Import / Export│ │ Cache │
|
|
100
|
+
├────────────────┤ ├────────────────┤ ├──────────────────┤ ├────────────────┤ ├────────────────┤
|
|
101
|
+
│ sql-core │ │validation-core │ │message-processing│ │import-service │ │ cache-plus │
|
|
102
|
+
│ mysql2-core │ │ │ │nats-plus │ │export-kit │ │ redis-plus │
|
|
103
|
+
│ postgres-kit │ │ │ │redis-messaging │ │ │ │ │
|
|
104
|
+
│ oracle-core │ │ │ │rabbitmq-transport│ │ │ │ │
|
|
105
|
+
│ mssql-core │ │ │ │activemq │ │ │ │ │
|
|
106
|
+
│ mongodb-kit │ │ │ │ibmmq-plus │ │ │ │ │
|
|
107
|
+
└────────────────┘ └────────────────┘ └──────────────────┘ └────────────────┘ └────────────────┘
|
|
108
|
+
|
|
109
|
+
```
|
|
110
|
+
|
|
111
|
+
All libraries share the same interfaces defined by `onecore`.
|
|
112
|
+
|
|
113
|
+
---
|
|
114
|
+
|
|
115
|
+
# Zero-Cost Abstractions
|
|
116
|
+
|
|
117
|
+
One of the goals of `onecore` is to provide a common API **without adding runtime overhead**.
|
|
118
|
+
|
|
119
|
+
## Interfaces
|
|
120
|
+
|
|
121
|
+
Interfaces disappear after TypeScript compilation.
|
|
122
|
+
|
|
123
|
+
```ts
|
|
124
|
+
import { Repository, Validator } from "onecore";
|
|
125
|
+
```
|
|
126
|
+
|
|
127
|
+
The generated JavaScript contains no implementation from `onecore`.
|
|
128
|
+
|
|
129
|
+
## Base Classes
|
|
130
|
+
|
|
131
|
+
If an application extends one of the reusable CRUD or Search use-case classes, only those classes are included in the final bundle.
|
|
132
|
+
|
|
133
|
+
Modern bundlers such as Webpack, Rollup, Vite, and esbuild tree-shake unused code automatically.
|
|
134
|
+
|
|
135
|
+
This allows frontend and backend projects to share the same package while keeping bundles minimal.
|
|
136
|
+
|
|
137
|
+
---
|
|
138
|
+
|
|
139
|
+
# Unified Metadata
|
|
140
|
+
|
|
141
|
+
The most important type in `onecore` is `Attribute`.
|
|
142
|
+
|
|
143
|
+
Unlike persistence-specific or validation-specific metadata, `Attribute` is the canonical metadata model shared across the entire ecosystem.
|
|
144
|
+
|
|
145
|
+
```
|
|
146
|
+
Attribute
|
|
147
|
+
│
|
|
148
|
+
┌───────────────┼────────────────┐
|
|
149
|
+
│ │ │
|
|
150
|
+
Validation Database Import/Export
|
|
151
|
+
│ │ │
|
|
152
|
+
validation-core sql-core import-service
|
|
153
|
+
mysql2-core export-kit
|
|
154
|
+
postgres-kit
|
|
155
|
+
mongodb-kit
|
|
156
|
+
```
|
|
157
|
+
|
|
158
|
+
Each library consumes only the properties that it understands.
|
|
159
|
+
|
|
160
|
+
For example:
|
|
161
|
+
|
|
162
|
+
Validation libraries use
|
|
163
|
+
|
|
164
|
+
* required
|
|
165
|
+
* format
|
|
166
|
+
* gt
|
|
167
|
+
* lt
|
|
168
|
+
* resource
|
|
169
|
+
* noValidate
|
|
170
|
+
|
|
171
|
+
Database libraries use
|
|
172
|
+
|
|
173
|
+
* noInsert
|
|
174
|
+
* noUpdate
|
|
175
|
+
* version
|
|
176
|
+
* createdAt
|
|
177
|
+
* updatedAt
|
|
178
|
+
* length
|
|
179
|
+
* type
|
|
180
|
+
|
|
181
|
+
The same metadata definition can therefore be used for
|
|
182
|
+
|
|
183
|
+
* Validation
|
|
184
|
+
* Database mapping
|
|
185
|
+
* CSV Import
|
|
186
|
+
* CSV Export
|
|
187
|
+
* Search
|
|
188
|
+
* Formatting
|
|
189
|
+
* Localization
|
|
190
|
+
|
|
191
|
+
without duplication.
|
|
192
|
+
|
|
193
|
+
---
|
|
194
|
+
|
|
195
|
+
# Shared Interfaces
|
|
196
|
+
|
|
197
|
+
`onecore` defines the common contracts used by the ecosystem.
|
|
198
|
+
|
|
199
|
+
## Database
|
|
200
|
+
|
|
201
|
+
* Repository
|
|
202
|
+
* GenericRepository
|
|
203
|
+
* SearchRepository
|
|
204
|
+
* Transaction
|
|
205
|
+
* Statement
|
|
206
|
+
* QueryBuilder
|
|
207
|
+
|
|
208
|
+
Implemented by
|
|
209
|
+
|
|
210
|
+
* sql-core
|
|
211
|
+
* mysql2-core
|
|
212
|
+
* postgres-kit
|
|
213
|
+
* mongodb-kit
|
|
214
|
+
|
|
215
|
+
---
|
|
216
|
+
|
|
217
|
+
## Validation
|
|
218
|
+
|
|
219
|
+
* Validator<T>
|
|
220
|
+
|
|
221
|
+
Implemented by
|
|
222
|
+
|
|
223
|
+
* validation-core
|
|
224
|
+
|
|
225
|
+
---
|
|
226
|
+
|
|
227
|
+
## Cache
|
|
228
|
+
|
|
229
|
+
* CachePort
|
|
230
|
+
|
|
231
|
+
Implemented by
|
|
232
|
+
|
|
233
|
+
* cache-plus
|
|
234
|
+
* redis-plus
|
|
235
|
+
|
|
236
|
+
---
|
|
237
|
+
|
|
238
|
+
## Message Queue
|
|
239
|
+
|
|
240
|
+
* Producer
|
|
241
|
+
* Consumer
|
|
242
|
+
* Publisher
|
|
243
|
+
* Subscriber
|
|
244
|
+
|
|
245
|
+
Implemented by
|
|
246
|
+
|
|
247
|
+
* message-processing
|
|
248
|
+
* redis-messaging
|
|
249
|
+
* nats-plus
|
|
250
|
+
* rabbitmq-transport
|
|
251
|
+
* ActiveMQ libraries
|
|
252
|
+
|
|
253
|
+
---
|
|
254
|
+
|
|
255
|
+
## Logging
|
|
256
|
+
|
|
257
|
+
* Logger
|
|
258
|
+
|
|
259
|
+
Implemented by
|
|
260
|
+
|
|
261
|
+
* logger-core
|
|
262
|
+
|
|
263
|
+
---
|
|
264
|
+
|
|
265
|
+
## Health Check
|
|
266
|
+
|
|
267
|
+
* HealthChecker
|
|
268
|
+
|
|
269
|
+
Implemented by
|
|
270
|
+
|
|
271
|
+
* health-service
|
|
272
|
+
|
|
273
|
+
---
|
|
274
|
+
|
|
275
|
+
## HTTP
|
|
276
|
+
|
|
277
|
+
* HttpRequest
|
|
278
|
+
* HttpOptionsService
|
|
279
|
+
|
|
280
|
+
Implemented by
|
|
281
|
+
|
|
282
|
+
* web-clients
|
|
283
|
+
|
|
284
|
+
---
|
|
285
|
+
|
|
286
|
+
## Localization
|
|
287
|
+
|
|
288
|
+
* Locale
|
|
289
|
+
* Currency
|
|
290
|
+
|
|
291
|
+
Implemented by
|
|
292
|
+
|
|
293
|
+
* locale-service
|
|
294
|
+
|
|
295
|
+
---
|
|
296
|
+
|
|
297
|
+
# Reusable Use Cases
|
|
298
|
+
|
|
299
|
+
`onecore` also provides reusable application-layer base classes.
|
|
300
|
+
|
|
301
|
+
Examples include
|
|
302
|
+
|
|
303
|
+
* CRUD services
|
|
304
|
+
* Search services
|
|
305
|
+
* View services
|
|
306
|
+
|
|
307
|
+
Applications can extend these classes instead of implementing common CRUD logic repeatedly.
|
|
308
|
+
|
|
309
|
+
Projects that do not use these classes pay no runtime cost.
|
|
310
|
+
|
|
311
|
+
---
|
|
312
|
+
|
|
313
|
+
# Frontend Support
|
|
314
|
+
|
|
315
|
+
`onecore` works in frontend applications.
|
|
316
|
+
|
|
317
|
+
React applications commonly use
|
|
318
|
+
|
|
319
|
+
* Attribute
|
|
320
|
+
* Locale
|
|
321
|
+
* Currency
|
|
322
|
+
* Validator interfaces
|
|
323
|
+
|
|
324
|
+
without importing any backend service classes.
|
|
325
|
+
|
|
326
|
+
The final JavaScript bundle remains minimal because interfaces are removed during compilation and unused code is tree-shaken.
|
|
327
|
+
|
|
328
|
+
---
|
|
329
|
+
|
|
330
|
+
# Backend Support
|
|
331
|
+
|
|
332
|
+
Infrastructure services often depend only on interfaces.
|
|
333
|
+
|
|
334
|
+
Examples include
|
|
335
|
+
|
|
336
|
+
* Message Queue services
|
|
337
|
+
* Import services
|
|
338
|
+
* Export services
|
|
339
|
+
* Background workers
|
|
340
|
+
|
|
341
|
+
Since these projects do not use application-layer base classes, the generated JavaScript contains virtually no runtime code from `onecore`.
|
|
342
|
+
|
|
343
|
+
---
|
|
344
|
+
|
|
345
|
+
# Sample Projects
|
|
346
|
+
|
|
347
|
+
The following sample applications demonstrate different ways of using `onecore`.
|
|
348
|
+
|
|
349
|
+
### CRUD Applications
|
|
350
|
+
|
|
351
|
+
* [**sql-modular-sample**](https://github.com/source-code-template/sql-modular-sample) — SQL modular microservice using MySQL
|
|
352
|
+
* [**sql-simple-modular-sample**](https://github.com/source-code-template/sql-simple-modular-sample) — SQL modular microservice using PosgreSQL
|
|
353
|
+
* [**mongo-simple-modular-sample**](https://github.com/source-code-template/mongo-simple-modular-sample) — MongoDB modular microservice
|
|
354
|
+
|
|
355
|
+
These projects extend the reusable CRUD and Search use-case classes.
|
|
356
|
+
|
|
357
|
+
### Import Data
|
|
358
|
+
- [import-sample](https://github.com/typescript-sample/import-sample): import a fix-length file to MySql.
|
|
359
|
+
- [import-csv-sample](https://github.com/typescript-sample/import-csv-sample): import a CSV file to MySql.
|
|
360
|
+
|
|
361
|
+
These projects depend only on interfaces and the shared `Attribute` metadata model.
|
|
362
|
+
|
|
363
|
+
### Export Data
|
|
364
|
+
- [postgres-export-sample](https://github.com/typescript-sample/postgres-export-sample): export data from Postgres to CSV.
|
|
365
|
+
- [mssql-export-sample](https://github.com/typescript-sample/mssql-export-sample): export data from MS SQL to CSV.
|
|
366
|
+
- [oracle-export-sample](https://github.com/typescript-sample/oracle-export-sample): export data from Oracle to CSV.
|
|
367
|
+
- [mysql-export-sample](https://github.com/typescript-sample/mysql-export-sample): export data from MySql to CSV.
|
|
368
|
+
|
|
369
|
+
These projects depend only on interfaces and the shared `Attribute` metadata model.
|
|
370
|
+
|
|
371
|
+
### Message Queue services
|
|
372
|
+
- [redis-messaging-sample](https://github.com/typescript-tutorial/redis-messaging-sample): An example to consume message from Redis.
|
|
373
|
+
- [rabbitmq-sample](https://github.com/typescript-tutorial/rabbitmq-sample): An example to consume message from rabbitmq.
|
|
374
|
+
- [activemq-sample](https://github.com/typescript-tutorial/activemq-sample): An example to consume message from activemq.
|
|
375
|
+
- [pubsub-sample](https://github.com/typescript-tutorial/pubsub-sample): An example to consume message from pubsub.
|
|
376
|
+
- [ibmmq-sample](https://github.com/typescript-tutorial/ibmmq-sample): An example to consume message from ibmmq.
|
|
377
|
+
- [kafka-sample](https://github.com/typescript-tutorial/kafka-sample): An example to consume message from kafka.
|
|
378
|
+
- [nats-sample](https://github.com/typescript-tutorial/nats-sample): An example to consume message from nats.
|
|
379
|
+
- [sqs-sample](https://github.com/typescript-tutorial/sqs-sample): An example to consume message from AWS sqs.
|
|
380
|
+
|
|
381
|
+
These projects depend only on interfaces and the shared `Attribute` metadata model.
|
|
382
|
+
|
|
383
|
+
---
|
|
384
|
+
|
|
385
|
+
# Design Principles
|
|
386
|
+
|
|
387
|
+
* Interface-first architecture
|
|
388
|
+
* Dependency inversion
|
|
389
|
+
* Clean Architecture
|
|
390
|
+
* Hexagonal Architecture
|
|
391
|
+
* Tree-shakeable design
|
|
392
|
+
* Shared metadata model
|
|
393
|
+
* Framework independent
|
|
394
|
+
* Enterprise ready
|
|
395
|
+
|
|
396
|
+
---
|
|
397
|
+
|
|
398
|
+
# License
|
|
399
|
+
|
|
400
|
+
MIT
|
package/package.json
CHANGED
package/src/cache.ts
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
export interface
|
|
1
|
+
export interface CachePort<K, V> {
|
|
2
2
|
isEnabled?(): boolean;
|
|
3
3
|
put(key: K, obj: V, expiresInSeconds?: number): Promise<boolean>;
|
|
4
4
|
expire(key: K, timeToLive: number): Promise<boolean>;
|
|
@@ -7,12 +7,12 @@ export interface CacheService<K, V> {
|
|
|
7
7
|
containsKey(key: K): Promise<boolean>;
|
|
8
8
|
remove(key: K): Promise<boolean>;
|
|
9
9
|
clear(): Promise<boolean>;
|
|
10
|
-
keys
|
|
11
|
-
count
|
|
12
|
-
size
|
|
10
|
+
keys(): Promise<string[]>;
|
|
11
|
+
count(): Promise<number>;
|
|
12
|
+
size(): Promise<number>;
|
|
13
13
|
}
|
|
14
14
|
|
|
15
|
-
export interface
|
|
15
|
+
export interface SyncCachePort<K, V> {
|
|
16
16
|
put(key: K, obj: V, expiresInMilliseconds?: number): boolean;
|
|
17
17
|
expire(key: K, timeToLive: number): boolean;
|
|
18
18
|
get(key: K): V;
|
|
@@ -20,6 +20,7 @@ export interface SyncCacheService<K, V> {
|
|
|
20
20
|
containsKey(key: K): boolean;
|
|
21
21
|
remove(key: K): boolean;
|
|
22
22
|
clear(): boolean;
|
|
23
|
-
keys
|
|
24
|
-
count
|
|
23
|
+
keys(): string[];
|
|
24
|
+
count(): number;
|
|
25
|
+
size(): number;
|
|
25
26
|
}
|
package/src/formatter.ts
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
export interface Locale {
|
|
2
|
-
id
|
|
2
|
+
id: string;
|
|
3
3
|
countryCode: string;
|
|
4
4
|
dateFormat: string;
|
|
5
5
|
firstDayOfWeek: number;
|
|
@@ -11,6 +11,11 @@ export interface Locale {
|
|
|
11
11
|
currencyPattern: number;
|
|
12
12
|
currencySample?: string;
|
|
13
13
|
}
|
|
14
|
+
export interface Currency {
|
|
15
|
+
code: string;
|
|
16
|
+
decimalDigits: number;
|
|
17
|
+
symbol: string;
|
|
18
|
+
}
|
|
14
19
|
|
|
15
20
|
export interface StringFormatter<T> {
|
|
16
21
|
format(obj: T): string;
|
package/src/index.ts
CHANGED
|
@@ -6,6 +6,10 @@ export * from './cache';
|
|
|
6
6
|
export * from './validator';
|
|
7
7
|
export * from './loader';
|
|
8
8
|
export * from './model';
|
|
9
|
+
export * from './health';
|
|
10
|
+
export * from './logger';
|
|
11
|
+
|
|
12
|
+
export * from './io';
|
|
9
13
|
|
|
10
14
|
import { GenericRepository, SearchRepository, GenericSearchRepository, Transaction } from './db';
|
|
11
15
|
import { GenericSearchService, GenericService } from './service';
|
|
@@ -22,9 +26,8 @@ export * from './mail/model/ASMOptions';
|
|
|
22
26
|
export * from './mail/config';
|
|
23
27
|
|
|
24
28
|
export * from './location';
|
|
29
|
+
export * from './job';
|
|
25
30
|
export * from './video';
|
|
26
|
-
export * from './health';
|
|
27
|
-
export * from './logger';
|
|
28
31
|
|
|
29
32
|
export type DeleteFile = (name: string, directory?: string) => Promise<boolean>;
|
|
30
33
|
export type Delete = (delFile: DeleteFile, url: string) => Promise<boolean>;
|
package/src/io.ts
ADDED
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
import { ErrorMessage } from "./model"
|
|
2
|
+
|
|
3
|
+
export interface Parser<T, S> {
|
|
4
|
+
parse: (data: S) => Promise<T>
|
|
5
|
+
}
|
|
6
|
+
export interface Transformer<T, S> {
|
|
7
|
+
transform: (data: S) => Promise<T>
|
|
8
|
+
}
|
|
9
|
+
|
|
10
|
+
export interface ICSVFieldParser<T> {
|
|
11
|
+
name: string
|
|
12
|
+
toString(data: T, key: string, v: string): void
|
|
13
|
+
}
|
|
14
|
+
|
|
15
|
+
export interface Writer<T> {
|
|
16
|
+
write: (obj: T) => Promise<number>
|
|
17
|
+
flush?: () => Promise<number>
|
|
18
|
+
}
|
|
19
|
+
export interface ErrorHandler<T> {
|
|
20
|
+
handleError(rs: T, errors: ErrorMessage[], i?: number, filename?: string): void
|
|
21
|
+
}
|
|
22
|
+
export interface ExceptionHandler<S> {
|
|
23
|
+
handleException(res: S, err: any, i?: number, filename?: string): void
|
|
24
|
+
}
|
package/src/job.ts
ADDED
|
@@ -0,0 +1,172 @@
|
|
|
1
|
+
import { DateRange, Filter, SearchResult, TimeRange } from "./model";
|
|
2
|
+
|
|
3
|
+
export interface Attachment {
|
|
4
|
+
originalFilename: string;
|
|
5
|
+
filename: string;
|
|
6
|
+
url: string;
|
|
7
|
+
size: number;
|
|
8
|
+
}
|
|
9
|
+
|
|
10
|
+
export interface Article {
|
|
11
|
+
id: string
|
|
12
|
+
slug: string
|
|
13
|
+
title: string
|
|
14
|
+
description?: string
|
|
15
|
+
publishedAt?: Date
|
|
16
|
+
tags?: string[]
|
|
17
|
+
thumbnail?: string
|
|
18
|
+
status?: string
|
|
19
|
+
createdAt?: Date
|
|
20
|
+
authorId?: string
|
|
21
|
+
savedAt?: Date
|
|
22
|
+
}
|
|
23
|
+
export interface ArticleFilter extends Filter {
|
|
24
|
+
id?: string
|
|
25
|
+
slug?: string
|
|
26
|
+
title?: string
|
|
27
|
+
description?: string
|
|
28
|
+
status?: string
|
|
29
|
+
publishedAt: TimeRange
|
|
30
|
+
tags?: string[]
|
|
31
|
+
authorId?: string
|
|
32
|
+
userId?: string
|
|
33
|
+
isSaved?: boolean
|
|
34
|
+
}
|
|
35
|
+
export interface ArticleRepository {
|
|
36
|
+
search(filter: ArticleFilter, limit: number, page?: number, fields?: string[]): Promise<SearchResult<Article>>
|
|
37
|
+
load(slug: string, userId?: string): Promise<Article | null>
|
|
38
|
+
getIdBySlug(slug: string): Promise<string>
|
|
39
|
+
}
|
|
40
|
+
|
|
41
|
+
export interface Achievement {
|
|
42
|
+
subject: string;
|
|
43
|
+
description: string;
|
|
44
|
+
}
|
|
45
|
+
export interface Skill {
|
|
46
|
+
skill: string;
|
|
47
|
+
hirable: boolean;
|
|
48
|
+
}
|
|
49
|
+
export interface UserFilter extends Filter {
|
|
50
|
+
userId?: string;
|
|
51
|
+
username?: string;
|
|
52
|
+
email?: string;
|
|
53
|
+
displayName?: string;
|
|
54
|
+
dateOfBirth?: DateRange;
|
|
55
|
+
status?: string[]|string;
|
|
56
|
+
interests?: string[];
|
|
57
|
+
skills?: Skill[];
|
|
58
|
+
achievements?: Achievement[];
|
|
59
|
+
}
|
|
60
|
+
export interface RoleFilter extends Filter {
|
|
61
|
+
roleId?: string;
|
|
62
|
+
roleName?: string;
|
|
63
|
+
status?: string[]|string;
|
|
64
|
+
remark?: string;
|
|
65
|
+
description?: string;
|
|
66
|
+
}
|
|
67
|
+
|
|
68
|
+
export interface ReviewComment {
|
|
69
|
+
commentId: string;
|
|
70
|
+
id: string;
|
|
71
|
+
author: string;
|
|
72
|
+
userId: string;
|
|
73
|
+
comment: string;
|
|
74
|
+
time: Date;
|
|
75
|
+
updatedAt?: Date;
|
|
76
|
+
histories?: ShortComment[];
|
|
77
|
+
userURL?: string;
|
|
78
|
+
authorURL?: string;
|
|
79
|
+
}
|
|
80
|
+
export interface ShortComment {
|
|
81
|
+
comment: string;
|
|
82
|
+
time: Date;
|
|
83
|
+
}
|
|
84
|
+
|
|
85
|
+
export interface ReviewCommentFilter extends Filter {
|
|
86
|
+
commentId?: string;
|
|
87
|
+
id?: string;
|
|
88
|
+
author?: string;
|
|
89
|
+
userId?: string;
|
|
90
|
+
comment?: string;
|
|
91
|
+
time?: DateRange;
|
|
92
|
+
updatedAt?: DateRange;
|
|
93
|
+
}
|
|
94
|
+
export interface Info {
|
|
95
|
+
id: string;
|
|
96
|
+
rate: number;
|
|
97
|
+
rate1: number;
|
|
98
|
+
rate2: number;
|
|
99
|
+
rate3: number;
|
|
100
|
+
rate4: number;
|
|
101
|
+
rate5: number;
|
|
102
|
+
count: number;
|
|
103
|
+
score: number;
|
|
104
|
+
}
|
|
105
|
+
export interface Info10 {
|
|
106
|
+
id: string;
|
|
107
|
+
rate: number;
|
|
108
|
+
rate1: number;
|
|
109
|
+
rate2: number;
|
|
110
|
+
rate3: number;
|
|
111
|
+
rate4: number;
|
|
112
|
+
rate5: number;
|
|
113
|
+
rate6: number;
|
|
114
|
+
rate7: number;
|
|
115
|
+
rate8: number;
|
|
116
|
+
rate9: number;
|
|
117
|
+
rate10: number;
|
|
118
|
+
count: number;
|
|
119
|
+
score: number;
|
|
120
|
+
}
|
|
121
|
+
export interface InfoRepository<ID> {
|
|
122
|
+
exist(id: ID, ctx?: any): Promise<boolean>;
|
|
123
|
+
}
|
|
124
|
+
|
|
125
|
+
export interface Company {
|
|
126
|
+
id: string
|
|
127
|
+
slug: string
|
|
128
|
+
name: string
|
|
129
|
+
overview: string
|
|
130
|
+
website?: string
|
|
131
|
+
industry?: string
|
|
132
|
+
size?: string
|
|
133
|
+
logo?: string
|
|
134
|
+
coverURL?: string
|
|
135
|
+
status: string
|
|
136
|
+
|
|
137
|
+
followerCount?: number
|
|
138
|
+
followingAt?: Date
|
|
139
|
+
followedAt?: Date
|
|
140
|
+
}
|
|
141
|
+
|
|
142
|
+
export interface Job {
|
|
143
|
+
id: string
|
|
144
|
+
slug: string
|
|
145
|
+
title: string
|
|
146
|
+
description: string
|
|
147
|
+
publishedAt?: Date
|
|
148
|
+
expiredAt?: Date
|
|
149
|
+
position?: string
|
|
150
|
+
quantity?: number
|
|
151
|
+
location?: string
|
|
152
|
+
applicantCount?: number
|
|
153
|
+
skills?: string[]
|
|
154
|
+
minSalary?: number
|
|
155
|
+
maxSalary?: number
|
|
156
|
+
companyId?: string
|
|
157
|
+
status: string
|
|
158
|
+
}
|
|
159
|
+
export interface JobFilter extends Filter {
|
|
160
|
+
id?: string
|
|
161
|
+
slug?: string
|
|
162
|
+
title?: string
|
|
163
|
+
description?: string
|
|
164
|
+
publishedAt?: TimeRange
|
|
165
|
+
expiredAt?: TimeRange
|
|
166
|
+
skills?: string[]
|
|
167
|
+
location?: string
|
|
168
|
+
quantity?: number
|
|
169
|
+
applicantCount?: number
|
|
170
|
+
companyId?: string
|
|
171
|
+
status?: string
|
|
172
|
+
}
|
package/src/location.ts
CHANGED
|
@@ -1,27 +1,5 @@
|
|
|
1
1
|
import {DateRange, Filter, NumberRange} from './model';
|
|
2
2
|
|
|
3
|
-
export interface Article {
|
|
4
|
-
id: string
|
|
5
|
-
slug: string
|
|
6
|
-
title: string
|
|
7
|
-
description?: string
|
|
8
|
-
content?: string
|
|
9
|
-
publishedAt?: Date
|
|
10
|
-
tags?: string[]
|
|
11
|
-
thumbnail?: string
|
|
12
|
-
status?: string
|
|
13
|
-
createdAt?: Date
|
|
14
|
-
authorId?: string
|
|
15
|
-
savedAt?: Date
|
|
16
|
-
}
|
|
17
|
-
export interface ArticleFilter extends Filter {
|
|
18
|
-
id?: string;
|
|
19
|
-
title?: string;
|
|
20
|
-
type?: string;
|
|
21
|
-
tags?: string[];
|
|
22
|
-
status?: string[]|string;
|
|
23
|
-
}
|
|
24
|
-
|
|
25
3
|
export interface Location {
|
|
26
4
|
id?: string;
|
|
27
5
|
name?: string;
|
package/src/logger.ts
CHANGED
|
@@ -1,5 +1,8 @@
|
|
|
1
|
+
export interface NumberMap {
|
|
2
|
+
[key: string]: number;
|
|
3
|
+
}
|
|
1
4
|
export interface SimpleMap {
|
|
2
|
-
[key: string]: string|number|boolean|Date;
|
|
5
|
+
[key: string]: string | number | boolean | Date;
|
|
3
6
|
}
|
|
4
7
|
export interface LogMap {
|
|
5
8
|
time: string;
|
|
@@ -11,8 +14,30 @@ export interface LogMapConfig {
|
|
|
11
14
|
level?: string;
|
|
12
15
|
msg?: string;
|
|
13
16
|
}
|
|
17
|
+
export interface Config {
|
|
18
|
+
level?: string;
|
|
19
|
+
map?: LogMapConfig;
|
|
20
|
+
constants?: SimpleMap;
|
|
21
|
+
name?: Name;
|
|
22
|
+
}
|
|
23
|
+
export type LogConf = Config;
|
|
24
|
+
export interface LogConfig {
|
|
25
|
+
log: Config;
|
|
26
|
+
}
|
|
27
|
+
export interface Name {
|
|
28
|
+
trace: string;
|
|
29
|
+
debug: string;
|
|
30
|
+
info: string;
|
|
31
|
+
warn: string;
|
|
32
|
+
error: string;
|
|
33
|
+
panic: string;
|
|
34
|
+
fatal: string;
|
|
35
|
+
}
|
|
14
36
|
export interface Logger {
|
|
37
|
+
name: Name;
|
|
15
38
|
level: number;
|
|
39
|
+
map: LogMap;
|
|
40
|
+
constants?: SimpleMap;
|
|
16
41
|
trace(msg: string, m?: SimpleMap, ctx?: any): void;
|
|
17
42
|
debug(msg: string, m?: SimpleMap, ctx?: any): void;
|
|
18
43
|
info(msg: string, m?: SimpleMap, ctx?: any): void;
|
package/src/model.ts
CHANGED
|
@@ -1,3 +1,5 @@
|
|
|
1
|
+
import { Transaction } from "./db";
|
|
2
|
+
|
|
1
3
|
export interface Headers {
|
|
2
4
|
[key: string]: any;
|
|
3
5
|
}
|
|
@@ -125,9 +127,6 @@ export interface ErrorMessage {
|
|
|
125
127
|
param?: string|number|Date;
|
|
126
128
|
message?: string;
|
|
127
129
|
}
|
|
128
|
-
export interface ErrorHandler<T> {
|
|
129
|
-
handleError(rs: T, errors: ErrorMessage[], i?: number, filename?: string): void;
|
|
130
|
-
}
|
|
131
130
|
|
|
132
131
|
export interface ResultInfo<T> {
|
|
133
132
|
status: number|string;
|
|
@@ -149,143 +148,31 @@ export interface User {
|
|
|
149
148
|
url?: string;
|
|
150
149
|
}
|
|
151
150
|
export interface History<T> {
|
|
152
|
-
id: string
|
|
153
|
-
|
|
154
|
-
time: Date
|
|
151
|
+
id: string
|
|
152
|
+
author: string
|
|
153
|
+
time: Date
|
|
154
|
+
action: string
|
|
155
|
+
data: T
|
|
155
156
|
user: User;
|
|
156
157
|
note?: string;
|
|
157
158
|
}
|
|
158
|
-
|
|
159
|
-
id: string;
|
|
160
|
-
time: Date;
|
|
161
|
-
notifier?: User;
|
|
162
|
-
message: string;
|
|
163
|
-
url?: string;
|
|
164
|
-
read: boolean;
|
|
165
|
-
}
|
|
166
|
-
export interface Attachment {
|
|
167
|
-
originalFilename: string;
|
|
168
|
-
filename: string;
|
|
169
|
-
url: string;
|
|
170
|
-
size: number;
|
|
171
|
-
}
|
|
172
|
-
export interface Achievement {
|
|
173
|
-
subject: string;
|
|
174
|
-
description: string;
|
|
175
|
-
}
|
|
176
|
-
export interface Skill {
|
|
177
|
-
skill: string;
|
|
178
|
-
hirable: boolean;
|
|
179
|
-
}
|
|
180
|
-
export interface UserFilter extends Filter {
|
|
181
|
-
userId?: string;
|
|
182
|
-
username?: string;
|
|
183
|
-
email?: string;
|
|
184
|
-
displayName?: string;
|
|
185
|
-
dateOfBirth?: DateRange;
|
|
186
|
-
status?: string[]|string;
|
|
187
|
-
interests?: string[];
|
|
188
|
-
skills?: Skill[];
|
|
189
|
-
achievements?: Achievement[];
|
|
190
|
-
}
|
|
191
|
-
export interface RoleFilter extends Filter {
|
|
192
|
-
roleId?: string;
|
|
193
|
-
roleName?: string;
|
|
194
|
-
status?: string[]|string;
|
|
195
|
-
remark?: string;
|
|
196
|
-
description?: string;
|
|
197
|
-
}
|
|
159
|
+
|
|
198
160
|
export type Validate<T> = (obj: T, patch?: boolean) => Promise<ErrorMessage[]>;
|
|
199
161
|
export type Save<T> = (obj: T, ctx?: any) => Promise<number|ResultInfo<T>>;
|
|
200
162
|
export type Load<T, ID> = ((id: ID, ctx?: any) => Promise<T|null>);
|
|
201
163
|
|
|
202
|
-
export interface
|
|
203
|
-
|
|
204
|
-
|
|
205
|
-
|
|
206
|
-
|
|
207
|
-
|
|
208
|
-
|
|
209
|
-
|
|
210
|
-
|
|
211
|
-
|
|
212
|
-
|
|
213
|
-
|
|
214
|
-
|
|
215
|
-
|
|
216
|
-
time: Date;
|
|
217
|
-
}
|
|
218
|
-
|
|
219
|
-
export interface ReviewCommentFilter extends Filter {
|
|
220
|
-
commentId?: string;
|
|
221
|
-
id?: string;
|
|
222
|
-
author?: string;
|
|
223
|
-
userId?: string;
|
|
224
|
-
comment?: string;
|
|
225
|
-
time?: DateRange;
|
|
226
|
-
updatedAt?: DateRange;
|
|
227
|
-
}
|
|
228
|
-
export interface Info {
|
|
229
|
-
id: string;
|
|
230
|
-
rate: number;
|
|
231
|
-
rate1: number;
|
|
232
|
-
rate2: number;
|
|
233
|
-
rate3: number;
|
|
234
|
-
rate4: number;
|
|
235
|
-
rate5: number;
|
|
236
|
-
count: number;
|
|
237
|
-
score: number;
|
|
238
|
-
}
|
|
239
|
-
export interface Info10 {
|
|
240
|
-
id: string;
|
|
241
|
-
rate: number;
|
|
242
|
-
rate1: number;
|
|
243
|
-
rate2: number;
|
|
244
|
-
rate3: number;
|
|
245
|
-
rate4: number;
|
|
246
|
-
rate5: number;
|
|
247
|
-
rate6: number;
|
|
248
|
-
rate7: number;
|
|
249
|
-
rate8: number;
|
|
250
|
-
rate9: number;
|
|
251
|
-
rate10: number;
|
|
252
|
-
count: number;
|
|
253
|
-
score: number;
|
|
254
|
-
}
|
|
255
|
-
export interface InfoRepository<ID> {
|
|
256
|
-
exist(id: ID, ctx?: any): Promise<boolean>;
|
|
257
|
-
}
|
|
258
|
-
|
|
259
|
-
export interface Company {
|
|
260
|
-
id: string
|
|
261
|
-
slug: string
|
|
262
|
-
name: string
|
|
263
|
-
overview: string
|
|
264
|
-
website?: string
|
|
265
|
-
industry?: string
|
|
266
|
-
size?: string
|
|
267
|
-
logo?: string
|
|
268
|
-
coverURL?: string
|
|
269
|
-
status: string
|
|
270
|
-
|
|
271
|
-
followerCount?: number
|
|
272
|
-
followingAt?: Date
|
|
273
|
-
followedAt?: Date
|
|
274
|
-
}
|
|
275
|
-
export interface Job {
|
|
276
|
-
id: string
|
|
277
|
-
slug: string
|
|
278
|
-
title: string
|
|
279
|
-
description: string
|
|
280
|
-
publishedAt?: Date
|
|
281
|
-
expiredAt?: Date
|
|
282
|
-
position?: string
|
|
283
|
-
quantity?: number
|
|
284
|
-
location?: string
|
|
285
|
-
applicantCount?: number
|
|
286
|
-
skills?: string[]
|
|
287
|
-
minSalary?: number
|
|
288
|
-
maxSalary?: number
|
|
289
|
-
companyId?: string
|
|
290
|
-
status: string
|
|
164
|
+
export interface Notification {
|
|
165
|
+
id?: string
|
|
166
|
+
sender: string
|
|
167
|
+
receiver: string
|
|
168
|
+
url?: string
|
|
169
|
+
message: string
|
|
170
|
+
}
|
|
171
|
+
export interface NotificationPort {
|
|
172
|
+
push(notification: Notification): Promise<number>
|
|
173
|
+
pushNotifications(notifications: Notification[]): Promise<number>
|
|
174
|
+
}
|
|
175
|
+
export interface NotificationRepository {
|
|
176
|
+
push(notification: Notification): Promise<number>
|
|
177
|
+
pushNotifications(notifications: Notification[]): Promise<number>
|
|
291
178
|
}
|
package/src/mq.ts
CHANGED
|
@@ -4,7 +4,8 @@ interface StringMap {
|
|
|
4
4
|
export interface NumberMap {
|
|
5
5
|
[key: number]: number;
|
|
6
6
|
}
|
|
7
|
-
export type
|
|
7
|
+
export type Process<T, R, M> = (data: T, attributes?: StringMap, msg?: M) => Promise<R>
|
|
8
|
+
export type Handle<T, R, M> = (data: T, attributes?: StringMap, msg?: M) => Promise<R>
|
|
8
9
|
export type Consume<T> = (handle: (data: T, header?: StringMap) => Promise<number>) => void;
|
|
9
10
|
export type Read<T> = Consume<T>;
|
|
10
11
|
export type Subscribe<T> = Consume<T>;
|
|
@@ -39,9 +40,6 @@ export interface Publisher<T, R, ID> {
|
|
|
39
40
|
export interface Sender<T, R, ID> {
|
|
40
41
|
send(data: T, attributes?: StringMap, id?: ID): Promise<R>;
|
|
41
42
|
}
|
|
42
|
-
export interface Writer<T, R, ID> {
|
|
43
|
-
write(data: T, attributes?: StringMap, id?: ID): Promise<R>;
|
|
44
|
-
}
|
|
45
43
|
|
|
46
44
|
export interface Producer<T, R, ID> {
|
|
47
45
|
produce(to: string, data: T, attributes?: StringMap, id?: ID): Promise<R>;
|
|
@@ -52,10 +50,11 @@ export interface Publisher<T, R, ID> {
|
|
|
52
50
|
export interface Sender<T, R, ID> {
|
|
53
51
|
send(to: string, data: T, attributes?: StringMap, id?: ID): Promise<R>;
|
|
54
52
|
}
|
|
53
|
+
/*
|
|
55
54
|
export interface Writer<T, R, ID> {
|
|
56
55
|
write(to: string, data: T, attributes?: StringMap, id?: ID): Promise<R>;
|
|
57
56
|
}
|
|
58
|
-
|
|
57
|
+
*/
|
|
59
58
|
export interface SimpleConsumer<T, R> {
|
|
60
59
|
consume(handle: (data: T, attributes?: StringMap, raw?: R) => Promise<number>): void;
|
|
61
60
|
}
|
package/src/validator.ts
CHANGED
|
@@ -4,11 +4,13 @@ interface ErrorMessage {
|
|
|
4
4
|
param?: string|number|Date;
|
|
5
5
|
message?: string;
|
|
6
6
|
}
|
|
7
|
-
|
|
7
|
+
export interface StringMap {
|
|
8
|
+
[key: string]: string;
|
|
9
|
+
}
|
|
8
10
|
export interface Validator<T> {
|
|
9
|
-
validate(model: T,
|
|
11
|
+
validate(model: T, resource?: StringMap, patch?: boolean): Promise<ErrorMessage[]>;
|
|
10
12
|
}
|
|
11
13
|
|
|
12
14
|
export interface SyncValidator<T> {
|
|
13
|
-
validate(model: T,
|
|
15
|
+
validate(model: T, resource?: StringMap, patch?: boolean): ErrorMessage[];
|
|
14
16
|
}
|
package/src/video.ts
CHANGED