mirror of
https://github.com/rustdesk/rustdesk.git
synced 2024-12-02 18:59:24 +08:00
89 lines
3.1 KiB
Python
89 lines
3.1 KiB
Python
|
from ast import parse
|
||
|
import os
|
||
|
import optparse
|
||
|
from hashlib import md5
|
||
|
import brotli
|
||
|
|
||
|
# file compress level(0-11)
|
||
|
compress_level = 11
|
||
|
# 4GB maximum
|
||
|
length_count = 4
|
||
|
# encoding
|
||
|
encoding = 'utf-8'
|
||
|
|
||
|
# output: {path: (compressed_data, file_md5)}
|
||
|
|
||
|
|
||
|
def generate_md5_table(folder: str) -> dict:
|
||
|
res: dict = dict()
|
||
|
curdir = os.curdir
|
||
|
os.chdir(folder)
|
||
|
for root, _, files in os.walk('.'):
|
||
|
# remove ./
|
||
|
for f in files:
|
||
|
md5_generator = md5()
|
||
|
full_path = os.path.join(root, f)
|
||
|
print(f"processing {full_path}...")
|
||
|
f = open(full_path, "rb")
|
||
|
content = f.read()
|
||
|
content_compressed = brotli.compress(
|
||
|
content, quality=compress_level)
|
||
|
md5_generator.update(content)
|
||
|
md5_code = md5_generator.hexdigest().encode(encoding=encoding)
|
||
|
res[full_path] = (content_compressed, md5_code)
|
||
|
os.chdir(curdir)
|
||
|
return res
|
||
|
|
||
|
|
||
|
def write_metadata(md5_table: dict, output_folder: str, exe: str):
|
||
|
output_path = os.path.join(output_folder, "data.bin")
|
||
|
with open(output_path, "wb") as f:
|
||
|
f.write("rustdesk".encode(encoding=encoding))
|
||
|
for path in md5_table.keys():
|
||
|
(compressed_data, md5_code) = md5_table[path]
|
||
|
data_length = len(compressed_data)
|
||
|
path = path.encode(encoding=encoding)
|
||
|
# path length & path
|
||
|
f.write((len(path)).to_bytes(length=length_count, byteorder='big'))
|
||
|
f.write(path)
|
||
|
# data length & compressed data
|
||
|
f.write((data_length).to_bytes(
|
||
|
length=length_count, byteorder='big'))
|
||
|
f.write(compressed_data)
|
||
|
# md5 code
|
||
|
f.write(md5_code)
|
||
|
# end
|
||
|
f.write("rustdesk".encode(encoding=encoding))
|
||
|
# executable
|
||
|
f.write(exe.encode(encoding='utf-8'))
|
||
|
print(f"metadata had written to {output_path}")
|
||
|
|
||
|
|
||
|
def build_portable(output_folder: str):
|
||
|
os.chdir(output_folder)
|
||
|
os.system("cargo build --release")
|
||
|
|
||
|
# Linux: python3 generate.py -f ../rustdesk-portable-packer/test -o . -e ./test/main.py
|
||
|
# Windows: python3 .\generate.py -f ..\rustdesk\flutter\build\windows\runner\Debug\ -o . -e ..\rustdesk\flutter\build\windows\runner\Debug\rustdesk.exe
|
||
|
if __name__ == '__main__':
|
||
|
parser = optparse.OptionParser()
|
||
|
parser.add_option("-f", "--folder", dest="folder",
|
||
|
help="folder to compress")
|
||
|
parser.add_option("-o", "--output", dest="output_folder",
|
||
|
help="the root of portable packer project")
|
||
|
parser.add_option("-e", "--executable", dest="executable",
|
||
|
help="specify startup file")
|
||
|
(options, args) = parser.parse_args()
|
||
|
folder = options.folder
|
||
|
output_folder = os.path.abspath(options.output_folder)
|
||
|
|
||
|
exe: str = os.path.abspath(options.executable)
|
||
|
if not exe.startswith(os.path.abspath(folder)):
|
||
|
print("the executable must locate in source folder")
|
||
|
exit(-1)
|
||
|
exe = '.' + exe[len(os.path.abspath(folder)):]
|
||
|
print("executable path: " + exe)
|
||
|
md5_table = generate_md5_table(folder)
|
||
|
write_metadata(md5_table, output_folder, exe)
|
||
|
build_portable(output_folder)
|