123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393 |
- ===================================
- Nim DocGen Tools Guide
- ===================================
- :Author: Erik O'Leary
- :Version: |nimversion|
- .. contents::
- Introduction
- ============
- This document describes the `documentation generation tools`:idx: built into
- the `Nim compiler <nimc.html>`_, which can generate HTML and JSON output
- from input .nim files and projects, as well as HTML and LaTeX from input RST
- (reStructuredText) files. The output documentation will include the module
- dependencies (``import``), any top-level documentation comments (##), and
- exported symbols (*), including procedures, types, and variables.
- Quick start
- -----------
- Generate HTML documentation for a file:
- ::
- nim doc <filename>.nim
- Generate HTML documentation for a whole project:
- ::
- # delete any htmldocs/*.idx file before starting
- nim doc --project --index:on --git.url:<url> --git.commit:<tag> --outdir:htmldocs <main_filename>.nim
- # this will generate html files, a theindex.html index, css and js under `htmldocs`
- # See also `--docroot` to specify a relative root.
- # to get search (dochacks.js) to work locally, you need a server otherwise
- # CORS will prevent opening file:// urls; this works:
- python3 -m http.server 7029 --directory htmldocs
- # When --outdir is omitted it defaults to $projectPath/htmldocs,
- or `$nimcache/htmldocs` with `--usenimcache` which avoids clobbering your sources;
- and likewise without `--project`.
- Adding `-r` will open in a browser directly.
- Documentation Comments
- ----------------------
- Any comments which are preceded by a double-hash (##), are interpreted as
- documentation. Comments are parsed as RST (see `reference
- <http://docutils.sourceforge.net/docs/user/rst/quickref.html>`_), providing
- Nim module authors the ability to easily generate richly formatted
- documentation with only their well-documented code.
- Example:
- .. code-block:: nim
- type Person* = object
- ## This type contains a description of a person
- name: string
- age: int
- Outputs::
- Person* = object
- name: string
- age: int
- This type contains a description of a person
- Field documentation comments can be added to fields like so:
- .. code-block:: nim
- var numValues: int ## \
- ## `numValues` stores the number of values
- Note that without the `*` following the name of the type, the documentation for
- this type would not be generated. Documentation will only be generated for
- *exported* types/procedures/etc.
- Nim file input
- -----------------
- The following examples will generate documentation for the below contrived
- *Nim* module, aptly named 'sample.nim'
- sample.nim:
- .. code-block:: nim
- ## This module is a sample.
- import strutils
- proc helloWorld*(times: int) =
- ## Takes an integer and outputs
- ## as many "hello world!"s
- for i in 0 .. times-1:
- echo "hello world!"
- helloWorld(5)
- Document Types
- ==============
- HTML
- ----
- The generation of HTML documents is done via the ``doc`` command. This command
- takes either a single .nim file, outputting a single .html file with the same
- base filename, or multiple .nim files, outputting multiple .html files and,
- optionally, an index file.
- The ``doc`` command::
- nim doc sample
- Partial Output::
- ...
- proc helloWorld(times: int) {.raises: [], tags: [].}
- ...
- The full output can be seen here: `docgen_sample.html <docgen_sample.html>`_.
- It runs after semantic checking and includes pragmas attached implicitly by the
- compiler.
- JSON
- ----
- The generation of JSON documents is done via the ``jsondoc`` command. This command
- takes in a .nim file and outputs a .json file with the same base filename. Note
- that this tool is built off of the ``doc`` command (previously ``doc2``), and
- contains the same information.
- The ``jsondoc`` command::
- nim jsondoc sample
- Output::
- {
- "orig": "docgen_sample.nim",
- "nimble": "",
- "moduleDescription": "This module is a sample",
- "entries": [
- {
- "name": "helloWorld",
- "type": "skProc",
- "line": 5,
- "col": 0,
- "description": "Takes an integer and outputs as many "hello world!"s",
- "code": "proc helloWorld(times: int) {.raises: [], tags: [].}"
- }
- ]
- }
- Similarly to the old ``doc`` command, the old ``jsondoc`` command has been
- renamed to ``jsondoc0``.
- The ``jsondoc0`` command::
- nim jsondoc0 sample
- Output::
- [
- {
- "comment": "This module is a sample."
- },
- {
- "name": "helloWorld",
- "type": "skProc",
- "description": "Takes an integer and outputs as many "hello world!"s",
- "code": "proc helloWorld*(times: int)"
- }
- ]
- Note that the ``jsondoc`` command outputs it's JSON without pretty-printing it,
- while ``jsondoc0`` outputs pretty-printed JSON.
- Related Options
- ===============
- Project switch
- --------------
- ::
- nim doc --project filename.nim
- This will recursively generate documentation of all nim modules imported
- into the input module that belong to the Nimble package that ``filename.nim``
- belongs to.
- Index switch
- ------------
- ::
- nim doc2 --index:on filename.nim
- This will generate an index of all the exported symbols in the input Nim
- module, and put it into a neighboring file with the extension of ``.idx``. The
- index file is line-oriented (newlines have to be escaped). Each line
- represents a tab-separated record of several columns, the first two mandatory,
- the rest optional. See the `Index (idx) file format`_ section for details.
- Once index files have been generated for one or more modules, the Nim
- compiler command ``buildIndex directory`` can be run to go over all the index
- files in the specified directory to generate a `theindex.html <theindex.html>`_
- file.
- See source switch
- -----------------
- ::
- nim doc2 --git.url:<url> filename.nim
- With the ``git.url`` switch the *See source* hyperlink will appear below each
- documented item in your source code pointing to the implementation of that
- item on a GitHub repository.
- You can click the link to see the implementation of the item.
- The ``git.commit`` switch overrides the hardcoded `devel` branch in config/nimdoc.cfg.
- This is useful to link to a different branch e.g. `--git.commit:master`,
- or to a tag e.g. `--git.commit:1.2.3` or a commit.
- Source URLs are generated as `href="${url}/tree/${commit}/${path}#L${line}"` by default and this compatible with GitHub but not with GitLab.
- Similarly, ``git.devel`` switch overrides the hardcoded `devel` branch for the `Edit` link which is also useful if you have a different working branch than `devel` e.g. `--git.devel:master`.
- Edit URLs are generated as `href="${url}/tree/${devel}/${path}#L${line}"` by default.
- You can edit ``config/nimdoc.cfg`` and modify the ``doc.item.seesrc`` value with a hyperlink to your own code repository.
- In the case of Nim's own documentation, the ``commit`` value is just a commit
- hash to append to a formatted URL to https://github.com/nim-lang/Nim. The
- ``tools/nimweb.nim`` helper queries the current git commit hash during the doc
- generation, but since you might be working on an unpublished repository, it
- also allows specifying a ``githash`` value in ``web/website.ini`` to force a
- specific commit in the output.
- Other Input Formats
- ===================
- The *Nim compiler* also has support for RST (reStructuredText) files with
- the ``rst2html`` and ``rst2tex`` commands. Documents like this one are
- initially written in a dialect of RST which adds support for nim source code
- highlighting with the ``.. code-block:: nim`` prefix. ``code-block`` also
- supports highlighting of C++ and some other c-like languages.
- Usage::
- nim rst2html docgen.txt
- Output::
- You're reading it!
- The ``rst2tex`` command is invoked identically to ``rst2html``, but outputs
- a .tex file instead of .html.
- HTML anchor generation
- ======================
- When you run the ``rst2html`` command, all sections in the RST document will
- get an anchor you can hyperlink to. Usually, you can guess the anchor lower
- casing the section title and replacing spaces with dashes, and in any case, you
- can get it from the table of contents. But when you run the ``doc`` or ``doc2``
- commands to generate API documentation, some symbol get one or two anchors at
- the same time: a numerical identifier, or a plain name plus a complex name.
- The numerical identifier is just a random number. The number gets assigned
- according to the section and position of the symbol in the file being processed
- and you should not rely on it being constant: if you add or remove a symbol the
- numbers may shuffle around.
- The plain name of a symbol is a simplified version of its fully exported
- signature. Variables or constants have the same plain name symbol as their
- complex name. The plain name for procs, templates, and other callable types
- will be their unquoted value after removing parameters, return types, and
- pragmas. The plain name allows short and nice linking of symbols that works
- unless you have a module with collisions due to overloading.
- If you hyperlink a plain name symbol and there are other matches on the same
- HTML file, most browsers will go to the first one. To differentiate the rest,
- you will need to use the complex name. A complex name for a callable type is
- made up of several parts:
- (**plain symbol**)(**.type**),(**first param**)?(**,param type**)\*
- The first thing to note is that all callable types have at least a comma, even
- if they don't have any parameters. If there are parameters, they are
- represented by their types and will be comma-separated. To the plain symbol a
- suffix may be added depending on the type of the callable:
- ------------- --------------
- Callable type Suffix
- ------------- --------------
- proc *empty string*
- macro ``.m``
- method ``.e``
- iterator ``.i``
- template ``.t``
- converter ``.c``
- ------------- --------------
- The relationship of type to suffix is made by the proc ``complexName`` in the
- ``compiler/docgen.nim`` file. Here are some examples of complex names for
- symbols in the `system module <system.html>`_.
- * ``type SomeSignedInt = int | int8 | int16 | int32 | int64`` **=>**
- `#SomeSignedInt <system.html#SomeSignedInt>`_
- * ``var globalRaiseHook: proc (e: ref E_Base): bool {.nimcall.}`` **=>**
- `#globalRaiseHook <system.html#globalRaiseHook>`_
- * ``const NimVersion = "0.0.0"`` **=>**
- `#NimVersion <system.html#NimVersion>`_
- * ``proc getTotalMem(): int {.rtl, raises: [], tags: [].}`` **=>**
- `#getTotalMem, <system.html#getTotalMem>`_
- * ``proc len[T](x: seq[T]): int {.magic: "LengthSeq", noSideEffect.}`` **=>**
- `#len,seq[T] <system.html#len,seq[T]>`_
- * ``iterator pairs[T](a: seq[T]): tuple[key: int, val: T] {.inline.}`` **=>**
- `#pairs.i,seq[T] <system.html#pairs.i,seq[T]>`_
- * ``template newException[](exceptn: typedesc; message: string;
- parentException: ref Exception = nil): untyped`` **=>**
- `#newException.t,typedesc,string,ref.Exception
- <system.html#newException.t,typedesc,string,ref.Exception>`_
- Index (idx) file format
- =======================
- Files with the ``.idx`` extension are generated when you use the `Index
- switch <#related-options-index-switch>`_ along with commands to generate
- documentation from source or text files. You can programmatically generate
- indices with the `setIndexTerm()
- <rstgen.html#setIndexTerm,RstGenerator,string,string,string,string,string>`_
- and `writeIndexFile() <rstgen.html#writeIndexFile,RstGenerator,string>`_ procs.
- The purpose of ``idx`` files is to hold the interesting symbols and their HTML
- references so they can be later concatenated into a big index file with
- `mergeIndexes() <rstgen.html#mergeIndexes,string>`_. This section documents
- the file format in detail.
- Index files are line-oriented and tab-separated (newline and tab characters
- have to be escaped). Each line represents a record with at least two fields
- but can have up to four (additional columns are ignored). The content of these
- columns is:
- 1. Mandatory term being indexed. Terms can include quoting according to
- Nim's rules (e.g. \`^\`).
- 2. Base filename plus anchor hyperlink (e.g. ``algorithm.html#*,int,SortOrder``).
- 3. Optional human-readable string to display as a hyperlink. If the value is not
- present or is the empty string, the hyperlink will be rendered
- using the term. Prefix whitespace indicates that this entry is
- not for an API symbol but for a TOC entry.
- 4. Optional title or description of the hyperlink. Browsers usually display
- this as a tooltip after hovering a moment over the hyperlink.
- The index generation tools try to differentiate between documentation
- generated from ``.nim`` files and documentation generated from ``.txt`` or
- ``.rst`` files. The former are always closely related to source code and
- consist mainly of API entries. The latter are generic documents meant for
- human reading.
- To differentiate both types (documents and APIs), the index generator will add
- to the index of documents an entry with the title of the document. Since the
- title is the topmost element, it will be added with a second field containing
- just the filename without any HTML anchor. By convention, this entry without
- anchor is the *title entry*, and since entries in the index file are added as
- they are scanned, the title entry will be the first line. The title for APIs
- is not present because it can be generated concatenating the name of the file
- to the word **Module**.
- Normal symbols are added to the index with surrounding whitespaces removed. An
- exception to this are the table of content (TOC) entries. TOC entries are added to
- the index file with their third column having as much prefix spaces as their
- level is in the TOC (at least 1 character). The prefix whitespace helps to
- filter TOC entries from API or text symbols. This is important because the
- amount of spaces is used to replicate the hierarchy for document TOCs in the
- final index, and TOC entries found in ``.nim`` files are discarded.
- Additional resources
- ====================
- `Nim Compiler User Guide <nimc.html#compiler-usage-commandminusline-switches>`_
- `RST Quick Reference
- <http://docutils.sourceforge.net/docs/user/rst/quickref.html>`_
- The output for HTML and LaTeX comes from the ``config/nimdoc.cfg`` and
- ``config/nimdoc.tex.cfg`` configuration files. You can add and modify these
- files to your project to change the look of the docgen output.
- You can import the `packages/docutils/rstgen module <rstgen.html>`_ in your
- programs if you want to reuse the compiler's documentation generation procs.
|