master
DebuggerX 5 years ago
commit c5befd94cb

11
.gitignore vendored

@ -0,0 +1,11 @@
# Files and directories created by pub
.dart_tool/
.packages
# Conventional directory for build outputs
build/
# Directory created by dartdoc
doc/api/
.idea

@ -0,0 +1,3 @@
#!/usr/bin/env bash
echo "test bash after"

@ -0,0 +1,3 @@
#!/usr/bin/env bash
echo "test bash pre"

@ -0,0 +1,37 @@
# Flutter工程条件编译打包脚本
## 原理
通过将 flutter run/build [--option] 命令替换为 bash flutter.sh run/build [--option] 在原有flutter运行/打包流程前后执行内置及用户自定义脚本,从而实现对打包流程的自定义控制,默认内置功能为根据命令参数中的 --debug/release 以及 --flavor 渠道名,对代码和资源文件的条件编译
## 用法语法
### 代码:
代码中使用形如以下的注释来进行代码块的条件标记
```dart
void main(List<String> arguments) {
print(1);
// #[release[google]]
// print(2);
// #[release[!asd]]
// print(3);
// #[debug]
// print(4);
// #[release[test]]
// print(5);
// #[[test asd]]
// print(6);
// #[[]]
// print(7)
// #[[]]
}
```
基本注释标记语法为 **// #[debug/release[flavorName1 flavorName2 ...]]** 外层方括号内填写debug模式或release模式可以留空表示同时匹配两种模式内层方括号内填写flavor名的列表打包命令中 --flavor flavorName 参数传递进来的渠道名在列表中则匹配成功。
特殊的,如果渠道名列表中的名称前加''表示取反命令参数中传入的渠道名不在该列表中时匹配成功ps: 注意普通渠道名条件列表与带取反的列表不能同时存在)
注释标记后紧跟该条件下的代码,并注意用 '// ' 进行代码注释,脚本解析时从上到下,某个注释标记的条件匹配成功,就会将紧跟的代码片段覆盖最近的默认代码块,并忽略掉两者之间的其他条件代码块。
默认代码块的前后需要用 '// #[[]]' 注释作为标记。
### 文件:
类似代码中注释条件标记的语法,文件名中使用形如 'abc[debug/release[flavorName1 flavorName2 ...]].xxx' 的形式进行文件命名,并用对应的 'abc.xxx' 文件名作为默认情况下使用的文件,即可在编译运行的时候自动根据传入参数将合适的文件替换为实际使用的文件,并在编译完成后自动还原。
# **WIP**

@ -0,0 +1,16 @@
import 'dart:io';
void main(List<String> arguments) {
print("running default after_script.");
var rootDir = Directory('./');
rootDir.listSync(recursive: true).forEach((p) {
if (p.path.endsWith('.bak')) {
File(p.path.substring(0, p.path.length - 4)).deleteSync();
p.renameSync(p.path.substring(0, p.path.length - 4));
}
if (p.path.endsWith('.default')) {
File(p.path.substring(0, p.path.length - 8)).deleteSync();
p.renameSync(p.path.substring(0, p.path.length - 8));
}
});
}

@ -0,0 +1,27 @@
class Args {
Args(this.mode, this.flavor);
String mode;
String flavor;
@override
String toString() {
return 'Current mode is $mode, and flavor is ${flavor == '' ? 'default' : flavor}';
}
}
Args parse(arguments) {
var args = Args('debug', 'default');
for (var value in arguments) {
if (value == '--release') {
args.mode = 'release';
} else if (value == '--debug') {
args.mode = 'debug';
}
if (value == '--flavor') {
args.flavor = arguments[arguments.indexOf('--flavor') + 1];
}
}
print(args);
return args;
}

@ -0,0 +1,11 @@
import 'dart:io';
class PathUtils {
static String baseName(FileSystemEntity file) {
return file.path.substring(file.parent.path.length + 1);
}
}
void main() {
print(PathUtils.baseName(File('./path_utils.dart')));
}

