refactor [git]: Allow passing entries explicitly to InMemoryRebaseOperations.kt

We need this when the log is out of date and we want to construct them manually

GitOrigin-RevId: 46e8d2144e1e39a431d0eaea1a306aa88b43a039
This commit is contained in:
Stanislau Palyn
2026-02-05 13:39:17 +01:00
committed by intellij-monorepo-bot
parent f31708536c
commit e52dd94ae1
5 changed files with 37 additions and 15 deletions

View File

@@ -6,7 +6,7 @@ import com.intellij.vcs.log.VcsCommitMetadata
import com.intellij.vcs.log.data.VcsLogData
import git4idea.inMemory.GitObjectRepository
import git4idea.inMemory.rebase.performInMemoryRebase
import git4idea.rebase.GitRebaseEntryWithDetails
import git4idea.rebase.GitRebaseEntry
import git4idea.rebase.interactive.GitRebaseTodoModel
import git4idea.rebase.interactive.convertToModel
import git4idea.rebase.interactive.tryGetEntriesUsingLog
@@ -14,35 +14,53 @@ import git4idea.rebase.log.GitCommitEditingOperationResult
import git4idea.rebase.log.indicesByPredicate
import git4idea.repo.GitRepository
internal sealed interface RebaseEntriesSource {
data class Entries(val entries: List<GitRebaseEntry>) : RebaseEntriesSource
data class LogData(val logData: VcsLogData) : RebaseEntriesSource
}
internal object InMemoryRebaseOperations {
private val LOG = logger<InMemoryRebaseOperations>()
suspend fun squash(repository: GitRepository, logData: VcsLogData, commitsToSquash: List<VcsCommitMetadata>, newMessage: String): GitCommitEditingOperationResult {
return executeInMemoryCommitModification(repository, logData, commitsToSquash) { model, toSquashIndices ->
suspend fun squash(
repository: GitRepository,
commitsToSquash: List<VcsCommitMetadata>,
newMessage: String,
entriesSource: RebaseEntriesSource,
): GitCommitEditingOperationResult {
return executeInMemoryCommitModification(repository, commitsToSquash, entriesSource) { model, toSquashIndices ->
val uniteRoot = model.unite(toSquashIndices)
model.reword(uniteRoot.index, newMessage)
}
}
suspend fun drop(repository: GitRepository, logData: VcsLogData, commitsToDrop: List<VcsCommitMetadata>): GitCommitEditingOperationResult {
return executeInMemoryCommitModification(repository, logData, commitsToDrop) { model, toDropIndices ->
suspend fun drop(
repository: GitRepository,
commitsToDrop: List<VcsCommitMetadata>,
entriesSource: RebaseEntriesSource,
): GitCommitEditingOperationResult {
return executeInMemoryCommitModification(repository, commitsToDrop, entriesSource) { model, toDropIndices ->
model.drop(toDropIndices)
}
}
private suspend fun executeInMemoryCommitModification(
repository: GitRepository,
logData: VcsLogData,
commits: List<VcsCommitMetadata>,
modelModifier: (GitRebaseTodoModel<out GitRebaseEntryWithDetails>, List<Int>) -> Unit,
entriesSource: RebaseEntriesSource,
modelModifier: (GitRebaseTodoModel<out GitRebaseEntry>, List<Int>) -> Unit,
): GitCommitEditingOperationResult {
val generatedEntries = tryGetEntriesUsingLog(repository, commits.last(), logData)
?: return GitCommitEditingOperationResult.Incomplete
val generatedEntries = when (entriesSource) {
is RebaseEntriesSource.Entries -> entriesSource.entries
is RebaseEntriesSource.LogData -> {
tryGetEntriesUsingLog(repository, commits.last(), entriesSource.logData)
}
} ?: return GitCommitEditingOperationResult.Incomplete
val model = convertToModel(generatedEntries)
val commitHashes = commits.map { commit -> commit.id.asString() }.toSet()
val targetIndices = model.elements.indicesByPredicate {
it.entry.commitDetails.id.asString() in commitHashes
val targetIndices = model.elements.indicesByPredicate { element ->
element.entry.commit in commitHashes
}
if (targetIndices.size != commits.size) {

View File

@@ -17,6 +17,7 @@ import com.intellij.vcs.log.ui.table.size
import git4idea.config.GitVcsApplicationSettings
import git4idea.i18n.GitBundle
import git4idea.inMemory.rebase.log.InMemoryRebaseOperations
import git4idea.inMemory.rebase.log.RebaseEntriesSource
import git4idea.rebase.log.GitCommitEditingOperationResult
import git4idea.rebase.log.GitMultipleCommitEditingAction
import git4idea.rebase.log.executeInMemoryWithFallback
@@ -65,7 +66,7 @@ internal class GitDropLogAction : GitMultipleCommitEditingAction() {
return withBackgroundProgress(commitEditingData.project, GitBundle.message("rebase.log.drop.progress.indicator.title", commitsToDrop.size)) {
executeInMemoryWithFallback(
inMemoryOperation = {
InMemoryRebaseOperations.drop(commitEditingData.repository, commitEditingData.logData, commitsToDrop)
InMemoryRebaseOperations.drop(commitEditingData.repository, commitsToDrop, RebaseEntriesSource.LogData(commitEditingData.logData))
},
fallbackOperation = {
coroutineToIndicator {

View File

@@ -8,6 +8,7 @@ import com.intellij.vcs.log.VcsCommitMetadata
import com.intellij.vcs.log.ui.table.size
import git4idea.i18n.GitBundle
import git4idea.inMemory.rebase.log.InMemoryRebaseOperations
import git4idea.inMemory.rebase.log.RebaseEntriesSource
import git4idea.rebase.GitSquashedCommitsMessage
import git4idea.rebase.log.GitCommitEditingOperationResult
import git4idea.rebase.log.GitMultipleCommitEditingAction
@@ -70,7 +71,7 @@ internal class GitSquashLogAction : GitMultipleCommitEditingAction() {
return withBackgroundProgress(commitEditingData.project, GitBundle.message("rebase.log.squash.progress.indicator.title")) {
executeInMemoryWithFallback(
inMemoryOperation = {
InMemoryRebaseOperations.squash(commitEditingData.repository, commitEditingData.logData, commitsToSquash, newMessage)
InMemoryRebaseOperations.squash(commitEditingData.repository, commitsToSquash, newMessage, RebaseEntriesSource.LogData(commitEditingData.logData))
},
fallbackOperation = {
coroutineToIndicator {

View File

@@ -4,6 +4,7 @@ package git4idea.inMemory.rebase.log.drop
import com.intellij.vcs.log.VcsCommitMetadata
import git4idea.GitDisposable
import git4idea.inMemory.rebase.log.InMemoryRebaseOperations
import git4idea.inMemory.rebase.log.RebaseEntriesSource
import git4idea.log.createLogDataIn
import git4idea.log.refreshAndWait
import git4idea.rebase.log.GitCommitEditingOperationResult
@@ -16,7 +17,7 @@ internal class GitInMemoryDropOperationTest : GitDropOperationTestBase() {
val testCs = GitDisposable.getInstance(project).coroutineScope
val logData = createLogDataIn(testCs, repo, logProvider)
logData.refreshAndWait(repo, true)
InMemoryRebaseOperations.drop(repo, logData, commitsToDrop)
InMemoryRebaseOperations.drop(repo, commitsToDrop, RebaseEntriesSource.LogData(logData))
}
}
}

View File

@@ -4,6 +4,7 @@ package git4idea.inMemory.rebase.log.squash
import com.intellij.vcs.log.VcsCommitMetadata
import git4idea.GitDisposable
import git4idea.inMemory.rebase.log.InMemoryRebaseOperations
import git4idea.inMemory.rebase.log.RebaseEntriesSource
import git4idea.log.createLogDataIn
import git4idea.log.refreshAndWait
import git4idea.rebase.log.GitCommitEditingOperationResult
@@ -16,7 +17,7 @@ internal class GitInMemorySquashOperationTest : GitSquashOperationTestBase() {
val testCs = GitDisposable.getInstance(project).coroutineScope
val logData = createLogDataIn(testCs, repo, logProvider)
logData.refreshAndWait(repo, true)
InMemoryRebaseOperations.squash(repo, logData, commitsToSquash, newMessage)
InMemoryRebaseOperations.squash(repo, commitsToSquash, newMessage, RebaseEntriesSource.LogData(logData))
}
}
}