~ubuntu-branches/ubuntu/saucy/php-codesniffer/saucy

« back to all changes in this revision

Viewing changes to PHP_CodeSniffer-1.1.0/CodeSniffer/Standards/Squiz/Sniffs/Commenting/InlineCommentSniff.php

  • Committer: Bazaar Package Importer
  • Author(s): Jack Bates
  • Date: 2008-10-01 17:39:43 UTC
  • mfrom: (1.1.1 upstream)
  • Revision ID: james.westby@ubuntu.com-20081001173943-2dy06n1e8zwyw1o8
Tags: 1.1.0-1
* New upstream release
* Acknowledge NMU, thanks Jan

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
<?php
 
2
/**
 
3
 * Squiz_Sniffs_Commenting_InlineCommentSniff.
 
4
 *
 
5
 * PHP version 5
 
6
 *
 
7
 * @category  PHP
 
8
 * @package   PHP_CodeSniffer
 
9
 * @author    Greg Sherwood <gsherwood@squiz.net>
 
10
 * @author    Marc McIntyre <mmcintyre@squiz.net>
 
11
 * @copyright 2006 Squiz Pty Ltd (ABN 77 084 670 600)
 
12
 * @license   http://matrix.squiz.net/developer/tools/php_cs/licence BSD Licence
 
13
 * @version   CVS: $Id: InlineCommentSniff.php,v 1.11 2008/02/26 03:47:35 squiz Exp $
 
14
 * @link      http://pear.php.net/package/PHP_CodeSniffer
 
15
 */
 
16
 
 
17
/**
 
18
 * Squiz_Sniffs_Commenting_InlineCommentSniff.
 
19
 *
 
20
 * Checks that there is adequate spacing between comments.
 
21
 *
 
22
 * @category  PHP
 
23
 * @package   PHP_CodeSniffer
 
24
 * @author    Greg Sherwood <gsherwood@squiz.net>
 
25
 * @author    Marc McIntyre <mmcintyre@squiz.net>
 
26
 * @copyright 2006 Squiz Pty Ltd (ABN 77 084 670 600)
 
27
 * @license   http://matrix.squiz.net/developer/tools/php_cs/licence BSD Licence
 
28
 * @version   Release: 1.1.0
 
29
 * @link      http://pear.php.net/package/PHP_CodeSniffer
 
30
 */
 
31
class Squiz_Sniffs_Commenting_InlineCommentSniff implements PHP_CodeSniffer_Sniff
 
