/**
  * Process the var tag
  *
  * @param  integer $commentStart The position in the stack where the comment started
  * @param  integer $commentEnd   The position in the stack where the comment ended
  * @return void
  */
 public function processVar($commentStart, $commentEnd)
 {
     $var = $this->commentParser->getVar();
     if ($var !== null) {
         $errorPos = $commentStart + $var->getLine();
         $index = array_keys($this->commentParser->getTagOrders(), 'var');
         if (count($index) > 1) {
             $this->currentFile->addEvent('ONE_VERSION_TAG_VARIABLE_COMMENT', array(), $errorPos);
             return;
         }
         if ($index[0] !== 1) {
             $this->currentFile->addEvent('ONE_VERSION_TAG_VARIABLE_COMMENT', array(), $errorPos);
         }
         $content = $var->getContent();
         if (empty($content) === true) {
             $this->currentFile->addEvent('TYPE_MISSING_VAR_TAG_VARIABLE_COMMENT', array(), $errorPos);
             return;
         } else {
             $suggestedType = PHP_CodeSniffer::suggestType($content);
             if ($content !== $suggestedType) {
                 $this->currentFile->addEvent('EXPECTED_FOUND_VAR_TAG_VARIABLE_COMMENT', array('suggestedyype' => $suggestedType, 'content' => $content), $errorPos);
             }
         }
         $spacing = substr_count($var->getWhitespaceBeforeContent(), ' ');
         if ($spacing !== $this->space) {
             $this->currentFile->addEvent('EXPECTED_SPACES_FOUND_VAR_TAG_VARIABLE_COMMENT', array('space' => $this->space, 'spacing' => $spacing), $errorPos);
         }
     } else {
         $this->currentFile->addEvent('MISSING_VAR_TAG_VARIABLE_COMMENT', array(), $commentEnd);
     }
 }
 /**
  * Process the var tag
  *
  * @param  integer $commentStart The position in the stack where the comment started
  * @param  integer $commentEnd   The position in the stack where the comment ended
  * @return void
  */
 public function processVar($commentStart, $commentEnd)
 {
     $var = $this->commentParser->getVar();
     if ($var !== null) {
         $errorPos = $commentStart + $var->getLine();
         $index = array_keys($this->commentParser->getTagOrders(), 'var');
         if (count($index) > 1) {
             $this->currentFile->addError("Le tag @version doit être présent une seule fois dans le commentaire de variable", $errorPos, 'OneVersionTagVariableComment');
             return;
         }
         if ($index[0] !== 1) {
             $this->currentFile->addError("Le tag @version doit être présent une seule fois dans le commentaire de variable", $errorPos, 'OneVersionTagVariableComment');
         }
         $content = $var->getContent();
         if (empty($content) === true) {
             $this->currentFile->addError("Le tag @type doit être suivi du type de variable", $errorPos, 'TypeMissingVarTagVariableComment');
             return;
         } else {
             $suggestedType = PHP_CodeSniffer::suggestType($content);
             if ($content !== $suggestedType) {
                 $this->currentFile->addError('Le tag @type devrait être suivi de "' . $suggestedType . '", "' . $content . '" trouvé', $errorPos, 'ExpectedFoundVarTagVariableComment');
             }
         }
         $spacing = substr_count($var->getWhitespaceBeforeContent(), ' ');
         if ($spacing !== $this->space) {
             $this->currentFile->addError($this->space . ' espace(s) attendu(s), ' . $spacing . ' trouvé(s)', $errorPos, 'ExpectedSpacesFoundVarTagVariableComment');
         }
     } else {
         $this->currentFile->addError('Le tag @var est manquant dans le commentaire de variable', $commentEnd, 'MissingVarTagVariableComment');
     }
 }
 /**
  * Process the var tag.
  *
  * @param int $commentStart The position in the stack where the comment started.
  * @param int $commentEnd   The position in the stack where the comment ended.
  *
  * @return void
  */
 protected function processVar($commentStart, $commentEnd)
 {
     $var = $this->commentParser->getVar();
     if ($var !== null) {
         $errorPos = $commentStart + $var->getLine();
         $index = array_keys($this->commentParser->getTagOrders(), 'var');
         if (count($index) > 1) {
             $error = 'Only 1 @var tag is allowed in variable comment';
             $this->currentFile->addError($error, $errorPos, 'DuplicateVar');
             return;
         }
         if ($index[0] !== 1) {
             $error = 'The @var tag must be the first tag in a variable comment';
             $this->currentFile->addError($error, $errorPos, 'VarOrder');
         }
         $content = $var->getContent();
         if (empty($content) === true) {
             $error = 'Var type missing for @var tag in variable comment';
             $this->currentFile->addError($error, $errorPos, 'MissingVarType');
             return;
         } else {
             $suggestedType = PHP_CodeSniffer::suggestType($content);
             if ($suggestedType !== $content) {
                 // hotfix - somehow they do not like "int" and "bool".
                 switch ($content) {
                     case 'int':
                         $suggestedType = 'int';
                         break;
                     case 'bool':
                         $suggestedType = 'bool';
                         break;
                     default:
                 }
             }
             if ($content !== $suggestedType) {
                 $error = 'Expected "%s"; found "%s" for @var tag in variable comment';
                 $data = array($suggestedType, $content);
                 $this->currentFile->addError($error, $errorPos, 'IncorrectVarType', $data);
             }
         }
         $spacing = substr_count($var->getWhitespaceBeforeContent(), ' ');
         if ($spacing !== 1) {
             $error = '@var tag indented incorrectly; expected 1 space but found %s';
             $data = array($spacing);
             $this->currentFile->addError($error, $errorPos, 'VarIndent', $data);
         }
     } else {
         $error = 'Missing @var tag in variable comment';
         $this->currentFile->addError($error, $commentEnd, 'MissingVar');
     }
     //end if
 }
 /**
  * Process the since tag.
  *
  * @param int $commentStart The position in the stack where the comment started.
  * @param int $commentEnd   The position in the stack where the comment ended.
  *
  * @return void
  */
 protected function processSince($commentStart, $commentEnd)
 {
     $since = $this->commentParser->getSince();
     if ($since !== null) {
         $errorPos = $commentStart + $since->getLine();
         $foundTags = $this->commentParser->getTagOrders();
         $index = array_keys($foundTags, 'since');
         $var = array_keys($foundTags, 'var');
         if (count($index) > 1) {
             $error = 'Only 1 @since tag is allowed in variable comment';
             $this->currentFile->addError($error, $errorPos);
             return;
         }
         // Only check order if there is one var tag in variable comment.
         if (count($var) === 1 && $index[0] !== 2) {
             $error = 'The order of @since tag is wrong in variable comment';
             $this->currentFile->addError($error, $errorPos);
         }
         $content = $since->getContent();
         if (empty($content) === true) {
             $error = 'Version number missing for @since tag in variable comment';
             $this->currentFile->addError($error, $errorPos);
             return;
         } else {
             if ($content !== '%release_version%') {
                 if (preg_match('/^([0-9]+)\\.([0-9]+)\\.([0-9]+)/', $content) === 0) {
                     $error = 'Expected version number to be in the form x.x.x in @since tag';
                     $this->currentFile->addError($error, $errorPos);
                 }
             }
         }
         $spacing = substr_count($since->getWhitespaceBeforeContent(), ' ');
         if ($spacing !== 1) {
             $error = '@since tag indented incorrectly. ';
             $error .= "Expected 1 space but found {$spacing}.";
             $this->currentFile->addError($error, $errorPos);
         }
     } else {
         $error = 'Missing @since tag in variable comment';
         $this->currentFile->addError($error, $commentEnd);
     }
     //end if
 }
