ai 开始测试

This commit is contained in:
2025-08-27 21:58:55 +08:00
parent 741e52afd3
commit 699cb18b7d
14 changed files with 827 additions and 342 deletions

6
.idea/git_toolbox_blame.xml generated Normal file
View File

@@ -0,0 +1,6 @@
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="GitToolBoxBlameSettings">
<option name="version" value="2" />
</component>
</project>

2
.idea/iOSAI.iml generated
View File

@@ -2,7 +2,7 @@
<module type="PYTHON_MODULE" version="4">
<component name="NewModuleRootManager">
<content url="file://$MODULE_DIR$" />
<orderEntry type="jdk" jdkName="Python 3.12" jdkType="Python SDK" />
<orderEntry type="jdk" jdkName="Python 3.12 (IOS-AI)" jdkType="Python SDK" />
<orderEntry type="sourceFolder" forTests="false" />
</component>
</module>

6
.idea/jsLibraryMappings.xml generated Normal file
View File

@@ -0,0 +1,6 @@
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="JavaScriptLibraryMappings">
<includedPredefinedLibrary name="Node.js Core" />
</component>
</project>

2
.idea/misc.xml generated
View File

@@ -3,5 +3,5 @@
<component name="Black">
<option name="sdkName" value="Python 3.12" />
</component>
<component name="ProjectRootManager" version="2" project-jdk-name="Python 3.12" project-jdk-type="Python SDK" />
<component name="ProjectRootManager" version="2" project-jdk-name="Python 3.12 (IOS-AI)" project-jdk-type="Python SDK" />
</project>

107
.idea/workspace.xml generated
View File

