forked from tensorflow/tfjs-models
-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathdiff.js
executable file
·121 lines (104 loc) · 4.22 KB
/
diff.js
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
#!/usr/bin/env node
// Copyright 2019 Google LLC. All Rights Reserved.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
// =============================================================================
const {exec} = require('./test-util');
const shell = require('shelljs');
const {readdirSync, statSync, writeFileSync} = require('fs');
const {join} = require('path');
const fs = require('fs');
const filesWhitelistToTriggerBuild = [
'cloudbuild.yml', 'package.json', 'tslint.json', 'scripts/diff.js',
'scripts/run-build.sh'
];
const CLONE_PATH = 'clone';
const dirs = readdirSync('.').filter(f => {
return f !== 'node_modules' && f !== '.git' && statSync(f).isDirectory();
});
let commitSha = process.env['COMMIT_SHA'];
let branchName = process.env['BRANCH_NAME'];
// If commit sha or branch name are null we are running this locally and are in
// a git repository.
if (commitSha == null) {
commitSha = exec(`git rev-parse HEAD`).stdout.trim();
}
if (branchName == null) {
branchName = exec(`git rev-parse --abbrev-ref HEAD`).stdout.trim();
}
console.log('commitSha: ', commitSha);
console.log('branchName: ', branchName);
// We cannot do --depth=1 here because we need to check out an old merge base.
// We cannot do --single-branch here because we need multiple branches.
exec(`git clone https://github.com/tensorflow/tfjs-models ${CLONE_PATH}`);
console.log(); // Break up the console for readability.
shell.cd(CLONE_PATH);
// If we cannot check out the commit then this PR is coming from a fork.
const res = shell.exec(`git checkout ${commitSha}`, {silent: true});
const isPullRequestFromFork = res.code !== 0;
// Only checkout the merge base if the pull requests comes from a
// tensorflow/tfjs branch. Otherwise clone master and diff against master.
if (!isPullRequestFromFork) {
console.log(
'PR is coming from tensorflow/tfjs-models. ' +
'Finding the merge base...');
exec(`git checkout master`);
exec(`git checkout ${branchName}`);
const mergeBase = exec(`git merge-base master ${branchName}`).stdout.trim();
exec(`git fetch origin ${mergeBase}`);
exec(`git checkout ${mergeBase}`);
console.log('mergeBase: ', mergeBase);
} else {
console.log('PR is coming from a fork. Diffing against master.');
}
shell.cd('..');
console.log(); // Break up the console for readability.
let triggerAllBuilds = false;
let whitelistDiffOutput = [];
filesWhitelistToTriggerBuild.forEach(fileToTriggerBuild => {
const diffOutput = diff(fileToTriggerBuild);
if (diffOutput !== '') {
console.log(fileToTriggerBuild, 'has changed. Triggering all builds.');
triggerAllBuilds = true;
whitelistDiffOutput.push(diffOutput);
}
});
console.log(); // Break up the console for readability.
let triggeredBuilds = [];
dirs.forEach(dir => {
shell.rm('-f', `${dir}/diff`);
const diffOutput = diff(`${dir}/`);
if (diffOutput !== '') {
console.log(`${dir} has modified files.`);
} else {
console.log(`No modified files found in ${dir}`);
}
const shouldDiff = diffOutput !== '' || triggerAllBuilds;
if (shouldDiff) {
const diffContents = whitelistDiffOutput.join('\n') + '\n' + diffOutput;
writeFileSync(join(dir, 'diff'), diffContents);
triggeredBuilds.push(dir);
}
});
console.log(); // Break up the console for readability.
// Filter the triggered builds to log by whether a cloudbuild.yml file
// exists for that directory.
triggeredBuilds = triggeredBuilds.filter(
triggeredBuild => fs.existsSync(triggeredBuild + '/cloudbuild.yml'));
console.log('Triggering builds for ', triggeredBuilds.join(', '));
function diff(fileOrDirName) {
const diffCmd = `diff -rq --exclude='settings.json' ` +
`${CLONE_PATH}/${fileOrDirName} ` +
`${fileOrDirName}`;
return exec(diffCmd, {silent: true}, true).stdout.trim();
}