Cs-doclet: Difference between revisions

From unkrig.de
Jump to navigation Jump to search
No edit summary
 
(16 intermediate revisions by the same user not shown)
Line 1: Line 1:
Cs-doclet is a [http://docs.oracle.com/javase/8/docs/technotes/guides/javadoc/ doclet] that generates the metadata files for CheckStyle checks and filters from 'doc tags' in the source files.
<meta name="keywords" content="java, doclet, javadoc, checkstyle"></meta>
<meta name="description" content="A doclet that generates the metadata files for CHECKSTYLE and ECLIPSE-CS from annotations and DOC tags in the source code of the checks and filters"></meta>
== Abstract ==


This tool is useful for developers of [http://checkstyle.sourceforge.net/ CheckStyle] checks and filters, and their integration in [http://eclipse-cs.sourceforge.net/ eclipse-cs].
Cs-doclet is a [http://docs.oracle.com/javase/8/docs/technotes/guides/javadoc/ JAVADOC doclet] that generates the metadata files for [http://checkstyle.sourceforge.net/ CheckStyle] and [http://eclipse-cs.sourceforge.net/ eclipse-cs] from annotations and [http://docs.oracle.com/javase/8/docs/technotes/tools/windows/javadoc.html#CHDJGIJB doc tags] in the source code of your checks and filters.
 
This doclet is useful only for authors of CheckStyle extensions, like [[Cs-contrib.unkrig.de|cs-contrib]].
 
== Intended audience ==
 
This tool is useful for the development of [http://checkstyle.sourceforge.net/ CheckStyle] checks and filters, and for their integration in [http://eclipse-cs.sourceforge.net/ eclipse-cs] and [http://www.mediawiki.org/wiki/MediaWiki MediaWiki].


== Extending CheckStyle ==
== Extending CheckStyle ==


CheckStyle comes with an API to [http://checkstyle.sourceforge.net/writingchecks.html extend the standard set of checks] and [http://checkstyle.sourceforge.net/writingfilters.html filters]:
CheckStyle comes with an API to [http://checkstyle.sourceforge.net/writingchecks.html extend] it with custom checks and filters. Here is a completely useless, yet typical example of a custom check:


'''File "src/com/pany/cs/checks/ColorCheck.java":'''
'''File "src/com/pany/cs/checks/ColorCheck.java":'''
Line 28: Line 36:
  }
  }


This API supports internationalization be means of "messages.properties" files:
The CheckStyle extension API supports internationalization be means of "messages.properties" files:


'''File "src/com/pany/cs/checks/messages.properties":'''
'''File "src/com/pany/cs/checks/messages.properties":'''
Line 36: Line 44:
  theColorIs = Die Farbe ist ''{0}''
  theColorIs = Die Farbe ist ''{0}''


Then you'd write a "CheckStyle configuration file"
To make use of this check, you'd write a "CheckStyle configuration file"


'''File "checkstyle-config.xml":'''
'''File "checkstyle-config.xml":'''
Line 45: Line 53:
   <property name="severity" value="warning" />
   <property name="severity" value="warning" />
   <module name="TreeWalker">
   <module name="TreeWalker">
     <module name="com.pany.cs.checks.ColorCheck">
     <module name="com.pany: ColorCheck">
       <property name="color" value="blue" />
       <property name="color" value="blue" />
     </module>
     </module>
Line 54: Line 62:


  $ javac -d bin src/com/pany/cs/checks/ColorCheck.java
  $ javac -d bin src/com/pany/cs/checks/ColorCheck.java
  $ java -classpath bin;path/to/checkstyle-6.1-all.jar \
  $ java -classpath '<span style="color:red">bin</span>;path/to/checkstyle-6.1-all.jar' \
  > com.puppycrawl.tools.checkstyle.Main \
  > com.puppycrawl.tools.checkstyle.Main \
  > -c checkstyle-config.xml \
  > -c checkstyle-config.xml \
Line 68: Line 76:
Obviously, the Java code and the "messages.properties" files must be kept in sync with the Java code at all times, which is naturally very error-prone.
Obviously, the Java code and the "messages.properties" files must be kept in sync with the Java code at all times, which is naturally very error-prone.


Cs-doclet facilitates the task by generating the "messages.properties" file from doc tags in the source code:
Cs-doclet facilitates the task by generating the "messages.properties" file from annotations in the source code:


'''File "src/com/pany/cs/checks/MyCheck.java":'''
'''File "src/com/pany/cs/checks/MyCheck.java":'''
Line 80: Line 88:
  class ColorCheck extends Check {
  class ColorCheck extends Check {
   
   
     <span style="color:red">/** @cs-message The color is ''{0}'' */
     <span style="color:red">@Message("The color is ''{0}''")
     public static final String MESSAGE_KEY_THE_COLOR_IS = "theColorIs";</span>
     private static final String MESSAGE_KEY_THE_COLOR_IS = "theColorIs";</span>
   
   
     public void
     public void
Line 97: Line 105:
  $ javadoc \
  $ javadoc \
  > <span style="color:red">-doclet de.unkrig.doclet.cs.CsDoclet</span> \
  > <span style="color:red">-doclet de.unkrig.doclet.cs.CsDoclet</span> \
  > <span style="color:red">-docletpath path/to/cs-doclet.jar;bin;path/to/checkstyle-6.1-all.jar;path/to/net.sf.eclipsecs.core-6.1.jar</span>
  > <span style="color:red">-docletpath "path/to/cs-doclet.jar;bin;path/to/checkstyle-6.1-all.jar;path/to/net.sf.eclipsecs.core-6.1.jar"</span> \
  > <span style="color:red">-messages.properties-dir src</span>
  > <span style="color:red">-messages.properties-dir src</span> \
  > -sourcepath src
  > -sourcepath src \
  > -classpath ../net.sf.checkstyle-6.1/checkstyle-6.1/checkstyle-6.1-all.jar
  > -classpath ../net.sf.checkstyle-6.1/checkstyle-6.1/checkstyle-6.1-all.jar \
> com.pany.cs.checks
  Loading source files for package com.pany.cs.checks...
  Loading source files for package com.pany.cs.checks...
  Constructing Javadoc information...
  Constructing Javadoc information...
Line 107: Line 116:
Notice that both "checkstyle.jar" and "net.sf.eclipsecs-core.jar" must be on the "-docletpath".
Notice that both "checkstyle.jar" and "net.sf.eclipsecs-core.jar" must be on the "-docletpath".


The generated "messages.properties" file looks like this:
The generated "src/com/pany/cs/checks/messages.properties" file looks like this:


  # This file was generated by the CS doclet; see http://cs-contrib.unkrig.de
  # This file was generated by the CS doclet; see http://cs-doclet.unkrig.de/
   
   
  # Custom check messages, in alphabetical order.
  # Custom check messages, in alphabetical order.
   
   
  # --------------- com.pany.cs.ColorCheck ---------------
  # --------------- com.pany: ColorCheck ---------------
  theColorIs = The color is ''{0}''
  <span style="color:red">theColorIs</span> = <span style="color:red">The color is ''{0}''</span>


Now all the documentation of the check and its property "color" is where it belongs: In the source code.
And voilà! All the messages are where they belong: In the source code.


== Integrating with eclipse-cs ==
== Integrating with eclipse-cs ==
Line 133: Line 142:
             internal-name="com.pany.cs.checks.ColorCheck"
             internal-name="com.pany.cs.checks.ColorCheck"
             parent="TreeWalker"
             parent="TreeWalker"
             name="%com.pany.cs.checks.ColorCheck.name"
             name="%ColorCheck.name"
         >
         >
             <alternative-name internal-name="com.pany.cs.checks.ColorCheck" />
             <alternative-name internal-name="com.pany.cs.checks.ColorCheck" />
             <description>%com.pany.cs.checks.ColorCheck.desc</description>
             <description>%ColorCheck.desc</description>
   
   
             <property-metadata
             <property-metadata
Line 143: Line 152:
                 default-value="Yellow"
                 default-value="Yellow"
             >
             >
                 <description>%com.pany.cs.checks.ColorCheck.color</description>
                 <description>%ColorCheck.color</description>
             </property-metadata>
             </property-metadata>
             <message-key key="theColorIs" />
             <message-key key="theColorIs" />
Line 152: Line 161:
'''File "checkstyle-metadata.properties":'''
'''File "checkstyle-metadata.properties":'''
  Whitespace.group = Whitespace
  Whitespace.group = Whitespace
  com.pany.cs.checks.ColorCheck.name = com.pany.cs.ColorCheck
  ColorCheck.name = com.pany: ColorCheck
  com.pany.cs.checks.ColorCheck.desc =\
  ColorCheck.desc =\
     A completely useless check which merely prints a (localizable) message each \
     A completely useless check which merely prints a (localizable) message each \
     time it encounters an annotation.
     time it encounters an annotation.
  com.pany.cs.checks.ColorCheck.color = A completely useless check parameter.
  ColorCheck.color = A completely useless check parameter.


Tedious, isn't it? Well, you can tell cs-doclet to also generate ''these'' files from doc comments:
Tedious, isn't it? Well, you can tell cs-doclet to also generate ''these'' files from annotations (and doc comments):


'''File "src/com/pany/cs/checks/MyCheck.java":'''
'''File "src/com/pany/cs/checks/MyCheck.java":'''
Line 169: Line 178:
  import com.puppycrawl.tools.checkstyle.api.TokenTypes;
  import com.puppycrawl.tools.checkstyle.api.TokenTypes;
   
   
  <span style="color:red">/**
  import de.unkrig.csdoclet.StringRuleProperty;
  * A completely useless check which merely prints a (localizable) message each time it encounters an annotation.
import de.unkrig.csdoclet.Rule;
   *
  * @cs-rule-group         %Whitespace.group
/**
  * @cs-rule-name         com.pany.cs.ColorCheck
  * <span style="color:red">A completely useless check which merely prints a</span>
  * @cs-rule-parent       TreeWalker
  * <span style="color:red">(localizable) message each time it encounters an annotation.</span>
  */</span>
   */
<span style="color:red">@Rule(
    group     = "%Whitespace.group",
    groupName  = "Whitespace",
    name       = "com.pany: ColorCheck",
    parent     = "TreeWalker"
)</span>
  public
  public
  class ColorCheck extends Check {
  class ColorCheck extends Check {
   
   
     /** @cs-message The color is ''{0}'' */
     @Message("The color is ''{0}''")
     public static final String MESSAGE_KEY_THE_COLOR_IS = "theColorIs";
     private static final String MESSAGE_KEY_THE_COLOR_IS = "theColorIs";
   
   
     <span style="color:red">/**
     /**
      * A completely useless check parameter.
      * <span style="color:red">A completely useless check parameter</span>.
       *
       */
      * @cs-property-name          color
    <span style="color:red">@StringRuleProperty(defaultValue = DEFAULT_COLOR)</span>
      * @cs-property-datatype      String
      * @cs-property-default-value Yellow
      */</span>
     public void
     public void
     setColor(String value) { this.color = value; }
     setColor(String value) { this.color = value; }
     private String color = "Yellow";
     private String color = <span style="color:red">DEFAULT_COLOR</span>;
    <span style="color:red">private static final String DEFAULT_COLOR = "Yellow";</span>
   
   
     @Override public int[]
     @Override public int[]
Line 202: Line 217:
  $ javadoc \
  $ javadoc \
  > -doclet de.unkrig.doclet.cs.CsDoclet \
  > -doclet de.unkrig.doclet.cs.CsDoclet \
  > -docletpath path/to/cs-doclet.jar;bin;path/to/checkstyle-6.1-all.jar;path/to/net.sf.eclipsecs.core-6.1.jar
  > -docletpath "path/to/cs-doclet.jar;bin;path/to/checkstyle-6.1-all.jar;path/to/net.sf.eclipsecs.core-6.1.jar" \
  > <span style="color:red">-checkstyle-metadata.properties-dir src</span>
  > <span style="color:red">-checkstyle-metadata.properties-dir src</span> \
  > <span style="color:red">-checkstyle-metadata.xml-dir src</span>
  > <span style="color:red">-checkstyle-metadata.xml-dir src</span> \
  > -messages.properties-dir src
  > -messages.properties-dir src \
  > -sourcepath src
  > -sourcepath src \
  > -classpath ../net.sf.checkstyle-6.1/checkstyle-6.1/checkstyle-6.1-all.jar
  > -classpath ../net.sf.checkstyle-6.1/checkstyle-6.1/checkstyle-6.1-all.jar \
> com.pany.cs.checks
  Loading source files for package com.pany.cs.checks...
  Loading source files for package com.pany.cs.checks...
  Constructing Javadoc information...
  Constructing Javadoc information...
Line 215: Line 231:


'''File "src/com/pany/cs/checks/checkstyle-metadata.properties":'''
'''File "src/com/pany/cs/checks/checkstyle-metadata.properties":'''
  # This file was generated by the CS doclet; see http://cs-contrib.unkrig.de.
  # This file was generated by the CS doclet; see http://cs-doclet.unkrig.de/
   
   
  # Rule groups:
  # Rule groups:
  Whitespace.group = Whitespace
  <span style="color:red">Whitespace.group</span> = <span style="color:red">Whitespace</span>
   
   
  # Custom checks, in alphabetical order.
  # Custom checks, in alphabetical order.
   
   
  # --------------- com.pany.cs.ColorCheck ---------------
  # --------------- <span style="color:red">com.pany: ColorCheck</span> ---------------
   
   
  com.pany.cs.checks.ColorCheck.name = com.pany.cs.ColorCheck
  <span style="color:red">ColorCheck.name</span> = <span style="color:red">com.pany: ColorCheck</span>
  com.pany.cs.checks.ColorCheck.desc =\
  <span style="color:red">ColorCheck.desc</span> =\
     A completely useless check which merely prints a (localizable) message each time it encounters an annotation.
     <span style="color:red">A completely useless check which merely prints a (localizable) message each time it encounters an annotation.</span>
  com.pany.cs.checks.ColorCheck.color                                  = A completely useless check parameter.
  <span style="color:red">ColorCheck.color</span>                                 = <span style="color:red">A completely useless check parameter.</span>


'''File "src/com/pany/cs/checks/checkstyle-metadata.xml":'''
'''File "src/com/pany/cs/checks/checkstyle-metadata.xml":'''
Line 236: Line 252:
  <checkstyle-metadata>
  <checkstyle-metadata>
   
   
     <!-- This file was generated by the CS doclet; see http://cs-contrib.unkrig.de -->
     &lt;!-- This file was generated by the CS doclet; see http://cs-doclet.unkrig.de/ -->
   
   
     <!-- ColorCheck -->
     &lt;!-- ColorCheck -->
   
   
     <rule-group-metadata name="%Whitespace.group" priority="999">
     <rule-group-metadata name="<span style="color:red">%Whitespace.group</span>" priority="999">
         <rule-metadata
         <rule-metadata
             internal-name="com.pany.cs.checks.ColorCheck"
             internal-name="<span style="color:red">com.pany.cs.checks.ColorCheck</span>"
             parent="TreeWalker"
             parent="<span style="color:red">TreeWalker</span>"
             name="%com.pany.cs.checks.ColorCheck.name"
             name="<span style="color:red">%ColorCheck.name</span>"
         >
         >
             <alternative-name internal-name="com.pany.cs.checks.ColorCheck" />
             <alternative-name internal-name="<span style="color:red">com.pany.cs.checks.ColorCheck</span>" />
             <description>%com.pany.cs.checks.ColorCheck.desc</description>
             <description><span style="color:red">%ColorCheck.desc</span></description>
   
   
             <property-metadata
             <property-metadata
                 name="color"
                 name="<span style="color:red">color</span>"
                 datatype="String"
                 datatype="<span style="color:red">String</span>"
                 default-value="Yellow"
                 default-value="<span style="color:red">Yellow</span>"
             >
             >
                 <description>%com.pany.cs.checks.ColorCheck.color</description>
                 <description><span style="color:red">%ColorCheck.color</span></description>
             </property-metadata>
             </property-metadata>
             <message-key key="theColorIs" />
             <message-key key="theColorIs" />
Line 261: Line 277:
  </checkstyle-metadata>
  </checkstyle-metadata>


== MediaWiki markup documentation ==
== Javadoc-like documentation ==


Typically, you will also want to publish human-readable documentation for your checks and filters, which is more or less identical with the text in the eclipse-cs files. This is also possible with the "-mediawiki-dir" command line option:
Typically, you will also want to publish human-readable documentation for your checks and filters, which is more or less identical with the text in the eclipse-cs metadata files. This is also possible with the "-d" command line option:


  $ javadoc \
  $ javadoc \
  > -doclet de.unkrig.doclet.cs.CsDoclet \
  > -doclet de.unkrig.doclet.cs.CsDoclet \
  > -docletpath path/to/cs-doclet.jar;bin;path/to/checkstyle-6.1-all.jar;path/to/net.sf.eclipsecs.core-6.1.jar
  > -docletpath "path/to/cs-doclet.jar;bin;path/to/checkstyle-6.1-all.jar;path/to/net.sf.eclipsecs.core-6.1.jar" \
  > -checkstyle-metadata.properties-dir src
  > -d ./csdoc \
> -checkstyle-metadata.xml-dir src
  > -sourcepath src \
> -messages.properties-dir src
  > -classpath ../net.sf.checkstyle-6.1/checkstyle-6.1/checkstyle-6.1-all.jar \
> <span style="color:red">-mediawiki-dir mediawiki</span>
> com.pany.cs.checks
  > -sourcepath src
  > -classpath ../net.sf.checkstyle-6.1/checkstyle-6.1/checkstyle-6.1-all.jar
  Loading source files for package com.pany.cs.checks...
  Loading source files for package com.pany.cs.checks...
  Constructing Javadoc information...
  Constructing Javadoc information...
  $
  $


This will generate:
This will generate a Javadoc-like HTML documentation for all checks and filters that are declared in the given Java packages.


'''File "mediawiki/com.pany.cs.ColorCheck.mw":'''
And you're done!
<!-- This file was generated by the CS doclet; see http://cs-contrib.unkrig.de -->
A completely useless check which merely prints a (localizable) message each time it encounters an annotation.


== Properties ==
== Summary ==
 
Default values appear <u>underlined</u>.
Before, you had to write one Java file and four more or less redundant metadata files per check; now you merely have to throw in a few annotations and doc comments and generate all four metadata files from the source code
 
<dl>
== Source code ==
<dt>color = "<i>String</i>" (optional; default value is Yellow)
<dd>A completely useless check parameter.
</dl>


Upload this text to a MediaWiki repository, and you'll see:
The source code for the plug-in is here:


[[File:screenshot_mediawiki.jpg]]
    https://github.com/aunkrig/doclet-cs
    https://github.com/aunkrig/doclet-cs-annotation

Latest revision as of 14:39, 25 January 2022

<meta name="keywords" content="java, doclet, javadoc, checkstyle"></meta> <meta name="description" content="A doclet that generates the metadata files for CHECKSTYLE and ECLIPSE-CS from annotations and DOC tags in the source code of the checks and filters"></meta>

Abstract[edit]

Cs-doclet is a JAVADOC doclet that generates the metadata files for CheckStyle and eclipse-cs from annotations and doc tags in the source code of your checks and filters.

This doclet is useful only for authors of CheckStyle extensions, like cs-contrib.

Intended audience[edit]

This tool is useful for the development of CheckStyle checks and filters, and for their integration in eclipse-cs and MediaWiki.

Extending CheckStyle[edit]

CheckStyle comes with an API to extend it with custom checks and filters. Here is a completely useless, yet typical example of a custom check:

File "src/com/pany/cs/checks/ColorCheck.java":

package com.pany.cs.checks;

import com.puppycrawl.tools.checkstyle.api.Check;
import com.puppycrawl.tools.checkstyle.api.DetailAST;
import com.puppycrawl.tools.checkstyle.api.TokenTypes;

public
class ColorCheck extends Check {

    public void
    setColor(String value) { this.color = value; }
    private String color = "Yellow";

    @Override public int[]
    getDefaultTokens() { return new int[] { TokenTypes.ANNOTATION }; }

    @Override public void
    visitToken(DetailAST ast) { this.log(ast, "theColorIs", this.color); }
}

The CheckStyle extension API supports internationalization be means of "messages.properties" files:

File "src/com/pany/cs/checks/messages.properties":

theColorIs = The color is {0}

File "src/com/pany/cs/checks/messages_de.properties":

theColorIs = Die Farbe ist {0}

To make use of this check, you'd write a "CheckStyle configuration file"

File "checkstyle-config.xml":

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE module PUBLIC "-//Puppy Crawl//DTD Check Configuration 1.3//EN" "http://www.puppycrawl.com/dtds/configuration_1_3.dtd">

<module name="Checker">
  <property name="severity" value="warning" />
  <module name="TreeWalker">
    <module name="com.pany: ColorCheck">
      <property name="color" value="blue" />
    </module>
  </module>
</module>

, and execute CheckStyle on a target project, e.g. on the example project itself:

$ javac -d bin src/com/pany/cs/checks/ColorCheck.java
$ java -classpath 'bin;path/to/checkstyle-6.1-all.jar' \
> com.puppycrawl.tools.checkstyle.Main \
> -c checkstyle-config.xml \
> -r src
Starting audit...
C:\dev\EclipseWS\de.unkrig.cs-contrib\foo\src\com\pany\cs\checks\ColorCheck.java:14:5: warning: The color is 'blue'
C:\dev\EclipseWS\de.unkrig.cs-contrib\foo\src\com\pany\cs\checks\ColorCheck.java:17:5: warning: The color is 'blue'
Audit done.
$

(We get the two warnings because there are two "@Override" annotations in the code.)

Obviously, the Java code and the "messages.properties" files must be kept in sync with the Java code at all times, which is naturally very error-prone.

Cs-doclet facilitates the task by generating the "messages.properties" file from annotations in the source code:

File "src/com/pany/cs/checks/MyCheck.java":

package com.pany.cs.checks;

import com.puppycrawl.tools.checkstyle.api.Check;
import com.puppycrawl.tools.checkstyle.api.DetailAST;
import com.puppycrawl.tools.checkstyle.api.TokenTypes;

public
class ColorCheck extends Check {

    @Message("The color is {0}")
    private static final String MESSAGE_KEY_THE_COLOR_IS = "theColorIs";

    public void
    setColor(String value) { this.color = value; }
    private String color = "Yellow";

    @Override public int[]
    getDefaultTokens() { return new int[] { TokenTypes.ANNOTATION }; }

    @Override public void
    visitToken(DetailAST ast) { this.log(ast, MESSAGE_KEY_THE_COLOR_IS, this.color); }
}

To generate the "messages.properties" file, you'd run JAVADOC with the cs-doclet and the "-messages.properties-dir" command line option:

$ javadoc \
> -doclet de.unkrig.doclet.cs.CsDoclet \
> -docletpath "path/to/cs-doclet.jar;bin;path/to/checkstyle-6.1-all.jar;path/to/net.sf.eclipsecs.core-6.1.jar" \
> -messages.properties-dir src \
> -sourcepath src \
> -classpath ../net.sf.checkstyle-6.1/checkstyle-6.1/checkstyle-6.1-all.jar \
> com.pany.cs.checks
Loading source files for package com.pany.cs.checks...
Constructing Javadoc information...
$

Notice that both "checkstyle.jar" and "net.sf.eclipsecs-core.jar" must be on the "-docletpath".

The generated "src/com/pany/cs/checks/messages.properties" file looks like this:

# This file was generated by the CS doclet; see http://cs-doclet.unkrig.de/

# Custom check messages, in alphabetical order.

# --------------- com.pany: ColorCheck ---------------
theColorIs = The color is {0}

And voilà! All the messages are where they belong: In the source code.

Integrating with eclipse-cs[edit]

When you integrate your checks with eclipse-cs, then you learn that you have to write two more metadata files:

File "checkstyle-metadata.xml":

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE checkstyle-metadata PUBLIC
"-//eclipse-cs//DTD Check Metadata 1.1//EN"
"http://eclipse-cs.sourceforge.net/dtds/checkstyle-metadata_1_1.dtd">
<checkstyle-metadata>

    <rule-group-metadata name="%Whitespace.group" priority="999">
        <rule-metadata
            internal-name="com.pany.cs.checks.ColorCheck"
            parent="TreeWalker"
            name="%ColorCheck.name"
        >
            <alternative-name internal-name="com.pany.cs.checks.ColorCheck" />
            <description>%ColorCheck.desc</description>

            <property-metadata
                name="color"
                datatype="String"
                default-value="Yellow"
            >
                <description>%ColorCheck.color</description>
            </property-metadata>
            <message-key key="theColorIs" />
        </rule-metadata>
    </rule-group-metadata>
</checkstyle-metadata>

File "checkstyle-metadata.properties":

Whitespace.group = Whitespace
ColorCheck.name = com.pany: ColorCheck
ColorCheck.desc =\
    A completely useless check which merely prints a (localizable) message each \
    time it encounters an annotation.
ColorCheck.color = A completely useless check parameter.

Tedious, isn't it? Well, you can tell cs-doclet to also generate these files from annotations (and doc comments):

File "src/com/pany/cs/checks/MyCheck.java":

// File "src/com/pany/cs/ColorCheck.java".

package com.pany.cs.checks;

import com.puppycrawl.tools.checkstyle.api.Check;
import com.puppycrawl.tools.checkstyle.api.DetailAST;
import com.puppycrawl.tools.checkstyle.api.TokenTypes;

import de.unkrig.csdoclet.StringRuleProperty;
import de.unkrig.csdoclet.Rule;

/**
 * A completely useless check which merely prints a
 * (localizable) message each time it encounters an annotation.
 */
@Rule(
    group      = "%Whitespace.group",
    groupName  = "Whitespace",
    name       = "com.pany: ColorCheck",
    parent     = "TreeWalker"
)
public
class ColorCheck extends Check {

    @Message("The color is {0}")
    private static final String MESSAGE_KEY_THE_COLOR_IS = "theColorIs";

    /**
     * A completely useless check parameter.
     */
    @StringRuleProperty(defaultValue = DEFAULT_COLOR)
    public void
    setColor(String value) { this.color = value; }

    private String color = DEFAULT_COLOR;

    private static final String DEFAULT_COLOR = "Yellow";

    @Override public int[]
    getDefaultTokens() { return new int[] { TokenTypes.ANNOTATION }; }

    @Override public void
    visitToken(DetailAST ast) { this.log(ast, MESSAGE_KEY_THE_COLOR_IS, this.color); }
}
$ javadoc \
> -doclet de.unkrig.doclet.cs.CsDoclet \
> -docletpath "path/to/cs-doclet.jar;bin;path/to/checkstyle-6.1-all.jar;path/to/net.sf.eclipsecs.core-6.1.jar" \
> -checkstyle-metadata.properties-dir src \
> -checkstyle-metadata.xml-dir src \
> -messages.properties-dir src \
> -sourcepath src \
> -classpath ../net.sf.checkstyle-6.1/checkstyle-6.1/checkstyle-6.1-all.jar \
> com.pany.cs.checks
Loading source files for package com.pany.cs.checks...
Constructing Javadoc information...
$

And you'll get:

File "src/com/pany/cs/checks/checkstyle-metadata.properties":

# This file was generated by the CS doclet; see http://cs-doclet.unkrig.de/

# Rule groups:
Whitespace.group = Whitespace

# Custom checks, in alphabetical order.

# --------------- com.pany: ColorCheck ---------------

ColorCheck.name = com.pany: ColorCheck
ColorCheck.desc =\
    A completely useless check which merely prints a (localizable) message each time it encounters an annotation.
ColorCheck.color                                  = A completely useless check parameter.

File "src/com/pany/cs/checks/checkstyle-metadata.xml":

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE checkstyle-metadata PUBLIC
"-//eclipse-cs//DTD Check Metadata 1.1//EN"
"http://eclipse-cs.sourceforge.net/dtds/checkstyle-metadata_1_1.dtd">
<checkstyle-metadata>

    <!-- This file was generated by the CS doclet; see http://cs-doclet.unkrig.de/ -->

    <!-- ColorCheck -->

    <rule-group-metadata name="%Whitespace.group" priority="999">
        <rule-metadata
            internal-name="com.pany.cs.checks.ColorCheck"
            parent="TreeWalker"
            name="%ColorCheck.name"
        >
            <alternative-name internal-name="com.pany.cs.checks.ColorCheck" />
            <description>%ColorCheck.desc</description>

            <property-metadata
                name="color"
                datatype="String"
                default-value="Yellow"
            >
                <description>%ColorCheck.color</description>
            </property-metadata>
            <message-key key="theColorIs" />
        </rule-metadata>
    </rule-group-metadata>
</checkstyle-metadata>

Javadoc-like documentation[edit]

Typically, you will also want to publish human-readable documentation for your checks and filters, which is more or less identical with the text in the eclipse-cs metadata files. This is also possible with the "-d" command line option:

$ javadoc \
> -doclet de.unkrig.doclet.cs.CsDoclet \
> -docletpath "path/to/cs-doclet.jar;bin;path/to/checkstyle-6.1-all.jar;path/to/net.sf.eclipsecs.core-6.1.jar" \
> -d ./csdoc \
> -sourcepath src \
> -classpath ../net.sf.checkstyle-6.1/checkstyle-6.1/checkstyle-6.1-all.jar \
> com.pany.cs.checks
Loading source files for package com.pany.cs.checks...
Constructing Javadoc information...
$

This will generate a Javadoc-like HTML documentation for all checks and filters that are declared in the given Java packages.

And you're done!

Summary[edit]

Before, you had to write one Java file and four more or less redundant metadata files per check; now you merely have to throw in a few annotations and doc comments and generate all four metadata files from the source code

Source code[edit]

The source code for the plug-in is here:

   https://github.com/aunkrig/doclet-cs
   https://github.com/aunkrig/doclet-cs-annotation