diff --git a/IntegrationTests/Tests/SnippetDocumentationGenerationTests.swift b/IntegrationTests/Tests/SnippetDocumentationGenerationTests.swift index 33c3b9d..3e537ad 100644 --- a/IntegrationTests/Tests/SnippetDocumentationGenerationTests.swift +++ b/IntegrationTests/Tests/SnippetDocumentationGenerationTests.swift @@ -10,10 +10,11 @@ import XCTest final class SnippetDocumentationGenerationTests: ConcurrencyRequiringTestCase { func testGenerateDocumentationForPackageWithSnippets() throws { + let packageName = "PackageWithSnippets" let result = try swiftPackage( "generate-documentation", "--target", "Library", - workingDirectory: try setupTemporaryDirectoryForFixture(named: "PackageWithSnippets") + workingDirectory: try setupTemporaryDirectoryForFixture(named: packageName) ) result.assertExitStatusEquals(0) @@ -45,6 +46,19 @@ final class SnippetDocumentationGenerationTests: ConcurrencyRequiringTestCase { "symbol-graphs/unified-symbol-graphs", ] ) + + let unifiedSymbolGraphDirectory = subDirectoriesOfSymbolGraphDirectory.first { + $0.pathComponents.last == "unified-symbol-graphs" + }! + + let symbolGraphEnumerator = FileManager.default.enumerator(at: unifiedSymbolGraphDirectory, + includingPropertiesForKeys: [.isRegularFileKey])! + let symbolGraphPaths = try (symbolGraphEnumerator.allObjects as! [URL]).filter { + try $0.resourceValues(forKeys: [.isRegularFileKey]).isRegularFile! + } + XCTAssertNotNil(symbolGraphPaths.first { + $0.pathComponents.last == "\(packageName)-snippets.symbols.json" + }) } func testPreviewDocumentationWithSnippets() throws { diff --git a/Plugins/SharedPackagePluginExtensions/PackageManager+getSymbolGraphsForDocC.swift b/Plugins/SharedPackagePluginExtensions/PackageManager+getSymbolGraphsForDocC.swift index 2b12ff3..24c59d1 100644 --- a/Plugins/SharedPackagePluginExtensions/PackageManager+getSymbolGraphsForDocC.swift +++ b/Plugins/SharedPackagePluginExtensions/PackageManager+getSymbolGraphsForDocC.swift @@ -13,22 +13,22 @@ extension PackageManager { struct DocCSymbolGraphResult { let unifiedSymbolGraphsDirectory: URL let targetSymbolGraphsDirectory: URL - let snippetSymbolGraphsDirectory: URL? + let snippetSymbolGraphFile: URL? init( unifiedSymbolGraphsDirectory: URL, targetSymbolGraphsDirectory: URL, - snippetSymbolGraphsDirectory: URL? + snippetSymbolGraphFile: URL? ) { self.unifiedSymbolGraphsDirectory = unifiedSymbolGraphsDirectory self.targetSymbolGraphsDirectory = targetSymbolGraphsDirectory - self.snippetSymbolGraphsDirectory = snippetSymbolGraphsDirectory + self.snippetSymbolGraphFile = snippetSymbolGraphFile } init(targetSymbolGraphsDirectory: URL) { self.unifiedSymbolGraphsDirectory = targetSymbolGraphsDirectory self.targetSymbolGraphsDirectory = targetSymbolGraphsDirectory - self.snippetSymbolGraphsDirectory = nil + self.snippetSymbolGraphFile = nil } } @@ -70,7 +70,7 @@ extension PackageManager { print("snippet extractor provided, attempting to generate snippet symbol graph") } - guard let snippetSymbolGraphsDirectory = try snippetExtractor.generateSnippets( + guard let snippetSymbolGraphFile = try snippetExtractor.generateSnippets( for: target, context: context ) else { @@ -82,7 +82,7 @@ extension PackageManager { } if verbose { - print("snippet symbol graph directory path: '\(snippetSymbolGraphsDirectory.path)'") + print("snippet symbol graph file: '\(snippetSymbolGraphFile.path)'") } // Since we successfully produced symbol graphs for snippets contained in the @@ -125,20 +125,20 @@ extension PackageManager { toPath: targetSymbolGraphsUnifiedDirectory.path ) - let snippetSymbolGraphsUnifiedDirectory = unifiedSymbolGraphsDirectory.appendingPathComponent( - "snippet-symbol-graphs", isDirectory: true + let snippetSymbolGraphFileInUnifiedDirectory = unifiedSymbolGraphsDirectory.appendingPathComponent( + snippetSymbolGraphFile.lastPathComponent, isDirectory: false ) // Copy the snippet symbol graphs into the unified directory try FileManager.default.copyItem( - atPath: snippetSymbolGraphsDirectory.path, - toPath: snippetSymbolGraphsUnifiedDirectory.path + atPath: snippetSymbolGraphFile.path, + toPath: snippetSymbolGraphFileInUnifiedDirectory.path ) return DocCSymbolGraphResult( unifiedSymbolGraphsDirectory: unifiedSymbolGraphsDirectory, targetSymbolGraphsDirectory: targetSymbolGraphsUnifiedDirectory, - snippetSymbolGraphsDirectory: snippetSymbolGraphsUnifiedDirectory + snippetSymbolGraphFile: snippetSymbolGraphFileInUnifiedDirectory ) } } diff --git a/Sources/snippet-extract/Utility/SymbolGraph+Snippet.swift b/Sources/snippet-extract/Utility/SymbolGraph+Snippet.swift index 4e5560a..e122d79 100644 --- a/Sources/snippet-extract/Utility/SymbolGraph+Snippet.swift +++ b/Sources/snippet-extract/Utility/SymbolGraph+Snippet.swift @@ -19,14 +19,18 @@ extension SymbolGraph.Symbol { let identifier = SymbolGraph.Symbol.Identifier(precise: "$snippet__\(moduleName).\(basename)", interfaceLanguage: "swift") let names = SymbolGraph.Symbol.Names.init(title: basename, navigator: nil, subHeading: nil, prose: nil) - var pathComponents = snippet.sourceFile.absoluteURL.deletingPathExtension().pathComponents[...] + var pathComponents = Array(snippet.sourceFile.absoluteURL.deletingPathExtension().pathComponents[...]) guard let snippetsPathComponentIndex = pathComponents.firstIndex(where: { $0 == "Snippets" }) else { throw SnippetExtractCommand.ArgumentError.snippetNotContainedInSnippetsDirectory(snippet.sourceFile) } - pathComponents = pathComponents[snippetsPathComponentIndex...] + + // In theory, there may be differently named snippet root directories in the future. + // Replace that path component with the standardized `Snippets`. + pathComponents.replaceSubrange(pathComponents.startIndex...snippetsPathComponentIndex, + with: CollectionOfOne("Snippets")) let docComment = SymbolGraph.LineList(snippet.explanation .split(separator: "\n", maxSplits: Int.max, omittingEmptySubsequences: false) @@ -39,7 +43,7 @@ extension SymbolGraph.Symbol { self.init(identifier: identifier, names: names, - pathComponents: ["Snippets"] + Array(pathComponents), + pathComponents: pathComponents, docComment: docComment, accessLevel: accessLevel, kind: kind, diff --git a/Tests/SwiftDocCPluginUtilitiesTests/Snippets/SnippetSymbolTests.swift b/Tests/SwiftDocCPluginUtilitiesTests/Snippets/SnippetSymbolTests.swift index d6eb2b1..1fe9877 100644 --- a/Tests/SwiftDocCPluginUtilitiesTests/Snippets/SnippetSymbolTests.swift +++ b/Tests/SwiftDocCPluginUtilitiesTests/Snippets/SnippetSymbolTests.swift @@ -30,4 +30,15 @@ class SnippetSymbolTests: XCTestCase { } }) } + + func testPathComponentsForSnippetSymbol() throws { + let source = """ + // A snippet. + foo() {} + """ + let snippet = Snippets.Snippet(parsing: source, + sourceFile: URL(fileURLWithPath: "/path/to/my-package/Snippets/ASnippet.swift")) + let symbol = try SymbolGraph.Symbol(snippet, moduleName: "my-package") + XCTAssertEqual(["Snippets", "ASnippet"], symbol.pathComponents) + } }