gomyck-tools 1.3.7__py3-none-any.whl → 1.3.9__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.
Files changed (78) hide show
  1. ctools/ai/env_config.py +2 -0
  2. ctools/ai/llm_chat.py +27 -26
  3. ctools/ai/llm_client.py +87 -66
  4. ctools/ai/llm_exception.py +17 -0
  5. ctools/ai/mcp/mcp_client.py +5 -1
  6. ctools/ai/tools/quick_tools.py +99 -0
  7. ctools/ai/tools/xml_extract.py +0 -1
  8. ctools/application.py +46 -44
  9. ctools/auto/__init__.py +4 -0
  10. ctools/{browser_element_tools.py → auto/browser_element.py} +3 -2
  11. ctools/{plan_area_tools.py → auto/plan_area.py} +3 -0
  12. ctools/{resource_bundle_tools.py → auto/resource_bundle.py} +3 -3
  13. ctools/{screenshot_tools.py → auto/screenshot.py} +3 -2
  14. ctools/{win_control.py → auto/win_control.py} +5 -2
  15. ctools/cid.py +18 -0
  16. ctools/cipher/__init__.py +4 -0
  17. ctools/{rsa.py → cipher/rsa.py} +2 -2
  18. ctools/database/__init__.py +4 -0
  19. ctools/{database.py → database/database.py} +4 -3
  20. ctools/geo/__init__.py +4 -0
  21. ctools/metrics.py +2 -2
  22. ctools/office/__init__.py +4 -0
  23. ctools/{word_fill.py → office/word_fill.py} +1 -1
  24. ctools/pools/__init__.py +4 -0
  25. ctools/similar.py +22 -0
  26. ctools/stream/__init__.py +4 -0
  27. ctools/{credis.py → stream/credis.py} +5 -4
  28. ctools/{mqtt_utils.py → stream/mqtt_utils.py} +13 -10
  29. ctools/sys_info.py +5 -4
  30. ctools/sys_log.py +32 -31
  31. ctools/util/__init__.py +4 -0
  32. ctools/{http_utils.py → util/http_util.py} +0 -1
  33. ctools/{snow_id.py → util/snow_id.py} +2 -2
  34. ctools/web/__init__.py +4 -0
  35. ctools/{aio_web_server.py → web/aio_web_server.py} +23 -4
  36. ctools/{bottle_web_base.py → web/bottle_web_base.py} +2 -2
  37. ctools/{download_tools.py → web/download_util.py} +3 -2
  38. ctools/web/params_util.py +42 -0
  39. ctools/{upload_tools.py → web/upload_util.py} +3 -2
  40. {gomyck_tools-1.3.7.dist-info → gomyck_tools-1.3.9.dist-info}/METADATA +1 -1
  41. gomyck_tools-1.3.9.dist-info/RECORD +82 -0
  42. ctools/bashPath.py +0 -13
  43. ctools/console.py +0 -55
  44. ctools/enums.py +0 -4
  45. ctools/excelOpt.py +0 -36
  46. ctools/imgDialog.py +0 -45
  47. ctools/obj.py +0 -20
  48. ctools/str_diff.py +0 -20
  49. ctools/string_tools.py +0 -85
  50. gomyck_tools-1.3.7.dist-info/RECORD +0 -76
  51. /ctools/{pacth.py → auto/pacth.py} +0 -0
  52. /ctools/{pty_tools.py → auto/pty_process.py} +0 -0
  53. /ctools/{win_canvas.py → auto/win_canvas.py} +0 -0
  54. /ctools/{date_utils.py → cdate.py} +0 -0
  55. /ctools/{aes_tools.py → cipher/aes_util.py} +0 -0
  56. /ctools/{b64.py → cipher/b64.py} +0 -0
  57. /ctools/{czip.py → cipher/czip.py} +0 -0
  58. /ctools/{sign.py → cipher/sign.py} +0 -0
  59. /ctools/{sm_tools.py → cipher/sm_util.py} +0 -0
  60. /ctools/{coord_trans.py → geo/coord_trans.py} +0 -0
  61. /ctools/{douglas_rarefy.py → geo/douglas_rarefy.py} +0 -0
  62. /ctools/{cword.py → office/cword.py} +0 -0
  63. /ctools/{word_fill_entity.py → office/word_fill_entity.py} +0 -0
  64. /ctools/{work_path.py → path_info.py} +0 -0
  65. /ctools/{process_pool.py → pools/process_pool.py} +0 -0
  66. /ctools/{thread_pool.py → pools/thread_pool.py} +0 -0
  67. /ctools/{ckafka.py → stream/ckafka.py} +0 -0
  68. /ctools/{cftp.py → util/cftp.py} +0 -0
  69. /ctools/{compile_tools.py → util/compile_util.py} +0 -0
  70. /ctools/{html_soup.py → util/html_soup.py} +0 -0
  71. /ctools/{images_tools.py → util/image_process.py} +0 -0
  72. /ctools/{api_result.py → web/api_result.py} +0 -0
  73. /ctools/{bottle_webserver.py → web/bottle_webserver.py} +0 -0
  74. /ctools/{bottle_websocket.py → web/bottle_websocket.py} +0 -0
  75. /ctools/{ctoken.py → web/ctoken.py} +0 -0
  76. {gomyck_tools-1.3.7.dist-info → gomyck_tools-1.3.9.dist-info}/WHEEL +0 -0
  77. {gomyck_tools-1.3.7.dist-info → gomyck_tools-1.3.9.dist-info}/licenses/LICENSE +0 -0
  78. {gomyck_tools-1.3.7.dist-info → gomyck_tools-1.3.9.dist-info}/top_level.txt +0 -0
