@togatherlabs/shared-utils 1.0.10 → 1.1.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 CHANGED
@@ -1,175 +1,250 @@
1
1
  # @togatherlabs/shared-utils
2
2
 
3
- A collection of **shared TypeScript utilities, constants, and types** used across ToGather microservices.
3
+ Shared utilities library for Togather services, providing production-grade utilities including logger, validators, and common helpers.
4
4
 
5
- [![npm package](https://img.shields.io/npm/v/@togatherlabs/shared-utils.svg)](https://www.npmjs.com/package/@togatherlabs/shared-utils)
6
- [![npm downloads](https://img.shields.io/npm/dm/@togatherlabs/shared-utils.svg)](https://www.npmjs.com/package/@togatherlabs/shared-utils)
7
- [![license](https://img.shields.io/npm/l/@togatherlabs/shared-utils.svg)](./LICENSE)
5
+ ## 📦 Installation
8
6
 
9
- ## Table of Contents
7
+ ```bash
8
+ pnpm add @togatherlabs/shared-utils
9
+ ```
10
10
 
11
- 1. [Directory Structure](#directory-structure)
12
- 2. [Package Development](#package-development)
11
+ ## 🚀 Features
13
12
 
14
- * [Adding New Utilities](#adding-new-utilities)
15
- * [Linting](#linting)
16
- * [Building](#building)
17
- * [Publishing Package](#publishing-package)
18
- 3. [Using the Utilities](#using-the-utilities)
13
+ ### Logger Module
14
+ Production-ready logging built on [Pino](https://getpino.io/) with:
15
+ - 🔒 Automatic sensitive data redaction
16
+ - 📊 Structured logging with context
17
+ - 🎨 Environment-aware (pretty dev logs, JSON production logs)
18
+ - 🔧 Fully configurable
19
+ - ⚡ High performance
19
20
 
20
- * [TypeScript](#typescript)
21
- 4. [Best Practices](#best-practices)
22
- 5. [Troubleshooting](#troubleshooting)
23
- 6. [License](#license)
21
+ ## 📚 Available Modules
24
22
 
25
- ## Directory Structure
23
+ ### Logger
26
24
 
27
- The package follows a **clear folder structure** for maintainability:
25
+ ```typescript
26
+ import { PinoLogger, ILogger } from '@togatherlabs/shared-utils/logger';
28
27
 
28
+ const logger = new PinoLogger();
29
+
30
+ logger.info({ label: 'app' }, 'Application started');
31
+ logger.error({ err, label: 'database' }, 'Connection failed');
29
32
  ```
30
- src/
31
- ├── constants/
32
- │ └── index.ts
33
- ├── utils/
34
- │ └── index.ts
35
- ├── types/
36
- │ └── index.ts
37
- └── index.ts
33
+
34
+ **Full documentation**: [Logger README](./src/logger/README.md)
35
+
36
+ ## 🔧 Usage
37
+
38
+ ### Basic Import
39
+
40
+ ```typescript
41
+ // Import from main entry point
42
+ import { PinoLogger, ILogger } from '@togatherlabs/shared-utils';
43
+
44
+ // Or import from specific module
45
+ import { PinoLogger, ILogger } from '@togatherlabs/shared-utils/logger';
38
46
  ```
39
47
 
40
- * **constants**: Shared constants across services
41
- * **utils**: Reusable utility functions
42
- * **types**: Shared TypeScript types and interfaces
43
- * **index.ts**: Exports all public utilities
48
+ ### Environment Variables
44
49
 
45
- ## Package Development
50
+ **All environment variables are optional.** The logger works with sensible defaults:
46
51
 
47
- ### Adding New Utilities
52
+ - `NODE_ENV` - Set to `production` in production (default: `development`)
53
+ - `SERVICE_NAME` - Your service name for log context (default: `undefined`)
54
+ - `LOG_LEVEL` - Log level: `trace`, `debug`, `info`, `warn`, `error`, `fatal` (default: `info`)
55
+ - `HOSTNAME` - Override hostname (default: OS hostname)
48
56
 
49
- 1. Add your function, constant, or type in the appropriate folder (`utils`, `constants`, or `types`).
50
- 2. Export it from the folder’s `index.ts`.
51
- 3. Re-export from the root `index.ts` for public usage.
57
+ See the [Logger README](./src/logger/README.md) for detailed configuration options.
52
58
 
53
- **Example:** Adding a new utility `capitalize`:
59
+ ### With Dependency Injection
54
60
 
55
- ```ts
56
- // src/utils/capitalize.ts
57
- export function capitalize(str: string): string {
58
- return str.charAt(0).toUpperCase() + str.slice(1);
59
- }
61
+ ```typescript
62
+ import { injectable, inject } from 'inversify';
63
+ import type { ILogger } from '@togatherlabs/shared-utils/logger';
60
64
 
61
- // src/utils/index.ts
62
- export * from './capitalize';
65
+ @injectable()
66
+ class UserService {
67
+ constructor(
68
+ @inject(TYPES.Logger) private logger: ILogger
69
+ ) {}
63
70
 
64
- // src/index.ts
65
- export * from './utils';
71
+ async createUser(data: CreateUserDTO) {
72
+ this.logger.info({ userId: data.id, label: 'UserService' }, 'Creating user');
73
+ // ... implementation
74
+ }
75
+ }
66
76
  ```
67
77
 
68
- ### Linting
78
+ ## 🛠️ Development
69
79
 
70
- Check code style and catch errors using Biome:
80
+ ### Setup
71
81
 
72
82
  ```bash
73
- pnpm lint
74
- pnpm lint:fix
75
- ```
83
+ # Install dependencies
84
+ pnpm install
76
85
 
77
- ### Building
86
+ # Build the library
87
+ pnpm run build
78
88
 
79
- Compile TypeScript into the `dist/` folder:
89
+ # Run type checking
90
+ pnpm run typecheck
80
91
 
81
- ```bash
82
- pnpm build
92
+ # Run linting
93
+ pnpm run lint
94
+
95
+ # Format code
96
+ pnpm run format
83
97
  ```
84
98
 
85
- Check types without generating output:
99
+ ### Project Structure
86
100
 
87
- ```bash
88
- pnpm typecheck
89
101
  ```
102
+ togather-shared-utils/
103
+ ├── src/
104
+ │ ├── logger/ # Logger module
105
+ │ │ ├── ILogger.ts # Logger interface
106
+ │ │ ├── PinoLogger.ts # Pino implementation
107
+ │ │ ├── index.ts # Module exports
108
+ │ │ └── README.md # Logger documentation
109
+ │ └── index.ts # Main library exports
110
+ ├── dist/ # Compiled output (generated)
111
+ ├── scripts/ # Publishing scripts
112
+ │ ├── publish.js # NPM publishing script
113
+ │ └── version.js # Version bumping script
114
+ ├── package.json
115
+ ├── tsconfig.json
116
+ ├── biome.json
117
+ └── README.md
118
+ ```
119
+
120
+ ## 📤 Publishing
90
121
 
91
- ### Publishing Package
122
+ ### Version Bumping
92
123
 
93
- To publish the package to npm:
124
+ ```bash
125
+ # Bump patch version (1.0.0 -> 1.0.1) for bug fixes
126
+ pnpm run version:patch
127
+
128
+ # Bump minor version (1.0.0 -> 1.1.0) for new features
129
+ pnpm run version:minor
130
+
131
+ # Bump major version (1.0.0 -> 2.0.0) for breaking changes
132
+ pnpm run version:major
133
+ ```
134
+
135
+ ### Publishing to NPM
94
136
 
95
137
  ```bash
96
- pnpm run release
138
+ # Dry run (test publishing without actually publishing)
139
+ pnpm run publish:npm -- --dry-run
140
+
141
+ # Publish to npm with 'latest' tag
142
+ pnpm run publish:npm
143
+
144
+ # Publish with a specific tag (e.g., beta)
145
+ pnpm run publish:npm -- --tag beta
97
146
  ```
98
147
 
99
- This script performs:
148
+ The publish script automatically:
149
+ - ✅ Checks git status
150
+ - ✅ Runs type checking
151
+ - ✅ Runs linting
152
+ - ✅ Builds the package
153
+ - ✅ Checks if version already exists
154
+ - ✅ Publishes to npm
155
+ - ✅ Creates and pushes git tag
100
156
 
101
- * Builds the package
102
- * Commits changes
103
- * Updates version (patch/minor/major)
104
- * Publishes to npm with public access
157
+ ## 🔄 Workflow
105
158
 
106
- Ensure all changes are committed and tests pass before publishing.
159
+ ### Adding a New Feature
107
160
 
108
- ## Using the Utilities
161
+ 1. Create a new branch
162
+ ```bash
163
+ git checkout -b feat/new-utility
164
+ ```
109
165
 
110
- ### TypeScript
166
+ 2. Make your changes and commit
167
+ ```bash
168
+ git add .
169
+ pnpm run commit # Uses commitizen for conventional commits
170
+ ```
111
171
 
112
- Install the package:
172
+ 3. Bump version
173
+ ```bash
174
+ pnpm run version:minor # or patch/major
175
+ ```
113
176
 
114
- ```bash
115
- pnpm add @togatherlabs/shared-utils
116
- ```
177
+ 4. Push changes
178
+ ```bash
179
+ git push origin feat/new-utility
180
+ git push --tags
181
+ ```
182
+
183
+ 5. Publish to npm
184
+ ```bash
185
+ pnpm run publish:npm
186
+ ```
117
187
 
118
- Example usage:
188
+ ## 📋 Commit Convention
119
189
 
120
- ```ts
121
- import { formatDate, generateId, logger } from '@togatherlabs/shared-utils';
190
+ This project uses [Conventional Commits](https://www.conventionalcommits.org/):
191
+
192
+ ```
193
+ <type>(<scope>): <subject>
122
194
 
123
- // Format a date
124
- console.log(formatDate(new Date()));
195
+ <body>
196
+ ```
125
197
 
126
- // Generate a unique ID
127
- const id = generateId();
128
- console.log(id);
198
+ **Types:**
199
+ - `feat`: New feature
200
+ - `fix`: Bug fix
201
+ - `docs`: Documentation changes
202
+ - `style`: Code style changes (formatting)
203
+ - `refactor`: Code refactoring
204
+ - `test`: Adding or updating tests
205
+ - `chore`: Maintenance tasks
129
206
 
130
- // Log messages
131
- logger.info('Service started');
132
- logger.error('Failed to fetch data', { error: new Error('Network error') });
207
+ **Example:**
133
208
  ```
209
+ feat(logger): Add support for custom log formatters
134
210
 
135
- ## Best Practices
211
+ Added a new option to PinoLogger constructor that allows users to
212
+ provide custom formatters for log messages. This enables better
213
+ integration with external logging services.
214
+ ```
136
215
 
137
- * Keep utilities small and focused each function should have a single responsibility.
138
- * Type safety – use TypeScript types/interfaces, avoid `any`.
139
- * Documentation – add JSDoc comments for each utility.
140
- * Testing – write unit tests for every new utility.
141
- * Consistent exports – always export utilities through `index.ts` files.
216
+ Use `pnpm run commit` for an interactive commit prompt.
142
217
 
143
- ## Troubleshooting
218
+ ## 🧪 Testing
144
219
 
145
- **Cannot find module '@togatherlabs/shared-utils'**
220
+ ```bash
221
+ # Run tests (when available)
222
+ pnpm test
146
223
 
147
- * Ensure the package is installed
148
- * Check `tsconfig.json` paths if using path aliases
149
- * Delete `node_modules` and reinstall dependencies
224
+ # Run tests with coverage
225
+ pnpm test:coverage
226
+ ```
150
227
 
151
- **Property 'myFunction' does not exist**
228
+ ## 📖 Documentation
152
229
 
153
- * Ensure the function is exported correctly
154
- * Verify the import path matches the package export
230
+ - [Logger Documentation](./src/logger/README.md)
155
231
 
156
- **Build errors**
232
+ ## 🤝 Contributing
157
233
 
158
- * Check for missing peer dependencies
159
- * Ensure relative imports are correct
160
- * Clean and rebuild the project
234
+ 1. Follow the commit convention
235
+ 2. Write tests for new features
236
+ 3. Update documentation
237
+ 4. Ensure all checks pass before publishing
161
238
 
162
- **Version mismatches across services**
239
+ ## 📄 License
163
240
 
164
- * Make sure all services use compatible versions of shared-utils
165
- * Check changelog for breaking changes
241
+ Internal use only - Togather Infrastructure
166
242
 
167
- **TypeScript declaration errors**
243
+ ## 🆘 Support
168
244
 
169
- * Ensure `declaration: true` is set in `tsconfig.json`
170
- * Verify the `types` field in `package.json` points to the correct declaration file
171
- * Run `pnpm build` to regenerate type definitions
245
+ For questions or issues, contact the platform team.
172
246
 
173
- ## License
247
+ ## 🔗 Related Packages
174
248
 
175
- MIT © ToGather Labs
249
+ - [@togatherlabs/shared-protos](../togather-shared-protos) - Shared Protocol Buffers
250
+ - [@togatherlabs/event-sdk](../togather-shared-events) - Event handling SDK
package/dist/index.d.ts CHANGED
@@ -1,4 +1,2 @@
1
- export * from "./constants/index.js";
2
- export * from "./helpers/index.js";
3
- export * from "./types/index.js";
1
+ export * from './logger/index.js';
4
2
  //# sourceMappingURL=index.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,cAAc,sBAAsB,CAAC;AACrC,cAAc,oBAAoB,CAAC;AACnC,cAAc,kBAAkB,CAAC"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AACA,cAAc,mBAAmB,CAAC"}
package/dist/index.js CHANGED
@@ -1,3 +1,3 @@
1
- export * from "./constants/index.js";
2
- export * from "./helpers/index.js";
3
- export * from "./types/index.js";
1
+ // Main library exports
2
+ export * from './logger/index.js';
3
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,uBAAuB;AACvB,cAAc,mBAAmB,CAAC"}
@@ -0,0 +1,98 @@
1
+ /**
2
+ * Logger interface for structured logging.
3
+ * Supports all standard log levels and child logger creation for contextual logging.
4
+ */
5
+ export interface ILogger {
6
+ /**
7
+ * Log informational messages
8
+ *
9
+ * @param labels - Context object that can include:
10
+ * - `label`: string | string[] - Categorization labels (e.g., class name, method name, operation type)
11
+ * - Any other contextual data (userId, requestId, etc.)
12
+ * @param msg - Human-readable log message (supports string interpolation with args)
13
+ * @param args - Values for string interpolation in the message (e.g., logger.info({}, 'User %s logged in', userId))
14
+ *
15
+ * @example
16
+ * logger.info({ label: 'UserService' }, 'User created');
17
+ * logger.info({ label: ['UserService', 'createUser'] }, 'Creating user');
18
+ * logger.info({ userId: '123', label: 'UserService.createUser' }, 'User created successfully');
19
+ * logger.info({ label: 'UserService' }, 'User %s created with email %s', userId, email);
20
+ */
21
+ info(labels: object | string, msg?: string, ...args: unknown[]): void;
22
+ /**
23
+ * Log warning messages
24
+ *
25
+ * @param labels - Context object that can include:
26
+ * - `label`: string | string[] - Categorization labels (e.g., class name, method name, operation type)
27
+ * - Any other contextual data (userId, requestId, etc.)
28
+ * @param msg - Human-readable log message (supports string interpolation with args)
29
+ * @param args - Values for string interpolation in the message
30
+ *
31
+ * @example
32
+ * logger.warn({ label: 'RateLimiter' }, 'Rate limit approaching');
33
+ * logger.warn({ userId: '123', label: ['AuthService', 'login'] }, 'Multiple failed attempts');
34
+ * logger.warn({ label: 'RateLimiter' }, 'User %s exceeded %d requests', userId, maxRequests);
35
+ */
36
+ warn(labels: object | string, msg?: string, ...args: unknown[]): void;
37
+ /**
38
+ * Log error messages
39
+ *
40
+ * @param labels - Context object that can include:
41
+ * - `label`: string | string[] - Categorization labels (e.g., class name, method name, operation type)
42
+ * - `err`: Error - The error object for proper serialization
43
+ * - Any other contextual data (userId, requestId, etc.)
44
+ * @param msg - Human-readable log message (supports string interpolation with args)
45
+ * @param args - Values for string interpolation in the message
46
+ *
47
+ * @example
48
+ * logger.error({ err, label: 'DatabaseService' }, 'Connection failed');
49
+ * logger.error({ err, userId: '123', label: ['UserRepository', 'findById'] }, 'Query failed');
50
+ * logger.error({ err, label: 'DatabaseService' }, 'Failed to connect to %s on port %d', host, port);
51
+ */
52
+ error(labels: object | string, msg?: string, ...args: unknown[]): void;
53
+ /**
54
+ * Log debug messages
55
+ *
56
+ * @param labels - Context object that can include:
57
+ * - `label`: string | string[] - Categorization labels (e.g., class name, method name, operation type)
58
+ * - Any other contextual data (userId, requestId, etc.)
59
+ * @param msg - Human-readable log message (supports string interpolation with args)
60
+ * @param args - Values for string interpolation in the message
61
+ *
62
+ * @example
63
+ * logger.debug({ label: 'CacheService' }, 'Cache hit');
64
+ * logger.debug({ cacheKey: 'user:123', label: ['CacheService', 'get'] }, 'Retrieved from cache');
65
+ * logger.debug({ label: 'CacheService' }, 'Cache hit for key %s in %dms', cacheKey, duration);
66
+ */
67
+ debug(labels: object | string, msg?: string, ...args: unknown[]): void;
68
+ /**
69
+ * Log fatal messages (highest severity)
70
+ *
71
+ * @param labels - Context object that can include:
72
+ * - `label`: string | string[] - Categorization labels (e.g., class name, method name, operation type)
73
+ * - `err`: Error - The error object for proper serialization
74
+ * - Any other contextual data (userId, requestId, etc.)
75
+ * @param msg - Human-readable log message (supports string interpolation with args)
76
+ * @param args - Values for string interpolation in the message
77
+ *
78
+ * @example
79
+ * logger.fatal({ err, label: 'Application' }, 'Critical system failure');
80
+ * logger.fatal({ err, label: 'Application' }, 'System crashed after %d retries', retryCount);
81
+ */
82
+ fatal(labels: object | string, msg?: string, ...args: unknown[]): void;
83
+ /**
84
+ * Log trace messages (lowest severity)
85
+ *
86
+ * @param labels - Context object that can include:
87
+ * - `label`: string | string[] - Categorization labels (e.g., class name, method name, operation type)
88
+ * - Any other contextual data (userId, requestId, etc.)
89
+ * @param msg - Human-readable log message (supports string interpolation with args)
90
+ * @param args - Values for string interpolation in the message
91
+ *
92
+ * @example
93
+ * logger.trace({ label: ['UserService', 'createUser', 'validation'] }, 'Validating input');
94
+ * logger.trace({ label: 'UserService' }, 'Step %d: %s', stepNumber, stepName);
95
+ */
96
+ trace(labels: object | string, msg?: string, ...args: unknown[]): void;
97
+ }
98
+ //# sourceMappingURL=ILogger.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"ILogger.d.ts","sourceRoot":"","sources":["../../src/logger/ILogger.ts"],"names":[],"mappings":"AAAA;;;GAGG;AACH,MAAM,WAAW,OAAO;IACvB;;;;;;;;;;;;;;OAcG;IACH,IAAI,CAAC,MAAM,EAAE,MAAM,GAAG,MAAM,EAAE,GAAG,CAAC,EAAE,MAAM,EAAE,GAAG,IAAI,EAAE,OAAO,EAAE,GAAG,IAAI,CAAC;IAEtE;;;;;;;;;;;;;OAaG;IACH,IAAI,CAAC,MAAM,EAAE,MAAM,GAAG,MAAM,EAAE,GAAG,CAAC,EAAE,MAAM,EAAE,GAAG,IAAI,EAAE,OAAO,EAAE,GAAG,IAAI,CAAC;IAEtE;;;;;;;;;;;;;;OAcG;IACH,KAAK,CAAC,MAAM,EAAE,MAAM,GAAG,MAAM,EAAE,GAAG,CAAC,EAAE,MAAM,EAAE,GAAG,IAAI,EAAE,OAAO,EAAE,GAAG,IAAI,CAAC;IAEvE;;;;;;;;;;;;;OAaG;IACH,KAAK,CAAC,MAAM,EAAE,MAAM,GAAG,MAAM,EAAE,GAAG,CAAC,EAAE,MAAM,EAAE,GAAG,IAAI,EAAE,OAAO,EAAE,GAAG,IAAI,CAAC;IAEvE;;;;;;;;;;;;;OAaG;IACH,KAAK,CAAC,MAAM,EAAE,MAAM,GAAG,MAAM,EAAE,GAAG,CAAC,EAAE,MAAM,EAAE,GAAG,IAAI,EAAE,OAAO,EAAE,GAAG,IAAI,CAAC;IAEvE;;;;;;;;;;;;OAYG;IACH,KAAK,CAAC,MAAM,EAAE,MAAM,GAAG,MAAM,EAAE,GAAG,CAAC,EAAE,MAAM,EAAE,GAAG,IAAI,EAAE,OAAO,EAAE,GAAG,IAAI,CAAC;CACvE"}
@@ -0,0 +1,2 @@
1
+ export {};
2
+ //# sourceMappingURL=ILogger.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"ILogger.js","sourceRoot":"","sources":["../../src/logger/ILogger.ts"],"names":[],"mappings":""}
@@ -0,0 +1,31 @@
1
+ import { type LoggerOptions } from 'pino';
2
+ import type { ILogger } from './ILogger.js';
3
+ /**
4
+ * Pino logger implementation with configurable options.
5
+ *
6
+ * @example
7
+ * const logger = new PinoLogger();
8
+ *
9
+ * @example
10
+ * const logger = new PinoLogger({
11
+ * level: 'debug',
12
+ * base: { service: 'my-service', version: '1.0.0' }
13
+ * });
14
+ */
15
+ export declare class PinoLogger implements ILogger {
16
+ private logger;
17
+ /**
18
+ * Creates a new PinoLogger instance.
19
+ *
20
+ * @param options - Pino logger options. If not provided, uses environment-aware defaults.
21
+ * Any options passed will be merged with defaults, with passed options taking precedence.
22
+ */
23
+ constructor(options?: LoggerOptions);
24
+ info(labels: object | string, msg?: string, ...args: unknown[]): void;
25
+ warn(labels: object | string, msg?: string, ...args: unknown[]): void;
26
+ error(labels: object | string, msg?: string, ...args: unknown[]): void;
27
+ debug(labels: object | string, msg?: string, ...args: unknown[]): void;
28
+ fatal(labels: object | string, msg?: string, ...args: unknown[]): void;
29
+ trace(labels: object | string, msg?: string, ...args: unknown[]): void;
30
+ }
31
+ //# sourceMappingURL=PinoLogger.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"PinoLogger.d.ts","sourceRoot":"","sources":["../../src/logger/PinoLogger.ts"],"names":[],"mappings":"AAAA,OAAa,EAAqC,KAAK,aAAa,EAAE,MAAM,MAAM,CAAC;AAEnF,OAAO,KAAK,EAAE,OAAO,EAAE,MAAM,cAAc,CAAC;AAG5C;;;;;;;;;;;GAWG;AACH,qBACa,UAAW,YAAW,OAAO;IACzC,OAAO,CAAC,MAAM,CAAqB;IAEnC;;;;;OAKG;gBACS,OAAO,CAAC,EAAE,aAAa;IA8EnC,IAAI,CAAC,MAAM,EAAE,MAAM,GAAG,MAAM,EAAE,GAAG,CAAC,EAAE,MAAM,EAAE,GAAG,IAAI,EAAE,OAAO,EAAE,GAAG,IAAI;IAIrE,IAAI,CAAC,MAAM,EAAE,MAAM,GAAG,MAAM,EAAE,GAAG,CAAC,EAAE,MAAM,EAAE,GAAG,IAAI,EAAE,OAAO,EAAE,GAAG,IAAI;IAIrE,KAAK,CAAC,MAAM,EAAE,MAAM,GAAG,MAAM,EAAE,GAAG,CAAC,EAAE,MAAM,EAAE,GAAG,IAAI,EAAE,OAAO,EAAE,GAAG,IAAI;IAItE,KAAK,CAAC,MAAM,EAAE,MAAM,GAAG,MAAM,EAAE,GAAG,CAAC,EAAE,MAAM,EAAE,GAAG,IAAI,EAAE,OAAO,EAAE,GAAG,IAAI;IAItE,KAAK,CAAC,MAAM,EAAE,MAAM,GAAG,MAAM,EAAE,GAAG,CAAC,EAAE,MAAM,EAAE,GAAG,IAAI,EAAE,OAAO,EAAE,GAAG,IAAI;IAItE,KAAK,CAAC,MAAM,EAAE,MAAM,GAAG,MAAM,EAAE,GAAG,CAAC,EAAE,MAAM,EAAE,GAAG,IAAI,EAAE,OAAO,EAAE,GAAG,IAAI;CAGtE"}
@@ -0,0 +1,128 @@
1
+ var __decorate = (this && this.__decorate) || function (decorators, target, key, desc) {
2
+ var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
3
+ if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
4
+ else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
5
+ return c > 3 && r && Object.defineProperty(target, key, r), r;
6
+ };
7
+ var __metadata = (this && this.__metadata) || function (k, v) {
8
+ if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
9
+ };
10
+ import pino from 'pino';
11
+ import { injectable } from 'inversify';
12
+ import { hostname } from 'node:os';
13
+ /**
14
+ * Pino logger implementation with configurable options.
15
+ *
16
+ * @example
17
+ * const logger = new PinoLogger();
18
+ *
19
+ * @example
20
+ * const logger = new PinoLogger({
21
+ * level: 'debug',
22
+ * base: { service: 'my-service', version: '1.0.0' }
23
+ * });
24
+ */
25
+ let PinoLogger = class PinoLogger {
26
+ logger;
27
+ /**
28
+ * Creates a new PinoLogger instance.
29
+ *
30
+ * @param options - Pino logger options. If not provided, uses environment-aware defaults.
31
+ * Any options passed will be merged with defaults, with passed options taking precedence.
32
+ */
33
+ constructor(options) {
34
+ const nodeEnv = process.env.NODE_ENV || 'development';
35
+ const isDevelopment = nodeEnv === 'development';
36
+ const isProduction = nodeEnv === 'production';
37
+ const defaultOptions = {
38
+ level: process.env.LOG_LEVEL || 'info',
39
+ base: {
40
+ pid: process.pid,
41
+ hostname: process.env.HOSTNAME || hostname(),
42
+ service: process.env.SERVICE_NAME,
43
+ environment: nodeEnv,
44
+ },
45
+ timestamp: isDevelopment ? pino.stdTimeFunctions.isoTime : pino.stdTimeFunctions.isoTime,
46
+ // Error serialization for proper error logging
47
+ serializers: {
48
+ err: pino.stdSerializers.err,
49
+ error: pino.stdSerializers.err,
50
+ req: pino.stdSerializers.req,
51
+ res: pino.stdSerializers.res,
52
+ },
53
+ // Redact sensitive information in production
54
+ redact: {
55
+ paths: [
56
+ 'password',
57
+ '*.password',
58
+ 'token',
59
+ '*.token',
60
+ 'accessToken',
61
+ '*.accessToken',
62
+ 'refreshToken',
63
+ '*.refreshToken',
64
+ 'secret',
65
+ '*.secret',
66
+ 'authorization',
67
+ '*.authorization',
68
+ 'cookie',
69
+ '*.cookie',
70
+ 'apiKey',
71
+ '*.apiKey',
72
+ ],
73
+ remove: isProduction, // Remove in production, mask in development
74
+ },
75
+ // Pretty printing for development
76
+ transport: isDevelopment
77
+ ? {
78
+ target: 'pino-pretty',
79
+ options: {
80
+ colorize: true,
81
+ translateTime: 'HH:MM:ss Z',
82
+ ignore: 'pid,hostname',
83
+ singleLine: false,
84
+ messageFormat: '{levelLabel} - {msg}',
85
+ },
86
+ }
87
+ : undefined,
88
+ };
89
+ const mergedOptions = {
90
+ ...defaultOptions,
91
+ ...options,
92
+ base: {
93
+ ...defaultOptions.base,
94
+ ...(options?.base || {}),
95
+ },
96
+ serializers: {
97
+ ...defaultOptions.serializers,
98
+ ...(options?.serializers || {}),
99
+ },
100
+ redact: options?.redact !== undefined ? options.redact : defaultOptions.redact,
101
+ };
102
+ this.logger = pino(mergedOptions);
103
+ }
104
+ info(labels, msg, ...args) {
105
+ this.logger.info(labels, msg, ...args);
106
+ }
107
+ warn(labels, msg, ...args) {
108
+ this.logger.warn(labels, msg, ...args);
109
+ }
110
+ error(labels, msg, ...args) {
111
+ this.logger.error(labels, msg, ...args);
112
+ }
113
+ debug(labels, msg, ...args) {
114
+ this.logger.debug(labels, msg, ...args);
115
+ }
116
+ fatal(labels, msg, ...args) {
117
+ this.logger.fatal(labels, msg, ...args);
118
+ }
119
+ trace(labels, msg, ...args) {
120
+ this.logger.trace(labels, msg, ...args);
121
+ }
122
+ };
123
+ PinoLogger = __decorate([
124
+ injectable(),
125
+ __metadata("design:paramtypes", [Object])
126
+ ], PinoLogger);
127
+ export { PinoLogger };
128
+ //# sourceMappingURL=PinoLogger.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"PinoLogger.js","sourceRoot":"","sources":["../../src/logger/PinoLogger.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,3 @@
1
+ export { ILogger } from './ILogger.js';
2
+ export { PinoLogger } from './PinoLogger.js';
3
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/logger/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,OAAO,EAAE,MAAM,cAAc,CAAC;AACvC,OAAO,EAAE,UAAU,EAAE,MAAM,iBAAiB,CAAC"}
@@ -0,0 +1,2 @@
1
+ export { PinoLogger } from './PinoLogger.js';
2
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/logger/index.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,UAAU,EAAE,MAAM,iBAAiB,CAAC"}
package/package.json CHANGED
@@ -1,88 +1,78 @@
1
1
  {
2
- "name": "@togatherlabs/shared-utils",
3
- "version": "1.0.10",
4
- "description": "Shared utility functions, constants, and types for ToGather microservices",
5
- "type": "module",
6
- "main": "dist/index.js",
7
- "types": "dist/index.d.ts",
8
- "exports": {
9
- ".": {
10
- "import": "./dist/index.js",
11
- "require": "./dist/index.js",
12
- "types": "./dist/index.d.ts"
13
- },
14
- "./helpers": {
15
- "import": "./dist/helpers/index.js",
16
- "require": "./dist/helpers/index.js",
17
- "types": "./dist/helpers/index.d.ts"
18
- },
19
- "./constants": {
20
- "import": "./dist/constants/index.js",
21
- "require": "./dist/constants/index.js",
22
- "types": "./dist/constants/index.d.ts"
23
- },
24
- "./types": {
25
- "import": "./dist/types/index.js",
26
- "require": "./dist/types/index.js",
27
- "types": "./dist/types/index.d.ts"
28
- }
29
- },
30
- "files": [
31
- "dist"
32
- ],
33
- "keywords": [
34
- "shared",
35
- "utils",
36
- "togather",
37
- "microservices"
38
- ],
39
- "author": "toGather team",
40
- "license": "ISC",
41
- "devDependencies": {
42
- "@biomejs/biome": "^2.2.6",
43
- "@commitlint/cli": "^20.1.0",
44
- "@commitlint/config-conventional": "^20.0.0",
45
- "@commitlint/cz-commitlint": "^20.1.0",
46
- "@commitlint/types": "^20.0.0",
47
- "@tsconfig/node22": "^22.0.2",
48
- "@types/node": "^24.7.2",
49
- "@vitest/coverage-v8": "^3.2.4",
50
- "@vitest/ui": "^3.2.4",
51
- "commitizen": "^4.3.1",
52
- "husky": "^9.1.7",
53
- "inquirer": "^9.3.8",
54
- "ts-node": "^10.9.2",
55
- "typescript": "^5.9.3",
56
- "vitest": "^3.2.4"
57
- },
58
- "config": {
59
- "commitizen": {
60
- "path": "@commitlint/cz-commitlint"
61
- }
62
- },
63
- "publishConfig": {
64
- "access": "public"
65
- },
66
- "scripts": {
67
- "build": "tsc",
68
- "lint": "biome lint .",
69
- "lint:fix": "biome lint --write .",
70
- "format": "biome format .",
71
- "format:fix": "biome format --write .",
72
- "check": "biome check .",
73
- "check:fix": "biome check --write .",
74
- "typecheck": "tsc --noEmit",
75
- "test": "vitest run",
76
- "test:watch": "vitest",
77
- "test:coverage": "vitest run --coverage",
78
- "test:ui": "vitest --ui",
79
- "commit": "git-cz",
80
- "package:patch": "pnpm version patch",
81
- "package:minor": "pnpm version minor",
82
- "package:major": "pnpm version major",
83
- "package:publish": "pnpm publish --access public",
84
- "release:patch": "pnpm build && git add . && pnpm commit && pnpm package:patch && git push --follow-tags && pnpm package:publish",
85
- "release:minor": "pnpm build && git add . && pnpm commit && pnpm package:minor && git push --follow-tags && pnpm package:publish",
86
- "release:major": "pnpm build && git add . && pnpm commit && pnpm package:major && git push --follow-tags && pnpm package:publish"
87
- }
88
- }
2
+ "name": "@togatherlabs/shared-utils",
3
+ "version": "1.1.0",
4
+ "description": "Shared utilities for Togather services including logger, validators, and common helpers",
5
+ "main": "dist/index.js",
6
+ "types": "dist/index.d.ts",
7
+ "type": "module",
8
+ "scripts": {
9
+ "prepare": "husky",
10
+ "build": "tsc",
11
+ "typecheck": "tsc --noEmit",
12
+ "lint": "biome check .",
13
+ "lint:fix": "biome check . --write",
14
+ "format": "biome format . --write",
15
+ "clean": "rm -rf dist",
16
+ "prebuild": "pnpm run clean",
17
+ "prepublishOnly": "pnpm run build",
18
+ "commit": "cz",
19
+ "publish:npm": "./scripts/publish.sh",
20
+ "version:patch": "./scripts/version.sh patch",
21
+ "version:minor": "./scripts/version.sh minor",
22
+ "version:major": "./scripts/version.sh major"
23
+ },
24
+ "keywords": [
25
+ "togather",
26
+ "utilities",
27
+ "logger",
28
+ "pino",
29
+ "shared"
30
+ ],
31
+ "author": "Togather Team",
32
+ "license": "ISC",
33
+ "packageManager": "pnpm@10.7.1",
34
+ "files": [
35
+ "dist",
36
+ "README.md",
37
+ "LICENSE"
38
+ ],
39
+ "exports": {
40
+ ".": {
41
+ "import": "./dist/index.js",
42
+ "types": "./dist/index.d.ts"
43
+ },
44
+ "./logger": {
45
+ "import": "./dist/logger/index.js",
46
+ "types": "./dist/logger/index.d.ts"
47
+ }
48
+ },
49
+ "dependencies": {
50
+ "inversify": "^7.10.4",
51
+ "pino": "^10.1.0"
52
+ },
53
+ "devDependencies": {
54
+ "@biomejs/biome": "2.2.5",
55
+ "@commitlint/cli": "^20.1.0",
56
+ "@commitlint/config-conventional": "^20.0.0",
57
+ "@commitlint/cz-commitlint": "^20.1.0",
58
+ "@commitlint/types": "^20.0.0",
59
+ "@types/node": "^24.9.1",
60
+ "commitizen": "^4.3.1",
61
+ "husky": "^9.1.7",
62
+ "pino-pretty": "^13.1.2",
63
+ "typescript": "^5.9.3"
64
+ },
65
+ "peerDependencies": {
66
+ "pino-pretty": "^13.1.2"
67
+ },
68
+ "peerDependenciesMeta": {
69
+ "pino-pretty": {
70
+ "optional": true
71
+ }
72
+ },
73
+ "config": {
74
+ "commitizen": {
75
+ "path": "@commitlint/cz-commitlint"
76
+ }
77
+ }
78
+ }
@@ -1,2 +0,0 @@
1
- export * from "./sample.js";
2
- //# sourceMappingURL=index.d.ts.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/constants/index.ts"],"names":[],"mappings":"AAAA,cAAc,aAAa,CAAC"}
@@ -1 +0,0 @@
1
- export * from "./sample.js";
@@ -1,4 +0,0 @@
1
- export declare const SAMPLE: {
2
- Char: string;
3
- };
4
- //# sourceMappingURL=sample.d.ts.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"sample.d.ts","sourceRoot":"","sources":["../../src/constants/sample.ts"],"names":[],"mappings":"AAAA,eAAO,MAAM,MAAM;;CAElB,CAAC"}
@@ -1,3 +0,0 @@
1
- export const SAMPLE = {
2
- Char: "A",
3
- };
@@ -1,2 +0,0 @@
1
- export declare function formatDate(date: Date, locale?: string): string;
2
- //# sourceMappingURL=formatDate.d.ts.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"formatDate.d.ts","sourceRoot":"","sources":["../../src/helpers/formatDate.ts"],"names":[],"mappings":"AAAA,wBAAgB,UAAU,CAAC,IAAI,EAAE,IAAI,EAAE,MAAM,SAAU,GAAG,MAAM,CAU/D"}
@@ -1,10 +0,0 @@
1
- export function formatDate(date, locale = "en-IN") {
2
- if (!(date instanceof Date) || Number.isNaN(date.getTime())) {
3
- throw new Error("Invalid Date");
4
- }
5
- return date.toLocaleDateString(locale, {
6
- year: "numeric",
7
- month: "short",
8
- day: "numeric",
9
- });
10
- }
@@ -1,2 +0,0 @@
1
- export * from "./formatDate.js";
2
- //# sourceMappingURL=index.d.ts.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/helpers/index.ts"],"names":[],"mappings":"AAAA,cAAc,iBAAiB,CAAC"}
@@ -1 +0,0 @@
1
- export * from "./formatDate.js";
@@ -1,2 +0,0 @@
1
- export * from "./user.js";
2
- //# sourceMappingURL=index.d.ts.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/types/index.ts"],"names":[],"mappings":"AAAA,cAAc,WAAW,CAAC"}
@@ -1 +0,0 @@
1
- export * from "./user.js";
@@ -1,6 +0,0 @@
1
- export interface UserDTO {
2
- id: string;
3
- name: string;
4
- email: string;
5
- }
6
- //# sourceMappingURL=user.d.ts.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"user.d.ts","sourceRoot":"","sources":["../../src/types/user.ts"],"names":[],"mappings":"AAAA,MAAM,WAAW,OAAO;IACtB,EAAE,EAAE,MAAM,CAAC;IACX,IAAI,EAAE,MAAM,CAAC;IACb,KAAK,EAAE,MAAM,CAAC;CACf"}
@@ -1 +0,0 @@
1
- export {};