ezKit 1.12.0__py3-none-any.whl → 1.12.2__py3-none-any.whl

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.
ezKit/utils.py CHANGED
@@ -1,4 +1,5 @@
1
- """Utils"""
1
+ """Utils Library"""
2
+
2
3
  import csv
3
4
  import hashlib
4
5
  import importlib
@@ -72,46 +73,39 @@ def isTrue(target: object, typeClass: Any) -> bool:
72
73
  # --------------------------------------------------------------------------------------------------
73
74
 
74
75
 
75
- def check_arguments(data: list) -> bool:
76
- """检查函数参数"""
76
+ # def check_arguments(data: list) -> bool:
77
+ # """检查函数参数"""
77
78
 
78
- # data 示例: [(name, str, "name"), (age, int, "age")]
79
+ # # data 示例: [(name, str, "name"), (age, int, "age")]
79
80
 
80
- try:
81
- if not isTrue(data, list):
82
- logger.error(f"argument error: data {type(data)}")
83
- return False
84
- for arg, arg_type, info in data:
85
- if not isTrue(arg, arg_type):
86
- logger.error(f"argument error: {info} {type(arg)}")
87
- return False
88
- return True
89
- except Exception as e:
90
- logger.exception(e)
91
- return False
81
+ # try:
82
+ # if not isTrue(data, list):
83
+ # logger.error(f"argument error: data {type(data)}")
84
+ # return False
85
+ # for arg, arg_type, info in data:
86
+ # if not isTrue(arg, arg_type):
87
+ # logger.error(f"argument error: {info} {type(arg)}")
88
+ # return False
89
+ # return True
90
+ # except Exception as e:
91
+ # logger.exception(e)
92
+ # return False
92
93
 
93
94
 
94
95
  # --------------------------------------------------------------------------------------------------
95
96
 
96
97
 
97
- def os_environ(
98
- name: str,
99
- value: Any = None
100
- ) -> Any:
98
+ def os_environ(name: str, value: Any = None) -> Any:
101
99
  """系统变量"""
102
100
 
103
101
  # 伪全局变量
104
102
  # Python 没有全局变量, 多个文件无法调用同一个变量.
105
103
  # 为了解决这个问题, 将变量设置为系统变量, 从而实现多个文件调用同一个变量.
106
104
 
107
- # 检查参数是否正确
108
- if not check_arguments([(name, str, "name")]):
109
- return None
110
-
111
105
  try:
112
106
 
113
107
  # 变量名添加一个前缀, 防止和系统中其它变量名冲突
114
- _variable_name = f'PYTHON_VARIABLE_{name}'
108
+ _variable_name = f"PYTHON_VARIABLE_{name}"
115
109
 
116
110
  # 如果 value 的值是 None, 则从系统环境获取变量数据
117
111
  if value is None:
