fix crash

This commit is contained in:
shenjack 2022-11-20 17:46:02 +08:00
parent 0203253cc9
commit 052dada1f5
3 changed files with 81 additions and 63 deletions

View File

@ -11,7 +11,6 @@ github: @shenjackyuanjie
gitee: @shenjackyuanjie
"""
from typing import Any, Dict, Callable, Union, Tuple, List, get_type_hints, Type
from Difficult_Rocket.utils.typings import Options
@ -26,6 +25,7 @@ class DR_option(Options):
"""
DR 的整体配置存储类
"""
name = 'DR Option'
# runtime options
InputBox_use_TextEntry: bool = False
record_threads: bool = True
@ -42,6 +42,7 @@ class _DR_runtime(Options):
"""
DR 的运行时配置
"""
name = 'DR Runtime'
# game statue
DR_version: Version = game_version
@ -74,7 +75,7 @@ class _DR_runtime(Options):
_DR_runtime.add_option('language', _DR_runtime.language)
# DR_option = _DR_option()
DR_option = DR_option()
DR_runtime = _DR_runtime()
if DR_option.playing:

View File

@ -11,8 +11,8 @@ github: @shenjackyuanjie
gitee: @shenjackyuanjie
"""
import io
import os
import sys
import time
import platform
import traceback
@ -72,7 +72,7 @@ def to_code(string: str):
def write_markdown_tablet(crash_file: TextIO, tablet: list) -> None:
a_len, b_len, c_len = tablet[0]
a_len, b_len, c_len = tablet[1:4]
...
@ -82,70 +82,74 @@ def create_crash_report(info: str = None) -> None:
os.mkdir('./crash_report')
date_time = time.strftime('%Y-%m-%d %H-%M-%S', time.gmtime(time.time()))
filename = 'crash-{}.md'.format(date_time)
with open('./crash_report/{}'.format(filename), 'w+', encoding='utf-8') as crash_file:
cache_stream = io.StringIO()
try:
# 开头信息
crash_file.write(Head_message.format(now_time=time.strftime('%Y/%m/%d %H:%M:%S', time.gmtime(time.time()))))
cache_stream.write(Head_message.format(now_time=time.strftime('%Y/%m/%d %H:%M:%S', time.gmtime(time.time()))))
# 崩溃信息
crash_file.write(crash_info)
cache_stream.write(crash_info)
# 运行状态信息
from Difficult_Rocket import DR_option, DR_runtime
crash_file.write(Run_message)
cache_stream.write(Run_message)
crash_file.write(markdown_line_handler(f'DR Version: {Difficult_Rocket.game_version}', level=1))
crash_file.write(markdown_line_handler(f'DR language: {DR_runtime.language}', level=1))
crash_file.write(markdown_line_handler(f'Running Dir: {os.path.abspath(os.curdir)}', level=1))
cache_stream.write(markdown_line_handler(f'DR Version: {Difficult_Rocket.game_version}', level=1))
cache_stream.write(markdown_line_handler(f'DR language: {DR_runtime.language}', level=1))
cache_stream.write(markdown_line_handler(f'Running Dir: {os.path.abspath(os.curdir)}', level=1))
option_with_len = DR_runtime.option_with_len()
option_with_len[1] = max(option_with_len[1], 6)
option_with_len[2] = max(option_with_len[2], 5)
option_with_len[3] = max(option_with_len[3], 10)
crash_file.write(f'\n| Option{" " * (option_with_len[1] - 4)} | Value{" " * (option_with_len[2] - 3)} | Value Type{" " * (option_with_len[3] - 8)} |\n')
crash_file.write(f'|:{"-" * (option_with_len[1] + 3)}|:{"-" * (option_with_len[2] + 3)}|:{"-" * (option_with_len[3] + 3)}|\n')
cache_stream.write(f'\n| Option{" " * (option_with_len[1] - 4)} | Value{" " * (option_with_len[2] - 3)} | Value Type{" " * (option_with_len[3] - 8)} |\n')
cache_stream.write(f'|:{"-" * (option_with_len[1] + 3)}|:{"-" * (option_with_len[2] + 3)}|:{"-" * (option_with_len[3] + 3)}|\n')
for a, b, c in option_with_len[0]:
b, c = str(b), str(c)
crash_file.write(f'| `{a}`{" " * (option_with_len[1] - len(a))} | `{b}`{" " * (option_with_len[2] - len(b))} | `{c}`{" " * (option_with_len[3] - len(c))} |\n')
cache_stream.write(f'| `{a}`{" " * (option_with_len[1] - len(a))} | `{b}`{" " * (option_with_len[2] - len(b))} | `{c}`{" " * (option_with_len[3] - len(c))} |\n')
# # DR 的游戏设置
crash_file.write(DR_configs)
cache_stream.write(DR_configs)
option_with_len = DR_option.option_with_len()
option_with_len[1] = max(option_with_len[1], 6)
option_with_len[2] = max(option_with_len[2], 5)
option_with_len[3] = max(option_with_len[3], 10)
crash_file.write(f'| Option{" " * (option_with_len[1] - 4)} | Value{" " * (option_with_len[2] - 3)} | Value Type{" " * (option_with_len[3] - 8)} |\n')
crash_file.write(f'|:{"-" * (option_with_len[1] + 3)}|:{"-" * (option_with_len[2] + 3)}|:{"-" * (option_with_len[3] + 3)}|\n')
cache_stream.write(f'| Option{" " * (option_with_len[1] - 4)} | Value{" " * (option_with_len[2] - 3)} | Value Type{" " * (option_with_len[3] - 8)} |\n')
cache_stream.write(f'|:{"-" * (option_with_len[1] + 3)}|:{"-" * (option_with_len[2] + 3)}|:{"-" * (option_with_len[3] + 3)}|\n')
for a, b, c in option_with_len[0]:
b, c = str(b), str(c)
crash_file.write(f'| `{a}`{" " * (option_with_len[1] - len(a))} | `{b}`{" " * (option_with_len[2] - len(b))} | `{c}`{" " * (option_with_len[3] - len(c))} |\n')
cache_stream.write(f'| `{a}`{" " * (option_with_len[1] - len(a))} | `{b}`{" " * (option_with_len[2] - len(b))} | `{c}`{" " * (option_with_len[3] - len(c))} |\n')
# 多进程信息
crash_file.write(Process_message)
cache_stream.write(Process_message)
for process in all_process:
process: multiprocessing.Process
crash_file.write(markdown_line_handler(f'{process.name}', code=True))
crash_file.write(markdown_line_handler(f'Ident: {process.ident}', level=2))
crash_file.write(markdown_line_handler(f'Running: {process.is_alive()}', level=2))
cache_stream.write(markdown_line_handler(f'{process.name}', code=True))
cache_stream.write(markdown_line_handler(f'Ident: {process.ident}', level=2))
cache_stream.write(markdown_line_handler(f'Running: {process.is_alive()}', level=2))
# 运行线程信息
crash_file.write(Thread_message)
cache_stream.write(Thread_message)
for thread in all_thread:
thread: threading.Thread
crash_file.write(markdown_line_handler(f'{thread.name}', code=True))
crash_file.write(markdown_line_handler(f'order: {all_thread.index(thread)}', level=2))
crash_file.write(markdown_line_handler(f'Ident: {thread.ident}', level=2))
crash_file.write(markdown_line_handler(f'Daemon: {thread.daemon}', level=2))
crash_file.write(markdown_line_handler(f'Running: {thread.is_alive()}', level=2))
cache_stream.write(markdown_line_handler(f'{thread.name}', code=True))
cache_stream.write(markdown_line_handler(f'order: {all_thread.index(thread)}', level=2))
cache_stream.write(markdown_line_handler(f'Ident: {thread.ident}', level=2))
cache_stream.write(markdown_line_handler(f'Daemon: {thread.daemon}', level=2))
cache_stream.write(markdown_line_handler(f'Running: {thread.is_alive()}', level=2))
# Python 信息
crash_file.write(Python_message)
crash_file.write(markdown_line_handler(f'Version: {to_code(platform.python_version())}', level=1))
crash_file.write(markdown_line_handler(f'Branch: {to_code(platform.python_branch())}', level=1))
# crash_file.write(markdown_line_handler(f'Build: {platform.python_implementation()}', code=True, level=1))
crash_file.write(markdown_line_handler(f'Implementation: {to_code(platform.python_implementation())}', level=1))
crash_file.write(markdown_line_handler(f'Compiler: {to_code(platform.python_compiler())}', level=1))
cache_stream.write(Python_message)
cache_stream.write(markdown_line_handler(f'Version: {to_code(platform.python_version())}', level=1))
cache_stream.write(markdown_line_handler(f'Branch: {to_code(platform.python_branch())}', level=1))
cache_stream.write(markdown_line_handler(f'Implementation: {to_code(platform.python_implementation())}', level=1))
cache_stream.write(markdown_line_handler(f'Compiler: {to_code(platform.python_compiler())}', level=1))
# 电脑系统信息
crash_file.write(System_message)
crash_file.write(markdown_line_handler(f'System: {to_code(platform.platform())}', level=1))
crash_file.write(markdown_line_handler(f'Computer name: {to_code(platform.node())}', level=1))
crash_file.write(markdown_line_handler(f'machine: {to_code(platform.machine())}', level=1))
crash_file.write(markdown_line_handler(f'processor: {to_code(platform.processor())}', level=1))
crash_file.write(markdown_line_handler(f'release: {to_code(platform.release())}', level=1))
crash_file.write(markdown_line_handler(f'version: {to_code(platform.version())}', level=1))
cache_stream.write(System_message)
cache_stream.write(markdown_line_handler(f'System: {to_code(platform.platform())}', level=1))
cache_stream.write(markdown_line_handler(f'Computer name: {to_code(platform.node())}', level=1))
cache_stream.write(markdown_line_handler(f'machine: {to_code(platform.machine())}', level=1))
cache_stream.write(markdown_line_handler(f'processor: {to_code(platform.processor())}', level=1))
cache_stream.write(markdown_line_handler(f'release: {to_code(platform.release())}', level=1))
cache_stream.write(markdown_line_handler(f'version: {to_code(platform.version())}', level=1))
finally:
get_cache = cache_stream.getvalue()
with open('./crash_report/{}'.format(filename), 'w+', encoding='utf-8') as crash_file:
crash_file.write(get_cache)
if __name__ == '__main__':

