完成优化
This commit is contained in:
Submodule Convention updated: 61df36626c...59dfd08c54
77
app.py
77
app.py
@@ -1,11 +1,11 @@
|
|||||||
from Convention.Convention.Runtime.GlobalConfig import *
|
from Convention.Convention.Runtime.GlobalConfig import *
|
||||||
from Convention.Convention.Runtime.File import *
|
from Convention.Convention.Runtime.File import *
|
||||||
from Convention.Convention.Runtime.String import GetEditorDistanceAndOperations, FillString
|
from Convention.Convention.Runtime.String import GetDiffOperations, FillString
|
||||||
|
|
||||||
import argparse
|
import argparse
|
||||||
from pydantic import BaseModel
|
from pydantic import BaseModel
|
||||||
import hashlib
|
import hashlib
|
||||||
import json
|
import pickle
|
||||||
|
|
||||||
class HistoryBlock(BaseModel):
|
class HistoryBlock(BaseModel):
|
||||||
mode: Literal["add","delete"] = "add"
|
mode: Literal["add","delete"] = "add"
|
||||||
@@ -13,6 +13,14 @@ class HistoryBlock(BaseModel):
|
|||||||
end: int = 0
|
end: int = 0
|
||||||
content: str = ""
|
content: str = ""
|
||||||
|
|
||||||
|
def ToOperation(self) -> Tuple[Literal["add","delete"], int, int, str]:
|
||||||
|
return (self.mode, self.begin, self.end, self.content)
|
||||||
|
def FromOperation(self, operation:Tuple[Literal["add","delete"], int, int, str]) -> None:
|
||||||
|
self.mode = operation[0]
|
||||||
|
self.begin = operation[1]
|
||||||
|
self.end = operation[2]
|
||||||
|
self.content = operation[3]
|
||||||
|
|
||||||
class HistoryObject(BaseModel):
|
class HistoryObject(BaseModel):
|
||||||
hashcode: str = ""
|
hashcode: str = ""
|
||||||
blocks: List[HistoryBlock] = []
|
blocks: List[HistoryBlock] = []
|
||||||
@@ -21,7 +29,8 @@ class HistoryCommit:
|
|||||||
def __init__(self, object_chain:List[HistoryObject]) -> None:
|
def __init__(self, object_chain:List[HistoryObject]) -> None:
|
||||||
self.content = ""
|
self.content = ""
|
||||||
for item in object_chain:
|
for item in object_chain:
|
||||||
for block in item.blocks:
|
# 从后往前应用操作,因为操作使用的是静态坐标系(基于原始字符串)
|
||||||
|
for block in reversed(item.blocks):
|
||||||
if block.mode == "add":
|
if block.mode == "add":
|
||||||
self.content = self.content[:block.begin] + block.content + self.content[block.end:]
|
self.content = self.content[:block.begin] + block.content + self.content[block.end:]
|
||||||
elif block.mode == "delete":
|
elif block.mode == "delete":
|
||||||
@@ -54,7 +63,7 @@ class HistoryModel(BaseModel):
|
|||||||
current_commit_file_path = commit_name
|
current_commit_file_path = commit_name
|
||||||
while current_commit_file_path is not None:
|
while current_commit_file_path is not None:
|
||||||
current_commit_file = parent_path|current_commit_file_path
|
current_commit_file = parent_path|current_commit_file_path
|
||||||
node = HistoryObject.model_validate_json(current_commit_file.LoadAsText())
|
node = pickle.loads(current_commit_file.LoadAsBinary())
|
||||||
object_chain.append(node)
|
object_chain.append(node)
|
||||||
current_commit_file_path = self.obj_paths[current_commit_file_path]
|
current_commit_file_path = self.obj_paths[current_commit_file_path]
|
||||||
# 反转链
|
# 反转链
|
||||||
@@ -139,22 +148,13 @@ class Cli:
|
|||||||
|
|
||||||
self.historys_file = self.config.GetFile(history_file if history_file is not None else break_down_path(self.file.GetAbsPath())|"history", False)
|
self.historys_file = self.config.GetFile(history_file if history_file is not None else break_down_path(self.file.GetAbsPath())|"history", False)
|
||||||
if self.historys_file.Exists():
|
if self.historys_file.Exists():
|
||||||
self.historys = HistoryModel.model_validate_json(self.historys_file.LoadAsText())
|
self.historys = pickle.loads(self.historys_file.LoadAsBinary())
|
||||||
else:
|
else:
|
||||||
self.historys = HistoryModel()
|
self.historys = HistoryModel()
|
||||||
|
|
||||||
self.prints: str = ""
|
self.prints: str = ""
|
||||||
|
|
||||||
def compare(self) -> None:
|
def show_compare_result(self, head_commit:str, operations:List[Tuple[Literal["add","delete"], int, int, str]]) -> None:
|
||||||
if self.branch not in self.historys.branches:
|
|
||||||
self.config.Log("Error", f"Branch {self.branch} not found")
|
|
||||||
return
|
|
||||||
head_commit = str(self.historys.ReadBranchHeadCommit(self.branch, self.historys_file.GetDirToolFile()))
|
|
||||||
current_content = self.file.LoadAsText()
|
|
||||||
step, operations = GetEditorDistanceAndOperations(head_commit, current_content)
|
|
||||||
if step == 0:
|
|
||||||
PrintColorful(ConsoleFrontColor.LIGHTMAGENTA_EX, "No changes")
|
|
||||||
return
|
|
||||||
index = 0
|
index = 0
|
||||||
for operation in operations:
|
for operation in operations:
|
||||||
# 显示操作前的不变内容
|
# 显示操作前的不变内容
|
||||||
@@ -162,14 +162,14 @@ class Cli:
|
|||||||
|
|
||||||
if operation[0] == "add":
|
if operation[0] == "add":
|
||||||
color = ConsoleFrontColor.GREEN
|
color = ConsoleFrontColor.GREEN
|
||||||
eline = "[>>>]"
|
eline = f"{ConsoleBackgroundColor.LIGHTGREEN_EX} {ConsoleBackgroundColor.RESET}"
|
||||||
etab = "[>>]"
|
etab = f"{ConsoleBackgroundColor.GREEN}\t{ConsoleBackgroundColor.RESET}"
|
||||||
ewrite = "[>]"
|
ewrite = f"{ConsoleBackgroundColor.GREEN} {ConsoleBackgroundColor.RESET}"
|
||||||
elif operation[0] == "delete":
|
elif operation[0] == "delete":
|
||||||
color = ConsoleFrontColor.RED
|
color = ConsoleFrontColor.RED
|
||||||
eline = "[<<<]"
|
eline = f"{ConsoleBackgroundColor.LIGHTRED_EX} {ConsoleBackgroundColor.RESET}"
|
||||||
etab = "[<<]"
|
etab = f"{ConsoleBackgroundColor.RED}\t{ConsoleBackgroundColor.RESET}"
|
||||||
ewrite = "[<]"
|
ewrite = f"{ConsoleBackgroundColor.RED} {ConsoleBackgroundColor.RESET}"
|
||||||
else:
|
else:
|
||||||
raise ValueError(f"Invalid operation: {operation}")
|
raise ValueError(f"Invalid operation: {operation}")
|
||||||
|
|
||||||
@@ -188,6 +188,20 @@ class Cli:
|
|||||||
self.print(head_commit[index:])
|
self.print(head_commit[index:])
|
||||||
self.print_out()
|
self.print_out()
|
||||||
|
|
||||||
|
|
||||||
|
def compare(self) -> None:
|
||||||
|
if self.branch not in self.historys.branches:
|
||||||
|
self.config.Log("Error", f"Branch {self.branch} not found")
|
||||||
|
return
|
||||||
|
head_commit = str(self.historys.ReadBranchHeadCommit(self.branch, self.historys_file.GetDirToolFile()))
|
||||||
|
current_content = self.file.LoadAsText()
|
||||||
|
operations = GetDiffOperations(head_commit, current_content)
|
||||||
|
if len(operations) == 0:
|
||||||
|
PrintColorful(ConsoleFrontColor.LIGHTMAGENTA_EX, "No changes")
|
||||||
|
return
|
||||||
|
|
||||||
|
self.show_compare_result(head_commit, operations)
|
||||||
|
|
||||||
if self.verbose:
|
if self.verbose:
|
||||||
PrintColorful(ConsoleFrontColor.LIGHTMAGENTA_EX, "\noperations:")
|
PrintColorful(ConsoleFrontColor.LIGHTMAGENTA_EX, "\noperations:")
|
||||||
print(f"{'\n'.join([f"{ConsoleFrontColor.GREEN if item[0] == "add" else ConsoleFrontColor.RED}{item[0]}{ConsoleFrontColor.RESET} \"{ConsoleFrontColor.YELLOW}{item[3]}{ConsoleFrontColor.RESET}\" on [{item[1]},{item[2]}]" for item in operations])}")
|
print(f"{'\n'.join([f"{ConsoleFrontColor.GREEN if item[0] == "add" else ConsoleFrontColor.RED}{item[0]}{ConsoleFrontColor.RESET} \"{ConsoleFrontColor.YELLOW}{item[3]}{ConsoleFrontColor.RESET}\" on [{item[1]},{item[2]}]" for item in operations])}")
|
||||||
@@ -206,7 +220,7 @@ class Cli:
|
|||||||
PrintColorful(ConsoleFrontColor.LIGHTMAGENTA_EX, "\nAll content is new")
|
PrintColorful(ConsoleFrontColor.LIGHTMAGENTA_EX, "\nAll content is new")
|
||||||
else:
|
else:
|
||||||
head_commit = str(self.historys.ReadBranchHeadCommit(self.branch, self.historys_file.GetDirToolFile()))
|
head_commit = str(self.historys.ReadBranchHeadCommit(self.branch, self.historys_file.GetDirToolFile()))
|
||||||
step, operations = GetEditorDistanceAndOperations(head_commit, content)
|
operations = GetDiffOperations(head_commit, content)
|
||||||
for operation in operations:
|
for operation in operations:
|
||||||
if operation[0] == "add":
|
if operation[0] == "add":
|
||||||
root.blocks.append(HistoryBlock(mode="add",begin=operation[1],end=operation[2],content=operation[3]))
|
root.blocks.append(HistoryBlock(mode="add",begin=operation[1],end=operation[2],content=operation[3]))
|
||||||
@@ -221,8 +235,8 @@ class Cli:
|
|||||||
# 创建树节点, 并链接
|
# 创建树节点, 并链接
|
||||||
self.historys.obj_paths[commit_name] = self.historys.branches[self.branch]
|
self.historys.obj_paths[commit_name] = self.historys.branches[self.branch]
|
||||||
self.historys.branches[self.branch] = commit_name
|
self.historys.branches[self.branch] = commit_name
|
||||||
(self.historys_file.GetDirToolFile()|commit_name).SaveAsText(root.model_dump_json())
|
(self.historys_file.GetDirToolFile()|commit_name).SaveAsBinary(pickle.dumps(root))
|
||||||
(self.historys_file).SaveAsText(self.historys.model_dump_json())
|
(self.historys_file).SaveAsBinary(pickle.dumps(self.historys))
|
||||||
|
|
||||||
def view(self, commit_name:Optional[str]=None) -> None:
|
def view(self, commit_name:Optional[str]=None) -> None:
|
||||||
if commit_name is None or commit_name == "":
|
if commit_name is None or commit_name == "":
|
||||||
@@ -235,10 +249,15 @@ class Cli:
|
|||||||
def restore(self) -> None:
|
def restore(self) -> None:
|
||||||
head_commit = str(self.historys.ReadBranchHeadCommit(self.branch, self.historys_file.GetDirToolFile()))
|
head_commit = str(self.historys.ReadBranchHeadCommit(self.branch, self.historys_file.GetDirToolFile()))
|
||||||
self.file.SaveAsText(head_commit)
|
self.file.SaveAsText(head_commit)
|
||||||
|
PrintColorful(ConsoleFrontColor.LIGHTMAGENTA_EX, f"\nRestored {self.file.GetAbsPath()}")
|
||||||
|
|
||||||
def take(self, commit_name:str) -> None:
|
def take(self, commit_name:Optional[str]=None) -> None:
|
||||||
commit = self.historys.ReadCommit(commit_name, self.historys_file.GetDirToolFile())
|
if commit_name is None or commit_name == "":
|
||||||
self.file.SaveAsText(commit.content)
|
head_commit = str(self.historys.ReadBranchHeadCommit(self.branch, self.historys_file.GetDirToolFile()))
|
||||||
|
else:
|
||||||
|
head_commit = str(self.historys.ReadCommit(commit_name, self.historys_file.GetDirToolFile()))
|
||||||
|
self.file.SaveAsText(head_commit)
|
||||||
|
PrintColorful(ConsoleFrontColor.LIGHTMAGENTA_EX, f"\nTaken {self.file} to commit {"head" if commit_name is None or commit_name == "" else commit_name}")
|
||||||
|
|
||||||
def run() -> int:
|
def run() -> int:
|
||||||
parser = argparse.ArgumentParser()
|
parser = argparse.ArgumentParser()
|
||||||
@@ -278,7 +297,7 @@ def run() -> int:
|
|||||||
cli.save()
|
cli.save()
|
||||||
return 0
|
return 0
|
||||||
# 查看记录内容
|
# 查看记录内容
|
||||||
elif "view" in args:
|
elif args.view is not None:
|
||||||
cli.view(args.view)
|
cli.view(args.view)
|
||||||
return 0
|
return 0
|
||||||
# 恢复
|
# 恢复
|
||||||
@@ -286,7 +305,7 @@ def run() -> int:
|
|||||||
cli.restore()
|
cli.restore()
|
||||||
return 0
|
return 0
|
||||||
# 获取指定提交的文件
|
# 获取指定提交的文件
|
||||||
elif "take" in args:
|
elif args.take is not None:
|
||||||
cli.take(args.take)
|
cli.take(args.take)
|
||||||
return 0
|
return 0
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user