@@ -140,19 +134,12 @@ def os_environ(
140
134
  # --------------------------------------------------------------------------------------------------
141
135
 
142
136
 
143
- def mam_of_numbers(
144
- numbers: list | tuple,
145
- dest_type: str | None = None
146
- ) -> tuple | None:
137
+ def mam_of_numbers(numbers: list | tuple, dest_type: str | None = None) -> tuple | None:
147
138
  """返回一组数字中的 最大值(maximum), 平均值(average), 最小值(minimum)"""
148
139
 
149
140
  # numbers 数字列表 (仅支持 list 和 tuple, 不支 set)
150
141
  # dest_type 目标类型 (将数字列表中的数字转换成统一的类型)
151
142
 
152
- # 检查参数是否正确
153
- if not check_arguments([(numbers, (list, tuple), "numbers")]):
154
- return None
155
-
156
143
  if not any([isTrue(dest_type, str), dest_type is None]):
157
144
  logger.error("argument error: dest_type")
158
145
  return None
@@ -189,10 +176,7 @@ def mam_of_numbers(
189
176
  # --------------------------------------------------------------------------------------------------
190
177
 
191
178
 
192
- def step_number_for_split_equally(
193
- integer: int,
194
- split_equally_number: int
195
- ) -> int | None:
179
+ def step_number_for_split_equally(integer: int, split_equally_number: int) -> int | None:
196
180
  """
197
181
  step number for split equally
198
182
 
@@ -222,14 +206,8 @@ def step_number_for_split_equally(
222
206
  # --------------------------------------------------------------------------------------------------
223
207
 
224
208
 
225
- def division(
226
- dividend: int | float,
227
- divisor: int | float
228
- ) -> float | None:
209
+ def division(dividend: int | float, divisor: int | float) -> float | None:
229
210
  """Division"""
230
- # 检查参数是否正确
231
- if not check_arguments([(dividend, (int, float), "dividend"), (divisor, (int, float), "divisor")]):
232
- return None
233
211
  try:
234
212
  return dividend / divisor
235
213
  except Exception as e:
@@ -245,14 +223,6 @@ def format_float(number: float | int, index: int = 2, limit: int = 3) -> float |
245
223
 
246
224
  # 以两位和三位为例, 如果结果为假, 即: 0, 0.0, 0.00 等,保留小数点后的三位, 否则保留小数点后的两位.
247
225
 
248
- # 检查参数
249
- if not check_arguments([
250
- (number, (float, int), "number"),
251
- (index, int, "index"),
252
- (limit, int, "limit")
253
- ]):
254
- return False
255
-
256
226
  try:
257
227
  rounded_float = round(number, index)
258
228
  return rounded_float if bool(rounded_float) else round(number, limit)
@@ -264,19 +234,12 @@ def format_float(number: float | int, index: int = 2, limit: int = 3) -> float |
264
234
  # --------------------------------------------------------------------------------------------------
265
235
 
266
236
 
267
- def check_file_type(
268
- file_object: str,
269
- file_type: str
270
- ) -> bool:
237
+ def check_file_type(file_object: str, file_type: str) -> bool:
271
238
  """检查文件类型"""
272
239
 
273
240
  # file_object 文件对象
274
241
  # file_type 文件类型
275
242
 
276
- # 检查参数是否正确
277
- if not check_arguments([(file_object, str, "file"), (file_type, str, "file_type")]):
278
- return False
279
-
280
243
  try:
281
244
 
282
245
  _file_path = Path(file_object)
@@ -284,25 +247,27 @@ def check_file_type(
284
247
  match True:
285
248
  case True if _file_path.exists() is False:
286
249
  result = False
287
- case True if file_type == 'absolute' and _file_path.is_absolute() is True:
288
- result = True
289
- case True if file_type == 'block_device' and _file_path.is_block_device() is True:
250
+ case True if file_type == "absolute" and _file_path.is_absolute() is True:
290
251
  result = True
291
- case True if file_type == 'dir' and _file_path.is_dir() is True:
252
+ case True if file_type == "block_device" and _file_path.is_block_device() is True:
292
253
  result = True
293
- case True if file_type == 'fifo' and _file_path.is_fifo() is True:
254
+ case True if file_type == "dir" and _file_path.is_dir() is True:
294
255
  result = True
295
- case True if file_type == 'file' and _file_path.is_file() is True:
256
+ case True if file_type == "fifo" and _file_path.is_fifo() is True:
296
257
  result = True
297
- case True if file_type == 'mount' and _file_path.is_mount() is True:
258
+ case True if file_type == "file" and _file_path.is_file() is True:
298
259
  result = True
299
- case True if file_type == 'relative_to' and _file_path.is_relative_to() is True:
260
+ case True if file_type == "mount" and _file_path.is_mount() is True:
300
261
  result = True
301
- case True if file_type == 'reserved' and _file_path.is_reserved() is True:
262
+ # case True if (
263
+ # file_type == "relative_to" and _file_path.is_relative_to() is True
264
+ # ):
265
+ # result = True
266
+ case True if file_type == "reserved" and _file_path.is_reserved() is True:
302
267
  result = True
303
- case True if file_type == 'socket' and _file_path.is_socket() is True:
268
+ case True if file_type == "socket" and _file_path.is_socket() is True:
304
269
  result = True
305
- case True if file_type == 'symlink' and _file_path.is_symlink() is True:
270
+ case True if file_type == "symlink" and _file_path.is_symlink() is True:
306
271
  result = True
307
272
  case _:
308
273
  result = False
@@ -317,11 +282,7 @@ def check_file_type(
317
282
  # --------------------------------------------------------------------------------------------------
318
283
 
319
284
 
320
- def list_sort(
321
- data: list,
322
- deduplication: bool = False,
323
- **kwargs
324
- ) -> list | None:
285
+ def list_sort(data: list, deduplication: bool = False, **kwargs) -> list | None:
325
286
  """list sort"""
326
287
  # 列表排序, 示例: list_sort(['1.2.3.4', '2.3.4.5'], key=inet_aton)
327
288
  # 参考文档:
@@ -345,11 +306,7 @@ def list_sort(
345
306
  return None
346
307
 
347
308
 
348
- def list_dict_sorted_by_key(
349
- data: list | tuple,
350
- key: str,
351
- **kwargs
352
- ) -> list | None:
309
+ def list_dict_sorted_by_key(data: list | tuple, key: str, **kwargs) -> list | None:
353
310
  """list dict sorted by key"""
354
311
  # 列表字典排序
355
312
  # 参考文档: https://stackoverflow.com/a/73050
@@ -360,11 +317,8 @@ def list_dict_sorted_by_key(
360
317
  logger.exception(e)
361
318
  return None
362
319
 
363
- def list_split(
364
- data: list,
365
- number: int,
366
- equally: bool = False
367
- ) -> list | None:
320
+
321
+ def list_split(data: list, number: int, equally: bool = False) -> list | None:
368
322
  """列表分割"""
369
323
 
370
324
  # 列表分割
@@ -389,10 +343,6 @@ def list_split(
389
343
  # list_split(data, 2, True) -> [[1, 2, 3, 4], [5, 6, 7, 8]] 将 data 平均分成 2个子list
390
344
  # list_split(data, 3, True) -> [[1, 2, 3], [4, 5, 6], [7, 8]] 将 data 平均分成 3个子list
391
345
 
392
- # 检查参数是否正确
393
- if not check_arguments([(data, list, "data"), (number, int, "number")]):
394
- return None
395
-
396
346
  try:
397
347
 
398
348
  # 要将列表平均分成 n 个子列表
@@ -410,17 +360,9 @@ def list_split(
410
360
  return None
411
361
 
412
362
 
413
- def list_print_by_step(
414
- data: list,
415
- step: int,
416
- separator: str = " "
417
- ) -> bool:
363
+ def list_print_by_step(data: list, step: int, separator: str = " ") -> bool:
418
364
  """根据 步长 和 分隔符 有规律的打印列表中的数据"""
419
365
 
420
- # 检查参数是否正确
421
- if not check_arguments([(data, list, "data"), (step, int, "step"), (separator, str, "separator")]):
422
- return False
423
-
424
366
  try:
425
367
 
426
368
  # 打印
@@ -433,7 +375,7 @@ def list_print_by_step(
433
375
 
434
376
  # 每行最后一个 或者 所有数据最后一个, 不打印分隔符
435
377
  if ((i % step) == (step - 1)) or ((i + 1) == len(data)):
436
- print(v, end='')
378
+ print(v, end="")
437
379
  else:
438
380
  print(v, end=separator)
439
381
 
@@ -446,10 +388,7 @@ def list_print_by_step(
446
388
  return False
447
389
 
448
390
 
449
- def list_remove_list(
450
- original: list,
451
- remove: list
452
- ) -> list | None:
391
+ def list_remove_list(original: list, remove: list) -> list | None:
453
392
  """List remove List"""
454
393
  try:
455
394
  _original = deepcopy(original)
@@ -460,9 +399,7 @@ def list_remove_list(
460
399
  return None
461
400
 
462
401
 
463
- def list_merge(
464
- data: list
465
- ) -> list | None:
402
+ def list_merge(data: list) -> list | None:
466
403
  """list merge"""
467
404
  # 合并 List 中的 List 为一个 List
468
405
  try:
@@ -475,14 +412,10 @@ def list_merge(
475
412
  return None
476
413
 
477
414
 
478
- def list_to_file(
479
- data: list,
480
- file: str,
481
- encoding: str = 'utf-8-sig'
482
- ) -> bool:
415
+ def list_to_file(data: list, file: str, encoding: str = "utf-8-sig") -> bool:
483
416
  """list to file"""
484
417
  try:
485
- with open(file, 'w', encoding=encoding) as _file:
418
+ with open(file, "w", encoding=encoding) as _file:
486
419
  for line in data:
487
420
  _file.write(f"{line}\n")
488
421
  return True
@@ -490,16 +423,17 @@ def list_to_file(
490
423
  logger.exception(e)
491
424
  return False
492
425
 
426
+
493
427
  def list_to_csvfile(
494
428
  data: list,
495
429
  file: str,
496
430
  fields: list | None = None,
497
- encoding: str = 'utf-8-sig',
498
- **kwargs
431
+ encoding: str = "utf-8-sig",
432
+ **kwargs,
499
433
  ) -> bool:
500
434
  """list to csvfile"""
501
435
  try:
502
- with open(file, 'w', encoding=encoding) as _file:
436
+ with open(file, "w", encoding=encoding) as _file:
503
437
  # CRLF replaced by LF
504
438
  # https://stackoverflow.com/a/29976091
505
439
  outcsv = csv.writer(_file, lineterminator=os.linesep, **kwargs)
@@ -511,12 +445,8 @@ def list_to_csvfile(
511
445
  logger.exception(e)
512
446
  return False
513
447
 
514
- def range_zfill(
515
- start: int,
516
- stop: int,
517
- step: int,
518
- width: int
519
- ) -> list | None:
448
+
449
+ def range_zfill(start: int, stop: int, step: int, width: int) -> list | None:
520
450
  """range zfill"""
521
451
  # 生成长度相同的字符串的列表
522
452
  # 示例: range_zfill(8, 13, 1, 2) => ['08', '09', '10', '11', '12']
@@ -534,10 +464,7 @@ def range_zfill(
534
464
  # --------------------------------------------------------------------------------------------------
535
465
 
536
466
 
537
- def dict_remove_key(
538
- data: dict,
539
- key: str
540
- ) -> dict | None:
467
+ def dict_remove_key(data: dict, key: str) -> dict | None:
541
468
  """dict remove key"""
542
469
  try:
543
470
  data_copy: dict = deepcopy(data)
@@ -547,15 +474,11 @@ def dict_remove_key(
547
474
  logger.exception(e)
548
475
  return None
549
476
 
550
- def dict_to_file(
551
- data: dict,
552
- file: str,
553
- encoding: str = 'utf-8-sig',
554
- **kwargs
555
- ) -> bool:
477
+
478
+ def dict_to_file(data: dict, file: str, encoding: str = "utf-8-sig", **kwargs) -> bool:
556
479
  """dict to file"""
557
480
  try:
558
- with open(file, 'w', encoding=encoding) as _file:
481
+ with open(file, "w", encoding=encoding) as _file:
559
482
  json.dump(obj=data, fp=_file, indent=4, sort_keys=True, **kwargs)
560
483
  return True
561
484
  except Exception as e:
@@ -563,11 +486,7 @@ def dict_to_file(
563
486
  return False
564
487
 
565
488
 
566
- def dict_nested_update(
567
- data: dict,
568
- key: str,
569
- value: Any
570
- ) -> bool:
489
+ def dict_nested_update(data: dict, key: str, value: Any) -> bool:
571
490
  """dict nested update"""
572
491
  # dictionary nested update
573
492
  # https://stackoverflow.com/a/58885744
@@ -602,10 +521,7 @@ def dict_nested_update(
602
521
  # --------------------------------------------------------------------------------------------------
603
522
 
604
523
 
605
- def filename(
606
- file: str,
607
- split: str = '.'
608
- ) -> str | None:
524
+ def filename(file: str, split: str = ".") -> str | None:
609
525
  """filename"""
610
526
  # 获取文件名称
611
527
  # https://stackoverflow.com/questions/678236/how-do-i-get-the-filename-without-the-extension-from-a-path-in-python
@@ -619,10 +535,7 @@ def filename(
619
535
  return None
620
536
 
621
537
 
622
- def filehash(
623
- file: str,
624
- sha: str = 'md5'
625
- ) -> str | None:
538
+ def filehash(file: str, sha: str = "md5") -> str | None:
626
539
  """filehash"""
627
540
  # 获取文件Hash
628
541
  # 参考文档:
@@ -631,23 +544,23 @@ def filehash(
631
544
  try:
632
545
  with open(file, "rb") as _file:
633
546
  match True:
634
- case True if sha == 'sha1':
547
+ case True if sha == "sha1":
635
548
  file_hash = hashlib.sha1()
636
- case True if sha == 'sha224':
549
+ case True if sha == "sha224":
637
550
  file_hash = hashlib.sha224()
638
- case True if sha == 'sha256':
551
+ case True if sha == "sha256":
639
552
  file_hash = hashlib.sha256()
640
- case True if sha == 'sha384':
553
+ case True if sha == "sha384":
641
554
  file_hash = hashlib.sha384()
642
- case True if sha == 'sha512':
555
+ case True if sha == "sha512":
643
556
  file_hash = hashlib.sha512()
644
- case True if sha == 'sha3_224':
557
+ case True if sha == "sha3_224":
645
558
  file_hash = hashlib.sha3_224()
646
- case True if sha == 'sha3_256':
559
+ case True if sha == "sha3_256":
647
560
  file_hash = hashlib.sha3_256()
648
- case True if sha == 'sha3_384':
561
+ case True if sha == "sha3_384":
649
562
  file_hash = hashlib.sha3_384()
650
- case True if sha == 'sha3_512':
563
+ case True if sha == "sha3_512":
651
564
  file_hash = hashlib.sha3_512()
652
565
  # case True if sha == 'shake_128':
653
566
  # file_hash = hashlib.shake_128()
@@ -666,9 +579,7 @@ def filehash(
666
579
  return None
667
580
 
668
581
 
669
- def filesize(
670
- file: str
671
- ) -> int | None:
582
+ def filesize(file: str) -> int | None:
672
583
  """filesize"""
673
584
  # 获取文件大小
674
585
  try:
@@ -701,10 +612,7 @@ def filesize(
701
612
  # return None
702
613
 
703
614
 
704
- def realpath(
705
- path: str,
706
- **kwargs
707
- ) -> str | None:
615
+ def realpath(path: str, **kwargs) -> str | None:
708
616
  """获取对象真实路径"""
709
617
  try:
710
618
  if not isTrue(path, str):
@@ -715,10 +623,7 @@ def realpath(
715
623
  return None
716
624
 
717
625
 
718
- def current_dir(
719
- path: str,
720
- **kwargs
721
- ) -> str | None:
626
+ def current_dir(path: str, **kwargs) -> str | None:
722
627
  """获取对象所在目录"""
723
628
  try:
724
629
  if not isTrue(path, str):
@@ -729,10 +634,7 @@ def current_dir(
729
634
  return None
730
635
 
731
636
 
732
- def parent_dir(
733
- path: str,
734
- **kwargs
735
- ) -> str | None:
637
+ def parent_dir(path: str, **kwargs) -> str | None:
736
638
  """获取对象所在目录的父目录"""
737
639
  try:
738
640
  if not isTrue(path, str):
@@ -759,7 +661,7 @@ def retry(func: Callable, times: int = 3, **kwargs) -> Any:
759
661
  except Exception as e:
760
662
  logger.exception(e)
761
663
  if attempt < (times - 1):
762
- logger.info('retrying ...')
664
+ logger.info("retrying ...")
763
665
  else:
764
666
  logger.error("all retries failed")
765
667
  return False
@@ -811,9 +713,7 @@ def retry(func: Callable, times: int = 3, **kwargs) -> Any:
811
713
  # datetime.fromisoformat(time.strftime(format, time.gmtime(dt)))
812
714
 
813
715
 
814
- def date_to_datetime(
815
- date_object: datetime
816
- ) -> datetime | None:
716
+ def date_to_datetime(date_object: datetime) -> datetime | None:
817
717
  """'日期'转换为'日期时间'"""
818
718
  # https://stackoverflow.com/a/1937636
819
719
  try:
@@ -823,9 +723,7 @@ def date_to_datetime(
823
723
  return None
824
724
 
825
725
 
826
- def datetime_to_date(
827
- datetime_instance: datetime
828
- ) -> date | None:
726
+ def datetime_to_date(datetime_instance: datetime) -> date | None:
829
727
  """'日期时间'转换为'日期'"""
830
728
  # https://stackoverflow.com/a/3743240
831
729
  try:
@@ -852,10 +750,7 @@ def datetime_now(**kwargs) -> datetime | None:
852
750
  return None
853
751
 
854
752
 
855
- def datetime_offset(
856
- datetime_instance: datetime | None = None,
857
- **kwargs
858
- ) -> datetime | None:
753
+ def datetime_offset(datetime_instance: datetime | None = None, **kwargs) -> datetime | None:
859
754
  """
860
755
  获取 '向前或向后特定日期时间' 的日期和时间
861
756
 
@@ -876,10 +771,7 @@ def datetime_offset(
876
771
  return None
877
772
 
878
773
 
879
- def datetime_to_string(
880
- datetime_instance: datetime,
881
- string_format: str = '%Y-%m-%d %H:%M:%S'
882
- ) -> str | None:
774
+ def datetime_to_string(datetime_instance: datetime, string_format: str = "%Y-%m-%d %H:%M:%S") -> str | None:
883
775
  """'日期时间'转换为'字符串'"""
884
776
  try:
885
777
  if not isTrue(datetime_instance, datetime):
@@ -890,10 +782,7 @@ def datetime_to_string(
890
782
  return None
891
783
 
892
784
 
893
- def datetime_to_timestamp(
894
- datetime_instance: datetime,
895
- utc: bool = False
896
- ) -> int | None:
785
+ def datetime_to_timestamp(datetime_instance: datetime, utc: bool = False) -> int | None:
897
786
  """
898
787
  Datatime 转换为 Unix Timestamp
899
788
  Local datetime 可以直接转换为 Unix Timestamp
@@ -908,10 +797,7 @@ def datetime_to_timestamp(
908
797
  return None
909
798
 
910
799
 
911
- def datetime_local_to_timezone(
912
- datetime_instance: datetime,
913
- tz: timezone = timezone.utc
914
- ) -> datetime | None:
800
+ def datetime_local_to_timezone(datetime_instance: datetime, tz: timezone = timezone.utc) -> datetime | None:
915
801
  """
916
802
  Local datetime to TimeZone datetime(默认转换为 UTC datetime)
917
803
  replace(tzinfo=None) 移除结尾的时区信息
@@ -927,7 +813,7 @@ def datetime_local_to_timezone(
927
813
 
928
814
  def datetime_utc_to_timezone(
929
815
  datetime_instance: datetime,
930
- tz: Any = datetime.now(timezone.utc).astimezone().tzinfo
816
+ tz: Any = datetime.now(timezone.utc).astimezone().tzinfo,
931
817
  ) -> datetime | None:
932
818
  """
933
819
  UTC datetime to TimeZone datetime(默认转换为 Local datetime)
@@ -943,10 +829,7 @@ def datetime_utc_to_timezone(
943
829
  return None
944
830
 
945
831
 
946
- def timestamp_to_datetime(
947
- timestamp: int,
948
- tz: timezone = timezone.utc
949
- ) -> datetime | None:
832
+ def timestamp_to_datetime(timestamp: int, tz: timezone = timezone.utc) -> datetime | None:
950
833
  """Unix Timestamp 转换为 Datatime"""
951
834
  try:
952
835
  if not isTrue(timestamp, int):
@@ -957,10 +840,7 @@ def timestamp_to_datetime(
957
840
  return None
958
841
 
959
842
 
960
- def datetime_string_to_datetime(
961
- datetime_string: str,
962
- datetime_format: str = '%Y-%m-%d %H:%M:%S'
963
- ) -> datetime | None:
843
+ def datetime_string_to_datetime(datetime_string: str, datetime_format: str = "%Y-%m-%d %H:%M:%S") -> datetime | None:
964
844
  """datetime string to datetime"""
965
845
  try:
966
846
  if not isTrue(datetime_string, str):
@@ -971,10 +851,7 @@ def datetime_string_to_datetime(
971
851
  return None
972
852
 
973
853
 
974
- def datetime_string_to_timestamp(
975
- datetime_string: str,
976
- datetime_format: str = '%Y-%m-%d %H:%M:%S'
977
- ) -> int | None:
854
+ def datetime_string_to_timestamp(datetime_string: str, datetime_format: str = "%Y-%m-%d %H:%M:%S") -> int | None:
978
855
  """datetime string to timestamp"""
979
856
  try:
980
857
  if not isTrue(datetime_string, str):
@@ -985,18 +862,16 @@ def datetime_string_to_timestamp(
985
862
  return None
986
863
 
987
864
 
988
- def datetime_object(
989
- date_time: datetime
990
- ) -> dict | None:
865
+ def datetime_object(date_time: datetime) -> dict | None:
991
866
  """datetime object"""
992
867
  try:
993
868
  return {
994
- 'date': date_time.strftime("%Y-%m-%d"),
995
- 'time': date_time.strftime("%H:%M:%S"),
996
- 'datetime_now': date_time.strftime("%Y-%m-%d %H:%M:%S"),
997
- 'datetime_minute': date_time.strftime("%Y-%m-%d %H:%M:00"),
998
- 'datetime_hour': date_time.strftime("%Y-%m-%d %H:00:00"),
999
- 'datetime_zero': date_time.strftime('%Y-%m-%d 00:00:00')
869
+ "date": date_time.strftime("%Y-%m-%d"),
870
+ "time": date_time.strftime("%H:%M:%S"),
871
+ "datetime_now": date_time.strftime("%Y-%m-%d %H:%M:%S"),
872
+ "datetime_minute": date_time.strftime("%Y-%m-%d %H:%M:00"),
873
+ "datetime_hour": date_time.strftime("%Y-%m-%d %H:00:00"),
874
+ "datetime_zero": date_time.strftime("%Y-%m-%d 00:00:00"),
1000
875
  }
1001
876
  except Exception as e:
1002
877
  logger.exception(e)
@@ -1011,7 +886,7 @@ def shell(
1011
886
  isfile: bool = False,
1012
887
  sh_shell: str = "/bin/bash",
1013
888
  sh_option: str | None = None,
1014
- **kwargs
889
+ **kwargs,
1015
890
  ) -> subprocess.CompletedProcess | None:
1016
891
  """执行 Shell 命令 或 脚本"""
1017
892
 
@@ -1053,12 +928,10 @@ def shell(
1053
928
  # --------------------------------------------------------------------------------------------------
1054
929
 
1055
930
 
1056
- def json_file_parser(
1057
- file: str
1058
- ) -> dict | None:
931
+ def json_file_parser(file: str) -> dict | None:
1059
932
  """JSON File Parser"""
1060
933
  try:
1061
- if not check_file_type(file, 'file'):
934
+ if not check_file_type(file, "file"):
1062
935
  logger.error(f"no such file: {file}")
1063
936
  return None
1064
937
  with open(file, encoding="utf-8") as json_raw:
@@ -1068,6 +941,7 @@ def json_file_parser(
1068
941
  logger.exception(e)
1069
942
  return None
1070
943
 
944
+
1071
945
  # json_raw = '''
1072
946
  # {
1073
947
  # "markdown.preview.fontSize": 14,
@@ -1087,10 +961,7 @@ def json_file_parser(
1087
961
  # }
1088
962
 
1089
963
 
1090
- def json_sort(
1091
- string: str,
1092
- **kwargs
1093
- ) -> str | None:
964
+ def json_sort(string: str, **kwargs) -> str | None:
1094
965
  """JSON Sort"""
1095
966
  try:
1096
967
  if not isTrue(string, str):
@@ -1104,15 +975,13 @@ def json_sort(
1104
975
  # --------------------------------------------------------------------------------------------------
1105
976
 
1106
977
 
1107
- def delete_files(
1108
- files: str | list
1109
- ) -> bool:
978
+ def delete_files(files: str | list) -> bool:
1110
979
  """删除文件"""
1111
980
  try:
1112
981
 
1113
- if isinstance(files, str) and check_file_type(files, 'file'):
982
+ if isinstance(files, str) and check_file_type(files, "file"):
1114
983
  os.remove(files)
1115
- logger.success(f'deleted file: {files}')
984
+ logger.success(f"deleted file: {files}")
1116
985
  return True
1117
986
 
1118
987
  if not isTrue(files, list):
@@ -1120,14 +989,14 @@ def delete_files(
1120
989
 
1121
990
  for _file in files:
1122
991
 
1123
- if isinstance(_file, str) and check_file_type(_file, 'file'):
992
+ if isinstance(_file, str) and check_file_type(_file, "file"):
1124
993
  try:
1125
994
  os.remove(_file)
1126
- logger.success(f'deleted file: {_file}')
995
+ logger.success(f"deleted file: {_file}")
1127
996
  except Exception as e:
1128
- logger.error(f'error file: {_file} {e}')
997
+ logger.error(f"error file: {_file} {e}")
1129
998
  else:
1130
- logger.error(f'error file: {_file}')
999
+ logger.error(f"error file: {_file}")
1131
1000
 
1132
1001
  return True
1133
1002
 
@@ -1164,25 +1033,25 @@ def delete_directory(
1164
1033
  """
1165
1034
  try:
1166
1035
 
1167
- if isinstance(directory, str) and check_file_type(directory, 'dir'):
1036
+ if isinstance(directory, str) and check_file_type(directory, "dir"):
1168
1037
  rmtree(directory)
1169
- logger.success(f'deleted directory: {directory}')
1038
+ logger.success(f"deleted directory: {directory}")
1170
1039
  return True
1171
1040
 
1172
1041
  if not isTrue(directory, list):
1173
- logger.error(f'error directory: {directory}')
1042
+ logger.error(f"error directory: {directory}")
1174
1043
  return False
1175
1044
 
1176
1045
  for _dir in directory:
1177
1046
 
1178
- if isTrue(_dir, str) and check_file_type(_dir, 'dir'):
1047
+ if isTrue(_dir, str) and check_file_type(_dir, "dir"):
1179
1048
  try:
1180
1049
  rmtree(_dir)
1181
- logger.success(f'deleted directory: {_dir}')
1050
+ logger.success(f"deleted directory: {_dir}")
1182
1051
  except Exception as e:
1183
- logger.error(f'error directory: {_dir} {e}')
1052
+ logger.error(f"error directory: {_dir} {e}")
1184
1053
  else:
1185
- logger.error(f'error directory: {_dir}')
1054
+ logger.error(f"error directory: {_dir}")
1186
1055
 
1187
1056
  return True
1188
1057
 
@@ -1199,7 +1068,7 @@ def processor(
1199
1068
  process_data: list,
1200
1069
  process_num: int = 2,
1201
1070
  thread: bool = False,
1202
- **kwargs
1071
+ **kwargs,
1203
1072
  ) -> Any:
1204
1073
  """使用多线程或多进程对数据进行并行处理"""
1205
1074
 
@@ -1224,25 +1093,15 @@ def processor(
1224
1093
 
1225
1094
  try:
1226
1095
 
1227
- # 检查参数
1228
- if not check_arguments([(process_data, list, "process_data")]):
1229
- return False
1230
-
1231
1096
  # 确保并行数不超过数据量
1232
1097
  process_num = min(len(process_data), process_num)
1233
- data_chunks = (
1234
- list_split(process_data, process_num, equally=True)
1235
- if process_num > 1
1236
- else [process_data]
1237
- )
1098
+ data_chunks = list_split(process_data, process_num, equally=True) if process_num > 1 else [process_data]
1238
1099
 
1239
1100
  if not data_chunks:
1240
1101
  logger.error("data chunks error")
1241
1102
  return False
1242
1103
 
1243
- logger.info(
1244
- f"Starting {'multi-threading' if thread else 'multi-processing'} with {process_num} workers..."
1245
- )
1104
+ logger.info(f"Starting {'multi-threading' if thread else 'multi-processing'} with {process_num} workers...")
1246
1105
 
1247
1106
  # 执行多线程或多进程任务
1248
1107
  pool = ThreadPoolExecutor if thread else ProcessPoolExecutor
@@ -1257,16 +1116,14 @@ def processor(
1257
1116
  # --------------------------------------------------------------------------------------------------
1258
1117
 
1259
1118
 
1260
- def create_empty_file(
1261
- file: str | None = None
1262
- ) -> str | None:
1119
+ def create_empty_file(file: str | None = None) -> str | None:
1263
1120
  """create empty file"""
1264
1121
  try:
1265
1122
  if file is None:
1266
1123
  # 当前时间戳(纳秒)
1267
1124
  timestamp = time.time_ns()
1268
1125
  # 空文件路径
1269
- file = f'/tmp/none_{timestamp}.txt'
1126
+ file = f"/tmp/none_{timestamp}.txt"
1270
1127
  # 创建一个空文件
1271
1128
  # pylint: disable=R1732
1272
1129
  open(file, "w", encoding="utf-8").close()
@@ -1285,14 +1142,12 @@ def uuid4_hex() -> str:
1285
1142
  return uuid4().hex
1286
1143
 
1287
1144
 
1288
- def increment_version(
1289
- version: str
1290
- ) -> str | None:
1145
+ def increment_version(version: str) -> str | None:
1291
1146
  """版本号递增"""
1292
1147
  try:
1293
- version_numbers = version.split('.')
1148
+ version_numbers = version.split(".")
1294
1149
  version_numbers[-1] = str(int(version_numbers[-1]) + 1)
1295
- return '.'.join(version_numbers)
1150
+ return ".".join(version_numbers)
1296
1151
  except Exception as e:
1297
1152
  logger.exception(e)
1298
1153
  return None
@@ -1301,9 +1156,7 @@ def increment_version(
1301
1156
  # --------------------------------------------------------------------------------------------------
1302
1157
 
1303
1158
 
1304
- def make_directory(
1305
- directory: str
1306
- ) -> bool:
1159
+ def make_directory(directory: str) -> bool:
1307
1160
  """创建目录"""
1308
1161
  try:
1309
1162
  os.makedirs(directory)
@@ -1312,16 +1165,15 @@ def make_directory(
1312
1165
  logger.exception(e)
1313
1166
  return False
1314
1167
 
1315
- def change_directory(
1316
- directory: str
1317
- ) -> bool:
1168
+
1169
+ def change_directory(directory: str) -> bool:
1318
1170
  """改变目录"""
1319
1171
  try:
1320
1172
 
1321
1173
  if not isTrue(directory, str):
1322
1174
  return False
1323
1175
 
1324
- if not check_file_type(directory, 'dir'):
1176
+ if not check_file_type(directory, "dir"):
1325
1177
  logger.error(f"no such directory: {directory}")
1326
1178
  return False
1327
1179
 
@@ -1337,19 +1189,17 @@ def change_directory(
1337
1189
  # --------------------------------------------------------------------------------------------------
1338
1190
 
1339
1191
 
1340
- def load_toml_file(
1341
- file: str
1342
- ) -> dict | None:
1192
+ def load_toml_file(file: str) -> dict | None:
1343
1193
  """Load TOML file"""
1344
- info = '解析配置文件'
1194
+ info = "解析配置文件"
1345
1195
  try:
1346
- logger.info(f'{info}[执行]')
1196
+ logger.info(f"{info}[执行]")
1347
1197
  with open(file, "rb") as _file:
1348
1198
  config = tomllib.load(_file)
1349
- logger.success(f'{info}[成功]')
1199
+ logger.success(f"{info}[成功]")
1350
1200
  return config
1351
1201
  except Exception as e:
1352
- logger.error(f'{info}[失败]')
1202
+ logger.error(f"{info}[失败]")
1353
1203
  logger.exception(e)
1354
1204
  return None
1355
1205
 
@@ -1359,12 +1209,12 @@ def git_clone(
1359
1209
  local_repository: str,
1360
1210
  timeout: int = 30,
1361
1211
  delete: bool = False,
1362
- log_prefix: str = ''
1212
+ log_prefix: str = "",
1363
1213
  ) -> bool:
1364
1214
  """GIT Clone"""
1365
1215
 
1366
1216
  # 日志前缀
1367
- log_prefix = f'{log_prefix} [GitClone]'
1217
+ log_prefix = f"{log_prefix} [GitClone]"
1368
1218
 
1369
1219
  try:
1370
1220
 
@@ -1385,10 +1235,10 @@ def git_clone(
1385
1235
 
1386
1236
  # 克隆仓库
1387
1237
  result = shell(
1388
- command=f'timeout -s 9 {timeout} git clone {git_repository} {local_repository}',
1238
+ command=f"timeout -s 9 {timeout} git clone {git_repository} {local_repository}",
1389
1239
  universal_newlines=True,
1390
1240
  stdout=subprocess.PIPE,
1391
- stderr=subprocess.STDOUT
1241
+ stderr=subprocess.STDOUT,
1392
1242
  )
1393
1243
 
1394
1244
  if result is None:
@@ -1399,26 +1249,24 @@ def git_clone(
1399
1249
 
1400
1250
  if result_code != 0:
1401
1251
  for i in result_info:
1402
- logger.error(f'{log_prefix}{i}')
1252
+ logger.error(f"{log_prefix}{i}")
1403
1253
  return False
1404
1254
 
1405
1255
  return True
1406
1256
 
1407
1257
  except Exception as e:
1408
- logger.error(f'{log_prefix} [failed]')
1258
+ logger.error(f"{log_prefix} [failed]")
1409
1259
  logger.exception(e)
1410
1260
  return False
1411
1261
 
1412
1262
 
1413
1263
  def url_parse(
1414
- url: str
1264
+ url: str,
1415
1265
  # scheme: str = "http"
1416
1266
  ) -> ParseResult | None:
1417
1267
  """URL Parse"""
1418
1268
  # none_result = ParseResult(scheme='', netloc='', path='', params='', query='', fragment='')
1419
1269
  try:
1420
- if not check_arguments([(url, str, "url_parse -> url")]):
1421
- return None
1422
1270
  # 如果没有 scheme 的话, 字符串是不解析的. 所以, 如果没有 scheme, 就添加一个 scheme, 默认添加 http
1423
1271
  # if isTrue(url, str) and (url.find('://') == -1) and isTrue(scheme, str):
1424
1272
  # url = f'{scheme}://{url}'
@@ -1430,6 +1278,7 @@ def url_parse(
1430
1278
  logger.exception(e)
1431
1279
  return None
1432
1280
 
1281
+
1433
1282
  # def debug_log(
1434
1283
  # log: None | str = None,
1435
1284
  # exception: None | Exception = None,
@@ -1462,13 +1311,6 @@ def markdown_to_html(markdown_file: str, html_file: str, title: str) -> bool:
1462
1311
 
1463
1312
  logger.info(f"{info} [开始]")
1464
1313
 
1465
- if not check_arguments([
1466
- (markdown_file, str, "markdown_to_html -> markdown_file"),
1467
- (html_file, str, "markdown_to_html -> html_file"),
1468
- (title, str, "markdown_to_html -> title"),
1469
- ]):
1470
- return False
1471
-
1472
1314
  # 读取 HTML模版 文件
1473
1315
  logger.info(f"{info} [读取 HTML模版 文件]")
1474
1316
  html_template_file = f"{current_dir(__file__)}/markdown_to_html.template"
@@ -1483,7 +1325,7 @@ def markdown_to_html(markdown_file: str, html_file: str, title: str) -> bool:
1483
1325
  # 将 Markdown 转换为 HTML
1484
1326
  logger.info(f"{info} [将 Markdown 转换为 HTML]")
1485
1327
  # pylint: disable=E0606
1486
- html_body = markdown.markdown(markdown_content, extensions=['tables']) # type: ignore
1328
+ html_body = markdown.markdown(markdown_content, extensions=["tables"]) # type: ignore
1487
1329
  # pylint: enable=E0606
1488
1330
 
1489
1331
  # 构造完整的 HTML
@@ -1493,7 +1335,7 @@ def markdown_to_html(markdown_file: str, html_file: str, title: str) -> bool:
1493
1335
 
1494
1336
  # 保存为 HTML 文件
1495
1337
  logger.info(f"{info} [保存为 HTML 文件: {html_file}]")
1496
- with open(html_file, "w", encoding='utf-8') as _:
1338
+ with open(html_file, "w", encoding="utf-8") as _:
1497
1339
  _.write(html_content)
1498
1340
 
1499
1341
  logger.success(f"{info} [成功]")