Пример #5
0
 /**
  * Processes each required or optional tag.
  *
  * @param int $commentStart Position in the stack where the comment started.
  * @param int $commentEnd   Position in the stack where the comment ended.
  *
  * @return void
  */
 protected function processTags($commentStart, $commentEnd)
 {
     $docBlock = get_class($this) === 'PEAR_Sniffs_Commenting_FileCommentSniff' ? 'file' : 'class';
     $foundTags = $this->commentParser->getTagOrders();
     $orderIndex = 0;
     $indentation = array();
     $longestTag = 0;
     $errorPos = 0;
     foreach ($this->tags as $tag => $info) {
         // Required tag missing.
         if ($info['required'] === true && in_array($tag, $foundTags) === false) {
             $error = "Missing @{$tag} tag in {$docBlock} comment";
             $this->currentFile->addError($error, $commentEnd);
             continue;
         }
         // Get the line number for current tag.
         $tagName = ucfirst($tag);
         if ($info['allow_multiple'] === true) {
             $tagName .= 's';
         }
         $getMethod = 'get' . $tagName;
         $tagElement = $this->commentParser->{$getMethod}();
         if (is_null($tagElement) === true || empty($tagElement) === true) {
             continue;
         }
         $errorPos = $commentStart;
         if (is_array($tagElement) === false) {
             $errorPos = $commentStart + $tagElement->getLine();
         }
         // Get the tag order.
         $foundIndexes = array_keys($foundTags, $tag);
         if (count($foundIndexes) > 1) {
             // Multiple occurance not allowed.
             if ($info['allow_multiple'] === false) {
                 $error = "Only 1 @{$tag} tag is allowed in a {$docBlock} comment";
                 $this->currentFile->addError($error, $errorPos);
             } else {
                 // Make sure same tags are grouped together.
                 $i = 0;
                 $count = $foundIndexes[0];
                 foreach ($foundIndexes as $index) {
                     if ($index !== $count) {
                         $errorPosIndex = $errorPos + $tagElement[$i]->getLine();
                         $error = "@{$tag} tags must be grouped together";
                         $this->currentFile->addError($error, $errorPosIndex);
                     }
                     $i++;
                     $count++;
                 }
             }
         }
         //end if
         // Check tag order.
         if ($foundIndexes[0] > $orderIndex) {
             $orderIndex = $foundIndexes[0];
         } else {
             if (is_array($tagElement) === true && empty($tagElement) === false) {
                 $errorPos += $tagElement[0]->getLine();
             }
             $orderText = $info['order_text'];
             $error = "The @{$tag} tag is in the wrong order; the tag {$orderText}";
             $this->currentFile->addError($error, $errorPos);
         }
         // Store the indentation for checking.
         $len = strlen($tag);
         if ($len > $longestTag) {
             $longestTag = $len;
         }
         if (is_array($tagElement) === true) {
             foreach ($tagElement as $key => $element) {
                 $indentation[] = array('tag' => $tag, 'space' => $this->getIndentation($tag, $element), 'line' => $element->getLine());
             }
         } else {
             $indentation[] = array('tag' => $tag, 'space' => $this->getIndentation($tag, $tagElement));
         }
         $method = 'process' . $tagName;
         if (method_exists($this, $method) === true) {
             // Process each tag if a method is defined.
             call_user_func(array($this, $method), $errorPos);
         } else {
             if (is_array($tagElement) === true) {
                 foreach ($tagElement as $key => $element) {
                     $element->process($this->currentFile, $commentStart, $docBlock);
                 }
             } else {
                 $tagElement->process($this->currentFile, $commentStart, $docBlock);
             }
         }
     }
     //end foreach
     foreach ($indentation as $indentInfo) {
         if ($indentInfo['space'] !== 0 && $indentInfo['space'] !== $longestTag + 1) {
             $expected = $longestTag - strlen($indentInfo['tag']) + 1;
             $space = $indentInfo['space'] - strlen($indentInfo['tag']);
             $error = "@{$indentInfo['tag']} tag comment indented incorrectly. ";
             $error .= "Expected {$expected} spaces but found {$space}.";
             $getTagMethod = 'get' . ucfirst($indentInfo['tag']);
             if ($this->tags[$indentInfo['tag']]['allow_multiple'] === true) {
                 $line = $indentInfo['line'];
             } else {
                 $tagElem = $this->commentParser->{$getTagMethod}();
                 $line = $tagElem->getLine();
             }
             $this->currentFile->addError($error, $commentStart + $line);
         }
     }
 }
