背景介绍
入职到公司一年多来,公司的业务逐渐步入正轨,定制的产品也是越来越多,从刚开始的基础版本,一直到最近的各种定制包,其中一个项目就有6个定制包,而且定制包还在不断的增加中,从前都是测试手动一个一个打包,打包用的mini本身配置低,打包很慢,打个包运气好等个十几分钟,人要一直守在电脑前,上次上线,测试需要将所有版本先打包出来测试一遍,然后再上传到appstore,就光打包就占用了一上午的时间,还导致测试一个人力的浪费,要是测试出现bug,又要重复上述过>程,而且联想到以后其他项目也有这种情况,所以自动化研发已是必不可少。
研发过程
网上自动化脚本很多,之前使用过一个打包脚本,但是这个打包脚本只能打一个包,可以上传fir测试,但是上传不了appstore,为了解决上面的问题,花了大概一下午的时间,查找资料学习shell脚本语法,在之前脚本的基础上,添加了for循环实现批量打包,同时为了方便测试进行个性化打包,又对脚本进行了优化,实现了执行脚本时 可以选择
- 批量打包上传appstore
- 批量打包上传fir 测试
- 批量打包放到桌面指定文件夹
- 单独打某个定制版的包
废话不多说,直接上脚本,要修改的变量我也在脚本开头单独标出。其他看备注即可。
#! bin/bash
#Author:Bruce http://www.heyuan110.com
#Update Date:2015.06.23
#Use:命令行进入目录直接执行sh Build+DeployToFir.sh即可完成打包发布到fir.im
echo "~~~~~~~~~~~~~~~~开始执行脚本~~~~~~~~~~~~~~~~"
#-------------------------脚本配置信息------------------------------------
beginTime=`date +%s`
DATE=`date '+%Y-%m-%d-%T'`
#需要编译的 targetName数组
array_tagName=(
"SoocQiPei"
"东方瑞艺"
"中程在线"
"智融在线"
"博智教育"
"四海华辰"
"青龙农信"
)
#需要编译的 证书数组
array_profileNames=(
"企培_发布"
"东方瑞艺_发布"
"中程在线_发布"
"e融_发布"
"博智教育_发布"
"四海华辰_发布"
"青龙农信_发布"
)
#生成的ipa包名(上传appstore的ipa包名不允许有中文)
array_ipaName=(
"SoocQiPei"
"dongfangruiyi"
"zhongchengzaixian"
"zhirongzaixian"
"bozhijianyu"
"sihaihuachen"
"qinglongnongxin"
)
#工程名称
PROJECT_NAME="SoocQiPei"
#编译模式 工程默认有 Debug Release
CONFIGURATION_TARGET=Release
#证书名
CODE_SIGN_IDENTITY="iPhone Distribution: xxxxxxx Stock Co., Ltd. (xxxxxxx)"
#苹果账号
AppleID="xxxxxxxxxxxxx"
AppleIDPWD="xxxxxxxxxxx"
#fir账号(自己去fir查看账号的token)
counttoken="xxxxxxxxxxxxxxx"
#fir账号下的appid(每个app有个id)
array_apptokens=(
"xxxxxxxxxxxxxxxxxxxxxxxx" #企培
"xxxxxxxxxxxxxxxxxxxxxxxx" #东方瑞艺
"xxxxxxxxxxxxxxxxxxxxxxxx" #中程在线
"xxxxxxxxxxxxxxxxxxxxxxxx" #e融
"xxxxxxxxxxxxxxxxxxxxxxxx" #博智教育
"xxxxxxxxxxxxxxxxxxxxxxxx" #四海华辰
"xxxxxxxxxxxxxxxxxxxxxxxx" #青龙农信
)
#导出ipa 所需plist
ADHOCExportOptionsPlist=./ADHOCExportOptionsPlist.plist
AppStoreExportOptionsPlist=./AppStoreExportOptionsPlist.plist
#-------------------------------------------------------------------------------------
echo "请选择上传方式:0 批量打包不上传 1 批量打包上传fir 2 批量打包上传appstore 3 单独打包某个版本"
read answer
array_way=(批量打包不上传 批量打包上传fir 批量打包上传appstore 单独打包某个版本)
echo "你的选择是:${array_way[$answer]}"
#定义打包函数 传入两个参数 $1 tagName $2证明文件
function archive(){
echo "tag名称----$1 证明文件是------$2"
#描述文件
PROVISIONING_PROFILE_NAME=$2
#需要编译的 targetName
TARGET_NAME=$1
ipa_name=$3
#编译路径
BUILDPATH=~/Desktop/所有的ipa包
#archivePath
ARCHIVEPATH=${BUILDPATH}/${PROJECT_NAME}.xcarchive
#输出的ipa目录
IPAPATH=~/Desktop/所有的ipa包
echo "~~~~~~~~~~~~~~~~开始编译~~~~~~~~~~~~~~~~~~~"
echo "~~~~~~~~~~~~~~~~开始清理~~~~~~~~~~~~~~~~~~~"
# 清理 避免出现一些莫名的错误
xcodebuild clean -workspace ${PROJECT_NAME}.xcworkspace \
-configuration \
${CONFIGURATION} -alltargets
echo "~~~~~~~~~~~~~~~~开始构建~~~~~~~~~~~~~~~~~~~"
#开始构建
xcodebuild archive -workspace ${PROJECT_NAME}.xcworkspace \
-scheme ${TARGET_NAME} \
-archivePath ${ARCHIVEPATH} \
-configuration ${CONFIGURATION_TARGET} \
CODE_SIGN_IDENTITY="${CODE_SIGN_IDENTITY}" \
PROVISIONING_PROFILE="${PROVISIONING_PROFILE_NAME}"
echo "~~~~~~~~~~~~~~~~检查是否构建成功~~~~~~~~~~~~~~~~~~~"
# xcarchive 实际是一个文件夹不是一个文件所以使用 -d 判断
if [ -d "$ARCHIVEPATH" ]
then
echo "构建成功......"
else
echo "构建失败......"
rm -rf $BUILDPATH
exit 1
fi
endTime=`date +%s`
ArchiveTime="构建时间$[ endTime - beginTime ]秒"
echo "~~~~~~~~~~~~~~~~导出ipa~~~~~~~~~~~~~~~~~~~"
beginTime=`date +%s`
xcodebuild -exportArchive \
-archivePath ${ARCHIVEPATH} \
-exportOptionsPlist ${ExportOptionsPlist} \
-exportPath ${IPAPATH}
echo "~~~~~~~~~~~~~~~~检查是否成功导出 ipa~~~~~~~~~~~~~~~~~~~"
IPAPATH=${IPAPATH}/${TARGET_NAME}.ipa
if [ -f "$IPAPATH" ]
then
echo "导出ipa成功......"
#修改ipa名字
mv ~/Desktop/所有的ipa包/${TARGET_NAME}.ipa ~/Desktop/所有的 ipa包/${ipa_name}.ipa
IPAPATH=~/Desktop/所有的ipa包/${ipa_name}.ipa
else
echo "导出ipa失败......"
# 结束时间
endTime=`date +%s`
echo "$ArchiveTime"
echo "导出ipa时间$[ endTime - beginTime ]秒"
exit 1
fi
endTime=`date +%s`
ExportTime="导出ipa时间$[ endTime - beginTime ]秒"
}
#上传fir的 函数 传两个参数 $1账号token $2 appid
function exportFir(){
export LANG=en_US
export LC_ALL=en_US;
echo "正在上传到fir.im...."
fir p $IPAPATH
changelog=`cat $projectDir/README`
curl -X PUT --data "changelog=$changelog" http://fir.im/api/v2/app/$2?token=$1
echo "\n打包上传更新成功!"
rm -rf $buildAppToDir
rm -rf $projectDir/tmp
}
#上传appstore -------------------------------------------
function exportAppStore(){
#mini的路径
altoolPath="/Applications/Xcode.app/Contents/Applications/Application\ Loader.app/Contents/Frameworks/ITunesSoftwareService.framework/Versions/A/Support/altool"
#我的电脑路径
#altoolPath="/Users/duanshuai/Desktop/Xcode.app/Contents/Applications/Application_Loader.app/Contents/Frameworks/ITunesSoftwareService.framework/Versions/A/Support/altool"
${altoolPath} --validate-app \
-f ${IPAPATH} \
-u ${AppleID} \
-p ${AppleIDPWD} \
-t ios --output-format xml
if [ $? = 0 ]
then
echo "~~~~~~~~~~~~~~~~验证ipa成功~~~~~~~~~~~~~~~~~~~"
"${altoolPath}" --upload-app \
-f ${IPAPATH} \
-u ${AppleID} \
-p ${AppleIDPWD} \
-t ios --output-format xml
if [ $? = 0 ]
then
echo "~~~~~~~~~~~~~~~~提交AppStore成功~~~~~~~~~~~~~~~~~~~"
else
echo "~~~~~~~~~~~~~~~~提交AppStore失败~~~~~~~~~~~~~~~~~~~"
fi
else
echo "~~~~~~~~~~~~~~~~验证ipa失败~~~~~~~~~~~~~~~~~~~"
fi
}
#开始运行脚本
if [ $answer -eq 0 ]
then
# 批量打包 放到桌面
echo "~~~~~~~~~~~~~~~~批量打包 放到桌面~~~~~~~~~~~~~~~~"
ExportOptionsPlist=${ADHOCExportOptionsPlist}
value=0
for tagName in ${array_tagName[@]}
do
archive ${tagName} ${array_profileNames[$value]} $ {array_ipaName[$value]}
let value++
done
elif [ $answer -eq 1 ]
then
#批量打包上传fir
echo "~~~~~~~~~~~~~~~~批量打包上传fir~~~~~~~~~~~~~~~~"
ExportOptionsPlist=${ADHOCExportOptionsPlist}
value=0
for tagName in ${array_tagName[@]}
do
#打包 导出ipa
archive ${tagName} ${array_profileNames[$value]} ${array_ipaName[$value]}
#上传fir
exportFir $counttoken ${array_apptokens[$value]}
let value++
done
elif [ $answer -eq 2 ]
then
#批量打包上传appstore
ExportOptionsPlist=${AppStoreExportOptionsPlist}
for tagName in ${array_tagName[@]}
do
#打包 导出ipa
archive ${tagName} ${array_profileNames[$value]} $ {array_ipaName[$value]}
#上传appstore
exportAppStore
let value++
done
echo "~~~~~~~~~~~~~~~~批量打包上传appstore~~~~~~~~~~~~~~~~"
elif [ $answer -eq 3 ]
then
#选择要打包的tag
ExportOptionsPlist=${ADHOCExportOptionsPlist}
echo "选择要打包的tag:0 SoocQiPei 1 东方瑞艺 2 中程在线 3 智融在线 4 博智教育 5 四海华辰 6 青龙农信/n"
read num
echo "是否上传ifr:1 上传 2 不上传/n"
read isfir
archive ${array_tagName[$num]} ${array_profileNames[$num]} ${array_ipaName[$num]}
if [ $isfir -eq 1 ]
then
#上传fir
exportFir $counttoken ${array_apptokens[$num]}
fi
else
echo "~~~~~~~~~~~~~~~~你选错了~~~~~~~~~~~~~~~~"
fi
使用说明
1 将脚本复制到工程目录
2 将ADHOCExportOptionsPlist.plist和 AppStoreExportOptionsPlist.plist文件也添加到工程目录,两个文件内容最后附加。
3 修改脚本里的配置信息
4 最后cd到工程目录,执行 sh 脚本名.sh
附录
adhoc.plist
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>method</key>
<string>ad-hoc</string>
<key>compileBitcode</key>
<false/>
</dict>
</plist>
appstore.plist
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>method</key>
<string>app-store</string>
<key>compileBitcode</key>
<false/>
<key>uploadSymbols</key>
<true/>
</dict>
</plist>