Skip to content

Commit

Permalink
Merge pull request #3211 from scala-steward-org/topic/catch-exception…
Browse files Browse the repository at this point in the history
…s-in-applyAll

Catch exceptions in Substring.Replacement.applyAll
  • Loading branch information
fthomas authored Nov 14, 2023
2 parents 2c6717b + a0d68e4 commit c12d4a4
Show file tree
Hide file tree
Showing 4 changed files with 21 additions and 17 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -105,8 +105,8 @@ final class EditAlg[F[_]](implicit
for {
repoDir <- workspaceAlg.repoDir(data.repo)
replacementsByPath = updateReplacements.groupBy(_.position.path).toList
_ <- replacementsByPath.traverse { case (path, replacements) =>
fileAlg.editFile(repoDir / path, Substring.Replacement.applyAll(replacements))
_ <- replacementsByPath.traverse_ { case (path, replacements) =>
fileAlg.editFile(repoDir / path, Substring.Replacement.applyAll[F](replacements))
}
_ <- reformatChangedFiles(data)
msgTemplate = data.config.commits.messageOrDefault
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@

package org.scalasteward.core.edit.update.data

import cats.ApplicativeThrow
import scala.util.matching.Regex.Match

object Substring {
Expand All @@ -41,16 +42,19 @@ object Substring {
final case class Replacement(position: Position, replacement: String)

object Replacement {
def applyAll(replacements: List[Replacement])(source: String): String = {
var start = 0
val sb = new java.lang.StringBuilder(source.length)
replacements.distinctBy(_.position.start).sortBy(_.position.start).foreach { r =>
val before = source.substring(start, r.position.start)
start = r.position.start + r.position.value.length
sb.append(before).append(r.replacement)
def applyAll[F[_]](replacements: List[Replacement])(source: String)(implicit
F: ApplicativeThrow[F]
): F[String] =
F.catchNonFatal {
var start = 0
val sb = new java.lang.StringBuilder(source.length)
replacements.distinctBy(_.position.start).sortBy(_.position.start).foreach { r =>
val before = source.substring(start, r.position.start)
start = r.position.start + r.position.value.length
sb.append(before).append(r.replacement)
}
sb.append(source.substring(start))
sb.toString
}
sb.append(source.substring(start))
sb.toString
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -63,9 +63,9 @@ trait FileAlg[F[_]] {
): Resource[F, Unit] =
createTemporarily(dir / data.path, data.content)

final def editFile(file: File, edit: String => String)(implicit F: MonadThrow[F]): F[Unit] =
final def editFile(file: File, edit: String => F[String])(implicit F: MonadThrow[F]): F[Unit] =
readFile(file)
.flatMap(_.fold(F.unit)(content => writeFile(file, edit(content))))
.flatMap(_.fold(F.unit)(edit(_).flatMap(writeFile(file, _))))
.adaptError { case t => new Throwable(s"failed to edit $file", t) }

final def findFiles[A, B](
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ import org.scalasteward.core.TestInstances.ioLogger
import org.scalasteward.core.io.FileAlgTest.ioFileAlg
import org.scalasteward.core.mock.MockConfig.mockRoot
import org.scalasteward.core.mock.MockContext.context.fileAlg
import org.scalasteward.core.mock.MockState
import org.scalasteward.core.mock.{MockEff, MockState}
import org.scalasteward.core.mock.MockState.TraceEntry.Cmd

class FileAlgTest extends CatsEffectSuite {
Expand Down Expand Up @@ -57,7 +57,7 @@ class FileAlgTest extends CatsEffectSuite {

test("editFile: nonexistent file") {
val obtained = fileAlg
.editFile(mockRoot / "does-not-exist.txt", identity)
.editFile(mockRoot / "does-not-exist.txt", MockEff.pure)
.runS(MockState.empty)

val expected =
Expand All @@ -69,7 +69,7 @@ class FileAlgTest extends CatsEffectSuite {
val file = mockRoot / "steward" / "test1.sbt"
val obtained = (for {
_ <- fileAlg.writeFile(file, "123")
_ <- fileAlg.editFile(file, _.replace("2", "4"))
_ <- fileAlg.editFile(file, content => MockEff.pure(content.replace("2", "4")))
} yield ()).runS(MockState.empty)

val expected = MockState.empty.copy(
Expand Down

0 comments on commit c12d4a4

Please sign in to comment.