Пример #6
0
 /**
  * Processes each required or optional tag.
  *
  * @param int $commentStart The position in the stack where the comment started.
  * @param int $commentEnd   The position in the stack where the comment ended.
  *
  * @return void
  */
 protected function processTags($commentStart, $commentEnd)
 {
     // Required tags in correct order.
     $tags = array('version' => 'precedes @package', 'package' => 'follows @version', 'subpackage' => 'follows @package', 'author' => 'follows @subpackage', 'copyright' => 'follows @author', 'license' => 'follows @copyright');
     $foundTags = $this->commentParser->getTagOrders();
     $errorPos = 0;
     $orderIndex = 0;
     $longestTag = 0;
     $indentation = array();
     foreach ($tags as $tag => $orderText) {
         // Required tag missing.
         if (in_array($tag, $foundTags) === false) {
             $error = "Missing @{$tag} tag in file comment";
             $this->currentFile->addError($error, $commentEnd);
             continue;
         }
         // Get the line number for current tag.
         $tagName = ucfirst($tag);
         if ($tagName === 'Author' || $tagName === 'Copyright') {
             // These tags are different because they return an array.
             $tagName .= 's';
         }
         // Work out the line number for this tag.
         $getMethod = 'get' . $tagName;
         $tagElement = $this->commentParser->{$getMethod}();
         if (is_null($tagElement) === true || empty($tagElement) === true) {
             continue;
         } else {
             if (is_array($tagElement) === true && empty($tagElement) === false) {
                 $tagElement = $tagElement[0];
             }
         }
         $errorPos = $commentStart + $tagElement->getLine();
         // Make sure there is no duplicate tag.
         $foundIndexes = array_keys($foundTags, $tag);
         if (count($foundIndexes) > 1) {
             $error = "Only 1 @{$tag} tag is allowed in file comment";
             $this->currentFile->addError($error, $errorPos);
         }
         // Check tag order.
         if ($foundIndexes[0] > $orderIndex) {
             $orderIndex = $foundIndexes[0];
         } else {
             $error = "The @{$tag} tag is in the wrong order; the tag {$orderText}";
             $this->currentFile->addError($error, $errorPos);
         }
         // Store the indentation of each tag.
         $len = strlen($tag);
         if ($len > $longestTag) {
             $longestTag = $len;
         }
         $indentation[] = array('tag' => $tag, 'errorPos' => $errorPos, 'space' => $this->getIndentation($tag, $tagElement));
         $method = 'process' . $tagName;
         if (method_exists($this, $method) === true) {
             // Process each tag if a method is defined.
             call_user_func(array($this, $method), $errorPos);
         } else {
             $tagElement->process($this->currentFile, $commentStart, 'file');
         }
     }
     //end foreach
     // Check tag indentation.
     foreach ($indentation as $indentInfo) {
         $tagName = ucfirst($indentInfo['tag']);
         if ($tagName === 'Author') {
             $tagName .= 's';
         }
         if ($indentInfo['space'] !== 0 && $indentInfo['space'] !== $longestTag + 1) {
             $expected = $longestTag - strlen($indentInfo['tag']) + 1;
             $space = $indentInfo['space'] - strlen($indentInfo['tag']);
             $error = "@{$indentInfo['tag']} tag comment indented incorrectly. ";
             $error .= "Expected {$expected} spaces but found {$space}.";
             $this->currentFile->addError($error, $indentInfo['errorPos']);
         }
     }
 }
