gomyck-tools 1.2.11__py3-none-any.whl → 1.3.1__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 (65) hide show
  1. gomyck_tools-1.3.1.dist-info/METADATA +66 -0
  2. gomyck_tools-1.3.1.dist-info/RECORD +4 -0
  3. {gomyck_tools-1.2.11.dist-info → gomyck_tools-1.3.1.dist-info}/WHEEL +1 -1
  4. gomyck_tools-1.3.1.dist-info/top_level.txt +1 -0
  5. ctools/__init__.py +0 -0
  6. ctools/aes_tools.py +0 -35
  7. ctools/api_result.py +0 -55
  8. ctools/application.py +0 -386
  9. ctools/b64.py +0 -7
  10. ctools/bashPath.py +0 -13
  11. ctools/bottle_web_base.py +0 -169
  12. ctools/bottle_webserver.py +0 -143
  13. ctools/bottle_websocket.py +0 -75
  14. ctools/browser_element_tools.py +0 -314
  15. ctools/call.py +0 -71
  16. ctools/cftp.py +0 -74
  17. ctools/cjson.py +0 -54
  18. ctools/ckafka.py +0 -159
  19. ctools/compile_tools.py +0 -18
  20. ctools/console.py +0 -55
  21. ctools/coord_trans.py +0 -127
  22. ctools/credis.py +0 -111
  23. ctools/cron_lite.py +0 -252
  24. ctools/ctoken.py +0 -34
  25. ctools/cword.py +0 -30
  26. ctools/czip.py +0 -19
  27. ctools/database.py +0 -193
  28. ctools/date_utils.py +0 -43
  29. ctools/dict_wrapper.py +0 -22
  30. ctools/douglas_rarefy.py +0 -136
  31. ctools/download_tools.py +0 -57
  32. ctools/enums.py +0 -4
  33. ctools/ex.py +0 -31
  34. ctools/excelOpt.py +0 -36
  35. ctools/html_soup.py +0 -35
  36. ctools/http_utils.py +0 -24
  37. ctools/images_tools.py +0 -27
  38. ctools/imgDialog.py +0 -44
  39. ctools/metrics.py +0 -131
  40. ctools/mqtt_utils.py +0 -289
  41. ctools/obj.py +0 -20
  42. ctools/pacth.py +0 -74
  43. ctools/plan_area_tools.py +0 -97
  44. ctools/process_pool.py +0 -36
  45. ctools/pty_tools.py +0 -72
  46. ctools/resource_bundle_tools.py +0 -121
  47. ctools/rsa.py +0 -70
  48. ctools/screenshot_tools.py +0 -127
  49. ctools/sign.py +0 -20
  50. ctools/sm_tools.py +0 -49
  51. ctools/snow_id.py +0 -76
  52. ctools/str_diff.py +0 -20
  53. ctools/string_tools.py +0 -85
  54. ctools/sys_info.py +0 -157
  55. ctools/sys_log.py +0 -89
  56. ctools/thread_pool.py +0 -35
  57. ctools/upload_tools.py +0 -40
  58. ctools/win_canvas.py +0 -83
  59. ctools/win_control.py +0 -106
  60. ctools/word_fill.py +0 -562
  61. ctools/word_fill_entity.py +0 -46
  62. ctools/work_path.py +0 -69
  63. gomyck_tools-1.2.11.dist-info/METADATA +0 -57
  64. gomyck_tools-1.2.11.dist-info/RECORD +0 -62
  65. gomyck_tools-1.2.11.dist-info/top_level.txt +0 -1
