@nuka9510/simple-validation 1.1.4 → 1.2.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/dist/index.js CHANGED
@@ -1,819 +1,2 @@
1
- var simpleValidation;
2
- /******/ (() => { // webpackBootstrap
3
- /******/ "use strict";
4
- /******/ var __webpack_modules__ = ([
5
- /* 0 */,
6
- /* 1 */
7
- /***/ ((__unused_webpack___webpack_module__, __webpack_exports__, __webpack_require__) => {
8
-
9
- __webpack_require__.r(__webpack_exports__);
10
- /* harmony export */ __webpack_require__.d(__webpack_exports__, {
11
- /* harmony export */ "default": () => (/* binding */ Validation)
12
- /* harmony export */ });
13
- /* harmony import */ var _nuka9510_js_util__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(2);
14
-
15
- /**
16
- * Validation Check를 위한 객체
17
- */
18
- class Validation {
19
- /** 결과 값 객체 */
20
- result;
21
- /** validation check할 Element를 담는 객체 */
22
- #el;
23
- /** validation check할 radio Element를 담는 객체 */
24
- #radio;
25
- /** validation check에 사용할 정규식을 담은 객체 */
26
- #regex;
27
- /**
28
- * Validation Check를 위한 객체
29
- *
30
- * ```
31
- * <form name="form">
32
- * <input type="text" name="text" data-sv-pattern="password" data-sv-input-name="비밀번호" minlength="0" maxlength="10">
33
- * <input type="text" name="text" data-sv-pattern="password" minlength="0" maxlength="10" required="비밀번호">
34
- * <input type="date" name="sdate1" data-sv-date="date1" data-sv-date-state="S" data-sv-input-name="검색일1">
35
- * <input type="date" name="edate1" data-sv-date="date1" data-sv-date-state="E" data-sv-input-name="검색일1">
36
- * <input type="date" name="sdate2" data-sv-date="date2" data-sv-date-state="S" required="검색일2">
37
- * <input type="date" name="edate2" data-sv-date="date2" data-sv-date-state="E" required="검색일2">
38
- * </form>
39
- * <script type="importmap">
40
- * {
41
- * "imports": {
42
- * "@nuka9510/js-util": "https://cdn.jsdelivr.net/npm/@nuka9510/js-util/dist/index.js",
43
- * "@nuka9510/simple-validation": "https://cdn.jsdelivr.net/npm/@nuka9510/simple-validation/dist/index.js"
44
- * }
45
- * }
46
- * </script>
47
- * <script type="module">
48
- * import { SValidation } from "@nuka9510/simple-validation";
49
- *
50
- * const validation = new SValidation({regex: {password: /^[\S!?@#$%^&*():;+-=~{}<>\_\[\]\|\\\"\'\,\.\/\`]{6,10}$/}});
51
- *
52
- * validation.run(form);
53
- *
54
- * if (validation.result.flag) {
55
- * form.submit();
56
- * } else {
57
- * alert(validation.result.alertMsg);
58
- * validation.result.el.focus();
59
- * }
60
- * </script>
61
- * ```
62
- */
63
- constructor(config) { this.init(config); }
64
- /** 객체 초기화 */
65
- init(
66
- /** validation 초기화를 위한 객체 */ config = null) {
67
- this.#resultInit();
68
- this.#elInit();
69
- this.#radioInit();
70
- this.#regexInit(config?.regex);
71
- }
72
- /** 결과 값 초기화 */
73
- #resultInit() {
74
- this.result = {
75
- flag: true,
76
- alertMsg: null,
77
- el: null
78
- };
79
- }
80
- /** validation check할 Element를 담는 객체 초기화 */
81
- #elInit() { this.#el = {}; }
82
- /** validation check할 radio Element를 담는 객체 초기화 */
83
- #radioInit() { this.#radio = {}; }
84
- /** validation check에 사용할 정규식을 담은 객체 초기화 */
85
- #regexInit(regex = null) {
86
- this.#regex = (!_nuka9510_js_util__WEBPACK_IMPORTED_MODULE_0__.JUtil.empty(regex) &&
87
- _nuka9510_js_util__WEBPACK_IMPORTED_MODULE_0__.JUtil.isObject(regex))
88
- ? {
89
- ...this.#regex,
90
- ...regex
91
- }
92
- : { ...this.#regex };
93
- }
94
- /** el에 있는 Element들을 required check한다. */
95
- #required(el) {
96
- const required = el.getAttribute('required');
97
- if (!_nuka9510_js_util__WEBPACK_IMPORTED_MODULE_0__.JUtil.empty(required)) {
98
- if (el.type == 'radio') {
99
- this.#setRadio(el);
100
- }
101
- else if (_nuka9510_js_util__WEBPACK_IMPORTED_MODULE_0__.JUtil.empty(el.value)) {
102
- this.result.flag = false;
103
- this.result.alertMsg = `'${required}'을/를 입력해 주세요.`;
104
- this.result.el = el;
105
- }
106
- }
107
- }
108
- /** radio에 있는 Element들을 required check한다. */
109
- #requiredRadio() {
110
- for (const i in this.#radio) {
111
- const el = this.#radio[i][0], flag = this.#radio[i].some((...arg) => arg[0].checked);
112
- if (!flag) {
113
- this.result.flag = false;
114
- this.result.alertMsg = `'${i}'을/를 선택해주세요.`;
115
- this.result.el = el;
116
- break;
117
- }
118
- }
119
- }
120
- /** el에 Element를 담는다. */
121
- #setEl(el) {
122
- const pattern = el.dataset['svPattern'], date = el.dataset['svDate'];
123
- if (!_nuka9510_js_util__WEBPACK_IMPORTED_MODULE_0__.JUtil.empty(pattern)) {
124
- if (_nuka9510_js_util__WEBPACK_IMPORTED_MODULE_0__.JUtil.empty(this.#el.el)) {
125
- this.#el.el = [];
126
- }
127
- this.#el.el?.push(el);
128
- }
129
- if (!_nuka9510_js_util__WEBPACK_IMPORTED_MODULE_0__.JUtil.empty(date)) {
130
- const state = el.dataset['svDateState'];
131
- switch (state) {
132
- case 'S':
133
- case 'E':
134
- if (_nuka9510_js_util__WEBPACK_IMPORTED_MODULE_0__.JUtil.empty(this.#el.date)) {
135
- this.#el.date = {};
136
- }
137
- if (_nuka9510_js_util__WEBPACK_IMPORTED_MODULE_0__.JUtil.empty(this.#el.date[date])) {
138
- this.#el.date[date] = {};
139
- }
140
- this.#el.date[date][state] = el;
141
- break;
142
- }
143
- }
144
- }
145
- /** `#radio`에 type이 'radio'인 Element를 담는다. */
146
- #setRadio(el) {
147
- const required = el.getAttribute('required');
148
- if (!_nuka9510_js_util__WEBPACK_IMPORTED_MODULE_0__.JUtil.empty(required)) {
149
- if (_nuka9510_js_util__WEBPACK_IMPORTED_MODULE_0__.JUtil.empty(this.#radio[required])) {
150
- this.#radio[required] = [el];
151
- }
152
- else {
153
- this.#radio[required].push(el);
154
- }
155
- }
156
- }
157
- /**
158
- * Element들을 validation check 한다.
159
- * ```
160
- * -----------------------
161
- * date : isDate
162
- * -----------------------
163
- * el : isPattern
164
- * ```
165
- */
166
- #match() {
167
- for (const i in this.#el) {
168
- if (this.result.flag) {
169
- switch (i) {
170
- case 'date':
171
- this.#isDate(this.#el[i]);
172
- break;
173
- case 'el':
174
- this.#isPattern(this.#el[i]);
175
- break;
176
- }
177
- }
178
- else {
179
- break;
180
- }
181
- }
182
- }
183
- /** date check */
184
- #isDate(el) {
185
- for (const i in el) {
186
- if (this.result.flag) {
187
- const sdate = el[i].S.value, edate = el[i].E.value;
188
- if (!_nuka9510_js_util__WEBPACK_IMPORTED_MODULE_0__.JUtil.empty(sdate) &&
189
- !_nuka9510_js_util__WEBPACK_IMPORTED_MODULE_0__.JUtil.empty(edate)) {
190
- const inputName = el[i].S.dataset['svInputName'] ||
191
- el[i].E.dataset['svInputName'], required = el[i].S.getAttribute('required') ||
192
- el[i].E.getAttribute('required');
193
- if ((new Date(sdate)).getTime() > (new Date(edate)).getTime()) {
194
- this.result.flag = false;
195
- this.result.alertMsg = `'${inputName || required}'의 시작일이 종료일 보다 늦습니다.`;
196
- this.result.el = el[i].S;
197
- }
198
- }
199
- }
200
- else {
201
- break;
202
- }
203
- }
204
- }
205
- /** regex check */
206
- #isPattern(el) {
207
- if (Array.isArray(el)) {
208
- for (const i of el) {
209
- const pattern = i.dataset['svPattern'], inputName = i.dataset['svInputName'], required = i.getAttribute('required'), val = i.value;
210
- if (Object.keys(this.#regex).includes(pattern)) {
211
- if (!_nuka9510_js_util__WEBPACK_IMPORTED_MODULE_0__.JUtil.empty(val) &&
212
- !this.#regex[pattern].test(val)) {
213
- this.result.flag = false;
214
- this.result.alertMsg = `'${inputName || required}'의 형식이 올바르지 않습니다.`;
215
- this.result.el = i;
216
- break;
217
- }
218
- }
219
- }
220
- }
221
- else {
222
- const pattern = el.dataset['svPattern'], inputName = el.dataset['svInputName'], required = el.getAttribute('required'), val = el.value;
223
- if (Object.keys(this.#regex).includes(pattern)) {
224
- if (!_nuka9510_js_util__WEBPACK_IMPORTED_MODULE_0__.JUtil.empty(val) &&
225
- !this.#regex[pattern].test(val)) {
226
- this.result.flag = false;
227
- this.result.alertMsg = `'${inputName || required}'의 형식이 올바르지 않습니다.`;
228
- this.result.el = el;
229
- }
230
- }
231
- }
232
- }
233
- /** Element value의 length를 check 한다. */
234
- #length() {
235
- for (const i in this.#el) {
236
- if (i == 'el' &&
237
- this.result.flag) {
238
- for (const j of this.#el[i]) {
239
- const inputName = j.dataset['svInputName'], required = j.getAttribute('required'), val = j.value.length;
240
- if (!(j instanceof HTMLSelectElement)) {
241
- if (j.minLength >= 0 &&
242
- j.maxLength >= 0) {
243
- if (val < j.minLength ||
244
- val > j.maxLength) {
245
- this.result.flag = false;
246
- this.result.alertMsg = `'${inputName || required}'은/는 ${j.minLength}~${j.maxLength}자 이내로 입력해주세요.`;
247
- this.result.el = j;
248
- break;
249
- }
250
- }
251
- else if (j.minLength >= 0 &&
252
- j.maxLength < 0) {
253
- if (val < j.minLength) {
254
- this.result.flag = false;
255
- this.result.alertMsg = `'${inputName || required}'은/는 ${j.minLength}자 이상으로 입력해주세요.`;
256
- this.result.el = j;
257
- break;
258
- }
259
- }
260
- else if (j.minLength < 0 &&
261
- j.maxLength >= 0) {
262
- if (val > j.maxLength) {
263
- this.result.flag = false;
264
- this.result.alertMsg = `'${inputName || required}'은/는 ${j.maxLength}자 이하로 입력해주세요.`;
265
- this.result.el = j;
266
- break;
267
- }
268
- }
269
- }
270
- }
271
- }
272
- else if (!this.result.flag) {
273
- break;
274
- }
275
- }
276
- }
277
- /** validation을 실행한다. */
278
- run(form) {
279
- this.init();
280
- for (const el of form.elements) {
281
- if (this.result.flag) {
282
- if (['INPUT', 'SELECT', 'TEXTAREA'].includes(el.tagName)) {
283
- if (!el.disabled) {
284
- this.#required(el);
285
- this.#setEl(el);
286
- }
287
- }
288
- }
289
- else {
290
- break;
291
- }
292
- }
293
- if (this.result.flag) {
294
- this.#requiredRadio();
295
- }
296
- if (this.result.flag) {
297
- this.#match();
298
- }
299
- if (this.result.flag) {
300
- this.#length();
301
- }
302
- }
303
- }
304
-
305
-
306
- /***/ }),
307
- /* 2 */
308
- /***/ ((__unused_webpack___webpack_module__, __webpack_exports__, __webpack_require__) => {
309
-
310
- __webpack_require__.r(__webpack_exports__);
311
- /* harmony export */ __webpack_require__.d(__webpack_exports__, {
312
- /* harmony export */ JUtil: () => (/* reexport safe */ _util_mjs__WEBPACK_IMPORTED_MODULE_0__["default"])
313
- /* harmony export */ });
314
- /* harmony import */ var _util_mjs__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(3);
315
-
316
-
317
-
318
-
319
- /***/ }),
320
- /* 3 */
321
- /***/ ((__unused_webpack___webpack_module__, __webpack_exports__, __webpack_require__) => {
322
-
323
- __webpack_require__.r(__webpack_exports__);
324
- /* harmony export */ __webpack_require__.d(__webpack_exports__, {
325
- /* harmony export */ "default": () => (/* binding */ Util)
326
- /* harmony export */ });
327
- class Util {
328
- /**
329
- * 값이 비어있는지 확인한다.
330
- *
331
- * ```
332
- * // returns true
333
- * empty(undefined);
334
- * empty(null);
335
- * empty(0);
336
- * empty('');
337
- * empty([]);
338
- * empty({});
339
- * ```
340
- */
341
- static empty(
342
- /** 확인할 값 */ arg) {
343
- let result = [undefined, null, 0, ''].includes(arg);
344
- if (!result) {
345
- if (arg.constructor == Object) {
346
- result = Object.keys(arg).length == 0 &&
347
- Object.keys(Object.getPrototypeOf(arg)).length == 0;
348
- }
349
- else if (arg.constructor == NodeList) {
350
- result = arg.length == 0;
351
- }
352
- else if (Array.isArray(arg)) {
353
- result = arg.length == 0;
354
- }
355
- }
356
- return result;
357
- }
358
- /**
359
- * 값이 숫자인지 확인한다.
360
- *
361
- * ```
362
- * // returns true
363
- * isNumber(1);
364
- * isNumber('1');
365
- *
366
- * // returns false
367
- * isNumber('test');
368
- * isNumber('1', true);
369
- * ```
370
- */
371
- static isNumber(
372
- /** 확인할 값 */ arg,
373
- /** `true`일 경우 `arg`의 `type`도 확인 | #default `false` */ strict = false) {
374
- let result = !Number.isNaN(Number(arg)) &&
375
- ['number', 'string'].includes(typeof arg) &&
376
- !/^\s*$/.test(`${arg}`);
377
- if (result &&
378
- strict) {
379
- result = typeof arg == 'number';
380
- }
381
- return result;
382
- }
383
- /**
384
- * 해당 값이 객체인지 확인
385
- *
386
- * ```
387
- * // returns true
388
- * isObject({});
389
- *
390
- * // returns false
391
- * isObject(undefined);
392
- * isObject(null);
393
- * isObject(0);
394
- * isObject('');
395
- * isObject([]);
396
- * ```
397
- */
398
- static isObject(
399
- /** 확인할 값 */ arg) { return arg?.constructor == Object; }
400
- /**
401
- * 천 단위 마다 그룹화 된 숫자 형식으로 변환한 문자열을 반환 한다.
402
- *
403
- * ```
404
- * // returns '1,000'
405
- * numberFormat(1000);
406
- * numberFormat(1000.01);
407
- *
408
- * // returns '1,000.0'
409
- * numberFormat(1000.01, 1);
410
- *
411
- * // returns '1,000 0'
412
- * numberFormat(1000.01, 1, ' ');
413
- *
414
- * // returns '1.000 0'
415
- * numberFormat(1000.01, 1, ' ', '.');
416
- * ```
417
- */
418
- static numberFormat(
419
- /** 변환할 숫자 - `number` 타입이 아닌경우 `null` 반환 */ num,
420
- /** 소숫점 아래 자리 수 - `number` 타입이 아닌경우 `null` 반환 | #default `0` */ decimals = 0,
421
- /** 소수점 구분자 | #default `'.'` */ decimalSeparator = '.',
422
- /** 천 단위 구분자 | #default `','` */ thousandsSeparator = ',') {
423
- if (!Util.isNumber(num, true) ||
424
- !Util.isNumber(decimals, true)) {
425
- return null;
426
- }
427
- const result = String(num).split('.');
428
- result[0] = result[0].replace(/\B(?=(\d{3})+(?!\d))/g, thousandsSeparator);
429
- if (!Util.empty(result[1])) {
430
- result[1] = result[1].substring(0, decimals);
431
- }
432
- return (!Util.empty(result[1])) ? result[0].concat(decimalSeparator, result[1]) : result[0];
433
- }
434
- /**
435
- * 주어진 포맷에 따라 `Date`객체를 문자열로 변환
436
- *
437
- * ```
438
- * const date = new Date(2022, 9, 27);
439
- *
440
- * // returns '2022-10-27'
441
- * strftime(date, '%Y-%m-%d');
442
- *
443
- * // returns '2022/10/27'
444
- * strftime(date, '%Y/%m/%d');
445
- * ```
446
- *
447
- * `%a`: 요일을 축약된 이름으로 - Sun, Mon, …, Sat \
448
- * `%A`: 요일을 전체 이름으로 - Sunday, Monday, …, Saturday \
449
- * `%d`: 월중 일(day of the month)을 0으로 채워진 10진수로 - 01, 02, …, 31 \
450
- * `%b`: 월을 축약된 이름으로 - Jan, Feb, …, Dec \
451
- * `%B`: 월을 전체 이름으로 - January, February, …, December \
452
- * `%m`: 월을 0으로 채워진 10진수로 - 01, 02, …, 12 \
453
- * `%y`: 세기가 없는 해(year)를 0으로 채워진 10진수로 - 00, 01, …, 99 \
454
- * `%Y`: 세기가 있는 해(year)를 10진수로 - 0001, 0002, …, 2013, 2014, …, 9998, 9999 \
455
- * `%H`: 시(24시간제)를 0으로 채워진 십진수로 - 00, 01, …, 23 \
456
- * `%I`: 시(12시간제)를 0으로 채워진 십진수로 - 01, 02, …, 12 \
457
- * `%p`: 오전이나 오후에 해당하는 것 - AM, PM \
458
- * `%M`: 분을 0으로 채워진 십진수로 - 00, 01, …, 59 \
459
- * `%S`: 초를 0으로 채워진 10진수로 - 00, 01, …, 59 \
460
- * `%%`: 리터럴 '%' 문자 - %
461
- */
462
- static strftime(
463
- /** 변환할 `Date`객체 */ date,
464
- /** 변활할 포맷 문자열 */ format) {
465
- const month = ['January', 'February', 'March', 'April', 'May', 'June', 'July', 'August', 'September', 'October', 'November', 'December'], week = ['Sunday', 'Monday', 'Tuesday', 'Wednesday', 'Thursday', 'Friday', 'Saturday'];
466
- format = format.replace(/(%{1})/g, '\\$1');
467
- format = format.replace(/(\\%){2}/g, '%');
468
- format = format.replace(/\\%Y/g, String(date.getFullYear()));
469
- format = format.replace(/\\%y/g, String(date.getFullYear()).replace(/^\d+(\d{2})$/, '$1'));
470
- format = format.replace(/\\%B/g, month[date.getMonth()]);
471
- format = format.replace(/\\%b/g, month[date.getMonth()].replace(/^(\w{3})\w*$/, '$1'));
472
- format = format.replace(/\\%m/g, String(date.getMonth() + 1).replace(/^(\d{1})$/, '0$1'));
473
- format = format.replace(/\\%d/g, String(date.getDate()).replace(/^(\d{1})$/, '0$1'));
474
- format = format.replace(/\\%A/g, week[date.getDay()]);
475
- format = format.replace(/\\%a/g, week[date.getDay()].replace(/^(\w{3})\w*$/, '$1'));
476
- format = format.replace(/\\%H/g, String(date.getHours()).replace(/^(\d{1})$/, '0$1'));
477
- format = format.replace(/\\%I/g, String((date.getHours() > 12) ? (date.getHours() - 12) : date.getHours()).replace(/^0$/, '12').replace(/^(\d{1})$/, '0$1'));
478
- format = format.replace(/\\%p/g, (date.getHours() < 12) ? 'AM' : 'PM');
479
- format = format.replace(/\\%M/g, String(date.getMinutes()).replace(/^(\d{1})$/, '0$1'));
480
- format = format.replace(/\\%S/g, String(date.getSeconds()).replace(/^(\d{1})$/, '0$1'));
481
- return format;
482
- }
483
- /**
484
- * 유효한 날짜인지 확인
485
- *
486
- * ```
487
- * // returns true
488
- * checkdate(2022, 10, 28);
489
- *
490
- * // returns false
491
- * checkdate(2022, 10, 32);
492
- * ```
493
- */
494
- static checkdate(
495
- /** 년 */ year,
496
- /** 월 */ month,
497
- /** 일 */ day) {
498
- const date = new Date(year, (month - 1), day);
499
- return date.getFullYear() == year &&
500
- (date.getMonth() + 1) == month &&
501
- date.getDate() == day;
502
- }
503
- /**
504
- * 같은 날짜인지 비교
505
- *
506
- * ```
507
- * const date1 = new Date();
508
- * const date2 = new Date();
509
- *
510
- * // returns true
511
- * equaldate(date1);
512
- * equaldate(date1, date2);
513
- *
514
- * // returns false
515
- * date1.setDate(date1.getDate() + 1);
516
- * date2.setDate(date2.getDate() + 2);
517
- * equaldate(date1);
518
- * equaldate(date1, date2);
519
- * ```
520
- */
521
- static equaldate(
522
- /** 기준 날짜 */ date1,
523
- /** 비교할 날짜 | #default `new Date()` */ date2 = new Date()) { return Util.strftime(date1, '%Y-%m-%d') == Util.strftime(date2, '%Y-%m-%d'); }
524
- /**
525
- * Date객체에서 해당 하는 요일을 반환한다.
526
- *
527
- * ```
528
- * const date = new Date(2022, 9, 27);
529
- *
530
- * // returns '목요일'
531
- * getWeek(date);
532
- *
533
- * // returns '목'
534
- * getWeek(date, false);
535
- * ```
536
- */
537
- static getWeek(
538
- /** 요일을 반환할 `Date` 객체 */ date,
539
- /** 해당 요일의 약어반환 대한 구분 값 `false`일 경우 약어 반환 | #default `true` */ flag = true) {
540
- const week = ['일요일', '월요일', '화요일', '수요일', '목요일', '금요일', '토요일'], result = week[date.getDay()];
541
- return (flag) ? result : result.replace(/^([ㄱ-ㅎㅏ-ㅣ가-힣]{1})[ㄱ-ㅎㅏ-ㅣ가-힣]+$/, '$1');
542
- }
543
- /**
544
- * `Date`객체에 `interval`를 더한 값을 반환한다.
545
- *
546
- * ```
547
- * const date = new Date(2022, 8, 27);
548
- *
549
- * // returns '2022-10-28'
550
- * strftime(util.addDate(date, {month: 1, day: 1}), '%Y-%m-%d');
551
- * ```
552
- */
553
- static addDate(
554
- /** 기준 `Date`객체 */ date,
555
- /** `Date`객체에 계산할 `interval` */ interval) {
556
- return new Date(date.getFullYear() + (Util.isNumber(interval.year, true) ? interval.year : 0), date.getMonth() + (Util.isNumber(interval.month, true) ? interval.month : 0), date.getDate() + (Util.isNumber(interval.day, true) ? interval.day : 0), date.getHours() + (Util.isNumber(interval.hour, true) ? interval.hour : 0), date.getMinutes() + (Util.isNumber(interval.minute, true) ? interval.minute : 0), date.getSeconds() + (Util.isNumber(interval.second, true) ? interval.second : 0), date.getMilliseconds() + (Util.isNumber(interval.millisecond, true) ? interval.millisecond : 0));
557
- }
558
- /**
559
- * `Date`객체에 `interval`를 뺀 값을 반환한다.
560
- *
561
- * ```
562
- * const date = new Date(2022, 8, 27);
563
- *
564
- * // returns '2022-08-26'
565
- * strftime(util.subDate(date, {month: 1, day: 1}), '%Y-%m-%d');
566
- * ```
567
- */
568
- static subDate(
569
- /** 기준 `Date`객체 */ date,
570
- /** `Date`객체에 계산할 `interval` */ interval) {
571
- return new Date(date.getFullYear() - (Util.isNumber(interval.year, true) ? interval.year : 0), date.getMonth() - (Util.isNumber(interval.month, true) ? interval.month : 0), date.getDate() - (Util.isNumber(interval.day, true) ? interval.day : 0), date.getHours() - (Util.isNumber(interval.hour, true) ? interval.hour : 0), date.getMinutes() - (Util.isNumber(interval.minute, true) ? interval.minute : 0), date.getSeconds() - (Util.isNumber(interval.second, true) ? interval.second : 0), date.getMilliseconds() - (Util.isNumber(interval.millisecond, true) ? interval.millisecond : 0));
572
- }
573
- /**
574
- * xor 비교
575
- *
576
- * ```
577
- * // returns true
578
- * xor(true, false);
579
- * xor(false, true);
580
- *
581
- * // returns false
582
- * xor(true, true);
583
- * xor(false, false);
584
- * ```
585
- */
586
- static xor(
587
- /** 비교할 값 1 */ arg1,
588
- /** 비교할 값 2 */ arg2) {
589
- return !(arg1 && arg2) &&
590
- (arg1 || arg2);
591
- }
592
- /**
593
- * `FormDate`객체에 설정된 값을 `json`문자열로 반환 한다.
594
- *
595
- * ```
596
- * const data = new FormData();
597
- *
598
- * data.append('key', value);
599
- *
600
- * const json = formDataToJson(data);
601
- * ```
602
- */
603
- static formDataToJson(
604
- /** `json`문자열로 반환할 `FormData`객체 */ formData) {
605
- return JSON.stringify(Object.fromEntries([...new Set(formData.keys())].map((...arg) => [
606
- arg[0],
607
- (formData.getAll(arg[0]).length > 1)
608
- ? formData.getAll(arg[0])
609
- : formData.get(arg[0])
610
- ])));
611
- }
612
- /**
613
- * 기준 숫자의 백분율 값을 적용했을 경우의 값을 반환한다.
614
- *
615
- * ```
616
- * // returns 10
617
- * percentage(100, 10);
618
- * ```
619
- */
620
- static percentage(
621
- /** 기준 숫자 */ num,
622
- /** 백분율 */ per) { return num * (per / 100); }
623
- /**
624
- * 기준 숫자의 비율 대비 값을 반환한다.
625
- *
626
- * ```
627
- * // returns 8
628
- * // 1 : 2 = 4 : x
629
- * ratio([1, 2], 4);
630
- *
631
- * // returns 2
632
- * // 1 : 2 = x : 4
633
- * ratio([1, 2], 4, false);
634
- * ```
635
- */
636
- static ratio(
637
- /** 비율 */ ratio,
638
- /** 기준 숫자 */ num,
639
- /** 비율 적용 기준 | #default `true` */ flag = true) {
640
- const index = flag
641
- ? [1, 0]
642
- : [0, 1];
643
- return (num * ratio[index[0]]) / ratio[index[1]];
644
- }
645
- /**
646
- * `x` 번째의 항이 `a`이고 공차가 `d`인 등차수열의 `n` 번째 항을 반환 한다.
647
- */
648
- static arithmeticSequence(
649
- /** 기준 항 */ a,
650
- /** 기준 위치 `x > 0`인 정수 */ x,
651
- /** 공차 */ d,
652
- /** 반환 위치 */ n) { return a + ((n - x) * d); }
653
- /**
654
- * `x` 번째의 항이 `a`이고 공비가 `r`인 등비수열의 `n` 번째 항을 반환 한다.
655
- */
656
- static geometricSequence(
657
- /** 기준 항 */ a,
658
- /** 기준 위치 `x > 0`인 정수 */ x,
659
- /** 공비 */ r,
660
- /** 반환 위치 */ n) { return (a / (r ** (x - 1))) * (r ** (n - 1)); }
661
- /**
662
- * `value`를 반올림(round), 내림(floor), 올림(ceil) 한 값을 반환한다.
663
- */
664
- static decimalAdjust(
665
- /** 구분 기준 `반올림(round)`, `내림(floor)`, `올림(ceil)` */ type,
666
- /** 기준 값 */ value,
667
- /** 소숫점 아래 자리 수 | #default `0` */ exp = 0) {
668
- const [m, n = '0'] = value.toString().split('e'), adjustValue = Math[type](Number(`${m}e${parseInt(n) + exp}`)), [nm, nn = '0'] = adjustValue.toString().split('e');
669
- return Number(`${nm}e${parseInt(nn) - exp}`);
670
- }
671
- /**
672
- * html entity를 인코딩 한다.
673
- */
674
- static encodeHtmlEntity(
675
- /** html entity를 인코딩 할 문자열 */ arg) {
676
- const textarea = document.createElement('textarea');
677
- textarea.innerText = arg;
678
- return textarea.innerHTML;
679
- }
680
- /**
681
- * html entity를 디코딩 한다.
682
- */
683
- static decodeHtmlEntity(
684
- /** html entity를 디코딩 할 문자열 */ arg) {
685
- const textarea = document.createElement('textarea');
686
- textarea.innerHTML = arg;
687
- return textarea.innerText;
688
- }
689
- /**
690
- * `Object`의 `deepCopy`를 반환 한다.
691
- */
692
- static copy(
693
- /** `deepCopy`할 `object` */ arg) {
694
- if (Util.isObject(arg)) {
695
- const result = {};
696
- for (const i in arg) {
697
- result[i] = Util.copy(arg[i]);
698
- }
699
- return result;
700
- }
701
- else if (Array.isArray(arg)) {
702
- const result = [];
703
- for (const i of arg) {
704
- result.push(Util.copy(i));
705
- }
706
- return result;
707
- }
708
- else {
709
- return arg;
710
- }
711
- }
712
- /**
713
- * `sNum` <= x <= `eNum` 범위의 배열을 반환한다.
714
- */
715
- static numRange(
716
- /** 시작 값 */ sNum,
717
- /** 종료 값 */ eNum) {
718
- let range = (eNum - sNum);
719
- const flag = (range > 0);
720
- range = Math.abs(range) + 1;
721
- return [...new Array(range)].map((...arg) => (arg[1] * ((flag) ? 1 : -1)) + sNum);
722
- }
723
- /**
724
- * `size`를 크기로 하는 `chunk`를 담은 배열을 반환한다.
725
- */
726
- static arrayChunk(
727
- /** 기준 배열 */ arr,
728
- /** `chunk`의 크기 (`size > 0`인 정수) */ size) {
729
- if (!Util.isNumber(size, true)) {
730
- throw new TypeError("size는 숫자 타입 이어야 합니다.");
731
- }
732
- if (size <= 0 &&
733
- Number.isInteger(size)) {
734
- throw new RangeError("size는 0보다 큰 정수여야 합니다.");
735
- }
736
- const _arr = [];
737
- Util.numRange(0, Util.decimalAdjust('ceil', arr.length / size) + ((arr.length > 0) ? -1 : 0))
738
- .forEach((...arg) => { _arr.push(arr.slice(arg[0] * size, (arg[0] + 1) * size)); });
739
- return _arr;
740
- }
741
- }
742
-
743
-
744
- /***/ })
745
- /******/ ]);
746
- /************************************************************************/
747
- /******/ // The module cache
748
- /******/ var __webpack_module_cache__ = {};
749
- /******/
750
- /******/ // The require function
751
- /******/ function __webpack_require__(moduleId) {
752
- /******/ // Check if module is in cache
753
- /******/ var cachedModule = __webpack_module_cache__[moduleId];
754
- /******/ if (cachedModule !== undefined) {
755
- /******/ return cachedModule.exports;
756
- /******/ }
757
- /******/ // Create a new module (and put it into the cache)
758
- /******/ var module = __webpack_module_cache__[moduleId] = {
759
- /******/ // no module.id needed
760
- /******/ // no module.loaded needed
761
- /******/ exports: {}
762
- /******/ };
763
- /******/
764
- /******/ // Execute the module function
765
- /******/ __webpack_modules__[moduleId](module, module.exports, __webpack_require__);
766
- /******/
767
- /******/ // Return the exports of the module
768
- /******/ return module.exports;
769
- /******/ }
770
- /******/
771
- /************************************************************************/
772
- /******/ /* webpack/runtime/define property getters */
773
- /******/ (() => {
774
- /******/ // define getter functions for harmony exports
775
- /******/ __webpack_require__.d = (exports, definition) => {
776
- /******/ for(var key in definition) {
777
- /******/ if(__webpack_require__.o(definition, key) && !__webpack_require__.o(exports, key)) {
778
- /******/ Object.defineProperty(exports, key, { enumerable: true, get: definition[key] });
779
- /******/ }
780
- /******/ }
781
- /******/ };
782
- /******/ })();
783
- /******/
784
- /******/ /* webpack/runtime/hasOwnProperty shorthand */
785
- /******/ (() => {
786
- /******/ __webpack_require__.o = (obj, prop) => (Object.prototype.hasOwnProperty.call(obj, prop))
787
- /******/ })();
788
- /******/
789
- /******/ /* webpack/runtime/make namespace object */
790
- /******/ (() => {
791
- /******/ // define __esModule on exports
792
- /******/ __webpack_require__.r = (exports) => {
793
- /******/ if(typeof Symbol !== 'undefined' && Symbol.toStringTag) {
794
- /******/ Object.defineProperty(exports, Symbol.toStringTag, { value: 'Module' });
795
- /******/ }
796
- /******/ Object.defineProperty(exports, '__esModule', { value: true });
797
- /******/ };
798
- /******/ })();
799
- /******/
800
- /************************************************************************/
801
- var __webpack_exports__ = {};
802
- // This entry needs to be wrapped in an IIFE because it needs to be isolated against other modules in the chunk.
803
- (() => {
804
- __webpack_require__.r(__webpack_exports__);
805
- /* harmony export */ __webpack_require__.d(__webpack_exports__, {
806
- /* harmony export */ JUtil: () => (/* reexport safe */ _nuka9510_js_util__WEBPACK_IMPORTED_MODULE_1__.JUtil),
807
- /* harmony export */ Validation: () => (/* reexport safe */ _validation_mjs__WEBPACK_IMPORTED_MODULE_0__["default"])
808
- /* harmony export */ });
809
- /* harmony import */ var _validation_mjs__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(1);
810
- /* harmony import */ var _nuka9510_js_util__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(2);
811
-
812
-
813
-
814
-
815
- })();
816
-
817
- simpleValidation = __webpack_exports__;
818
- /******/ })()
819
- ;
1
+ import Validation from "./validation.js";
2
+ export { Validation };