Пример #7
0
 /**
  * Processes each required or optional tag
  *
  * @param  integer $commentStart The position in the stack where the comment started
  * @param  integer $commentEnd   The position in the stack where the comment ended
  * @return void
  */
 protected function _processTags($commentStart, $commentEnd)
 {
     // Tags in correct order and related info
     $tags = array('category' => array('required' => true, 'allow_multiple' => false, 'order_text' => 'precedes @package'), 'package' => array('required' => true, 'allow_multiple' => false, 'order_text' => 'follows @category'), 'subpackage' => array('required' => false, 'allow_multiple' => false, 'order_text' => 'follows @package'), 'copyright' => array('required' => true, 'allow_multiple' => false, 'order_text' => 'follows @subpackage (if used) or @package'), 'license' => array('required' => true, 'allow_multiple' => false, 'order_text' => 'follows @copyright'), 'version' => array('required' => true, 'allow_multiple' => false, 'order_text' => 'follows @license'), 'deprecated' => array('required' => false, 'allow_multiple' => false, 'order_text' => 'follows @version'));
     $foundTags = $this->_commentParser->getTagOrders();
     $orderIndex = 0;
     $indentation = array();
     $longestTag = 0;
     $errorPos = 0;
     foreach ($foundTags as $tag => $info) {
         if (array_key_exists($info, $tags) === false and $info !== 'comment') {
             $error = "Tag @{$info} is not allowed";
             $this->_currentFile->addError($error, $commentStart + $tag + 13, 'TagNotAllowedFileComment');
         }
     }
     foreach ($tags as $tag => $info) {
         // Required tag missing
         if ($info['required'] === true and in_array($tag, $foundTags) === false) {
             $error = "Missing @{$tag} tag in file comment";
             $this->_currentFile->addError($error, $commentEnd, 'TagRequiredFileComment');
             continue;
         }
         // Get the line number for current tag
         $tagName = ucfirst($tag);
         if ($info['allow_multiple'] === true or $tag === 'copyright') {
             $tagName .= 's';
         }
         $getMethod = 'get' . $tagName;
         $tagElement = $this->_commentParser->{$getMethod}();
         if (is_null($tagElement) === true or empty($tagElement) === true) {
             continue;
         }
         $errorPos = $commentStart;
         if (is_array($tagElement) === false) {
             $errorPos = $commentStart + $tagElement->getLine();
         }
         // Get the tag order
         $foundIndexes = array_keys($foundTags, $tag);
         if (count($foundIndexes) > 1) {
             // Multiple occurance not allowed
             if ($info['allow_multiple'] === false) {
                 $error = "Only 1 @{$tag} tag is allowed in a file comment";
                 $this->_currentFile->addError($error, $errorPos, 'NoDuplicateTagFileComment');
             } else {
                 // Make sure same tags are grouped together
                 $i = 0;
                 $count = $foundIndexes[0];
                 foreach ($foundIndexes as $index) {
                     if ($index !== $count) {
                         $errorPosIndex = $errorPos + $tagElement[$i]->getLine();
                         $error = "@{$tag} tags must be grouped together";
                         $this->_currentFile->addError($error, $errorPosIndex, 'TagsMustBeGroupedFileComment');
                     }
                     $i++;
                     $count++;
                 }
             }
         }
         // Check tag order
         if ($foundIndexes[0] > $orderIndex) {
             $orderIndex = $foundIndexes[0];
         } else {
             if (is_array($tagElement) === true and empty($tagElement) === false) {
                 $errorPos += $tagElement[0]->getLine();
             }
             $orderText = $info['order_text'];
             $error = "The @{$tag} tag is in the wrong order; the tag {$orderText}";
             $this->_currentFile->addError($error, $errorPos, 'TagsOrderFileComment');
         }
         // Store the indentation for checking
         $len = strlen($tag);
         if ($len > $longestTag) {
             $longestTag = $len;
         }
         if (is_array($tagElement) === true) {
             foreach ($tagElement as $key => $element) {
                 $indentation[] = array('tag' => $tag, 'space' => $this->_getIndentation($tag, $element), 'line' => $element->getLine());
             }
         } else {
             $indentation[] = array('tag' => $tag, 'space' => $this->_getIndentation($tag, $tagElement));
         }
         $method = '_process' . $tagName;
         if (method_exists($this, $method) === true) {
             // Process each tag if a method is defined
             call_user_func(array($this, $method), $errorPos);
         } else {
             if (is_array($tagElement) === true) {
                 foreach ($tagElement as $key => $element) {
                     $element->process($this->_currentFile, $commentStart, 'file');
                 }
             } else {
                 $tagElement->process($this->_currentFile, $commentStart, 'file');
             }
         }
     }
     foreach ($indentation as $indentInfo) {
         if ($indentInfo['space'] !== 0 and $indentInfo['space'] !== $longestTag + 1) {
             $expected = $longestTag - strlen($indentInfo['tag']) + 1;
             $space = $indentInfo['space'] - strlen($indentInfo['tag']);
             $error = "@{$indentInfo['tag']} tag comment indented incorrectly. ";
             $error .= "Expected {$expected} spaces but found {$space}.";
             $getTagMethod = 'get' . ucfirst($indentInfo['tag']);
             if ($tags[$indentInfo['tag']]['allow_multiple'] === true or $indentInfo['tag'] === 'copyright') {
                 $line = $indentInfo['line'];
             } else {
                 $tagElem = $this->_commentParser->{$getTagMethod}();
                 $line = $tagElem->getLine();
             }
             $this->_currentFile->addError($error, $commentStart + $line, 'TagIndentationFileComment');
         }
     }
 }
