View Javadoc

    1   /**
    2    * BSD-style license; for more info see http://pmd.sourceforge.net/license.html
    3    */
    4   package net.sourceforge.pmd;
    5
    6   import java.io.File;
    7   import java.util.Map;
    8   import java.util.concurrent.ConcurrentHashMap;
    9
    10  import net.sourceforge.pmd.lang.LanguageVersion;
    11
    12  /**
    13   * The RuleContext provides access to Rule processing state.  This information
    14   * includes the following global information:
    15   * <ul>
    16   * 	<li>The Report to which Rule Violations are sent.</li>
    17   * 	<li>Named attributes.</li>
    18   * </ul>
    19   * As well as the following source file specific information:
    20   * <ul>
    21   * 	<li>A File for the source file.</li>
    22   * 	<li>A String for the name of the source file.</li>
    23   * 	<li>The Language Version of the source file.</li>
    24   * </ul>
    25   * It is <strong>required</strong> that all source file specific options
    26   * be set between calls to difference source files.  Failure to do so, may
    27   * result in undefined behavior.
    28   */
    29  public class RuleContext {
    30
    31      private Report report = new Report();
    32      private File sourceCodeFile;
    33      private String sourceCodeFilename;
    34      private LanguageVersion languageVersion;
    35      private final Map<String, Object> attributes;
    36
    37      /**
    38       * Default constructor.
    39       */
    40      public RuleContext() {
    41  	attributes = new ConcurrentHashMap<String, Object>();
    42      }
    43
    44      /**
    45       * Constructor which shares attributes and report listeners with the given RuleContext.
    46       */
    47      public RuleContext(RuleContext ruleContext) {
    48  	this.attributes = ruleContext.attributes;
    49  	this.report.addSynchronizedListeners(ruleContext.getReport().getSynchronizedListeners());
    50      }
    51
    52      /**
    53       * Get the Report to which Rule Violations are sent.
    54       * @return The Report.
    55       */
    56      public Report getReport() {
    57  	return report;
    58      }
    59
    60      /**
    61       * Set the Report to which Rule Violations are sent.
    62       * @param report The Report.
    63       */
    64      public void setReport(Report report) {
    65  	this.report = report;
    66      }
    67
    68      /**
    69       * Get the File associated with the current source file.
    70       * @return The File.
    71       */
    72      public File getSourceCodeFile() {
    73  	return sourceCodeFile;
    74      }
    75
    76      /**
    77       * Set the File associated with the current source file.
    78       * While this may be set to <code>null</code>, the exclude/include
    79       * facilities will not work properly without a File.
    80       * @param sourceCodeFile The File.
    81       */
    82      public void setSourceCodeFile(File sourceCodeFile) {
    83  	this.sourceCodeFile = sourceCodeFile;
    84      }
    85
    86      /**
    87       * Get the file name associated with the current source file.
    88       * @return The file name.
    89       */
    90      public String getSourceCodeFilename() {
    91  	return sourceCodeFilename;
    92      }
    93
    94      /**
    95       * Set the file name associated with the current source file.
    96       * @param filename The file name.
    97       */
    98      public void setSourceCodeFilename(String filename) {
    99  	this.sourceCodeFilename = filename;
    100     }
    101
    102     /**
    103      * Get the LanguageVersion associated with the current source file.
    104      * @return The LanguageVersion, <code>null</code> if unknown.
    105      */
    106     public LanguageVersion getLanguageVersion() {
    107 	return this.languageVersion;
    108     }
    109
    110     /**
    111      * Set the LanguageVersion associated with the current source file.
    112      * This may be set to <code>null</code> to indicate the version is
    113      * unknown and should be automatically determined.
    114      *
    115      * @param languageVersion The LanguageVersion.
    116      */
    117     public void setLanguageVersion(LanguageVersion languageVersion) {
    118 	this.languageVersion = languageVersion;
    119     }
    120
    121     /**
    122      * Set an attribute value on the RuleContext, if it does not already exist.
    123      * <p>
    124      * Attributes can be shared between RuleContext instances.  This operation
    125      * is thread-safe.
    126      * <p>
    127      * Attribute values should be modified directly via the reference provided.
    128      * It is not necessary to call <code>setAttribute(String, Object)</code> to
    129      * update an attribute value.  Modifications made to the attribute value
    130      * will automatically be seen by other threads.  Because of this, you must
    131      * ensure the attribute values are themselves thread safe.
    132      *
    133      * @param name The attribute name.
    134      * @param value The attribute value.
    135      * @exception IllegalArgumentException if <code>name</code> or <code> value</code> are <code>null</code>
    136      * @return <code>true</code> if the attribute was set, <code>false</code> otherwise.
    137      */
    138     public boolean setAttribute(String name, Object value) {
    139 	if (name == null) {
    140 	    throw new IllegalArgumentException("Parameter 'name' cannot be null.");
    141 	}
    142 	if (value == null) {
    143 	    throw new IllegalArgumentException("Parameter 'value' cannot be null.");
    144 	}
    145 	synchronized (this.attributes) {
    146 	    if (!this.attributes.containsKey(name)) {
    147 		this.attributes.put(name, value);
    148 		return true;
    149 	    } else {
    150 		return false;
    151 	    }
    152 	}
    153     }
    154
    155     /**
    156      * Get an attribute value on the RuleContext.
    157      * <p>
    158      * Attributes can be shared between RuleContext instances.  This operation
    159      * is thread-safe.
    160      * <p>
    161      * Attribute values should be modified directly via the reference provided.
    162      * It is not necessary to call <code>setAttribute(String, Object)</code> to
    163      * update an attribute value.  Modifications made to the attribute value
    164      * will automatically be seen by other threads.  Because of this, you must
    165      * ensure the attribute values are themselves thread safe.
    166      *
    167      * @param name The attribute name.
    168      * @return The current attribute value, or <code>null</code> if the attribute does not exist.
    169      */
    170     public Object getAttribute(String name) {
    171 	return this.attributes.get(name);
    172     }
    173
    174     /**
    175      * Remove an attribute value on the RuleContext.
    176      * <p>
    177      * Attributes can be shared between RuleContext instances.  This operation
    178      * is thread-safe.
    179      * <p>
    180      * Attribute values should be modified directly via the reference provided.
    181      * It is not necessary to call <code>setAttribute(String, Object)</code> to
    182      * update an attribute value.  Modifications made to the attribute value
    183      * will automatically be seen by other threads.  Because of this, you must
    184      * ensure the attribute values are themselves thread safe.
    185      *
    186      * @param name The attribute name.
    187      * @return The current attribute value, or <code>null</code> if the attribute does not exist.
    188      */
    189     public Object removeAttribute(String name) {
    190 	return this.attributes.remove(name);
    191     }
    192 }