1
0
mirror of https://github.com/TheFunny/ArisuAutoSweeper synced 2025-12-16 22:05:12 +00:00

Compare commits

...

4 Commits

5 changed files with 13 additions and 313 deletions

View File

@ -65,9 +65,6 @@ class ConfigModel:
AppAsarUpdate: bool = True
NoSandbox: bool = True
# Dynamic
GitOverCdn: bool = False
class DeployConfig(ConfigModel):
def __init__(self, file=DEPLOY_CONFIG):
@ -82,8 +79,9 @@ class DeployConfig(ConfigModel):
# Bypass webui.config.DeployConfig.__setattr__()
# Don't write these into deploy.yaml
super().__setattr__('GitOverCdn', self.Repository in ['cn'])
if self.Repository in ['global', 'cn']:
if self.Repository == 'cn':
super().__setattr__('Repository', 'https://git.yoursfunny.top/YoursFunny/ArisuAutoSweeper.git')
if self.Repository == 'global':
super().__setattr__('Repository', 'https://github.com/TheFunny/ArisuAutoSweeper')
self.write()

View File

@ -4,7 +4,6 @@ import os
from deploy.Windows.config import DeployConfig
from deploy.Windows.logger import Progress, logger
from deploy.Windows.utils import cached_property
# from deploy.git_over_cdn.client import GitOverCdnClient
class GitConfigParser(configparser.ConfigParser):
@ -17,25 +16,6 @@ class GitConfigParser(configparser.ConfigParser):
return False
# class GitOverCdnClientWindows(GitOverCdnClient):
# def update(self, *args, **kwargs):
# Progress.GitInit()
# _ = super().update(*args, **kwargs)
# Progress.GitShowVersion()
# return _
#
# @cached_property
# def latest_commit(self) -> str:
# _ = super().latest_commit
# Progress.GitLatestCommit()
# return _
#
# def download_pack(self):
# _ = super().download_pack()
# Progress.GitDownloadPack()
# return _
class GitManager(DeployConfig):
@staticmethod
def remove(file):
@ -128,18 +108,6 @@ class GitManager(DeployConfig):
self.execute(f'"{self.git}" --no-pager log --no-merges -1')
Progress.GitShowVersion()
# @property
# def goc_client(self):
# client = GitOverCdnClient(
# url='https://vip.123pan.cn/1815343254/pack/LmeSzinc_StarRailCopilot_master',
# folder=self.root_filepath,
# source='origin',
# branch='master',
# git=self.git,
# )
# client.logger = logger
# return client
def git_install(self):
logger.hr('Update Alas', 0)
@ -148,10 +116,6 @@ class GitManager(DeployConfig):
Progress.GitShowVersion()
return
# if self.GitOverCdn:
# if self.goc_client.update(keep_changes=self.KeepLocalChanges):
# return
self.git_repository_init(
repo=self.Repository,
source='origin',

View File

@ -1,266 +0,0 @@
import io
import json
import os
import re
import shutil
import subprocess
import zipfile
from typing import Callable, Generic, TypeVar
import requests
from requests.adapters import HTTPAdapter
T = TypeVar("T")
TEMPLATE_FILE = './config/template.yaml'
class cached_property(Generic[T]):
"""
cached-property from https://github.com/pydanny/cached-property
Add typing support
A property that is only computed once per instance and then replaces itself
with an ordinary attribute. Deleting the attribute resets the property.
Source: https://github.com/bottlepy/bottle/commit/fa7733e075da0d790d809aa3d2f53071897e6f76
"""
def __init__(self, func: Callable[..., T]):
self.func = func
def __get__(self, obj, cls) -> T:
if obj is None:
return self
value = obj.__dict__[self.func.__name__] = self.func(obj)
return value
class PrintLogger:
info = print
warning = print
error = print
@staticmethod
def attr(name, text):
print(f'[{name}] {text}')
class GitOverCdnClient:
logger = PrintLogger()
def __init__(self, url, folder, source='origin', branch='master', git='git'):
"""
Args:
url: http://127.0.0.1:22251/pack/LmeSzinc_AzurLaneAutoScript_master/
folder: D:/AzurLaneAutoScript
"""
self.url = url.strip('/')
self.folder = folder.replace('\\', '/')
self.source = source
self.branch = branch
self.git = git
def filepath(self, path):
path = os.path.join(self.folder, '.git', path)
return os.path.abspath(path).replace('\\', '/')
def urlpath(self, path):
return f'{self.url}{path}'
@cached_property
def current_commit(self) -> str:
for file in [
f'./refs/remotes/{self.source}/{self.branch}',
f'./refs/heads/{self.branch}',
'ORIG_HEAD',
]:
file = self.filepath(file)
try:
with open(file, 'r', encoding='utf-8') as f:
commit = f.read()
res = re.search(r'([0-9a-f]{40})', commit)
if res:
commit = res.group(1)
self.logger.attr('CurrentCommit', commit)
return commit
except FileNotFoundError as e:
self.logger.error(f'Failed to get local commit: {e}')
except Exception as e:
self.logger.error(f'Failed to get local commit: {e}')
return ''
@property
def session(self):
session = requests.Session()
session.trust_env = False
session.mount('http://', HTTPAdapter(max_retries=3))
session.mount('https://', HTTPAdapter(max_retries=3))
return session
@cached_property
def latest_commit(self) -> str:
try:
url = self.urlpath('/latest.json')
self.logger.info(f'Fetch url: {url}')
resp = self.session.get(url, timeout=3)
except Exception as e:
self.logger.error(f'Failed to get remote commit: {e}')
return ''
if resp.status_code == 200:
try:
info = json.loads(resp.text)
commit = info['commit']
self.logger.attr('LatestCommit', commit)
return commit
except json.JSONDecodeError:
self.logger.error(f'Failed to get remote commit, response is not a json: {resp.text}')
return ''
except KeyError:
self.logger.error(f'Failed to get remote commit, key "commit" is not found: {resp.text}')
return ''
else:
self.logger.error(f'Failed to get remote commit, status={resp.status_code}, text={resp.text}')
return ''
def download_pack(self):
try:
url = self.urlpath(f'/{self.latest_commit}/{self.current_commit}.zip')
self.logger.info(f'Fetch url: {url}')
resp = self.session.get(url, timeout=20)
except Exception as e:
self.logger.error(f'Failed to download pack: {e}')
return False
if resp.status_code == 200:
try:
zipped = zipfile.ZipFile(io.BytesIO(resp.content))
for file in [f'pack-{self.latest_commit}.pack', f'pack-{self.latest_commit}.idx']:
self.logger.info(f'Unzip {file}')
member = zipped.getinfo(file)
tmp = self.filepath(f'./objects/pack/{file}.tmp')
out = self.filepath(f'./objects/pack/{file}')
with zipped.open(member) as source, open(tmp, "wb") as target:
shutil.copyfileobj(source, target)
os.replace(tmp, out)
return True
except zipfile.BadZipFile as e:
# File is not a zip file
self.logger.error(e)
return False
except KeyError as e:
# There is no item named 'xxx.idx' in the archive
self.logger.error(e)
return False
except Exception as e:
self.logger.error(e)
return False
elif resp.status_code == 404:
self.logger.error(f'Failed to download pack, status={resp.status_code}, no such pack files provided')
return False
else:
self.logger.error(f'Failed to download pack, status={resp.status_code}, text={resp.text}')
return False
def update_refs(self):
file = self.filepath(f'./refs/remotes/{self.source}/{self.branch}')
text = f'{self.latest_commit}\n'
self.logger.info(f'Update refs: {file}')
os.makedirs(os.path.dirname(file), exist_ok=True)
try:
with open(file, 'w', encoding='utf-8', newline='') as f:
f.write(text)
return True
except FileNotFoundError as e:
self.logger.error(f'Failed to get local commit: {e}')
except Exception as e:
self.logger.error(f'Failed to get local commit: {e}')
return False
def git_command(self, *args, timeout=300):
"""
Execute ADB commands in a subprocess,
usually to be used when pulling or pushing large files.
Args:
timeout (int):
Returns:
str:
"""
os.chdir(self.folder)
cmd = list(map(str, args))
cmd = [self.git] + cmd
self.logger.info(f'Execute: {cmd}')
process = subprocess.Popen(cmd, stdout=subprocess.PIPE, shell=False)
try:
stdout, stderr = process.communicate(timeout=timeout)
except subprocess.TimeoutExpired:
process.kill()
stdout, stderr = process.communicate()
self.logger.warning(f'TimeoutExpired when calling {cmd}, stdout={stdout}, stderr={stderr}')
return stdout.decode()
def git_reset(self, keep_changes=False):
"""
git reset --hard <commit>
"""
if keep_changes:
self.git_command('stash')
self.git_command('reset', '--hard', f'{self.source}/{self.branch}')
self.git_command('stash', 'pop')
else:
self.git_command('reset', '--hard', f'{self.source}/{self.branch}')
def get_status(self):
"""
Returns:
str: 'uptodate' if repo is up-to-date
'behind' if repos is not up-to-date
'failed' if failed
"""
_ = self.current_commit
_ = self.latest_commit
if not self.current_commit:
self.logger.error('Failed to get current commit')
return 'failed'
if not self.latest_commit:
self.logger.error('Failed to get latest commit')
return 'failed'
if self.current_commit == self.latest_commit:
self.logger.info('Already up to date')
return 'uptodate'
self.logger.info('Current repo is behind remote')
return 'behind'
def update(self, keep_changes=False):
"""
Args:
keep_changes:
Returns:
bool: If repo is up-to-date
"""
_ = self.current_commit
_ = self.latest_commit
if not self.current_commit:
self.logger.error('Failed to get current commit')
return False
if not self.latest_commit:
self.logger.error('Failed to get latest commit')
return False
if self.current_commit == self.latest_commit:
self.logger.info('Already up to date')
self.git_reset(keep_changes=keep_changes)
return True
if not self.download_pack():
return False
if not self.update_refs():
return False
self.git_reset(keep_changes=keep_changes)
self.logger.info('Update success')
return True

View File

@ -49,6 +49,7 @@ class UI(MainPage):
self.device.get_orientation()
timeout = Timer(10, count=20).start()
back_timer = Timer(0.5, count=2)
while 1:
if skip_first_screenshot:
skip_first_screenshot = False
@ -76,8 +77,9 @@ class UI(MainPage):
logger.info("Additional ui page handled")
timeout.reset()
continue
logger.info("May be in standby main page")
self.device.click(BACK)
if back_timer.reached_and_reset():
logger.info("Unknown page, try to back")
self.device.click(BACK)
app_check()
minicap_check()

View File

@ -44,14 +44,14 @@ class Cafe(UI):
image = cv2.cvtColor(image, cv2.COLOR_RGB2BGR)
hsv = cv2.cvtColor(image, cv2.COLOR_BGR2HSV)
# set color range
lower_hsv = np.array([17, 200, 220])
upper_hsv = np.array([28, 255, 255])
lower_hsv = np.array([18, 200, 220])
upper_hsv = np.array([30, 255, 255])
# get mask
mask = cv2.inRange(hsv, lower_hsv, upper_hsv)
# generate result
return cv2.bitwise_and(image, image, mask=mask)
def _match_clickable_points(self, image, threshold=0.9):
def _match_clickable_points(self, image, threshold=0.8):
image = cv2.cvtColor(image, cv2.COLOR_BGR2GRAY)
template = self.btn.matched_button.image
template = cv2.cvtColor(template, cv2.COLOR_BGR2GRAY)
@ -60,7 +60,7 @@ class Cafe(UI):
loc = np.where(res >= threshold)
return [point for point in zip(*loc[::-1])]
def _get_clickable_buttons(self, threshold=0.9, offset=(0, 0)):
def _get_clickable_buttons(self, threshold=0.8, offset=(0, 0)):
image = cv2.copyMakeBorder(self.device.image, 20, 20, 10, 60, cv2.BORDER_CONSTANT, value=(0, 0, 0))
image = self._extract_clickable_from_image(image)
points = self._match_clickable_points(image, threshold)
@ -98,6 +98,8 @@ class Cafe(UI):
case 'right':
self.device.swipe_vector(vector_right, box=BOX_CAFE.area, random_range=random_r, padding=5)
self.device.swipe_vector(vector_right, box=BOX_CAFE.area, random_range=random_r, padding=5)
# solve too much swipe causing restart
self.device.click_record_clear()
def _get_reward_num(self):
ocr = Digit(OCR_CAFE)