doczar

    0.3.4 • Public • Published

    doczar

    Doczar (pronounced dōzer) is a simple, explicit documentation generator for javascript, python, ruby, java, c-like languages, and others. It is used to generate its own docs.

    Rather than attempting to document the source code itself, doczar only uses tagged comments. The comment format has been designed for legibility and uses a simple scope model to make documenting large, complex entities easy.

    Features

    • describe modules and object-oriented structures
    • inheritence, multiple inheritence and Java interface
    • Github-flavored markdown with syntax highlighting
    • semi-automatic crosslinking
    • callbacks and events
    • multiple return values and keyword arguments
    • function signatures
    • automatic Node.js dependency graph documentation
    Table Of Contents
    1 Installation
    2 Shell Usage
    3 Development
    4 Comment Syntax
    5 Components, Types and Paths
    6 Documents and Spares
    7 Functions
    8 Inheritence
    9 Events and Errors
    10 Generics
    11 Javascript ES6
    12 LICENSE

    Installation

    doczar is cross-platform. Because pathnames are sanitized differently on Windows, documentation is best viewed and/or hosted on the same machine where it was generated.

    To add the binary doczar to your executable path:

    $ sudo npm install -g doczar

    Shell Usage

    $ doczar --in=src/**/*.c --out docz
    $ doczar --jsmod ./main # outputs to ./docs 
    option description
    o, out Selects a directory to fill with documentation output. The directory need not exist or be empty.
    i, in Selects files to document. Parses nix-like wildcards using glob. doczar does not parse directories - you must select files.
    j, js, jsmod Loads the filename with required and documents every required source file.
    with Include a prebuilt standard library in the documentation.
    dev Display Components marked with the @development modifier.
    api Display only Components marked with the @api modifier.
    raw Log events as json strings instead of pretty printing them.
    json Create an index.json file in each directory instead of a rendered index.html.
    date Explicitly set the datestamp on each page with any Date-compatible string.

    Development

    doczar is developed and maintained by Kevin "Schmidty" Smith under the MIT license. If you want to see continued development on doczar, please help me pay my bills!

    Comment Syntax

    Declarations

    The simplest form of documentation is a single Declaration in its own block comment with an informational summary. The opening line of a block comment must contain only the characters opening the comment, a Declaration and as many spaces and tabs as you want. On the next line you may begin describing this unit of code with github-flavored markdown.

    In languages with c-like block comments (don't forget css) it looks like this:

    /**     @class MyClass
        For compatibility purposes, c-like comments support any
        number of asterisks *immediately after the slash*.
    */
    /************* @member MyClass#asteriskCount
        *Any* number of asterisks (greater than zero).
    */

    The final newline is not required. This is mainly to support @module declarations that span multiple files. See Modules for more information on scope and @module.

    /** @module BoxFactory */
    int myInt = 42/* @local/int myInt */
     
    /** @spare ExtraDocs
        These extra documents are part of the
        [BoxFactory](.) module. Their full
        path is `BoxFactory~ExtraDocs`.
    */

    A special markdown caveat: you will need two newlines to terminate a bullet list.

    /**     @property/Function doTheThings
        Does all the things. It does:
         * the hottest things
         * the coolest things
         * all the things you could ever
            possibly imagine
     
        And it does them fast!
    */

    In python, any "triple" string literal that meets the first-line requirements is a document comment.

    def referenceMontyPython (skit):
        """     @property/function referenceMontyPython
            Either triple or triple-double is fine.
        """

    Ruby users may use =begin and =end with the same rules.

    =begin  @module MyRubyGem
        I don't know very much about Ruby.
    =end

    Finally, HTML comments are also supported.

    <!--    @module SplashPage
        Guest user landing page with corporate logo and account login/registration tools.
    -->

    Indentation of a markdown section is automagically normalized to the least-indented line and you may include any number of tab and space characters before any Declaration. You can even break in the middle of a link definition.

    /** @member/int foo
        A contracted document with
        little available horizontal
        space that needs a [link]
        (http://google.com) to a
        search engine.
    */

    To add a child with a standalone doc comment, simply specify a complex path of any length.

    /**     @class FooClass
        A simple class.
    */
    /**     @property/Function FooClass.getDefault
        Get a new default instance of FooClass.
    */
    /**     @returns/FooClass FooClass.getDefault)defaultInstance
        Returns a new instance with the default configuration.
    */

    Inner Declarations

    Once you have opened a declaration, you may write additional declarations which will all be scoped to the enclosing comment.

    /**     @class MyClass
        A simple class.
    @property/Function getAllInstances
        A static Function that returns all instances of MyClass.
    @member/Function doSomethingCool
        A member Function on each instance of MyClass.
    */

    Modules

    In some languages such as Java, the concept of a module is very specific and @module declarations always describe an importable structure. In environments like Node.js where directly importing submodules is rare, one might use a @module to describe a type that is involved in processing or may be returned but which is abstract or cannot be accessed directly.

    The @module Declaration has an infectious scope. Every Declaration after it is scoped to the module Component, as are value type paths that begin with a delimiter. See crosslinking for more information. If you want to semantically declare a @module without affecting the scope, use the @submodule declaration instead.

    The global namespace and the first level of modules live together. Beyond the root, modules possess their own namespace and are delimited with :.

    /**     @module Foo
        The Foo module.
    */
    /**     @class Bar
        The Foo.Bar class.
    */
    /**     @submodule/class Baz
        The Foo:Baz class.
    */
    /**     @property/Function createBar
     
    */

    Value Types

    A value type is declared with a forward slash. Multiple value types are declared with the pipe | character.

    /**     @property/String foobar
        A String property called "foobar".
    */
    /**     @property/Number|undefined result
        This property may be either a Number or `undefined`.
    */

    Modifiers and Flags

    Modifiers, and their simpler counterpart Flags, are statements which modify the Declaration directly above them rather than declaring a new Component. Modifiers have serious consequences for the visibility and position of a Component and its children. Flags just render literally as helpful keywords in a contrasting color.

    /**     @class MyClass
        @super LisasClass
        @public
        A simple subclass of Lisa's class.
    @member/String uniqueID
        @const
        This id String is generated at instantiation and because
        it is constant, it will never give you up, never let you
        down.
    */

    Here is a list of the available Modifiers and Flags

    Modifiers

    • @development hides this Component unless the --dev flag is used
    • @api reveals this Component and its ancestors when the --api flag is used
    • @optional indicates something which need not exist (usually an argument)
    • @super inherits from a superclass
    • @implements associates an implemented Java interface
    • @default describes a default value. Always use backticks.

    Flags

    • @public
    • @protected
    • @private
    • @abstract
    • @final
    • @volatile

    Components, Types and Paths

    Let's look at all the Components we have available.

    Primary Components

    These are the only Components which may be used to open a new document comment.

    • @module organizational Component
    • @class instantiable class objects
    • @struct c-like structures
    • @interface Java interface
    • @spare bare markdown document
    • @property static property
    • @member instance property or method
    • @event event descriptions
    • @throws conditions causing an exception to be thrown
    • @enum list of named values

    Inner Components

    These may only appear inside a document comment opened by a Primary Component Declaration.

    • @argument optionally-named function or event argument
    • @kwarg python-style keyword argument
    • @callback callback function
    • @returns return value
    • @signature an alternate function signature
    • @named a named value in an @enum.

    Many of these Component types have their own special path delimiters. This lets us reference more things as paths than in any other document generator. Here they are:

    Special Delimiters

    • ~ @spare
    • . @property
    • # @member
    • ( @argument
    • ) @returns
    • ! @throws
    • + @event
    • & @signature

    You can use a name starting with a delimiter to imply the Component type of any Inner Declaration, skipping directly to the value type. You may do this with any of the types listed above as an entirely optional feature. My personal recommendation is to use it only for @property and @member.

    The default delimiter is ".", for @property.

    /**     @class MyClass
    @Function .getAllInstances
        Load all instances of MyClass.
    @Number count
        Total number of instances.
    @String #uniqueID
        The unique identifier of this MyClass instance.
    @Error !EnvironFailure
        Throws an Error during instantiation if the local
        environment is configured incorrectly.
    @String (uniqueID
        A unique identifier to instantiate with.
    */

    Feel free to document a type as being a pointer or array.

    /**     @struct Node
        A linked list node.
    @member/Node* previous
        Previous Node in the chain.
    @member/Node* next
        Next Node in the chain.
    @member/String[] payload
        Data stored by this node in the chain.
    */

    Crosslinking

    You can easily crosslink to any other defined Component using the normal markdown link syntax. If you start a crosslink path with a delimiter, the target will be rooted to the current module scope.

    Furthermore, every defined Component is also a valid type, and the same rule applies when starting a type path with a delimiter.

    /**     @module MyModule
        A simple module.
    */
    /**     @class MyClass
        A simple class.
    */
    /**     @property/Function clone
    @argument/.MyClass source
        The [MyClass](.MyClass) instance to clone.
    @returns/MyModule.MyClass
        The fresh [MyClass](MyModule.MyClass) instance.
    */

    Documents and Spares

    You may Declare a Component any number of times. Child Components and documentation accumulates in the order in which it is loaded.

    /**     @class MyClass
        Some information about MyClass.
    */
    /**     @class MyClass
        Some (more) information about MyClass.
    */

    Available exclusively as an Inner Declaration, @load allows you to pull in an external markdown document. Because in loaded docs it's valuable to support html hash links , i.e. [more info](#more-info), it is impossible to properly support localized paths when using @load. Your links will be scoped to the global namespace and any type link starting with a delimiter will be rejected.

    This example is taken directly from the doczar doc comments.

    /**     @module doczar
        Select, load and parse source files for `doczar`-format
        documentation comments. Render html output to a
        configured disk location.
    @spare README
        This is the rendered output of the `doczar` source
        documentation. *View the [source]
        (https://github.com/shenanigans/node-doczar) on GitHub!*
        @load
            ./README.md
    */

    In the first stage of rendering, the markdown document(s) on a Component are moved into new @spare instances. The normal documentation appearing after a Declaration is moved to the path ~summary. When available, ~summary is used when a Component is displayed on another Component's output page, and ~details is used on a Component's own page. If you choose to manually specify only one of these two paths, all accumulated documentation not associated with a @spare will default to the unspecified path. When both paths are specified, unassociated documentation is appended to ~details.

    There is no limit to how many spares a Component may have, however their titles are subject to normal namespace restrictions (sorry).

    /**     @class FooClass
        Basic information.
    @spare details
        Detailed information.
    */
    /**     @class FooClass
        More basic information.
    */
    /**     @class BarClass
        Detailed information.
    @spare summary
        Basic information.
    */
    /**     @class BarClass
        More detailed information.
    */

    Functions

    The Inner Declarations @argument, @kwarg, @callback, @signature and @returns are used to describe Functions. During parsing, these Components have special scoping which is designed to help intuitively document an entire Function in one tag. Never forget that this special scope only affects these Component types exclusively. The scope will be immediately reset by the first normal Declaration.

    Here is a simple Function Declaration with @argument and @returns declarations. You may name your arguments and return values, or not.

    /**     @property/Function doTheDew
        Do the Dew until you can't even.
    @argument/Number volume
        Volume of Dew to do, in fluid ounces.
    @argument/String method
        How to do the Dew.
    @returns/String message
        Returns a hip phase, such as "Totally radical!!!".
    */
    /**     @property/Function sortItems
        A sorting function for Item instances.
    @argument/Item
        The first Item.
    @argument/Item
        The second Item.
    @returns/Number
        -1, 0, or 1.
    */

    Keyword arguments are as easy as replacing @argument with @kwarg.

    /**     @property/Function tellParrotJoke
        Repeat some Monty Python jokes about a parrot.
    @kwarg/String parrotType
        Type of parrot to joke about.
    */

    Callback Functions

    The @callback Declaration expands the @argument scope in order to document the callback Function's arguments. You may reclose this scope with any unnamed @returns Declaration. You may name your callbacks, or not.

    /**     @property/Function loadDefinitions
        Load definition file from the remote server.
    @argument/String hostname
        URL of the remote server.
    @callback
        @argument/Error|undefined error
            If a fatal Error prevented the file from
            being loaded properly, it is passed to
            the callback.
        @argument/Buffer|undefined definitionsFile
            The loaded definitions file, or `undefined`
            if an Error occured.
        @returns
    @argument/Boolean devLogging
        @optional
        Activate development-mode logging messages.
    */

    Although I've never seen this pattern used, it is possible to document multiple (pythonic) @returns Declarations on a @callback. You can still close the scope manually with a blank @returns Declaration.

    /**     @property/Function getJiggyWithIt
        Get jiggy with it.
    @callback onError
        Called if a fatal Exception occured.
        @returns/function responseAction
            What to do about the Exception.
        @returns/Number priority
            How important this reaction is.
        @returns
    @callback onSuccess
        Called if we got jiggy successfully.
        @argument/Number jigginessLevel
            Maximum level of jigginess achieved.
    */

    Function Signatures

    If you're writing an overloaded function with multiple signatures or need to document special permutations of optional arguments, @signature is there for you. It redefines the return value and argument signature and documents the signature separately.

    When you create a @signature with an Inner Declaration, the scope rules for Functions and @argument Components apply.

    /**     @property/Function writeBuffer
        Interprets the contents of a Buffer as UTF-8
        and writes it in the sky with smoke signals.
    @signature/Number (content)
        Write out the entire Buffer and return the
        number of bytes written.
    @signature/Number|undefined (content, bytes)
        Write up to `bytes` bytes of text from
        `content`. If there is content remaining,
        returns the number of unwritten bytes.
    @argument/Buffer content
        Text content to skywrite.
    @argument/Number bytes
        Limit output to a set number of bytes.
    */

    Signatures may be declared in their own comments.

    /**     @signature writeBuffer (content, bytes)
        Write up to `bytes` bytes of text from `content`.
        If there is content remaining, returns the number
        of unwritten bytes.

    You may also define a signature with value types. These types have no additional implications, they are only displayed in the documentation (and crosslinked).

    /**     @property/Function write
        Output information through the Morse telegram interface.
    @argument content
        The content to send.
    @signature (String content)
        Send the content as ascii text, followed by `STOP`.
    @signature (Number content)
        Convert the number to ascii text and send, followed
        by `STOP`.
    @signature (Array<String> content)
        Send each message, delimited and terminated with
        `STOP`.
    */

    Signatures cannot be inherited or overridden individually.

    Inheritence

    To inherit static and member properties from another Component of any type, use the @super modifier.

    /**     @class BaseClass
        A simple base class.
    @Function createDefault
        Create and return a default instance.
        @returns/.BaseClass
    @Function #toString
        Produce a String representation of this instance.
    */
    /**     @class SubClass
        A simple subclass.
    @Function #toString
        Overrides `BaseClass#toString`.
    */

    If a Component with a superclass also has at least one value type that is exactly "function" or "Function", it will also inherit arguments, signatures, return values and thrown exceptions.

    Java interfaces are also supported, with @interface and @implements.

    /**     @interface UniversalRemote
        The common interface for a universal remote control.
    @member/Function volumeUp
        Increase speaker volume.
    @member/Function volumeDown
        Decrease speaker volume.
    */
    /**     @class Tamtung_Model042_3
        @implements .UniversalRemote
    @member/Function volumeUp
        Increase speaker volume.
    @member/Function volumeDown
        Decrease speaker volume.
    */

    Events and Errors

    Document events with the @event declaration. Pass information with your Event by attaching @argument Components.

    /**     @class Element
        An HTML DOM Element.
    @event click
        Sent when a user presses down and releases the
        same mouse button within the bounding box of this
        Element, without exceeding the host browser's
        minimum threshold for [drag](Element+drag) events.
        Unless cancelled, this event bubbles upward and
        occurs in parent Elements until the `document` is
        reached.
        @argument/MouseEvent
            The originating mouse event.
    */

    Cases which cause exceptions to be thrown may be documented with the simple Declaration @throws. You may name your exception cases, or not.

    class dict:
        """     @class dict
            A hash map of Strings to untyped references.
        """
        def get (self, key):
            """     @member/function dict#get
                Retrieve a reference.
            @throws/KeyError notFound
                Failure to find a key results in an exception.
            @throws/TypeError
                If the key reference does not implement
                `__hash__`, a TypeError is raised.
            """

    Generics

    Type paths support generics (java), templates (c++) and arrays-of-things (javascript). You may specify any number of generic types on any type path, including with the use of multiple types and pipes |.

    /**     @property/Array<String>|Object<String, String>|undefined fooProp
        An Array of Strings, an Object mapping Strings to Strings, or undefined.
    */

    Coming Soon

    Generics in Class Declarations.

    /**     @class Container<Object elemType>
        A container of arbitrarily-typed references.
    @function #get
        @argument/String elemName
            The name of the element to get.
        @returns/%elemType|null
            The requested element, or `null`.
    */

    Javascript ES6

    There is standard library coverage for ES6. Call doczar with the --with es6 option. Additionally, the browser-strict and iojs standard libraries will pull in ES6 documentation.

    Several additional tricks were added to doczar itself to support the documentation of ES6 scripts.

    Symbols

    Symbols are supported inline everywhere normal paths are supported. You may use either absolute or locally rooted paths in Symbols.

    /**     @module MainPackage */
     
    /**     @class FooList
        An Iterable collection of Foos.
    @member/Function [Symbol.iterator]
        Create an [Iterator]() that lists all our Foos.
    @property/Symbol staticSymbol
        A Symbol stored statically on the FooList class.
    */
     
    /**     @member/String FooList#[.FooList.staticSymbol]
        A String stored on FooList instances, mapped to a
        static symbol.
    */

    The History Channel Presents: Ancient Symbols

    /**     @class Foo
        @root
    @property/Symbol alfa
        A static Symbol mapped to a String.
    @property/Symbol [.alfa]
        A static Symbol mapped to a static Symbol.
    @property/Symbol [.[.alfa]]
        Another static Symbol mapped to a static Symbol.
    @member/String [.[.[.alfa]]]
        A String mapped to a static Symbol.
    */

    Rest and Spread

    To document use of the rest keyword or "spread" syntax to accept arbitrary numbers of arguments, use the @args declaration.

    /**     @member/Function Foo#methodAlfa
        A method that takes at least one argument.
    @argument/String firstArgument
        The first, mandatory argument.
    @args/Number restArguments
        An arbitrary number of additional arguments.
    */

    LICENSE

    The MIT License (MIT)

    Copyright (c) 2015 Kevin "Schmidty" Smith

    Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions:

    The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.

    THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.

    Install

    npm i doczar

    DownloadsWeekly Downloads

    16

    Version

    0.3.4

    License

    MIT

    Last publish

    Collaborators

    • shenanigans