Пример #8
0
 /**
  * Processes each required or optional tag.
  *
  * @param int $commentStart Position in the stack where the comment started.
  * @param int $commentEnd   Position in the stack where the comment ended.
  *
  * @return void
  */
 protected function processTags($commentStart, $commentEnd)
 {
     $docBlock = get_class($this) === 'Joomla_Sniffs_Commenting_FileCommentSniff' ? 'file' : 'class';
     $foundTags = $this->commentParser->getTagOrders();
     $orderIndex = 0;
     $indentation = array();
     $longestTag = 0;
     $errorPos = 0;
     foreach ($this->tags as $tag => $info) {
         // Required tag missing.
         if ($info['required'] === true && in_array($tag, $foundTags) === false) {
             // We don't use package tags in namespaced code or the bootstrap file
             if ($tag == 'package') {
                 // this should return 0 if there is no namespaced tokens
                 $namespaced = $this->currentFile->findNext(T_NAMESPACE, 0);
                 if ($namespaced !== 0 || strpos($this->currentFile->getFilename(), '/libraries/bootstrap.php')) {
                     continue;
                 }
             }
             $error = 'Missing @%s tag in %s comment';
             $data = array($tag, $docBlock);
             $this->currentFile->addError($error, $commentEnd, 'MissingTag', $data);
             continue;
         }
         // Get the line number for current tag.
         $tagName = ucfirst($tag);
         if ($info['allow_multiple'] === true) {
             $tagName .= 's';
         }
         $getMethod = 'get' . $tagName;
         $tagElement = $this->commentParser->{$getMethod}();
         if (is_null($tagElement) === true || empty($tagElement) === true) {
             continue;
         }
         $errorPos = $commentStart;
         if (is_array($tagElement) === false) {
             $errorPos = $commentStart + $tagElement->getLine();
         }
         // Get the tag order.
         $foundIndexes = array_keys($foundTags, $tag);
         if (count($foundIndexes) > 1) {
             // Multiple occurance not allowed.
             if ($info['allow_multiple'] === false) {
                 $error = 'Only 1 @%s tag is allowed in a %s comment';
                 $data = array($tag, $docBlock);
                 $this->currentFile->addError($error, $errorPos, 'DuplicateTag', $data);
             } else {
                 // Make sure same tags are grouped together.
                 $i = 0;
                 $count = $foundIndexes[0];
                 foreach ($foundIndexes as $index) {
                     if ($index !== $count) {
                         $errorPosIndex = $errorPos + $tagElement[$i]->getLine();
                         $error = '@%s tags must be grouped together';
                         $data = array($tag);
                         $this->currentFile->addError($error, $errorPosIndex, 'TagsNotGrouped', $data);
                     }
                     $i++;
                     $count++;
                 }
             }
         }
         //end if
         // Check tag order.
         if ($foundIndexes[0] > $orderIndex) {
             $orderIndex = $foundIndexes[0];
         } else {
             if (is_array($tagElement) === true && empty($tagElement) === false) {
                 $errorPos += $tagElement[0]->getLine();
             }
             $error = 'The @%s tag is in the wrong order; the tag %s';
             $data = array($tag, $info['order_text']);
             $this->currentFile->addError($error, $errorPos, 'WrongTagOrder', $data);
         }
         // Store the indentation for checking.
         $len = strlen($tag);
         if ($len > $longestTag) {
             $longestTag = $len;
         }
         if (is_array($tagElement) === true) {
             foreach ($tagElement as $key => $element) {
                 $indentation[] = array('tag' => $tag, 'space' => $this->getIndentation($tag, $element), 'line' => $element->getLine());
             }
         } else {
             $indentation[] = array('tag' => $tag, 'space' => $this->getIndentation($tag, $tagElement));
         }
         $method = 'process' . $tagName;
         if (method_exists($this, $method) === true) {
             // Process each tag if a method is defined.
             call_user_func(array($this, $method), $errorPos);
         } else {
             if (is_array($tagElement) === true) {
                 foreach ($tagElement as $key => $element) {
                     $element->process($this->currentFile, $commentStart, $docBlock);
                 }
             } else {
                 $tagElement->process($this->currentFile, $commentStart, $docBlock);
             }
         }
     }
     //end foreach
     foreach ($indentation as $indentInfo) {
         if ($indentInfo['space'] !== 0 && $indentInfo['space'] !== $longestTag + 2) {
             $expected = $longestTag - strlen($indentInfo['tag']) + 2;
             $space = $indentInfo['space'] - strlen($indentInfo['tag']);
             $error = '@%s tag comment indented incorrectly; expected %s spaces but found %s';
             $data = array($indentInfo['tag'], $expected, $space);
             $getTagMethod = 'get' . ucfirst($indentInfo['tag']);
             if ($this->tags[$indentInfo['tag']]['allow_multiple'] === true) {
                 $line = $indentInfo['line'];
             } else {
                 $tagElem = $this->commentParser->{$getTagMethod}();
                 $line = $tagElem->getLine();
             }
             $this->currentFile->addError($error, $commentStart + $line, 'TagIndent', $data);
         }
     }
 }
