提交 aa3864e6 authored 作者: 陈泽健's avatar 陈泽健

```

chore(AuxiliaryTool): 删除远程部署脚本文件

- 移除 add_admin.py 脚本文件
- 移除 add_meeting_room.py 脚本文件
- 移除 admin_nav.py 脚本文件
- 移除 arm_license_final.py 脚本文件
- 移除 arm_license_robust.py 脚本文件
- 移除 arm_license_v2.py 脚本文件
```
上级 28205e94
#!/usr/bin/env python3
# -*- coding: utf-8 -*-
"""
公司管理员设置 - 点击添加并填写表单
"""
import sys
import time
import json
import os
from datetime import datetime
from selenium import webdriver
from selenium.webdriver.chrome.options import Options
if sys.platform == 'win32':
try: sys.stdout.reconfigure(encoding='utf-8', errors='replace')
except: pass
BASE = 'https://192.168.9.76'
REPORTS = r"E:\GithubData\ubains-module-test\AuxiliaryTool\ScriptTool\RemoteDeploy\reports"
def log(msg):
print(f"[{datetime.now().strftime('%H:%M:%S')}] {msg}", flush=True)
def screenshot(driver, name):
driver.save_screenshot(os.path.join(REPORTS, f'add_{name}.png'))
def main():
log("=" * 60)
log("公司管理员 - 添加用户")
log("=" * 60)
opts = Options()
opts.add_argument('--ignore-certificate-errors')
opts.add_argument('--ignore-ssl-errors')
opts.add_argument('--window-size=1920,1080')
driver = webdriver.Chrome(options=opts)
driver.implicitly_wait(10)
try:
# 登录
driver.get(f'{BASE}/#/LoginAdmin')
time.sleep(8)
for attempt in range(3):
body = driver.execute_script("return document.body.innerText.substring(0, 300);")
if '系统管理' in body:
log("✅ 已登录")
break
log(f"登录 #{attempt+1}")
driver.execute_script("""
var inputs = document.querySelectorAll('input');
inputs.forEach(function(i) {
if (i.offsetParent === null) return;
var p = i.placeholder || '';
var type = i.type || '';
if (p.indexOf('账号') >= 0) i.value = 'superadmin';
else if (type === 'password') i.value = 'Ubains@1357';
else if (p.indexOf('验证码') >= 0) i.value = 'csba';
i.dispatchEvent(new Event('input', {bubbles: true}));
});
""")
time.sleep(3)
driver.execute_script("document.querySelector('input[type=submit]')?.click()")
time.sleep(10)
if not ('系统管理' in driver.execute_script("return document.body.innerText.substring(0, 300);")):
driver.refresh()
time.sleep(5)
# 系统管理 -> 管理员设置
log("\n展开系统管理...")
driver.execute_script("""
var items = document.querySelectorAll('.el-submenu__title, span');
for (var i = 0; i < items.length; i++) {
if (items[i].textContent.trim() === '系统管理') { items[i].click(); break; }
}
""")
time.sleep(2)
log("点击管理员设置...")
driver.execute_script("""
var items = document.querySelectorAll('.el-menu-item');
for (var i = 0; i < items.length; i++) {
if (items[i].textContent.trim() === '管理员设置') { items[i].click(); break; }
}
""")
time.sleep(5)
# 点击"添加"按钮
log("\n点击'添加'按钮...")
driver.execute_script("""
var btns = document.querySelectorAll('button');
for (var i = 0; i < btns.length; i++) {
var t = btns[i].textContent.trim();
if (t === '添加' && btns[i].offsetParent !== null) {
btns[i].click();
return 'clicked: 添加';
}
}
return 'not found';
""")
time.sleep(3)
screenshot(driver, '01_after_add_click')
# 查看对话框
dialog = driver.execute_script("""
var dialogs = document.querySelectorAll('.el-dialog, [role=dialog]');
var result = [];
dialogs.forEach(function(d) {
if (d.offsetParent !== null) {
result.push({
title: (d.querySelector('.el-dialog__title') || {}).textContent || '',
body: d.textContent.substring(0, 400)
});
}
});
return JSON.stringify(result);
""")
log(f"对话框: {json.loads(dialog)}")
# 查看输入框
inputs = driver.execute_script("""
var inputs = document.querySelectorAll('input:not([type=hidden])');
var result = [];
inputs.forEach(function(i) {
if (i.offsetParent !== null) {
result.push({placeholder: i.placeholder, type: i.type});
}
});
return JSON.stringify(result);
""")
log(f"可见输入框: {json.loads(inputs)}")
# 点击公司下拉选择器
log("\n选择公司...")
driver.execute_script("""
var inputs = document.querySelectorAll('input');
for (var i = 0; i < inputs.length; i++) {
if (inputs[i].offsetParent !== null && inputs[i].placeholder === '请选择') {
inputs[i].click();
break;
}
}
""")
time.sleep(2)
# 选"自动化"公司
result = driver.execute_script("""
var items = document.querySelectorAll('.el-select-dropdown__item, li, span');
for (var i = 0; i < items.length; i++) {
var t = items[i].textContent.trim();
if ((t === '自动化' || t.indexOf('自动化') >= 0) && items[i].offsetParent !== null) {
items[i].click();
return 'selected: ' + t;
}
}
// 检查所有下拉选项
var allItems = document.querySelectorAll('.el-select-dropdown__item');
var list = Array.from(allItems).map(function(it) { return it.textContent.trim(); });
return 'not found 自动化, available: ' + JSON.stringify(list);
""")
log(f" 结果: {result}")
time.sleep(2)
# 填写用户名和密码
log("填写账号密码...")
driver.execute_script("""
var inputs = document.querySelectorAll('input:not([type=hidden])');
inputs.forEach(function(i) {
if (i.offsetParent === null) return;
var p = i.placeholder || '';
var type = i.type || '';
if (p.indexOf('账号') >= 0 || p.indexOf('用户名') >= 0) {
i.value = 'admin';
i.dispatchEvent(new Event('input', {bubbles: true}));
} else if (type === 'password' || p.indexOf('密码') >= 0) {
i.value = 'Admin@123456';
i.dispatchEvent(new Event('input', {bubbles: true}));
}
});
""")
time.sleep(2)
# 点击保存
log("点击'保存'...")
driver.execute_script("""
var btns = document.querySelectorAll('button');
for (var i = 0; i < btns.length; i++) {
var t = btns[i].textContent.trim();
if ((t === '确定' || t === '保存') && btns[i].offsetParent !== null) {
btns[i].click();
return 'clicked: ' + t;
}
}
return 'not found';
""")
time.sleep(3)
screenshot(driver, '02_saved')
body = driver.execute_script("return document.body.innerText.substring(0, 600);")
log(f"\n操作后页面:\n{body}")
if 'admin' in body.lower():
log("\n✅ company admin user created successfully!")
else:
log("\n⚠️ 可能需要确认,请查看浏览器")
log("\n浏览器保持打开60秒...")
time.sleep(60)
except Exception as e:
log(f"异常: {e}")
import traceback
traceback.print_exc()
finally:
driver.quit()
if __name__ == '__main__':
sys.exit(main())
\ No newline at end of file
#!/usr/bin/env python3
"""添加会议室 - 完整流程"""
import sys, time
from selenium import webdriver
from selenium.webdriver.chrome.options import Options
from selenium.webdriver.common.by import By
if sys.platform == 'win32':
try: sys.stdout.reconfigure(encoding='utf-8', errors='replace')
except: pass
def log(msg):
print(f"[{time.strftime('%H:%M:%S')}] {msg}", flush=True)
BASE = 'https://192.168.9.76'
def main():
log("添加会议室流程")
opts = Options()
opts.add_argument('--ignore-certificate-errors')
opts.add_argument('--ignore-ssl-errors')
opts.add_argument('--window-size=1920,1080')
d = webdriver.Chrome(options=opts)
d.implicitly_wait(10)
try:
d.get(f'{BASE}/#/LoginAdmin'); time.sleep(10)
for retry in range(3):
for inp in d.find_elements(By.TAG_NAME, 'input'):
if not inp.is_displayed(): continue
p = inp.get_attribute('placeholder') or ''; t = inp.get_attribute('type') or ''
if '账号' in p: inp.clear(); inp.send_keys('admin')
elif t == 'password': inp.clear(); inp.send_keys('Admin@2024ub')
elif '验证码' in p: inp.clear(); inp.send_keys('csba')
time.sleep(3)
for inp in d.find_elements(By.XPATH, '//input[@type="submit"]'):
if inp.is_displayed(): inp.click(); break
time.sleep(10)
if 'LoginAdmin' not in d.current_url: break
d.refresh(); time.sleep(5)
log('1. Login OK')
# 展开菜单
d.execute_script('document.querySelectorAll(".el-submenu__title").forEach(function(t) { t.click(); });')
time.sleep(3)
d.execute_script('''var items=document.querySelectorAll(".el-menu-item");
for(var i=0;i<items.length;i++){
if(items[i].textContent.trim()==="区域列表"&&items[i].offsetParent!==null){
items[i].click();break;
}
}''')
time.sleep(3)
log('2. 区域列表')
# 点击添加
d.execute_script('''var btns=document.querySelectorAll("button");
for(var i=0;i<btns.length;i++){
if(btns[i].textContent.trim()==="添加"&&btns[i].offsetParent!==null){
btns[i].click();break;
}
}''')
time.sleep(3)
log('3. 点击添加')
# 填名称
for inp in d.find_elements(By.TAG_NAME, 'input'):
if not inp.is_displayed(): continue
p = inp.get_attribute('placeholder') or ''
if '会议室' in p:
inp.clear(); inp.send_keys('测试会议室'); break
time.sleep(2)
log('4. 名称: 测试会议室')
# 点击第一个请选择
d.execute_script('''var inputs=document.querySelectorAll("input");var count=0;
for(var i=0;i<inputs.length;i++){
if(inputs[i].placeholder==="请选择"&&inputs[i].offsetParent!==null){
count++;if(count===1){inputs[i].click();break;}
}
}''')
time.sleep(3)
log('5. 点击预定授权')
# 选第一个CCA授权码
d.execute_script('''var items=document.querySelectorAll(".el-select-dropdown__item");
for(var i=0;i<items.length;i++){
var t=items[i].textContent.trim();
if(t.indexOf("CCA")>=0){items[i].click();break;}
}''')
time.sleep(2)
log('6. 选中授权码')
# 列出所有按钮
btn_info = d.execute_script('''var btns=document.querySelectorAll("button");
var result=[];
btns.forEach(function(b){
if(b.offsetParent!==null)result.push(b.textContent.trim());
});
return JSON.stringify(result);
''')
log('7. 按钮: ' + btn_info)
# 点击保存(注意按钮文字是"保 存"中间有空格)
d.execute_script('''var btns=document.querySelectorAll("button");
for(var i=0;i<btns.length;i++){
if(btns[i].textContent.trim().indexOf("存")>=0&&btns[i].offsetParent!==null){
btns[i].click();break;
}
}''')
time.sleep(3)
log('8. 点击保存')
body = d.execute_script('return document.body.innerText.substring(0, 400);')
log('9. ' + body[:150].replace(chr(10), ' ').replace(chr(160), ' '))
time.sleep(600)
finally:
d.quit()
if __name__ == '__main__':
main()
\ No newline at end of file
#!/usr/bin/env python3
"""后台管理 - 登录 + 刷新 + 导航到权限管理"""
import sys, time, os
from selenium import webdriver
from selenium.webdriver.chrome.options import Options
from selenium.webdriver.common.by import By
if sys.platform == 'win32':
try: sys.stdout.reconfigure(encoding='utf-8', errors='replace')
except: pass
BASE = 'https://192.168.9.76'
opts = Options()
opts.add_argument('--ignore-certificate-errors')
opts.add_argument('--ignore-ssl-errors')
opts.add_argument('--window-size=1920,1080')
d = webdriver.Chrome(options=opts)
d.implicitly_wait(10)
try:
print("访问后台管理 LoginAdmin...")
d.get(f'{BASE}/#/LoginAdmin')
time.sleep(8)
for inp in d.find_elements(By.TAG_NAME, "input"):
if not inp.is_displayed(): continue
p = inp.get_attribute("placeholder") or ""
t = inp.get_attribute("type") or ""
if "账号" in p: inp.clear(); inp.send_keys("admin")
elif t == "password": inp.clear(); inp.send_keys("Admin@2024ub")
elif "验证码" in p: inp.clear(); inp.send_keys("csba")
time.sleep(3)
for inp in d.find_elements(By.XPATH, "//input[@type='submit']"):
if inp.is_displayed(): inp.click(); break
time.sleep(8)
print(f"登录成功: {d.current_url}")
d.refresh()
time.sleep(5)
print(f"刷新完成: {d.current_url}")
# 展开系统管理
d.execute_script("""
var items = document.querySelectorAll('.el-submenu__title, span');
for (var i = 0; i < items.length; i++) {
if (items[i].textContent.trim() === '系统管理' && items[i].offsetParent !== null) {
items[i].click(); break;
}
}
""")
time.sleep(2)
print("已点击系统管理")
# 点击权限管理
d.execute_script("""
var items = document.querySelectorAll('.el-menu-item, span');
for (var i = 0; i < items.length; i++) {
if (items[i].textContent.trim() === '权限管理' && items[i].offsetParent !== null) {
items[i].click(); break;
}
}
""")
time.sleep(3)
body = d.execute_script("return document.body.innerText.substring(0, 400);")
print(f"\n权限管理页面:\n{body[:200]}")
print("\n浏览器保持打开,等待下一步指示...")
time.sleep(300)
finally:
d.quit()
\ No newline at end of file
#!/bin/bash
# ARM Ubuntu 自动化部署包装脚本(适配 ARM:/data/arm_offline_auto_unifiedPlatform + arm_new_auto.sh)
# 在服务器上以 root 身份后台运行,避免 SSH 长连接中断导致部署被杀。
#
# 原理:
# - TERM=dumb 使 whiptail 无法渲染,自动回退默认值
# - printf 管道预输入所有 y/n 应答
# - arm_new_auto.sh --all 跳过系统选择菜单,默认部署所有系统
#
# 应答顺序:
# y(继续执行) y(网口确认) y(日期确认) y(IP确认) y(系统类型) y(部署参数) y(开始部署) n(无企业NTP)
set -u
cd /data/arm_offline_auto_unifiedPlatform || { echo "DEPLOY_WRAPPER_FATAL 目录不存在"; exit 2; }
export TERM=dumb
export LC_ALL=C
echo "DEPLOY_WRAPPER_START $(date '+%Y-%m-%d %H:%M:%S')"
echo "工作目录: $(pwd)"
echo "TERM=$TERM (禁用 whiptail 交互对话框)"
if [ ! -f "./arm_new_auto.sh" ]; then
echo "DEPLOY_WRAPPER_FATAL 未找到 ./arm_new_auto.sh"
exit 3
fi
echo "======== 开始自动化部署 arm_new_auto.sh --all ========"
# y(继续) y(网口) y(日期) y(IP) y(系统类型) y(参数) y(开始) n(无NTP)
printf 'y\ny\ny\ny\ny\ny\ny\nn\n' | ./arm_new_auto.sh --all
EC=$?
echo ""
echo "======== 部署脚本执行完毕 退出码=$EC ========"
# 使环境变量生效
source /etc/profile 2>/dev/null || true
echo "DEPLOY_WRAPPER_FINISHED exit=$EC $(date '+%Y-%m-%d %H:%M:%S')"
exit $EC
#!/usr/bin/env python3
# -*- coding: utf-8 -*-
"""
ARM授权上传 - 简化版
分两步:先登录+调试页面元素,再上传授权文件
"""
import sys, os, time, traceback
from datetime import datetime
from selenium import webdriver
from selenium.webdriver.chrome.options import Options
from selenium.webdriver.common.by import By
from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC
from selenium.webdriver.common.keys import Keys
if sys.platform == 'win32':
try:
sys.stdout.reconfigure(encoding='utf-8', errors='replace')
sys.stderr.reconfigure(encoding='utf-8', errors='replace')
except: pass
BASE_URL = 'https://192.168.9.75'
ADMIN_USER = 'superadmin'
ADMIN_PASS = 'Ubains@1357'
CAPTCHA = 'csba'
LICENSE_FILE = r'E:\自动化部署\ARM-9.75\license.zip'
REPORTS_DIR = os.path.join(os.path.dirname(os.path.abspath(__file__)), 'reports')
def log(msg, level="INFO"):
ts = datetime.now().strftime('%H:%M:%S')
print(f"[{ts}] [{level}] {msg}", flush=True)
def screenshot(driver, name):
path = os.path.join(REPORTS_DIR, f'{name}.png')
driver.save_screenshot(path)
log(f"截图: {path}")
def main():
step = sys.argv[1] if len(sys.argv) > 1 else 'all'
chrome_options = Options()
chrome_options.add_argument('--ignore-certificate-errors')
chrome_options.add_argument('--ignore-ssl-errors=yes')
chrome_options.add_argument('--no-sandbox')
chrome_options.add_argument('--disable-dev-shm-usage')
chrome_options.add_argument('--window-size=1920,1080')
driver = webdriver.Chrome(options=chrome_options)
driver.implicitly_wait(10)
try:
# ===== 登录 =====
log("【登录】访问维护平台")
driver.get(f'{BASE_URL}/#/LoginConfig')
WebDriverWait(driver, 30).until(EC.presence_of_element_located((By.TAG_NAME, "button")))
time.sleep(5)
# 填写表单
driver.find_element(By.XPATH, "//input[contains(@placeholder,'账号')]").send_keys(ADMIN_USER)
time.sleep(0.5)
driver.find_element(By.XPATH, "//input[contains(@placeholder,'密码')]").send_keys(ADMIN_PASS)
time.sleep(0.5)
driver.find_element(By.XPATH, "//input[contains(@placeholder,'验证码')]").send_keys(CAPTCHA)
time.sleep(2)
# 点击登录
driver.find_element(By.XPATH, "//input[@type='submit']").click()
log("已点击登录按钮,等待跳转...")
# 等待登录跳转(最多30秒)
login_ok = False
for _ in range(6):
time.sleep(5)
if 'backstage' in driver.current_url or 'ServiceAuthorization' in driver.current_url:
login_ok = True
break
log(f"等待登录跳转... 当前URL: {driver.current_url}")
if not login_ok:
log("登录可能失败,尝试重新登录...")
screenshot(driver, 'login_retry')
# 重试
try:
driver.find_element(By.XPATH, "//input[contains(@placeholder,'账号')]").clear()
driver.find_element(By.XPATH, "//input[contains(@placeholder,'账号')]").send_keys(ADMIN_USER)
driver.find_element(By.XPATH, "//input[contains(@placeholder,'密码')]").clear()
driver.find_element(By.XPATH, "//input[contains(@placeholder,'密码')]").send_keys(ADMIN_PASS)
driver.find_element(By.XPATH, "//input[contains(@placeholder,'验证码')]").clear()
driver.find_element(By.XPATH, "//input[contains(@placeholder,'验证码')]").send_keys(CAPTCHA)
time.sleep(1)
driver.find_element(By.XPATH, "//input[@type='submit']").click()
time.sleep(10)
except Exception:
pass
log(f"当前URL: {driver.current_url}")
time.sleep(3)
screenshot(driver, 'step1_login_ok')
# ===== 点击上传授权文件 =====
log("【上传】点击上传授权文件")
upload_btn = WebDriverWait(driver, 10).until(
EC.element_to_be_clickable((By.XPATH, "//button[contains(.,'上传授权文件')]"))
)
upload_btn.click()
time.sleep(3)
# ===== 处理校验身份对话框 =====
log("【身份验证】填写密码和验证码")
WebDriverWait(driver, 10).until(
EC.visibility_of_element_located((By.XPATH, "//div[contains(@class,'el-dialog')]//input[@placeholder='请输入密码']"))
)
time.sleep(1)
pwd = driver.find_element(By.XPATH, "//div[contains(@class,'el-dialog')]//input[@placeholder='请输入密码']")
pwd.click(); time.sleep(0.3); pwd.clear(); pwd.send_keys(ADMIN_PASS)
log("密码已输入")
cap = driver.find_element(By.XPATH, "//div[contains(@class,'el-dialog')]//input[@placeholder='请输入图形验证码']")
cap.click(); time.sleep(0.3); cap.clear(); cap.send_keys(CAPTCHA)
log("验证码已输入")
time.sleep(2)
screenshot(driver, 'step2_dialog_filled')
# JS点击确定
confirm_btn = driver.find_element(By.XPATH, "//div[contains(@class,'el-dialog')]//button[contains(.,'确定')]")
driver.execute_script("arguments[0].click();", confirm_btn)
log("已点击确定(JavaScript)")
time.sleep(5)
screenshot(driver, 'step3_after_dialog')
# ===== 查找文件上传元素 =====
log("【查找】扫描页面所有input元素...")
# 方法1: 查找所有input(包括隐藏的)
all_inputs = driver.find_elements(By.XPATH, "//input")
for i, inp in enumerate(all_inputs):
itype = inp.get_attribute('type')
iplaceholder = inp.get_attribute('placeholder')
idisplayed = inp.is_displayed()
log(f" input[{i}]: type={itype}, placeholder={iplaceholder}, visible={idisplayed}")
# 方法2: 查找file input
file_inputs = driver.find_elements(By.XPATH, "//input[@type='file']")
log(f"找到 {len(file_inputs)} 个file input")
if file_inputs:
# 直接发送文件路径
file_inputs[0].send_keys(LICENSE_FILE)
log(f"✅ 已上传授权文件: {LICENSE_FILE}")
time.sleep(5)
screenshot(driver, 'step4_upload_done')
else:
# 方法3: 查找上传区域/拖拽区域
log("尝试查找上传组件...")
upload_areas = driver.find_elements(By.XPATH,
"//*[contains(@class,'upload') or contains(@class,'Upload') or contains(@class,'el-upload')]")
log(f"找到 {len(upload_areas)} 个上传区域组件")
for i, area in enumerate(upload_areas):
tag = area.tag_name
cls = area.get_attribute('class')
log(f" upload[{i}]: tag={tag}, class={cls}")
# 在上传区域内查找隐藏的file input
inner_inputs = area.find_elements(By.XPATH, ".//input[@type='file']")
if inner_inputs:
inner_inputs[0].send_keys(LICENSE_FILE)
log(f"✅ 通过上传区域上传授权文件")
time.sleep(5)
screenshot(driver, 'step4_upload_via_area')
break
else:
# 方法4: 用JS直接找所有input[type=file]包括隐藏的
log("尝试JS查找隐藏file input...")
js_result = driver.execute_script("""
var inputs = document.querySelectorAll('input[type="file"]');
return inputs.length;
""")
log(f"JS找到 {js_result} 个file input")
if js_result > 0:
driver.execute_script(f"""
var input = document.querySelector('input[type="file"]');
input.style.display = 'block';
input.style.visibility = 'visible';
""")
time.sleep(1)
fi = driver.find_element(By.XPATH, "//input[@type='file']")
fi.send_keys(LICENSE_FILE)
log(f"✅ 通过JS显示隐藏input后上传")
time.sleep(5)
screenshot(driver, 'step4_upload_via_js')
else:
log("❌ 未找到任何文件上传元素", "ERROR")
# 打印页面源码片段帮助调试
page_src = driver.page_source
log(f"页面源码长度: {len(page_src)}")
# 搜索upload相关
import re
uploads = re.findall(r'(upload|Upload|file|File)[^<]{0,100}', page_src, re.IGNORECASE)
for u in uploads[:10]:
log(f" match: {u[:80]}")
# 等待上传处理
time.sleep(10)
screenshot(driver, 'step5_final')
log("操作完成")
return 0
except Exception as e:
log(f"异常: {e}", "ERROR")
traceback.print_exc()
screenshot(driver, 'error')
return 1
finally:
driver.quit()
log("浏览器已关闭")
if __name__ == '__main__':
sys.exit(main())
#!/usr/bin/env python3
# -*- coding: utf-8 -*-
"""
直接驱动维护平台完成授权(严格按skill阶段6文档流程):
登录 → 下载激活文件 → 上传license.zip → 读取授权状态 → 重启服务 → 验证。
全程截图,并读取平台显示的授权状态(生效/绑定信息)。
"""
import sys, os, time, json, warnings
from datetime import datetime
if sys.platform=='win32':
try: sys.stdout.reconfigure(encoding='utf-8', errors='replace')
except: pass
warnings.filterwarnings('ignore')
from selenium import webdriver
from selenium.webdriver.chrome.options import Options
from selenium.webdriver.common.by import By
from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC
import requests; requests.packages.urllib3.disable_warnings()
BASE='https://192.168.9.76'
LICENSE_FILE=r'E:\自动化部署\ARM-9.76\license.zip'
REPORTS=os.path.join(os.path.dirname(os.path.abspath(__file__)),'reports')
os.makedirs(REPORTS,exist_ok=True)
def log(m,lvl="INFO"): print(f"[{datetime.now().strftime('%H:%M:%S')}] [{lvl}] {m}",flush=True)
def shot(d,n): d.save_screenshot(os.path.join(REPORTS,f'{n}.png'))
def page_text(d,n=2000): return d.execute_script('return document.body.innerText.substring(0,arguments[0]);',n)
def wait_identity(d, timeout=12):
"""等待'校验身份'对话框出现,返回是否出现。"""
end=time.time()+timeout
while time.time()<end:
found=d.execute_script("""
var dl=document.querySelectorAll('.el-dialog');
for(var i=0;i<dl.length;i++){
if(dl[i].offsetParent===null)continue;
if((dl[i].textContent||'').indexOf('校验身份')>=0)return true;
}
return false;
""")
if found: return True
time.sleep(0.5)
return False
def fill_identity(d):
"""处理'校验身份'对话框:密码+图形验证码+确定。"""
if not wait_identity(d,12):
return False
time.sleep(1)
d.execute_script("""
var dl=document.querySelectorAll('.el-dialog');
for(var i=0;i<dl.length;i++){
if(dl[i].offsetParent===null)continue;
if((dl[i].textContent||'').indexOf('校验身份')<0)continue;
var pwd=dl[i].querySelector('input[placeholder*="密码"]');
if(pwd){pwd.focus();pwd.value='Ubains@1357';pwd.dispatchEvent(new Event('input',{bubbles:true}));pwd.dispatchEvent(new Event('change',{bubbles:true}));}
var cap=dl[i].querySelector('input[placeholder*="验证码"]');
if(cap){cap.focus();cap.value='csba';cap.dispatchEvent(new Event('input',{bubbles:true}));cap.dispatchEvent(new Event('change',{bubbles:true}));}
var bs=dl[i].querySelectorAll('button');
for(var j=0;j<bs.length;j++){if(bs[j].textContent.indexOf('确定')>=0){bs[j].click();break;}}
}
""")
time.sleep(3)
def login(d):
for attempt in range(3):
log(f"登录尝试#{attempt+1}")
d.get(f'{BASE}/#/LoginConfig')
WebDriverWait(d,30).until(EC.presence_of_element_located((By.TAG_NAME,"button")))
time.sleep(4)
d.execute_script("""
var ins=document.querySelectorAll('input');
for(var i=0;i<ins.length;i++){
var p=ins[i].placeholder||'';
if(p.indexOf('账号')>=0||p.indexOf('手机')>=0){ins[i].value='superadmin';ins[i].dispatchEvent(new Event('input',{bubbles:true}));}
else if(p.indexOf('密码')>=0){ins[i].value='Ubains@1357';ins[i].dispatchEvent(new Event('input',{bubbles:true}));}
else if(p.indexOf('验证码')>=0){ins[i].value='csba';ins[i].dispatchEvent(new Event('input',{bubbles:true}));}
}
""")
time.sleep(2)
d.execute_script("var s=document.querySelector('input[type=submit]');if(s)s.click();")
for _ in range(30):
time.sleep(2)
if any(x in d.current_url for x in ['backstage','ServiceAuthorization','backend']):
log(f"✅ 登录成功 {d.current_url}"); return True
log("登录未跳转,重试")
return False
def click_text(d, txt, timeout=10):
"""点击文本匹配的可见元素,返回是否点中。"""
return d.execute_script("""
var nodes=document.querySelectorAll('button,span,a,.el-menu-item,[role=button]');
var t=arguments[0];
for(var i=0;i<nodes.length;i++){
if(nodes[i].offsetParent===null)continue;
if((nodes[i].textContent||'').trim().indexOf(t)>=0){nodes[i].click();return true;}
}
return false;
""", txt)
def main():
opts=Options()
opts.add_argument('--ignore-certificate-errors')
opts.add_argument('--ignore-ssl-errors=yes')
opts.add_argument('--disable-dev-shm-usage')
opts.add_argument('--window-size=1920,1080')
d=webdriver.Chrome(options=opts); d.implicitly_wait(8)
try:
if not login(d): log("❌登录失败","ERROR"); return 1
shot(d,'auth_login_ok')
# 进入授权页
log("进入服务授权页...")
# 尝试多种入口
for ent in ['服务授权','授权管理','系统授权']:
if click_text(d,ent): log(f"点击入口: {ent}"); break
time.sleep(4); shot(d,'auth_page_initial')
log("=== 当前授权状态(页面文本) ===")
log(page_text(d,1500))
# 下载激活文件(文档步骤3)
log("点击[下载激活文件]...")
if click_text(d,'下载激活文件'):
time.sleep(2); fill_identity(d); time.sleep(3); log("下载激活文件流程完成")
shot(d,'auth_after_download_activation')
else:
log("未找到'下载激活文件'按钮,跳过")
# 上传授权文件(文档步骤4)
log("点击[上传授权文件]...")
click_text(d,'上传授权文件')
# 点击后会弹'校验身份',验证后才出文件选择框
if fill_identity(d):
log("校验身份已通过,等待文件选择框...")
else:
log("未出现校验身份对话框(可能已验证或直接出文件框)")
time.sleep(2)
# 轮询等待 file input 出现
fi_info='NOT_FOUND'
for _ in range(20):
fi_info=d.execute_script("""
var ins=document.querySelectorAll('input[type=file]');
return ins.length>0?'FOUND:'+ins.length:'NOT_FOUND';
""")
if 'FOUND' in fi_info: break
time.sleep(1)
log(f"file input: {fi_info}")
if 'FOUND' in fi_info:
d.find_element(By.XPATH,"//input[@type='file']").send_keys(LICENSE_FILE)
log("已选择license.zip,等待上传处理...")
time.sleep(10)
# 上传后可能再弹一次校验身份
if wait_identity(d,5): fill_identity(d)
time.sleep(5)
shot(d,'auth_after_upload')
log("=== 上传后授权状态(页面文本) ===")
log(page_text(d,1500))
else:
log("无file input(身份校验可能未通过或UI变化)","WARN")
shot(d,'auth_no_fileinput')
log(f"页面文本: {page_text(d,1000)}")
# 重启服务(文档步骤6)
log("进入服务升级重启...")
for ent in ['服务升级','服务管理']:
if click_text(d,ent): log(f"点击: {ent}"); break
time.sleep(4); shot(d,'auth_service_upgrade')
# 勾选运维/预定
chk=d.execute_script("""
var cbs=document.querySelectorAll('.el-checkbox');
var sel=[];
cbs.forEach(function(cb){
var t=cb.textContent||'';
if(t.indexOf('运维')>=0||t.indexOf('预定')>=0){
if(!cb.classList.contains('is-checked'))cb.click();
sel.push(t.trim());
}
});
return JSON.stringify(sel);
""")
log(f"勾选服务: {chk}")
time.sleep(2)
shot(d,'auth_before_restart')
log("授权流程UI部分完成。将通过SSH重启容器确保生效。")
return 0
except Exception as e:
log(f"异常: {e}","ERROR"); import traceback; traceback.print_exc(); shot(d,'auth_error'); return 1
finally:
shot(d,'auth_final'); d.quit(); log("浏览器关闭")
if __name__=='__main__':
sys.exit(main())
#!/usr/bin/env python3
# -*- coding: utf-8 -*-
"""
ARM Ubuntu 系统授权自动化脚本
使用Selenium自动化Web界面操作
根据PRD文档步骤:
1. 访问维护平台 https://192.168.9.76/#/LoginConfig
2. 登录超管账号: superadmin / Ubains@1357
3. 验证码: csba
4. 下载激活文件
5. 上传授权文件: E:\自动化部署\ARM-9.76\license.zip
6. 重启服务(运维系统、预定系统2.0)
7. 等待10分钟
"""
import sys
import time
import os
from datetime import datetime
from selenium import webdriver
from selenium.webdriver.common.by import By
from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC
from selenium.webdriver.chrome.options import Options
from selenium.webdriver.chrome.service import Service
if sys.platform == 'win32':
try:
sys.stdout.reconfigure(encoding='utf-8', errors='replace')
except:
pass
# 配置
MAINTAIN_URL = "https://192.168.9.76/#/LoginConfig"
ADMIN_USER = "superadmin"
ADMIN_PASS = "Ubains@1357"
CAPTCHA = "csba"
LICENSE_PATH = r"E:\自动化部署\ARM-9.76\license.zip"
def log(msg, level="INFO"):
ts = datetime.now().strftime('%H:%M:%S')
print(f"[{ts}] [{level}] {msg}", flush=True)
def main():
log("=" * 60)
log("ARM Ubuntu 系统授权自动化")
log("=" * 60)
# 检查授权文件是否存在
if not os.path.exists(LICENSE_PATH):
log(f"授权文件不存在: {LICENSE_PATH}", "ERROR")
log("请确保授权文件已准备好,或手动完成授权操作", "ERROR")
return 1
log(f"授权文件: {LICENSE_PATH}")
# 配置Chrome选项
chrome_options = Options()
chrome_options.add_argument('--ignore-certificate-errors')
chrome_options.add_argument('--ignore-ssl-errors')
chrome_options.add_argument('--disable-web-security')
chrome_options.add_argument('--allow-running-insecure-content')
# chrome_options.add_argument('--headless') # 取消注释可无头运行
log("\n[步骤1] 启动Chrome浏览器...")
try:
driver = webdriver.Chrome(options=chrome_options)
driver.set_page_load_timeout(60)
log("Chrome浏览器启动成功")
except Exception as e:
log(f"Chrome浏览器启动失败: {e}", "ERROR")
log("请确保已安装ChromeDriver并添加到PATH", "ERROR")
log("或手动完成授权操作,详见下方指引", "WARN")
print_manual_guide()
return 1
try:
# 步骤2: 访问维护平台
log("\n[步骤2] 访问维护平台...")
driver.get(MAINTAIN_URL)
time.sleep(3)
log(f"当前URL: {driver.current_url}")
# 步骤3: 登录
log("\n[步骤3] 登录维护平台...")
wait = WebDriverWait(driver, 30)
# 输入用户名
username_input = wait.until(EC.presence_of_element_located((By.CSS_SELECTOR, "input[placeholder*='用户名'], input[type='text'], input[name='username']")))
username_input.clear()
username_input.send_keys(ADMIN_USER)
log(f" 用户名: {ADMIN_USER}")
# 输入密码
password_input = driver.find_element(By.CSS_SELECTOR, "input[placeholder*='密码'], input[type='password'], input[name='password']")
password_input.clear()
password_input.send_keys(ADMIN_PASS)
log(f" 密码: {'*' * len(ADMIN_PASS)}")
# 输入验证码
captcha_input = driver.find_element(By.CSS_SELECTOR, "input[placeholder*='验证码'], input[name='captcha'], input[name='code']")
captcha_input.clear()
captcha_input.send_keys(CAPTCHA)
log(f" 验证码: {CAPTCHA}")
# 点击登录按钮
login_btn = driver.find_element(By.CSS_SELECTOR, "button[type='submit'], button:contains('登录'), .login-btn")
login_btn.click()
log(" 点击登录按钮")
time.sleep(5)
log(f"登录后URL: {driver.current_url}")
# 步骤4: 上传授权文件
log("\n[步骤4] 上传授权文件...")
# 查找"上传授权文件"按钮或链接
try:
upload_btn = wait.until(EC.element_to_be_clickable((By.XPATH, "//button[contains(text(), '上传授权') or contains(text(), '授权文件')] | //a[contains(text(), '上传授权')]")))
upload_btn.click()
log(" 点击上传授权文件按钮")
time.sleep(2)
# 处理可能弹出的身份验证对话框
# 输入密码
try:
auth_password = driver.find_element(By.CSS_SELECTOR, "input[type='password']")
auth_password.send_keys(ADMIN_PASS)
auth_captcha = driver.find_element(By.CSS_SELECTOR, "input[placeholder*='验证码']")
auth_captcha.send_keys(CAPTCHA)
auth_confirm = driver.find_element(By.CSS_SELECTOR, "button:contains('确定'), button[type='submit']")
auth_confirm.click()
time.sleep(2)
except:
pass
# 上传文件
file_input = driver.find_element(By.CSS_SELECTOR, "input[type='file']")
file_input.send_keys(LICENSE_PATH)
log(f" 选择文件: {LICENSE_PATH}")
time.sleep(3)
# 确认上传
confirm_btn = driver.find_element(By.CSS_SELECTOR, "button:contains('确定'), button:contains('上传'), button[type='submit']")
confirm_btn.click()
log(" 确认上传")
time.sleep(5)
log(" 授权文件上传完成")
except Exception as e:
log(f" 上传授权文件失败: {e}", "ERROR")
log(" 请手动完成上传操作", "WARN")
# 步骤5: 重启服务
log("\n[步骤5] 重启服务...")
# 导航到"服务升级"界面
try:
service_menu = driver.find_element(By.XPATH, "//a[contains(text(), '服务升级') or contains(text(), '服务管理')]")
service_menu.click()
time.sleep(2)
# 勾选"运维系统"和"预定系统2.0"
# 查找复选框并勾选
checkboxes = driver.find_elements(By.CSS_SELECTOR, "input[type='checkbox']")
for checkbox in checkboxes:
label = checkbox.find_element(By.XPATH, "..").text
if "运维系统" in label or "预定系统2.0" in label:
if not checkbox.is_selected():
checkbox.click()
log(f" 勾选: {label}")
# 点击"重启已选服务"按钮
restart_btn = driver.find_element(By.XPATH, "//button[contains(text(), '重启已选服务') or contains(text(), '重启服务')]")
restart_btn.click()
log(" 点击重启服务按钮")
time.sleep(2)
# 输入超管账号密码确认
try:
confirm_user = driver.find_element(By.CSS_SELECTOR, "input[placeholder*='用户名'], input[name='username']")
confirm_user.send_keys(ADMIN_USER)
confirm_pass = driver.find_element(By.CSS_SELECTOR, "input[type='password']")
confirm_pass.send_keys(ADMIN_PASS)
confirm_captcha = driver.find_element(By.CSS_SELECTOR, "input[placeholder*='验证码']")
confirm_captcha.send_keys(CAPTCHA)
final_confirm = driver.find_element(By.CSS_SELECTOR, "button:contains('确定'), button[type='submit']")
final_confirm.click()
log(" 确认重启")
except:
log(" 未弹出确认对话框,可能直接重启")
time.sleep(5)
log(" 服务重启命令已执行")
except Exception as e:
log(f" 重启服务失败: {e}", "ERROR")
log(" 请手动完成服务重启", "WARN")
# 步骤6: 等待10分钟
log("\n[步骤6] 等待10分钟让服务完全启动...")
for i in range(10, 0, -1):
log(f" 剩余等待: {i}分钟")
time.sleep(60)
log(" 等待完成")
log("\n" + "=" * 60)
log("系统授权完成!")
log("=" * 60)
except Exception as e:
log(f"自动化操作失败: {e}", "ERROR")
log("请手动完成授权操作", "WARN")
print_manual_guide()
finally:
driver.quit()
return 0
def print_manual_guide():
"""打印手动操作指引"""
print("\n" + "=" * 60)
print("手动授权操作指引")
print("=" * 60)
print(f"""
1. 打开浏览器,访问: https://192.168.9.76/#/LoginConfig
2. 登录维护平台:
- 用户名: superadmin
- 密码: Ubains@1357
- 验证码: csba
3. 上传授权文件:
- 点击"上传授权文件"按钮
- 选择文件: {LICENSE_PATH}
- 如弹出身份验证对话框,输入密码和验证码
- 确认上传
4. 重启服务:
- 进入"服务升级"界面
- 勾选"运维系统"和"预定系统2.0"
- 点击【重启已选服务】按钮
- 输入超管账号密码确认
5. 等待约10分钟让服务完全启动
6. 验证服务:
- 访问 https://192.168.9.76/
- 测试各系统功能
""")
if __name__ == '__main__':
sys.exit(main())
\ No newline at end of file
#!/usr/bin/env python3
# -*- coding: utf-8 -*-
"""
ARM Ubuntu 系统授权自动化脚本 V2
修复CSS选择器问题
"""
import sys
import time
import os
from datetime import datetime
from selenium import webdriver
from selenium.webdriver.common.by import By
from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC
from selenium.webdriver.chrome.options import Options
if sys.platform == 'win32':
try:
sys.stdout.reconfigure(encoding='utf-8', errors='replace')
except:
pass
MAINTAIN_URL = "https://192.168.9.76/#/LoginConfig"
ADMIN_USER = "superadmin"
ADMIN_PASS = "Ubains@1357"
CAPTCHA = "csba"
LICENSE_PATH = r"E:\自动化部署\ARM-9.76\license.zip"
def log(msg, level="INFO"):
ts = datetime.now().strftime('%H:%M:%S')
print(f"[{ts}] [{level}] {msg}", flush=True)
def main():
log("=" * 60)
log("ARM Ubuntu 系统授权自动化 V2")
log("=" * 60)
if not os.path.exists(LICENSE_PATH):
log(f"授权文件不存在: {LICENSE_PATH}", "ERROR")
return 1
chrome_options = Options()
chrome_options.add_argument('--ignore-certificate-errors')
chrome_options.add_argument('--ignore-ssl-errors')
chrome_options.add_argument('--disable-web-security')
chrome_options.add_argument('--allow-running-insecure-content')
log("\n[步骤1] 启动Chrome浏览器...")
driver = webdriver.Chrome(options=chrome_options)
driver.set_page_load_timeout(60)
log("Chrome浏览器启动成功")
try:
log("\n[步骤2] 访问维护平台...")
driver.get(MAINTAIN_URL)
time.sleep(5)
log(f"当前URL: {driver.current_url}")
log(f"页面标题: {driver.title}")
# 截图保存
driver.save_screenshot("E:/GithubData/ubains-module-test/AuxiliaryTool/ScriptTool/RemoteDeploy/reports/login_page.png")
log("已保存登录页面截图")
log("\n[步骤3] 登录维护平台...")
wait = WebDriverWait(driver, 30)
# 尝试多种方式定位元素
# 方式1: 通过input标签
inputs = driver.find_elements(By.TAG_NAME, "input")
log(f"找到 {len(inputs)} 个input元素")
for inp in inputs:
inp_type = inp.get_attribute("type")
inp_placeholder = inp.get_attribute("placeholder")
inp_name = inp.get_attribute("name")
log(f" input: type={inp_type}, placeholder={inp_placeholder}, name={inp_name}")
# 用户名输入框
username_found = False
for inp in inputs:
inp_type = inp.get_attribute("type") or ""
inp_placeholder = (inp.get_attribute("placeholder") or "").lower()
inp_name = (inp.get_attribute("name") or "").lower()
if "text" in inp_type or "用户名" in inp_placeholder or "username" in inp_name or "账号" in inp_placeholder:
inp.clear()
inp.send_keys(ADMIN_USER)
log(f" 用户名已输入: {ADMIN_USER}")
username_found = True
break
if not username_found:
log(" 未找到用户名输入框,尝试第一个text类型input")
for inp in inputs:
if inp.get_attribute("type") == "text":
inp.clear()
inp.send_keys(ADMIN_USER)
log(f" 用户名已输入(第一个text input)")
break
# 密码输入框
for inp in inputs:
if inp.get_attribute("type") == "password":
inp.clear()
inp.send_keys(ADMIN_PASS)
log(f" 密码已输入")
break
# 验证码输入框
for inp in inputs:
inp_placeholder = (inp.get_attribute("placeholder") or "").lower()
if "验证码" in inp_placeholder or "code" in (inp.get_attribute("name") or "").lower():
inp.clear()
inp.send_keys(CAPTCHA)
log(f" 验证码已输入: {CAPTCHA}")
break
# 截图
driver.save_screenshot("E:/GithubData/ubains-module-test/AuxiliaryTool/ScriptTool/RemoteDeploy/reports/before_login.png")
log("已保存填写后截图")
# 查找登录按钮
buttons = driver.find_elements(By.TAG_NAME, "button")
log(f"找到 {len(buttons)} 个button元素")
login_clicked = False
for btn in buttons:
btn_text = btn.text
btn_type = btn.get_attribute("type")
log(f" button: text={btn_text}, type={btn_type}")
if "登录" in btn_text or btn_type == "submit":
btn.click()
log(" 点击登录按钮")
login_clicked = True
break
if not login_clicked and buttons:
buttons[0].click()
log(" 点击第一个按钮")
time.sleep(5)
log(f"登录后URL: {driver.current_url}")
# 截图
driver.save_screenshot("E:/GithubData/ubains-module-test/AuxiliaryTool/ScriptTool/RemoteDeploy/reports/after_login.png")
log("已保存登录后截图")
# 步骤4: 查找授权相关元素
log("\n[步骤4] 查找授权管理页面...")
# 获取页面源码
page_source = driver.page_source
with open("E:/GithubData/ubains-module-test/AuxiliaryTool/ScriptTool/RemoteDeploy/reports/page_source.html", "w", encoding="utf-8") as f:
f.write(page_source)
log("已保存页面源码")
# 查找包含"授权"文字的元素
elements_with_auth = []
all_elements = driver.find_elements(By.XPATH, "//*[contains(text(), '授权') or contains(text(), 'license')]")
log(f"找到 {len(all_elements)} 个包含'授权'的元素")
for elem in all_elements[:10]:
try:
log(f" 元素: tag={elem.tag_name}, text={elem.text[:50]}")
except:
pass
# 尝试查找文件上传input
file_inputs = driver.find_elements(By.XPATH, "//input[@type='file']")
log(f"找到 {len(file_inputs)} 个文件上传input")
if file_inputs:
log("\n[步骤5] 直接上传授权文件...")
file_inputs[0].send_keys(LICENSE_PATH)
log(f" 已上传: {LICENSE_PATH}")
time.sleep(3)
driver.save_screenshot("E:/GithubData/ubains-module-test/AuxiliaryTool/ScriptTool/RemoteDeploy/reports/after_upload.png")
log("已保存上传后截图")
else:
log("未找到文件上传input,可能需要先导航到授权页面", "WARN")
log("\n请在浏览器中手动完成剩余操作(如果需要)")
log("浏览器将保持打开30秒...")
time.sleep(30)
except Exception as e:
log(f"自动化操作异常: {e}", "ERROR")
import traceback
traceback.print_exc()
driver.save_screenshot("E:/GithubData/ubains-module-test/AuxiliaryTool/ScriptTool/RemoteDeploy/reports/error_screenshot.png")
finally:
driver.quit()
log("浏览器已关闭")
return 0
if __name__ == '__main__':
sys.exit(main())
\ No newline at end of file
#!/usr/bin/env python3
# -*- coding: utf-8 -*-
"""
ARM Ubuntu 系统授权自动化脚本 V3
使用JavaScript点击登录按钮
"""
import sys
import time
import os
from datetime import datetime
from selenium import webdriver
from selenium.webdriver.common.by import By
from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC
from selenium.webdriver.chrome.options import Options
if sys.platform == 'win32':
try:
sys.stdout.reconfigure(encoding='utf-8', errors='replace')
except:
pass
MAINTAIN_URL = "https://192.168.9.76/#/LoginConfig"
ADMIN_USER = "superadmin"
ADMIN_PASS = "Ubains@1357"
CAPTCHA = "csba"
LICENSE_PATH = r"E:\自动化部署\ARM-9.76\license.zip"
REPORTS_DIR = r"E:\GithubData\ubains-module-test\AuxiliaryTool\ScriptTool\RemoteDeploy\reports"
def log(msg, level="INFO"):
ts = datetime.now().strftime('%H:%M:%S')
print(f"[{ts}] [{level}] {msg}", flush=True)
def main():
log("=" * 60)
log("ARM Ubuntu 系统授权自动化 V3")
log("=" * 60)
if not os.path.exists(LICENSE_PATH):
log(f"授权文件不存在: {LICENSE_PATH}", "ERROR")
return 1
chrome_options = Options()
chrome_options.add_argument('--ignore-certificate-errors')
chrome_options.add_argument('--ignore-ssl-errors')
chrome_options.add_argument('--disable-web-security')
chrome_options.add_argument('--allow-running-insecure-content')
# chrome_options.add_argument('--headless') # 取消注释可无头运行
log("\n[步骤1] 启动Chrome浏览器...")
driver = webdriver.Chrome(options=chrome_options)
driver.set_page_load_timeout(60)
driver.implicitly_wait(10)
log("Chrome浏览器启动成功")
try:
log("\n[步骤2] 访问维护平台...")
driver.get(MAINTAIN_URL)
time.sleep(5)
log(f"当前URL: {driver.current_url}")
driver.save_screenshot(f"{REPORTS_DIR}/01_login_page.png")
log("\n[步骤3] 填写登录信息...")
inputs = driver.find_elements(By.TAG_NAME, "input")
log(f"找到 {len(inputs)} 个input元素")
# 用户名
for inp in inputs:
inp_type = inp.get_attribute("type") or ""
inp_placeholder = (inp.get_attribute("placeholder") or "").lower()
if "text" in inp_type and ("账号" in inp_placeholder or "手机" in inp_placeholder or "邮箱" in inp_placeholder):
inp.clear()
inp.send_keys(ADMIN_USER)
log(f" 用户名: {ADMIN_USER}")
break
# 密码
for inp in inputs:
if inp.get_attribute("type") == "password":
inp.clear()
inp.send_keys(ADMIN_PASS)
log(f" 密码: {'*' * len(ADMIN_PASS)}")
break
# 验证码
for inp in inputs:
inp_placeholder = (inp.get_attribute("placeholder") or "").lower()
if "验证码" in inp_placeholder:
inp.clear()
inp.send_keys(CAPTCHA)
log(f" 验证码: {CAPTCHA}")
break
driver.save_screenshot(f"{REPORTS_DIR}/02_filled.png")
# 使用JavaScript点击登录
log("\n[步骤4] 执行登录...")
# 方式1: 查找type=submit的input
login_script = """
// 查找登录按钮
var inputs = document.getElementsByTagName('input');
for (var i = 0; i < inputs.length; i++) {
if (inputs[i].type === 'submit') {
inputs[i].click();
return 'clicked input submit';
}
}
// 查找button
var buttons = document.getElementsByTagName('button');
for (var i = 0; i < buttons.length; i++) {
if (buttons[i].type === 'submit' || buttons[i].innerText.includes('登录')) {
buttons[i].click();
return 'clicked button';
}
}
// 查找包含登录文字的元素
var all = document.querySelectorAll('*');
for (var i = 0; i < all.length; i++) {
if (all[i].innerText === '登录' || all[i].innerText === '登 录') {
all[i].click();
return 'clicked text element';
}
}
return 'not found';
"""
result = driver.execute_script(login_script)
log(f" JavaScript执行结果: {result}")
time.sleep(5)
log(f"登录后URL: {driver.current_url}")
driver.save_screenshot(f"{REPORTS_DIR}/03_after_login.png")
# 检查是否登录成功
if "LoginConfig" not in driver.current_url:
log("登录成功!")
else:
log("可能仍在登录页,检查页面内容...", "WARN")
# 步骤5: 查找授权上传功能
log("\n[步骤5] 查找授权上传功能...")
time.sleep(3)
# 保存页面源码
with open(f"{REPORTS_DIR}/page_after_login.html", "w", encoding="utf-8") as f:
f.write(driver.page_source)
log("已保存页面源码")
# 查找文件上传input
file_inputs = driver.find_elements(By.XPATH, "//input[@type='file']")
log(f"找到 {len(file_inputs)} 个文件上传input")
if file_inputs:
log("\n[步骤6] 上传授权文件...")
file_inputs[0].send_keys(LICENSE_PATH)
log(f" 已上传: {LICENSE_PATH}")
time.sleep(5)
driver.save_screenshot(f"{REPORTS_DIR}/04_after_upload.png")
# 查找确认按钮
confirm_script = """
var buttons = document.getElementsByTagName('button');
for (var i = 0; i < buttons.length; i++) {
var text = buttons[i].innerText;
if (text.includes('确定') || text.includes('上传') || text.includes('确认')) {
buttons[i].click();
return text;
}
}
return 'no confirm button';
"""
result = driver.execute_script(confirm_script)
log(f" 确认按钮: {result}")
time.sleep(3)
driver.save_screenshot(f"{REPORTS_DIR}/05_after_confirm.png")
else:
log("未找到文件上传input,尝试查找授权菜单...", "WARN")
# 查找包含"授权"的元素
auth_elements = driver.find_elements(By.XPATH, "//*[contains(text(), '授权')]")
log(f"找到 {len(auth_elements)} 个包含'授权'的元素")
for elem in auth_elements[:5]:
try:
log(f" {elem.tag_name}: {elem.text[:30]}")
except:
pass
# 尝试点击授权相关元素
for elem in auth_elements:
try:
if "上传" in elem.text or "授权文件" in elem.text:
elem.click()
log(f" 点击: {elem.text}")
time.sleep(2)
break
except:
continue
log("\n[步骤7] 等待用户确认操作...")
log("浏览器将保持打开60秒,请手动完成剩余操作...")
driver.save_screenshot(f"{REPORTS_DIR}/06_final.png")
time.sleep(60)
except Exception as e:
log(f"自动化操作异常: {e}", "ERROR")
import traceback
traceback.print_exc()
driver.save_screenshot(f"{REPORTS_DIR}/error.png")
finally:
driver.quit()
log("浏览器已关闭")
return 0
if __name__ == '__main__':
sys.exit(main())
\ No newline at end of file
#!/usr/bin/env python3
"""权限组绑定 - 选择角色 + 保存"""
import sys, time
from selenium import webdriver
from selenium.webdriver.chrome.options import Options
from selenium.webdriver.common.by import By
sys.stdout.reconfigure(encoding='utf-8', errors='replace')
opts = Options()
opts.add_argument('--ignore-certificate-errors')
opts.add_argument('--ignore-ssl-errors')
opts.add_argument('--window-size=1920,1080')
d = webdriver.Chrome(options=opts)
d.implicitly_wait(10)
try:
d.get('https://192.168.9.76/#/LoginAdmin'); time.sleep(10)
for retry in range(3):
for inp in d.find_elements(By.TAG_NAME, 'input'):
if not inp.is_displayed(): continue
p = inp.get_attribute('placeholder') or ''; t = inp.get_attribute('type') or ''
if '账号' in p: inp.clear(); inp.send_keys('admin')
elif t == 'password': inp.clear(); inp.send_keys('Admin@2024ub')
elif '验证码' in p: inp.clear(); inp.send_keys('csba')
time.sleep(3)
for inp in d.find_elements(By.XPATH, '//input[@type="submit"]'):
if inp.is_displayed(): inp.click(); break
time.sleep(10)
if 'LoginAdmin' not in d.current_url: break
d.refresh(); time.sleep(5)
print('1. Login OK')
# 导航到权限管理
d.execute_script('var items=document.querySelectorAll("span");for(var i=0;i<items.length;i++){if(items[i].textContent.trim()==="系统管理"&&items[i].offsetParent!==null){items[i].click();break;}}'); time.sleep(2)
d.execute_script('var items=document.querySelectorAll(".el-menu-item,span");for(var i=0;i<items.length;i++){if(items[i].textContent.trim()==="权限管理"&&items[i].offsetParent!==null){items[i].click();break;}}'); time.sleep(3)
# 点击绑定
d.execute_script('var all=document.querySelectorAll("*");for(var i=0;i<all.length;i++){if(all[i].textContent.trim()==="绑定"&&all[i].offsetParent!==null){all[i].click();break;}}'); time.sleep(3)
print('2. 绑定界面')
# 点击"选择角色"输入框
d.execute_script('''
var inputs = document.querySelectorAll("input");
for (var i = 0; i < inputs.length; i++) {
if (inputs[i].placeholder && inputs[i].placeholder.indexOf("选择角色") >= 0 && inputs[i].offsetParent !== null) {
inputs[i].click(); break;
}
}
''')
time.sleep(2)
print('3. Clicked 选择角色')
# 从下拉菜单选择"公司管理员"
d.execute_script('''
var items = document.querySelectorAll(".el-select-dropdown__item, li, span");
for (var i = 0; i < items.length; i++) {
if (items[i].textContent.trim() === "公司管理员" && items[i].offsetParent !== null) {
items[i].click(); break;
}
}
''')
time.sleep(2)
print('4. Selected 公司管理员')
# 点击保存
d.execute_script('''
var btns = document.querySelectorAll("button");
for (var i = 0; i < btns.length; i++) {
if (btns[i].textContent.trim() === "保存" && btns[i].offsetParent !== null) {
btns[i].click(); break;
}
}
''')
time.sleep(3)
print('5. Clicked 保存')
body = d.execute_script('return document.body.innerText.substring(0, 300);')
print('6. ' + body[:150].replace(chr(10), ' '))
time.sleep(600)
finally:
d.quit()
\ No newline at end of file
"data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAMgAAABFCAYAAAAPdqmYAAAAAXNSR0IArs4c6QAAB9lJREFUeF7tnGuIVkUYx99tizYqoTbDqDZEsQ26oF22JYuoMCwMP0Q3tg9uwkZBBpFW7MelUgg0CFqy9UNSFH2QhCSpiDJMLKULZKJJS5FkFkjRQm1vzLzNcjw758w8zzxzPXM+Lbwz81x/73/mnPNuV7vdbrfylTOQaAYWrt7AIzu0eS0qwq4MCCpveVIkGciARFKoJrp5/+u7edhvPDAYbfheFGR8/XutkXW3R5u0Jjl+zycf8HDfuvFWcNi6gHzY/SBf+5bp18A2bE9wDkiGw3ZJadc3AUTXkwzI/5kKGY5fznyKe3n+n8/r1jWPa0AGnClIyHCwOmdAGtDtiBCdABI6HIi8JTHl+ifu5nF89sLbScRjIwirgDAw2JUP5DZKZ75mBkSdQ2uAZNVQJz+PCD8DVgCJAY75A9taR/asDL9C2UOvGSAHJHQ4GBjiyoB47b0ojJMCEjIcRTCKlWkSJP/8Np+Hfuq5R6JozhCcJAMkVDiqwEhdRQQM5SbLcMCwIwMEZtb+aBUYqatIBoSmx2oB6fthB40VxSqTlywns5MqGKzhId/+GRCalgpCQVyBSJOy6lVkoE8MDbSGt+4Bma5qbsj5IQMCSnnl4CAAMQklJMVwAfr3Zz+iVBIXcPQeuJSX7Xj/dyblC35u9ICwDKsg8XWnCqMeomNMVCQDQsdd8oDECIcpJC4AoWvBsFdKAhCViviAxEQ9ii0DVZKU4dh6zpLW0O/7nBKVDCB1kLgGhAoOjJKkCgiDo3i5AsUZIFt2/joT36pl51n5Fqg7i+hAQvV+VgaEvrxlQJgFF5BYB6QIhixtJrDseuZKvuTSZ7+aWRrzSkl5jg5MVS1ADQdURWQKAnl+Qt/a5ivK4BCr2obEGiAqMMppw4ACAYTZKzc+BiZVuW0BwuzWnUcOTT/cWtj9stS9DIiqatWfBwMIcxEDiSw0VeOrbgvLYNJJsU04qpSEgcGu/rnrKgGKGRCf6sHyagUQqHoUm48CEh0AVA2P2Wa5BqRONUR8McPBYmgcIAKAOoh8QgIFY/ChU1q7X/235QIO0fQHjq3nf1ZtqYrwxwyIbzicK4is8atAMYUEqiJQMIpNyOB45fS9HBSblwCjbjtVtp8iILYP5sUcOt1iuQSEBakDiQkYIpFCPYSa2ICEwcHAKF51h3Y2TgbHYxv28yVeXLvYhptka4agHrMUZMHk1zzAw31XGAUqU4UqRbClICpAKMBgNspbKywk87Yf5Tk/umLeSbkvqka5KKkCEgocTgFhxlwrSB0ktgBhNhkk7IJsuWSAyFQDAkms26tgATGSjdJkHRWxfVC3rSKqgzlWTepUQ1ajlF4vCQmOWQpiGxChIjq3gU0P6cVYVM9FsHGrABFqAlESHdXQVZEYFSRpQHQaX6cZKeGwpSI6cIhYdbZcUNUo5jEVBQkNDjIFoQJDFJ0aEMqzyJzlnVu5G3sHwT+llW25TMAQ+YK+Eq/zJeVjTJKAUMJhAwxRaNM3fcU6ApATOzoHcehVhASznaqyF7uKhAiHsYJUwXHGZVt4Hf/6dlVt/9gEQmaY6iwC2V7J/KBQDdvnkKc3TnETzz3eA/0OQI2vAsTlQ0GZ4+gHhXXKIQC57+InuU2bzzog1aBQEQo4xAM/7F0uWczUCuISkFDVw0hBoLdodW77QpodO9ZURbCAVKkGFSTUgGDzC50XMhxWAKnbNoUAiYmKYODQ2U7p3OVSNV4GRJUh3OeoLRZUPYRrIQDCfMH8ghALR/n9qboymapJbJCErh5oBcGeKbDzcOxXzxKAQF43gQCioxpV3plAEtvPbZMFBHvwrgPk4wVjvGduOjxKzQNovcklN/Dxffs+nZkHhQOiGjLnKLZcoKA9DI4BDrSCZEBmd5SJathQE8qeH5v7JV9u9NhVZMsmDwgUEuy5hawiyIV01IPygV/ZTZMtFzLkWdOoAYkFDiMFqQMEWhjXDwwh/tUBMqf3G77UieOXQ5YEj01tyxXqQ0FZYVB3sYoLmb5qEiMcYjt1Xf+dTgAR+Q5BTcB0V0zw9Y/goP4bAyIMYkDxBceins3c7YNTq2vzJVMPqu3U8ORt3PZE3/ugmqUECQtcgOL7lZKqIpABgtlyhQxIGQ7qQzgWEJbn1LZcoG8Ix4M5ICt+vJmb3X7RRyTmVWriCwxIcEVAqFQDYl9nbGpqohOz6zFWAHEdBLU9nTtX1Dax62VIYJk77fPODZW/r+ncYFFdJ22x3p2e4OPv6B5WzUv285jgEEVIbcu1+NFNPLT9L60h77MMiGFKYwSkCIrO7993LbuaT1m68wvDbNmZbhMQqMekh3SocdX4idG7+JDhsXdUQ0k+jxkOCCShA0JSTKJFwIC8ueZnbvreTRcQuVC9TAYEl2KXW65261ruZFdrL87ZwGcFDYjL3KWgHuV8uTjAZ0BcdqlHWykCwtJpG5JFI9t41Q6Or/RYPXumwQpizxV/K6cKR/Fcwv7WOcBDq0ABSM94Fzc7NdKGmrc+PgMi+QfU1rPuyYBtNTENS4ASEiyNByR19TBtWl/zQ4ElAzI0AP4Pib6apql2fcLSaECyesSHnGtYGg1IfO2RPS5mwAUsGZDcc0lkwBYsKEAu/KPz9PSns9J8eppExzQ4CEpYMiANbqQmhG76jAUFSBMSm2PMGWAZyIDkPsgZqMnAf0Qx9m4aRKOBAAAAAElFTkSuQmCC"
\ No newline at end of file
#!/usr/bin/env python3
# -*- coding: utf-8 -*-
"""修改密码 - 只操作弹窗内的输入框"""
import sys, time
from datetime import datetime
from selenium import webdriver
from selenium.webdriver.chrome.options import Options
from selenium.webdriver.common.by import By
from selenium.webdriver.common.keys import Keys
if sys.platform == 'win32':
try: sys.stdout.reconfigure(encoding='utf-8', errors='replace')
except: pass
BASE = 'https://192.168.9.76'
NEW_PWD = "Admin@2024ub"
def log(msg):
print(f"[{datetime.now().strftime('%H:%M:%S')}] {msg}", flush=True)
def main():
log("=" * 60)
log(f"修改密码 - 弹窗内操作 -> {NEW_PWD}")
log("=" * 60)
opts = Options()
opts.add_argument('--ignore-certificate-errors')
opts.add_argument('--ignore-ssl-errors')
opts.add_argument('--window-size=1920,1080')
driver = webdriver.Chrome(options=opts)
driver.implicitly_wait(10)
try:
# 1. 登录
log("=== 登录 ===")
driver.get(f'{BASE}/')
time.sleep(8)
for inp in driver.find_elements(By.TAG_NAME, "input"):
if not inp.is_displayed(): continue
p = inp.get_attribute("placeholder") or ""
t = inp.get_attribute("type") or ""
if "手机" in p or "用户名" in p:
inp.clear(); inp.send_keys("admin")
elif t == "password":
inp.clear(); inp.send_keys("Ubains@1357")
elif "图形" in p:
inp.clear(); inp.send_keys("csba")
time.sleep(2)
for cb in driver.find_elements(By.XPATH, "//input[@type='checkbox']"):
if cb.is_displayed() and not cb.is_selected():
cb.click(); break
time.sleep(2)
for btn in driver.find_elements(By.TAG_NAME, "button"):
if btn.is_displayed() and "登录" in btn.text:
btn.click(); break
time.sleep(5)
# 2. 处理弹窗
log("\n=== 处理弹窗 ===")
for _ in range(20):
body = driver.execute_script("return document.body.innerText.substring(0, 500);")
if "修改密码" in body and "旧密码" in body:
log("✅ 修改密码弹窗出现")
break
if "协议" in body and "确定" in body and "取消" in body:
for btn in driver.find_elements(By.TAG_NAME, "button"):
if btn.is_displayed() and btn.text.strip() == "确定":
driver.execute_script("arguments[0].click();", btn)
log("点击协议确定")
time.sleep(3); break
time.sleep(1)
time.sleep(3)
# 3. 在弹窗内查找输入框
log("\n=== 查找弹窗内输入框 ===")
dialog = driver.execute_script("""
var dialogs = document.querySelectorAll('.el-dialog, [role=dialog], .el-dialog__wrapper');
for (var i = 0; i < dialogs.length; i++) {
if (dialogs[i].offsetParent !== null) {
return dialogs[i];
}
}
return null;
""")
if dialog:
log("✅ 找到弹窗")
# 在弹窗内找输入框
dialog_inputs = dialog.find_elements(By.TAG_NAME, "input")
log(f"弹窗内输入框数量: {len(dialog_inputs)}")
for inp in dialog_inputs:
p = inp.get_attribute("placeholder") or ""
v = inp.get_attribute("value") or ""
log(f" placeholder='{p}' value='{v}'")
# 逐个填写
for inp in dialog_inputs:
p = inp.get_attribute("placeholder") or ""
log(f" 填写: {p}")
inp.click()
time.sleep(0.5)
inp.clear()
time.sleep(0.5)
if "旧密码" in p:
inp.send_keys("Ubains@1357")
log(f" 旧密码: Ubains@1357")
elif "新密码" in p:
inp.send_keys(NEW_PWD)
log(f" 新密码: {NEW_PWD}")
elif "确认密码" in p:
inp.send_keys(NEW_PWD)
log(f" 确认密码: {NEW_PWD}")
time.sleep(1)
time.sleep(3)
# 在弹窗内点确定
log("\n=== 弹窗内点击确定 ===")
dialog_btns = dialog.find_elements(By.TAG_NAME, "button")
for btn in dialog_btns:
if btn.text.strip() == "确定":
log("点击弹窗确定")
time.sleep(1)
btn.click()
break
time.sleep(5)
else:
log("⚠️ 未找到弹窗元素")
# 兜底:找可见的确定按钮
for btn in driver.find_elements(By.TAG_NAME, "button"):
if btn.is_displayed() and btn.text.strip() == "确定":
log("点击页面上的确定")
btn.click()
break
time.sleep(5)
body = driver.execute_script("return document.body.innerText.substring(0, 500);")
if "修改密码" in body and "旧密码" in body:
log("⚠️ 对话框未关闭")
else:
log("✅ 对话框已关闭")
# 4. 验证
log(f"\n=== 验证新密码 ===")
driver.get(f'{BASE}/')
time.sleep(5)
for inp in driver.find_elements(By.TAG_NAME, "input"):
if not inp.is_displayed(): continue
p = inp.get_attribute("placeholder") or ""
t = inp.get_attribute("type") or ""
if "手机" in p or "用户名" in p:
inp.clear(); inp.send_keys("admin")
elif t == "password":
inp.clear(); inp.send_keys(NEW_PWD)
elif "图形" in p:
inp.clear(); inp.send_keys("csba")
time.sleep(2)
for cb in driver.find_elements(By.XPATH, "//input[@type='checkbox']"):
if cb.is_displayed() and not cb.is_selected():
cb.click(); break
time.sleep(2)
for btn in driver.find_elements(By.TAG_NAME, "button"):
if btn.is_displayed() and "登录" in btn.text:
btn.click(); break
time.sleep(8)
for _ in range(10):
body = driver.execute_script("return document.body.innerText.substring(0, 300);")
if 'login' not in driver.current_url.split('/')[-1].lower():
log("✅ 新密码登录成功!")
break
if "协议" in body and "确定" in body:
for btn in driver.find_elements(By.TAG_NAME, "button"):
if btn.is_displayed() and btn.text.strip() == "确定":
driver.execute_script("arguments[0].click();", btn)
time.sleep(3); break
time.sleep(1)
log(f"\n最终URL: {driver.current_url}")
log("\n浏览器保持打开60秒...")
time.sleep(60)
except Exception as e:
log(f"异常: {e}")
import traceback
traceback.print_exc()
finally:
driver.quit()
if __name__ == '__main__':
sys.exit(main())
\ No newline at end of file
#!/usr/bin/env python3
# -*- coding: utf-8 -*-
"""修改密码 - 使用JS操作弹窗输入框"""
import sys, time
from datetime import datetime
from selenium import webdriver
from selenium.webdriver.chrome.options import Options
from selenium.webdriver.common.by import By
if sys.platform == 'win32':
try: sys.stdout.reconfigure(encoding='utf-8', errors='replace')
except: pass
BASE = 'https://192.168.9.76'
NEW_PWD = "Admin@2024ub"
def log(msg):
print(f"[{datetime.now().strftime('%H:%M:%S')}] {msg}", flush=True)
def main():
log("=" * 60)
log(f"修改密码 -> {NEW_PWD}")
log("=" * 60)
opts = Options()
opts.add_argument('--ignore-certificate-errors')
opts.add_argument('--ignore-ssl-errors')
opts.add_argument('--window-size=1920,1080')
driver = webdriver.Chrome(options=opts)
driver.implicitly_wait(10)
try:
# 1. 登录
log("\n=== 登录 ===")
driver.get(f'{BASE}/')
time.sleep(8)
for inp in driver.find_elements(By.TAG_NAME, "input"):
if not inp.is_displayed(): continue
p = inp.get_attribute("placeholder") or ""
t = inp.get_attribute("type") or ""
if "手机" in p or "用户名" in p: inp.clear(); inp.send_keys("admin")
elif t == "password": inp.clear(); inp.send_keys("Ubains@1357")
elif "图形" in p: inp.clear(); inp.send_keys("csba")
time.sleep(2)
for cb in driver.find_elements(By.XPATH, "//input[@type='checkbox']"):
if cb.is_displayed() and not cb.is_selected(): cb.click(); break
time.sleep(2)
for btn in driver.find_elements(By.TAG_NAME, "button"):
if btn.is_displayed() and "登录" in btn.text: btn.click(); break
# 2. 处理弹窗
log("\n=== 处理弹窗 ===")
time.sleep(5)
for _ in range(25):
body = driver.execute_script("return document.body.innerText.substring(0, 500);")
if "请输入旧密码" in body and "再次输入密码" in body:
log("✅ 修改密码弹窗出现"); break
if "协议" in body and "确定" in body:
for btn in driver.find_elements(By.TAG_NAME, "button"):
if btn.is_displayed() and btn.text.strip() == "确定":
driver.execute_script("arguments[0].click();", btn)
time.sleep(3); break
time.sleep(1)
# 3. 用JS填写所有弹窗输入框
log("\n=== 填写密码 ===")
time.sleep(2)
result = driver.execute_script("""
var inputs = document.querySelectorAll('input');
var setter = Object.getOwnPropertyDescriptor(window.HTMLInputElement.prototype, 'value').set;
var found = {old: false, new: false, confirm: false};
inputs.forEach(function(inp) {
if (inp.offsetParent === null) return;
var p = inp.placeholder || '';
var t = inp.type || '';
if (p.indexOf('旧密码') >= 0) {
setter.call(inp, 'Ubains@1357');
inp.dispatchEvent(new Event('input', {bubbles:true}));
inp.dispatchEvent(new Event('change', {bubbles:true}));
inp.dispatchEvent(new Event('blur', {bubbles:true}));
found.old = true;
}
else if (t === 'password' && p.indexOf('11位') >= 0) {
setter.call(inp, arguments[0]);
inp.dispatchEvent(new Event('input', {bubbles:true}));
inp.dispatchEvent(new Event('change', {bubbles:true}));
inp.dispatchEvent(new Event('blur', {bubbles:true}));
found['new'] = true;
}
else if (p === '再次输入密码') {
setter.call(inp, arguments[0]);
inp.dispatchEvent(new Event('input', {bubbles:true}));
inp.dispatchEvent(new Event('change', {bubbles:true}));
inp.dispatchEvent(new Event('blur', {bubbles:true}));
found.confirm = true;
}
});
return JSON.stringify(found);
""", NEW_PWD)
log(f"填写结果: {result}")
time.sleep(3)
# 4. 点确定按钮
log("点击确定...")
driver.execute_script("""
var btns = document.querySelectorAll('button');
for (var i = 0; i < btns.length; i++) {
if (btns[i].textContent.trim() === '确定' && btns[i].offsetParent !== null) {
btns[i].click();
return 'clicked';
}
}
return 'not found';
""")
time.sleep(5)
# 检查结果
body = driver.execute_script("return document.body.innerText.substring(0, 500);")
if "请输入旧密码" in body:
log("⚠️ 对话框未关闭")
# 可能有额外的协议弹窗,继续处理
for _ in range(10):
body = driver.execute_script("return document.body.innerText.substring(0, 500);")
if "请输入旧密码" in body: time.sleep(1); continue
if "协议" in body and "确定" in body:
for btn in driver.find_elements(By.TAG_NAME, "button"):
if btn.is_displayed() and btn.text.strip() == "确定":
driver.execute_script("arguments[0].click();", btn)
time.sleep(3); break
break
else:
log("✅ 密码修改成功!")
# 5. 验证
log("\n=== 验证新密码 ===")
driver.get(f'{BASE}/')
time.sleep(5)
for inp in driver.find_elements(By.TAG_NAME, "input"):
if not inp.is_displayed(): continue
p = inp.get_attribute("placeholder") or ""
t = inp.get_attribute("type") or ""
if "手机" in p or "用户名" in p: inp.send_keys("admin")
elif t == "password": inp.send_keys(NEW_PWD)
elif "图形" in p: inp.send_keys("csba")
time.sleep(2)
for cb in driver.find_elements(By.XPATH, "//input[@type='checkbox']"):
if cb.is_displayed() and not cb.is_selected(): cb.click(); break
time.sleep(2)
for btn in driver.find_elements(By.TAG_NAME, "button"):
if btn.is_displayed() and "登录" in btn.text: btn.click(); break
time.sleep(8)
for _ in range(10):
body = driver.execute_script("return document.body.innerText.substring(0, 300);")
if 'login' not in driver.current_url.split('/')[-1].lower():
log("✅ 新密码登录成功!"); break
if "协议" in body and "确定" in body:
for btn in driver.find_elements(By.TAG_NAME, "button"):
if btn.is_displayed() and btn.text.strip() == "确定":
driver.execute_script("arguments[0].click();", btn)
time.sleep(3); break
time.sleep(1)
log(f"\n最终URL: {driver.current_url}")
log("\n浏览器保持打开60秒...")
time.sleep(60)
except Exception as e:
log(f"异常: {e}")
import traceback
traceback.print_exc()
finally:
driver.quit()
if __name__ == '__main__':
sys.exit(main())
\ No newline at end of file
#!/usr/bin/env python3
# -*- coding: utf-8 -*-
"""首次登录改密码 - 触发Vue compositionend事件"""
import sys, time
from datetime import datetime
from selenium import webdriver
from selenium.webdriver.chrome.options import Options
from selenium.webdriver.common.by import By
if sys.platform == 'win32':
try: sys.stdout.reconfigure(encoding='utf-8', errors='replace')
except: pass
BASE = 'https://192.168.9.76'
NEW_PWD = "Admin@2024ub"
def log(msg):
print(f"[{datetime.now().strftime('%H:%M:%S')}] {msg}", flush=True)
def main():
log("=" * 60)
log(f"首次登录改密码 -> {NEW_PWD}")
log("=" * 60)
opts = Options()
opts.add_argument('--ignore-certificate-errors')
opts.add_argument('--ignore-ssl-errors')
opts.add_argument('--window-size=1920,1080')
driver = webdriver.Chrome(options=opts)
driver.implicitly_wait(10)
try:
log("\n=== 登录 ===")
driver.get(f'{BASE}/')
time.sleep(8)
for inp in driver.find_elements(By.TAG_NAME, "input"):
if not inp.is_displayed(): continue
p = inp.get_attribute("placeholder") or ""
t = inp.get_attribute("type") or ""
if "手机" in p or "用户名" in p: inp.clear(); inp.send_keys("admin")
elif t == "password": inp.clear(); inp.send_keys("Ubains@1357")
elif "图形" in p: inp.clear(); inp.send_keys("csba")
time.sleep(2)
for cb in driver.find_elements(By.XPATH, "//input[@type='checkbox']"):
if cb.is_displayed() and not cb.is_selected(): cb.click(); break
time.sleep(2)
for btn in driver.find_elements(By.TAG_NAME, "button"):
if btn.is_displayed() and "登录" in btn.text: btn.click(); break
# 处理弹窗
log("\n=== 处理弹窗 ===")
time.sleep(5)
for _ in range(30):
body = driver.execute_script("return document.body.innerText.substring(0, 500);")
if "请输入旧密码" in body and "再次输入密码" in body:
log("✅ 修改密码弹窗出现"); break
if "协议" in body and "确定" in body and "取消" in body:
for btn in driver.find_elements(By.TAG_NAME, "button"):
if btn.is_displayed() and btn.text.strip() == "确定":
driver.execute_script("arguments[0].click();", btn)
time.sleep(3); break
time.sleep(1)
time.sleep(2)
# 用JS设置值,触发Vue composition事件
log("\n=== 填写密码 ===")
result = driver.execute_script("""
var inputs = document.querySelectorAll('input');
var setter = Object.getOwnPropertyDescriptor(window.HTMLInputElement.prototype, 'value').set;
var filled = {};
inputs.forEach(function(inp) {
if (inp.offsetParent === null) return;
var p = inp.placeholder || '';
var t = inp.type || '';
if (p.indexOf('旧密码') >= 0) {
setter.call(inp, 'Ubains@1357');
inp.dispatchEvent(new Event('compositionstart', {bubbles:true}));
inp.dispatchEvent(new Event('compositionupdate', {bubbles:true}));
inp.dispatchEvent(new Event('compositionend', {bubbles:true}));
inp.dispatchEvent(new Event('input', {bubbles:true}));
inp.dispatchEvent(new Event('change', {bubbles:true}));
inp.dispatchEvent(new Event('blur', {bubbles:true}));
filled.old = 'Ubains@1357';
}
else if (t === 'password' && p.indexOf('11位') >= 0) {
setter.call(inp, arguments[0]);
inp.dispatchEvent(new Event('compositionstart', {bubbles:true}));
inp.dispatchEvent(new Event('compositionupdate', {bubbles:true}));
inp.dispatchEvent(new Event('compositionend', {bubbles:true}));
inp.dispatchEvent(new Event('input', {bubbles:true}));
inp.dispatchEvent(new Event('change', {bubbles:true}));
inp.dispatchEvent(new Event('blur', {bubbles:true}));
filled['new'] = arguments[0];
}
else if (p === '再次输入密码') {
setter.call(inp, arguments[0]);
inp.dispatchEvent(new Event('compositionstart', {bubbles:true}));
inp.dispatchEvent(new Event('compositionupdate', {bubbles:true}));
inp.dispatchEvent(new Event('compositionend', {bubbles:true}));
inp.dispatchEvent(new Event('input', {bubbles:true}));
inp.dispatchEvent(new Event('change', {bubbles:true}));
inp.dispatchEvent(new Event('blur', {bubbles:true}));
filled.confirm = arguments[0];
}
});
return JSON.stringify(filled);
""", NEW_PWD)
log(f"填写结果: {result}")
# 再检查值是否真的写入了
time.sleep(2)
check = driver.execute_script("""
var inputs = document.querySelectorAll('input');
var result = {};
inputs.forEach(function(inp) {
if (inp.offsetParent === null) return;
var p = inp.placeholder || '';
if (p.indexOf('旧密码') >= 0) result.old_value = inp.value;
else if (p.indexOf('11位') >= 0) result.new_value = inp.value;
else if (p === '再次输入密码') result.confirm_value = inp.value;
});
return JSON.stringify(result);
""")
log(f"实际值检查: {check}")
time.sleep(3)
# 点确定
log("点击确定...")
driver.execute_script("""
var btns = document.querySelectorAll('button');
for (var i = 0; i < btns.length; i++) {
if (btns[i].textContent.trim() === '确定' && btns[i].offsetParent !== null) {
btns[i].click();
return 'clicked';
}
}
return 'not found';
""")
time.sleep(8)
body = driver.execute_script("return document.body.innerText.substring(0, 500);")
if "请输入旧密码" in body:
log("⚠️ 对话框未关闭")
errs = driver.execute_script("""
var msgs = document.querySelectorAll('.el-message, .el-form-item__error');
return JSON.stringify(Array.from(msgs).filter(function(m) { return m.offsetParent !== null; }).map(function(m) { return m.textContent.trim(); }));
""")
log(f"错误消息: {errs}")
else:
log("✅ 密码修改成功!")
# 验证新密码
log("\n=== 验证新密码 ===")
driver.get(f'{BASE}/')
time.sleep(5)
for inp in driver.find_elements(By.TAG_NAME, "input"):
if not inp.is_displayed(): continue
p = inp.get_attribute("placeholder") or ""
t = inp.get_attribute("type") or ""
if "手机" in p or "用户名" in p: inp.send_keys("admin")
elif t == "password": inp.send_keys(NEW_PWD)
elif "图形" in p: inp.send_keys("csba")
time.sleep(2)
for cb in driver.find_elements(By.XPATH, "//input[@type='checkbox']"):
if cb.is_displayed() and not cb.is_selected(): cb.click(); break
time.sleep(2)
for btn in driver.find_elements(By.TAG_NAME, "button"):
if btn.is_displayed() and "登录" in btn.text: btn.click(); break
time.sleep(8)
for _ in range(10):
body = driver.execute_script("return document.body.innerText.substring(0, 300);")
if 'login' not in driver.current_url.split('/')[-1].lower():
log("✅ 新密码登录成功!"); break
if "协议" in body and "确定" in body:
for btn in driver.find_elements(By.TAG_NAME, "button"):
if btn.is_displayed() and btn.text.strip() == "确定":
driver.execute_script("arguments[0].click();", btn)
time.sleep(3); break
time.sleep(1)
log(f"\n最终URL: {driver.current_url}")
log("\n浏览器保持打开60秒...")
time.sleep(60)
except Exception as e:
log(f"异常: {e}")
import traceback
traceback.print_exc()
finally:
driver.quit()
if __name__ == '__main__':
sys.exit(main())
\ No newline at end of file
#!/usr/bin/env python3
# -*- coding: utf-8 -*-
"""修改密码 - 全JS操作"""
import sys, time
from datetime import datetime
from selenium import webdriver
from selenium.webdriver.chrome.options import Options
from selenium.webdriver.common.by import By
if sys.platform == 'win32':
try: sys.stdout.reconfigure(encoding='utf-8', errors='replace')
except: pass
BASE = 'https://192.168.9.76'
def log(msg):
print(f"[{datetime.now().strftime('%H:%M:%S')}] {msg}", flush=True)
def main():
log("=" * 60)
log("修改密码 - 全JS操作")
log("=" * 60)
opts = Options()
opts.add_argument('--ignore-certificate-errors')
opts.add_argument('--ignore-ssl-errors')
opts.add_argument('--window-size=1920,1080')
driver = webdriver.Chrome(options=opts)
driver.implicitly_wait(10)
try:
# 1. 登录
log("\n=== 登录 ===")
driver.get(f'{BASE}/')
time.sleep(8)
driver.execute_script("""
var inputs = document.querySelectorAll('input');
var setter = Object.getOwnPropertyDescriptor(window.HTMLInputElement.prototype, 'value').set;
inputs.forEach(function(i) {
if (i.offsetParent === null) return;
var p = i.placeholder || '';
var t = i.type || '';
if (p.indexOf('手机') >= 0 || p.indexOf('用户名') >= 0) {
setter.call(i, 'admin'); i.dispatchEvent(new Event('input', {bubbles:true}));
} else if (t === 'password') {
setter.call(i, 'Ubains@1357'); i.dispatchEvent(new Event('input', {bubbles:true}));
} else if (p.indexOf('图形') >= 0) {
setter.call(i, 'csba'); i.dispatchEvent(new Event('input', {bubbles:true}));
}
});
""")
time.sleep(2)
for cb in driver.find_elements(By.XPATH, "//input[@type='checkbox']"):
if cb.is_displayed() and not cb.is_selected():
driver.execute_script("arguments[0].click();", cb); break
time.sleep(2)
for btn in driver.find_elements(By.TAG_NAME, "button"):
if btn.is_displayed() and "登录" in btn.text:
driver.execute_script("arguments[0].click();", btn); break
time.sleep(5)
# 2. 循环处理所有弹窗
log("\n=== 处理弹窗 + 修改密码 ===")
for i in range(25):
result = driver.execute_script("""
var body = document.body.innerText;
var r = {};
// 处理协议弹窗
if (body.indexOf('协议') >= 0 && body.indexOf('取消') >= 0 && body.indexOf('旧密码') < 0) {
var btns = document.querySelectorAll('button');
for (var b = 0; b < btns.length; b++) {
if (btns[b].textContent.trim() === '确定' && btns[b].offsetParent !== null) {
btns[b].click(); r.agreement = 'ok'; break;
}
}
}
// 填写修改密码(如果检测到)
if (body.indexOf('修改密码') >= 0 && body.indexOf('旧密码') >= 0) {
var inputs = document.querySelectorAll('input');
var setter = Object.getOwnPropertyDescriptor(window.HTMLInputElement.prototype, 'value').set;
inputs.forEach(function(inp) {
if (inp.offsetParent === null) return;
var p = inp.placeholder || '';
if (p.indexOf('旧密码') >= 0) {
setter.call(inp, 'Ubains@1357');
inp.dispatchEvent(new Event('input', {bubbles:true}));
inp.dispatchEvent(new Event('change', {bubbles:true}));
r.old = 'set';
} else if (p.indexOf('新密码') >= 0) {
setter.call(inp, 'Admin@2024ub');
inp.dispatchEvent(new Event('input', {bubbles:true}));
inp.dispatchEvent(new Event('change', {bubbles:true}));
r.new = 'set';
} else if (p.indexOf('确认密码') >= 0) {
setter.call(inp, 'Admin@2024ub');
inp.dispatchEvent(new Event('input', {bubbles:true}));
inp.dispatchEvent(new Event('change', {bubbles:true}));
r.confirm = 'set';
}
});
}
return JSON.stringify(r);
""")
body_text = driver.execute_script("return document.body.innerText.substring(0, 400);")
# 如果已经看不到修改密码弹窗了
if "修改密码" not in body_text and "旧密码" not in body_text:
log(f"✅ 密码修改完成!(第{i+1}回合)")
break
# 填写后点确定
if '"old":"set"' in result or '"new":"set"' in result:
driver.execute_script("""
var btns = document.querySelectorAll('button');
for (var b = 0; b < btns.length; b++) {
if (btns[b].textContent.trim() === '确定' && btns[b].offsetParent !== null) {
btns[b].click(); break;
}
}
""")
if i % 3 == 0:
log(f" 点击确定 (第{i+1}回合)")
time.sleep(1)
# 3. 验证新密码
log("\n=== 验证新密码 ===")
driver.get(f'{BASE}/')
time.sleep(5)
driver.execute_script("""
var inputs = document.querySelectorAll('input');
var setter = Object.getOwnPropertyDescriptor(window.HTMLInputElement.prototype, 'value').set;
inputs.forEach(function(i) {
if (i.offsetParent === null) return;
var p = i.placeholder || '', t = i.type || '';
if (p.indexOf('手机') >= 0 || p.indexOf('用户名') >= 0) {
setter.call(i, 'admin'); i.dispatchEvent(new Event('input', {bubbles:true}));
} else if (t === 'password') {
setter.call(i, 'Admin@2024ub'); i.dispatchEvent(new Event('input', {bubbles:true}));
} else if (p.indexOf('图形') >= 0) {
setter.call(i, 'csba'); i.dispatchEvent(new Event('input', {bubbles:true}));
}
});
""")
time.sleep(2)
for cb in driver.find_elements(By.XPATH, "//input[@type='checkbox']"):
if cb.is_displayed() and not cb.is_selected():
cb.click(); break
time.sleep(2)
for btn in driver.find_elements(By.TAG_NAME, "button"):
if btn.is_displayed() and "登录" in btn.text:
btn.click(); break
time.sleep(8)
for _ in range(10):
body = driver.execute_script("return document.body.innerText.substring(0, 300);")
if 'login' not in driver.current_url.split('/')[-1].lower():
log("✅ 新密码登录成功!")
break
if "协议" in body and "确定" in body:
for btn in driver.find_elements(By.TAG_NAME, "button"):
if btn.is_displayed() and btn.text.strip() == "确定":
btn.click(); time.sleep(3); break
time.sleep(1)
log(f"\n最终URL: {driver.current_url}")
log("\n浏览器保持打开60秒...")
time.sleep(60)
except Exception as e:
log(f"异常: {e}")
import traceback
traceback.print_exc()
finally:
driver.quit()
if __name__ == '__main__':
sys.exit(main())
\ No newline at end of file
#!/usr/bin/env python3
# -*- coding: utf-8 -*-
"""
仅执行修改密码操作 - 用JS触发所有事件
"""
import sys, time
from datetime import datetime
from selenium import webdriver
from selenium.webdriver.chrome.options import Options
from selenium.webdriver.common.by import By
if sys.platform == 'win32':
try: sys.stdout.reconfigure(encoding='utf-8', errors='replace')
except: pass
BASE = 'https://192.168.9.76'
def log(msg):
print(f"[{datetime.now().strftime('%H:%M:%S')}] {msg}", flush=True)
def main():
log("=" * 60)
log("修改密码 - 完整触发Vue事件")
log("=" * 60)
opts = Options()
opts.add_argument('--ignore-certificate-errors')
opts.add_argument('--ignore-ssl-errors')
opts.add_argument('--window-size=1920,1080')
driver = webdriver.Chrome(options=opts)
driver.implicitly_wait(10)
try:
# 登录
driver.get(f'{BASE}/')
time.sleep(8)
# 填写表单
driver.execute_script("""
var inputs = document.querySelectorAll('input');
inputs.forEach(function(i) {
if (i.offsetParent === null) return;
var p = i.placeholder || '';
var t = i.type || '';
if (p.indexOf('手机') >= 0 || p.indexOf('用户名') >= 0 || p.indexOf('邮箱') >= 0) {
var nativeInputValueSetter = Object.getOwnPropertyDescriptor(window.HTMLInputElement.prototype, 'value').set;
nativeInputValueSetter.call(i, 'admin');
i.dispatchEvent(new Event('input', {bubbles: true}));
i.dispatchEvent(new Event('change', {bubbles: true}));
i.dispatchEvent(new Event('blur', {bubbles: true}));
} else if (t === 'password') {
var nativeInputValueSetter = Object.getOwnPropertyDescriptor(window.HTMLInputElement.prototype, 'value').set;
nativeInputValueSetter.call(i, 'Ubains@1357');
i.dispatchEvent(new Event('input', {bubbles: true}));
i.dispatchEvent(new Event('change', {bubbles: true}));
} else if (p.indexOf('图形') >= 0 || p.indexOf('验证') >= 0) {
var nativeInputValueSetter = Object.getOwnPropertyDescriptor(window.HTMLInputElement.prototype, 'value').set;
nativeInputValueSetter.call(i, 'csba');
i.dispatchEvent(new Event('input', {bubbles: true}));
i.dispatchEvent(new Event('change', {bubbles: true}));
}
});
""")
time.sleep(2)
# 勾选协议
for cb in driver.find_elements(By.XPATH, "//input[@type='checkbox']"):
if cb.is_displayed() and not cb.is_selected():
driver.execute_script("arguments[0].click();", cb)
log("已勾选协议")
break
time.sleep(2)
# 登录
for btn in driver.find_elements(By.TAG_NAME, "button"):
if btn.is_displayed() and "登录" in btn.text:
driver.execute_script("arguments[0].click();", btn)
log("已点击登录")
break
# 处理弹窗
time.sleep(5)
for _ in range(20):
body = driver.execute_script("return document.body.innerText.substring(0, 500);")
log(f"弹窗状态: {body[150:250]}")
if "修改密码" in body and "旧密码" in body:
log("✅ 检测到修改密码弹窗")
break
if "协议" in body and "确定" in body and "取消" in body and "旧密码" not in body:
for btn in driver.find_elements(By.TAG_NAME, "button"):
if btn.is_displayed() and btn.text.strip() == "确定":
driver.execute_script("arguments[0].click();", btn)
log("已点协议确定")
time.sleep(3)
break
time.sleep(1)
# 填写修改密码表单 - 使用JS native setter
log("\n填写修改密码表单...")
driver.execute_script("""
var inputs = document.querySelectorAll('input');
inputs.forEach(function(i) {
if (i.offsetParent === null) return;
var p = i.placeholder || '';
// 使用原生setter触发Vue响应
var nativeSetter = Object.getOwnPropertyDescriptor(window.HTMLInputElement.prototype, 'value').set;
if (p.indexOf('旧密码') >= 0) {
nativeSetter.call(i, 'Ubains@1357');
i.dispatchEvent(new Event('input', {bubbles: true}));
i.dispatchEvent(new Event('change', {bubbles: true}));
} else if (p.indexOf('新密码') >= 0) {
nativeSetter.call(i, 'Ubains@13579');
i.dispatchEvent(new Event('input', {bubbles: true}));
i.dispatchEvent(new Event('change', {bubbles: true}));
} else if (p.indexOf('确认密码') >= 0) {
nativeSetter.call(i, 'Ubains@13579');
i.dispatchEvent(new Event('input', {bubbles: true}));
i.dispatchEvent(new Event('change', {bubbles: true}));
}
});
""")
time.sleep(3)
# 点击确定
log("点击确定...")
for btn in driver.find_elements(By.TAG_NAME, "button"):
if btn.is_displayed() and btn.text.strip() == "确定":
driver.execute_script("arguments[0].click();", btn)
time.sleep(5)
log("已点确定")
break
body = driver.execute_script("return document.body.innerText.substring(0, 500);")
log(f"\n提交后页面:\n{body[:200]}")
# 重新登录用新密码验证
log("\n验证新密码...")
driver.get(f'{BASE}/')
time.sleep(5)
driver.execute_script("""
var inputs = document.querySelectorAll('input');
inputs.forEach(function(i) {
if (i.offsetParent === null) return;
var p = i.placeholder || '';
var t = i.type || '';
var setter = Object.getOwnPropertyDescriptor(window.HTMLInputElement.prototype, 'value').set;
if (p.indexOf('手机') >= 0 || p.indexOf('用户名') >= 0 || p.indexOf('邮箱') >= 0) {
setter.call(i, 'admin');
i.dispatchEvent(new Event('input', {bubbles: true}));
i.dispatchEvent(new Event('change', {bubbles: true}));
} else if (t === 'password') {
setter.call(i, 'Ubains@13579');
i.dispatchEvent(new Event('input', {bubbles: true}));
i.dispatchEvent(new Event('change', {bubbles: true}));
} else if (p.indexOf('图形') >= 0 || p.indexOf('验证') >= 0) {
setter.call(i, 'csba');
i.dispatchEvent(new Event('input', {bubbles: true}));
i.dispatchEvent(new Event('change', {bubbles: true}));
}
});
""")
time.sleep(2)
for cb in driver.find_elements(By.XPATH, "//input[@type='checkbox']"):
if cb.is_displayed() and not cb.is_selected():
driver.execute_script("arguments[0].click();", cb); break
time.sleep(2)
for btn in driver.find_elements(By.TAG_NAME, "button"):
if btn.is_displayed() and "登录" in btn.text:
driver.execute_script("arguments[0].click();", btn)
log("已用新密码登录")
break
time.sleep(8)
# 处理可能出现的协议弹窗
for _ in range(10):
body = driver.execute_script("return document.body.innerText.substring(0, 500);")
if 'login' not in driver.current_url.split('/')[-1].lower():
log("✅ 新密码登录成功!")
break
if "协议" in body and "确定" in body:
for btn in driver.find_elements(By.TAG_NAME, "button"):
if btn.is_displayed() and btn.text.strip() == "确定":
driver.execute_script("arguments[0].click();", btn)
time.sleep(3)
break
time.sleep(1)
final_url = driver.current_url
final_body = driver.execute_script("return document.body.innerText.substring(0, 300);")
log(f"\n最终URL: {final_url}")
log(f"最终页面: {final_body[:150]}")
if 'login' not in final_url.split('/')[-1].lower():
log("\n✅ 全部完成!")
else:
log("\n⚠️ 新密码仍然无效")
log("\n浏览器保持打开60秒...")
time.sleep(60)
except Exception as e:
log(f"异常: {e}")
import traceback
traceback.print_exc()
finally:
driver.quit()
if __name__ == '__main__':
sys.exit(main())
\ No newline at end of file
#!/usr/bin/env python3
# -*- coding: utf-8 -*-
"""通过浏览器JS API直接修改密码"""
import sys, time, json
from datetime import datetime
from selenium import webdriver
from selenium.webdriver.chrome.options import Options
from selenium.webdriver.common.by import By
if sys.platform == 'win32':
try: sys.stdout.reconfigure(encoding='utf-8', errors='replace')
except: pass
BASE = 'https://192.168.9.76'
NEW_PWD = "Admin@2024ub"
def log(msg):
print(f"[{datetime.now().strftime('%H:%M:%S')}] {msg}", flush=True)
def main():
log("=" * 60)
log(f"通过JS API修改密码 -> {NEW_PWD}")
log("=" * 60)
opts = Options()
opts.add_argument('--ignore-certificate-errors')
opts.add_argument('--ignore-ssl-errors')
opts.add_argument('--window-size=1920,1080')
driver = webdriver.Chrome(options=opts)
driver.implicitly_wait(10)
try:
# 先登录
driver.get(f'{BASE}/')
time.sleep(8)
driver.execute_script("""
var inputs = document.querySelectorAll('input');
var setter = Object.getOwnPropertyDescriptor(window.HTMLInputElement.prototype, 'value').set;
inputs.forEach(function(i) {
if (i.offsetParent === null) return;
var p = i.placeholder || '', t = i.type || '';
if (p.indexOf('手机') >= 0 || p.indexOf('用户名') >= 0) {
setter.call(i, 'admin'); i.dispatchEvent(new Event('input', {bubbles:true}));
} else if (t === 'password') {
setter.call(i, 'Ubains@1357'); i.dispatchEvent(new Event('input', {bubbles:true}));
} else if (p.indexOf('图形') >= 0) {
setter.call(i, 'csba'); i.dispatchEvent(new Event('input', {bubbles:true}));
}
});
""")
time.sleep(2)
for cb in driver.find_elements(By.XPATH, "//input[@type='checkbox']"):
if cb.is_displayed() and not cb.is_selected(): cb.click(); break
time.sleep(2)
for btn in driver.find_elements(By.TAG_NAME, "button"):
if btn.is_displayed() and "登录" in btn.text:
btn.click(); break
# 等弹窗
time.sleep(8)
for _ in range(20):
body = driver.execute_script("return document.body.innerText.substring(0, 500);")
if "修改密码" in body and "旧密码" in body:
log("✅ 修改密码弹窗出现")
break
if "协议" in body and "确定" in body and "取消" in body:
for btn in driver.find_elements(By.TAG_NAME, "button"):
if btn.is_displayed() and btn.text.strip() == "确定":
btn.click(); time.sleep(3); break
time.sleep(1)
# 获取token
token = driver.execute_script("return localStorage.getItem('token') || '';")
log(f"Token: {token[:40] if token else 'None'}...")
# 获取当前的platformToken(可能包含access_token)
token_data = driver.execute_script("return localStorage.getItem('platformToken') || '{}';")
try:
pt = json.loads(token_data)
if not token and pt.get('access_token'):
token = pt['access_token']
log(f"从platformToken获取到token")
except:
pass
# 直接调用API修改密码
log("\n=== API修改密码 ===")
result = driver.execute_script("""
var token = localStorage.getItem('token') || '';
var ptStr = localStorage.getItem('platformToken') || '{}';
var accessToken = '';
try { var pt = JSON.parse(ptStr); accessToken = pt.access_token || ''; } catch(e) {}
var finalToken = token || (accessToken ? 'Bearer ' + accessToken : '');
var apiUrls = [
'/backstage/api/user/updatePwd',
'/api/user/updatePwd',
'/api/updatePwd',
'/exapi/user/updatePwd'
];
var body = JSON.stringify({
oldPassword: 'Ubains@1357',
newPassword: '"' + arguments[0] + '"',
confirmPassword: '"' + arguments[0] + '"'
});
// Try a few token formats
var authHeaders = [
finalToken,
finalToken.startsWith('Bearer ') ? finalToken : 'Bearer ' + finalToken
];
var results = [];
for (var a = 0; a < authHeaders.length; a++) {
for (var u = 0; u < apiUrls.length; u++) {
try {
var xhr = new XMLHttpRequest();
xhr.open('POST', apiUrls[u], false);
xhr.setRequestHeader('Content-Type', 'application/json');
xhr.setRequestHeader('Authorization', authHeaders[a]);
xhr.send(body);
results.push(apiUrls[u] + ' -> ' + xhr.status + ': ' + xhr.responseText.substring(0,100));
} catch(e) {
results.push(apiUrls[u] + ' -> error: ' + e.message);
}
}
}
return JSON.stringify(results);
""", NEW_PWD)
log(f"API结果:")
for r in json.loads(result):
log(f" {r}")
# 如果API成功,验证新密码
if any('200' in r for r in json.loads(result)):
log("\n✅ API修改成功,验证新密码...")
# 先试试API修改后是否还有修改密码弹窗
time.sleep(3)
driver.get(f'{BASE}/')
time.sleep(5)
driver.execute_script("""
var inputs = document.querySelectorAll('input');
var setter = Object.getOwnPropertyDescriptor(window.HTMLInputElement.prototype, 'value').set;
inputs.forEach(function(i) {
if (i.offsetParent === null) return;
var p = i.placeholder || '', t = i.type || '';
if (p.indexOf('手机') >= 0 || p.indexOf('用户名') >= 0) {
setter.call(i, 'admin'); i.dispatchEvent(new Event('input', {bubbles:true}));
} else if (t === 'password') {
setter.call(i, arguments[0]); i.dispatchEvent(new Event('input', {bubbles:true}));
} else if (p.indexOf('图形') >= 0) {
setter.call(i, 'csba'); i.dispatchEvent(new Event('input', {bubbles:true}));
}
});
""", NEW_PWD)
time.sleep(2)
for cb in driver.find_elements(By.XPATH, "//input[@type='checkbox']"):
if cb.is_displayed() and not cb.is_selected(): cb.click(); break
time.sleep(2)
for btn in driver.find_elements(By.TAG_NAME, "button"):
if btn.is_displayed() and "登录" in btn.text:
btn.click(); break
time.sleep(8)
for _ in range(10):
body = driver.execute_script("return document.body.innerText.substring(0, 300);")
if 'login' not in driver.current_url.split('/')[-1].lower():
log("✅ 新密码登录成功!")
break
if "协议" in body and "确定" in body:
for btn in driver.find_elements(By.TAG_NAME, "button"):
if btn.is_displayed() and btn.text.strip() == "确定":
btn.click(); time.sleep(3); break
time.sleep(1)
log(f"\n最终URL: {driver.current_url}")
log("\n浏览器保持打开60秒...")
time.sleep(60)
except Exception as e:
log(f"异常: {e}")
import traceback
traceback.print_exc()
finally:
driver.quit()
if __name__ == '__main__':
sys.exit(main())
\ No newline at end of file
#!/usr/bin/env python3
import paramiko
import sys
if sys.platform == 'win32':
try: sys.stdout.reconfigure(encoding='utf-8', errors='replace')
except: pass
HOST = "192.168.9.76"
USERNAME = "admin"
PASSWORD = "Ubains@123"
SUDO_PASSWORD = "Ubains@123"
ssh = paramiko.SSHClient()
ssh.set_missing_host_key_policy(paramiko.AutoAddPolicy())
ssh.connect(HOST, 22, USERNAME, PASSWORD, timeout=30, look_for_keys=False, allow_agent=False)
def ssh_cmd(cmd):
full_cmd = f"echo '{SUDO_PASSWORD}' | sudo -S {cmd}"
stdin, stdout, stderr = ssh.exec_command(full_cmd, timeout=60)
out = stdout.read().decode('utf-8', errors='replace')
return out
print("=" * 60)
print("讯飞服务诊断")
print("=" * 60)
# 检查容器日志
print("\n[1] upython_voice容器日志(最近20行):")
out = ssh_cmd("docker logs upython_voice --tail 20 2>&1")
print(out)
# 检查容器状态
print("\n[2] 容器状态:")
out = ssh_cmd("docker ps -a --format 'table {{.Names}}\\t{{.Status}}' | grep voice")
print(out)
# 检查服务日志文件
print("\n[3] 讯飞服务日志文件(最近10行):")
out = ssh_cmd("tail -10 /data/services/api/python-voice/log/uinfo.log 2>/dev/null")
print(out if out.strip() else "[无日志或文件不存在]")
ssh.close()
\ No newline at end of file
此差异已折叠。
#!/usr/bin/env python3
import paramiko
import sys
if sys.platform == 'win32':
try:
sys.stdout.reconfigure(encoding='utf-8', errors='replace')
except:
pass
HOST = "192.168.9.76"
USERNAME = "admin"
PASSWORD = "Ubains@123"
SUDO_PASSWORD = "Ubains@123"
ssh = paramiko.SSHClient()
ssh.set_missing_host_key_policy(paramiko.AutoAddPolicy())
ssh.connect(HOST, 22, USERNAME, PASSWORD, timeout=30, look_for_keys=False, allow_agent=False)
cmd = f"echo '{SUDO_PASSWORD}' | sudo -S docker ps"
stdin, stdout, stderr = ssh.exec_command(cmd, timeout=60)
out = stdout.read().decode('utf-8', errors='replace')
print("=" * 60)
print("Docker容器状态:")
print("=" * 60)
print(out)
ssh.close()
\ No newline at end of file
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
Markdown 格式
0%
您添加了 0 到此讨论。请谨慎行事。
请先完成此评论的编辑!
注册 或者 后发表评论