@hy_ong/zod-kit 0.2.0 → 0.2.2

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.
Files changed (191) hide show
  1. package/.github/workflows/ci.yml +24 -0
  2. package/CLAUDE.md +64 -22
  3. package/dist/chunk-2SWEVDFZ.js +134 -0
  4. package/dist/chunk-32JI34CV.cjs +146 -0
  5. package/dist/chunk-42C5OHRK.js +71 -0
  6. package/dist/chunk-46VAH2BJ.js +160 -0
  7. package/dist/chunk-5JGTDL3Y.js +87 -0
  8. package/dist/chunk-5LEXCVLX.js +257 -0
  9. package/dist/chunk-6AAP4LPF.js +2606 -0
  10. package/dist/chunk-B4EZYZOK.cjs +215 -0
  11. package/dist/chunk-COYKBWTI.js +161 -0
  12. package/dist/chunk-DFJZ3NS2.cjs +151 -0
  13. package/dist/chunk-EDHT4LPO.js +118 -0
  14. package/dist/chunk-EGHL277K.cjs +165 -0
  15. package/dist/chunk-ERH4NIMU.cjs +69 -0
  16. package/dist/chunk-FM3EZ72O.js +165 -0
  17. package/dist/chunk-GJIRDBZJ.cjs +90 -0
  18. package/dist/chunk-H2XTEM4M.js +696 -0
  19. package/dist/chunk-HMSM6FFA.cjs +181 -0
  20. package/dist/chunk-HTEHINI7.cjs +177 -0
  21. package/dist/chunk-JOLSGZGN.cjs +696 -0
  22. package/dist/chunk-JXY7APBU.js +69 -0
  23. package/dist/chunk-K2UOY6TB.js +136 -0
  24. package/dist/chunk-KFOHKTFD.js +61 -0
  25. package/dist/chunk-L4HSIKTU.cjs +135 -0
  26. package/dist/chunk-LH7ZB4BK.js +124 -0
  27. package/dist/chunk-LL4ZWLGO.js +90 -0
  28. package/dist/chunk-M6MTP3NY.cjs +99 -0
  29. package/dist/chunk-MHJFYYGV.js +215 -0
  30. package/dist/chunk-MINMXGW3.js +135 -0
  31. package/dist/chunk-MM7IL2RG.js +181 -0
  32. package/dist/chunk-OPQJWHXN.cjs +301 -0
  33. package/dist/chunk-ORFHDJII.cjs +136 -0
  34. package/dist/chunk-ORVV4MCF.cjs +87 -0
  35. package/dist/chunk-QICQ6YEY.js +75 -0
  36. package/dist/chunk-RKUQREMW.js +127 -0
  37. package/dist/chunk-RO47DKQG.js +146 -0
  38. package/dist/chunk-RRPXIRTQ.cjs +257 -0
  39. package/dist/chunk-RYFG2GKM.cjs +118 -0
  40. package/dist/chunk-STNHTRG7.cjs +124 -0
  41. package/dist/chunk-TFGS34VD.cjs +71 -0
  42. package/dist/chunk-TQXDUMML.cjs +61 -0
  43. package/dist/chunk-UBK3VCVH.cjs +134 -0
  44. package/dist/chunk-UCOXAZJF.cjs +2606 -0
  45. package/dist/chunk-UQZKFAFX.js +130 -0
  46. package/dist/chunk-VB2KV2ZM.cjs +130 -0
  47. package/dist/chunk-WABKPFPK.js +151 -0
  48. package/dist/chunk-WDI4QJMQ.js +177 -0
  49. package/dist/chunk-YDH3L27K.cjs +127 -0
  50. package/dist/chunk-YIM3D2AD.js +99 -0
  51. package/dist/chunk-YPSEIDUR.cjs +160 -0
  52. package/dist/chunk-ZNJLWJX3.cjs +75 -0
  53. package/dist/chunk-ZTFCJCPO.cjs +161 -0
  54. package/dist/chunk-ZXUMK2RR.js +301 -0
  55. package/dist/common/boolean.cjs +7 -0
  56. package/dist/common/boolean.d.cts +119 -0
  57. package/dist/common/boolean.d.ts +119 -0
  58. package/dist/common/boolean.js +7 -0
  59. package/dist/common/color.cjs +9 -0
  60. package/dist/common/color.d.cts +26 -0
  61. package/dist/common/color.d.ts +26 -0
  62. package/dist/common/color.js +9 -0
  63. package/dist/common/coordinate.cjs +11 -0
  64. package/dist/common/coordinate.d.cts +23 -0
  65. package/dist/common/coordinate.d.ts +23 -0
  66. package/dist/common/coordinate.js +11 -0
  67. package/dist/common/credit-card.cjs +11 -0
  68. package/dist/common/credit-card.d.cts +22 -0
  69. package/dist/common/credit-card.d.ts +22 -0
  70. package/dist/common/credit-card.js +11 -0
  71. package/dist/common/date.cjs +7 -0
  72. package/dist/common/date.d.cts +174 -0
  73. package/dist/common/date.d.ts +174 -0
  74. package/dist/common/date.js +7 -0
  75. package/dist/common/datetime.cjs +15 -0
  76. package/dist/common/datetime.d.cts +301 -0
  77. package/dist/common/datetime.d.ts +301 -0
  78. package/dist/common/datetime.js +15 -0
  79. package/dist/common/email.cjs +7 -0
  80. package/dist/common/email.d.cts +149 -0
  81. package/dist/common/email.d.ts +149 -0
  82. package/dist/common/email.js +7 -0
  83. package/dist/common/file.cjs +7 -0
  84. package/dist/common/file.d.cts +178 -0
  85. package/dist/common/file.d.ts +178 -0
  86. package/dist/common/file.js +7 -0
  87. package/dist/common/id.cjs +13 -0
  88. package/dist/common/id.d.cts +288 -0
  89. package/dist/common/id.d.ts +288 -0
  90. package/dist/common/id.js +13 -0
  91. package/dist/common/ip.cjs +11 -0
  92. package/dist/common/ip.d.cts +25 -0
  93. package/dist/common/ip.d.ts +25 -0
  94. package/dist/common/ip.js +11 -0
  95. package/dist/common/number.cjs +7 -0
  96. package/dist/common/number.d.cts +167 -0
  97. package/dist/common/number.d.ts +167 -0
  98. package/dist/common/number.js +7 -0
  99. package/dist/common/password.cjs +7 -0
  100. package/dist/common/password.d.cts +192 -0
  101. package/dist/common/password.d.ts +192 -0
  102. package/dist/common/password.js +7 -0
  103. package/dist/common/text.cjs +7 -0
  104. package/dist/common/text.d.cts +156 -0
  105. package/dist/common/text.d.ts +156 -0
  106. package/dist/common/text.js +7 -0
  107. package/dist/common/time.cjs +15 -0
  108. package/dist/common/time.d.cts +268 -0
  109. package/dist/common/time.d.ts +268 -0
  110. package/dist/common/time.js +15 -0
  111. package/dist/common/url.cjs +7 -0
  112. package/dist/common/url.d.cts +196 -0
  113. package/dist/common/url.d.ts +196 -0
  114. package/dist/common/url.js +7 -0
  115. package/dist/config-CABSSvAp.d.cts +5 -0
  116. package/dist/config-CABSSvAp.d.ts +5 -0
  117. package/dist/index.cjs +180 -5255
  118. package/dist/index.d.cts +28 -3150
  119. package/dist/index.d.ts +28 -3150
  120. package/dist/index.js +135 -5131
  121. package/dist/taiwan/bank-account.cjs +11 -0
  122. package/dist/taiwan/bank-account.d.cts +22 -0
  123. package/dist/taiwan/bank-account.d.ts +22 -0
  124. package/dist/taiwan/bank-account.js +11 -0
  125. package/dist/taiwan/business-id.cjs +9 -0
  126. package/dist/taiwan/business-id.d.cts +133 -0
  127. package/dist/taiwan/business-id.d.ts +133 -0
  128. package/dist/taiwan/business-id.js +9 -0
  129. package/dist/taiwan/fax.cjs +9 -0
  130. package/dist/taiwan/fax.d.cts +157 -0
  131. package/dist/taiwan/fax.d.ts +157 -0
  132. package/dist/taiwan/fax.js +9 -0
  133. package/dist/taiwan/invoice.cjs +9 -0
  134. package/dist/taiwan/invoice.d.cts +17 -0
  135. package/dist/taiwan/invoice.d.ts +17 -0
  136. package/dist/taiwan/invoice.js +9 -0
  137. package/dist/taiwan/license-plate.cjs +9 -0
  138. package/dist/taiwan/license-plate.d.cts +19 -0
  139. package/dist/taiwan/license-plate.d.ts +19 -0
  140. package/dist/taiwan/license-plate.js +9 -0
  141. package/dist/taiwan/mobile.cjs +9 -0
  142. package/dist/taiwan/mobile.d.cts +146 -0
  143. package/dist/taiwan/mobile.d.ts +146 -0
  144. package/dist/taiwan/mobile.js +9 -0
  145. package/dist/taiwan/national-id.cjs +15 -0
  146. package/dist/taiwan/national-id.d.cts +214 -0
  147. package/dist/taiwan/national-id.d.ts +214 -0
  148. package/dist/taiwan/national-id.js +15 -0
  149. package/dist/taiwan/passport.cjs +9 -0
  150. package/dist/taiwan/passport.d.cts +19 -0
  151. package/dist/taiwan/passport.d.ts +19 -0
  152. package/dist/taiwan/passport.js +9 -0
  153. package/dist/taiwan/postal-code.cjs +17 -0
  154. package/dist/taiwan/postal-code.d.cts +237 -0
  155. package/dist/taiwan/postal-code.d.ts +237 -0
  156. package/dist/taiwan/postal-code.js +17 -0
  157. package/dist/taiwan/tel.cjs +9 -0
  158. package/dist/taiwan/tel.d.cts +162 -0
  159. package/dist/taiwan/tel.d.ts +162 -0
  160. package/dist/taiwan/tel.js +9 -0
  161. package/package.json +132 -6
  162. package/src/i18n/locales/en-GB.json +51 -0
  163. package/src/i18n/locales/en-US.json +52 -1
  164. package/src/i18n/locales/id-ID.json +51 -0
  165. package/src/i18n/locales/ja-JP.json +51 -0
  166. package/src/i18n/locales/ko-KR.json +51 -0
  167. package/src/i18n/locales/ms-MY.json +51 -0
  168. package/src/i18n/locales/th-TH.json +51 -0
  169. package/src/i18n/locales/vi-VN.json +51 -0
  170. package/src/i18n/locales/zh-CN.json +51 -0
  171. package/src/i18n/locales/zh-TW.json +51 -0
  172. package/src/index.ts +10 -2
  173. package/src/validators/common/color.ts +192 -0
  174. package/src/validators/common/coordinate.ts +159 -0
  175. package/src/validators/common/credit-card.ts +134 -0
  176. package/src/validators/common/id.ts +45 -3
  177. package/src/validators/common/ip.ts +210 -0
  178. package/src/validators/taiwan/bank-account.ts +176 -0
  179. package/src/validators/taiwan/invoice.ts +84 -0
  180. package/src/validators/taiwan/license-plate.ts +110 -0
  181. package/src/validators/taiwan/passport.ts +103 -0
  182. package/tests/common/color.test.ts +587 -0
  183. package/tests/common/coordinate.test.ts +345 -0
  184. package/tests/common/credit-card.test.ts +378 -0
  185. package/tests/common/id.test.ts +68 -3
  186. package/tests/common/ip.test.ts +419 -0
  187. package/tests/taiwan/bank-account.test.ts +286 -0
  188. package/tests/taiwan/invoice.test.ts +227 -0
  189. package/tests/taiwan/license-plate.test.ts +280 -0
  190. package/tests/taiwan/passport.test.ts +277 -0
  191. package/tsup.config.ts +36 -0