View File

@ -14,58 +14,69 @@ def get_type_hints_(cls: Type):
return get_type_hints(cls, globalns={})
class OptionNameNotDefined(Exception):
"""向初始化的 option 里添加了一个不存在于选项里的选项"""
class OptionsError(Exception):
""" option 的错误基类"""
class OptionNameNotDefined(OptionsError):
""" 向初始化的 option 里添加了一个不存在于选项里的选项 """
class OptionNotFound(OptionsError):
""" 某个选项没有找到 """
class Options:
"""
Difficult Rocket 的游戏配置的存储基类
"""
__options: Dict[str, Union[Callable, object]] = {}
name = 'Option Base'
cached_options: Dict[str, Union[str, Any]] = {}
def __init__(self, **kwargs):
self.flush_option()
for option, value in kwargs.items():
if option not in self.option():
if option not in self.cached_options:
raise OptionNameNotDefined(f"option: {option} with value: {value} is not defined")
setattr(self, option, value)
self.flush_option()
@classmethod
def option(cls) -> Dict[str, Any]:
def option(self) -> Dict[str, Any]:
"""
获取配置类的所有配置
:return: 自己的所有配置
"""
values = {}
for ann in cls.__annotations__: # 获取类型注释
values[ann] = getattr(cls, ann, None)
for ann in self.__annotations__: # 获取类型注释
values[ann] = getattr(self, ann, None)
if values[ann] is None:
values[ann] = cls.__annotations__[ann]
values[ann] = self.__annotations__[ann]
for option, a_fun in cls.__options.items(): # 获取额外内容
if not hasattr(self, 'options'):
self.options: Dict[str, Union[Callable, object]] = {}
for option, a_fun in self.options.items(): # 获取额外内容
values[option] = a_fun
for option, a_fun in values.items(): # 检查是否为 property
if a_fun is bool and getattr(cls, option, None) is not None:
if a_fun is bool and getattr(self, option, None) is not None:
values[option] = False
if isinstance(a_fun, property):
values[option] = getattr(cls, option)
try:
values[option] = getattr(self, option)
except AttributeError as e:
raise OptionNotFound(f'Option {option} is not found in {self.name}')
return values
@classmethod
def flush_option(cls) -> Dict[str, Any]:
def flush_option(self) -> Dict[str, Any]:
"""
刷新缓存 options 的内容
:return: 刷新过的 options
"""
cls.cached_options = cls.option()
return cls.cached_options
self.cached_options = self.option()
return self.cached_options
@classmethod
def option_with_len(cls) -> List[Union[List[Tuple[str, Any, Any]], int, Any]]:
options = cls.flush_option()
def option_with_len(self) -> List[Union[List[Tuple[str, Any, Any]], int, Any]]:
options = self.flush_option()
max_len_key = 1
max_len_value = 1
max_len_value_t = 1
@ -79,6 +90,8 @@ class Options:
return [option_list, max_len_key, max_len_value, max_len_value_t]
@classmethod
def add_option(cls, name, value: Union[Callable, object]) -> Dict:
cls.__options[name] = value
return cls.__options
def add_option(cls, name: str, value: Union[Callable, object]) -> Dict:
if not hasattr(cls, 'options'):
cls.options: Dict[str, Union[Callable, object]] = {}
cls.options[name] = value
return cls.options