@bereasoftware/time-guard 1.0.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.en.md ADDED
@@ -0,0 +1,1248 @@
1
+ # TimeGuard 🕐
2
+
3
+ A modern, production-grade date/time manipulation library built with **TypeScript**, **Temporal API**, and **SOLID principles**. TimeGuard leverages modern JavaScript standards and best practices.
4
+
5
+ [![Tests](https://img.shields.io/badge/Tests-530%2B-green?style=for-the-badge)](#testing)
6
+ [![Locales](https://img.shields.io/badge/Locales-40%2B-orange?style=for-the-badge)](#supported-locales)
7
+ [![Calendars](https://img.shields.io/badge/Calendars-6+-blue?style=for-the-badge)](#calendar-systems)
8
+ [![NPM version](https://img.shields.io/npm/v/@bereasoftware/time-guard?style=for-the-badge)](https://www.npmjs.com/package/@bereasoftware/time-guard)
9
+ [![Bundle size](https://img.shields.io/bundlephobia/minzip/@bereasoftware/time-guard?style=for-the-badge)](https://www.npmjs.com/package/@bereasoftware/time-guard)
10
+ [![NPM downloads](https://img.shields.io/npm/dm/@bereasoftware/time-guard?style=for-the-badge)](https://www.npmjs.com/package/@bereasoftware/time-guard)
11
+ [![CI](https://img.shields.io/github/actions/workflow/status/Berea-Soft/time-guard/ci.yml?style=for-the-badge)](https://github.com/Berea-Soft/time-guard/actions/workflows/ci.yml)
12
+ [![Node](https://img.shields.io/node/v/@bereasoftware/time-guard?style=for-the-badge)](https://www.npmjs.com/package/@bereasoftware/time-guard)
13
+ [![TypeScript](https://img.shields.io/badge/TypeScript-5.x-3178C6?style=for-the-badge)](https://www.typescriptlang.org/)
14
+ [![License](https://img.shields.io/github/license/Berea-Soft/email-validator?style=for-the-badge)](https://github.com/Berea-Soft/email-validator/blob/main/LICENSE)
15
+ [![Last commit](https://img.shields.io/github/last-commit/Berea-Soft/time-guard?style=for-the-badge)](https://github.com/Berea-Soft/time-guard/commits/main)
16
+ [![Repository](https://img.shields.io/badge/github-repo-blue?logo=github&style=for-the-badge)](https://github.com/Berea-Soft/time-guard)
17
+ [![Coverage](https://img.shields.io/badge/coverage-95%25-orange?style=for-the-badge)](https://github.com/Berea-Soft/time-guard)
18
+
19
+ ---
20
+
21
+ ## 🎯 Features
22
+
23
+ - ✨ **Modern JavaScript** - Built on Temporal API (TC39 standard)
24
+ - 🏛️ **SOLID Principles** - Clean, maintainable, extensible architecture
25
+ - 🌍 **40+ Locales** - Comprehensive internationalization support
26
+ - 📦 **TypeScript** - Full type safety with strict mode enabled
27
+ - 🧪 **530+ Tests** - Complete BDD/TDD test coverage
28
+ - 🎨 **Multiple Formats** - ISO, RFC2822, RFC3339, UTC, and custom patterns
29
+ - ⚡ **Tree-Shakeable** - Modular structure for optimal bundle size
30
+ - 📚 **Well-Documented** - Extensive guides, examples, and API reference
31
+ - 🔌 **Plugin System** - Extend with optional plugins (relative time, duration, advanced formatting)
32
+ - 📅 **Multiple Calendars** - Gregorian, Islamic, Hebrew, Chinese, Japanese, Buddhist, and more
33
+ - ⏱️ **Nanosecond Precision** - Full Temporal API nanosecond support
34
+ - 🔄 **Duration API** - `until()`, `round()` methods for advanced calculations
35
+
36
+ ---
37
+
38
+ ## 📋 Table of Contents
39
+
40
+ - [Quick Start](#quick-start)
41
+ - [Installation](#installation)
42
+ - [Core Concepts](#core-concepts)
43
+ - [Component Accessors](#component-accessors)
44
+ - [Advanced Calculations](#advanced-calculations)
45
+ - [Calendar Systems](#calendar-systems)
46
+ - [Plugins](#plugins)
47
+ - [Documentation](#documentation)
48
+ - [Supported Locales](#supported-locales)
49
+ - [API Overview](#api-overview)
50
+ - [Testing](#testing)
51
+ - [Architecture](#architecture)
52
+ - [Contributing](#contributing)
53
+ - [License](#license)
54
+
55
+ ---
56
+
57
+ ## 🚀 Quick Start
58
+
59
+ ```typescript
60
+ import { TimeGuard } from "time-guard";
61
+
62
+ // Create a date
63
+ const now = TimeGuard.now();
64
+ const date = TimeGuard.from("2024-03-13");
65
+
66
+ // Manipulate dates
67
+ const tomorrow = date.add(1, "day");
68
+ const nextMonth = date.add(1, "month");
69
+
70
+ // Format with locales
71
+ const spanish = date.locale("es").format("dddd, DD MMMM YYYY");
72
+ // Output: miércoles, 13 marzo 2024
73
+
74
+ const japanese = date.locale("ja").format("YYYY年M月D日");
75
+ // Output: 2024年3月13日
76
+
77
+ // Get date components
78
+ console.log(date.year()); // 2024
79
+ console.log(date.month()); // 3
80
+ console.log(date.day()); // 13
81
+ console.log(date.dayOfWeek()); // 3 (Wednesday)
82
+
83
+ // Compare dates
84
+ console.log(date.isBefore(tomorrow)); // true
85
+ console.log(date.isSame(date.clone())); // true
86
+ console.log(date.isAfter(new Date("2020-01-01"))); // true
87
+ ```
88
+
89
+ ---
90
+
91
+ ## 📦 Installation
92
+
93
+ ```bash
94
+ npm install time-guard
95
+ # or
96
+ yarn add time-guard
97
+ # or
98
+ pnpm add time-guard
99
+ ```
100
+
101
+ ### Requirements
102
+
103
+ - **Node.js** 16+ (Temporal API support)
104
+ - **TypeScript** 5.0+ (optional but recommended)
105
+
106
+ ---
107
+
108
+ ## 🏗️ Core Concepts
109
+
110
+ ### 1. Immutability
111
+
112
+ All TimeGuard instances are immutable. Every operation returns a new instance:
113
+
114
+ ```typescript
115
+ const date = TimeGuard.from("2024-03-13");
116
+ const modified = date.add(1, "day");
117
+
118
+ console.log(date.day()); // 13 (unchanged)
119
+ console.log(modified.day()); // 14 (new instance)
120
+ ```
121
+
122
+ ### 2. Timezone Support
123
+
124
+ Handle timezones with full Temporal API support:
125
+
126
+ ```typescript
127
+ const date = TimeGuard.from("2024-03-13 10:30:00");
128
+
129
+ // Set timezone
130
+ const inNYC = date.timezone("America/New_York");
131
+ const inTokyo = date.timezone("Asia/Tokyo");
132
+
133
+ console.log(inNYC.format("YYYY-MM-DD HH:mm:ss Z"));
134
+ console.log(inTokyo.format("YYYY-MM-DD HH:mm:ss Z"));
135
+ ```
136
+
137
+ ### 3. Localization
138
+
139
+ Support for 40+ languages and locales:
140
+
141
+ ```typescript
142
+ const date = TimeGuard.from("2024-03-13");
143
+
144
+ date.locale("en").format("MMMM DD, YYYY"); // March 13, 2024
145
+ date.locale("es").format("DD MMMM YYYY"); // 13 marzo 2024
146
+ date.locale("fr").format("DD MMMM YYYY"); // 13 mars 2024
147
+ date.locale("de").format("DD. MMMM YYYY"); // 13. März 2024
148
+ date.locale("ja").format("YYYY年M月D日"); // 2024年3月13日
149
+ date.locale("zh-cn").format("YYYY年M月D日"); // 2024年3月13日
150
+ date.locale("ar").format("DD MMMM YYYY"); // 13 مارس 2024
151
+ ```
152
+
153
+ ### 4. Format Strategies
154
+
155
+ Multiple preset formats and custom patterns:
156
+
157
+ ```typescript
158
+ const date = TimeGuard.from("2024-03-13 14:30:45");
159
+
160
+ // Presets
161
+ date.format("iso"); // 2024-03-13T14:30:45
162
+ date.format("date"); // 2024-03-13
163
+ date.format("time"); // 14:30:45
164
+ date.format("datetime"); // 2024-03-13 14:30:45
165
+ date.format("rfc2822"); // Wed, 13 Mar 2024 14:30:45 GMT
166
+ date.format("rfc3339"); // 2024-03-13T14:30:45Z
167
+ date.format("utc"); // 2024-03-13T14:30:45.000Z
168
+
169
+ // Custom patterns
170
+ date.format("YYYY-MM-DD HH:mm:ss");
171
+ date.format("dddd, MMMM DD, YYYY");
172
+ date.format("MM/DD/YYYY");
173
+ ```
174
+
175
+ ---
176
+
177
+ ## 🎯 Component Accessors
178
+
179
+ Quick access to individual date components:
180
+
181
+ ```typescript
182
+ const date = TimeGuard.from("2024-03-13 14:30:45.123");
183
+
184
+ // Individual components
185
+ console.log(date.year()); // 2024
186
+ console.log(date.month()); // 3
187
+ console.log(date.day()); // 13
188
+ console.log(date.hour()); // 14
189
+ console.log(date.minute()); // 30
190
+ console.log(date.second()); // 45
191
+ console.log(date.millisecond()); // 123
192
+
193
+ // Week information
194
+ console.log(date.dayOfWeek()); // 3 (Wed: 1=Sun, 7=Sat)
195
+ console.log(date.dayOfYear()); // 73
196
+ console.log(date.weekOfYear()); // 11
197
+
198
+ // Month/Year information
199
+ console.log(date.daysInMonth()); // 31
200
+ console.log(date.daysInYear()); // 366 (leap year)
201
+ console.log(date.inLeapYear()); // true
202
+ ```
203
+
204
+ ---
205
+
206
+ ## ⏱️ Advanced Calculations
207
+
208
+ ### Duration: Calculate time between dates
209
+
210
+ ```typescript
211
+ const start = TimeGuard.from("2024-01-15");
212
+ const end = TimeGuard.from("2024-03-20");
213
+
214
+ const duration = start.until(end);
215
+
216
+ console.log(duration);
217
+ // {
218
+ // years: 0,
219
+ // months: 2,
220
+ // days: 5,
221
+ // hours: 0,
222
+ // minutes: 0,
223
+ // seconds: 0,
224
+ // milliseconds: 0
225
+ // }
226
+ ```
227
+
228
+ ### Round: Precision control
229
+
230
+ ```typescript
231
+ const date = TimeGuard.from("2024-03-13 14:35:47.654");
232
+
233
+ // Round to different units
234
+ date.round({ smallestUnit: "second" }); // 2024-03-13 14:35:48
235
+ date.round({ smallestUnit: "minute" }); // 2024-03-13 14:36:00
236
+ date.round({ smallestUnit: "hour" }); // 2024-03-13 15:00:00
237
+ date.round({ smallestUnit: "day" }); // 2024-03-14 00:00:00
238
+
239
+ // Rounding modes: 'ceil', 'floor', 'trunc', 'half' (default)
240
+ date.round({
241
+ smallestUnit: "minute",
242
+ roundingMode: "ceil",
243
+ });
244
+ ```
245
+
246
+ ---
247
+
248
+ ## 📅 Calendar Systems
249
+
250
+ TimeGuard includes support for multiple calendar systems, extendable via the calendar manager:
251
+
252
+ ### Supported Calendars
253
+
254
+ ```typescript
255
+ import { TimeGuard, CalendarManager } from "time-guard";
256
+ import {
257
+ IslamicCalendar,
258
+ HebrewCalendar,
259
+ ChineseCalendar,
260
+ JapaneseCalendar,
261
+ BuddhistCalendar,
262
+ } from "time-guard/calendars";
263
+
264
+ // Get calendar manager
265
+ const calendarMgr = CalendarManager.getInstance();
266
+
267
+ // List available calendars
268
+ console.log(calendarMgr.list());
269
+ // ['gregory', 'islamic', 'hebrew', 'chinese', 'japanese', 'buddhist']
270
+
271
+ // Register custom calendar
272
+ const islamic = new IslamicCalendar();
273
+ calendarMgr.register(islamic);
274
+
275
+ // Get calendar info
276
+ const gregorian = calendarMgr.get("gregory");
277
+ console.log(gregorian.getMonthName(3)); // "March"
278
+ console.log(gregorian.getMonthName(3, true)); // "Mar"
279
+ console.log(gregorian.getWeekdayName(1)); // "Sunday"
280
+ console.log(gregorian.isLeapYear(2024)); // true
281
+ ```
282
+
283
+ ---
284
+
285
+ ## 🔌 Plugins
286
+
287
+ TimeGuard includes an optional plugin system for extended functionality:
288
+
289
+ ### Available Plugins
290
+
291
+ 1. **Relative Time Plugin** - Human-readable time differences
292
+
293
+ ```typescript
294
+ import { TimeGuard, PluginManager } from "time-guard";
295
+ import relativeTimePlugin from "time-guard/plugins/relative-time";
296
+
297
+ PluginManager.use(relativeTimePlugin, TimeGuard);
298
+
299
+ TimeGuard.from("2024-01-01").fromNow(); // "2 months ago"
300
+ TimeGuard.from("2024-04-01").toNow(); // "in 19 days"
301
+ ```
302
+
303
+ 2. **Duration Plugin** - ISO 8601 duration support
304
+
305
+ ```typescript
306
+ import { Duration } from "time-guard/plugins/duration";
307
+
308
+ const duration = Duration.fromISO("P2Y3M4D");
309
+ duration.humanize(); // "2 years, 3 months, 4 days"
310
+ duration.asDays(); // 1159
311
+ ```
312
+
313
+ 3. **Advanced Format Plugin** - Extended format tokens
314
+
315
+ ```typescript
316
+ import advancedFormatPlugin from "time-guard/plugins/advanced-format";
317
+
318
+ PluginManager.use(advancedFormatPlugin, TimeGuard);
319
+
320
+ date.format("Do MMMM YYYY"); // "13th March 2024"
321
+ date.format("Q [Q] YYYY"); // "1 Q 2024"
322
+ ```
323
+
324
+ **📖 Full Details:** See [PLUGINS.md](PLUGINS.md) for complete plugin documentation.
325
+
326
+ ---
327
+
328
+ ## 📚 Documentation
329
+
330
+ ### Main Documentation Files
331
+
332
+ | Document | Purpose |
333
+ | ------------------------------------- | ------------------------------------------------------------------------- |
334
+ | [📖 ARCHITECTURE.md](ARCHITECTURE.md) | Deep dive into design patterns, SOLID principles, and system architecture |
335
+ | [💡 EXAMPLES.md](EXAMPLES.md) | Real-world usage examples and common scenarios |
336
+ | [🌍 LOCALES.md](LOCALES.md) | Complete guide to localization and supported languages |
337
+ | [🔌 PLUGINS.md](PLUGINS.md) | Plugin system documentation and usage guide |
338
+ | [📖 API Reference](#api-overview) | Quick API reference (below) |
339
+
340
+ ### Quick Navigation
341
+
342
+ - **Getting Started** → Start with [Quick Start](#quick-start) above
343
+ - **Advanced Usage** → See [EXAMPLES.md](EXAMPLES.md)
344
+ - **Localization** → See [LOCALES.md](LOCALES.md)
345
+ - **Architecture** → See [ARCHITECTURE.md](ARCHITECTURE.md)
346
+
347
+ ## 🌍 Supported Locales - Complete Guide
348
+
349
+ TimeGuard provides **40+ languages and regional variants** with full internationalization support. Locales are organized by language family for easy discovery.
350
+
351
+ ### Locale Code Format
352
+
353
+ Locale codes follow the standard `[language]-[region]` pattern:
354
+
355
+ - `en` - Default form (used if region variant not specified)
356
+ - `en-gb` - Specific region variant (Great Britain)
357
+ - `es-mx` - Spanish variant for Mexico
358
+ - `zh-cn` - Simplified Chinese
359
+
360
+ ### Available Locales by Family
361
+
362
+ #### 🇬🇧 English (4 variants)
363
+
364
+ - `en` - English (US)
365
+ - `en-au` - English (Australia)
366
+ - `en-gb` - English (Great Britain)
367
+ - `en-ca` - English (Canada)
368
+
369
+ ### Spanish (3 variants)
370
+
371
+ - `es` - Spanish (Spain)
372
+ - `es-mx` - Spanish (Mexico)
373
+ - `es-us` - Spanish (US)
374
+
375
+ ### Romance Languages (5)
376
+
377
+ - `fr` - French
378
+ - `it` - Italian
379
+ - `pt` - Portuguese (Portugal)
380
+ - `pt-br` - Portuguese (Brazil)
381
+ - `ro` - Romanian
382
+
383
+ ### Slavic Languages (4)
384
+
385
+ - `ru` - Russian
386
+ - `pl` - Polish
387
+ - `cs` - Czech
388
+ - `sk` - Slovak
389
+
390
+ ### Nordic Languages (4)
391
+
392
+ - `sv` - Swedish
393
+ - `nb` - Norwegian (Bokmål)
394
+ - `da` - Danish
395
+ - `fi` - Finnish
396
+
397
+ ### Asian Languages (7)
398
+
399
+ - `ja` - Japanese
400
+ - `zh-cn` - Chinese (Simplified)
401
+ - `zh-tw` - Chinese (Traditional)
402
+ - `ko` - Korean
403
+ - `th` - Thai
404
+ - `vi` - Vietnamese
405
+ - `id` - Indonesian
406
+
407
+ ### European Languages (7)
408
+
409
+ - `de` - German
410
+ - `nl` - Dutch
411
+ - `el` - Greek
412
+ - `hu` - Hungarian
413
+ - `eu` - Basque
414
+ - `ca` - Catalan
415
+ - `tr` - Turkish
416
+
417
+ ### Middle Eastern & South Asian (3)
418
+
419
+ - `ar` - Arabic
420
+ - `he` - Hebrew
421
+ - `hi` - Hindi
422
+
423
+ ---
424
+
425
+ ### Locale Usage Guide
426
+
427
+ #### Setting Locales
428
+
429
+ ```typescript
430
+ import { TimeGuard } from "time-guard";
431
+
432
+ const date = TimeGuard.from("2024-03-13 14:30:00");
433
+
434
+ // Get current locale
435
+ const currentLocale = date.locale(); // "en"
436
+
437
+ // Change locale (returns new instance)
438
+ const spanish = date.locale("es");
439
+ const french = date.locale("fr");
440
+ const japanese = date.locale("ja");
441
+ const arabic = date.locale("ar");
442
+
443
+ // Chain operations
444
+ date.locale("es").format("dddd, DD MMMM YYYY"); // miércoles, 13 marzo 2024
445
+
446
+ // Or use constructor config
447
+ TimeGuard.from("2024-03-13", { locale: "de" });
448
+ TimeGuard.now({ locale: "ja" });
449
+ ```
450
+
451
+ #### Formatting in Different Locales
452
+
453
+ ```typescript
454
+ const date = TimeGuard.from("2024-03-13");
455
+
456
+ // English variants
457
+ date.locale("en").format("MMMM DD, YYYY"); // March 13, 2024
458
+ date.locale("en-gb").format("DD MMMM YYYY"); // 13 March 2024
459
+ date.locale("en-au").format("DD/MM/YYYY"); // 13/03/2024
460
+ date.locale("en-ca").format("YYYY-MM-DD"); // 2024-03-13
461
+
462
+ // Spanish variants
463
+ date.locale("es").format("DD MMMM YYYY"); // 13 marzo 2024
464
+ date.locale("es-mx").format("DD/MM/YYYY"); // 13/03/2024
465
+ date.locale("es-us").format("MMMM D"); // marzo 13
466
+
467
+ // Romance languages
468
+ date.locale("fr").format("dddd D MMMM YYYY"); // mercredi 13 mars 2024
469
+ date.locale("it").format("dddd, D MMMM YYYY"); // mercoledì, 13 marzo 2024
470
+ date.locale("pt").format("dddd, D MMMM YYYY"); // quarta-feira, 13 de março de 2024
471
+ date.locale("pt-br").format("DD/MM/YYYY"); // 13/03/2024
472
+ date.locale("ro").format("DD MMMM YYYY"); // 13 martie 2024
473
+
474
+ // Slavic languages
475
+ date.locale("ru").format("DD MMMM YYYY"); // 13 марта 2024
476
+ date.locale("pl").format("DD MMMM YYYY"); // 13 marca 2024
477
+ date.locale("cs").format("DD. MMMM YYYY"); // 13. března 2024
478
+ date.locale("sk").format("DD. MMMM YYYY"); // 13. marca 2024
479
+
480
+ // Nordic languages
481
+ date.locale("sv").format("DD MMMM YYYY"); // 13 mars 2024
482
+ date.locale("nb").format("DD. MMMM YYYY"); // 13. mars 2024
483
+ date.locale("da").format("DD. MMMM YYYY"); // 13. marts 2024
484
+ date.locale("fi").format("DD. MMMM YYYY"); // 13. maaliskuuta 2024
485
+
486
+ // Asian languages
487
+ date.locale("ja").format("YYYY年M月D日"); // 2024年3月13日
488
+ date.locale("zh-cn").format("YYYY年M月D日"); // 2024年3月13日
489
+ date.locale("zh-tw").format("YYYY年M月D日"); // 2024年3月13日
490
+ date.locale("ko").format("YYYY년 M월 D일"); // 2024년 3월 13일
491
+ date.locale("th").format("DD MMMM YYYY"); // 13 มีนาคม 2567 (BE)
492
+ date.locale("vi").format("DD/MM/YYYY"); // 13/03/2024
493
+ date.locale("id").format("DD MMMM YYYY"); // 13 Maret 2024
494
+
495
+ // European languages
496
+ date.locale("de").format("DD. MMMM YYYY"); // 13. März 2024
497
+ date.locale("nl").format("DD MMMM YYYY"); // 13 maart 2024
498
+ date.locale("el").format("DD MMMM YYYY"); // 13 Μαρτίου 2024
499
+ date.locale("hu").format("YYYY. MMMM DD."); // 2024. március 13.
500
+ date.locale("eu").format("YYYY[ko] MMMM[ren] DD"); // 2024ko martsaren 13
501
+ date.locale("ca").format("DD MMMM YYYY"); // 13 de març de 2024
502
+ date.locale("tr").format("DD MMMM YYYY"); // 13 Mart 2024
503
+
504
+ // Middle Eastern & South Asian
505
+ date.locale("ar").format("DD MMMM YYYY"); // 13 مارس 2024
506
+ date.locale("he").format("DD.MM.YYYY"); // 13.03.2024
507
+ date.locale("hi").format("DD MMMM YYYY"); // 13 मार्च 2024
508
+ ```
509
+
510
+ #### Day and Month Names
511
+
512
+ ```typescript
513
+ // Get localized day names
514
+ date.locale("es").format("dddd"); // miércoles
515
+ date.locale("es").format("ddd"); // mié
516
+ date.locale("fr").format("dddd"); // mercredi
517
+ date.locale("de").format("dddd"); // Mittwoch
518
+ date.locale("ja").format("dddd"); // 水曜日
519
+
520
+ // Get localized month names
521
+ date.locale("es").format("MMMM"); // marzo
522
+ date.locale("es").format("MMM"); // mar
523
+ date.locale("fr").format("MMMM"); // mars
524
+ date.locale("de").format("MMMM"); // März
525
+ date.locale("ru").format("MMMM"); // марта
526
+ ```
527
+
528
+ #### Multi-Locale Applications
529
+
530
+ ```typescript
531
+ // Switch language at runtime (user preference)
532
+ let currentLocale = "en";
533
+
534
+ function formatUserDate(
535
+ date: TimeGuard,
536
+ locale: string = currentLocale,
537
+ ): string {
538
+ return date.locale(locale).format("dddd, MMMM D, YYYY [at] HH:mm");
539
+ }
540
+
541
+ const date = TimeGuard.now();
542
+
543
+ // English user
544
+ console.log(formatUserDate(date, "en")); // Wednesday, March 13, 2024 at 14:30
545
+
546
+ // Spanish user
547
+ currentLocale = "es";
548
+ console.log(formatUserDate(date, "es")); // miércoles, 13 de marzo de 2024 a las 14:30
549
+
550
+ // French user
551
+ console.log(formatUserDate(date, "fr")); // mercredi, 13 mars 2024 à 14:30
552
+
553
+ // Japanese user
554
+ console.log(formatUserDate(date, "ja")); // 水曜日、2024年3月13日 14:30
555
+ ```
556
+
557
+ #### Getting Available Locales Programmatically
558
+
559
+ ```typescript
560
+ // Get all available locales
561
+ const locales = TimeGuard.getAvailableLocales();
562
+ // Returns: ['en', 'en-au', 'en-gb', 'en-ca', 'es', 'es-mx', 'es-us', ...]
563
+
564
+ // Filter by prefix
565
+ const englishLocales = locales.filter((l) => l.startsWith("en"));
566
+ const spanishLocales = locales.filter((l) => l.startsWith("es"));
567
+ const asianLocales = locales.filter((l) =>
568
+ ["ja", "zh-cn", "zh-tw", "ko"].includes(l),
569
+ );
570
+
571
+ // Create locale selector UI
572
+ function createLocaleSelector() {
573
+ const locales = TimeGuard.getAvailableLocales();
574
+ return locales.map((locale) => ({
575
+ code: locale,
576
+ label: new Intl.DisplayNames("en", { type: "language" }).of(locale),
577
+ }));
578
+ }
579
+ ```
580
+
581
+ **📖 Full Details:** See [LOCALES.md](LOCALES.md) for locale-specific usage and characteristics.
582
+
583
+ ---
584
+
585
+ ## 🔌 Plugins - Complete Guide
586
+
587
+ TimeGuard includes a powerful plugin system for extending functionality. Plugins follow SOLID principles and are fully optional.
588
+
589
+ ### Plugin Manager
590
+
591
+ ```typescript
592
+ import { TimeGuard, PluginManager } from "time-guard";
593
+
594
+ // Use a plugin
595
+ PluginManager.use(myPlugin, TimeGuard);
596
+
597
+ // Check if plugin is installed
598
+ PluginManager.isInstalled(pluginName);
599
+
600
+ // List installed plugins
601
+ PluginManager.listInstalled();
602
+ ```
603
+
604
+ ### 1️⃣ Relative Time Plugin
605
+
606
+ Adds human-readable time differences like "2 hours ago" or "in 3 days".
607
+
608
+ ```typescript
609
+ import { TimeGuard, PluginManager } from "time-guard";
610
+ import relativeTimePlugin from "time-guard/plugins/relative-time";
611
+
612
+ // Install plugin once
613
+ PluginManager.use(relativeTimePlugin, TimeGuard);
614
+
615
+ // Now use relative time methods
616
+ const date = TimeGuard.from("2024-01-15");
617
+
618
+ // Relative to now
619
+ date.fromNow(); // "2 months ago"
620
+ date.toNow(); // "in 2 months"
621
+
622
+ // Without suffix
623
+ date.fromNow(true); // "2 months"
624
+ date.toNow(true); // "2 months"
625
+
626
+ // Relative to another date
627
+ const other = TimeGuard.from("2024-02-15");
628
+ date.from(other); // "a month ago"
629
+ date.to(other); // "in a month"
630
+
631
+ // Humanize duration
632
+ date.humanize(other); // "a month"
633
+ date.humanize(other, true); // "a month" (exact mode)
634
+ ```
635
+
636
+ **Supported Relative Time Formats:**
637
+
638
+ ```
639
+ "a few seconds ago" // Very recent
640
+ "a minute ago" / "2 minutes ago"
641
+ "an hour ago" / "3 hours ago"
642
+ "a day ago" / "5 days ago"
643
+ "a month ago" / "2 months ago"
644
+ "a year ago" / "3 years ago"
645
+ "in a few seconds" // Future
646
+ "in a minute" / "in 2 minutes"
647
+ "in an hour" / "in 3 hours"
648
+ "in a day" / "in 5 days"
649
+ "in a month" / "in 2 months"
650
+ "in a year" / "in 3 years"
651
+ ```
652
+
653
+ ---
654
+
655
+ ### 2️⃣ Duration Plugin
656
+
657
+ ISO 8601 duration support with advanced calculations.
658
+
659
+ ```typescript
660
+ import { TimeGuard } from "time-guard";
661
+ import { Duration, durationPlugin } from "time-guard/plugins/duration";
662
+ import { PluginManager } from "time-guard";
663
+
664
+ // Install plugin
665
+ PluginManager.use(durationPlugin, TimeGuard);
666
+
667
+ // ===== Create Durations =====
668
+
669
+ // From object
670
+ const duration1 = new Duration({
671
+ years: 2,
672
+ months: 3,
673
+ days: 4,
674
+ hours: 12,
675
+ minutes: 30,
676
+ });
677
+
678
+ // From ISO 8601 string
679
+ const duration2 = Duration.fromISO("P3Y6M4DT12H30M5S");
680
+ // P = Period marker
681
+ // 3Y = 3 years
682
+ // 6M = 6 months
683
+ // 4D = 4 days
684
+ // T = Time marker
685
+ // 12H = 12 hours
686
+ // 30M = 30 minutes
687
+ // 5S = 5 seconds
688
+
689
+ // From TimeGuard dates
690
+ const start = TimeGuard.from("2024-01-15");
691
+ const end = TimeGuard.from("2024-05-20");
692
+ const between = Duration.between(start, end);
693
+ // { years: 0, months: 4, days: 5, ... }
694
+
695
+ // ===== Duration Operations =====
696
+
697
+ // Get ISO string
698
+ duration1.toISO(); // "P2Y3M4DT12H30M"
699
+
700
+ // Get total in different units
701
+ duration1.asDays(); // Total days
702
+ duration1.asHours(); // Total hours
703
+ duration1.asSeconds(); // Total seconds
704
+ duration1.asMilliseconds(); // Total milliseconds
705
+
706
+ // Humanize
707
+ duration1.humanize(); // "2 years, 3 months, 4 days, 12 hours, 30 minutes"
708
+ duration1.humanize("es"); // Spanish: "2 años, 3 meses..."
709
+ duration1.humanize("fr"); // French: "2 ans, 3 mois..."
710
+
711
+ // Get components
712
+ duration1.years;
713
+ duration1.months;
714
+ duration1.days;
715
+ duration1.hours;
716
+ duration1.minutes;
717
+ duration1.seconds;
718
+ duration1.milliseconds;
719
+
720
+ // Clone
721
+ const copy = duration1.clone();
722
+
723
+ // Arithmetic
724
+ duration1.add(new Duration({ days: 5 }));
725
+ duration1.subtract(new Duration({ hours: 2 }));
726
+ duration1.multiply(2); // Double the duration
727
+ duration1.negate(); // Reverse direction
728
+ ```
729
+
730
+ **ISO 8601 Duration Examples:**
731
+
732
+ ```typescript
733
+ Duration.fromISO("P1Y"); // 1 year
734
+ Duration.fromISO("P3M"); // 3 months
735
+ Duration.fromISO("P1W"); // 1 week (7 days)
736
+ Duration.fromISO("P1D"); // 1 day
737
+ Duration.fromISO("PT1H"); // 1 hour
738
+ Duration.fromISO("PT30M"); // 30 minutes
739
+ Duration.fromISO("PT45S"); // 45 seconds
740
+ Duration.fromISO("P1Y2M3DT4H5M6S"); // Complex: 1 year, 2 months, ...
741
+ Duration.fromISO("-P1D"); // Negative: -1 day
742
+ ```
743
+
744
+ ---
745
+
746
+ ### 3️⃣ Advanced Format Plugin
747
+
748
+ Extended format tokens for specialized formatting needs.
749
+
750
+ ```typescript
751
+ import { TimeGuard, PluginManager } from "time-guard";
752
+ import advancedFormatPlugin from "time-guard/plugins/advanced-format";
753
+
754
+ // Install plugin
755
+ PluginManager.use(advancedFormatPlugin, TimeGuard);
756
+
757
+ const date = TimeGuard.from("2024-03-13 14:30:00");
758
+
759
+ // Advanced tokens become available
760
+ date.format("Do MMMM YYYY"); // "13th March 2024"
761
+ date.format("Q [Q] YYYY"); // "1 Q 2024"
762
+ date.format("[Week] w, YYYY"); // "Week 11, 2024"
763
+ date.format("W [of] ww"); // "11 of 11"
764
+ date.format("gggg-[W]ww"); // "2024-W11" (ISO week)
765
+ date.format("GGGG-[W]WW"); // 2024-W11 (alternative)
766
+
767
+ // Timezone abbreviation
768
+ date.format("HH:mm zzz"); // "14:30 UTC"
769
+
770
+ // 24-hour (k = 1-24 instead of 0-23)
771
+ date.format("k:mm"); // "14:30"
772
+
773
+ // Unix timestamps
774
+ date.format("X"); // Unix seconds
775
+ date.format("x"); // Unix milliseconds
776
+ ```
777
+
778
+ **Advanced Format Tokens:**
779
+
780
+ ```
781
+ Q // Quarter (1, 2, 3, 4)
782
+ Do // Ordinal day (1st, 2nd, 3rd, etc.)
783
+ w // Week of year (no padding)
784
+ ww // Week of year (zero-padded)
785
+ W // ISO week number
786
+ gggg // ISO week year
787
+ GGGG // Alternative ISO week year
788
+ k / kk // 24-hour format (1-24)
789
+ X // Unix seconds
790
+ x // Unix milliseconds
791
+ zzz // Timezone abbreviation (UTC, EST, etc.)
792
+ ```
793
+
794
+ ---
795
+
796
+ ### Plugin Architecture
797
+
798
+ All plugins implement `ITimeGuardPlugin`:
799
+
800
+ ```typescript
801
+ interface ITimeGuardPlugin {
802
+ name: string;
803
+ version: string;
804
+ install(TimeGuardClass: typeof TimeGuard): void;
805
+ }
806
+ ```
807
+
808
+ ### Creating Custom Plugins
809
+
810
+ ```typescript
811
+ import { TimeGuard } from "time-guard";
812
+ import type { ITimeGuardPlugin } from "time-guard/types";
813
+
814
+ class MyCustomPlugin implements ITimeGuardPlugin {
815
+ name = "my-plugin";
816
+ version = "1.0.0";
817
+
818
+ install(TimeGuardClass: typeof TimeGuard): void {
819
+ // Add method to TimeGuard prototype
820
+ (TimeGuardClass.prototype as any).myMethod = function () {
821
+ return "Hello from my plugin!";
822
+ };
823
+ }
824
+ }
825
+
826
+ // Use it
827
+ const plugin = new MyCustomPlugin();
828
+ PluginManager.use(plugin, TimeGuard);
829
+
830
+ // Now available
831
+ const date = TimeGuard.now();
832
+ date.myMethod(); // "Hello from my plugin!"
833
+ ```
834
+
835
+ **📖 Full Plugin Details:** See [PLUGINS.md](PLUGINS.md) for extended documentation.
836
+
837
+ ---
838
+
839
+ ## 🎯 Complete API Reference
840
+
841
+ ### Factory Methods
842
+
843
+ ```typescript
844
+ // Create current date/time
845
+ TimeGuard.now();
846
+ TimeGuard.now({ locale: "es", timezone: "America/Mexico_City" });
847
+
848
+ // Create from various inputs
849
+ TimeGuard.from("2024-03-13");
850
+ TimeGuard.from("2024-03-13T14:30:00");
851
+ TimeGuard.from(new Date());
852
+ TimeGuard.from(1234567890000); // milliseconds
853
+ TimeGuard.from(1234567890, { timezone: "UTC" }); // seconds
854
+ TimeGuard.from("2024-03-13", { locale: "es" });
855
+
856
+ // Create from Temporal object
857
+ TimeGuard.fromTemporal(temporalPlainDateTime, config);
858
+ ```
859
+
860
+ ### 🔄 Conversion Methods
861
+
862
+ ```typescript
863
+ const date = TimeGuard.from("2024-03-13 14:30:45");
864
+
865
+ date.toDate(); // Convert to JavaScript Date
866
+ date.toTemporal(); // Get underlying Temporal object
867
+ date.toISOString(); // ISO 8601: "2024-03-13T14:30:45Z"
868
+ date.toJSON(); // JSON serialization (ISO string)
869
+ date.toString(); // Human readable: "2024-03-13 14:30:45"
870
+
871
+ date.valueOf(); // Milliseconds since epoch
872
+ date.unix(); // Seconds since epoch
873
+ ```
874
+
875
+ ### ➕ Manipulation Methods
876
+
877
+ ```typescript
878
+ const date = TimeGuard.from("2024-03-13 14:30:00");
879
+
880
+ // Add time - accepts partial record of units
881
+ date.add({ days: 5 });
882
+ date.add({ months: 1, days: 5 });
883
+ date.add({ years: 1, hours: 2, minutes: 30 });
884
+
885
+ // Subtract time - same syntax as add
886
+ date.subtract({ days: 5 });
887
+ date.subtract({ months: 1 });
888
+
889
+ // Set specific component(s)
890
+ date.set({ day: 15 }); // Keep other components
891
+ date.set({ hour: 10, minute: 0 });
892
+ date.set({ year: 2025, month: 1, day: 1 });
893
+
894
+ // Start/End of period
895
+ date.startOf("year"); // 2024-01-01 00:00:00
896
+ date.startOf("month"); // 2024-03-01 00:00:00
897
+ date.startOf("day"); // 2024-03-13 00:00:00
898
+ date.startOf("hour"); // 2024-03-13 14:00:00
899
+ date.endOf("year"); // 2024-12-31 23:59:59
900
+ date.endOf("month"); // 2024-03-31 23:59:59
901
+
902
+ date.clone(); // Create independent copy
903
+ ```
904
+
905
+ ### 🔍 Component Accessors (Getters)
906
+
907
+ ```typescript
908
+ const date = TimeGuard.from("2024-03-13 14:30:45.123");
909
+
910
+ // Date components
911
+ date.year(); // 2024
912
+ date.month(); // 3 (January = 1, December = 12)
913
+ date.day(); // 13
914
+ date.quarter(); // 1 (Q1, Q2, Q3, or Q4)
915
+
916
+ // Time components
917
+ date.hour(); // 14
918
+ date.minute(); // 30
919
+ date.second(); // 45
920
+ date.millisecond(); // 123
921
+
922
+ // Week/Day information
923
+ date.dayOfWeek(); // 3 (1=Sunday, 7=Saturday)
924
+ date.dayOfYear(); // 73
925
+ date.weekOfYear(); // 11
926
+
927
+ // Month/Year information
928
+ date.daysInMonth(); // 31
929
+ date.daysInYear(); // 366 (leap year)
930
+ date.inLeapYear(); // true
931
+ ```
932
+
933
+ ### ⚖️ Comparison Methods
934
+
935
+ ```typescript
936
+ const date1 = TimeGuard.from("2024-03-13");
937
+ const date2 = TimeGuard.from("2024-03-20");
938
+
939
+ // Direct comparison
940
+ date1.isBefore(date2); // true
941
+ date1.isAfter(date2); // false
942
+ date1.isSame(date1); // true
943
+
944
+ // Unit-specific comparison
945
+ date1.isSame(date2, "month"); // true (same month)
946
+ date1.isSame(date2, "year"); // true (same year)
947
+ date1.isSame(date2, "day"); // false (different day)
948
+
949
+ // Range checking
950
+ date1.isBetween(date1, date2); // true
951
+ date1.isBetween(date1, date2, undefined, "[]"); // inclusive both ends
952
+ date1.isBetween(date1, date2, undefined, "()"); // exclusive both ends
953
+ date1.isBetween(date1, date2, "month", "[]"); // granular range
954
+
955
+ // Calculate difference
956
+ date1.diff(date2, "days"); // -7
957
+ date1.diff(date2, "millisecond"); // difference in ms
958
+ date1.diff(date2, "months"); // -0
959
+ ```
960
+
961
+ ### 📊 Advanced Calculations
962
+
963
+ ```typescript
964
+ const date = TimeGuard.from("2024-01-15");
965
+ const future = TimeGuard.from("2024-05-20");
966
+
967
+ // Duration: Get complete breakdown
968
+ const duration = date.until(future);
969
+ // { years: 0, months: 4, days: 5, hours: 0, minutes: 0, seconds: 0, milliseconds: 0 }
970
+
971
+ // Rounding: Precision control
972
+ date.round({ smallestUnit: "millisecond" }); // Default, no change
973
+ date.round({ smallestUnit: "second" }); // Removes milliseconds
974
+ date.round({ smallestUnit: "minute" }); // 2024-03-13 14:30:00
975
+ date.round({ smallestUnit: "hour" }); // 2024-03-13 14:00:00
976
+ date.round({ smallestUnit: "day" }); // 2024-03-13 00:00:00
977
+
978
+ // Rounding modes
979
+ date.round({
980
+ smallestUnit: "minute",
981
+ roundingMode: "halfExpand", // Default: round to nearest
982
+ });
983
+
984
+ date.round({
985
+ smallestUnit: "minute",
986
+ roundingMode: "ceil", // Always round up
987
+ });
988
+ ```
989
+
990
+ ### 🌍 Locale & Timezone
991
+
992
+ ```typescript
993
+ const date = TimeGuard.from("2024-03-13 14:30:00");
994
+
995
+ // Get/Set locale
996
+ date.locale(); // Returns current locale: 'en'
997
+ date.locale("es"); // Set locale, returns new instance
998
+
999
+ // Format in different locales
1000
+ date.format("YYYY-MM-DD"); // 2024-03-13
1001
+ date.locale("es").format("DD MMMM YYYY"); // 13 marzo 2024
1002
+ date.locale("es-mx").format("DD/MM/YYYY"); // 13/03/2024
1003
+ date.locale("fr").format("dddd, DD MMMM YYYY"); // mercredi, 13 mars 2024
1004
+ date.locale("de").format("DD. MMMM YYYY"); // 13. März 2024
1005
+ date.locale("ja").format("YYYY年M月D日"); // 2024年3月13日
1006
+ date.locale("zh-cn").format("YYYY年M月D日"); // 2024年3月13日
1007
+ date.locale("ar").format("DD MMMM YYYY"); // 13 مارس 2024
1008
+
1009
+ // Get/Set timezone
1010
+ date.timezone(); // Returns current timezone: 'UTC'
1011
+ const inNYC = date.timezone("America/New_York");
1012
+ const inTokyo = date.timezone("Asia/Tokyo");
1013
+ const inDubai = date.timezone("Asia/Dubai");
1014
+
1015
+ // Format with timezone info
1016
+ inNYC.format("YYYY-MM-DD HH:mm:ss Z"); // 2024-03-13 10:30:00 -04:00
1017
+ inTokyo.format("YYYY-MM-DD HH:mm:ss Z"); // 2024-03-13 23:30:00 +09:00
1018
+
1019
+ // Get all available locales
1020
+ TimeGuard.getAvailableLocales(); // Array of 40+ locale codes
1021
+ ```
1022
+
1023
+ ### 🎨 Format Patterns
1024
+
1025
+ #### Format Presets
1026
+
1027
+ ```typescript
1028
+ const date = TimeGuard.from("2024-03-13 14:30:45.123");
1029
+
1030
+ // Built-in presets
1031
+ date.format("iso"); // 2024-03-13T14:30:45.123Z
1032
+ date.format("date"); // 2024-03-13
1033
+ date.format("time"); // 14:30:45
1034
+ date.format("datetime"); // 2024-03-13 14:30:45
1035
+ date.format("rfc2822"); // Wed, 13 Mar 2024 14:30:45 +0000
1036
+ date.format("rfc3339"); // 2024-03-13T14:30:45Z
1037
+ date.format("utc"); // 2024-03-13T14:30:45.123Z
1038
+ ```
1039
+
1040
+ #### Format Tokens
1041
+
1042
+ ```typescript
1043
+ // Year
1044
+ 'YYYY' // 2024 (4-digit)
1045
+ 'YY' // 24 (2-digit)
1046
+
1047
+ // Month
1048
+ 'MMMM' // March
1049
+ 'MMM' // Mar
1050
+ 'MM' // 03 (zero-padded)
1051
+ 'M' // 3 (no padding)
1052
+
1053
+ // Day
1054
+ 'DDDD' or 'DDD' // Monday (full day name)
1055
+ 'ddd' // Mon (abbreviated)
1056
+ 'DD' // 13 (zero-padded)
1057
+ 'D' // 13 (no padding)
1058
+
1059
+ // Hours, minutes, seconds
1060
+ 'HH' // 14 (24-hour, zero-padded)
1061
+ 'H' // 14
1062
+ 'hh' // 02 (12-hour, zero-padded)
1063
+ 'h' // 2
1064
+ 'mm' // 30
1065
+ 'm' // 30
1066
+ 'ss' // 45
1067
+ 's' // 45
1068
+ 'A' // AM or PM
1069
+ 'a' // am or pm
1070
+
1071
+ // Milliseconds & Week
1072
+ 'SSS' // 123 (milliseconds)
1073
+ 'SS' // 12
1074
+ 'S' // 1
1075
+ 'ww' // 11 (week with padding)
1076
+ 'w' // 11 (week no padding)
1077
+
1078
+ // Escaped text
1079
+ '[text]' // Protects text: [UTC]
1080
+ '"text"' // Alternative protection: "o'clock"
1081
+ ```
1082
+
1083
+ #### Custom Format Examples
1084
+
1085
+ ```typescript
1086
+ date.format("YYYY-MM-DD"); // 2024-03-13
1087
+ date.format("DD/MM/YYYY"); // 13/03/2024
1088
+ date.format("MMMM D, YYYY"); // March 13, 2024
1089
+ date.format("dddd, MMMM D, YYYY"); // Wednesday, March 13, 2024
1090
+ date.format("DD-MMMM-YY"); // 13-Mar-24
1091
+ date.format("h:mm A"); // 2:30 PM
1092
+ date.format("HH:mm:ss"); // 14:30:45
1093
+ date.format("[Today is] dddd"); // Today is Wednesday
1094
+ date.format("HH:mm [UTC]"); // 14:30 UTC
1095
+ date.format('DD/MM/YYYY "at" HH:mm'); // 13/03/2024 at 14:30
1096
+ ```
1097
+
1098
+ **📖 Complete Format Guide:** See [EXAMPLES.md](EXAMPLES.md) for more patterns and use cases.
1099
+
1100
+ ---
1101
+
1102
+ ## 🧪 Testing
1103
+
1104
+ TimeGuard includes **530+ comprehensive tests** covering:
1105
+
1106
+ - ✅ Core functionality (creation, manipulation, querying)
1107
+ - ✅ Advanced features (timezones, locales, formatting)
1108
+ - ✅ Edge cases (leap years, month boundaries, DST)
1109
+ - ✅ SOLID principle validation
1110
+ - ✅ Type safety verification
1111
+
1112
+ ### Run Tests
1113
+
1114
+ ```bash
1115
+ # Run all tests
1116
+ npm test
1117
+
1118
+ # Run with coverage
1119
+ npm test -- --coverage
1120
+
1121
+ # Run specific test file
1122
+ npm test -- locales.test.ts
1123
+
1124
+ # Watch mode
1125
+ npm test -- --watch
1126
+ ```
1127
+
1128
+ ### Test Coverage
1129
+
1130
+ ```
1131
+ Core functionality: 65+ tests
1132
+ Advanced features: 50+ tests
1133
+ Locale support: 100+ tests
1134
+ Integration scenarios: 250+ tests
1135
+ Edge cases: 65+ tests
1136
+ ```
1137
+
1138
+ ---
1139
+
1140
+ ## 🏛️ Architecture
1141
+
1142
+ TimeGuard is built on **SOLID principles** ensuring clean, maintainable, and extensible code:
1143
+
1144
+ ### Key Principles
1145
+
1146
+ - **Single Responsibility** - Each class has one reason to change
1147
+ - **Open/Closed** - Open for extension, closed for modification
1148
+ - **Liskov Substitution** - Proper interface contracts
1149
+ - **Interface Segregation** - Minimal, focused interfaces
1150
+ - **Dependency Inversion** - Depend on abstractions, not concretions
1151
+
1152
+ ### Design Patterns
1153
+
1154
+ - **Factory Pattern** - Date creation and parsing
1155
+ - **Adapter Pattern** - Temporal API abstraction
1156
+ - **Strategy Pattern** - Multiple formatting strategies
1157
+ - **Singleton Pattern** - Locale manager
1158
+ - **Facade Pattern** - Simple public API
1159
+ - **Immutable Pattern** - Safe data handling
1160
+
1161
+ **📖 Deep Dive:** See [ARCHITECTURE.md](ARCHITECTURE.md) for detailed architecture explanation.
1162
+
1163
+ ---
1164
+
1165
+ ## 🔧 Development
1166
+
1167
+ ### Build
1168
+
1169
+ ```bash
1170
+ # Build for production
1171
+ npm run build
1172
+
1173
+ # Watch mode for development
1174
+ npm run dev
1175
+ ```
1176
+
1177
+ ### Project Structure
1178
+
1179
+ ```
1180
+ time-guard/
1181
+ ├── src/
1182
+ │ ├── index.ts # Public API exports
1183
+ │ ├── types.ts # Type definitions
1184
+ │ ├── time-guard.ts # Main class
1185
+ │ ├── adapters/
1186
+ │ │ └── temporal.adapter.ts # Temporal API wrapper
1187
+ │ ├── formatters/
1188
+ │ │ └── date.formatter.ts # Format strategies
1189
+ │ └── locales/
1190
+ │ ├── index.ts # Locale registry
1191
+ │ └── ... # 9+ locale files
1192
+ ├── test/
1193
+ │ ├── time-guard.test.ts # Core tests
1194
+ │ ├── advanced.test.ts # Advanced tests
1195
+ │ └── locales.test.ts # Locale tests
1196
+ └── docs/
1197
+ ├── ARCHITECTURE.md # Architecture guide
1198
+ ├── EXAMPLES.md # Usage examples
1199
+ └── LOCALES.md # Locale documentation
1200
+ ```
1201
+
1202
+ ---
1203
+
1204
+ ## 🤝 Contributing
1205
+
1206
+ We welcome contributions! Please:
1207
+
1208
+ 1. Follow SOLID principles and existing code patterns
1209
+ 2. Write tests for new features
1210
+ 3. Update documentation
1211
+ 4. Ensure all tests pass (`npm test`)
1212
+ 5. Check types pass (`npx tsc --noEmit`)
1213
+
1214
+ ---
1215
+
1216
+ ## 📄 License
1217
+
1218
+ MIT License © 2024 Berea-Soft
1219
+
1220
+ See [LICENSE](LICENSE) file for details.
1221
+
1222
+ ---
1223
+
1224
+ ## 🔗 Quick Links
1225
+
1226
+ - 📖 [Full API Reference](EXAMPLES.md)
1227
+ - 🏛️ [Architecture Guide](ARCHITECTURE.md)
1228
+ - 🌍 [Localization Guide](LOCALES.md)
1229
+ - 🐛 [Issue Tracker](https://github.com/bereasoftware/time-guard/issues)
1230
+ - 💬 [Discussions](https://github.com/bereasoftware/time-guard/discussions)
1231
+
1232
+ ---
1233
+
1234
+ ## 📞 Support
1235
+
1236
+ For questions, issues, or feature requests:
1237
+
1238
+ - Open an issue on GitHub
1239
+ - Start a discussion
1240
+ - Check existing documentation
1241
+
1242
+ ---
1243
+
1244
+ ---
1245
+
1246
+ ## Built with ❤️ by Berea-Soft
1247
+
1248
+ A modern date/time library with SOLID principles and TypeScript