Skip to content

Commit

Permalink
Merge pull request #18 from mateusfpleite/main
Browse files Browse the repository at this point in the history
[Clause In Case] Escape clause if it's a string
  • Loading branch information
jxxcarlson authored Jun 12, 2024
2 parents f9b714c + c5505c5 commit 913cd24
Show file tree
Hide file tree
Showing 2 changed files with 160 additions and 11 deletions.
63 changes: 52 additions & 11 deletions src/Install/ClauseInCase.elm
Original file line number Diff line number Diff line change
Expand Up @@ -190,14 +190,17 @@ visitFunction namespace clause functionCall ignored function insertAt customErro
List.any
(\pattern -> patternToString pattern == clause_)
(getPatterns cases_)

isClauseStringPattern =
List.any isStringPattern (getPatterns cases)
in
if not (findClause clause cases) then
let
rangeToInsert : Maybe ( Range, Int, Int )
rangeToInsert =
rangeToInsertClause insertAt cases expression |> Just
rangeToInsertClause insertAt isClauseStringPattern cases expression |> Just
in
( [ errorWithFix customError clause functionCall declaration.expression rangeToInsert ], context )
( [ errorWithFix customError isClauseStringPattern clause functionCall declaration.expression rangeToInsert ], context )

else
( [], context )
Expand All @@ -206,8 +209,8 @@ visitFunction namespace clause functionCall ignored function insertAt customErro
( [], context )


rangeToInsertClause : InsertAt -> List Case -> Node Expression -> ( Range, Int, Int )
rangeToInsertClause insertAt cases expression =
rangeToInsertClause : InsertAt -> Bool -> List Case -> Node Expression -> ( Range, Int, Int )
rangeToInsertClause insertAt isClauseStringPattern cases expression =
let
lastClauseExpression =
cases
Expand All @@ -226,11 +229,18 @@ rangeToInsertClause insertAt cases expression =
case insertAt of
After previousClause ->
let
normalizedPreviousClause =
if isClauseStringPattern then
escapeString previousClause

else
previousClause

previousClausePattern =
cases
|> List.Extra.find
(\( pattern, _ ) ->
nodePatternToString pattern == previousClause
nodePatternToString pattern == normalizedPreviousClause
)
in
case previousClausePattern of
Expand Down Expand Up @@ -259,8 +269,8 @@ rangeToInsertClause insertAt cases expression =
( range, 2, lastClauseStartingColumn )


errorWithFix : CustomError -> String -> String -> Node a -> Maybe ( Range, Int, Int ) -> Error {}
errorWithFix (CustomError customError) clause functionCall node errorRange =
errorWithFix : CustomError -> Bool -> String -> String -> Node a -> Maybe ( Range, Int, Int ) -> Error {}
errorWithFix (CustomError customError) isClauseStringPattern clause functionCall node errorRange =
Rule.errorWithFix
customError
(Node.range node)
Expand All @@ -273,18 +283,25 @@ errorWithFix (CustomError customError) clause functionCall node errorRange =
prefix =
"\n" ++ String.repeat horizontalOffset " "
in
[ addMissingCase insertionPoint prefix clause functionCall ]
[ addMissingCase insertionPoint isClauseStringPattern prefix clause functionCall ]

Nothing ->
[]
)


addMissingCase : { row : Int, column : Int } -> String -> String -> String -> Fix
addMissingCase { row, column } prefix clause functionCall =
addMissingCase : { row : Int, column : Int } -> Bool -> String -> String -> String -> Fix
addMissingCase { row, column } isClauseStringPattern prefix clause functionCall =
let
clauseToAdd =
if isClauseStringPattern then
escapeString clause

else
clause

insertion =
prefix ++ clause ++ " -> " ++ functionCall ++ "\n\n"
prefix ++ clauseToAdd ++ " -> " ++ functionCall ++ "\n\n"
in
Fix.insertAt { row = row, column = column } insertion

Expand Down Expand Up @@ -436,3 +453,27 @@ nodePatternToString node =
node
|> Node.value
|> patternToString


isStringPattern : Pattern -> Bool
isStringPattern pattern =
case pattern of
StringPattern _ ->
True

_ ->
False


escapeString : String -> String
escapeString str =
if isStringScaped str then
str

else
"\"" ++ str ++ "\""


isStringScaped : String -> Bool
isStringScaped str =
String.startsWith "\\" str
108 changes: 108 additions & 0 deletions tests/Install/ClauseInCaseTest2.elm
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
module Install.ClauseInCaseTest2 exposing (all)

import Install.ClauseInCase
import Review.Rule exposing (Rule)
import Run
import Test exposing (Test, describe)

Expand All @@ -12,13 +13,15 @@ all =
, Run.testFix test1b
, Run.testFix test1c
, Run.testFix test2
, Run.testFix test3
]



-- TEST 1


test1a : { description : String, src : String, rule : Rule, under : String, fixed : String, message : String }
test1a =
{ description = "Test 1a, simple makeRule: should report an error and fix it"
, src = src1
Expand All @@ -29,6 +32,7 @@ test1a =
}


