update: bump 'common' version to 0.1.15

This commit is contained in:
2026-05-22 15:51:49 +08:00
parent 9779d1d407
commit 3b9af6e57e
3 changed files with 37 additions and 41 deletions

View File

@@ -4,26 +4,26 @@
<textarea id="messages" name="messages" rows="45" cols="100" readonly> <textarea id="messages" name="messages" rows="45" cols="100" readonly>
</textarea> </textarea>
<script type="text/javascript"> <script type="module">
function main(args) { import { default as $, Rpc2, LogRecord } from '/';
let messages = document.querySelector("#messages"); let { parameters } = await Rpc2.invoke('context');
let account = new String(args['account']);
let name = account.split('@', 1).pop() ?? 'unknown';
name = name.charAt(0).toLocaleUpperCase() + name.slice(1); let account = new String(parameters['account']);
document.title += ` (${name})`; let name = account.split('@', 1).pop() ?? 'unknown';
name = name.charAt(0).toLocaleUpperCase() + name.slice(1);
document.title += ` (${name})`;
setInterval(async () => { while (await new Promise(o => setTimeout(o, 1000, true))) {
let result = await Rpc2.invoke('history'); let result = await Rpc2.invoke('history').catch(() => []);
let logs = Array.from(result); let logs = Array.from(result);
for (let record of logs) { for (let record of logs) {
let message = LogRecord.format(record); if ($('#messages').childNodes.length >= 500) $('#messages').childNodes.item(0)?.remove();
let node = document.createTextNode(new String(message).concat('\n')); let message = LogRecord.format(record);
messages.appendChild(node); let node = document.createTextNode(new String(message).concat('\n'));
} $('#messages').appendChild(node);
messages.scrollTop = messages.scrollHeight; }
}, 1000); $('#messages').scrollTop = messages.scrollHeight;
} }
</script> </script>
@@ -45,4 +45,4 @@ textarea {
textarea:focus { textarea:focus {
outline: none; outline: none;
} }
</style> </style>

42
main.py
View File

@@ -9,7 +9,7 @@ from selenium.webdriver.chrome.webdriver import WebDriver
from selenium.webdriver.chrome.options import Options from selenium.webdriver.chrome.options import Options
from selenium.webdriver.common.by import By from selenium.webdriver.common.by import By
from common import jsonrpc2 from common.jsonrpc2 import ServiceProvider
from common.utils import * from common.utils import *
from io import BytesIO from io import BytesIO
@@ -33,28 +33,30 @@ WEBURL = "https://crm.xiaoman.cn/business/export"
APIURL = "https://crm.xiaoman.cn/api/opportunityRead/export" APIURL = "https://crm.xiaoman.cn/api/opportunityRead/export"
def main(driver: WebDriver, logger = logging.getLogger('main')): def main(driver: WebDriver, logger = logging.getLogger('main')):
parameters = vars(args)
http = PoolManager()
sp = ServiceProvider.default()
try: try:
http = PoolManager() sp.set('context', lambda: { 'parameters': parameters })
parameters = vars(args) driver.get(sp.run())
driver.get(str(Path('index.html').resolve()))
driver.execute_script(jsonrpc2.prelude(), parameters)
except Exception as e: except Exception as e:
logger.critical('Unable to load starup page', exc_info=e) logger.critical('Unable to load starup page', exc_info=e)
return 2 return 2
try: try:
driver.switch_to.new_window('tab') driver.switch_to.new_window('tab')
driver.set_page_load_timeout(parameters.get('timeout')) driver.set_page_load_timeout(parameters['timeout'])
driver.get(WEBURL) driver.get(WEBURL)
except TimeoutException: except TimeoutException:
logger.warning('Timeout') logger.warning('Timeout')
driver.execute_script("window.stop();") driver.execute_script("window.stop();")
try: try:
setup(driver, parameters.get('attempts'), parameters.get('timeout'), 0) setup(driver, parameters)
until(lambda x: 'loginProgress' in x.find_element(By.TAG_NAME, "body").get_attribute('class'), watch=False) until(lambda x: 'loginProgress' in x.find_element(By.TAG_NAME, "body").get_attribute('class'), watch=False)
account = str(parameters.get('account')) account = str(parameters['account'])
password = str(parameters.get('password')) password = str(parameters['password'])
logger.info('Logging in as %s (%s)', account.split('@', 1).pop(0).capitalize(), account) logger.info('Logging in as %s (%s)', account.split('@', 1).pop(0).capitalize(), account)
locate("input.account").send_keys(account) locate("input.account").send_keys(account)
@@ -62,7 +64,7 @@ def main(driver: WebDriver, logger = logging.getLogger('main')):
click("input.agree-checkbox") click("input.agree-checkbox")
click("button.login-btn") click("button.login-btn")
except Exception as e: except Exception as e:
logger.critical('Unable to login to %s', parameters.get('url'), exc_info=e) logger.critical('Unable to login to %s', parameters['url'], exc_info=e)
return 3 return 3
logger.info('Waiting for authentication to complete...') logger.info('Waiting for authentication to complete...')
@@ -101,8 +103,8 @@ def main(driver: WebDriver, logger = logging.getLogger('main')):
continue continue
try: try:
locate(".safe-verify-dialog:not([style*='display: none']) .mm-modal-content .mm-modal-body input", wait=False).send_keys(parameters.get('password')) locate(".safe-verify-dialog:not([style*='display: none']) .mm-modal-content .mm-modal-body input", wait=False).send_keys(parameters['password'])
click(".mm-modal-footer button.okki-btn-primary", wait=False) click(".mm-modal-footer button.okki-btn-primary")
except: except:
pass pass
@@ -121,7 +123,7 @@ def main(driver: WebDriver, logger = logging.getLogger('main')):
href = download.get_attribute('href') href = download.get_attribute('href')
response = http.request("GET", href) response = http.request("GET", href)
text = response.data.decode(parameters.get('encoding')).splitlines() text = response.data.decode(parameters['encoding']).splitlines()
data = csv.reader(text) data = csv.reader(text)
logger.info('Read %d line(s) total', len(text)) logger.info('Read %d line(s) total', len(text))
except Exception as e: except Exception as e:
@@ -185,9 +187,9 @@ def main(driver: WebDriver, logger = logging.getLogger('main')):
href href
) )
if parameters.get('open'): if parameters['open']:
try: try:
path = Path.home() / 'Downloads' / filename path = Path(parameters['directory']) / filename
until(lambda _: path.exists(), watch=False) until(lambda _: path.exists(), watch=False)
Popen(['start', str(path)], shell=True) Popen(['start', str(path)], shell=True)
except Exception as e: except Exception as e:
@@ -204,20 +206,14 @@ if __name__ == '__main__':
level = logging.getLevelNamesMapping().get(args.log_level, 'INFO') level = logging.getLevelNamesMapping().get(args.log_level, 'INFO')
logger.setLevel(level) logger.setLevel(level)
logger.info('Initializing...')
history = jsonrpc2.History()
logger.addHandler(history)
opts = jsonrpc2.Options()
jsonrpc2.define('history', lambda: history.truncate())
jsonrpc2.run(opts)
logger.info('Creating automation instance')
opts = Options() opts = Options()
opts.enable_downloads = True opts.enable_downloads = True
opts.add_argument('--deny-permission-prompts') opts.add_argument('--deny-permission-prompts')
opts.add_experimental_option('prefs', { 'download.default_directory': args.directory }) opts.add_experimental_option('prefs', { 'download.default_directory': args.directory })
driver = WebDriver(options=opts) driver = WebDriver(options=opts)
status = main(driver) status = main(driver)
except KeyboardInterrupt:
status = 0
except Exception as e: except Exception as e:
logger.critical('Fatal error', exc_info=e) logger.critical('Fatal error', exc_info=e)
status = 1 status = 1

Binary file not shown.