Skip to content

Instantly share code, notes, and snippets.

@imdong
Last active February 17, 2023 06:35
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 1 You must be signed in to fork a gist
  • Save imdong/f687211bf5ae5cd7cae1b83cebb40567 to your computer and use it in GitHub Desktop.
Save imdong/f687211bf5ae5cd7cae1b83cebb40567 to your computer and use it in GitHub Desktop.
shell Self-decompression、Self-release、Multi-file support, 支持将多个文件打包为一个sh脚本并实现自释放,自解压能力 https://www.qs5.org/Post/729.html
#!/bin/bash
# 如果没有 传递文件夹参数
source_dir=$1
if [ -z "${source_dir}" ]; then
echo "请输入源文件夹路径"
echo "Usage: $0 source_dir"
exit 1
fi
# 需要压缩的文件列表
files=($(ls $source_dir))
# 自释放模板文件
unpack_tpl=./unpack-tpl.sh
# 生成结果
unpack_done=./unpack.sh
# 最终的临时文件
cp "${unpack_tpl}" "${unpack_done}"
# 获取标记行位置
attachment_start_line=($(awk '/^__ARCHIVE_BELOW__/ {; print NR; exit 0;}' "${unpack_done}"))
echo "Attachment Start Line: ${attachment_start_line}"
# 遍历文件获取文件尺寸头信息
file_info=()
for file in ${files[@]}; do
echo -e "File Name: $file,\c"
# 获取文件尺寸
file_size=$(stat -c%s "${source_dir}/$file")
echo -e " File Size: $file_size, File Md5: \c"
# 获取文件 md5
file_md5=$(md5sum "${source_dir}/${file}" | awk '{print $1}')
echo -e "$file_md5\c"
# 记录文件信息
file_info[${#file_info[@]}]="${file},${file_size},${file_md5}"
# 将文件追加到文件后面
echo -e " Packing...\c"
cat "${source_dir}/${file}" >>"${unpack_done}"
echo " Done"
done
# 替换文件列表
echo -e "Save File Info To File...\c"
file_info=$(
IFS=:
echo "${file_info[*]}"
)
sed -i "${attachment_start_line}s/^__ARCHIVE_BELOW__/__ARCHIVE_BELOW__[${file_info}]/" "${unpack_done}"
echo -e "\nBuild Pack Done, File Save To ${unpack_done}"
# 查看结果头信息
# awk '/^__ARCHIVE_BELOW__/ {; print $1; exit 0;}' ./untardone.sh
#!/bin/bash
# 获取解压目录
output_dir=$1
if [ "${output_dir}" == "" ]; then
output_dir=$(mktemp -d)
fi
echo "Output Dir: ${output_dir}"
# 取出附件信息
attachment_info=($(awk '/^__ARCHIVE_BELOW__/ {files=gensub(/.*\[([^]]+)]/,"\\1",1,$0); print NR+1,files;exit 0;}' $0))
# 取出附件开始位置
attachment_start_line=${attachment_info[0]}
echo "Attachment Start Line: ${attachment_start_line}"
# 临时的过度文件
temp_file=$(mktemp)
echo "Unpack Temp File: ${temp_file}"
# 释放文件
tail -n+$attachment_start_line "$0" >${temp_file}
# 取出附件文件列表
attachment_files=(${attachment_info[1]//:/ })
# echo "Attachment Files: ${attachment_files[@]}"
# 获取一个文件信息
getFile() {
# 获取文件信息
file_info=$1
# 拆分结构
file_info=(${file_info//,/ })
# 文件名
file_name="${file_info[0]}"
file_path="${output_dir}/${file_info[0]}"
# 文件尺寸
file_size=${file_info[1]}
# 文件 hash
file_md5=${file_info[2]}
# 调试输出
echo "File Name: ${file_name}, Save Path: ${file_path}, File Size: ${file_size}, File Md5: ${file_md5}"
}
# 以字节为单位读取文件
for file_info in ${attachment_files[@]}; do
# 获取文件信息
getFile $file_info
# 读取文件头一段长度到文件
echo "Read File To ${file_path} ..."
head --bytes=${file_size} ${temp_file} >${file_path}
# 重新计算 文件 md5
echo -e "Calculate File Md5 \c"
file_md5=$(md5sum ${file_path} | awk '{print $1}')
if [ "${file_md5}" != "${file_md5}" ]; then
echo "${file_path} Error"
else
echo "${file_md5} Success"
fi
# 重置临时文件
echo "Reset Temp File ..."
file_size=$(($file_size + 1))
tail --bytes=+${file_size} ${temp_file} >"${temp_file}2"
rm -rf ${temp_file}
mv "${temp_file}2" ${temp_file}
done
# 删除临时文件
rm -rf ${temp_file}
###### 用户的自定义代码 开始 ######
#
# 文件释放后,并没有解压功能,需要自己打包时带上解压程序,并自己在下面调用程序解压
# After the file is released, there is no decompression function.
# You need to take the decompression program with you when you pack it,
# and call the program below to extract it.
#
# 以下为示例代码 The following is the sample code
# 进入临时文件夹
cd $output_dir
# 安装 tar
rpm -ivh --nodeps --force tar-1.30-5.an8.x86_64.rpm
# 解压出文件
echo "Untar ..."
tar -xvf *.tar.gz
# 执行安装脚本
echo "Sleep 10s, Execute Install Script ..."
sleep 10s
chmod +x *.sh
./install.sh
###### 用户的自定义代码 结束 以下勿动 ######
exit 0
__ARCHIVE_BELOW__
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment