From f39faf0a23d6ca55dc6fd78e70a80fc8e1eac85d Mon Sep 17 00:00:00 2001 From: Wojciech Mazur Date: Sat, 20 Jul 2024 16:17:49 +0200 Subject: [PATCH] Add search and replace script to be used instead of sed to apply patches --- project-builder/mill/build.sh | 2 +- project-builder/mill/prepare-project.sh | 8 +------- project-builder/sbt/prepare-project.sh | 10 +--------- scripts/searchAndReplace.scala | 22 ++++++++++++++++++++++ 4 files changed, 25 insertions(+), 17 deletions(-) create mode 100644 scripts/searchAndReplace.scala diff --git a/project-builder/mill/build.sh b/project-builder/mill/build.sh index f0bb59ac..a4a9e95b 100755 --- a/project-builder/mill/build.sh +++ b/project-builder/mill/build.sh @@ -1,7 +1,7 @@ #!/usr/bin/env bash set -e -if [ $# -ne 7]; then +if [ $# -ne 7 ]; then echo "Wrong number of script arguments, expected $0 , got $#: $@" exit 1 fi diff --git a/project-builder/mill/prepare-project.sh b/project-builder/mill/prepare-project.sh index aca27cc7..607528e2 100755 --- a/project-builder/mill/prepare-project.sh +++ b/project-builder/mill/prepare-project.sh @@ -76,13 +76,7 @@ for elem in $(echo "${projectConfig}" | jq -r '.sourcePatches // [] | .[] | @bas echo "Path: $path" echo "Pattern: $pattern" echo "Replacement: $replaceWith" - - set -x - # Cannot determinate did sed script was applied, so perform two ops each time - # Don't use in-place option for easier cross-platform compat (macos vs unix) - (sed "s/$pattern/$replaceWith/" "$path" > $path.tmp && mv $path.tmp $path ) || true - (sed -E "s/$pattern/$replaceWith/" "$path" > $path.tmp && mv $path.tmp $path ) || true - set +x + scala-cli run ${scriptDir}/../../scripts/searchAndReplace.scala -- "${repoDir}/${path}" "${pattern}" "${replaceWith}" done prepareScript="${OPENCB_SCRIPT_DIR:?OPENCB_SCRIPT_DIR not defined}/prepare-scripts/${projectName}.sh" diff --git a/project-builder/sbt/prepare-project.sh b/project-builder/sbt/prepare-project.sh index 8b735967..31cbd90f 100755 --- a/project-builder/sbt/prepare-project.sh +++ b/project-builder/sbt/prepare-project.sh @@ -75,15 +75,7 @@ for elem in $(echo "${projectConfig}" | jq -r '.sourcePatches // [] | .[] | @bas echo "Path: $path" echo "Pattern: $pattern" echo "Replacement: $replaceWith" - - set -x - # Cannot determinate did sed script was applied, so perform two ops each time - # Don't use in-place option for easier cross-platform compat (macos vs unix) - repoPath=$repoDir/$path - (sed "s/$pattern/$replaceWith/" "$repoPath" > $repoPath.tmp && mv $repoPath.tmp $repoPath ) || true - (sed -E "s/$pattern/$replaceWith/" "$repoPath" > $repoPath.tmp && mv $repoPath.tmp $repoPath ) || true - - set +x + scala-cli run ${scriptDir}/../../scripts/searchAndReplace.scala -- "${repoDir}/${path}" "${pattern}" "${replaceWith}" done prepareScript="${OPENCB_SCRIPT_DIR:?OPENCB_SCRIPT_DIR not defined}/prepare-scripts/${projectName}.sh" diff --git a/scripts/searchAndReplace.scala b/scripts/searchAndReplace.scala new file mode 100644 index 00000000..6b163900 --- /dev/null +++ b/scripts/searchAndReplace.scala @@ -0,0 +1,22 @@ +import java.nio.file.Path +import java.nio.file.Paths +import java.util.regex.PatternSyntaxException +import java.nio.file.Files + +import scala.util.chaining.* + +given scala.util.CommandLineParser.FromString[Path] = Paths.get(_) + +@main def searchAndReplace(file: Path, textOrPattern: String, replacement: String): Unit = + val input = io.Source.fromFile(file.toFile()).mkString + input + .replace(textOrPattern, replacement) + .pipe: input => + try textOrPattern.r.replaceAllIn(input, replacement) + catch case _: PatternSyntaxException => input + .pipe: output => + if input != output then + println(s"Successfully applied pattern '$textOrPattern' in $file") + Files.write(file, output.getBytes()) + else + System.err.println(s"Failed to apply pattern '$textOrPattern' in $file")