ctools/sys_log.py CHANGED
@@ -2,9 +2,8 @@ import logging
2
2
  import os
3
3
  import sys
4
4
  import time
5
- import traceback
6
5
 
7
- from ctools import call, work_path
6
+ from ctools import call, path_info
8
7
 
9
8
  clog: logging.Logger = None
10
9
  flog: logging.Logger = None
@@ -27,7 +26,7 @@ def _file_log(sys_log_path: str = './', log_level: int = logging.INFO, mixin: bo
27
26
  else:
28
27
  handlers = [logging.FileHandler(filename=log_file, encoding='utf-8')]
29
28
  logging.basicConfig(level=log_level,
30
- format='%(asctime)s-%(levelname)s-%(thread)d-%(module)s(%(funcName)s:%(lineno)d) %(message)s',
29
+ format='%(asctime)s | %(levelname)-5s | T%(thread)d | %(module)s.%(funcName)s:%(lineno)d: %(message)s',
31
30
  datefmt='%Y%m%d%H%M%S',
32
31
  handlers=handlers)
33
32
  logger = logging.getLogger('ck-flog')
@@ -39,53 +38,55 @@ def _file_log(sys_log_path: str = './', log_level: int = logging.INFO, mixin: bo
39
38
  def _console_log(log_level: int = logging.INFO) -> logging:
40
39
  handler = logging.StreamHandler()
41
40
  logging.basicConfig(level=log_level,
42
- format='%(asctime)s-%(levelname)s-%(thread)d-%(module)s(%(funcName)s:%(lineno)d) %(message)s',
41
+ format='%(asctime)s | %(levelname)-5s | T%(thread)d | %(name)s | %(module)s.%(funcName)s:%(lineno)d: %(message)s',
43
42
  datefmt='%Y%m%d%H%M%S',
44
43
  handlers=[handler])
45
44
  logger = logging.getLogger('ck-clog')
46
45
  return logger
47
46
 
48
47
 
49
- class GlobalLogger(object):
50
- def __init__(self, logger):
51
- sys.stdout = self
52
- sys.stderr = self
53
- sys.excepthook = self.handle_exception
54
- self.log = logger
48
+ import io
49
+ import logging
55
50
 
56
- def write(self, message):
57
- if message == '\n' or message == '\r\n': return
58
- global neglect_keywords
59
- for neglect_keyword in neglect_keywords:
60
- if neglect_keyword in message: return
61
- try:
62
- stack = traceback.extract_stack(limit=3)
63
- caller = stack[-2]
64
- location = f"{os.path.splitext(os.path.basename(caller.filename))[0]}({caller.name}:{caller.lineno})"
65
- self.log.info(f"{location} {message.strip()}")
66
- except Exception:
67
- self.log.info(message.strip())
51
+ class StreamToLogger(io.StringIO):
52
+ def __init__(self, logger: logging.Logger, level: int = logging.INFO):
53
+ super().__init__()
54
+ self.logger = logger
55
+ self.level = level
56
+ self._buffer = ''
68
57
 
69
- def handle_exception(self, exc_type, exc_value, exc_traceback):
70
- if issubclass(exc_type, KeyboardInterrupt):
71
- sys.__excepthook__(exc_type, exc_value, exc_traceback)
58
+ def write(self, message: str):
59
+ if not message:
72
60
  return
73
- formatted_exception = ''.join(traceback.format_exception(exc_type, exc_value, exc_traceback))
74
- self.log.error(f"An error occurred:\n{formatted_exception.strip()}")
61
+ self._buffer += message
62
+ if '\n' in self._buffer:
63
+ lines = self._buffer.splitlines(keepends=False)
64
+ for line in lines:
65
+ if line.strip():
66
+ try:
67
+ self.logger.log(self.level, line.strip(), stacklevel=3)
68
+ except Exception:
69
+ self.logger.log(self.level, line.strip())
70
+ self._buffer = ''
75
71
 
76
72
  def flush(self):
77
- pass
73
+ if self._buffer.strip():
74
+ try:
75
+ self.logger.log(self.level, self._buffer.strip(), stacklevel=3)
76
+ except Exception:
77
+ self.logger.log(self.level, self._buffer.strip())
78
+ self._buffer = ''
78
79
 
79
80
  def fileno(self):
80
81
  return sys.__stdout__.fileno()
81
82
 
82
-
83
83
  @call.init
84
84
  def _init_log() -> None:
85
85
  global flog, clog
86
- flog = _file_log(sys_log_path='{}/ck-py-log/'.format(work_path.get_user_work_path()), mixin=True, log_level=logging.DEBUG)
86
+ flog = _file_log(sys_log_path='{}/ck-py-log/'.format(path_info.get_user_work_path()), mixin=True, log_level=logging.DEBUG)
87
87
  clog = _console_log()
88
- GlobalLogger(flog)
88
+ sys.stdout = StreamToLogger(flog, level=logging.INFO)
89
+ sys.stderr = StreamToLogger(flog, level=logging.ERROR)
89
90
 
90
91
  def setLevel(log_level=logging.INFO):
91
92
  flog.setLevel(log_level)
@@ -0,0 +1,4 @@
1
+ #!/usr/bin/env python
2
+ # -*- coding: UTF-8 -*-
3
+ __author__ = 'haoyang'
4
+ __date__ = '2025/6/11 09:29'
@@ -1,6 +1,5 @@
1
1
  import requests
2
2
 
3
-
4
3
  def get(url, params=None, headers=None):
5
4
  result = ""
6
5
  try:
@@ -8,7 +8,7 @@ SEQUENCE_BITS = 12
8
8
  MAX_WORKER_ID = -1 ^ (-1 << WORKER_ID_BITS) # 2**5-1 0b11111
9
9
  MAX_DATACENTER_ID = -1 ^ (-1 << DATACENTER_ID_BITS)
10
10
  # 移位偏移计算
11
- WOKER_ID_SHIFT = SEQUENCE_BITS
11
+ WORKER_ID_SHIFT = SEQUENCE_BITS
12
12
  DATACENTER_ID_SHIFT = SEQUENCE_BITS + WORKER_ID_BITS
13
13
  TIMESTAMP_LEFT_SHIFT = SEQUENCE_BITS + WORKER_ID_BITS + DATACENTER_ID_BITS
14
14
  # 序号循环掩码
@@ -63,7 +63,7 @@ class SnowId(object):
63
63
  self.sequence = 0
64
64
  self.last_timestamp = timestamp
65
65
  new_id = ((timestamp - TWEPOCH) << TIMESTAMP_LEFT_SHIFT) | (self.datacenter_id << DATACENTER_ID_SHIFT) | \
66
- (self.worker_id << WOKER_ID_SHIFT) | self.sequence
66
+ (self.worker_id << WORKER_ID_SHIFT) | self.sequence
67
67
  return new_id
68
68
 
69
69
  def _til_next_millis(self, last_timestamp):
ctools/web/__init__.py ADDED
@@ -0,0 +1,4 @@
1
+ #!/usr/bin/env python
2
+ # -*- coding: UTF-8 -*-
3
+ __author__='haoyang'
4
+ __date__='2025/6/11 09:12'
@@ -12,7 +12,8 @@ from typing import Optional, Dict, Any
12
12
  from aiohttp import web
13
13
 
14
14
  from ctools import sys_info, cjson
15
- from ctools.api_result import R
15
+ from ctools.sys_log import flog as log
16
+ from ctools.web.api_result import R
16
17
 
17
18
  DEFAULT_PORT = 8888
18
19
 
@@ -23,11 +24,16 @@ async def response_wrapper_middleware(request, handler):
23
24
  if isinstance(result, web.Response):
24
25
  return result
25
26
  elif isinstance(result, str):
26
- return web.Response(text=result)
27
+ return web.Response(text=result, content_type='application/json')
28
+ elif isinstance(result, dict):
29
+ return web.Response(text=cjson.dumps(result), content_type='application/json')
27
30
  else:
28
- return web.Response(text=cjson.dumps(result))
31
+ return result
32
+ except web.HTTPException as http_exc:
33
+ raise http_exc
29
34
  except Exception as e:
30
- return web.json_response(text=R.error(str(e)), status=200)
35
+ log.error(f"Error in response_wrapper_middleware: {e}", exc_info=True)
36
+ return web.json_response(text=R.error(str(e)), status=500, content_type='application/json')
31
37
 
32
38
  class AioHttpServer:
33
39
  def __init__(self, port: int = DEFAULT_PORT, app: Optional[web.Application] = None, routes: Optional[web.RouteTableDef] = None, async_func = None):
@@ -155,3 +161,16 @@ def init_routes() -> web.RouteTableDef:
155
161
  def init_server(routes: Optional[web.RouteTableDef] = None, app: Optional[web.Application] = None, port: int = DEFAULT_PORT, async_func = None) -> AioHttpServer:
156
162
  """Initialize and return a new AioHttpServer instance."""
157
163
  return AioHttpServer(port=port, app=app, routes=routes, async_func=async_func)
164
+
165
+ async def get_stream_resp(request, content_type: str = 'text/event-stream') -> web.StreamResponse:
166
+ resp = web.StreamResponse(
167
+ status=200,
168
+ reason='OK',
169
+ headers={
170
+ 'Content-Type': content_type,
171
+ 'Cache-Control': 'no-cache',
172
+ 'X-Accel-Buffering': 'no',
173
+ }
174
+ )
175
+ await resp.prepare(request)
176
+ return resp
@@ -5,10 +5,10 @@ from functools import wraps
5
5
  import bottle
6
6
  from bottle import response, Bottle, request
7
7
 
8
- from ctools import ctoken
9
- from ctools.api_result import R
10
8
  from ctools.dict_wrapper import DictWrapper
11
9
  from ctools.sys_log import flog as log
10
+ from ctools.web import ctoken
11
+ from ctools.web.api_result import R
12
12
 
13
13
  bottle.BaseRequest.MEMFILE_MAX = 1024 * 1024 * 50
14
14
  func_has_params = {}
@@ -3,7 +3,8 @@ from urllib.parse import urlencode
3
3
 
4
4
  from bottle import static_file, HTTPResponse
5
5
 
6
- from ctools import sys_log, http_utils
6
+ from ctools import sys_log
7
+ from ctools.util import http_util
7
8
 
8
9
  log = sys_log.flog
9
10
 
@@ -50,7 +51,7 @@ def download_bytes(file_bytes: bytes, download_name: str):
50
51
 
51
52
 
52
53
  def download_url(url: str, save_path: str):
53
- content = http_utils.get(url)
54
+ content = http_util.get(url)
54
55
  if content:
55
56
  with open(save_path, "wb") as f:
56
57
  f.write(content)
@@ -0,0 +1,42 @@
1
+ #!/usr/bin/env python
2
+ # -*- coding: UTF-8 -*-
3
+ __author__ = 'haoyang'
4
+ __date__ = '2025/6/11 09:35'
5
+
6
+ def is_list(v: str):
7
+ try:
8
+ list(v)
9
+ if v[0] == "[" and v[-1] == "]":
10
+ return True
11
+ else:
12
+ return False
13
+ except Exception:
14
+ return False
15
+
16
+ def is_digit(v: str):
17
+ try:
18
+ float(v)
19
+ return True
20
+ except Exception:
21
+ return False
22
+
23
+ def is_bool(v: str):
24
+ if v in ["False", "True"]:
25
+ return True
26
+ else:
27
+ return False
28
+
29
+ def dict_to_params(obj: dict):
30
+ params = ""
31
+ for k, v in obj.items():
32
+ if k == 'varname':
33
+ continue
34
+ v = str(v)
35
+ if not is_list(v) and not is_digit(v) and not is_bool(v):
36
+ if k == "path" and v[:4] != "http":
37
+ v = "r'%s'" % v
38
+ else:
39
+ v = "'%s'" % v
40
+ params += "%s=%s, " % (k, v)
41
+ params = params[:params.rfind(',')]
42
+ return params
@@ -1,6 +1,7 @@
1
1
  import os
2
2
 
3
- from ctools import sys_log, date_utils
3
+ from ctools import sys_log
4
+ from ctools import cdate
4
5
 
5
6
  log = sys_log.flog
6
7
 
@@ -25,7 +26,7 @@ def save(upload, output_dir: str, file_name: str = None):
25
26
  if not unique_filename:
26
27
  # 生成不重复的文件名,加上时间戳
27
28
  file_name, ext = os.path.splitext(upload.raw_filename)
28
- timestamp = date_utils.get_time()
29
+ timestamp = cdate.get_time()
29
30
  unique_filename = f'{file_name}_{timestamp}{ext}'
30
31
  else:
31
32
  dot_index = unique_filename.find(".")
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: gomyck-tools
3
- Version: 1.3.7
3
+ Version: 1.3.9
4
4
  Summary: A tools collection for python development by hao474798383
5
5
  Author-email: gomyck <hao474798383@163.com>
6
6
  License-Expression: Apache-2.0
@@ -0,0 +1,82 @@
1
+ ctools/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
2
+ ctools/application.py,sha256=yXqCVbBbfe_bhHDBxV7grj9KzVr72tM7we2pYTQ4eiY,15943
3
+ ctools/call.py,sha256=BCr8wzt5qd70okv8IZn-9-EpjywleZgvA3u1vfZ_Kt8,1581
4
+ ctools/cdate.py,sha256=h3rvlw_K2F0QTac2Zat_1us76R0P-Qj6_6NeQPfM3VE,1697
5
+ ctools/cdebug.py,sha256=_mihZRCEx_bi7Kv_QPjP4MPLNFrl-GR1Y_irTgOP7OU,4021
6
+ ctools/cid.py,sha256=_0CCz3Mr1hHtj7FKDdD0vXU5tk6h42qTF8IIU8XvYxA,340
7
+ ctools/cjson.py,sha256=d0RZ53b-M18OudRFGRtPCvvGofJcaLHdbNlTCemyJag,1365
8
+ ctools/cron_lite.py,sha256=CUqdtO02VnYUWcw6t6Jr7v2dKKhx3_G7CDAtlWnirBE,8232
9
+ ctools/dict_wrapper.py,sha256=otxDX0CCKbBCVFtASweo5VEv6_ettH-CptA6azX1mJI,460
10
+ ctools/ex.py,sha256=_UtbmDLrC7uZsoBtTdecuCZAlf2DA7fvojUf5fGZDVo,795
11
+ ctools/metrics.py,sha256=YaTBCfvL9Y0uciDuxQ5WJEAn2bUaLtQP6F5Xfr_2Iuc,5248
12
+ ctools/path_info.py,sha256=OmfYu-Jjg2huRY6Su8zJ_2EGFFhtBZFbobYTwbjJtG4,1817
13
+ ctools/similar.py,sha256=7mBbp7JrGGyAgA_hDmCvGJ6hGE1Lh43ocyqPkLGclyc,695
14
+ ctools/sys_info.py,sha256=T5pcRblNHEmXEvPk2PPvQga7Hh5aDnNN72pt4U176SE,4270
15
+ ctools/sys_log.py,sha256=T-tgOcrFggSJ2I6pLHhKpj4fvVFk_vbZBOrInKC6y3Q,2789
16
+ ctools/ai/__init__.py,sha256=gTYAICILq48icnFbg0HCbsQO8PbU02EDOQ0JeMvfqTY,98
17
+ ctools/ai/env_config.py,sha256=CQtvQz1f3lvVuDTcnvDDZitnUeUdM3Ta8fXMn-x5Etg,1100
18
+ ctools/ai/llm_chat.py,sha256=dAFar0A5h3ws_kjx9MlWZAawLPYHIwvfdyO_umJgkpU,8655
19
+ ctools/ai/llm_client.py,sha256=iI8kUPn8z0pgTq8mTwnIJm9bOREmSZU5btePinmgGpg,5515
20
+ ctools/ai/llm_exception.py,sha256=wsCVl0m53Mk7Xfug1obocAthlX0oEo4dytg1eOhWHPg,389
21
+ ctools/ai/mcp/__init__.py,sha256=gTYAICILq48icnFbg0HCbsQO8PbU02EDOQ0JeMvfqTY,98
22
+ ctools/ai/mcp/mcp_client.py,sha256=eDxiG6ZHa4HX-Sz63ObmxyXIq2WZwUxQt8fSw9COfGc,11589
23
+ ctools/ai/tools/__init__.py,sha256=gPc-ViRgtFlfX7JUbk5wQZ3wkJ5Ylh14CIqPwa83VPs,98
24
+ ctools/ai/tools/json_extract.py,sha256=bgubZ2RwTo_R1X0CzMnvBWu61hglB1l6oO553645RXc,4842
25
+ ctools/ai/tools/quick_tools.py,sha256=_bJNH4miLltoFjolvJKnOzrArF0hRrXrkBO4elV-Mug,2335
26
+ ctools/ai/tools/think_process.py,sha256=RGU9j3_O328Byw05ILek-aMfFBczbly2RA-QRouqUjM,257
27
+ ctools/ai/tools/tool_use_xml_parse.py,sha256=zpHKMhU5LFSpuznU_Z5w_HHp-Bney-Te8DxoU1BNHZ0,1429
28
+ ctools/ai/tools/xml_extract.py,sha256=lpUTERzUQhbiWanc5_ukBP0wPIVg0F9va39S36yyI-4,231
29
+ ctools/auto/__init__.py,sha256=zERjXFeDwOnR6GW77qJfpxTFv-otJK2HvI241-214N4,98
30
+ ctools/auto/browser_element.py,sha256=OkGrQJZMnxx9i_uzjrSnnvRTK6fvP0nN6ztNze1UE0g,9957
31
+ ctools/auto/pacth.py,sha256=MJ9Du-J9Gv62y4cZKls1jKbl5a5kL2y9bD-gzYUCveQ,2604
32
+ ctools/auto/plan_area.py,sha256=yEpW562h9TgKfENwO5oOtJ9F0CXxseHJiqF6SiBbnrs,3358
33
+ ctools/auto/pty_process.py,sha256=r3-MF5hkFQ7ZAGlrvUKtCEeQS1V2yWW4JDlPrFZXCkc,1623
34
+ ctools/auto/resource_bundle.py,sha256=FA0p_yLp6dxVwCqUgorVUq495J-RDhmCMe5P5f4F_oc,3796
35
+ ctools/auto/screenshot.py,sha256=sDcNPg22IQL5qXADFJObunSeSC6kEkrtYpe2Fje0rIk,4539
36
+ ctools/auto/win_canvas.py,sha256=PAxI4i1jalfree9d1YG4damjc2EzaHZrgHZCTgk2GiM,2530
37
+ ctools/auto/win_control.py,sha256=vs1qz1Repj3efeU8iSecW-w4d3w-BYRAxmx7wXyhnzs,3536
38
+ ctools/cipher/__init__.py,sha256=OkUaZv5ckkXJFNbRyFZqkX5m3GxTueEGEBU99_jJQNE,98
39
+ ctools/cipher/aes_util.py,sha256=L5Jg4QtVTdIxHe9zEpR8oMQx0IrYK68vjEYb_RmkhPA,699
40
+ ctools/cipher/b64.py,sha256=_BdhX3p3-MaSSlU2wivN5qPxQfacR3VRBr1WC456tU0,194
41
+ ctools/cipher/czip.py,sha256=8LBoB4PsjN2HGga5sWk1FSigP21kIrRrzK63l92H0R8,4675
42
+ ctools/cipher/rsa.py,sha256=hxks2--eJvo2OW5Hj7xzOjF1QkybgR-3fUcvGpEO_ko,2259
43
+ ctools/cipher/sign.py,sha256=JOkgpgsMbk7T3c3MOj1U6eiEndUG9XQ-uIX9e615A_Y,566
44
+ ctools/cipher/sm_util.py,sha256=R0m52TQE-CT7pvGTP27UWNCfdzpQ8C-ALz7p0mnOnLU,1672
45
+ ctools/database/__init__.py,sha256=fB36UC93Pya_1YyWGMzDy3D4tMDTBQoYK20E4wgNqec,98
46
+ ctools/database/database.py,sha256=_DnzaIC_daO_60ixkQGGtgHJhwFceTZBNJ79H4pofZI,6421
47
+ ctools/geo/__init__.py,sha256=OkUaZv5ckkXJFNbRyFZqkX5m3GxTueEGEBU99_jJQNE,98
48
+ ctools/geo/coord_trans.py,sha256=pzIHxC4aLwvOF3eJG47Dda3vIq-Zp42xnu_FwILDflU,3951
49
+ ctools/geo/douglas_rarefy.py,sha256=iRdUdhmaMmdfXPzoleQaGMrtcAoHUDRPHYtWStTx4U4,4889
50
+ ctools/office/__init__.py,sha256=wum34b8YJg0qD7uKdDEbozSE8RIxWqTVa44CCIZyqPU,98
51
+ ctools/office/cword.py,sha256=ZRzAFn96yjo-hAbZuGIm4DoBAL2y8tFySWZ5xbYgY6Q,857
52
+ ctools/office/word_fill.py,sha256=bId-pMuPVQm7bMySJgcTvSETT3H2gPqii0bHpWOWOmY,18217
53
+ ctools/office/word_fill_entity.py,sha256=eX3G0Gy16hfGpavQSEkCIoKDdTnNgRRJrFvKliETZK8,985
54
+ ctools/pools/__init__.py,sha256=3_W3mvEs6pInRTvK7TqOPu9dC2z8rCHvHZFXO4KNYT8,98
55
+ ctools/pools/process_pool.py,sha256=1TuZySUbQjgYYcuwis54DIwQTimWvTLNahSra7Ia8Ps,951
56
+ ctools/pools/thread_pool.py,sha256=Mt60XMhs-nk-hbkPo8NA7wQ4RxRLZTk4X6vh5Wn3WEw,944
57
+ ctools/stream/__init__.py,sha256=mf8vkbcJdYpvDslgXkkHOz6rKBzU1qfxi8xQGQ1A90w,98
58
+ ctools/stream/ckafka.py,sha256=8zMTS6iCCvxi5Ez4z9mcaBoVX7tb4R5tfyjG-xlM1HQ,5907
59
+ ctools/stream/credis.py,sha256=Cd14--jl-kCEDPbHcv6UWlVK4lwXT3XbqVN7T-KWMEQ,4509
60
+ ctools/stream/mqtt_utils.py,sha256=0MUDjOBORR4Tbao4nsta3SJ_ZEDawzkwhXOoh9IMMcQ,10718
61
+ ctools/util/__init__.py,sha256=jJLxgj-rdTVIo_czMcN83-HQI9yyBYy1L5gw8ZAbmyc,98
62
+ ctools/util/cftp.py,sha256=SkHPDvKu58jnMnl68u5WxWEiFWsm2C0CGa5_GR_Obcw,2481
63
+ ctools/util/compile_util.py,sha256=Nybh3vnkurIKnPnubdYzigjnzFu4GaTMKPvqFdibxmE,510
64
+ ctools/util/html_soup.py,sha256=rnr8M3gn3gQGo-wNaNFXDjdzp8AAkv9o4yqfIIfO-zw,1567
65
+ ctools/util/http_util.py,sha256=8kt_9v9YwTmzvqNBBAWOfFGAurbjJIPeyEwg3X1Bpy8,768
66
+ ctools/util/image_process.py,sha256=TapXYCPqC7GesgrALecxxa_ApuT_dxUG5fqQIJF2bNY,670
67
+ ctools/util/snow_id.py,sha256=B26wzGOqV3cs5bC_z5ulXlDxPXWrHdwVPM7N4kjmZqI,2272
68
+ ctools/web/__init__.py,sha256=sMc0cAWWs3h1pAoapzE69DfvdfbA4P4JNkJRBy2qQhM,94
69
+ ctools/web/aio_web_server.py,sha256=cO0HRdsJ9iHSO1HCT--TwdFTSM5y26RTl8HwuEfVKBg,5413
70
+ ctools/web/api_result.py,sha256=UeQXI_zuZB-uY5qECTpz1fC7EGy82yGQqWMx20tyRTw,1572
71
+ ctools/web/bottle_web_base.py,sha256=GEz2D33pI5iGzooMn1ffoFw3Gc_gb433AFnYVcEFci8,6336
72
+ ctools/web/bottle_webserver.py,sha256=tJtMSZ7r6jiIk2NzrX4uSoRQnTqueM6AYdGKd9AhgOg,4676
73
+ ctools/web/bottle_websocket.py,sha256=zqCE1rGlMeC9oxFOULNd137IWIhdetq83Oq5OoH_zGI,1953
74
+ ctools/web/ctoken.py,sha256=CdHm6-ykBLh7Lv8ZRMunSW40qMTkRH0ITeMLuG9z1ts,883
75
+ ctools/web/download_util.py,sha256=EVN3fxwbUE5Q8nurAya5IYialIKBMoFtSOy0uPKyV-E,1951
76
+ ctools/web/params_util.py,sha256=2vAuwn8OPydv_7BPKypqk4zuerPZqOGcf95wV19H1Ks,824
77
+ ctools/web/upload_util.py,sha256=xH4Z-sz-s7EVDEz2gKXoP9OZTLc-er5yvsiLqhSDFm8,1076
78
+ gomyck_tools-1.3.9.dist-info/licenses/LICENSE,sha256=X25ypfH9E6VTht2hcO8k7LCSdHUcoG_ALQt80jdYZfY,547
79
+ gomyck_tools-1.3.9.dist-info/METADATA,sha256=Z8IRmbiJXNtXNq1ezTsNFHTeLCI1he23ONzg4KOjwY4,1595
80
+ gomyck_tools-1.3.9.dist-info/WHEEL,sha256=_zCd3N1l69ArxyTb8rzEoP9TpbYXkqRFSNOD5OuxnTs,91
81
+ gomyck_tools-1.3.9.dist-info/top_level.txt,sha256=-MiIH9FYRVKp1i5_SVRkaI-71WmF1sZSRrNWFU9ls3s,7
82
+ gomyck_tools-1.3.9.dist-info/RECORD,,
ctools/bashPath.py DELETED
@@ -1,13 +0,0 @@
1
- import inspect
2
- import os
3
- import sys
4
-
5
-
6
- def path(subPath: str = '') -> str:
7
- if getattr(sys, 'frozen', False):
8
- base_path = sys._MEIPASS
9
- else:
10
- caller_frame = inspect.currentframe().f_back
11
- caller_path = caller_frame.f_globals["__file__"]
12
- base_path = os.path.dirname(caller_path)
13
- return base_path + os.path.sep + subPath
ctools/console.py DELETED
@@ -1,55 +0,0 @@
1
- import logging
2
- import sys
3
- import tkinter as tk
4
-
5
-
6
- class Console:
7
-
8
- def __init__(self, master):
9
- self.master = master
10
-
11
- # 创建文本框和滚动条
12
- self.textbox = tk.Text(self.master, wrap=tk.NONE)
13
-
14
- self.vertical_scrollbar = tk.Scrollbar(self.textbox, command=self.textbox.yview)
15
- self.horizontal_scrollbar = tk.Scrollbar(self.textbox, command=self.textbox.xview, orient=tk.HORIZONTAL)
16
-
17
- self.textbox.configure(yscrollcommand=self.vertical_scrollbar.set, xscrollcommand=self.horizontal_scrollbar.set)
18
- self.textbox.pack(side=tk.LEFT, pady=10, padx=10, ipadx=10, ipady=10, fill=tk.BOTH, expand=True)
19
-
20
- self.vertical_scrollbar.pack(side=tk.RIGHT, fill=tk.Y)
21
- self.horizontal_scrollbar.pack(side=tk.BOTTOM, fill=tk.X)
22
-
23
- # 将标准输出和标准错误输出重定向到文本框中
24
- sys.stdout = self
25
- sys.stderr = self
26
-
27
- # # 创建输入框和按钮
28
- # self.entry = tk.Entry(self.master)
29
- # self.entry.pack(side=tk.BOTTOM, fill=tk.X, expand=True)
30
- # self.button = tk.Button(self.master, text="Send", command=self.send)
31
- # self.button.pack(side=tk.BOTTOM)
32
-
33
- # 将日志输出到文本框中
34
- self.log_handler = logging.StreamHandler(self)
35
- self.log_handler.setFormatter(logging.Formatter('%(asctime)s - %(message)s'))
36
- logging.getLogger().addHandler(self.log_handler)
37
- # logging.getLogger().setLevel(logging.INFO)
38
-
39
- def write(self, message):
40
- # 在文本框中输出消息
41
- self.textbox.insert(tk.END, message + '\n')
42
- self.textbox.see(tk.END)
43
-
44
- def flush(self):
45
- pass
46
-
47
- def send(self):
48
- # 获取输入框中的文本并打印到控制台
49
- text = self.entry.get()
50
- print(text)
51
- self.entry.delete(0, tk.END)
52
-
53
- def __del__(self):
54
- # 关闭日志处理器
55
- logging.getLogger().removeHandler(self.log_handler)
ctools/enums.py DELETED
@@ -1,4 +0,0 @@
1
- def value_of(e, v):
2
- for member_name, member in e.__members__.items():
3
- if member.value == v:
4
- return member
ctools/excelOpt.py DELETED
@@ -1,36 +0,0 @@
1
- from openpyxl import load_workbook
2
- from openpyxl.worksheet.datavalidation import DataValidation
3
-
4
-
5
- class excelUtil:
6
- wb = None
7
- sourcePath = None
8
- savePath = None
9
-
10
- def __init__(self, path, save_path):
11
- # 创建一个 Workbook 对象
12
- self.wb = load_workbook(path)
13
- # 在 Workbook 中创建一个 Worksheet 对象
14
- self.ws = self.wb.active
15
- self.sourcePath = path
16
- self.savePath = save_path
17
-
18
- def makeDropData(self, col, drop_data):
19
- # 定义下拉框的数据
20
- dropdown_items = drop_data
21
- # 将下拉框数据转换成字符串
22
- dropdown_items_str = ','.join(dropdown_items)
23
- # 在第一列中添加下拉框
24
- dropdown_col = col
25
- dropdown_start_row = 2
26
- dropdown_end_row = 200
27
- # 配置下拉框参数
28
- dropdown = DataValidation(type="list", formula1=f'"{dropdown_items_str}"', allow_blank=True)
29
- # 添加下拉框到指定的单元格区域
30
- dropdown_range = f"{dropdown_col}{dropdown_start_row}:{dropdown_col}{dropdown_end_row}"
31
- self.ws.add_data_validation(dropdown)
32
- dropdown.add(dropdown_range)
33
-
34
- def save(self):
35
- # 保存工作簿
36
- self.wb.save(self.savePath)
ctools/imgDialog.py DELETED
@@ -1,45 +0,0 @@
1
- import tkinter
2
- import tkinter as tk
3
- from io import BytesIO
4
- from tkinter import ttk
5
-
6
- import requests
7
- from PIL import Image, ImageTk
8
-
9
-
10
- def showImageTip(root, title, imagePath, tips):
11
- # 创建一个Tk对象
12
- if root:
13
- window = root
14
- else:
15
- window = tk.Tk()
16
- # 设置窗口大小和位置
17
- win_width = 400
18
- win_height = 480
19
- screen_width = window.winfo_screenwidth()
20
- screen_height = window.winfo_screenheight()
21
- x = int((screen_width - win_width) / 2)
22
- y = int((screen_height - win_height) / 2)
23
- window.geometry("{}x{}+{}+{}".format(win_width, win_height, x, y))
24
-
25
- # 设置窗口大小和标题
26
- window.title(title)
27
-
28
- # 创建一个Label控件用于显示图片
29
- resp = requests.get(imagePath)
30
- image = Image.open(BytesIO(resp.content)) # 替换你自己的图片路径
31
- image = image.resize((400, 400))
32
- photo = ImageTk.PhotoImage(image)
33
- label1 = ttk.Label(window, image=photo)
34
- label1.pack(side=tkinter.TOP)
35
-
36
- # 创建一个Label控件用于显示提示文字
37
- label2 = ttk.Label(window, text=tips, font=("Arial Bold", 16))
38
- label2.config(anchor='center', justify='center')
39
- label2.pack(side=tkinter.BOTTOM)
40
- # 显示窗口
41
- window.mainloop()
42
-
43
-
44
- if __name__ == '__main__':
45
- showImageTip(root=None, title='在线授权', imagePath='https://blog.gomyck.com/img/pay-img/wechatPay2Me.jpg', tips='{}\n授权已失效,请联系微信:\n{}'.format(123, 123))
ctools/obj.py DELETED
@@ -1,20 +0,0 @@
1
-
2
- def isNull(param) -> bool:
3
- if type(param) == str:
4
- return param == ''
5
- elif type(param) == list:
6
- return len(param) == 0
7
- elif type(param) == dict:
8
- return len(param) == 0
9
- elif type(param) == int:
10
- return param == 0
11
- elif type(param) == float:
12
- return param == 0.0
13
- elif type(param) == bool:
14
- return param == False
15
- else:
16
- return param is None
17
-
18
- def isNotNull(param) -> bool:
19
- return not isNull(param)
20
-
ctools/str_diff.py DELETED
@@ -1,20 +0,0 @@
1
- # import difflib
2
- #
3
- # s1 = '12-23'
4
- # s2 = '00-11'
5
- # s3 = '2023-05-05 12:00:00-2023-05-06 23:00:00 剩余4'
6
- #
7
- # sm = difflib.SequenceMatcher(None, s1, s3)
8
- #
9
- # print(sm.ratio()) # 输出相似度得分
10
-
11
-
12
- from fuzzywuzzy import fuzz
13
-
14
- s1 = '12-23'
15
- s2 = '00-11'
16
- s3 = '2023-05-05 12:00:00-2023-05-06 23:00:00 剩余4'
17
- s4 = '2023-04-28 00:00:00-2023-04-28 11:00:00 剩余12'
18
- score = fuzz.ratio(s2, s4)
19
-
20
- print(score) # 输出相似度得
ctools/string_tools.py DELETED
@@ -1,85 +0,0 @@
1
- from ctools.snow_id import SnowId
2
-
3
- idWorker = SnowId(1, 2, 0)
4
-
5
- def get_random_str(size: int = 10) -> str:
6
- import random
7
- return "".join(random.sample('abcdefghjklmnpqrstuvwxyz123456789', size))
8
-
9
- def get_uuid() -> str:
10
- import uuid
11
- return str(uuid.uuid1()).replace("-", "")
12
-
13
- def get_snowflake_id():
14
- return idWorker.get_id()
15
-
16
- def decode_bytes(bytes_str):
17
- import chardet
18
- res_str = ""
19
- if bytes_str:
20
- detect = chardet.detect(bytes_str)
21
- if detect:
22
- confidence = 0
23
- chardet_error = False
24
- try:
25
- confidence = float(detect.get('confidence'))
26
- res_str = bytes_str.decode(encoding=detect.get('encoding'))
27
- except Exception:
28
- chardet_error = True
29
-
30
- try:
31
- if confidence <= 0.95 or chardet_error:
32
- encoding = "utf-8" if detect.get('encoding') == "utf-8" else "gbk"
33
- res_str = bytes_str.decode(encoding=encoding)
34
- except Exception:
35
- res_str = str(bytes_str)
36
- return res_str
37
-
38
-
39
- def check_sum(content: str):
40
- import hashlib
41
- try:
42
- algorithm = hashlib.sha256()
43
- algorithm.update(content.encode())
44
- return algorithm.hexdigest()
45
- except Exception:
46
- return None
47
-
48
-
49
- def is_list(v: str):
50
- try:
51
- list(v)
52
- if v[0] == "[" and v[-1] == "]":
53
- return True
54
- else:
55
- return False
56
- except Exception:
57
- return False
58
-
59
- def is_digit(v: str):
60
- try:
61
- float(v)
62
- return True
63
- except Exception:
64
- return False
65
-
66
- def is_bool(v: str):
67
- if v in ["False", "True"]:
68
- return True
69
- else:
70
- return False
71
-
72
- def dict_to_params(obj: dict):
73
- params = ""
74
- for k, v in obj.items():
75
- if k == 'varname':
76
- continue
77
- v = str(v)
78
- if not is_list(v) and not is_digit(v) and not is_bool(v):
79
- if k == "path" and v[:4] != "http":
80
- v = "r'%s'" % v
81
- else:
82
- v = "'%s'" % v
83
- params += "%s=%s, " % (k, v)
84
- params = params[:params.rfind(',')]
85
- return params