ctools/bottle_web_base.py DELETED
@@ -1,169 +0,0 @@
1
- import inspect
2
- import threading
3
- from functools import wraps
4
-
5
- import bottle
6
- from bottle import response, Bottle, request
7
-
8
- from ctools import ctoken
9
- from ctools.dict_wrapper import DictWrapper
10
- from ctools.api_result import R
11
- from ctools.sys_log import flog as log
12
-
13
- bottle.BaseRequest.MEMFILE_MAX = 1024 * 1024 * 50
14
- func_has_params = {}
15
-
16
- class GlobalState:
17
- lock = threading.Lock()
18
- withOutLoginURI = [
19
- '/',
20
- '/index',
21
- '/login'
22
- ]
23
- allowRemoteCallURI = [
24
-
25
- ]
26
- token = {}
27
- interceptors = []
28
-
29
- def init_app(context_path=None):
30
- app = Bottle()
31
- app.context_path = context_path
32
-
33
- @app.hook('before_request')
34
- def before_request():
35
- for interceptor in GlobalState.interceptors:
36
- res: R = interceptor['func']()
37
- if res.code != 200: bottle.abort(res.code, res.message)
38
-
39
- @app.error(401)
40
- def unauthorized(error):
41
- response.status = 401
42
- log.error("系统未授权: {} {} {}".format(error.body, request.method, request.fullpath))
43
- return R.error(resp=R.Code.cus_code(401, "系统未授权! {}".format(error.body)))
44
-
45
- @app.error(403)
46
- def unauthorized(error):
47
- response.status = 403
48
- log.error("访问受限: {} {} {}".format(error.body, request.method, request.fullpath))
49
- return R.error(resp=R.Code.cus_code(403, "访问受限: {}".format(error.body)))
50
-
51
- @app.error(404)
52
- def not_found(error):
53
- response.status = 404
54
- log.error("404 not found : {} {} {}".format(error.body, request.method, request.fullpath))
55
- return R.error(resp=R.Code.cus_code(404, "资源未找到: {}".format(error.body)))
56
-
57
- @app.error(405)
58
- def method_not_allow(error):
59
- response.status = 405
60
- log.error("请求方法错误: {} {} {}".format(error.status_line, request.method, request.fullpath))
61
- return R.error(resp=R.Code.cus_code(405, '请求方法错误: {}'.format(error.status_line)))
62
-
63
- @app.error(500)
64
- def internal_error(error):
65
- response.status = 500
66
- log.error("系统发生错误: {} {} {}".format(error.body, request.method, request.fullpath))
67
- return R.error(msg='系统发生错误: {}'.format(error.exception))
68
-
69
- @app.hook('after_request')
70
- def after_request():
71
- enable_cors()
72
-
73
- app.install(params_resolve)
74
- return app
75
-
76
- def enable_cors():
77
- response.headers['Access-Control-Allow-Origin'] = '*'
78
- response.headers['Access-Control-Allow-Methods'] = 'GET, POST, PUT, DELETE, OPTIONS'
79
- request_headers = request.headers.get('Access-Control-Request-Headers')
80
- response.headers['Access-Control-Allow-Headers'] = request_headers if request_headers else ''
81
- response.headers['Access-Control-Expose-Headers'] = '*'
82
-
83
- # annotation
84
- def before_intercept(order=0):
85
- def decorator(func):
86
- log.info("add before interceptor: {}".format(func.__name__))
87
- GlobalState.interceptors.append({'order': order, 'func': func})
88
- GlobalState.interceptors = sorted(GlobalState.interceptors, key=lambda x: x['order'])
89
- return decorator
90
-
91
- # annotation
92
- def rule(key):
93
- def return_func(func):
94
- @wraps(func)
95
- def decorated(*args, **kwargs):
96
- # if GlobalState.licenseInfo is not None and key not in GlobalState.licenseInfo.access_module:
97
- # log.error("系统未授权! {} {}".format(request.fullpath, '当前请求的模块未授权!请联系管理员!'))
98
- # return R.error(resp=R.Code.cus_code(9999, "系统未授权! {}".format('当前请求的模块未授权!请联系管理员!')))
99
- return func(*args, **kwargs)
100
- return decorated
101
- return return_func
102
-
103
- # annotation or plugins, has auto install, don't need to call
104
- def params_resolve(func):
105
- @wraps(func)
106
- def decorated(*args, **kwargs):
107
- if func_has_params.get(request.fullpath) is not None and not func_has_params.get(request.fullpath):
108
- return func(*args, **kwargs)
109
- if func_has_params.get(request.fullpath) is None:
110
- sig = inspect.signature(func)
111
- params = sig.parameters
112
- if not params.get('params'):
113
- func_has_params[request.fullpath] = False
114
- return func(*args, **kwargs)
115
- else:
116
- func_has_params[request.fullpath] = True
117
- if request.method == 'GET':
118
- queryStr = request.query.decode('utf-8')
119
- page_info = PageInfo(
120
- page_size=10 if request.headers.get('page_size') is None else int(request.headers.get('page_size')),
121
- page_index=1 if request.headers.get('page_index') is None else int(request.headers.get('page_index'))
122
- )
123
- queryStr.page_info = page_info
124
- return func(params=queryStr, *args, **kwargs)
125
- elif request.method == 'POST':
126
- query_params = request.query.decode('utf-8')
127
- content_type = request.get_header('content-type')
128
- if content_type == 'application/json':
129
- params = request.json or {}
130
- dict_wrapper = DictWrapper(params)
131
- dict_wrapper.update(query_params.dict)
132
- return func(params=dict_wrapper, *args, **kwargs)
133
- elif 'multipart/form-data' in content_type:
134
- form_data = request.forms.decode()
135
- form_files = request.files.decode()
136
- dict_wrapper = DictWrapper(form_data)
137
- dict_wrapper.update(query_params.dict)
138
- dict_wrapper.files = form_files
139
- return func(params=dict_wrapper, *args, **kwargs)
140
- elif 'application/x-www-form-urlencoded' in content_type:
141
- params = request.forms.decode()
142
- dict_wrapper = DictWrapper(params.dict)
143
- dict_wrapper.update(query_params.dict)
144
- return func(params=dict_wrapper, *args, **kwargs)
145
- elif 'text/plain' in content_type:
146
- params = request.body.read().decode('utf-8')
147
- dict_wrapper = DictWrapper({'body': params})
148
- dict_wrapper.update(query_params.dict)
149
- return func(params=dict_wrapper, *args, **kwargs)
150
- else:
151
- return func(*args, **kwargs)
152
- return decorated
153
-
154
- class PageInfo:
155
- def __init__(self, page_size, page_index):
156
- self.page_size = page_size
157
- self.page_index = page_index
158
-
159
- # 通用的鉴权方法
160
- def common_auth_verify(aes_key):
161
- if request.path.startswith('/static') or request.path in GlobalState.withOutLoginURI:
162
- return R.ok(to_json_str=False)
163
- auth_token = request.get_header('Authorization')
164
- if auth_token is None:
165
- auth_token = request.get_cookie('Authorization')
166
- payload = ctoken.get_payload(auth_token, aes_key)
167
- if payload:
168
- return R.ok(to_json_str=False)
169
- return R.error(resp=R.Code.cus_code(401, "未授权"), to_json_str=False)
@@ -1,143 +0,0 @@
1
- import sys
2
- from socketserver import ThreadingMixIn
3
- from wsgiref.simple_server import WSGIServer, WSGIRequestHandler, make_server
4
-
5
- from bottle import ServerAdapter, Bottle, template, static_file, abort, redirect, response
6
-
7
- from ctools import sys_info
8
-
9
- """
10
- module_names = list(globals().keys())
11
- def get_modules():
12
- mods = []
13
- for modname in module_names:
14
- if modname == 'base' or modname == 'online' or modname.startswith('__') or modname == 'importlib': continue
15
- module = globals()[modname]
16
- mods.append(module)
17
- return mods
18
-
19
- def get_ws_modules():
20
- from . import websocket
21
- return [websocket]
22
- """
23
-
24
- """
25
- from ctools import bottle_web_base, token, bottle_webserver
26
- from ctools.api_result import R
27
-
28
- secret_key = "xxx"
29
- app = bottle_web_base.init_app('子模块写 context_path, 主模块就不用写任何东西')
30
-
31
- # 通用的鉴权方法
32
- @bottle_web_base.before_intercept(0)
33
- def token_check():
34
- return bottle_web_base.common_auth_verify(secret_key)
35
-
36
- @app.post('/login')
37
- def login(params):
38
- return R.ok(token.gen_token({'username': 'xxx'}, secret_key, 3600))
39
-
40
- @app.get('/demo')
41
- @bottle_web_base.rule('DOC:DOWNLOAD')
42
- def demo(params):
43
- print(params)
44
-
45
- main_app = bottle_webserver.init_bottle() # 这里可以传 APP 当做主模块, 但是 context_path 就不好使了, 上下文必须是 /
46
- main_app.mount(app.context_path, app)
47
- main_app.set_index(r'轨迹点位压缩.html')
48
- main_app.run()
49
- """
50
-
51
- _default_port = 8888
52
-
53
- class CBottle:
54
-
55
- def __init__(self, bottle: Bottle, port=_default_port, quiet=False):
56
- self.port = port
57
- self.quiet = quiet
58
- self.bottle = bottle
59
- self.index_root = './'
60
- self.index_filename = 'index.html'
61
- self.is_tpl = False
62
- self.tmp_args = {}
63
- self.redirect_url = None
64
- self.static_root = './static'
65
- self.download_root = './download'
66
-
67
- @self.bottle.route(['/', '/index'])
68
- def index():
69
- try:
70
- if self.redirect_url: return redirect(self.redirect_url)
71
- if self.is_tpl: return template(f"{self.index_root}/{self.index_filename}", self.tmp_args)
72
- return static_file(filename=self.index_filename, root=self.index_root)
73
- except FileNotFoundError:
74
- abort(404, "File not found...")
75
-
76
- @self.bottle.route('/static/<filepath:path>')
77
- def static(filepath):
78
- try:
79
- return static_file(filepath, root=self.static_root)
80
- except FileNotFoundError:
81
- abort(404, "File not found...")
82
-
83
- @self.bottle.route('/download/<filepath:path>')
84
- def download(filepath):
85
- return static_file(filepath, root=self.download_root, download=True)
86
-
87
- @self.bottle.route('/favicon.ico')
88
- def favicon():
89
- response.content_type = 'image/svg+xml'
90
- svg_icon = '''<?xml version="1.0" encoding="UTF-8"?>
91
- <svg width="32" height="32" viewBox="0 0 32 32" xmlns="http://www.w3.org/2000/svg">
92
- <circle cx="16" cy="16" r="14" fill="#007bff"/>
93
- <path d="M16 8a8 8 0 0 0-8 8h2a6 6 0 0 1 12 0h2a8 8 0 0 0-8-8z" fill="white"/>
94
- <circle cx="16" cy="20" r="2" fill="white"/>
95
- </svg>
96
- '''
97
- return svg_icon
98
-
99
- def run(self):
100
- http_server = WSGIRefServer(port=self.port)
101
- print('Click the link below to open the service homepage %s' % '\n \t\t http://localhost:%s \n \t\t http://%s:%s' % (self.port, sys_info.get_local_ipv4(), self.port), file=sys.stderr)
102
- self.bottle.run(server=http_server, quiet=self.quiet)
103
-
104
- def set_index(self, filename='index.html', root='./', is_tpl=False, redirect_url=None, **kwargs):
105
- self.index_root = root
106
- self.index_filename = filename
107
- self.is_tpl = is_tpl
108
- self.redirect_url = redirect_url
109
- self.tmp_args = kwargs
110
-
111
- def set_static(self, root='./static'):
112
- self.static_root = root
113
-
114
- def set_download(self, root='./download'):
115
- self.download_root = root
116
-
117
- def mount(self, context_path, app, **kwargs):
118
- self.bottle.mount(context_path, app, **kwargs)
119
-
120
- def init_bottle(app:Bottle=None, port=_default_port, quiet=False) -> CBottle:
121
- bottle = app or Bottle()
122
- return CBottle(bottle, port, quiet)
123
-
124
- class ThreadedWSGIServer(ThreadingMixIn, WSGIServer):
125
- daemon_threads = True
126
-
127
- class CustomWSGIHandler(WSGIRequestHandler):
128
- def log_request(*args, **kw): pass
129
-
130
- class WSGIRefServer(ServerAdapter):
131
-
132
- def __init__(self, host='0.0.0.0', port=_default_port):
133
- super().__init__(host, port)
134
- self.server = None
135
-
136
- def run(self, handler):
137
- req_handler = WSGIRequestHandler
138
- if self.quiet: req_handler = CustomWSGIHandler
139
- self.server = make_server(self.host, self.port, handler, server_class=ThreadedWSGIServer, handler_class=req_handler)
140
- self.server.serve_forever()
141
-
142
- def stop(self):
143
- self.server.shutdown()
@@ -1,75 +0,0 @@
1
- from bottle import ServerAdapter, Bottle
2
- from geventwebsocket.handler import WebSocketHandler
3
-
4
- from ctools import sys_log
5
-
6
- """
7
- module_names = list(globals().keys())
8
- def get_modules():
9
- mods = []
10
- for modname in module_names:
11
- if modname == 'base' or modname == 'online' or modname.startswith('__') or modname == 'importlib': continue
12
- module = globals()[modname]
13
- mods.append(module)
14
- return mods
15
-
16
- def get_ws_modules():
17
- from . import websocket
18
- return [websocket]
19
- """
20
-
21
- """
22
- ws_app = bottle_web_base.init_app('/websocket_demo')
23
-
24
- @ws_app.route('/script_debug', apply=[websocket])
25
- @bottle_web_base.rule('DOC:DOWNLOAD')
26
- def script_debug(ws: WebSocket):
27
- print(123)
28
-
29
- socket_app = bottle_websocket.init_bottle()
30
- socket_app.mount(app.context_path, ws_app)
31
- socket_app.run()
32
- """
33
-
34
- _default_port = 8887
35
-
36
- class CBottle:
37
-
38
- def __init__(self, bottle: Bottle, port=_default_port, quiet=False):
39
- self.port = port
40
- self.quiet = quiet
41
- self.bottle = bottle
42
-
43
- def run(self):
44
- socket_server = WebSocketServer(port=self.port)
45
- self.bottle.run(server=socket_server, quiet=self.quiet)
46
-
47
- def mount(self, context_path, app):
48
- self.bottle.mount(context_path, app)
49
-
50
- def init_bottle(port=_default_port, quiet=False) -> CBottle:
51
- bottle = Bottle()
52
- return CBottle(bottle, port, quiet)
53
-
54
- class CustomWebSocketHandler(WebSocketHandler):
55
- def log_request(self):
56
- if '101' not in str(self.status):
57
- log_msg = self.format_request()
58
- for nk in sys_log.neglect_keywords:
59
- if nk in log_msg:
60
- return
61
- self.logger.info(log_msg)
62
-
63
- class WebSocketServer(ServerAdapter):
64
-
65
- def __init__(self, host='0.0.0.0', port=_default_port):
66
- super().__init__(host, port)
67
- self.server = None
68
-
69
- def run(self, handler):
70
- from gevent import pywsgi
71
- self.server = pywsgi.WSGIServer((self.host, self.port), handler, handler_class=CustomWebSocketHandler)
72
- self.server.serve_forever()
73
-
74
- def stop(self):
75
- self.server.stop()
@@ -1,314 +0,0 @@
1
- import os
2
- import time
3
-
4
- from business.common.constant import Scheduler
5
- from lxml import etree
6
- from lxml import html
7
- from pynput import keyboard
8
- from selenium import webdriver
9
- from selenium.common import NoSuchElementException, WebDriverException, NoSuchWindowException
10
- from selenium.webdriver.chrome.options import Options
11
- from selenium.webdriver.chrome.service import Service
12
- from selenium.webdriver.common.by import By
13
- from urllib3.exceptions import MaxRetryError
14
-
15
- from ctools import application, string_tools
16
-
17
- keyboard_listener = None
18
- ctrl_pressed = None
19
- g_driver = None
20
- g_callback = None
21
- g_result = []
22
- g_quite_flag = False
23
- picture_path = ""
24
-
25
- def get_hovered_element_html(url, explore, callback):
26
- global g_driver, g_callback, g_result
27
- g_callback = callback
28
- g_driver = explore.init()
29
- driver = g_driver
30
- driver.maximize_window()
31
- driver.get(url)
32
- start_keyboard_listener()
33
- handle_arr = [driver.current_window_handle]
34
- close_page_flag = False
35
- while g_driver and not g_quite_flag:
36
- try:
37
- try:
38
- if len(driver.window_handles) == 0:
39
- break_func()
40
- break
41
- except WebDriverException:
42
- break_func()
43
- break
44
- except MaxRetryError:
45
- break_func()
46
- break
47
- try:
48
- driver.find_element(value="ck-overlay")
49
- except NoSuchElementException as e:
50
- driver.execute_script(explore.listen_script)
51
- except Exception:
52
- pass
53
- for handle in driver.window_handles:
54
- if handle in handle_arr: continue
55
- if not close_page_flag: driver.execute_script(overlay_script)
56
- handle_arr.append(handle)
57
- driver.switch_to.window(handle)
58
- try:
59
- driver.execute_script(explore.listen_script)
60
- except Exception:
61
- continue
62
- close_page_flag = False
63
- time.sleep(0.5)
64
- cursor_html = driver.execute_script(explore.return_script)
65
- if cursor_html:
66
- g_result.clear()
67
- cursor_dom = html.fragment_fromstring(cursor_html)
68
- cursor_dom.set("ck-flag", "ck")
69
- enhance_cursor_html = etree.tostring(cursor_dom, method="html", encoding="unicode")
70
- page_html = driver.page_source.replace(cursor_html, enhance_cursor_html)
71
- page_dom_tree = etree.ElementTree(etree.HTML(page_html))
72
- match_dom = page_dom_tree.xpath('//*[@ck-flag="ck"]')
73
- for ck_element in match_dom:
74
- ck_xpath = page_dom_tree.getpath(ck_element)
75
- #print('XPATH IS {}'.format(ck_xpath))
76
- try:
77
- ele = driver.find_element(By.XPATH, ck_xpath)
78
- #print('XPATH_HTML: {}'.format(ele.get_attribute('outerHTML')))
79
- except Exception:
80
- pass
81
- g_result.append(ck_xpath)
82
- except NoSuchWindowException as e:
83
- close_page_flag = True
84
- handle_arr = []
85
- try:
86
- driver.switch_to.window(driver.window_handles[-1])
87
- driver.execute_script(hide_shade)
88
- except Exception:
89
- print('切换HANDLE失败:', e)
90
- break_func()
91
- break
92
- except Exception as e:
93
- print('全局错误:', e)
94
- break_func()
95
- break
96
- try:
97
- g_driver.quit()
98
- except Exception as e:
99
- pass
100
-
101
- def break_func():
102
- keyboard_listener.stop()
103
- g_callback(None)
104
-
105
- def on_press(key):
106
- global keyboard_listener, ctrl_pressed, g_driver, g_quite_flag, picture_path
107
- if key == keyboard.Key.ctrl_l and not ctrl_pressed:
108
- ctrl_pressed = True
109
- elif key == keyboard.Key.esc:
110
- g_result.clear()
111
- keyboard_listener.stop()
112
- g_quite_flag = True
113
- g_callback(None)
114
- elif hasattr(key, 'vk') and key.vk == 192 and ctrl_pressed:
115
- # print("g_result: %s" % g_result)
116
- if g_result:
117
- try:
118
- select_element = g_driver.find_element(By.XPATH, g_result[0])
119
- picture_path = "%s.png" % os.path.join(application.Server.screenshotPath, "element-"+string_tools.get_uuid())
120
- select_element.screenshot(picture_path)
121
- except Exception:
122
- pass
123
-
124
- keyboard_listener.stop()
125
- g_quite_flag = True
126
- g_callback(g_result)
127
-
128
- def on_release(key):
129
- global ctrl_pressed
130
- if key == keyboard.Key.ctrl_l:
131
- ctrl_pressed = False
132
-
133
- def start_keyboard_listener():
134
- global keyboard_listener
135
- keyboard_listener = keyboard.Listener(on_press=on_press, on_release=on_release)
136
- keyboard_listener.start()
137
-
138
-
139
- overlay_script = """
140
- // 创建遮罩层
141
- var shade = document.createElement('div');
142
- shade.id = 'ck-shade-parent';
143
- shade.style.position = 'fixed';
144
- shade.style.top = '0';
145
- shade.style.left = '0';
146
- shade.style.width = '100%';
147
- shade.style.height = '100%';
148
- shade.style.backgroundColor = '#000'; // 使用纯色背景
149
- shade.style.filter = 'alpha(opacity=60)'; // 设置透明度,IE8-IE9
150
- shade.style.opacity = '0.8'; // 设置透明度,现代浏览器
151
- shade.style.zIndex = '9999';
152
- document.body.appendChild(shade);
153
-
154
- // 创建覆盖内容
155
- var overlayContent = document.createElement('div');
156
- overlayContent.id = 'ck-shade-oc';
157
- overlayContent.className = 'overlay-content';
158
- overlayContent.style.position = 'absolute';
159
- overlayContent.style.top = '50%';
160
- overlayContent.style.left = '50%';
161
- overlayContent.style.transform = 'translate(-50%, -50%)';
162
- overlayContent.style.backgroundColor = 'white';
163
- overlayContent.style.padding = '20px';
164
- overlayContent.style.borderRadius = '8px';
165
- overlayContent.style.textAlign = 'center';
166
- shade.appendChild(overlayContent);
167
-
168
- // 创建消息内容
169
- var message = document.createElement('p');
170
- message.id = 'ck-shade-msg';
171
- message.innerText = '当前页面未激活,请关闭激活状态的录制页面';
172
- message.style.color = '#000'; // 设置文本颜色为黑色
173
- message.style.fontSize = '16px'; // 设置文本大小
174
- overlayContent.appendChild(message);
175
-
176
- """
177
-
178
- hide_shade = """
179
- var shade = document.getElementById('ck-shade-parent');
180
- if (shade) {
181
- shade.parentNode.removeChild(shade);
182
- }
183
- """
184
-
185
- class IE:
186
-
187
- @staticmethod
188
- def init():
189
- ie_options = webdriver.IeOptions()
190
- ie_options.ignore_protected_mode_settings = True
191
- ie_options.ignore_zoom_level = True
192
- ie_options.require_window_focus = True
193
- return webdriver.Ie(options=ie_options)
194
-
195
- listen_script = """
196
- var overlay = document.createElement('div');
197
- overlay.id = 'ck-overlay';
198
- overlay.style.position = 'absolute';
199
- overlay.style.border = '2px solid red';
200
- overlay.style.pointerEvents = 'none';
201
- overlay.style.zIndex = '9999';
202
- document.body.appendChild(overlay);
203
- var addEvent = function(elem, type, eventHandle) {
204
- if (elem == null || typeof(elem) == 'undefined') return;
205
- if (elem.addEventListener) {
206
- elem.addEventListener(type, eventHandle, false);
207
- } else if (elem.attachEvent) {
208
- elem.attachEvent('on' + type, eventHandle);
209
- } else {
210
- elem['on' + type] = eventHandle;
211
- }
212
- };
213
-
214
- addEvent(document, 'mousemove', function(e) {
215
- e = e || window.event;
216
- var element = document.elementFromPoint(e.clientX, e.clientY);
217
- window.hoveredElement = element;
218
- if (element === overlay) return;
219
- var rect = element.getBoundingClientRect();
220
- overlay.style.left = (rect.left + (window.pageXOffset || document.documentElement.scrollLeft || document.body.scrollLeft) - 5) + 'px';
221
- overlay.style.top = (rect.top + (window.pageYOffset || document.documentElement.scrollTop || document.body.scrollTop) - 5) + 'px';
222
- overlay.style.width = (element.offsetWidth + 10) + 'px';
223
- overlay.style.height = (element.offsetHeight + 10) + 'px';
224
- });
225
- """
226
-
227
- return_script = """
228
- return window.hoveredElement ? window.hoveredElement.outerHTML : null;
229
- """
230
-
231
- overlay_script = overlay_script
232
-
233
-
234
- class Chrome:
235
-
236
- @staticmethod
237
- def init():
238
- option = Options()
239
- option.binary_location = Scheduler.CHROME_PATH
240
- service = Service(Scheduler.CHROME_DRIVER_PATH)
241
- return webdriver.Chrome(options=option, service=service)
242
-
243
- listen_script = """
244
- var overlay = document.createElement('div');
245
- overlay.id = 'ck-overlay';
246
- overlay.style.position = 'absolute';
247
- overlay.style.border = '2px solid red';
248
- overlay.style.pointerEvents = 'none';
249
- overlay.style.zIndex = '9998';
250
- document.body.appendChild(overlay);
251
-
252
- function throttle(func, limit) {
253
- let inThrottle;
254
- return function() {
255
- const args = arguments,
256
- context = this;
257
- if (!inThrottle) {
258
- func.apply(context, args);
259
- inThrottle = true;
260
- setTimeout(() => inThrottle = false, limit);
261
- }
262
- };
263
- }
264
-
265
- document.addEventListener('mousemove', throttle(function(e) {
266
- var element = document.elementFromPoint(e.clientX, e.clientY);
267
- window.hoveredElement = element;
268
- if(element.id.indexOf('ck-shade') !== -1) return;
269
- if (window.hoveredElement) {
270
- var rect = element.getBoundingClientRect();
271
- overlay.style.left = (rect.left + window.pageXOffset - 5) + 'px';
272
- overlay.style.top = (rect.top + window.pageYOffset - 5) + 'px';
273
- overlay.style.width = (element.offsetWidth + 10) + 'px';
274
- overlay.style.height = (element.offsetHeight + 10) + 'px';
275
- }
276
- }, 50));
277
- """
278
-
279
- return_script = """
280
- return window.hoveredElement ? window.hoveredElement.outerHTML : null;
281
- """
282
-
283
- overlay_script = overlay_script
284
-
285
-
286
- def callback(xpath):
287
- print("Hovered Element XPATH IS :", xpath)
288
-
289
- def get_element(url: str = None, explore: str = "chrome"):
290
- global keyboard_listener, ctrl_pressed, g_driver, g_callback, g_result, g_quite_flag, picture_path
291
- keyboard_listener = None
292
- ctrl_pressed = None
293
- g_driver = None
294
- g_callback = None
295
- g_result = []
296
- g_quite_flag = False
297
- picture_path = ""
298
-
299
- if explore == "chrome":
300
- explore = Chrome
301
- else:
302
- explore = IE
303
-
304
- if "http" not in url[:5]:
305
- url = "http://%s" % url
306
-
307
- get_hovered_element_html(url, explore, callback)
308
-
309
- return g_result, picture_path
310
-
311
- if __name__ == "__main__":
312
- # from explore_record_core import get_hovered_element_html, Chrome
313
- g_result, picture_path = get_element("weibo.com")
314
- print(g_result, picture_path)