Пример #9
0
	/**
	 * Processes each required or optional tag.
	 *
	 * @param int $commentStart The position in the stack where the comment started.
	 * @param int $commentEnd   The position in the stack where the comment ended.
	 *
	 * @return void
	 */
	protected function processTags($commentStart, $commentEnd)
	{
		// Tags in correct order and related info.
		$tags = array(
			'category'   => array(
					'required'       => true,
					'allow_multiple' => false,
					'order_text'     => 'precedes @package',
					),
			'package'    => array(
					'required'       => true,
					'allow_multiple' => false,
					'order_text'     => 'follows @category',
					),
			'subpackage' => array(
					'required'       => false,
					'allow_multiple' => false,
					'order_text'     => 'follows @package',
					),
			'author'     => array(
					'required'       => false,
					'allow_multiple' => true,
					'order_text'     => 'follows @subpackage (if used) or @package',
					),
			'copyright'  => array(
					'required'       => false,
					'allow_multiple' => true,
					'order_text'     => 'follows @author',
					),
			'license'    => array(
					'required'       => false,
					'allow_multiple' => false,
					'order_text'     => 'follows @copyright (if used) or @author',
					),
			'version'    => array(
					'required'       => false,
					'allow_multiple' => false,
					'order_text'     => 'follows @licence',
					),
			'link'       => array(
					'required'       => false,
					'allow_multiple' => true,
					'order_text'     => 'follows @version',
					),
			'see'        => array(
					'required'       => false,
					'allow_multiple' => true,
					'order_text'     => 'follows @link',
					),
			'since'      => array(
					'required'       => false,
					'allow_multiple' => false,
					'order_text'     => 'follows @see (if used) or @link',
					),
			'deprecated' => array(
					'required'       => false,
					'allow_multiple' => false,
					'order_text'     => 'follows @since (if used) or @see (if used) or @link',
					),
		);

		$docBlock    = (get_class($this) === 'PEAR_Sniffs_Commenting_FileCommentSniff') ? 'file' : 'class';
		$foundTags   = $this->commentParser->getTagOrders();
		$orderIndex  = 0;
		$indentation = array();
		$longestTag  = 0;
		$errorPos    = 0;

		foreach ($tags as $tag => $info) {

			// Required tag missing.
			if ($info['required'] === true && in_array($tag, $foundTags) === false) {
				$error = "Missing @$tag tag in $docBlock comment";
				$this->currentFile->addError($error, $commentEnd);
				continue;
			}

			// Get the line number for current tag.
			$tagName = ucfirst($tag);
			if ($info['allow_multiple'] === true) {
				$tagName .= 's';
			}

			$getMethod  = 'get'.$tagName;
			$tagElement = $this->commentParser->$getMethod();
			if (is_null($tagElement) === true || empty($tagElement) === true) {
				continue;
			}

			$errorPos = $commentStart;
			if (is_array($tagElement) === false) {
				$errorPos = ($commentStart + $tagElement->getLine());
			}

			// Get the tag order.
			$foundIndexes = array_keys($foundTags, $tag);

			if (count($foundIndexes) > 1) {
				// Multiple occurance not allowed.
				if ($info['allow_multiple'] === false) {
					$error = "Only 1 @$tag tag is allowed in a $docBlock comment";
					$this->currentFile->addError($error, $errorPos);
				} else {
					// Make sure same tags are grouped together.
					$i     = 0;
					$count = $foundIndexes[0];
					foreach ($foundIndexes as $index) {
						if ($index !== $count) {
							$errorPosIndex = ($errorPos + $tagElement[$i]->getLine());
							$error         = "@$tag tags must be grouped together";
							$this->currentFile->addError($error, $errorPosIndex);
						}

						$i++;
						$count++;
					}
				}
			}//end if

			// Check tag order.
			if ($foundIndexes[0] > $orderIndex) {
				$orderIndex = $foundIndexes[0];
			} else {
				if (is_array($tagElement) === true && empty($tagElement) === false) {
					$errorPos += $tagElement[0]->getLine();
				}

				$orderText = $info['order_text'];
				$error     = "The @$tag tag is in the wrong order; the tag $orderText";
				$this->currentFile->addError($error, $errorPos);
			}

			// Store the indentation for checking.
			$len = strlen($tag);
			if ($len > $longestTag) {
				$longestTag = $len;
			}

			if (is_array($tagElement) === true) {
				foreach ($tagElement as $key => $element) {
					$indentation[] = array(
										'tag'   => $tag,
										'space' => $this->getIndentation($tag, $element),
										'line'  => $element->getLine(),
					);
				}
			} else {
				$indentation[] = array(
									'tag'   => $tag,
									'space' => $this->getIndentation($tag, $tagElement),
				);
			}

			$method = 'process'.$tagName;
			if (method_exists($this, $method) === true) {
				// Process each tag if a method is defined.
				call_user_func(array($this, $method), $errorPos);
			} else {
				if (is_array($tagElement) === true) {
					foreach ($tagElement as $key => $element) {
						$element->process($this->currentFile, $commentStart, $docBlock);
					}
				} else {
					$tagElement->process($this->currentFile, $commentStart, $docBlock);
				}
			}
		}//end foreach



	}//end processTags()
