com.avito.impact.changes.GitDiffLine.kt Maven / Gradle / Ivy
The newest version!
package com.avito.impact.changes
import com.avito.android.Result
import java.io.File
internal data class GitDiffLine(val path: String, val changeType: ChangeType)
internal fun GitDiffLine.asChangedFile(rootDir: File): ChangedFile {
return ChangedFile(rootDir, File(rootDir, path), changeType)
}
/**
* Parses line from git diff command.
* Examples:
* ```
* A README.md
* R95 old_name.kt new_name.kt
* ```
*/
internal fun String.parseGitDiffLine(): Result {
val parts = this.split(Regex("[ \t]"))
.map { it.trim() }
if (parts.size < 2) {
return Result.Failure(IllegalArgumentException("Line has invalid syntax: $this "))
}
val diffTypeCode = extractDiffTypeCode(parts)
return ChangeType.getTypeByCode(diffTypeCode)
.flatMap { changeType: ChangeType ->
if (isSyntaxCorrect(parts, changeType)) {
Result.Success(GitDiffLine(extractFilePath(parts, changeType), changeType))
} else {
Result.Failure(IllegalArgumentException("Line has invalid syntax: $this "))
}
}
}
// diff type 'R' and 'C' is followed by probability score e.g. R95, C100 etc
private fun extractDiffTypeCode(parts: List): Char {
return parts[0].first()
}
@Suppress("MagicNumber")
private fun isSyntaxCorrect(parts: List, changeType: ChangeType): Boolean {
return when (changeType) {
ChangeType.ADDED, ChangeType.MODIFIED, ChangeType.DELETED -> parts.size == 2
ChangeType.COPIED, ChangeType.RENAMED -> parts.size == 3
}
}
private fun extractFilePath(parts: List, changeType: ChangeType): String {
return when (changeType) {
ChangeType.ADDED, ChangeType.MODIFIED, ChangeType.DELETED -> parts[1]
ChangeType.COPIED, ChangeType.RENAMED -> parts[2]
}
}