From ea4e1130f1182f0bdd4c899d20b8548c62977bcf Mon Sep 17 00:00:00 2001 From: Joe Heck Date: Tue, 21 Jan 2025 11:22:46 -0800 Subject: [PATCH 1/3] Initial work on snippets documentation Co-authored-by: Joe Heck Co-authored-by: Jacob Hearst --- .../DocC Documentation.md | 1 + .../API Reference Syntax/Snippet.md | 25 +++ .../docc/DocCDocumentation.docc/snippets.md | 143 ++++++++++++++++++ 3 files changed, 169 insertions(+) create mode 100644 Sources/docc/DocCDocumentation.docc/Reference Syntax/API Reference Syntax/Snippet.md create mode 100644 Sources/docc/DocCDocumentation.docc/snippets.md diff --git a/Sources/docc/DocCDocumentation.docc/DocC Documentation.md b/Sources/docc/DocCDocumentation.docc/DocC Documentation.md index acff62f201..7890b53331 100644 --- a/Sources/docc/DocCDocumentation.docc/DocC Documentation.md +++ b/Sources/docc/DocCDocumentation.docc/DocC Documentation.md @@ -25,6 +25,7 @@ DocC syntax — called _documentation markup_ — is a custom variant of Markdow - - - +- - ### Structure and Formatting diff --git a/Sources/docc/DocCDocumentation.docc/Reference Syntax/API Reference Syntax/Snippet.md b/Sources/docc/DocCDocumentation.docc/Reference Syntax/API Reference Syntax/Snippet.md new file mode 100644 index 0000000000..e4894399ec --- /dev/null +++ b/Sources/docc/DocCDocumentation.docc/Reference Syntax/API Reference Syntax/Snippet.md @@ -0,0 +1,25 @@ +# ``docc/Snippet`` + +Embeds a code example from the project's code snippets. + +```markdown +@Snippet(path: "my-package/Snippets/example-snippet", slice: "setup") +``` + +- Parameters: + - path: A reference to the location of a code example. + - slice: The name of a section within the code example that you annotate with comments in the snippet. **(optional)** + +## Overview + +Place the `Snippet` directive to embed a code example from the project's snippet directory. The path to the snippet is identified with three parts: + +1. The package name as defined in `Package.swift` + +2. The directory path to the snippet file, starting with "Snippets". + +3. The name of your snippet file without the `.swift` extension + +If the snippet had slices annotated within it, an individual slice of the snippet can be referenced with the `slice` option. Without the option defined, the directive embeds the entire snippet. + + diff --git a/Sources/docc/DocCDocumentation.docc/snippets.md b/Sources/docc/DocCDocumentation.docc/snippets.md new file mode 100644 index 0000000000..f3e4e097c3 --- /dev/null +++ b/Sources/docc/DocCDocumentation.docc/snippets.md @@ -0,0 +1,143 @@ +# Adding Code Snippets to your Content + +Create and include code snippets to illustrate and provide examples of how to use your API. + +## Overview + +...tbd... +- Describe the problem and summarize the developer action. +- Explain why the problem is relevant and provide context for the task. Don't simply repeat the abstract; expand on it. +- Keep the Overview to one or two paragraphs. +- For very short articles that consist of just a couple of paragraphs, all of the content can be in the Overview. + +...tbd... + +### Create a code snippet + +Swift Package Manager expects to find your code examples in the directory `Snippets` at the top of your project, parallel to the file `Package.swift` and the directory `Sources`. +At the root of your project, create the directory `Snippets`. +Within the Snippets directory, create a file with your code snippet. + +The following example illustrates a code example in the file `Snippets/example-snippet.swift`: + +```swift +import Foundation + +print("Hello") +``` + +Within your snippet, you can import your local module, as well as any module that your package depends on. + +Every time you build your project, the Swift Package Manager compiles any code snippets, and then fails if the build if they are unable to compile. + +### Run the snippet + +Each code example file you create becomes it's own module. +The name of the code example file you create is the name of the module that Swift creates. +Use the `swift run` command in a terminal to compile and run the module to verify it compiles does what you expect. + +Run the earlier code example file named `example-snippet.swift` using the following command: + +```bash +swift run example-snippet +``` + +### Reference the snippet + +To reference your snippet in an article or within the symbol reference pages, use the `@Snippet` directive. +```markdown +@Snippet(path: "my-package/Snippets/example-snippet") +``` + +The `path` argument has three parts: + +1. The package name as defined in `Package.swift` + +2. The directory path to the snippet file, starting with "Snippets". + +3. The name of your snippet file without the `.swift` extension + +Without any additional annotations in your snippet, Docc includes the entirety of your code example as the snippet. +To prevent parts of your snippet file from being rendered in documentation, add comments in your code in the format `// snippet.hide` and `// snippet.show` on new lines, surrounding the content you want to hide. +These comments act as a toggle to hide or show content from the snippet. + +```swift +print("Hello") + +// snippet.hide + +print("Hidden") + +// snippet.show + +print("Shown") +``` + +Hide segments of your snippet for things like license footers, test code, or unique setup code. +Generally, it is mostly useful for things that you wouldn't want the reader to take with them as a starting point. + +### Preview your content + +Use the [swift-docc-plugin](https://github.com/swiftlang/swift-docc-plugin) to preview content that includes snippets. +To run the preview, use the following command from a terminal: + +```bash +swift package --disable-sandbox preview-documentation +``` + +### Slice up your snippet to break it up in your content. + +Long snippets dropped into documentation can result in a wall of text that is harder to parse and understand. +Instead, annotate non-overlapping slices in the snippet, which allows you to reference and embed the slice portion of the example code. + +Annotating slices in a snippet looks similiar to annotating `snippet.show` and `snippet.hide`. +You define the slice's identity in the comment, and that slice continues until the next instance of `// snippet.end` appears on a new line. +When selecting your identifiers, use URL-compatible path characters. + +For example, to start a slice with an ID of `setup`, add the following comment on a new line. + +```swift +// snippet.setup +``` + +Then end the `setup` slice with: + +```swift +// snippet.end +``` + +Adding a new slice identifier automatically terminates an earlier slice. +For example, the follow code examples are effectively the same: + +```swift +// snippet.setup +var item = MyObject.init() +// snippet.end + +// snipppet.configure +item.size = 3 +// snippet.end +``` + +```swift +// snippet.setup +var item = MyObject.init() + +// snipppet.configure +item.size = 3 +``` + +Use the `@Snippet` directive with the `slice` parameter to embed that slice as sample code on your documentation. +Extending the earlier snippet example, the slice `setup` would be referenced with + +```markdown +@Snippet(path: "my-package/Snippets/example-snippet", slice: "setup") +``` + +### Documenting the code in your snippet + +DocC parses contiguous comments within your the code of a snippet as markdown to annotate your code when embedded in documentation. +DocC will attempt to reference symbols from within these comments just like any other documentation content. +You can reference symbols from your API, which DocC converts into hyperlinks to that symbol when displaying the content. + + \ No newline at end of file From d8d27fe7a47b4e94cdce608912476acff1b693c0 Mon Sep 17 00:00:00 2001 From: Joe Heck Date: Wed, 5 Mar 2025 12:53:36 -0800 Subject: [PATCH 2/3] consolidate copyright statements at bottom of markdown files and add a newline to the end of the file --- .../Reference Syntax/API Reference Syntax/Snippet.md | 3 ++- Sources/docc/DocCDocumentation.docc/snippets.md | 3 ++- 2 files changed, 4 insertions(+), 2 deletions(-) diff --git a/Sources/docc/DocCDocumentation.docc/Reference Syntax/API Reference Syntax/Snippet.md b/Sources/docc/DocCDocumentation.docc/Reference Syntax/API Reference Syntax/Snippet.md index e4894399ec..451ae93755 100644 --- a/Sources/docc/DocCDocumentation.docc/Reference Syntax/API Reference Syntax/Snippet.md +++ b/Sources/docc/DocCDocumentation.docc/Reference Syntax/API Reference Syntax/Snippet.md @@ -22,4 +22,5 @@ Place the `Snippet` directive to embed a code example from the project's snippet If the snippet had slices annotated within it, an individual slice of the snippet can be referenced with the `slice` option. Without the option defined, the directive embeds the entire snippet. - + + diff --git a/Sources/docc/DocCDocumentation.docc/snippets.md b/Sources/docc/DocCDocumentation.docc/snippets.md index f3e4e097c3..2e49763252 100644 --- a/Sources/docc/DocCDocumentation.docc/snippets.md +++ b/Sources/docc/DocCDocumentation.docc/snippets.md @@ -140,4 +140,5 @@ DocC parses contiguous comments within your the code of a snippet as markdown to DocC will attempt to reference symbols from within these comments just like any other documentation content. You can reference symbols from your API, which DocC converts into hyperlinks to that symbol when displaying the content. - \ No newline at end of file + + From fdccaf0d670ece8e826e356790018598e1bf74f4 Mon Sep 17 00:00:00 2001 From: Joe Heck Date: Sun, 9 Mar 2025 12:20:24 -0700 Subject: [PATCH 3/3] enables Snippet directive code for documentation, and updates the generated symbolgraph with that change --- .../Semantics/Snippets/Snippet.swift | 2 - .../DocCDocumentation.docc/DocC.symbols.json | 156 ++++++++++++++++++ 2 files changed, 156 insertions(+), 2 deletions(-) diff --git a/Sources/SwiftDocC/Semantics/Snippets/Snippet.swift b/Sources/SwiftDocC/Semantics/Snippets/Snippet.swift index 5539125d77..7861fe9e43 100644 --- a/Sources/SwiftDocC/Semantics/Snippets/Snippet.swift +++ b/Sources/SwiftDocC/Semantics/Snippets/Snippet.swift @@ -30,8 +30,6 @@ public final class Snippet: Semantic, AutomaticDirectiveConvertible { "slice" : \Snippet._slice, ] - static var hiddenFromDocumentation = true - @available(*, deprecated, message: "Do not call directly. Required for 'AutomaticDirectiveConvertible'.") init(originalMarkup: BlockDirective) { self.originalMarkup = originalMarkup diff --git a/Sources/docc/DocCDocumentation.docc/DocC.symbols.json b/Sources/docc/DocCDocumentation.docc/DocC.symbols.json index 1d87e25a69..18006f572d 100644 --- a/Sources/docc/DocCDocumentation.docc/DocC.symbols.json +++ b/Sources/docc/DocCDocumentation.docc/DocC.symbols.json @@ -5246,6 +5246,162 @@ "Small" ] }, + { + "accessLevel" : "public", + "availability" : [ + { + "domain" : "Swift-DocC", + "introduced" : { + "major" : 5, + "minor" : 6, + "patch" : 0 + } + } + ], + "declarationFragments" : [ + { + "kind" : "typeIdentifier", + "spelling" : "@" + }, + { + "kind" : "typeIdentifier", + "spelling" : "Snippet" + }, + { + "kind" : "text", + "spelling" : "(" + }, + { + "kind" : "identifier", + "spelling" : "path" + }, + { + "kind" : "text", + "spelling" : ": " + }, + { + "kind" : "typeIdentifier", + "spelling" : "String" + }, + { + "kind" : "text", + "spelling" : ", " + }, + { + "kind" : "identifier", + "spelling" : "slice" + }, + { + "kind" : "text", + "spelling" : ": " + }, + { + "kind" : "typeIdentifier", + "spelling" : "String" + }, + { + "kind" : "text", + "spelling" : "?" + }, + { + "kind" : "text", + "spelling" : ")" + } + ], + "docComment" : { + "lines" : [ + { + "text" : "- Parameters:" + }, + { + "text" : " - path: The path components of a symbol link that would be used to resolve a reference to a snippet," + }, + { + "text" : " only occurring as a block directive argument." + }, + { + "text" : " **(required)**" + }, + { + "text" : " - slice: An optional named range to limit the lines shown." + }, + { + "text" : " **(optional)**" + } + ] + }, + "identifier" : { + "interfaceLanguage" : "swift", + "precise" : "__docc_universal_symbol_reference_$Snippet" + }, + "kind" : { + "displayName" : "Directive", + "identifier" : "class" + }, + "names" : { + "navigator" : [ + { + "kind" : "attribute", + "spelling" : "@" + }, + { + "kind" : "identifier", + "preciseIdentifier" : "__docc_universal_symbol_reference_$Snippet", + "spelling" : "Snippet" + } + ], + "subHeading" : [ + { + "kind" : "identifier", + "spelling" : "@" + }, + { + "kind" : "identifier", + "spelling" : "Snippet" + }, + { + "kind" : "text", + "spelling" : "(" + }, + { + "kind" : "identifier", + "spelling" : "path" + }, + { + "kind" : "text", + "spelling" : ": " + }, + { + "kind" : "typeIdentifier", + "spelling" : "String" + }, + { + "kind" : "text", + "spelling" : ", " + }, + { + "kind" : "identifier", + "spelling" : "slice" + }, + { + "kind" : "text", + "spelling" : ": " + }, + { + "kind" : "typeIdentifier", + "spelling" : "String" + }, + { + "kind" : "text", + "spelling" : ")" + } + ], + "title" : "Snippet" + }, + "pathComponents" : [ + "Snippet" + ] + }, { "accessLevel" : "public", "availability" : [