Skip to content

Commit

Permalink
🐛 fix: diagram syntax error when class inherited a generic type (#67)
Browse files Browse the repository at this point in the history
* 🐛 fix: diagram syntax error when class inherited a generic type (fix #65)

* 🧪 test: testStructureGenericsParent

* 💎 style: swiftformat
  • Loading branch information
MarcoEidinger authored Feb 17, 2023
1 parent 04622f3 commit 35439af
Show file tree
Hide file tree
Showing 4 changed files with 42 additions and 2 deletions.
20 changes: 19 additions & 1 deletion Sources/SwiftPlantUMLFramework/Internal/String+Extensions.swift
Original file line number Diff line number Diff line change
Expand Up @@ -7,8 +7,26 @@ internal extension String {
}

internal extension String {
/// example: "Hello<World>".getAngleBracketsWithContent() returns "Hello"
func removeAngleBracketsWithContent() -> String {
replacingOccurrences(of: "\\<[^\\]]+\\>", with: "", options: .regularExpression)
replacingOccurrences(of: "\\<.*\\>", with: "", options: .regularExpression)
}

/// example: "Hello<World>".getAngleBracketsWithContent() returns "<World>"
func getAngleBracketsWithContent() -> String? {
do {
let regex = try NSRegularExpression(pattern: "\\<.*\\>")
let results = regex.matches(in: self,
range: NSRange(startIndex..., in: self))
let result = results.map {
String(self[Range($0.range, in: self)!])
}

return result.first
} catch {
print("invalid regex: \(error.localizedDescription)")
return nil
}
}
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -141,7 +141,10 @@ extension SyntaxStructure {
}

private func genericsStatement() -> String? {
guard let substructure = substructure else { return nil }
guard let substructure = substructure else {
guard let parent = inheritedTypes?.first else { return nil }
return parent.name?.getAngleBracketsWithContent()
}
let params = substructure.filter { $0.kind == SwiftPlantUMLFramework.ElementKind.genericTypeParam }
var genParts: [String] = []
for param in params {
Expand Down
9 changes: 9 additions & 0 deletions Tests/SwiftPlantUMLFrameworkTests/StringExtensionsTests.swift
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,15 @@ final class StringExtensionsTests: XCTestCase {
func testRemoveAngleBracketsWithContent() {
XCTAssertEqual("A<U>".removeAngleBracketsWithContent(), "A")
XCTAssertEqual("A<U: View, T: View>".removeAngleBracketsWithContent(), "A")
XCTAssertEqual("Handler<Void, [SelectedTenant]>".removeAngleBracketsWithContent(), "Handler")
}

func testExtractsContentInAngleBrackets() {
XCTAssertEqual("Hello, <[World]>".getAngleBracketsWithContent(), "<[World]>")
XCTAssertEqual("Hello, <<[World]>>".getAngleBracketsWithContent(), "<<[World]>>")
XCTAssertNil("Hello, World!".getAngleBracketsWithContent())
XCTAssertNil("Hello, <World!".getAngleBracketsWithContent())
XCTAssertNil("Hello, World!>".getAngleBracketsWithContent())
}

func testIsMatching() {
Expand Down
10 changes: 10 additions & 0 deletions Tests/SwiftPlantUMLFrameworkTests/SyntaxStructureTests.swift
Original file line number Diff line number Diff line change
Expand Up @@ -106,6 +106,16 @@ final class SyntaxStructureTests: XCTestCase {
XCTAssertTrue(plantUMLElement!.contains("<Title: View>"))
}

func testStructureGenericsParent() {
let code = """
class Handler<T, S> {}
class MyHandler: Handler<Int, String> {}
"""
let cut = SyntaxStructure.create(from: code)
let plantUMLElement = cut?.find(.class, named: "MyHandler")?.plantuml(context: PlantUMLContext(configuration: Configuration(elements: ElementOptions(showGenerics: true))))
XCTAssertTrue(plantUMLElement!.contains(#"class "MyHandler" as MyHandler<Int, String>"#))
}

func testStructureHideGenerics() {
let cut = SyntaxStructure.create(from: "struct aStruct <Title: View> {}")
let plantUMLElement = cut?.find(.struct, named: "aStruct")?.plantuml(context: PlantUMLContext(configuration: Configuration(elements: ElementOptions(showGenerics: false))))
Expand Down

0 comments on commit 35439af

Please sign in to comment.