@ -0,0 +1,120 @@
import 'dart:io';
import 'parse_arguments.dart';
import 'path_utils.dart';
String mode;
List<String> flavors;
Args args;
enum STATE {
none,
notMatch,
caching,
cached,
replace,
}
void main(List<String> arguments) {
print("Running default pre_script.");
args = parse(arguments);
var rootDir = Directory('./');
rootDir.listSync().forEach(walkPath);
}
File file;
StringBuffer sb = StringBuffer();
StringBuffer tmp = StringBuffer();
STATE state = STATE.none;
RegExp re = RegExp(r'// #\[(debug|release)?(?:\[(.*)\])?\]');
RegExp pathRe = RegExp(r'\[(debug|release)?(?:\[(.*)\])?\]');
Match ma;
void walkPath(FileSystemEntity path) {
var stat = path.statSync();
if (stat.type == FileSystemEntityType.directory) {
Directory(path.path).listSync().forEach(walkPath);
} else if (stat.type == FileSystemEntityType.file) {
ma = pathRe.firstMatch(PathUtils.baseName(path));
if (ma != null) {
mode = ma.group(1);
flavors = (ma.group(2) ?? '').split(' ').where((ele) => ele.trim() != '').toList();
if (checkModeAndFlavors()) {
var defaultFilePath = path.path.replaceFirst(ma.group(0), '');
var defaultFile = File(defaultFilePath);
if (defaultFile.existsSync()) {
defaultFile.renameSync(defaultFilePath + '.default');
}
File(path.path).copySync(defaultFilePath);
}
return;
}
//
file = File(path.path);
sb.clear();
try {
file.readAsLinesSync().forEach((line) {
ma = re.firstMatch(line);
if (ma != null) {
mode = ma.group(1);
flavors = (ma.group(2) ?? '').split(' ').where((ele) => ele.trim() != '').toList();
//
if (mode == null && flavors.length == 0) {
// replacenone
if (state == STATE.replace) {
sb.write(tmp);
state = STATE.none;
}
//
else if (state == STATE.caching || state == STATE.cached) {
state = STATE.replace;
}
} else {
//
if (state == STATE.caching) {
//
state = STATE.cached;
} else if (state == STATE.none || state == STATE.notMatch) {
// none
if (checkModeAndFlavors()) {
state = STATE.caching;
tmp.clear();
} else {
state = STATE.notMatch;
}
}
}
} else {
// nonelinesb
if (state == STATE.none)
sb.writeln(line);
//
else if (state == STATE.caching) tmp.writeln(line.replaceFirst('// ', ''));
//
}
});
file.renameSync(path.path + '.bak');
File(path.path).writeAsStringSync(sb.toString(), flush: true);
} catch (e) {
if (!(e is FileSystemException)) {
rethrow;
}
}
}
}
bool checkModeAndFlavors() {
if (mode != null && mode != args.mode) {
return false;
}
if (flavors.isEmpty) return true;
if (flavors[0].startsWith('!')) {
return !flavors.map((e) => e.replaceFirst('!', '')).toList().contains(args.flavor);
} else {
return flavors.contains(args.flavor);
}
}

@ -0,0 +1,52 @@
#!/usr/bin/env bash
SCRIPT_ABS=$(readlink -f "$0")
SCRIPT_DIR=$(dirname "$SCRIPT_ABS")
# shellcheck disable=SC2005
DART_EXE=$(echo "$(command -v flutter)" | awk '{print substr($0,0,length()-7)}')cache/dart-sdk/bin/dart
if [[ ! -x "$DART_EXE" ]]; then
echo "Can't find dart executable file !"
return 1
fi
if [[ -f "./.hooks/pre_script.dart" ]]; then
${DART_EXE} ./.hooks/pre_script.dart "$@"
fi
if [[ -f "./pre_script.dart" ]]; then
${DART_EXE} ./.hooks/pre_script.dart "$@"
fi
if [[ -f "./.hooks/pre_script.sh" ]]; then
./.hooks/pre_script.sh "$@"
fi
if [[ -f "./pre_script.sh" ]]; then
./pre_script.sh "$@"
fi
${DART_EXE} "$SCRIPT_DIR"/bin/pre_script.dart "$@"
#flutter "$@"
${DART_EXE} "$SCRIPT_DIR"/bin/after_script.dart "$@"
if [[ -f "./.hooks/after_script.dart" ]]; then
${DART_EXE} ./.hooks/after_script.dart "$@"
fi
if [[ -f "./after_script.dart" ]]; then
${DART_EXE} ./after_script.dart "$@"
fi
if [[ -f "./.hooks/after_script.sh" ]]; then
./.hooks/after_script.sh "$@"
fi
if [[ -f "./after_script.sh" ]]; then
./after_script.sh "$@"
fi

Binary file not shown.

After

Width:  |  Height:  |  Size: 10 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 127 KiB

@ -0,0 +1,16 @@
void main(List<String> arguments) {
print(1);
// #[release[google]]
// print(2);
// #[release[!asd]]
// print(3);
// #[debug]
// print(4);
// #[release[test]]
// print(5);
// #[[test asd]]
// print(6);
// #[[]]
// print(7)
// #[[]]
}
Loading…
Cancel
Save