From 22347b8ce68ea955dbf9d9cbb7c2a737391984d0 Mon Sep 17 00:00:00 2001 From: Jakub Florek Date: Mon, 29 Jul 2024 21:15:53 +0200 Subject: [PATCH 1/6] Adjust closure capture syntax node. --- .../Sources/SyntaxSupport/ExprNodes.swift | 12 +-- .../IdentifiableSyntax.swift | 7 +- Sources/SwiftParser/Expressions.swift | 37 ++++----- Sources/SwiftParser/Parameters.swift | 4 +- Sources/SwiftSyntax/Convenience.swift | 27 ------ .../generated/ChildNameForKeyPath.swift | 16 ++-- .../RenamedChildrenCompatibility.swift | 67 --------------- .../generated/raw/RawSyntaxNodesC.swift | 50 +++++------ .../generated/raw/RawSyntaxValidation.swift | 10 +-- .../generated/syntaxNodes/SyntaxNodesC.swift | 82 ++++++------------- .../syntaxNodes/SyntaxNodesGHI.swift | 1 + Tests/SwiftParserTest/TypeTests.swift | 4 +- Tests/SwiftSyntaxTest/SyntaxTests.swift | 8 -- 13 files changed, 81 insertions(+), 244 deletions(-) diff --git a/CodeGeneration/Sources/SyntaxSupport/ExprNodes.swift b/CodeGeneration/Sources/SyntaxSupport/ExprNodes.swift index 1d75123631e..bf0e51e3863 100644 --- a/CodeGeneration/Sources/SyntaxSupport/ExprNodes.swift +++ b/CodeGeneration/Sources/SyntaxSupport/ExprNodes.swift @@ -341,19 +341,13 @@ public let EXPR_NODES: [Node] = [ ), Child( name: "name", - kind: .token(choices: [.token(.identifier)]), - isOptional: true + kind: .token(choices: [.token(.identifier)]) ), Child( - name: "equal", - deprecatedName: "assignToken", - kind: .token(choices: [.token(.equal)]), + name: "initializer", + kind: .node(kind: .initializerClause), isOptional: true ), - Child( - name: "expression", - kind: .node(kind: .expr) - ), Child( name: "trailingComma", kind: .token(choices: [.token(.comma)]), diff --git a/Sources/SwiftLexicalLookup/IdentifiableSyntax.swift b/Sources/SwiftLexicalLookup/IdentifiableSyntax.swift index 67e6de6b4e9..ffb0442e254 100644 --- a/Sources/SwiftLexicalLookup/IdentifiableSyntax.swift +++ b/Sources/SwiftLexicalLookup/IdentifiableSyntax.swift @@ -33,11 +33,6 @@ extension ClosureShorthandParameterSyntax: IdentifiableSyntax { extension ClosureCaptureSyntax: IdentifiableSyntax { @_spi(Experimental) public var identifier: TokenSyntax { - /* Doesn't work with closures like: - _ = { [y=1+2] in - print(y) - } - */ - expression.as(DeclReferenceExprSyntax.self)!.baseName + name } } diff --git a/Sources/SwiftParser/Expressions.swift b/Sources/SwiftParser/Expressions.swift index 6bdc159dcaf..2c9472045d3 100644 --- a/Sources/SwiftParser/Expressions.swift +++ b/Sources/SwiftParser/Expressions.swift @@ -1615,7 +1615,7 @@ extension Parser { } extension Parser { - mutating func parseDefaultArgument() -> RawInitializerClauseSyntax { + mutating func parseInitializerClause() -> RawInitializerClauseSyntax { let unexpectedBeforeEq: RawUnexpectedNodesSyntax? let eq: RawTokenSyntax if let comparison = self.consumeIfContextualPunctuator("==") { @@ -1704,29 +1704,28 @@ extension Parser { let specifier = self.parseClosureCaptureSpecifiers() // The thing being capture specified is an identifier, or as an identifier - // followed by an expression. + // followed by an initializer clause. let unexpectedBeforeName: RawUnexpectedNodesSyntax? - let name: RawTokenSyntax? - let unexpectedBeforeEqual: RawUnexpectedNodesSyntax? - let equal: RawTokenSyntax? - let expression: RawExprSyntax + let name: RawTokenSyntax + let initializer: RawInitializerClauseSyntax? if self.peek(isAt: .equal) { - // The name is a new declaration. + // The name is a new declaration with + // initializer clause. (unexpectedBeforeName, name) = self.expect( .identifier, TokenSpec(.self, remapping: .identifier), default: .identifier ) - (unexpectedBeforeEqual, equal) = self.expect(.equal) - expression = self.parseExpression(flavor: .basic, pattern: .none) + initializer = self.parseInitializerClause() } else { - // This is the simple case - the identifier is both the name and - // the expression to capture. - unexpectedBeforeName = nil - name = nil - unexpectedBeforeEqual = nil - equal = nil - expression = RawExprSyntax(self.parseIdentifierExpression(flavor: .basic)) + // This is the simple case - the identifier is the name and + // the initializer clause is empty. + (unexpectedBeforeName, name) = self.expect( + .identifier, + TokenSpec(.self), + default: .identifier + ) + initializer = nil } keepGoing = self.consume(if: .comma) @@ -1735,11 +1734,9 @@ extension Parser { specifier: specifier, unexpectedBeforeName, name: name, - unexpectedBeforeEqual, - equal: equal, - expression: expression, + initializer: initializer, trailingComma: keepGoing, - arena: self.arena + arena: arena ) ) } while keepGoing != nil && self.hasProgressed(&loopProgress) diff --git a/Sources/SwiftParser/Parameters.swift b/Sources/SwiftParser/Parameters.swift index 06354b5837b..3b0af8b2f6e 100644 --- a/Sources/SwiftParser/Parameters.swift +++ b/Sources/SwiftParser/Parameters.swift @@ -129,7 +129,7 @@ extension Parser { let defaultValue: RawInitializerClauseSyntax? if self.at(.equal) || self.atContextualPunctuator("==") { - defaultValue = self.parseDefaultArgument() + defaultValue = self.parseInitializerClause() } else { defaultValue = nil } @@ -234,7 +234,7 @@ extension Parser { let defaultValue: RawInitializerClauseSyntax? if self.at(.equal) || self.atContextualPunctuator("==") { - defaultValue = self.parseDefaultArgument() + defaultValue = self.parseInitializerClause() } else { defaultValue = nil } diff --git a/Sources/SwiftSyntax/Convenience.swift b/Sources/SwiftSyntax/Convenience.swift index 3c0c51bad5c..36b2e11e9ac 100644 --- a/Sources/SwiftSyntax/Convenience.swift +++ b/Sources/SwiftSyntax/Convenience.swift @@ -10,33 +10,6 @@ // //===----------------------------------------------------------------------===// -extension ClosureCaptureSyntax { - - /// Creates a ``ClosureCaptureSyntax`` with a `name`, and automatically adds an `equal` token to it since the name is non-optional. - /// - /// - SeeAlso: ``ClosureCaptureSyntax/init(leadingTrivia:_:specifier:_:name:_:equal:_:expression:_:trailingComma:_:trailingTrivia:)``. - /// - public init( - leadingTrivia: Trivia? = nil, - specifier: ClosureCaptureSpecifierSyntax? = nil, - name: TokenSyntax, - equal: TokenSyntax = TokenSyntax.equalToken(), - expression: some ExprSyntaxProtocol, - trailingComma: TokenSyntax? = nil, - trailingTrivia: Trivia? = nil - ) { - self.init( - leadingTrivia: leadingTrivia, - specifier: specifier, - name: name as TokenSyntax?, - equal: equal, - expression: expression, - trailingComma: trailingComma, - trailingTrivia: trailingTrivia - ) - } -} - extension EnumCaseParameterSyntax { /// Creates an ``EnumCaseParameterSyntax`` with a `firstName`, and automatically adds a `colon` to it. diff --git a/Sources/SwiftSyntax/generated/ChildNameForKeyPath.swift b/Sources/SwiftSyntax/generated/ChildNameForKeyPath.swift index b328be7cf7d..0779415c327 100644 --- a/Sources/SwiftSyntax/generated/ChildNameForKeyPath.swift +++ b/Sources/SwiftSyntax/generated/ChildNameForKeyPath.swift @@ -499,16 +499,12 @@ public func childName(_ keyPath: AnyKeyPath) -> String? { return "unexpectedBetweenSpecifierAndName" case \ClosureCaptureSyntax.name: return "name" - case \ClosureCaptureSyntax.unexpectedBetweenNameAndEqual: - return "unexpectedBetweenNameAndEqual" - case \ClosureCaptureSyntax.equal: - return "equal" - case \ClosureCaptureSyntax.unexpectedBetweenEqualAndExpression: - return "unexpectedBetweenEqualAndExpression" - case \ClosureCaptureSyntax.expression: - return "expression" - case \ClosureCaptureSyntax.unexpectedBetweenExpressionAndTrailingComma: - return "unexpectedBetweenExpressionAndTrailingComma" + case \ClosureCaptureSyntax.unexpectedBetweenNameAndInitializer: + return "unexpectedBetweenNameAndInitializer" + case \ClosureCaptureSyntax.initializer: + return "initializer" + case \ClosureCaptureSyntax.unexpectedBetweenInitializerAndTrailingComma: + return "unexpectedBetweenInitializerAndTrailingComma" case \ClosureCaptureSyntax.trailingComma: return "trailingComma" case \ClosureCaptureSyntax.unexpectedAfterTrailingComma: diff --git a/Sources/SwiftSyntax/generated/RenamedChildrenCompatibility.swift b/Sources/SwiftSyntax/generated/RenamedChildrenCompatibility.swift index c798061a9e6..a1b26254cbf 100644 --- a/Sources/SwiftSyntax/generated/RenamedChildrenCompatibility.swift +++ b/Sources/SwiftSyntax/generated/RenamedChildrenCompatibility.swift @@ -1167,73 +1167,6 @@ extension ClassDeclSyntax { } } -extension ClosureCaptureSyntax { - @available(*, deprecated, renamed: "unexpectedBetweenNameAndEqual") - public var unexpectedBetweenNameAndAssignToken: UnexpectedNodesSyntax? { - get { - return unexpectedBetweenNameAndEqual - } - set { - unexpectedBetweenNameAndEqual = newValue - } - } - - @available(*, deprecated, renamed: "equal") - public var assignToken: TokenSyntax? { - get { - return equal - } - set { - equal = newValue - } - } - - @available(*, deprecated, renamed: "unexpectedBetweenEqualAndExpression") - public var unexpectedBetweenAssignTokenAndExpression: UnexpectedNodesSyntax? { - get { - return unexpectedBetweenEqualAndExpression - } - set { - unexpectedBetweenEqualAndExpression = newValue - } - } - - @available(*, deprecated, renamed: "ClosureCaptureSyntax(leadingTrivia:_:specifier:_:name:_:equal:_:expression:_:trailingComma:_:trailingTrivia:)") - @_disfavoredOverload - public init( - leadingTrivia: Trivia? = nil, - _ unexpectedBeforeSpecifier: UnexpectedNodesSyntax? = nil, - specifier: ClosureCaptureSpecifierSyntax? = nil, - _ unexpectedBetweenSpecifierAndName: UnexpectedNodesSyntax? = nil, - name: TokenSyntax? = nil, - _ unexpectedBetweenNameAndAssignToken: UnexpectedNodesSyntax? = nil, - assignToken: TokenSyntax? = nil, - _ unexpectedBetweenAssignTokenAndExpression: UnexpectedNodesSyntax? = nil, - expression: some ExprSyntaxProtocol, - _ unexpectedBetweenExpressionAndTrailingComma: UnexpectedNodesSyntax? = nil, - trailingComma: TokenSyntax? = nil, - _ unexpectedAfterTrailingComma: UnexpectedNodesSyntax? = nil, - trailingTrivia: Trivia? = nil - - ) { - self.init( - leadingTrivia: leadingTrivia, - unexpectedBeforeSpecifier, - specifier: specifier, - unexpectedBetweenSpecifierAndName, - name: name, - unexpectedBetweenNameAndAssignToken, - equal: assignToken, - unexpectedBetweenAssignTokenAndExpression, - expression: expression, - unexpectedBetweenExpressionAndTrailingComma, - trailingComma: trailingComma, - unexpectedAfterTrailingComma, - trailingTrivia: trailingTrivia - ) - } -} - extension ClosureParameterClauseSyntax { @available(*, deprecated, renamed: "unexpectedBetweenLeftParenAndParameters") public var unexpectedBetweenLeftParenAndParameterList: UnexpectedNodesSyntax? { diff --git a/Sources/SwiftSyntax/generated/raw/RawSyntaxNodesC.swift b/Sources/SwiftSyntax/generated/raw/RawSyntaxNodesC.swift index ba466a6adff..79c158bf4b5 100644 --- a/Sources/SwiftSyntax/generated/raw/RawSyntaxNodesC.swift +++ b/Sources/SwiftSyntax/generated/raw/RawSyntaxNodesC.swift @@ -935,30 +935,26 @@ public struct RawClosureCaptureSyntax: RawSyntaxNodeProtocol { _ unexpectedBeforeSpecifier: RawUnexpectedNodesSyntax? = nil, specifier: RawClosureCaptureSpecifierSyntax?, _ unexpectedBetweenSpecifierAndName: RawUnexpectedNodesSyntax? = nil, - name: RawTokenSyntax?, - _ unexpectedBetweenNameAndEqual: RawUnexpectedNodesSyntax? = nil, - equal: RawTokenSyntax?, - _ unexpectedBetweenEqualAndExpression: RawUnexpectedNodesSyntax? = nil, - expression: RawExprSyntax, - _ unexpectedBetweenExpressionAndTrailingComma: RawUnexpectedNodesSyntax? = nil, + name: RawTokenSyntax, + _ unexpectedBetweenNameAndInitializer: RawUnexpectedNodesSyntax? = nil, + initializer: RawInitializerClauseSyntax?, + _ unexpectedBetweenInitializerAndTrailingComma: RawUnexpectedNodesSyntax? = nil, trailingComma: RawTokenSyntax?, _ unexpectedAfterTrailingComma: RawUnexpectedNodesSyntax? = nil, arena: __shared SyntaxArena ) { let raw = RawSyntax.makeLayout( - kind: .closureCapture, uninitializedCount: 11, arena: arena) { layout in + kind: .closureCapture, uninitializedCount: 9, arena: arena) { layout in layout.initialize(repeating: nil) layout[0] = unexpectedBeforeSpecifier?.raw layout[1] = specifier?.raw layout[2] = unexpectedBetweenSpecifierAndName?.raw - layout[3] = name?.raw - layout[4] = unexpectedBetweenNameAndEqual?.raw - layout[5] = equal?.raw - layout[6] = unexpectedBetweenEqualAndExpression?.raw - layout[7] = expression.raw - layout[8] = unexpectedBetweenExpressionAndTrailingComma?.raw - layout[9] = trailingComma?.raw - layout[10] = unexpectedAfterTrailingComma?.raw + layout[3] = name.raw + layout[4] = unexpectedBetweenNameAndInitializer?.raw + layout[5] = initializer?.raw + layout[6] = unexpectedBetweenInitializerAndTrailingComma?.raw + layout[7] = trailingComma?.raw + layout[8] = unexpectedAfterTrailingComma?.raw } self.init(unchecked: raw) } @@ -975,36 +971,28 @@ public struct RawClosureCaptureSyntax: RawSyntaxNodeProtocol { layoutView.children[2].map(RawUnexpectedNodesSyntax.init(raw:)) } - public var name: RawTokenSyntax? { - layoutView.children[3].map(RawTokenSyntax.init(raw:)) + public var name: RawTokenSyntax { + layoutView.children[3].map(RawTokenSyntax.init(raw:))! } - public var unexpectedBetweenNameAndEqual: RawUnexpectedNodesSyntax? { + public var unexpectedBetweenNameAndInitializer: RawUnexpectedNodesSyntax? { layoutView.children[4].map(RawUnexpectedNodesSyntax.init(raw:)) } - public var equal: RawTokenSyntax? { - layoutView.children[5].map(RawTokenSyntax.init(raw:)) + public var initializer: RawInitializerClauseSyntax? { + layoutView.children[5].map(RawInitializerClauseSyntax.init(raw:)) } - public var unexpectedBetweenEqualAndExpression: RawUnexpectedNodesSyntax? { + public var unexpectedBetweenInitializerAndTrailingComma: RawUnexpectedNodesSyntax? { layoutView.children[6].map(RawUnexpectedNodesSyntax.init(raw:)) } - public var expression: RawExprSyntax { - layoutView.children[7].map(RawExprSyntax.init(raw:))! - } - - public var unexpectedBetweenExpressionAndTrailingComma: RawUnexpectedNodesSyntax? { - layoutView.children[8].map(RawUnexpectedNodesSyntax.init(raw:)) - } - public var trailingComma: RawTokenSyntax? { - layoutView.children[9].map(RawTokenSyntax.init(raw:)) + layoutView.children[7].map(RawTokenSyntax.init(raw:)) } public var unexpectedAfterTrailingComma: RawUnexpectedNodesSyntax? { - layoutView.children[10].map(RawUnexpectedNodesSyntax.init(raw:)) + layoutView.children[8].map(RawUnexpectedNodesSyntax.init(raw:)) } } diff --git a/Sources/SwiftSyntax/generated/raw/RawSyntaxValidation.swift b/Sources/SwiftSyntax/generated/raw/RawSyntaxValidation.swift index 9896d11e81d..0c5cf183dbc 100644 --- a/Sources/SwiftSyntax/generated/raw/RawSyntaxValidation.swift +++ b/Sources/SwiftSyntax/generated/raw/RawSyntaxValidation.swift @@ -563,18 +563,16 @@ func validateLayout(layout: RawSyntaxBuffer, as kind: SyntaxKind) { assertNoError(kind, 7, verify(layout[7], as: RawTokenSyntax?.self, tokenChoices: [.tokenKind(.rightParen)])) assertNoError(kind, 8, verify(layout[8], as: RawUnexpectedNodesSyntax?.self)) case .closureCapture: - assert(layout.count == 11) + assert(layout.count == 9) assertNoError(kind, 0, verify(layout[0], as: RawUnexpectedNodesSyntax?.self)) assertNoError(kind, 1, verify(layout[1], as: RawClosureCaptureSpecifierSyntax?.self)) assertNoError(kind, 2, verify(layout[2], as: RawUnexpectedNodesSyntax?.self)) - assertNoError(kind, 3, verify(layout[3], as: RawTokenSyntax?.self, tokenChoices: [.tokenKind(.identifier)])) + assertNoError(kind, 3, verify(layout[3], as: RawTokenSyntax.self, tokenChoices: [.tokenKind(.identifier)])) assertNoError(kind, 4, verify(layout[4], as: RawUnexpectedNodesSyntax?.self)) - assertNoError(kind, 5, verify(layout[5], as: RawTokenSyntax?.self, tokenChoices: [.tokenKind(.equal)])) + assertNoError(kind, 5, verify(layout[5], as: RawInitializerClauseSyntax?.self)) assertNoError(kind, 6, verify(layout[6], as: RawUnexpectedNodesSyntax?.self)) - assertNoError(kind, 7, verify(layout[7], as: RawExprSyntax.self)) + assertNoError(kind, 7, verify(layout[7], as: RawTokenSyntax?.self, tokenChoices: [.tokenKind(.comma)])) assertNoError(kind, 8, verify(layout[8], as: RawUnexpectedNodesSyntax?.self)) - assertNoError(kind, 9, verify(layout[9], as: RawTokenSyntax?.self, tokenChoices: [.tokenKind(.comma)])) - assertNoError(kind, 10, verify(layout[10], as: RawUnexpectedNodesSyntax?.self)) case .closureExpr: assert(layout.count == 9) assertNoError(kind, 0, verify(layout[0], as: RawUnexpectedNodesSyntax?.self)) diff --git a/Sources/SwiftSyntax/generated/syntaxNodes/SyntaxNodesC.swift b/Sources/SwiftSyntax/generated/syntaxNodes/SyntaxNodesC.swift index bfdce0dd3ce..6bdb2e5ca8e 100644 --- a/Sources/SwiftSyntax/generated/syntaxNodes/SyntaxNodesC.swift +++ b/Sources/SwiftSyntax/generated/syntaxNodes/SyntaxNodesC.swift @@ -1528,9 +1528,8 @@ public struct ClosureCaptureSpecifierSyntax: SyntaxProtocol, SyntaxHashable, _Le /// ### Children /// /// - `specifier`: ``ClosureCaptureSpecifierSyntax``? -/// - `name`: ``? -/// - `equal`: `=`? -/// - `expression`: ``ExprSyntax`` +/// - `name`: `` +/// - `initializer`: ``InitializerClauseSyntax``? /// - `trailingComma`: `,`? /// /// ### Contained in @@ -1554,12 +1553,10 @@ public struct ClosureCaptureSyntax: SyntaxProtocol, SyntaxHashable, _LeafSyntaxN _ unexpectedBeforeSpecifier: UnexpectedNodesSyntax? = nil, specifier: ClosureCaptureSpecifierSyntax? = nil, _ unexpectedBetweenSpecifierAndName: UnexpectedNodesSyntax? = nil, - name: TokenSyntax? = nil, - _ unexpectedBetweenNameAndEqual: UnexpectedNodesSyntax? = nil, - equal: TokenSyntax? = nil, - _ unexpectedBetweenEqualAndExpression: UnexpectedNodesSyntax? = nil, - expression: some ExprSyntaxProtocol, - _ unexpectedBetweenExpressionAndTrailingComma: UnexpectedNodesSyntax? = nil, + name: TokenSyntax, + _ unexpectedBetweenNameAndInitializer: UnexpectedNodesSyntax? = nil, + initializer: InitializerClauseSyntax? = nil, + _ unexpectedBetweenInitializerAndTrailingComma: UnexpectedNodesSyntax? = nil, trailingComma: TokenSyntax? = nil, _ unexpectedAfterTrailingComma: UnexpectedNodesSyntax? = nil, trailingTrivia: Trivia? = nil @@ -1572,11 +1569,9 @@ public struct ClosureCaptureSyntax: SyntaxProtocol, SyntaxHashable, _LeafSyntaxN specifier, unexpectedBetweenSpecifierAndName, name, - unexpectedBetweenNameAndEqual, - equal, - unexpectedBetweenEqualAndExpression, - expression, - unexpectedBetweenExpressionAndTrailingComma, + unexpectedBetweenNameAndInitializer, + initializer, + unexpectedBetweenInitializerAndTrailingComma, trailingComma, unexpectedAfterTrailingComma ))) { (arena, _) in @@ -1584,12 +1579,10 @@ public struct ClosureCaptureSyntax: SyntaxProtocol, SyntaxHashable, _LeafSyntaxN unexpectedBeforeSpecifier?.raw, specifier?.raw, unexpectedBetweenSpecifierAndName?.raw, - name?.raw, - unexpectedBetweenNameAndEqual?.raw, - equal?.raw, - unexpectedBetweenEqualAndExpression?.raw, - expression.raw, - unexpectedBetweenExpressionAndTrailingComma?.raw, + name.raw, + unexpectedBetweenNameAndInitializer?.raw, + initializer?.raw, + unexpectedBetweenInitializerAndTrailingComma?.raw, trailingComma?.raw, unexpectedAfterTrailingComma?.raw ] @@ -1635,16 +1628,16 @@ public struct ClosureCaptureSyntax: SyntaxProtocol, SyntaxHashable, _LeafSyntaxN /// ### Tokens /// /// For syntax trees generated by the parser, this is guaranteed to be ``. - public var name: TokenSyntax? { + public var name: TokenSyntax { get { - return Syntax(self).child(at: 3)?.cast(TokenSyntax.self) + return Syntax(self).child(at: 3)!.cast(TokenSyntax.self) } set(value) { self = Syntax(self).replacingChild(at: 3, with: Syntax(value), arena: SyntaxArena()).cast(ClosureCaptureSyntax.self) } } - public var unexpectedBetweenNameAndEqual: UnexpectedNodesSyntax? { + public var unexpectedBetweenNameAndInitializer: UnexpectedNodesSyntax? { get { return Syntax(self).child(at: 4)?.cast(UnexpectedNodesSyntax.self) } @@ -1653,19 +1646,16 @@ public struct ClosureCaptureSyntax: SyntaxProtocol, SyntaxHashable, _LeafSyntaxN } } - /// ### Tokens - /// - /// For syntax trees generated by the parser, this is guaranteed to be `=`. - public var equal: TokenSyntax? { + public var initializer: InitializerClauseSyntax? { get { - return Syntax(self).child(at: 5)?.cast(TokenSyntax.self) + return Syntax(self).child(at: 5)?.cast(InitializerClauseSyntax.self) } set(value) { self = Syntax(self).replacingChild(at: 5, with: Syntax(value), arena: SyntaxArena()).cast(ClosureCaptureSyntax.self) } } - public var unexpectedBetweenEqualAndExpression: UnexpectedNodesSyntax? { + public var unexpectedBetweenInitializerAndTrailingComma: UnexpectedNodesSyntax? { get { return Syntax(self).child(at: 6)?.cast(UnexpectedNodesSyntax.self) } @@ -1674,42 +1664,24 @@ public struct ClosureCaptureSyntax: SyntaxProtocol, SyntaxHashable, _LeafSyntaxN } } - public var expression: ExprSyntax { - get { - return Syntax(self).child(at: 7)!.cast(ExprSyntax.self) - } - set(value) { - self = Syntax(self).replacingChild(at: 7, with: Syntax(value), arena: SyntaxArena()).cast(ClosureCaptureSyntax.self) - } - } - - public var unexpectedBetweenExpressionAndTrailingComma: UnexpectedNodesSyntax? { - get { - return Syntax(self).child(at: 8)?.cast(UnexpectedNodesSyntax.self) - } - set(value) { - self = Syntax(self).replacingChild(at: 8, with: Syntax(value), arena: SyntaxArena()).cast(ClosureCaptureSyntax.self) - } - } - /// ### Tokens /// /// For syntax trees generated by the parser, this is guaranteed to be `,`. public var trailingComma: TokenSyntax? { get { - return Syntax(self).child(at: 9)?.cast(TokenSyntax.self) + return Syntax(self).child(at: 7)?.cast(TokenSyntax.self) } set(value) { - self = Syntax(self).replacingChild(at: 9, with: Syntax(value), arena: SyntaxArena()).cast(ClosureCaptureSyntax.self) + self = Syntax(self).replacingChild(at: 7, with: Syntax(value), arena: SyntaxArena()).cast(ClosureCaptureSyntax.self) } } public var unexpectedAfterTrailingComma: UnexpectedNodesSyntax? { get { - return Syntax(self).child(at: 10)?.cast(UnexpectedNodesSyntax.self) + return Syntax(self).child(at: 8)?.cast(UnexpectedNodesSyntax.self) } set(value) { - self = Syntax(self).replacingChild(at: 10, with: Syntax(value), arena: SyntaxArena()).cast(ClosureCaptureSyntax.self) + self = Syntax(self).replacingChild(at: 8, with: Syntax(value), arena: SyntaxArena()).cast(ClosureCaptureSyntax.self) } } @@ -1718,11 +1690,9 @@ public struct ClosureCaptureSyntax: SyntaxProtocol, SyntaxHashable, _LeafSyntaxN \Self.specifier, \Self.unexpectedBetweenSpecifierAndName, \Self.name, - \Self.unexpectedBetweenNameAndEqual, - \Self.equal, - \Self.unexpectedBetweenEqualAndExpression, - \Self.expression, - \Self.unexpectedBetweenExpressionAndTrailingComma, + \Self.unexpectedBetweenNameAndInitializer, + \Self.initializer, + \Self.unexpectedBetweenInitializerAndTrailingComma, \Self.trailingComma, \Self.unexpectedAfterTrailingComma ]) diff --git a/Sources/SwiftSyntax/generated/syntaxNodes/SyntaxNodesGHI.swift b/Sources/SwiftSyntax/generated/syntaxNodes/SyntaxNodesGHI.swift index 2a4290515da..c72423c0f2e 100644 --- a/Sources/SwiftSyntax/generated/syntaxNodes/SyntaxNodesGHI.swift +++ b/Sources/SwiftSyntax/generated/syntaxNodes/SyntaxNodesGHI.swift @@ -3746,6 +3746,7 @@ public struct InheritedTypeSyntax: SyntaxProtocol, SyntaxHashable, _LeafSyntaxNo /// /// ### Contained in /// +/// - ``ClosureCaptureSyntax``.``ClosureCaptureSyntax/initializer`` /// - ``EnumCaseElementSyntax``.``EnumCaseElementSyntax/rawValue`` /// - ``EnumCaseParameterSyntax``.``EnumCaseParameterSyntax/defaultValue`` /// - ``FunctionParameterSyntax``.``FunctionParameterSyntax/defaultValue`` diff --git a/Tests/SwiftParserTest/TypeTests.swift b/Tests/SwiftParserTest/TypeTests.swift index 496b65264a0..0e8bd40d38f 100644 --- a/Tests/SwiftParserTest/TypeTests.swift +++ b/Tests/SwiftParserTest/TypeTests.swift @@ -94,8 +94,8 @@ final class TypeTests: ParserTestCase { diagnostics: [ DiagnosticSpec( locationMarker: "1️⃣", - message: "expected identifier in closure capture", - fixIts: ["insert identifier"] + message: "expected closure capture in closure capture clause", + fixIts: ["insert closure capture"] ), DiagnosticSpec( locationMarker: "1️⃣", diff --git a/Tests/SwiftSyntaxTest/SyntaxTests.swift b/Tests/SwiftSyntaxTest/SyntaxTests.swift index a07a5265c19..42e569153cb 100644 --- a/Tests/SwiftSyntaxTest/SyntaxTests.swift +++ b/Tests/SwiftSyntaxTest/SyntaxTests.swift @@ -139,14 +139,6 @@ class SyntaxTests: XCTestCase { XCTAssertEqual(node.formatted().description, "label: MyType") } - public func testClosureCaptureSyntaxConvenienceInitWithEqual() { - let noNameClosureCapture = ClosureCaptureSyntax(expression: ExprSyntax("123")) - XCTAssertEqual(noNameClosureCapture.formatted().description, "123") - - let node = ClosureCaptureSyntax(name: "test", expression: ExprSyntax("123")) - XCTAssertEqual(node.formatted().description, "test = 123") - } - func testShareSyntaxIndexInTreeBetweenTrees() throws { let source = "func foo() {}" From d5bbac9a2a72cce96b302bb321577c7a35f49496 Mon Sep 17 00:00:00 2001 From: Jakub Florek Date: Tue, 30 Jul 2024 10:30:09 +0200 Subject: [PATCH 2/6] Bring back the convenience initializer and deprecate it. Add entries to release notes. --- Release Notes/601.md | 8 +++++++ Sources/SwiftParser/Expressions.swift | 20 ++++++----------- Sources/SwiftSyntax/Convenience.swift | 31 +++++++++++++++++++++++++++ 3 files changed, 46 insertions(+), 13 deletions(-) diff --git a/Release Notes/601.md b/Release Notes/601.md index 7036e503b33..5491d93bfc7 100644 --- a/Release Notes/601.md +++ b/Release Notes/601.md @@ -14,6 +14,10 @@ - `Error` protocol now has an `asDiagnostics(at:)` method. - Description: This method translates an error into one or more diagnostics, recognizing `DiagnosticsError` and `DiagnosticMessage` instances or providing its own `Diagnostic` as needed. - Pull Request: https://github.com/swiftlang/swift-syntax/pull/1816 + +- `ClosureCaptureSyntax` now has a new node structure. + - Description: `ClosureCaptureSyntax` now has an `initializer` property instead of `equal` and `expression`. Additionally, the `name` property is no longer optional. + - Pull request: https://github.com/swiftlang/swift-syntax/pull/2763 ## API Behavior Changes @@ -27,6 +31,10 @@ - Description: `IncrementalEdit` is being dropped for `SourceEdit`. `SourceEdit` has deprecated compatibility layers to make it API-compatible with `IncrementalEdit` - Issue: https://github.com/apple/swift-syntax/issues/2532 - Pull request: https://github.com/apple/swift-syntax/pull/2604 + +- `ClosureCaptureSyntax.init(leadingTrivia:specifier:name:equal:expression:trailingComma:trailingTrivia:)` deprecated in favor of a new `ClosureCaptureSyntax.init(leadingTrivia:_:specifier:_:name:_:initializer:_:trailingComma:_:trailingTrivia:)` initializer. + - Description: The change is due to a new `ClosureCaptureSyntax` node structure. + - Pull request: https://github.com/swiftlang/swift-syntax/pull/2763 ## API-Incompatible Changes diff --git a/Sources/SwiftParser/Expressions.swift b/Sources/SwiftParser/Expressions.swift index 2c9472045d3..2b99d46d536 100644 --- a/Sources/SwiftParser/Expressions.swift +++ b/Sources/SwiftParser/Expressions.swift @@ -1705,26 +1705,20 @@ extension Parser { // The thing being capture specified is an identifier, or as an identifier // followed by an initializer clause. - let unexpectedBeforeName: RawUnexpectedNodesSyntax? - let name: RawTokenSyntax + let (unexpectedBeforeName, name) = self.expect( + .identifier, + TokenSpec(.self), + default: .identifier + ) + let initializer: RawInitializerClauseSyntax? - if self.peek(isAt: .equal) { + if self.at(.equal) { // The name is a new declaration with // initializer clause. - (unexpectedBeforeName, name) = self.expect( - .identifier, - TokenSpec(.self, remapping: .identifier), - default: .identifier - ) initializer = self.parseInitializerClause() } else { // This is the simple case - the identifier is the name and // the initializer clause is empty. - (unexpectedBeforeName, name) = self.expect( - .identifier, - TokenSpec(.self), - default: .identifier - ) initializer = nil } diff --git a/Sources/SwiftSyntax/Convenience.swift b/Sources/SwiftSyntax/Convenience.swift index 36b2e11e9ac..64dbc848234 100644 --- a/Sources/SwiftSyntax/Convenience.swift +++ b/Sources/SwiftSyntax/Convenience.swift @@ -10,6 +10,37 @@ // //===----------------------------------------------------------------------===// +extension ClosureCaptureSyntax { + + /// Creates a ``ClosureCaptureSyntax`` with a `name`, and automatically adds an `equal` token to it since the name is non-optional. + /// + /// - SeeAlso: ``ClosureCaptureSyntax/init(leadingTrivia:_:specifier:_:name:_:initializer:_:trailingComma:_:trailingTrivia:)``. + /// + @available( + *, + deprecated, + message: "Use 'init(leadingTrivia:_:specifier:_:name:_:initializer:_:trailingComma:_:trailingTrivia:)' instead" + ) + public init( + leadingTrivia: Trivia? = nil, + specifier: ClosureCaptureSpecifierSyntax? = nil, + name: TokenSyntax, + equal: TokenSyntax = TokenSyntax.equalToken(), + expression: some ExprSyntaxProtocol, + trailingComma: TokenSyntax? = nil, + trailingTrivia: Trivia? = nil + ) { + self.init( + leadingTrivia: leadingTrivia, + specifier: specifier, + name: name, + initializer: InitializerClauseSyntax(equal: equal, value: expression), + trailingComma: trailingComma, + trailingTrivia: trailingTrivia + ) + } +} + extension EnumCaseParameterSyntax { /// Creates an ``EnumCaseParameterSyntax`` with a `firstName`, and automatically adds a `colon` to it. From abc705fab5b7ab8548ab0d4a2a3cea1fc15a6a23 Mon Sep 17 00:00:00 2001 From: Jakub Florek Date: Wed, 31 Jul 2024 11:58:58 +0200 Subject: [PATCH 3/6] Add deprecated signatures to `SwiftSyntaxCompatibility.swift`. Adjust release notes. --- Release Notes/601.md | 10 +- Sources/SwiftSyntax/Convenience.swift | 31 --- .../SwiftSyntaxCompatibility.swift | 183 ++++++++++++++++++ 3 files changed, 188 insertions(+), 36 deletions(-) diff --git a/Release Notes/601.md b/Release Notes/601.md index 5491d93bfc7..65df65fe485 100644 --- a/Release Notes/601.md +++ b/Release Notes/601.md @@ -14,10 +14,6 @@ - `Error` protocol now has an `asDiagnostics(at:)` method. - Description: This method translates an error into one or more diagnostics, recognizing `DiagnosticsError` and `DiagnosticMessage` instances or providing its own `Diagnostic` as needed. - Pull Request: https://github.com/swiftlang/swift-syntax/pull/1816 - -- `ClosureCaptureSyntax` now has a new node structure. - - Description: `ClosureCaptureSyntax` now has an `initializer` property instead of `equal` and `expression`. Additionally, the `name` property is no longer optional. - - Pull request: https://github.com/swiftlang/swift-syntax/pull/2763 ## API Behavior Changes @@ -33,7 +29,7 @@ - Pull request: https://github.com/apple/swift-syntax/pull/2604 - `ClosureCaptureSyntax.init(leadingTrivia:specifier:name:equal:expression:trailingComma:trailingTrivia:)` deprecated in favor of a new `ClosureCaptureSyntax.init(leadingTrivia:_:specifier:_:name:_:initializer:_:trailingComma:_:trailingTrivia:)` initializer. - - Description: The change is due to a new `ClosureCaptureSyntax` node structure. + - Description: `ClosureCaptureSyntax` now has an `initializer` property instead of `equal` and `expression`. Additionally, the `name` property is no longer optional. - Pull request: https://github.com/swiftlang/swift-syntax/pull/2763 ## API-Incompatible Changes @@ -42,6 +38,10 @@ - Description: Allows retrieving the radix value from the `literal.text`. - Issue: https://github.com/apple/swift-syntax/issues/405 - Pull Request: https://github.com/apple/swift-syntax/pull/2605 + +- `ClosureCaptureSyntax.name` is no longer optional. + - Description: Due to the new `ClosureCaptureSyntax` node structure, `name` property is non-optional. + - Pull request: https://github.com/swiftlang/swift-syntax/pull/2763 ## Template diff --git a/Sources/SwiftSyntax/Convenience.swift b/Sources/SwiftSyntax/Convenience.swift index 64dbc848234..36b2e11e9ac 100644 --- a/Sources/SwiftSyntax/Convenience.swift +++ b/Sources/SwiftSyntax/Convenience.swift @@ -10,37 +10,6 @@ // //===----------------------------------------------------------------------===// -extension ClosureCaptureSyntax { - - /// Creates a ``ClosureCaptureSyntax`` with a `name`, and automatically adds an `equal` token to it since the name is non-optional. - /// - /// - SeeAlso: ``ClosureCaptureSyntax/init(leadingTrivia:_:specifier:_:name:_:initializer:_:trailingComma:_:trailingTrivia:)``. - /// - @available( - *, - deprecated, - message: "Use 'init(leadingTrivia:_:specifier:_:name:_:initializer:_:trailingComma:_:trailingTrivia:)' instead" - ) - public init( - leadingTrivia: Trivia? = nil, - specifier: ClosureCaptureSpecifierSyntax? = nil, - name: TokenSyntax, - equal: TokenSyntax = TokenSyntax.equalToken(), - expression: some ExprSyntaxProtocol, - trailingComma: TokenSyntax? = nil, - trailingTrivia: Trivia? = nil - ) { - self.init( - leadingTrivia: leadingTrivia, - specifier: specifier, - name: name, - initializer: InitializerClauseSyntax(equal: equal, value: expression), - trailingComma: trailingComma, - trailingTrivia: trailingTrivia - ) - } -} - extension EnumCaseParameterSyntax { /// Creates an ``EnumCaseParameterSyntax`` with a `firstName`, and automatically adds a `colon` to it. diff --git a/Sources/SwiftSyntax/SwiftSyntaxCompatibility.swift b/Sources/SwiftSyntax/SwiftSyntaxCompatibility.swift index a46a784af09..5d2486c5683 100644 --- a/Sources/SwiftSyntax/SwiftSyntaxCompatibility.swift +++ b/Sources/SwiftSyntax/SwiftSyntaxCompatibility.swift @@ -144,6 +144,189 @@ extension DeclGroupSyntax { } } +extension ClosureCaptureSyntax { + @available(*, deprecated, renamed: "unexpectedBetweenNameAndInitializer") + public var unexpectedBetweenNameAndAssignToken: UnexpectedNodesSyntax? { + get { + return unexpectedBetweenNameAndInitializer + } + set { + unexpectedBetweenNameAndInitializer = newValue + } + } + + @available(*, deprecated, renamed: "initializer.equal") + public var assignToken: TokenSyntax? { + get { + return initializer?.equal + } + set { + initializer?.equal = newValue ?? .equalToken(presence: .missing) + } + } + + @available(*, deprecated, renamed: "initializer.unexpectedBetweenEqualAndValue") + public var unexpectedBetweenAssignTokenAndExpression: UnexpectedNodesSyntax? { + get { + return initializer?.unexpectedBetweenEqualAndValue + } + set { + initializer?.unexpectedBetweenEqualAndValue = newValue + } + } + + @available(*, deprecated, renamed: "ClosureCaptureSyntax(leadingTrivia:_:specifier:_:name:_:initializer:_:trailingComma:_:trailingTrivia:)") + @_disfavoredOverload + public init( + leadingTrivia: Trivia? = nil, + _ unexpectedBeforeSpecifier: UnexpectedNodesSyntax? = nil, + specifier: ClosureCaptureSpecifierSyntax? = nil, + _ unexpectedBetweenSpecifierAndName: UnexpectedNodesSyntax? = nil, + name: TokenSyntax? = nil, + _ unexpectedBetweenNameAndAssignToken: UnexpectedNodesSyntax? = nil, + assignToken: TokenSyntax? = nil, + _ unexpectedBetweenAssignTokenAndExpression: UnexpectedNodesSyntax? = nil, + expression: some ExprSyntaxProtocol, + _ unexpectedBetweenExpressionAndTrailingComma: UnexpectedNodesSyntax? = nil, + trailingComma: TokenSyntax? = nil, + _ unexpectedAfterTrailingComma: UnexpectedNodesSyntax? = nil, + trailingTrivia: Trivia? = nil + + ) { + self.init( + leadingTrivia: leadingTrivia, + unexpectedBeforeSpecifier, + specifier: specifier, + unexpectedBetweenSpecifierAndName, + name: name ?? .identifier("", presence: .missing), + unexpectedBetweenNameAndAssignToken, + initializer: InitializerClauseSyntax( + equal: assignToken ?? .equalToken(presence: .missing), + unexpectedBetweenAssignTokenAndExpression, + value: expression + ), + unexpectedBetweenExpressionAndTrailingComma, + trailingComma: trailingComma, + unexpectedAfterTrailingComma, + trailingTrivia: trailingTrivia + ) + } + + /// Creates a ``ClosureCaptureSyntax`` with a `name`, and automatically adds an `equal` token to it since the name is non-optional. + /// + /// - SeeAlso: ``ClosureCaptureSyntax/init(leadingTrivia:_:specifier:_:name:_:initializer:_:trailingComma:_:trailingTrivia:)``. + /// + @available( + *, + deprecated, + message: "Use 'init(leadingTrivia:_:specifier:_:name:_:initializer:_:trailingComma:_:trailingTrivia:)' instead" + ) + public init( + leadingTrivia: Trivia? = nil, + specifier: ClosureCaptureSpecifierSyntax? = nil, + name: TokenSyntax, + equal: TokenSyntax = TokenSyntax.equalToken(), + expression: some ExprSyntaxProtocol, + trailingComma: TokenSyntax? = nil, + trailingTrivia: Trivia? = nil + ) { + self.init( + leadingTrivia: leadingTrivia, + specifier: specifier, + name: name, + initializer: InitializerClauseSyntax(equal: equal, value: expression), + trailingComma: trailingComma, + trailingTrivia: trailingTrivia + ) + } + + @available(*, deprecated, renamed: "unexpectedBetweenNameAndInitializer") + public var unexpectedBetweenNameAndEqual: UnexpectedNodesSyntax? { + get { + return unexpectedBetweenNameAndInitializer + } + set { + unexpectedBetweenNameAndInitializer = newValue + } + } + + @available(*, deprecated, renamed: "initializer.equal") + public var equal: TokenSyntax? { + get { + return initializer?.equal + } + set { + initializer?.equal = newValue ?? .equalToken(presence: .missing) + } + } + + @available(*, deprecated, renamed: "initializer.unexpectedBetweenEqualAndValue") + public var unexpectedBetweenEqualAndExpression: UnexpectedNodesSyntax? { + get { + return initializer?.unexpectedBetweenEqualAndValue + } + set { + initializer?.unexpectedBetweenEqualAndValue = newValue + } + } + + @available(*, deprecated, renamed: "initializer.value") + public var expression: ExprSyntax { + get { + return initializer?.value ?? ExprSyntax(MissingExprSyntax()) + } + set(value) { + initializer?.value = value + } + } + + @available(*, deprecated, renamed: "unexpectedBetweenInitializerAndTrailingComma") + public var unexpectedBetweenExpressionAndTrailingComma: UnexpectedNodesSyntax? { + get { + return unexpectedBetweenInitializerAndTrailingComma + } + set(value) { + unexpectedBetweenInitializerAndTrailingComma = value + } + } + + @available(*, deprecated, renamed: "ClosureCaptureSyntax(leadingTrivia:_:specifier:_:name:_:initializer:_:trailingComma:_:trailingTrivia:)") + @_disfavoredOverload + public init( + leadingTrivia: Trivia? = nil, + _ unexpectedBeforeSpecifier: UnexpectedNodesSyntax? = nil, + specifier: ClosureCaptureSpecifierSyntax? = nil, + _ unexpectedBetweenSpecifierAndName: UnexpectedNodesSyntax? = nil, + name: TokenSyntax? = nil, + _ unexpectedBetweenNameAndEqual: UnexpectedNodesSyntax? = nil, + equal: TokenSyntax? = nil, + _ unexpectedBetweenEqualAndExpression: UnexpectedNodesSyntax? = nil, + expression: some ExprSyntaxProtocol, + _ unexpectedBetweenExpressionAndTrailingComma: UnexpectedNodesSyntax? = nil, + trailingComma: TokenSyntax? = nil, + _ unexpectedAfterTrailingComma: UnexpectedNodesSyntax? = nil, + trailingTrivia: Trivia? = nil + ) { + self.init( + leadingTrivia: leadingTrivia, + unexpectedBeforeSpecifier, + specifier: specifier, + unexpectedBetweenSpecifierAndName, + name: name ?? .identifier("", presence: .missing), + unexpectedBetweenNameAndEqual, + initializer: InitializerClauseSyntax( + equal: equal ?? .equalToken(presence: .missing), + unexpectedBetweenEqualAndExpression, + value: expression + ), + unexpectedBetweenExpressionAndTrailingComma, + trailingComma: trailingComma, + unexpectedAfterTrailingComma, + trailingTrivia: trailingTrivia + ) + } +} + extension EffectSpecifiersSyntax { @available(*, deprecated, renamed: "unexpectedBetweenAsyncSpecifierAndThrowsClause") public var unexpectedBetweenAsyncSpecifierAndThrowsSpecifier: UnexpectedNodesSyntax? { From 2984ad80c25fa586cec7e3527fe128996f1ff3e9 Mon Sep 17 00:00:00 2001 From: Jakub Florek Date: Wed, 31 Jul 2024 12:03:59 +0200 Subject: [PATCH 4/6] Format. --- .../SwiftSyntaxCompatibility.swift | 50 +++++++++++-------- 1 file changed, 29 insertions(+), 21 deletions(-) diff --git a/Sources/SwiftSyntax/SwiftSyntaxCompatibility.swift b/Sources/SwiftSyntax/SwiftSyntaxCompatibility.swift index 5d2486c5683..0c4f5131a16 100644 --- a/Sources/SwiftSyntax/SwiftSyntaxCompatibility.swift +++ b/Sources/SwiftSyntax/SwiftSyntaxCompatibility.swift @@ -175,22 +175,26 @@ extension ClosureCaptureSyntax { } } - @available(*, deprecated, renamed: "ClosureCaptureSyntax(leadingTrivia:_:specifier:_:name:_:initializer:_:trailingComma:_:trailingTrivia:)") + @available( + *, + deprecated, + renamed: "ClosureCaptureSyntax(leadingTrivia:_:specifier:_:name:_:initializer:_:trailingComma:_:trailingTrivia:)" + ) @_disfavoredOverload public init( - leadingTrivia: Trivia? = nil, - _ unexpectedBeforeSpecifier: UnexpectedNodesSyntax? = nil, - specifier: ClosureCaptureSpecifierSyntax? = nil, - _ unexpectedBetweenSpecifierAndName: UnexpectedNodesSyntax? = nil, - name: TokenSyntax? = nil, - _ unexpectedBetweenNameAndAssignToken: UnexpectedNodesSyntax? = nil, - assignToken: TokenSyntax? = nil, - _ unexpectedBetweenAssignTokenAndExpression: UnexpectedNodesSyntax? = nil, - expression: some ExprSyntaxProtocol, - _ unexpectedBetweenExpressionAndTrailingComma: UnexpectedNodesSyntax? = nil, - trailingComma: TokenSyntax? = nil, - _ unexpectedAfterTrailingComma: UnexpectedNodesSyntax? = nil, - trailingTrivia: Trivia? = nil + leadingTrivia: Trivia? = nil, + _ unexpectedBeforeSpecifier: UnexpectedNodesSyntax? = nil, + specifier: ClosureCaptureSpecifierSyntax? = nil, + _ unexpectedBetweenSpecifierAndName: UnexpectedNodesSyntax? = nil, + name: TokenSyntax? = nil, + _ unexpectedBetweenNameAndAssignToken: UnexpectedNodesSyntax? = nil, + assignToken: TokenSyntax? = nil, + _ unexpectedBetweenAssignTokenAndExpression: UnexpectedNodesSyntax? = nil, + expression: some ExprSyntaxProtocol, + _ unexpectedBetweenExpressionAndTrailingComma: UnexpectedNodesSyntax? = nil, + trailingComma: TokenSyntax? = nil, + _ unexpectedAfterTrailingComma: UnexpectedNodesSyntax? = nil, + trailingTrivia: Trivia? = nil ) { self.init( @@ -211,7 +215,7 @@ extension ClosureCaptureSyntax { trailingTrivia: trailingTrivia ) } - + /// Creates a ``ClosureCaptureSyntax`` with a `name`, and automatically adds an `equal` token to it since the name is non-optional. /// /// - SeeAlso: ``ClosureCaptureSyntax/init(leadingTrivia:_:specifier:_:name:_:initializer:_:trailingComma:_:trailingTrivia:)``. @@ -239,7 +243,7 @@ extension ClosureCaptureSyntax { trailingTrivia: trailingTrivia ) } - + @available(*, deprecated, renamed: "unexpectedBetweenNameAndInitializer") public var unexpectedBetweenNameAndEqual: UnexpectedNodesSyntax? { get { @@ -249,7 +253,7 @@ extension ClosureCaptureSyntax { unexpectedBetweenNameAndInitializer = newValue } } - + @available(*, deprecated, renamed: "initializer.equal") public var equal: TokenSyntax? { get { @@ -259,7 +263,7 @@ extension ClosureCaptureSyntax { initializer?.equal = newValue ?? .equalToken(presence: .missing) } } - + @available(*, deprecated, renamed: "initializer.unexpectedBetweenEqualAndValue") public var unexpectedBetweenEqualAndExpression: UnexpectedNodesSyntax? { get { @@ -269,7 +273,7 @@ extension ClosureCaptureSyntax { initializer?.unexpectedBetweenEqualAndValue = newValue } } - + @available(*, deprecated, renamed: "initializer.value") public var expression: ExprSyntax { get { @@ -289,8 +293,12 @@ extension ClosureCaptureSyntax { unexpectedBetweenInitializerAndTrailingComma = value } } - - @available(*, deprecated, renamed: "ClosureCaptureSyntax(leadingTrivia:_:specifier:_:name:_:initializer:_:trailingComma:_:trailingTrivia:)") + + @available( + *, + deprecated, + renamed: "ClosureCaptureSyntax(leadingTrivia:_:specifier:_:name:_:initializer:_:trailingComma:_:trailingTrivia:)" + ) @_disfavoredOverload public init( leadingTrivia: Trivia? = nil, From 612109fb6f0c17011275eea496e6b5a0e26f77b8 Mon Sep 17 00:00:00 2001 From: Jakub Florek Date: Thu, 1 Aug 2024 11:06:05 +0200 Subject: [PATCH 5/6] Add `self` keyword as a possible name kind in ClosureCaptureSyntax. --- .../Sources/SyntaxSupport/ExprNodes.swift | 2 +- .../generated/Parser+TokenSpecSet.swift | 52 +++++++++++++++++++ .../generated/raw/RawSyntaxValidation.swift | 2 +- .../generated/syntaxNodes/SyntaxNodesC.swift | 6 ++- 4 files changed, 58 insertions(+), 4 deletions(-) diff --git a/CodeGeneration/Sources/SyntaxSupport/ExprNodes.swift b/CodeGeneration/Sources/SyntaxSupport/ExprNodes.swift index bf0e51e3863..c642bf81efb 100644 --- a/CodeGeneration/Sources/SyntaxSupport/ExprNodes.swift +++ b/CodeGeneration/Sources/SyntaxSupport/ExprNodes.swift @@ -341,7 +341,7 @@ public let EXPR_NODES: [Node] = [ ), Child( name: "name", - kind: .token(choices: [.token(.identifier)]) + kind: .token(choices: [.token(.identifier), .keyword(.self)]) ), Child( name: "initializer", diff --git a/Sources/SwiftParser/generated/Parser+TokenSpecSet.swift b/Sources/SwiftParser/generated/Parser+TokenSpecSet.swift index d26de02a349..1f83e88bf73 100644 --- a/Sources/SwiftParser/generated/Parser+TokenSpecSet.swift +++ b/Sources/SwiftParser/generated/Parser+TokenSpecSet.swift @@ -560,6 +560,58 @@ extension ClosureCaptureSpecifierSyntax { } } +extension ClosureCaptureSyntax { + @_spi(Diagnostics) + public enum NameOptions: TokenSpecSet { + case identifier + case `self` + + init?(lexeme: Lexer.Lexeme, experimentalFeatures: Parser.ExperimentalFeatures) { + switch PrepareForKeywordMatch(lexeme) { + case TokenSpec(.identifier): + self = .identifier + case TokenSpec(.self): + self = .self + default: + return nil + } + } + + public init?(token: TokenSyntax) { + switch token { + case TokenSpec(.identifier): + self = .identifier + case TokenSpec(.self): + self = .self + default: + return nil + } + } + + var spec: TokenSpec { + switch self { + case .identifier: + return .identifier + case .self: + return .keyword(.self) + } + } + + /// Returns a token that satisfies the `TokenSpec` of this case. + /// + /// If the token kind of this spec has variable text, e.g. for an identifier, this returns a token with empty text. + @_spi(Diagnostics) + public var tokenSyntax: TokenSyntax { + switch self { + case .identifier: + return .identifier("") + case .self: + return .keyword(.self) + } + } + } +} + extension ClosureParameterSyntax { @_spi(Diagnostics) public enum FirstNameOptions: TokenSpecSet { diff --git a/Sources/SwiftSyntax/generated/raw/RawSyntaxValidation.swift b/Sources/SwiftSyntax/generated/raw/RawSyntaxValidation.swift index 0c5cf183dbc..ae36578f97b 100644 --- a/Sources/SwiftSyntax/generated/raw/RawSyntaxValidation.swift +++ b/Sources/SwiftSyntax/generated/raw/RawSyntaxValidation.swift @@ -567,7 +567,7 @@ func validateLayout(layout: RawSyntaxBuffer, as kind: SyntaxKind) { assertNoError(kind, 0, verify(layout[0], as: RawUnexpectedNodesSyntax?.self)) assertNoError(kind, 1, verify(layout[1], as: RawClosureCaptureSpecifierSyntax?.self)) assertNoError(kind, 2, verify(layout[2], as: RawUnexpectedNodesSyntax?.self)) - assertNoError(kind, 3, verify(layout[3], as: RawTokenSyntax.self, tokenChoices: [.tokenKind(.identifier)])) + assertNoError(kind, 3, verify(layout[3], as: RawTokenSyntax.self, tokenChoices: [.tokenKind(.identifier), .keyword("self")])) assertNoError(kind, 4, verify(layout[4], as: RawUnexpectedNodesSyntax?.self)) assertNoError(kind, 5, verify(layout[5], as: RawInitializerClauseSyntax?.self)) assertNoError(kind, 6, verify(layout[6], as: RawUnexpectedNodesSyntax?.self)) diff --git a/Sources/SwiftSyntax/generated/syntaxNodes/SyntaxNodesC.swift b/Sources/SwiftSyntax/generated/syntaxNodes/SyntaxNodesC.swift index 6bdb2e5ca8e..4b830a51aa5 100644 --- a/Sources/SwiftSyntax/generated/syntaxNodes/SyntaxNodesC.swift +++ b/Sources/SwiftSyntax/generated/syntaxNodes/SyntaxNodesC.swift @@ -1528,7 +1528,7 @@ public struct ClosureCaptureSpecifierSyntax: SyntaxProtocol, SyntaxHashable, _Le /// ### Children /// /// - `specifier`: ``ClosureCaptureSpecifierSyntax``? -/// - `name`: `` +/// - `name`: (`` | `self`) /// - `initializer`: ``InitializerClauseSyntax``? /// - `trailingComma`: `,`? /// @@ -1627,7 +1627,9 @@ public struct ClosureCaptureSyntax: SyntaxProtocol, SyntaxHashable, _LeafSyntaxN /// ### Tokens /// - /// For syntax trees generated by the parser, this is guaranteed to be ``. + /// For syntax trees generated by the parser, this is guaranteed to be one of the following kinds: + /// - `` + /// - `self` public var name: TokenSyntax { get { return Syntax(self).child(at: 3)!.cast(TokenSyntax.self) From e3f6436714e4009712affdcdc417ff6eabb4c4bc Mon Sep 17 00:00:00 2001 From: Jakub Florek Date: Fri, 2 Aug 2024 09:50:46 +0200 Subject: [PATCH 6/6] Fix failing inconsistent initializer naming test. --- .../Tests/ValidateSyntaxNodes/ValidateSyntaxNodes.swift | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/CodeGeneration/Tests/ValidateSyntaxNodes/ValidateSyntaxNodes.swift b/CodeGeneration/Tests/ValidateSyntaxNodes/ValidateSyntaxNodes.swift index 93046782bf3..4a1612b07e2 100644 --- a/CodeGeneration/Tests/ValidateSyntaxNodes/ValidateSyntaxNodes.swift +++ b/CodeGeneration/Tests/ValidateSyntaxNodes/ValidateSyntaxNodes.swift @@ -482,22 +482,22 @@ class ValidateSyntaxNodes: XCTestCase { ValidationFailure( node: .enumCaseElement, message: - "child 'rawValue' is named inconsistently with 'MatchingPatternConditionSyntax.initializer', which has the same type ('InitializerClauseSyntax')" + "child 'rawValue' is named inconsistently with 'ClosureCaptureSyntax.initializer', which has the same type ('InitializerClauseSyntax')" ), ValidationFailure( node: .enumCaseParameter, message: - "child 'defaultValue' is named inconsistently with 'MatchingPatternConditionSyntax.initializer', which has the same type ('InitializerClauseSyntax')" + "child 'defaultValue' is named inconsistently with 'ClosureCaptureSyntax.initializer', which has the same type ('InitializerClauseSyntax')" ), ValidationFailure( node: .functionParameter, message: - "child 'defaultValue' is named inconsistently with 'MatchingPatternConditionSyntax.initializer', which has the same type ('InitializerClauseSyntax')" + "child 'defaultValue' is named inconsistently with 'ClosureCaptureSyntax.initializer', which has the same type ('InitializerClauseSyntax')" ), ValidationFailure( node: .macroDecl, message: - "child 'definition' is named inconsistently with 'MatchingPatternConditionSyntax.initializer', which has the same type ('InitializerClauseSyntax')" + "child 'definition' is named inconsistently with 'ClosureCaptureSyntax.initializer', which has the same type ('InitializerClauseSyntax')" ), // MARK: Miscellaneous ValidationFailure(