From d065b3d36de4235e77220526097fd2b365b9692d Mon Sep 17 00:00:00 2001 From: Guillaume Bouchard Date: Fri, 3 Jan 2025 17:34:37 +0400 Subject: [PATCH] fix: correctly remove indentation one line even if escaped line brake Close #141. ``` [fmtTrim| foo\ bar |] ``` should be `foobar` instead of `foo bar`. This is fixed by doing the whitespace trimming on the input string of the quasiquotes (here `\n foo\ bar`) instead of the output string. However it breaks two previous features: - When an interpolation block had whitespace, it should now be indented at least as much as the string, otherwise the interpolation block indentation will be used as reference. - Escaping the first line is now ignored. But actually, escaping the first line behaves exactly as not escaping the first line, so it breaks nothing. --- ChangeLog.md | 4 +++- src/PyF.hs | 7 +++++-- test/Spec.hs | 14 +++++++------- 3 files changed, 15 insertions(+), 10 deletions(-) diff --git a/ChangeLog.md b/ChangeLog.md index 27a2ef0..5354b66 100644 --- a/ChangeLog.md +++ b/ChangeLog.md @@ -1,6 +1,8 @@ # Revision history for PyF -- Support for GHC 9.12 +- Fix indentation in `fmtTrim` when line break was escaped (bug https://github.com/guibou/PyF/issues/141). +- Support for GHC 9.12. +- Fix for tests in GHC 9.10. - No more "python" reference check in the test phase. I'm removing complexity, and if it does not match the python implementation, we can just introduce a new test case. Note that python checking can be reimplemented easilly by diff --git a/src/PyF.hs b/src/PyF.hs index 6cea571..f774337 100644 --- a/src/PyF.hs +++ b/src/PyF.hs @@ -38,7 +38,9 @@ fmt = mkFormatter "fmt" fmtConfig -- | Format with whitespace trimming. fmtTrim :: QuasiQuoter -fmtTrim = mkFormatter "fmtTrim" (addTrim fmtConfig) +fmtTrim = let + qq = mkFormatter "fmtTrim" fmtConfig + in qq { quoteExp = \s -> quoteExp qq (trimIndent s) } -- | Multiline string, no interpolation. str :: QuasiQuoter @@ -46,7 +48,8 @@ str = mkFormatter "str" strConfig -- | Multiline string, no interpolation, but does indentation trimming. strTrim :: QuasiQuoter -strTrim = mkFormatter "strTrim" (addTrim strConfig) +strTrim = let qq = mkFormatter "strTrim" strConfig + in qq { quoteExp = \s -> quoteExp qq (trimIndent s) } -- | Raw string, neither interpolation nor escaping is performed. raw :: QuasiQuoter diff --git a/test/Spec.hs b/test/Spec.hs index f9133ac..2b3dff0 100644 --- a/test/Spec.hs +++ b/test/Spec.hs @@ -482,18 +482,18 @@ yeah\ hello - a - { - 2 + 2 + 2 + 2 :d}|] `shouldBe` "hello\n- a\n - 4" - it "behaves well with escaped first line" $ do - [fmtTrim|\ - - a - - b - |] - `shouldBe` "- a\n- b\n" it "Do not touch single lines" $ do [fmtTrim| hello|] `shouldBe` " hello" + it "trim when there is a linebreak" $ do + -- https://github.com/guibou/PyF/issues/141 + [fmtTrim| + Cannot convert formula 2.0 * exponent(unit=s, value=1.0) which has unit dimensionless to\ + unit dimensionless for they have different dimensions|] + `shouldBe` "Cannot convert formula 2.0 * exponent(unit=s, value=1.0) which has unit dimensionless to unit dimensionless for they have different dimensions" describe "raw" $ do it "does not escape anything" $ [raw|hello