Пример #10
0
 /**
  * Processes each required or optional tag.
  *
  * @param int $commentStart Position in the stack where the comment started.
  * @param int $commentEnd   Position in the stack where the comment ended.
  *
  * @return void
  */
 protected function processTags($commentStart, $commentEnd)
 {
     $foundTags = $this->commentParser->getTagOrders();
     $orderIndex = 0;
     $indentation = array();
     $longestTag = 0;
     $errorPos = 0;
     $this->checkGotchas($commentStart, $commentEnd);
     $diff = array_diff($foundTags, array_keys($this->tags), array('comment'));
     if (count($diff) > 0 && $this->reqCodeForbidden) {
         foreach ($diff as $tag) {
             $error = "Forbidden @{$tag} tag in " . $this->docBlock . " comment";
             $this->currentFile->addError($this->getReqPrefix($this->reqCodeForbidden) . $error, $commentEnd);
         }
     }
     foreach ($this->tags as $tag => $info) {
         // Required tag missing.
         if ($this->getTagRule($info, 'required') && in_array($tag, $foundTags) === false && $this->reqCodeRequire) {
             $error = "Missing @{$tag} tag in " . $this->docBlock . " comment";
             $this->currentFile->addError($this->getReqPrefix($this->reqCodeRequire) . $error, $commentEnd);
             continue;
         }
         // Get the line number for current tag.
         $tagName = ucfirst($tag);
         if ($info['allow_multiple'] === true) {
             $tagName .= 's';
         }
         $getMethod = 'get' . $tagName;
         if (!method_exists($this->commentParser, $getMethod) && $info['allow_multiple'] !== true) {
             $getMethod .= 's';
         }
         if (!method_exists($this->commentParser, $getMethod)) {
             continue;
         }
         $tagElement = $this->commentParser->{$getMethod}();
         if (is_null($tagElement) === true || empty($tagElement) === true) {
             continue;
         }
         $tagElements = is_array($tagElement) ? $tagElement : array($tagElement);
         $errorPos = $commentStart;
         if (is_array($tagElement) === false) {
             $errorPos = $commentStart + $tagElement->getLine();
         }
         // Get the tag order.
         $foundIndexes = array_keys($foundTags, $tag);
         if (count($foundIndexes) > 1) {
             // Multiple occurance not allowed.
             if (!$this->getTagRule($info, 'allow_multiple')) {
                 if ($this->reqCodeOnlyOne) {
                     $error = "Only 1 @{$tag} tag is allowed in a " . $this->docBlock . " comment";
                     $this->currentFile->addError($this->getReqPrefix($this->reqCodeOnlyOne) . $error, $errorPos);
                 }
             } else {
                 // Make sure same tags are grouped together.
                 $i = 0;
                 $count = $foundIndexes[0];
                 foreach ($foundIndexes as $index) {
                     if ($index !== $count) {
                         $errorPosIndex = $errorPos + $tagElement[$i]->getLine();
                         $error = "@{$tag} tags must be grouped together";
                         $this->currentFile->addError($this->getReqPrefix($this->reqCodeUngroup) . $error, $errorPosIndex);
                     }
                     $i++;
                     $count++;
                 }
             }
         }
         //end if
         // Check tag order.
         if ($foundIndexes[0] > $orderIndex) {
             $orderIndex = $foundIndexes[0];
         } else {
             if (is_array($tagElement) === true && empty($tagElement) === false) {
                 $errorPos += $tagElement[0]->getLine();
             }
             $orderText = $info['order_text'];
             $error = "The @{$tag} tag is in the wrong order; the tag {$orderText}";
             $this->currentFile->addError($this->getReqPrefix($this->reqCodeWrongOrder) . $error, $errorPos);
         }
         // Store the indentation for checking.
         $len = strlen($tag);
         if ($len > $longestTag) {
             $longestTag = $len;
         }
         foreach ($tagElements as $key => $element) {
             $indentation[] = array('tag' => $tag, 'space' => $this->getIndentation($tag, $element), 'line' => $element->getLine(), 'value' => $this->getTagValue($element));
         }
         $method1 = 'process' . ucfirst($tag);
         $method2 = 'process' . ucfirst($tag) . 's';
         if (method_exists($this, $method1) === true) {
             // Process each tag if a method is defined.
             call_user_func(array($this, $method1), $errorPos, $commentEnd, $tagElements);
         } elseif (method_exists($this, $method2) === true) {
             // Process each tag if a method is defined.
             call_user_func(array($this, $method2), $errorPos, $commentEnd, $tagElements);
         } else {
             foreach ($tagElements as $key => $element) {
                 if (method_exists($element, 'process')) {
                     $element->process($this->currentFile, $commentStart, $this->docBlock);
                 }
             }
         }
     }
     //end foreach
     foreach ($indentation as $indentInfo) {
         $this->checkForDefaultValue($indentInfo['value'], $indentInfo['tag'], $commentStart + $indentInfo['line']);
         if ($indentInfo['space'] !== 0 && $indentInfo['space'] !== $longestTag + 1) {
             $expected = $longestTag - strlen($indentInfo['tag']) + 1;
             $space = $indentInfo['space'] - strlen($indentInfo['tag']);
             $error = "@{$indentInfo['tag']} tag comment indented incorrectly. ";
             $error .= "Expected {$expected} spaces but found {$space}.";
             $getTagMethod = isset($this->reqCodesWrongFormat[$indentInfo['tag']]) ? $this->reqCodesWrongFormat[$indentInfo['tag']]['function'] : false;
             $line = $indentInfo['line'];
             if ($this->tags[$indentInfo['tag']]['allow_multiple'] === true) {
                 $line = $indentInfo['line'];
             } elseif ($getTagMethod && method_exists($this->commentParser, $getTagMethod)) {
                 $tagElem = $this->commentParser->{$getTagMethod}();
                 if ('array' === $this->reqCodesWrongFormat[$indentInfo['tag']]['type']) {
                     $tagElem = array_pop($tagElem);
                 }
                 $line = $tagElem->getLine();
             }
             $this->currentFile->addError($this->getReqPrefix($this->reqCodeIndent) . $error, $commentStart + $line);
         }
     }
 }