@@ -0,0 +1,268 @@
1
+ import { ZodString, ZodNullable } from 'zod';
2
+ import { L as Locale } from '../config-CABSSvAp.cjs';
3
+
4
+ /**
5
+ * @fileoverview Time validator for Zod Kit
6
+ *
7
+ * Provides comprehensive time validation with support for multiple time formats,
8
+ * hour/minute constraints, and advanced time-based validation options.
9
+ *
10
+ * @author Ong Hoe Yuan
11
+ * @version 0.0.5
12
+ */
13
+
14
+ /**
15
+ * Type definition for time validation error messages
16
+ *
17
+ * @interface TimeMessages
18
+ * @property {string} [required] - Message when field is required but empty
19
+ * @property {string} [invalid] - Message when time format is invalid
20
+ * @property {string} [format] - Message when time doesn't match expected format
21
+ * @property {string} [min] - Message when time is before minimum allowed
22
+ * @property {string} [max] - Message when time is after maximum allowed
23
+ * @property {string} [hour] - Message when hour is outside allowed range
24
+ * @property {string} [minute] - Message when minute doesn't match step requirement
25
+ * @property {string} [second] - Message when second doesn't match step requirement
26
+ * @property {string} [includes] - Message when time doesn't contain required string
27
+ * @property {string} [excludes] - Message when time contains forbidden string
28
+ * @property {string} [customRegex] - Message when custom regex validation fails
29
+ * @property {string} [notInWhitelist] - Message when value is not in whitelist
30
+ */
31
+ type TimeMessages = {
32
+ required?: string;
33
+ invalid?: string;
34
+ format?: string;
35
+ min?: string;
36
+ max?: string;
37
+ hour?: string;
38
+ minute?: string;
39
+ second?: string;
40
+ includes?: string;
41
+ excludes?: string;
42
+ customRegex?: string;
43
+ notInWhitelist?: string;
44
+ };
45
+ /**
46
+ * Supported time formats for validation
47
+ *
48
+ * @typedef {string} TimeFormat
49
+ *
50
+ * Available formats:
51
+ * - HH:mm: 24-hour format with leading zeros (14:30, 09:30)
52
+ * - HH:mm:ss: 24-hour format with seconds (14:30:45, 09:30:15)
53
+ * - hh:mm A: 12-hour format with AM/PM (02:30 PM, 09:30 AM)
54
+ * - hh:mm:ss A: 12-hour format with seconds and AM/PM (02:30:45 PM)
55
+ * - H:mm: 24-hour format without leading zeros (14:30, 9:30)
56
+ * - h:mm A: 12-hour format without leading zeros (2:30 PM, 9:30 AM)
57
+ */
58
+ type TimeFormat = "HH:mm" | "HH:mm:ss" | "hh:mm A" | "hh:mm:ss A" | "H:mm" | "h:mm A";
59
+ /**
60
+ * Configuration options for time validation
61
+ *
62
+ * @template IsRequired - Whether the field is required (affects return type)
63
+ *
64
+ * @interface TimeOptions
65
+ * @property {IsRequired} [required=true] - Whether the field is required
66
+ * @property {TimeFormat} [format="HH:mm"] - Expected time format
67
+ * @property {string} [min] - Minimum allowed time (e.g., "09:00")
68
+ * @property {string} [max] - Maximum allowed time (e.g., "17:00")
69
+ * @property {number} [minHour] - Minimum allowed hour (0-23)
70
+ * @property {number} [maxHour] - Maximum allowed hour (0-23)
71
+ * @property {number[]} [allowedHours] - Specific hours that are allowed
72
+ * @property {number} [minuteStep] - Required minute intervals (e.g., 15 for :00, :15, :30, :45)
73
+ * @property {number} [secondStep] - Required second intervals
74
+ * @property {string} [includes] - String that must be included in the time
75
+ * @property {string | string[]} [excludes] - String(s) that must not be included
76
+ * @property {RegExp} [regex] - Custom regex for validation (overrides format validation)
77
+ * @property {"trim" | "trimStart" | "trimEnd" | "none"} [trimMode="trim"] - Whitespace handling
78
+ * @property {"upper" | "lower" | "none"} [casing="none"] - Case transformation
79
+ * @property {string[]} [whitelist] - Specific time strings that are always allowed
80
+ * @property {boolean} [whitelistOnly=false] - If true, only values in whitelist are allowed
81
+ * @property {Function} [transform] - Custom transformation function applied before validation
82
+ * @property {string | null} [defaultValue] - Default value when input is empty
83
+ * @property {Record<Locale, TimeMessages>} [i18n] - Custom error messages for different locales
84
+ */
85
+ type TimeOptions<IsRequired extends boolean = true> = {
86
+ format?: TimeFormat;
87
+ min?: string;
88
+ max?: string;
89
+ minHour?: number;
90
+ maxHour?: number;
91
+ allowedHours?: number[];
92
+ minuteStep?: number;
93
+ secondStep?: number;
94
+ includes?: string;
95
+ excludes?: string | string[];
96
+ regex?: RegExp;
97
+ trimMode?: "trim" | "trimStart" | "trimEnd" | "none";
98
+ casing?: "upper" | "lower" | "none";
99
+ whitelist?: string[];
100
+ whitelistOnly?: boolean;
101
+ transform?: (value: string) => string;
102
+ defaultValue?: IsRequired extends true ? string : string | null;
103
+ i18n?: Partial<Record<Locale, Partial<TimeMessages>>>;
104
+ };
105
+ /**
106
+ * Type alias for time validation schema based on required flag
107
+ *
108
+ * @template IsRequired - Whether the field is required
109
+ * @typedef TimeSchema
110
+ * @description Returns ZodString if required, ZodNullable<ZodString> if optional
111
+ */
112
+ type TimeSchema<IsRequired extends boolean> = IsRequired extends true ? ZodString : ZodNullable<ZodString>;
113
+ /**
114
+ * Regular expression patterns for time format validation
115
+ *
116
+ * @constant {Record<TimeFormat, RegExp>} TIME_PATTERNS
117
+ * @description Maps each supported time format to its corresponding regex pattern
118
+ */
119
+ declare const TIME_PATTERNS: Record<TimeFormat, RegExp>;
120
+ /**
121
+ * Parses a time string to minutes since midnight for comparison
122
+ *
123
+ * @param {string} timeStr - The time string to parse
124
+ * @param {TimeFormat} format - The expected time format
125
+ * @returns {number | null} Minutes since midnight (0-1439) or null if parsing fails
126
+ *
127
+ * @description
128
+ * Converts time strings to minutes since midnight for easy comparison and validation.
129
+ * Handles both 12-hour and 24-hour formats with proper AM/PM conversion.
130
+ *
131
+ * @example
132
+ * ```typescript
133
+ * parseTimeToMinutes("14:30", "HH:mm") // 870 (14*60 + 30)
134
+ * parseTimeToMinutes("2:30 PM", "h:mm A") // 870 (14*60 + 30)
135
+ * parseTimeToMinutes("12:00 AM", "hh:mm A") // 0 (midnight)
136
+ * parseTimeToMinutes("12:00 PM", "hh:mm A") // 720 (noon)
137
+ * ```
138
+ */
139
+ declare const parseTimeToMinutes: (timeStr: string, format: TimeFormat) => number | null;
140
+ /**
141
+ * Validates if a time string matches the specified format pattern
142
+ *
143
+ * @param {string} value - The time string to validate
144
+ * @param {TimeFormat} format - The expected time format
145
+ * @returns {boolean} True if the time matches the format pattern
146
+ *
147
+ * @description
148
+ * Performs regex pattern matching to validate time format.
149
+ * Does not validate actual time values (e.g., 25:00 would pass pattern but fail logic).
150
+ *
151
+ * @example
152
+ * ```typescript
153
+ * validateTimeFormat("14:30", "HH:mm") // true
154
+ * validateTimeFormat("2:30 PM", "h:mm A") // true
155
+ * validateTimeFormat("25:00", "HH:mm") // true (pattern matches)
156
+ * validateTimeFormat("14:30", "h:mm A") // false (wrong format)
157
+ * ```
158
+ */
159
+ declare const validateTimeFormat: (value: string, format: TimeFormat) => boolean;
160
+ /**
161
+ * Normalizes time to 24-hour format for internal processing
162
+ *
163
+ * @param {string} timeStr - The time string to normalize
164
+ * @param {TimeFormat} format - The current time format
165
+ * @returns {string | null} Normalized time string or null if parsing fails
166
+ *
167
+ * @description
168
+ * Converts time strings to a standardized 24-hour format for consistent processing.
169
+ * Handles AM/PM conversion and leading zero normalization.
170
+ *
171
+ * @example
172
+ * ```typescript
173
+ * normalizeTime("2:30 PM", "h:mm A") // "14:30"
174
+ * normalizeTime("12:00 AM", "hh:mm A") // "00:00"
175
+ * normalizeTime("9:30", "H:mm") // "09:30"
176
+ * normalizeTime("14:30:45", "HH:mm:ss") // "14:30:45"
177
+ * ```
178
+ */
179
+ declare const normalizeTime: (timeStr: string, format: TimeFormat) => string | null;
180
+ /**
181
+ * Creates a Zod schema for time validation with comprehensive options
182
+ *
183
+ * @template IsRequired - Whether the field is required (affects return type)
184
+ * @param {IsRequired} [required=false] - Whether the field is required
185
+ * @param {Omit<ValidatorOptions<IsRequired>, 'required'>} [options] - Configuration options for validation
186
+ * @returns {TimeSchema<IsRequired>} Zod schema for time validation
187
+ *
188
+ * @description
189
+ * Creates a comprehensive time validator that supports multiple time formats,
190
+ * hour/minute constraints, step validation, and extensive customization options.
191
+ *
192
+ * Features:
193
+ * - Multiple time formats (24-hour, 12-hour, with/without seconds)
194
+ * - Time range validation (min/max)
195
+ * - Hour and minute constraints
196
+ * - Step validation (e.g., 15-minute intervals)
197
+ * - Whitelist/blacklist support
198
+ * - Custom regex patterns
199
+ * - String transformation and case handling
200
+ * - Comprehensive internationalization
201
+ *
202
+ * @example
203
+ * ```typescript
204
+ * // Basic time validation (24-hour format)
205
+ * const basicSchema = time()
206
+ * basicSchema.parse("14:30") // ✓ Valid
207
+ * basicSchema.parse(null) // ✓ Valid (optional)
208
+ *
209
+ * // Required validation
210
+ * const requiredSchema = parse("14:30") // ✓ Valid
211
+ (true)
212
+ * requiredSchema.parse(null) // ✗ Invalid (required)
213
+ *
214
+ * basicSchema.parse("2:30 PM") // ✗ Invalid (wrong format)
215
+ *
216
+ * // 12-hour format with AM/PM
217
+ * const ampmSchema = time(false, { format: "hh:mm A" })
218
+ * ampmSchema.parse("02:30 PM") // ✓ Valid
219
+ * ampmSchema.parse("14:30") // ✗ Invalid (wrong format)
220
+ *
221
+ * // Business hours validation
222
+ * const businessHours = time({
223
+ * format: "HH:mm",
224
+ * minHour: 9,
225
+ * maxHour: 17,
226
+ * minuteStep: 15 // Only :00, :15, :30, :45
227
+ * })
228
+ * businessHours.parse("09:15") // ✓ Valid
229
+ * businessHours.parse("18:00") // ✗ Invalid (after maxHour)
230
+ * businessHours.parse("09:05") // ✗ Invalid (not 15-minute step)
231
+ *
232
+ * // Time range validation
233
+ * const timeRangeSchema = time(false, {
234
+ * min: "09:00",
235
+ * max: "17:00"
236
+ * })
237
+ * timeRangeSchema.parse("12:30") // ✓ Valid
238
+ * timeRangeSchema.parse("08:00") // ✗ Invalid (before min)
239
+ *
240
+ * // Allowed hours only
241
+ * const specificHours = time({
242
+ * allowedHours: [9, 12, 15, 18]
243
+ * })
244
+ * specificHours.parse("12:30") // ✓ Valid
245
+ * specificHours.parse("11:30") // ✗ Invalid (hour not allowed)
246
+ *
247
+ * // Whitelist specific times
248
+ * const whitelistSchema = time(false, {
249
+ * whitelist: ["09:00", "12:00", "17:00"],
250
+ * whitelistOnly: true
251
+ * })
252
+ * whitelistSchema.parse("12:00") // ✓ Valid (in whitelist)
253
+ * whitelistSchema.parse("13:00") // ✗ Invalid (not in whitelist)
254
+ *
255
+ * // Optional with default
256
+ * const optionalSchema = time(false, {
257
+ * defaultValue: "09:00"
258
+ * })
259
+ * optionalSchema.parse("") // ✓ Valid (returns "09:00")
260
+ * ```
261
+ *
262
+ * @throws {z.ZodError} When validation fails with specific error messages
263
+ * @see {@link TimeOptions} for all available configuration options
264
+ * @see {@link TimeFormat} for supported time formats
265
+ */
266
+ declare function time<IsRequired extends boolean = false>(required?: IsRequired, options?: Omit<TimeOptions<IsRequired>, 'required'>): TimeSchema<IsRequired>;
267
+
268
+ export { TIME_PATTERNS, type TimeFormat, type TimeMessages, type TimeOptions, type TimeSchema, normalizeTime, parseTimeToMinutes, time, validateTimeFormat };
@@ -0,0 +1,268 @@
1
+ import { ZodString, ZodNullable } from 'zod';
2
+ import { L as Locale } from '../config-CABSSvAp.js';
3
+
4
+ /**
5
+ * @fileoverview Time validator for Zod Kit
6
+ *
7
+ * Provides comprehensive time validation with support for multiple time formats,
8
+ * hour/minute constraints, and advanced time-based validation options.
9
+ *
10
+ * @author Ong Hoe Yuan
11
+ * @version 0.0.5
12
+ */
13
+
14
+ /**
15
+ * Type definition for time validation error messages
16
+ *
17
+ * @interface TimeMessages
18
+ * @property {string} [required] - Message when field is required but empty
19
+ * @property {string} [invalid] - Message when time format is invalid
20
+ * @property {string} [format] - Message when time doesn't match expected format
21
+ * @property {string} [min] - Message when time is before minimum allowed
22
+ * @property {string} [max] - Message when time is after maximum allowed
23
+ * @property {string} [hour] - Message when hour is outside allowed range
24
+ * @property {string} [minute] - Message when minute doesn't match step requirement
25
+ * @property {string} [second] - Message when second doesn't match step requirement
26
+ * @property {string} [includes] - Message when time doesn't contain required string
27
+ * @property {string} [excludes] - Message when time contains forbidden string
28
+ * @property {string} [customRegex] - Message when custom regex validation fails
29
+ * @property {string} [notInWhitelist] - Message when value is not in whitelist
30
+ */
31
+ type TimeMessages = {
32
+ required?: string;
33
+ invalid?: string;
34
+ format?: string;
35
+ min?: string;
36
+ max?: string;
37
+ hour?: string;
38
+ minute?: string;
39
+ second?: string;
40
+ includes?: string;
41
+ excludes?: string;
42
+ customRegex?: string;
43
+ notInWhitelist?: string;
44
+ };
45
+ /**
46
+ * Supported time formats for validation
47
+ *
48
+ * @typedef {string} TimeFormat
49
+ *
50
+ * Available formats:
51
+ * - HH:mm: 24-hour format with leading zeros (14:30, 09:30)
52
+ * - HH:mm:ss: 24-hour format with seconds (14:30:45, 09:30:15)
53
+ * - hh:mm A: 12-hour format with AM/PM (02:30 PM, 09:30 AM)
54
+ * - hh:mm:ss A: 12-hour format with seconds and AM/PM (02:30:45 PM)
55
+ * - H:mm: 24-hour format without leading zeros (14:30, 9:30)
56
+ * - h:mm A: 12-hour format without leading zeros (2:30 PM, 9:30 AM)
57
+ */
58
+ type TimeFormat = "HH:mm" | "HH:mm:ss" | "hh:mm A" | "hh:mm:ss A" | "H:mm" | "h:mm A";
59
+ /**
60
+ * Configuration options for time validation
61
+ *
62
+ * @template IsRequired - Whether the field is required (affects return type)
63
+ *
64
+ * @interface TimeOptions
65
+ * @property {IsRequired} [required=true] - Whether the field is required
66
+ * @property {TimeFormat} [format="HH:mm"] - Expected time format
67
+ * @property {string} [min] - Minimum allowed time (e.g., "09:00")
68
+ * @property {string} [max] - Maximum allowed time (e.g., "17:00")
69
+ * @property {number} [minHour] - Minimum allowed hour (0-23)
70
+ * @property {number} [maxHour] - Maximum allowed hour (0-23)
71
+ * @property {number[]} [allowedHours] - Specific hours that are allowed
72
+ * @property {number} [minuteStep] - Required minute intervals (e.g., 15 for :00, :15, :30, :45)
73
+ * @property {number} [secondStep] - Required second intervals
74
+ * @property {string} [includes] - String that must be included in the time
75
+ * @property {string | string[]} [excludes] - String(s) that must not be included
76
+ * @property {RegExp} [regex] - Custom regex for validation (overrides format validation)
77
+ * @property {"trim" | "trimStart" | "trimEnd" | "none"} [trimMode="trim"] - Whitespace handling
78
+ * @property {"upper" | "lower" | "none"} [casing="none"] - Case transformation
79
+ * @property {string[]} [whitelist] - Specific time strings that are always allowed
80
+ * @property {boolean} [whitelistOnly=false] - If true, only values in whitelist are allowed
81
+ * @property {Function} [transform] - Custom transformation function applied before validation
82
+ * @property {string | null} [defaultValue] - Default value when input is empty
83
+ * @property {Record<Locale, TimeMessages>} [i18n] - Custom error messages for different locales
84
+ */
85
+ type TimeOptions<IsRequired extends boolean = true> = {
86
+ format?: TimeFormat;
87
+ min?: string;
88
+ max?: string;
89
+ minHour?: number;
90
+ maxHour?: number;
91
+ allowedHours?: number[];
92
+ minuteStep?: number;
93
+ secondStep?: number;
94
+ includes?: string;
95
+ excludes?: string | string[];
96
+ regex?: RegExp;
97
+ trimMode?: "trim" | "trimStart" | "trimEnd" | "none";
98
+ casing?: "upper" | "lower" | "none";
99
+ whitelist?: string[];
100
+ whitelistOnly?: boolean;
101
+ transform?: (value: string) => string;
102
+ defaultValue?: IsRequired extends true ? string : string | null;
103
+ i18n?: Partial<Record<Locale, Partial<TimeMessages>>>;
104
+ };
105
+ /**
106
+ * Type alias for time validation schema based on required flag
107
+ *
108
+ * @template IsRequired - Whether the field is required
109
+ * @typedef TimeSchema
110
+ * @description Returns ZodString if required, ZodNullable<ZodString> if optional
111
+ */
112
+ type TimeSchema<IsRequired extends boolean> = IsRequired extends true ? ZodString : ZodNullable<ZodString>;
113
+ /**
114
+ * Regular expression patterns for time format validation
115
+ *
116
+ * @constant {Record<TimeFormat, RegExp>} TIME_PATTERNS
117
+ * @description Maps each supported time format to its corresponding regex pattern
118
+ */
119
+ declare const TIME_PATTERNS: Record<TimeFormat, RegExp>;
120
+ /**
121
+ * Parses a time string to minutes since midnight for comparison
122
+ *
123
+ * @param {string} timeStr - The time string to parse
124
+ * @param {TimeFormat} format - The expected time format
125
+ * @returns {number | null} Minutes since midnight (0-1439) or null if parsing fails
126
+ *
127
+ * @description
128
+ * Converts time strings to minutes since midnight for easy comparison and validation.
129
+ * Handles both 12-hour and 24-hour formats with proper AM/PM conversion.
130
+ *
131
+ * @example
132
+ * ```typescript
133
+ * parseTimeToMinutes("14:30", "HH:mm") // 870 (14*60 + 30)
134
+ * parseTimeToMinutes("2:30 PM", "h:mm A") // 870 (14*60 + 30)
135
+ * parseTimeToMinutes("12:00 AM", "hh:mm A") // 0 (midnight)
136
+ * parseTimeToMinutes("12:00 PM", "hh:mm A") // 720 (noon)
137
+ * ```
138
+ */
139
+ declare const parseTimeToMinutes: (timeStr: string, format: TimeFormat) => number | null;
140
+ /**
141
+ * Validates if a time string matches the specified format pattern
142
+ *
143
+ * @param {string} value - The time string to validate
144
+ * @param {TimeFormat} format - The expected time format
145
+ * @returns {boolean} True if the time matches the format pattern
146
+ *
147
+ * @description
148
+ * Performs regex pattern matching to validate time format.
149
+ * Does not validate actual time values (e.g., 25:00 would pass pattern but fail logic).
150
+ *
151
+ * @example
152
+ * ```typescript
153
+ * validateTimeFormat("14:30", "HH:mm") // true
154
+ * validateTimeFormat("2:30 PM", "h:mm A") // true
155
+ * validateTimeFormat("25:00", "HH:mm") // true (pattern matches)
156
+ * validateTimeFormat("14:30", "h:mm A") // false (wrong format)
157
+ * ```
158
+ */
159
+ declare const validateTimeFormat: (value: string, format: TimeFormat) => boolean;
160
+ /**
161
+ * Normalizes time to 24-hour format for internal processing
162
+ *
163
+ * @param {string} timeStr - The time string to normalize
164
+ * @param {TimeFormat} format - The current time format
165
+ * @returns {string | null} Normalized time string or null if parsing fails
166
+ *
167
+ * @description
168
+ * Converts time strings to a standardized 24-hour format for consistent processing.
169
+ * Handles AM/PM conversion and leading zero normalization.
170
+ *
171
+ * @example
172
+ * ```typescript
173
+ * normalizeTime("2:30 PM", "h:mm A") // "14:30"
174
+ * normalizeTime("12:00 AM", "hh:mm A") // "00:00"
175
+ * normalizeTime("9:30", "H:mm") // "09:30"
176
+ * normalizeTime("14:30:45", "HH:mm:ss") // "14:30:45"
177
+ * ```
178
+ */
179
+ declare const normalizeTime: (timeStr: string, format: TimeFormat) => string | null;
180
+ /**
181
+ * Creates a Zod schema for time validation with comprehensive options
182
+ *
183
+ * @template IsRequired - Whether the field is required (affects return type)
184
+ * @param {IsRequired} [required=false] - Whether the field is required
185
+ * @param {Omit<ValidatorOptions<IsRequired>, 'required'>} [options] - Configuration options for validation
186
+ * @returns {TimeSchema<IsRequired>} Zod schema for time validation
187
+ *
188
+ * @description
189
+ * Creates a comprehensive time validator that supports multiple time formats,
190
+ * hour/minute constraints, step validation, and extensive customization options.
191
+ *
192
+ * Features:
193
+ * - Multiple time formats (24-hour, 12-hour, with/without seconds)
194
+ * - Time range validation (min/max)
195
+ * - Hour and minute constraints
196
+ * - Step validation (e.g., 15-minute intervals)
197
+ * - Whitelist/blacklist support
198
+ * - Custom regex patterns
199
+ * - String transformation and case handling
200
+ * - Comprehensive internationalization
201
+ *
202
+ * @example
203
+ * ```typescript
204
+ * // Basic time validation (24-hour format)
205
+ * const basicSchema = time()
206
+ * basicSchema.parse("14:30") // ✓ Valid
207
+ * basicSchema.parse(null) // ✓ Valid (optional)
208
+ *
209
+ * // Required validation
210
+ * const requiredSchema = parse("14:30") // ✓ Valid
211
+ (true)
212
+ * requiredSchema.parse(null) // ✗ Invalid (required)
213
+ *
214
+ * basicSchema.parse("2:30 PM") // ✗ Invalid (wrong format)
215
+ *
216
+ * // 12-hour format with AM/PM
217
+ * const ampmSchema = time(false, { format: "hh:mm A" })
218
+ * ampmSchema.parse("02:30 PM") // ✓ Valid
219
+ * ampmSchema.parse("14:30") // ✗ Invalid (wrong format)
220
+ *
221
+ * // Business hours validation
222
+ * const businessHours = time({
223
+ * format: "HH:mm",
224
+ * minHour: 9,
225
+ * maxHour: 17,
226
+ * minuteStep: 15 // Only :00, :15, :30, :45
227
+ * })
228
+ * businessHours.parse("09:15") // ✓ Valid
229
+ * businessHours.parse("18:00") // ✗ Invalid (after maxHour)
230
+ * businessHours.parse("09:05") // ✗ Invalid (not 15-minute step)
231
+ *
232
+ * // Time range validation
233
+ * const timeRangeSchema = time(false, {
234
+ * min: "09:00",
235
+ * max: "17:00"
236
+ * })
237
+ * timeRangeSchema.parse("12:30") // ✓ Valid
238
+ * timeRangeSchema.parse("08:00") // ✗ Invalid (before min)
239
+ *
240
+ * // Allowed hours only
241
+ * const specificHours = time({
242
+ * allowedHours: [9, 12, 15, 18]
243
+ * })
244
+ * specificHours.parse("12:30") // ✓ Valid
245
+ * specificHours.parse("11:30") // ✗ Invalid (hour not allowed)
246
+ *
247
+ * // Whitelist specific times
248
+ * const whitelistSchema = time(false, {
249
+ * whitelist: ["09:00", "12:00", "17:00"],
250
+ * whitelistOnly: true
251
+ * })
252
+ * whitelistSchema.parse("12:00") // ✓ Valid (in whitelist)
253
+ * whitelistSchema.parse("13:00") // ✗ Invalid (not in whitelist)
254
+ *
255
+ * // Optional with default
256
+ * const optionalSchema = time(false, {
257
+ * defaultValue: "09:00"
258
+ * })
259
+ * optionalSchema.parse("") // ✓ Valid (returns "09:00")
260
+ * ```
261
+ *
262
+ * @throws {z.ZodError} When validation fails with specific error messages
263
+ * @see {@link TimeOptions} for all available configuration options
264
+ * @see {@link TimeFormat} for supported time formats
265
+ */
266
+ declare function time<IsRequired extends boolean = false>(required?: IsRequired, options?: Omit<TimeOptions<IsRequired>, 'required'>): TimeSchema<IsRequired>;
267
+
268
+ export { TIME_PATTERNS, type TimeFormat, type TimeMessages, type TimeOptions, type TimeSchema, normalizeTime, parseTimeToMinutes, time, validateTimeFormat };
@@ -0,0 +1,15 @@
1
+ import {
2
+ TIME_PATTERNS,
3
+ normalizeTime,
4
+ parseTimeToMinutes,
5
+ time,
6
+ validateTimeFormat
7
+ } from "../chunk-5LEXCVLX.js";
8
+ import "../chunk-6AAP4LPF.js";
9
+ export {
10
+ TIME_PATTERNS,
11
+ normalizeTime,
12
+ parseTimeToMinutes,
13
+ time,
14
+ validateTimeFormat
15
+ };
@@ -0,0 +1,7 @@
1
+ "use strict";Object.defineProperty(exports, "__esModule", {value: true});
2
+
3
+ var _chunkDFJZ3NS2cjs = require('../chunk-DFJZ3NS2.cjs');
4
+ require('../chunk-UCOXAZJF.cjs');
5
+
6
+
7
+ exports.url = _chunkDFJZ3NS2cjs.url;