32
{
 
33
 
 
34
 
 
35
    /**
 
36
     * Returns an array of tokens this test wants to listen for.
 
37
     *
 
38
     * @return array
 
39
     */
 
40
    public function register()
 
41
    {
 
42
        return array(
 
43
                T_COMMENT,
 
44
                T_DOC_COMMENT,
 
45
               );
 
46
 
 
47
    }//end register()
 
48
 
 
49
 
 
50
    /**
 
51
     * Processes this test, when one of its tokens is encountered.
 
52
     *
 
53
     * @param PHP_CodeSniffer_File $phpcsFile The file being scanned.
 
54
     * @param int                  $stackPtr  The position of the current token in the
 
55
     *                                        stack passed in $tokens.
 
56
     *
 
57
     * @return void
 
58
     */
 
59
    public function process(PHP_CodeSniffer_File $phpcsFile, $stackPtr)
 
60
    {
 
61
        $tokens = $phpcsFile->getTokens();
 
62
 
 
63
        // If this is a function/class/interface doc block comment, skip it.
 
64
        // We are only interested in inline doc block comments, which are
 
65
        // not allowed.
 
66
        if ($tokens[$stackPtr]['code'] === T_DOC_COMMENT) {
 
67
            $nextToken = $phpcsFile->findNext(PHP_CodeSniffer_Tokens::$emptyTokens, ($stackPtr + 1), null, true);
 
68
            $ignore    = array(
 
69
                          T_CLASS,
 
70
                          T_INTERFACE,
 
71
                          T_FUNCTION,
 
72
                          T_PUBLIC,
 
73
                          T_PRIVATE,
 
74
                          T_PROTECTED,
 
75
                          T_STATIC,
 
76
                          T_ABSTRACT,
 
77
                          T_CONST,
 
78
                         );
 
79
            if (in_array($tokens[$nextToken]['code'], $ignore) === true) {
 
80
                return;
 
81
            } else {
 
82
                $prevToken = $phpcsFile->findPrevious(PHP_CodeSniffer_Tokens::$emptyTokens, ($stackPtr - 1), null, true);
 
83
                if ($tokens[$prevToken]['code'] === T_OPEN_TAG) {
 
84
                    return;
 
85
                }
 
86
 
 
87
                // Only error once per comment.
 
88
                if (substr($tokens[$stackPtr]['content'], 0, 3) === '/**') {
 
89
                    $error  = 'Inline doc block comments are not allowed; use "/* Comment */" or "// Comment" instead';
 
90
                    $phpcsFile->addError($error, $stackPtr);
 
91
                }
 
92
            }
 
93
        }
 
94
 
 
95
        if ($tokens[$stackPtr]['content']{0} === '#') {
 
96
            $error  = 'Perl-style comments are not allowed; use "// Comment" instead';
 
97
            $phpcsFile->addError($error, $stackPtr);
 
98
        }
 
99
 
 
100
        // We don't want end of block comments. If the last comment is a closing
 
101
        // curly brace.
 
102
        $previousContent = $phpcsFile->findPrevious(array(T_WHITESPACE), ($stackPtr - 1), null, true);
 
103
        if (($tokens[$previousContent]['line'] === $tokens[$stackPtr]['line']) && ($tokens[$previousContent]['code'] === T_CLOSE_CURLY_BRACKET)) {
 
104
            return;
 
105
        }
 
106
 
 
107
        $comment = rtrim($tokens[$stackPtr]['content']);
 
108
        // Only want inline comments.
 
109
        if (substr($comment, 0, 2) !== '//') {
 
110
            return;
 
111
        }
 
112
 
 
113
        $spaceCount = 0;
 
114
        for ($i = 2; $i < strlen($comment); $i++) {
 
115
            if ($comment[$i] !== ' ') {
 
116
                break;
 
117
            }
 
118
 
 
119
            $spaceCount++;
 
120
        }
 
121
 
 
122
        if ($spaceCount === 0) {
 
123
            $error = 'No space before comment text; expected "// '.substr($comment, 2).'" but found "'.$comment.'"';
 
124
            $phpcsFile->addError($error, $stackPtr);
 
125
        }
 
126
 
 
127
        if ($spaceCount > 1) {
 
128
            $error = $spaceCount.' spaces found before inline comment; expected "// '.substr($comment, (2 + $spaceCount)).'" but found "'.$comment.'"';
 
129
            $phpcsFile->addError($error, $stackPtr);
 
130
        }
 
131
 
 
132
 
 
133
        // The below section determines if a comment block is correctly capitalised,
 
134
        // and ends in a full-stop. It will find the last comment in a block, and
 
135
        // work its way up.
 
136
        $nextComment = $phpcsFile->findNext(array(T_COMMENT), ($stackPtr + 1), null, false);
 
137
 
 
138
        if (($nextComment !== false) && (($tokens[$nextComment]['line']) === ($tokens[$stackPtr]['line'] + 1))) {
 
139
            return;
 
140
        }
 
141
 
 
142
        $topComment  = $stackPtr;
 
143
        $lastComment = $stackPtr;
 
144
        while (($topComment = $phpcsFile->findPrevious(array(T_COMMENT), ($lastComment - 1), null, false)) !== false) {
 
145
            if ($tokens[$topComment]['line'] !== ($tokens[$lastComment]['line'] - 1)) {
 
146
                break;
 
147
            }
 
148
 
 
149
            $lastComment = $topComment;
 
150
        }
 
151
 
 
152
        $topComment  = $lastComment;
 
153
        $commentText = '';
 
154
 
 
155
        for ($i = $topComment; $i <= $stackPtr; $i++) {
 
156
            if ($tokens[$i]['code'] === T_COMMENT) {
 
157
                $commentText .= trim(substr($tokens[$i]['content'], 2));
 
158
            }
 
159
        }
 
160
 
 
161
        if ($commentText === '') {
 
162
            $error = 'Blank comments are not allowed';
 
163
            $phpcsFile->addError($error, $stackPtr);
 
164
            return;
 
165
        }
 
166
 
 
167
        if (preg_match('|[A-Z]|', $commentText[0]) === 0) {
 
168
            $error = 'Inline comments must start with a capital letter';
 
169
            $phpcsFile->addError($error, $topComment);
 
170
        }
 
171
 
 
172
        $commentCloser   = $commentText[(strlen($commentText) - 1)];
 
173
        $acceptedClosers = array(
 
174
                            'full-stops'        => '.',
 
175
                            'exclamation marks' => '!',
 
176
                            'or question marks' => '?',
 
177
                           );
 
178
 
 
179
        if (in_array($commentCloser, $acceptedClosers) === false) {
 
180
            $error = 'Inline comments must end in';
 
181
            foreach ($acceptedClosers as $closerName => $symbol) {
 
182
                $error .= ' '.$closerName.',';
 
183
            }
 
184
 
 
185
            $error = rtrim($error, ',');
 
186
            $phpcsFile->addError($error, $stackPtr);
 
187
        }
 
188
 
 
189
        // Finally, the line below the last comment cannot be empty.
 
190
        $start = false;
 
191
        for ($i = ($stackPtr + 1); $i < $phpcsFile->numTokens; $i++) {
 
192
            if ($tokens[$i]['line'] === ($tokens[$stackPtr]['line'] + 1)) {
 
193
                if ($tokens[$i]['code'] !== T_WHITESPACE) {
 
194
                    return;
 
195
                }
 
196
            } else if ($tokens[$i]['line'] > ($tokens[$stackPtr]['line'] + 1)) {
 
197
                break;
 
198
            }
 
199
        }
 
200
 
 
201
        $error = 'There must be no blank line following an inline comment';
 
202
        $phpcsFile->addError($error, $stackPtr);
 
203
 
 
204
    }//end process()
 
205
 
 
206
 
 
207
}//end class
 
208
 
 
209
 
 
210
?>