test1b : { description : String, src : String, rule : Rule, under : String, fixed : String, message : String }
test1b =
{ description = "Test 1b, withInsertAfter CounterIncremented: should report an error and fix it"
, src = src1
Expand All @@ -39,6 +43,7 @@ test1b =
}


test1c : { description : String, src : String, rule : Rule, under : String, fixed : String, message : String }
test1c =
{ description = "Test 1c, withInsertAtBeginning: should report an error and fix it"
, src = src1
Expand All @@ -49,23 +54,27 @@ test1c =
}


rule1a : Rule
rule1a =
Install.ClauseInCase.init "Backend" "updateFromFrontend" "ResetCounter" "( { model | counter = 0 }, broadcast (CounterNewValue 0 clientId) )"
|> Install.ClauseInCase.makeRule


rule1b : Rule
rule1b =
Install.ClauseInCase.init "Backend" "updateFromFrontend" "ResetCounter" "( { model | counter = 0 }, broadcast (CounterNewValue 0 clientId) )"
|> Install.ClauseInCase.withInsertAfter "CounterIncremented"
|> Install.ClauseInCase.makeRule


rule1c : Rule
rule1c =
Install.ClauseInCase.init "Backend" "updateFromFrontend" "ResetCounter" "( { model | counter = 0 }, broadcast (CounterNewValue 0 clientId) )"
|> Install.ClauseInCase.withInsertAtBeginning
|> Install.ClauseInCase.makeRule


src1 : String
src1 =
"""module Backend exposing (..)
Expand All @@ -83,6 +92,7 @@ updateFromFrontend sessionId clientId msg model =
"""


fixed1 : String
fixed1 =
"""module Backend exposing (..)
Expand All @@ -103,6 +113,7 @@ updateFromFrontend sessionId clientId msg model =
"""


fixed1c : String
fixed1c =
"""module Backend exposing (..)
Expand All @@ -123,6 +134,7 @@ updateFromFrontend sessionId clientId msg model =
"""


under1 : String
under1 =
"""case msg of
CounterIncremented ->
Expand All @@ -137,6 +149,7 @@ under1 =
-- TEST 2


test2 : { description : String, src : String, rule : Rule, under : String, fixed : String, message : String }
test2 =
{ description = "Test 2 (Reset, Frontend.update): should report an error and fix it"
, src = src2
Expand All @@ -147,12 +160,14 @@ test2 =
}


rule2 : Rule
rule2 =
Install.ClauseInCase.init "Frontend" "update" "Reset" "( { model | counter = 0 }, sendToBackend CounterReset )"
|> Install.ClauseInCase.withInsertAfter "Increment"
|> Install.ClauseInCase.makeRule


src2 : String
src2 =
"""module Frontend exposing (Model, app)
Expand All @@ -170,6 +185,7 @@ update msg model =
"""


fixed2 : String
fixed2 =
"""module Frontend exposing (Model, app)
Expand All @@ -190,6 +206,7 @@ update msg model =
"""


under2 : String
under2 =
"""case msg of
Increment ->
Expand All @@ -200,3 +217,94 @@ under2 =
FNoop ->
( model, Cmd.none )"""



-- TEST 3


test3 : { description : String, src : String, rule : Rule, under : String, fixed : String, message : String }
test3 =
{ description = "Test 2: should escape string pattern when is a case of string patterns"
, src = src3
, rule = rule3
, under = under3
, fixed = fixed3
, message = "Add handler for Aspasia"
}


src3 : String
src3 =
"""module Philosopher exposing (Philosopher(..), stringToPhilosopher)
type Philosopher
= Socrates
| Plato
| Aristotle
stringToPhilosopher : String -> Maybe Philosopher
stringToPhilosopher str =
case str of
"Socrates" ->
Just Socrates
"Plato" ->
Just Plato
"Aristotle" ->
Just Aristotle
_ ->
Nothing"""


rule3 : Rule
rule3 =
Install.ClauseInCase.init "Philosopher" "stringToPhilosopher" "Aspasia" "Just Aspasia"
|> Install.ClauseInCase.withInsertAfter "Aristotle"
|> Install.ClauseInCase.makeRule


under3 : String
under3 =
"""case str of
"Socrates" ->
Just Socrates
"Plato" ->
Just Plato
"Aristotle" ->
Just Aristotle
_ ->
Nothing"""


fixed3 : String
fixed3 =
"""module Philosopher exposing (Philosopher(..), stringToPhilosopher)
type Philosopher
= Socrates
| Plato
| Aristotle
stringToPhilosopher : String -> Maybe Philosopher
stringToPhilosopher str =
case str of
"Socrates" ->
Just Socrates
"Plato" ->
Just Plato
"Aristotle" ->
Just Aristotle
"Aspasia" -> Just Aspasia
_ ->
Nothing"""

0 comments on commit 913cd24

Please sign in to comment.