Skip to content

Commit c5143b2

Browse files
Merge pull request #164 from Evleaps/feature/new-specified-branch-commit
Feature/new specified branch commit
2 parents ae455b5 + 06b84e0 commit c5143b2

File tree

9 files changed

+141
-8
lines changed

9 files changed

+141
-8
lines changed

README.md

Lines changed: 24 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -112,7 +112,10 @@ affectedModuleDetector {
112112
- `compareFrom`: A commit to compare the branch changes against. Can be either:
113113
- PreviousCommit: compare against the previous commit
114114
- ForkCommit: compare against the commit the branch was forked from
115-
- SpecifiedBranchCommit: specify the branch to compare changes against using the `specifiedBranch` configuration before the `compareFrom` configuration
115+
- SpecifiedBranchCommit: compare against the last commit of `$specifiedBranch` using `git rev-parse` approach.
116+
- SpecifiedBranchCommitMergeBase: compare against the nearest ancestors with `$specifiedBranch` using `git merge base` approach.
117+
118+
**Note:** specify the branch to compare changes against using the `specifiedBranch` configuration before the `compareFrom` configuration
116119
- `excludedModules`: A list of modules that will be excluded from the build process
117120
- `includeUncommitted`: If uncommitted files should be considered affected
118121
- `top`: The top of the git log to use. Must be used in combination with configuration `includeUncommitted = false`
@@ -132,6 +135,26 @@ affectedModuleDetector {
132135
* `./gradlew runAffectedAndroidTests` - runs connected tests
133136
* `./gradlew assembleAffectedAndroidTests` - assembles but does not run on device tests, useful when working with device labs
134137

138+
## SpecifiedBranchCommit vs SpecifiedBranchCommitMergeBase
139+
140+
- SpecifiedBranchCommit using `git rev-parse` command for getting sha.
141+
- SpecifiedBranchCommitMergeBase using `git merge base` command for getting sha.
142+
143+
What does it mean?
144+
When we run any AMD command we compare the current branch with the specified parent branch. Consider an example when, during the development of our feature,
145+
another developer merged his changes (9 files) into our common remote parent branch - "origin/dev".
146+
147+
Please, look at picture:
148+
![specified_branch_difference.png](specified_branch_difference.png)
149+
150+
Suppose we have changed 6 files in our "feature" branch.
151+
152+
1. Behaviour of SpecifiedBranchCommit:
153+
AMD will show the result that 15 files were affected. Because our branch is not updated (pull) and AMD will see our 6 files and 9 files that were merged by another developer.
154+
2. Behaviour of SpecifiedBranchCommitMergeBase:
155+
AMD will show the result that 6 files were affected. And this is the correct behavior.
156+
157+
Hence, depends on your CI settings you have to configure AMD right.
135158

136159
## Sample Usage
137160

affectedmoduledetector/src/main/kotlin/com/dropbox/affectedmoduledetector/AffectedModuleConfiguration.kt

Lines changed: 7 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -81,11 +81,16 @@ class AffectedModuleConfiguration {
8181

8282
var compareFrom: String = "PreviousCommit"
8383
set(value) {
84-
val commitShaProviders = listOf("PreviousCommit", "ForkCommit", "SpecifiedBranchCommit")
84+
val commitShaProviders = listOf(
85+
"PreviousCommit",
86+
"ForkCommit",
87+
"SpecifiedBranchCommit",
88+
"SpecifiedBranchCommitMergeBase"
89+
)
8590
require(commitShaProviders.contains(value)) {
8691
"The property configuration compareFrom must be one of the following: ${commitShaProviders.joinToString(", ")}"
8792
}
88-
if (value == "SpecifiedBranchCommit") {
93+
if (value == "SpecifiedBranchCommit" || value == "SpecifiedBranchCommitMergeBase") {
8994
requireNotNull(specifiedBranch) {
9095
"Specify a branch using the configuration specifiedBranch"
9196
}

affectedmoduledetector/src/main/kotlin/com/dropbox/affectedmoduledetector/commitshaproviders/CommitShaProvider.kt

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@ import com.dropbox.affectedmoduledetector.GitClient
44
import com.dropbox.affectedmoduledetector.Sha
55

66
interface CommitShaProvider {
7+
78
fun get(commandRunner: GitClient.CommandRunner): Sha
89

910
companion object {
@@ -17,9 +18,14 @@ interface CommitShaProvider {
1718
}
1819
SpecifiedBranchCommit(specifiedBranch)
1920
}
21+
"SpecifiedBranchCommitMergeBase" -> {
22+
requireNotNull(specifiedBranch) {
23+
"Specified branch must be defined"
24+
}
25+
SpecifiedBranchCommitMergeBase(specifiedBranch)
26+
}
2027
else -> throw IllegalArgumentException("Unsupported compareFrom type")
2128
}
2229
}
2330
}
2431
}
25-
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
package com.dropbox.affectedmoduledetector.commitshaproviders
2+
3+
import com.dropbox.affectedmoduledetector.GitClient
4+
import com.dropbox.affectedmoduledetector.Sha
5+
6+
class SpecifiedBranchCommitMergeBase(private val specifiedBranch: String) : CommitShaProvider {
7+
8+
override fun get(commandRunner: GitClient.CommandRunner): Sha {
9+
val currentBranch = commandRunner.executeAndParseFirst(CURRENT_BRANCH_CMD)
10+
return commandRunner.executeAndParseFirst("git merge-base $currentBranch $specifiedBranch")
11+
}
12+
13+
companion object {
14+
15+
const val CURRENT_BRANCH_CMD = "git rev-parse --abbrev-ref HEAD"
16+
}
17+
}

affectedmoduledetector/src/test/kotlin/com/dropbox/affectedmoduledetector/AffectedModuleConfigurationTest.kt

Lines changed: 25 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,6 @@ import org.junit.rules.TemporaryFolder
99
import org.junit.runner.RunWith
1010
import org.junit.runners.JUnit4
1111
import java.io.File
12-
import java.lang.Exception
1312

1413
@RunWith(JUnit4::class)
1514
class AffectedModuleConfigurationTest {
@@ -173,6 +172,30 @@ class AffectedModuleConfigurationTest {
173172
assertThat(actual).isEqualTo("PreviousCommit")
174173
}
175174

175+
@Test
176+
fun `WHEN compareFrom is set to SpecifiedBranchCommitMergeBase AND specifiedBranch is set THEN return SpecifiedBranchCommitMergeBase`() {
177+
val specifiedBranchCommitMergeBase = "SpecifiedBranchCommitMergeBase"
178+
val specifiedBranch = "origin/dev"
179+
180+
config.specifiedBranch = specifiedBranch
181+
config.compareFrom = specifiedBranchCommitMergeBase
182+
183+
val actual = config.compareFrom
184+
185+
assertThat(actual).isEqualTo(specifiedBranchCommitMergeBase)
186+
}
187+
188+
@Test
189+
fun `WHEN compareFrom is set to SpecifiedBranchCommitMergeBase AND specifiedBranch isn't set THEN throw exception`() {
190+
val specifiedBranchCommitMergeBase = "SpecifiedBranchCommitMergeBase"
191+
192+
try {
193+
config.compareFrom = specifiedBranchCommitMergeBase
194+
} catch (e: IllegalArgumentException) {
195+
assertThat(e.message).isEqualTo("Specify a branch using the configuration specifiedBranch")
196+
}
197+
}
198+
176199
@Test
177200
fun `GIVEN AffectedModuleConfiguration WHEN compareFrom is set to ForkCommit THEN is ForkCommit`() {
178201
val forkCommit = "ForkCommit"
@@ -218,7 +241,7 @@ class AffectedModuleConfigurationTest {
218241
fail()
219242
} catch (e: Exception) {
220243
assertThat(e::class).isEqualTo(IllegalArgumentException::class)
221-
assertThat(e.message).isEqualTo("The property configuration compareFrom must be one of the following: PreviousCommit, ForkCommit, SpecifiedBranchCommit")
244+
assertThat(e.message).isEqualTo("The property configuration compareFrom must be one of the following: PreviousCommit, ForkCommit, SpecifiedBranchCommit, SpecifiedBranchCommitMergeBase")
222245
assertThat(config.compareFrom).isEqualTo("PreviousCommit")
223246
}
224247
}

affectedmoduledetector/src/test/kotlin/com/dropbox/affectedmoduledetector/commitshaproviders/CommitShaProviderTest.kt

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -41,6 +41,23 @@ class CommitShaProviderTest {
4141
}
4242
}
4343

44+
@Test
45+
fun givenSpecifiedBranchCommitMergeBaseAndSpecifiedBranchNull_whenFromString_thenThrowException() {
46+
try {
47+
CommitShaProvider.fromString("SpecifiedBranchCommitMergeBase")
48+
} catch (e: Exception) {
49+
assertThat(e::class).isEqualTo(IllegalArgumentException::class)
50+
assertThat(e.message).isEqualTo("Specified branch must be defined")
51+
}
52+
}
53+
54+
@Test
55+
fun givenSpecifiedBranchCommitMergeBase_whenFromString_thenReturnSpecifiedBranchCommitMergeBase() {
56+
val actual = CommitShaProvider.fromString("SpecifiedBranchCommitMergeBase", "branch")
57+
58+
assertThat(actual::class).isEqualTo(SpecifiedBranchCommitMergeBase::class)
59+
}
60+
4461
@Test
4562
fun givenInvalidCommitString_whenFromString_thenExceptionThrown() {
4663
try {
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,42 @@
1+
package com.dropbox.affectedmoduledetector.commitshaproviders
2+
3+
import com.dropbox.affectedmoduledetector.AttachLogsTestRule
4+
import com.dropbox.affectedmoduledetector.mocks.MockCommandRunner
5+
import com.google.common.truth.Truth
6+
import org.junit.Rule
7+
import org.junit.Test
8+
import org.junit.runner.RunWith
9+
import org.junit.runners.JUnit4
10+
11+
@RunWith(JUnit4::class)
12+
class SpecifiedBranchCommitMergeBaseTest {
13+
14+
@Rule
15+
@JvmField
16+
val attachLogsRule = AttachLogsTestRule()
17+
private val logger = attachLogsRule.logger
18+
private val commandRunner = MockCommandRunner(logger)
19+
private val previousCommit = SpecifiedBranchCommitMergeBase(SPECIFIED_BRANCH)
20+
21+
@Test
22+
fun `WHEN CURRENT_BRANCH_CMD THEN command returned`() {
23+
Truth.assertThat(SpecifiedBranchCommitMergeBase.CURRENT_BRANCH_CMD).isEqualTo("git rev-parse --abbrev-ref HEAD")
24+
}
25+
26+
@Test
27+
fun `WHEN get commit sha THEN return sha`() {
28+
29+
commandRunner.addReply(SpecifiedBranchCommitMergeBase.CURRENT_BRANCH_CMD, NEW_FEATURE_BRANCH)
30+
commandRunner.addReply("git merge-base $NEW_FEATURE_BRANCH $SPECIFIED_BRANCH", "commit-sha")
31+
32+
val actual = previousCommit.get(commandRunner)
33+
34+
Truth.assertThat(actual).isEqualTo("commit-sha")
35+
}
36+
37+
private companion object {
38+
39+
const val SPECIFIED_BRANCH = "origin/dev"
40+
const val NEW_FEATURE_BRANCH = "newFeatureBranch"
41+
}
42+
}

sample/build.gradle

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -31,8 +31,8 @@ affectedModuleDetector {
3131
pathsAffectingAllModules = [
3232
"buildSrc/"
3333
]
34-
specifiedBranch = "main"
35-
compareFrom = "SpecifiedBranchCommit"
34+
specifiedBranch = "origin/main"
35+
compareFrom = "SpecifiedBranchCommitMergeBase"
3636
customTasks = [
3737
new AffectedModuleConfiguration.CustomTask(
3838
"runDetektByImpact",

specified_branch_difference.png

19.2 KB
Loading

0 commit comments

Comments
 (0)