前言
由于工作需要,需要将定义好的多个proto文件合并为一个,然后调用python脚本生成cpp文件,鉴于大家都工作在windows环境下,而且该需求定制化不高,所以考虑直接使用PowerShell脚本来做。这也是笔者第一次使用PowerShell来解决实际应用问题,是一次比较好的实践,下边贴出来具体的脚本代码,以供参考及记录。
######################### 使用方法 ##################################
# 1. 允许执行本地脚本 策略,以管理员身份打开一个PowerShell窗口并执行以下命令:
# Set-ExecutionPolicy RemoteSigned
# 2. 执行本脚本:
# ./batch.ps1
#########################################################################
$currLocation = Get-Location
Push-Location
$targetPath = $args[0];
if(($targetPath -eq "") -or ($targetPath -eq $null)){
Write-Host "use default path ./.proto"
$targetPath = "./.proto";
}
Set-Location -Path $targetPath;
# 中间文件
$metadataFile = "./_metadataTmp.txt";
$allInOneFile = "./_protoTmp.txt";
$defaltEncodingFile = "./_encodingTmp.txt";
# 最终文件
$targetFile = "./one.proto";
$keywordMatchReg = "syntax|package|option|import.*proto.*";
# 删除上次的生成文件
if((Test-Path $targetFile) -eq "True"){
Remove-Item $targetFile;
}
# 处理所有proto文件
$allFile = Get-ChildItem -recurse *.proto;
foreach($file in $allFile) {
#Write-Host $file.name;
$newFileReader = New-Object System.IO.StreamReader($file);
while($null -ne ($eachLine = $newFileReader.ReadLine())){
if($eachLine -match $keywordMatchReg){
# 元数据单独写文件
#Write-Host " $eachLine"
write-output $eachLine >> $metadataFile ;
}else{
# 定义数据写proto文件
write-output $eachLine >> $allInOneFile ;
}
#Write-Host " $eachLine"
}
$newFileReader.Dispose();
}
# 合并数据,写入基础信息
write-output 'syntax = "proto3";' >> $defaltEncodingFile ;
# 合并元数据
foreach($line in Get-Content $metadataFile|Sort-Object -unique){
#Write-Host "line: $line"
if($line -match 'import.*google.*protobuf.*\.proto'){
write-output $line >> $defaltEncodingFile ;
continue;
}
if(($line -notmatch 'syntax.*') -and ($line -notmatch 'import.*')){
write-output $line >> $defaltEncodingFile ;
#Write-Host "filter: $line"
}
}
# 合并消息定义
foreach($line in Get-Content $allInOneFile){
write-output $line >> $defaltEncodingFile ;
}
# 转换编码
Get-Content $defaltEncodingFile|Set-Content $targetFile -Encoding UTF8
# 删除中间文件
Remove-Item $metadataFile
Remove-Item $allInOneFile
Remove-Item $defaltEncodingFile
# 设置回系统默认策略
#Set-ExecutionPolicy default
Pop-Location
Write-Host "merge complite......"