@@ -4,15 +4,45 @@
<option name="autoReloadType" value="SELECTIVE" />
</component>
<component name="ChangeListManager">
<list default="true" id="eceeff5e-51c1-459c-a911-d21ec090a423" name="Changes" comment="">
<list default="true" id="eceeff5e-51c1-459c-a911-d21ec090a423" name="Changes" comment="Changes">
<change afterPath="$PROJECT_DIR$/.idea/git_toolbox_blame.xml" afterDir="false" />
<change afterPath="$PROJECT_DIR$/.idea/jsLibraryMappings.xml" afterDir="false" />
<change afterPath="$PROJECT_DIR$/resources/03cb0d61638ab919e9c9c5e016b969ff40925b0c/bgv.png" afterDir="false" />
<change afterPath="$PROJECT_DIR$/resources/833c034d29ee6b79e1dfd88dc1d454f3da1e8a3d/bgv.png" afterDir="false" />
<change beforePath="$PROJECT_DIR$/.idea/iOSAI.iml" beforeDir="false" afterPath="$PROJECT_DIR$/.idea/iOSAI.iml" afterDir="false" />
<change beforePath="$PROJECT_DIR$/.idea/misc.xml" beforeDir="false" afterPath="$PROJECT_DIR$/.idea/misc.xml" afterDir="false" />
<change beforePath="$PROJECT_DIR$/.idea/workspace.xml" beforeDir="false" afterPath="$PROJECT_DIR$/.idea/workspace.xml" afterDir="false" />
<change beforePath="$PROJECT_DIR$/Entity/Variables.py" beforeDir="false" afterPath="$PROJECT_DIR$/Entity/Variables.py" afterDir="false" />
<change beforePath="$PROJECT_DIR$/Module/FlaskService.py" beforeDir="false" afterPath="$PROJECT_DIR$/Module/FlaskService.py" afterDir="false" />
<change beforePath="$PROJECT_DIR$/Module/Main.py" beforeDir="false" afterPath="$PROJECT_DIR$/Module/Main.py" afterDir="false" />
<change beforePath="$PROJECT_DIR$/Utils/AiUtils.py" beforeDir="false" afterPath="$PROJECT_DIR$/Utils/AiUtils.py" afterDir="false" />
<change beforePath="$PROJECT_DIR$/Utils/ControlUtils.py" beforeDir="false" afterPath="$PROJECT_DIR$/Utils/ControlUtils.py" afterDir="false" />
<change beforePath="$PROJECT_DIR$/Utils/Requester.py" beforeDir="false" afterPath="$PROJECT_DIR$/Utils/Requester.py" afterDir="false" />
<change beforePath="$PROJECT_DIR$/script/ScriptManager.py" beforeDir="false" afterPath="$PROJECT_DIR$/script/ScriptManager.py" afterDir="false" />
</list>
<option name="SHOW_DIALOG" value="false" />
<option name="HIGHLIGHT_CONFLICTS" value="true" />
<option name="HIGHLIGHT_NON_ACTIVE_CHANGELIST" value="false" />
<option name="LAST_RESOLUTION" value="IGNORE" />
</component>
<component name="FileTemplateManagerImpl">
<option name="RECENT_TEMPLATES">
<list>
<option value="Python Script" />
</list>
</option>
</component>
<component name="FlaskConsoleOptions" custom-start-script="import sys&#10;sys.path.extend([WORKING_DIR_AND_PYTHON_PATHS])&#10;from flask.cli import ScriptInfo&#10;locals().update(ScriptInfo(create_app=None).load_app().make_shell_context())&#10;print(&quot;Python %s on %s\nApp: %s [%s]\nInstance: %s&quot; % (sys.version, sys.platform, app.import_name, app.env, app.instance_path))">
<envs>
<env key="FLASK_APP" value="app" />
</envs>
<option name="myCustomStartScript" value="import sys&#10;sys.path.extend([WORKING_DIR_AND_PYTHON_PATHS])&#10;from flask.cli import ScriptInfo&#10;locals().update(ScriptInfo(create_app=None).load_app().make_shell_context())&#10;print(&quot;Python %s on %s\nApp: %s [%s]\nInstance: %s&quot; % (sys.version, sys.platform, app.import_name, app.env, app.instance_path))" />
<option name="myEnvs">
<map>
<entry key="FLASK_APP" value="app" />
</map>
</option>
</component>
<component name="Git.Settings">
<option name="RECENT_GIT_ROOT_PATH" value="$PROJECT_DIR$" />
</component>
@@ -28,27 +58,55 @@
<option name="hideEmptyMiddlePackages" value="true" />
<option name="showLibraryContents" value="true" />
</component>
<component name="PropertiesComponent">{
&quot;keyToString&quot;: {
&quot;Python.Main.executor&quot;: &quot;Run&quot;,
&quot;RunOnceActivity.ShowReadmeOnStart&quot;: &quot;true&quot;,
&quot;git-widget-placeholder&quot;: &quot;main&quot;,
&quot;last_opened_file_path&quot;: &quot;E:/Code/python/iOSAI/Module/Main.py&quot;,
&quot;node.js.detected.package.eslint&quot;: &quot;true&quot;,
&quot;node.js.detected.package.tslint&quot;: &quot;true&quot;,
&quot;node.js.selected.package.eslint&quot;: &quot;(autodetect)&quot;,
&quot;node.js.selected.package.tslint&quot;: &quot;(autodetect)&quot;,
&quot;nodejs_package_manager_path&quot;: &quot;npm&quot;,
&quot;vue.rearranger.settings.migration&quot;: &quot;true&quot;
<component name="PropertiesComponent"><![CDATA[{
"keyToString": {
"Python.123.executor": "Run",
"Python.Main.executor": "Run",
"RunOnceActivity.ShowReadmeOnStart": "true",
"SHARE_PROJECT_CONFIGURATION_FILES": "true",
"git-widget-placeholder": "main",
"javascript.nodejs.core.library.configured.version": "20.17.0",
"javascript.nodejs.core.library.typings.version": "20.17.58",
"last_opened_file_path": "F:/company code/AI item/20250820/iOSAI",
"node.js.detected.package.eslint": "true",
"node.js.detected.package.tslint": "true",
"node.js.selected.package.eslint": "(autodetect)",
"node.js.selected.package.tslint": "(autodetect)",
"nodejs_package_manager_path": "npm",
"settings.editor.selected.configurable": "com.gitee.ui.GiteeSettingsConfigurable",
"vue.rearranger.settings.migration": "true"
}
}</component>
}]]></component>
<component name="RecentsManager">
<key name="MoveFile.RECENT_KEYS">
<recent name="E:\Code\python\iOSAI\resources" />
<recent name="E:\Code\python\iOSAI" />
</key>
</component>
<component name="RunManager">
<component name="RunManager" selected="Python.Main">
<configuration name="123" type="PythonConfigurationType" factoryName="Python" temporary="true" nameIsGenerated="true">
<module name="iOSAI" />
<option name="ENV_FILES" value="" />
<option name="INTERPRETER_OPTIONS" value="" />
<option name="PARENT_ENVS" value="true" />
<envs>
<env name="PYTHONUNBUFFERED" value="1" />
</envs>
<option name="SDK_HOME" value="" />
<option name="WORKING_DIRECTORY" value="$PROJECT_DIR$/test" />
<option name="IS_MODULE_SDK" value="true" />
<option name="ADD_CONTENT_ROOTS" value="true" />
<option name="ADD_SOURCE_ROOTS" value="true" />
<EXTENSION ID="PythonCoverageRunConfigurationExtension" runner="coverage.py" />
<option name="SCRIPT_NAME" value="$PROJECT_DIR$/test/123.py" />
<option name="PARAMETERS" value="" />
<option name="SHOW_COMMAND_LINE" value="false" />
<option name="EMULATE_TERMINAL" value="false" />
<option name="MODULE_MODE" value="false" />
<option name="REDIRECT_INPUT" value="false" />
<option name="INPUT_FILE" value="" />
<method v="2" />
</configuration>
<configuration name="Main" type="PythonConfigurationType" factoryName="Python" nameIsGenerated="true">
<module name="iOSAI" />
<option name="ENV_FILES" value="" />
@@ -58,7 +116,6 @@
<env name="PYTHONUNBUFFERED" value="1" />
</envs>
<option name="SDK_HOME" value="" />
<option name="SDK_NAME" value="Python 3.12" />
<option name="WORKING_DIRECTORY" value="" />
<option name="IS_MODULE_SDK" value="false" />
<option name="ADD_CONTENT_ROOTS" value="true" />
@@ -73,6 +130,11 @@
<option name="INPUT_FILE" value="" />
<method v="2" />
</configuration>
<recent_temporary>
<list>
<item itemvalue="Python.123" />
</list>
</recent_temporary>
</component>
<component name="SharedIndexes">
<attachedChunks>
@@ -103,6 +165,16 @@
<workItem from="1755604973651" duration="15000" />
<workItem from="1755606718587" duration="4204000" />
<workItem from="1755667295017" duration="5106000" />
<workItem from="1755680203414" duration="14026000" />
<workItem from="1755752625133" duration="20173000" />
<workItem from="1755790427362" duration="83000" />
<workItem from="1755790609876" duration="6000" />
<workItem from="1755840447414" duration="7214000" />
<workItem from="1755921690509" duration="17000" />
<workItem from="1756101135190" duration="18679000" />
<workItem from="1756124879602" duration="580000" />
<workItem from="1756184656258" duration="24292000" />
<workItem from="1756271781908" duration="26051000" />
</task>
<servers />
</component>
@@ -113,6 +185,7 @@
<option featureType="com.intellij.fileTypeFactory" implementationName="*.bat" />
</component>
<component name="com.intellij.coverage.CoverageDataManagerImpl">
<SUITE FILE_PATH="coverage/iOSAI$Main.coverage" NAME="Main Coverage Results" MODIFIED="1755671811518" SOURCE_PROVIDER="com.intellij.coverage.DefaultCoverageFileProvider" RUNNER="coverage.py" COVERAGE_BY_TEST_ENABLED="false" COVERAGE_TRACING_ENABLED="false" WORKING_DIRECTORY="" />
<SUITE FILE_PATH="coverage/iOSAI$Main.coverage" NAME="Main 覆盖结果" MODIFIED="1756302588713" SOURCE_PROVIDER="com.intellij.coverage.DefaultCoverageFileProvider" RUNNER="coverage.py" COVERAGE_BY_TEST_ENABLED="false" COVERAGE_TRACING_ENABLED="false" WORKING_DIRECTORY="" />
<SUITE FILE_PATH="coverage/iOSAI$123.coverage" NAME="123 覆盖结果" MODIFIED="1756300694280" SOURCE_PROVIDER="com.intellij.coverage.DefaultCoverageFileProvider" RUNNER="coverage.py" COVERAGE_BY_TEST_ENABLED="false" COVERAGE_TRACING_ENABLED="false" WORKING_DIRECTORY="$PROJECT_DIR$/test" />
</component>
</project>

View File

@@ -10,7 +10,7 @@ anchorList: list[AnchorModel] = []
# 线程锁
anchorListLock = threading.Lock()
# 打招呼数据
prologueList = []
prologueList = ["hello"]
# 评论列表
commentsList = []
# 存储主播名和session_id的字典

View File

@@ -93,6 +93,7 @@ def passToken():
print(e)
return ResultData(data="").toJson()
# 获取设备列表
@app.route('/deviceList', methods=['GET'])
def deviceList():
@@ -112,6 +113,7 @@ def deviceList():
LogManager.error("获取设备列表失败:", e)
return ResultData(data=[]).toJson()
# 获取设备应用列表
@app.route('/deviceAppList', methods=['POST'])
def deviceAppList():
@@ -230,11 +232,14 @@ def stopScript():
return ResultData(code=code, data="", msg=msg).toJson()
# 传递主播数据
# 传递主播数据(关注主播打招呼)
@app.route('/passAnchorData', methods=['POST'])
def passAnchorData():
data: Dict[str, Any] = request.get_json()
# 设备列表
print("接收的数据", data)
idList = data.get("deviceList", [])
# 主播列表
acList = data.get("anchorList", [])
@@ -247,7 +252,8 @@ def passAnchorData():
manager = ScriptManager()
event = threading.Event()
# 启动脚本
thread = threading.Thread(target=manager.greetNewFollowers, args=(udid, needReply, event))
# thread = threading.Thread(target=manager.greetNewFollowers, args=(udid, needReply, event))
thread = threading.Thread(target=manager.safe_greetNewFollowers, args=(udid, needReply, event))
thread.start()
# 添加到线程管理
ThreadManager.add(udid, thread, event)
@@ -270,8 +276,24 @@ def getChatTextInfo():
client = wda.USBClient(udid)
session = client.session()
xml = session.source()
result = AiUtils.extract_messages_from_xml(xml)
return ResultData(data=result).toJson()
try:
result = AiUtils.extract_messages_from_xml(xml)
print(result)
return ResultData(data=result).toJson()
except Exception as e:
data = [
{
'type': 'msg',
'dir': 'in',
'text': '当前页面无法获取聊天记录请在tiktok聊天页面进行获取'
},
{
'type': 'msg',
'dir': 'in',
'text': 'Unable to retrieve chat messages on the current screen. Please navigate to the TikTok chat page and try again!!!'
}
]
return ResultData(data=data, msg="解析失败").toJson()
# 监控消息

View File

@@ -27,7 +27,7 @@ if "--role=flask" in sys.argv:
# 项目入口
if __name__ == "__main__":
# 清空日志等
LogManager.clearLogs()
# LogManager.clearLogs()
# 启动 Flask 子进程
manager = FlaskSubprocessManager.get_instance()

View File

@@ -200,7 +200,7 @@ class AiUtils(object):
homeButton = session.xpath("//*[@label='首页']")
try:
if homeButton.label == "首页":
print("找到了")
print("1.找到了")
return homeButton
else:
print("没找到")
@@ -243,7 +243,7 @@ class AiUtils(object):
def getFollowButton(cls, session: Client):
followButton = session.xpath("//Window[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[2]/Other[2]/Other[1]/Other[1]/Other[3]/Other[1]/Other[1]/Button[1]")
if followButton.exists:
print("找到了")
print("2.找到了")
return followButton
else:
print("没找到")
@@ -254,7 +254,7 @@ class AiUtils(object):
def getSendMesageButton(cls, session: Client):
msgButton = session.xpath("//Window[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[2]/Other[2]/Other[1]/Other[1]/Other[3]/Other[1]/Other[1]")
if msgButton.exists:
print("找到了")
print("3.找到了")
return msgButton
else:
print("没找到")
@@ -294,6 +294,16 @@ class AiUtils(object):
root = etree.fromstring(xml.encode("utf-8"))
items = []
# 判断是否是聊天页面
is_chat_page = False
if root.xpath('//XCUIElementTypeStaticText[contains(@traits, "Header")]'):
is_chat_page = True
elif root.xpath('//XCUIElementTypeCell//XCUIElementTypeOther[@name or @label]'):
is_chat_page = True
if not is_chat_page:
raise Exception("请先进入聊天页面")
# 屏幕宽度
app = root.xpath('/XCUIElementTypeApplication')
screen_w = cls.parse_float(app[0], 'width', 414.0) if app else 414.0

View File

@@ -1,8 +1,11 @@
import re
import tidevice
from wda import Client
from Utils.AiUtils import AiUtils
from Utils.LogManager import LogManager
# 页面控制工具类
class ControlUtils(object):
@@ -59,8 +62,10 @@ class ControlUtils(object):
back = session.xpath("//*[@name='nav_bar_start_back']")
back.click()
return True
elif session.xpath("//Window[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]").exists:
back = session.xpath("//Window[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]")
elif session.xpath(
"//Window[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]").exists:
back = session.xpath(
"//Window[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]")
back.click()
return True
else:
@@ -73,7 +78,7 @@ class ControlUtils(object):
@classmethod
def clickLike(cls, session: Client, udid):
scale = session.scale
x, y = AiUtils.findImageInScreen("add",udid)
x, y = AiUtils.findImageInScreen("add", udid)
print(x, y)
if x > -1:
print("点赞了")
@@ -108,13 +113,29 @@ class ControlUtils(object):
# 获取主播详情页的第一个视频
@classmethod
def clickFirstVideoFromDetailPage(cls, session: Client):
videoCell = session.xpath('//Window/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[2]/Other[1]/ScrollView[1]/Other[1]/CollectionView[1]/Cell[2]')
if videoCell.exists:
# videoCell = session.xpath(
# '//Window/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[1]/Other[2]/Other[1]/ScrollView[1]/Other[1]/CollectionView[1]/Cell[2]')
videoCell = session.xpath(
'(//XCUIElementTypeCollectionView//XCUIElementTypeCell[.//XCUIElementTypeImage[@name="profile_video"]])[1]').get(
timeout=5)
tab = session.xpath('//XCUIElementTypeButton[@name="TTKProfileTabVideoButton_0"]').get(timeout=2)
# 某些版本 tab.value 可能就是数量;或者 tab.label 类似 “作品 7”
m = re.search(r"\d+", tab.label)
num = 0
if m:
# 判断当前的作品的数量
num = int(m.group())
print("作品数量为:", num)
if videoCell is not None:
videoCell.click()
# 点击视频
return True
print("找到主页的第一个视频")
return True, num
else:
return False
print("没有找到主页的第一个视频")
return False, num

View File

@@ -1,5 +1,5 @@
import requests
from Entity.Variables import prologueList
from Entity.Variables import prologueList
BaseUrl = "https://crawlclient.api.yolozs.com/api/common/"
# BaseUrl = "http://192.168.1.174:8101/api/common/"
@@ -17,9 +17,12 @@ class Requester():
url = BaseUrl + cls.prologue
result = requests.get(headers=headers, url=url)
json = result.json()
print("json",json
)
data = json.get("data")
print("返回的数据",data)
for i in data:
prologueList.append(i)
prologueList.append("hello")
# 翻译

Binary file not shown.

After

Width:  |  Height:  |  Size: 769 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.0 MiB

File diff suppressed because it is too large Load Diff