Пример #11
0
 /**
  * Processes this test, when one of its tokens is encountered.
  *
  * @param PHP_CodeSniffer_File $phpcsFile The file being scanned.
  * @param int                  $stackPtr  The position of the current token
  *                                        in the stack passed in $tokens.
  *
  * @return void
  */
 public function process(PHP_CodeSniffer_File $phpcsFile, $stackPtr)
 {
     $this->currentFile = $phpcsFile;
     // We are only interested if this is the first open tag.
     if ($stackPtr !== 0) {
         if ($phpcsFile->findPrevious(T_OPEN_TAG, $stackPtr - 1) !== false) {
             return;
         }
     }
     $tokens = $phpcsFile->getTokens();
     // Find the next non whitespace token.
     $commentStart = $phpcsFile->findNext(T_WHITESPACE, $stackPtr + 1, null, true);
     // Ignore vim header.
     if ($tokens[$commentStart]['code'] === T_COMMENT) {
         if (strstr($tokens[$commentStart]['content'], 'vim:') !== false) {
             $commentStart = $phpcsFile->findNext(T_WHITESPACE, $commentStart + 1, null, true);
         }
     }
     if ($tokens[$commentStart]['code'] === T_CLOSE_TAG) {
         // We are only interested if this is the first open tag.
         return;
     } else {
         if ($tokens[$commentStart]['code'] === T_COMMENT) {
             $phpcsFile->addError('You must use "/**" style comments for a file comment', $stackPtr + 1);
             return;
         } else {
             if ($commentStart === false || $tokens[$commentStart]['code'] !== T_DOC_COMMENT) {
                 $phpcsFile->addError('Missing file doc comment', $stackPtr + 1);
                 return;
             } else {
                 // Extract the header comment docblock.
                 $commentEnd = $phpcsFile->findNext(T_DOC_COMMENT, $commentStart + 1, null, true) - 1;
                 // Check if there is only 1 doc comment between the open tag and class token.
                 $nextToken = array(T_ABSTRACT, T_CLASS, T_FUNCTION, T_DOC_COMMENT);
                 $commentNext = $phpcsFile->findNext($nextToken, $commentEnd + 1);
                 if ($commentNext !== false && $tokens[$commentNext]['code'] !== T_DOC_COMMENT) {
                     // Found a class token right after comment doc block.
                     $newlineToken = $phpcsFile->findNext(T_WHITESPACE, $commentEnd + 1, $commentNext, false, $phpcsFile->eolChar);
                     if ($newlineToken !== false) {
                         $newlineToken = $phpcsFile->findNext(T_WHITESPACE, $newlineToken + 1, $commentNext, false, $phpcsFile->eolChar);
                         if ($newlineToken === false) {
                             // No blank line between the class token and the doc block.
                             // The doc block is most likely a class comment.
                             $phpcsFile->addError('Missing file doc comment', $stackPtr + 1);
                             return;
                         }
                     }
                 }
                 $comment = $phpcsFile->getTokensAsString($commentStart, $commentEnd - $commentStart + 1);
                 // Parse the header comment docblock.
                 try {
                     $this->commentParser = new PHP_CodeSniffer_CommentParser_ClassCommentParser($comment, $phpcsFile);
                     $this->commentParser->parse();
                 } catch (PHP_CodeSniffer_CommentParser_ParserException $e) {
                     $line = $e->getLineWithinComment() + $commentStart;
                     $phpcsFile->addError($e->getMessage(), $line);
                     return;
                 }
                 $comment = $this->commentParser->getComment();
                 if (is_null($comment) === true) {
                     $error = 'File doc comment is empty';
                     $phpcsFile->addError($error, $commentStart);
                     return;
                 }
                 // No extra newline before short description.
                 $short = $comment->getShortComment();
                 $newlineCount = 0;
                 $newlineSpan = strspn($short, $phpcsFile->eolChar);
                 if ($short !== '' && $newlineSpan > 0) {
                     $line = $newlineSpan > 1 ? 'newlines' : 'newline';
                     $error = "Extra {$line} found before file comment short description";
                     $phpcsFile->addError($error, $commentStart + 1);
                 }
                 $newlineCount = substr_count($short, $phpcsFile->eolChar) + 1;
                 // Exactly one blank line between short and long description.
                 $long = $comment->getLongComment();
                 if (empty($long) === false) {
                     $between = $comment->getWhiteSpaceBetween();
                     $newlineBetween = substr_count($between, $phpcsFile->eolChar);
                     if ($newlineBetween !== 2) {
                         $error = 'There must be exactly one blank line between descriptions in file comment';
                         $phpcsFile->addError($error, $commentStart + $newlineCount + 1);
                     }
                     $newlineCount += $newlineBetween;
                 }
                 // Exactly one blank line before tags.
                 $tags = $this->commentParser->getTagOrders();
                 if (count($tags) > 1) {
                     $newlineSpan = $comment->getNewlineAfter();
                     if ($newlineSpan !== 2) {
                         $error = 'There must be exactly one blank line before the tags in file comment';
                         if ($long !== '') {
                             $newlineCount += substr_count($long, $phpcsFile->eolChar) - $newlineSpan + 1;
                         }
                         $phpcsFile->addError($error, $commentStart + $newlineCount);
                         $short = rtrim($short, $phpcsFile->eolChar . ' ');
                     }
                 }
                 // Check each tag.
                 $this->processTags($commentStart, $commentEnd);
             }
         }
     }
     //end if
 }