@@ -727,20 +727,30 @@ func assertParse<S: SyntaxProtocol>(
727727 }
728728}
729729
730+ /// Removes trivia from all tokens that don’t occur inside multiline string
731+ /// literals.
732+ ///
733+ /// We keep trivia inside multiline string literals because the indentation of
734+ /// the closing quote of a multi-line string literals has impact on how much
735+ /// leading trivia is stripped from the literal’s content.
730736class TriviaRemover : SyntaxRewriter {
731- override func visit( _ token: TokenSyntax ) -> TokenSyntax {
732- var ancestor = Syntax ( token)
733- while let parent = ancestor. parent {
734- ancestor = parent
735- if ancestor. is ( StringLiteralExprSyntax . self) || ancestor. is ( RegexLiteralExprSyntax . self) || ancestor. is ( SimpleStringLiteralExprSyntax . self) {
736- // Don't mess with indentation inside string or regex literals.
737- // BasicFormat doesn't know where to re-apply newlines and how much to indent the string literal contents.
738- return token
739- }
737+ override func visit( _ node: StringLiteralExprSyntax ) -> ExprSyntax {
738+ if node. openingQuote. tokenKind == . multilineStringQuote {
739+ return ExprSyntax ( node)
740+ } else {
741+ return super. visit ( node)
740742 }
741- if token. parent? . is ( StringSegmentSyntax . self) ?? false {
742- return token
743+ }
744+
745+ override func visit( _ node: SimpleStringLiteralExprSyntax ) -> ExprSyntax {
746+ if node. openingQuote. tokenKind == . multilineStringQuote {
747+ return ExprSyntax ( node)
748+ } else {
749+ return super. visit ( node)
743750 }
751+ }
752+
753+ override func visit( _ token: TokenSyntax ) -> TokenSyntax {
744754 return token. with ( \. leadingTrivia, [ ] ) . with ( \. trailingTrivia, [ ] )
745755 }
746756}
0 commit comments