source: trunk/docs/coding_standards.txt @ 334

Last change on this file since 334 was 334, checked in by quinn, 16 years ago

Fixed lots of misplings. I'm so embarrassed! ;P

File size: 13.3 KB
Line 
1Strangecode coding standards
229 Aug 2005 20:12:49
3
4
5======================================================================
6Preamble
7======================================================================
8
9Our standards follow closely the PEAR coding standards.
10
11Essential reading:
12http://pear.php.net/manual/en/standards.php
13
14
15======================================================================
16File Naming Conventions
17======================================================================
18
19script.php              Public accessible scripts.
20
21Auth_SQL.inc.php        One PHP Class to be included. The filename is the
22                        type of class, underscore, name. Or if in subdirs,
23                        this could be /Auth/SQL.inc.php while the class name
24                        remains "Auth_SQL"
25
26some_file.inc.html      HTML file, which may or may not have some PHP,
27                        but will be included by some other PHP file. Never
28                        includes sensitive code as these files may be accessed
29                        directly in the web root.
30
31script.cli.php          A command-line executable script, possibly executed
32                        with CRON. Outputs TEXT if any instead of HTML.
33
34script.inc.eml          Text file to be sent by email.
35
36schema.mysql            Database schema file that goes with the application.
37
38main.screen.css         CSS file with media: screen/print/all
39main.print.css
40
41
42======================================================================
43Indenting and Wrap
44======================================================================
45
46Use an indent of 4 spaces, with no tabs. Code and especially comments should
47usually be wrapped <= 80 characters. Exceptions are made in the case where
48code readability is significantly improved with longer lines.
49
50
51======================================================================
52Control Structures
53======================================================================
54
55These include if, for, while, switch, etc. Here is an example if statement,
56since it is the most complicated of them:
57
58    if ((condition1) || (condition2)) {
59        action1;
60    } else if ((condition3) && (condition4)) {
61        action2;
62    } else {
63        defaultaction;
64    }
65
66Control statements should have one space between the control keyword
67and opening parenthesis, to distinguish them from function calls.
68
69Even in the case of an if with no else clauses, and only a 1 line action,
70the curly braces should still be used:
71
72    if (condition) {
73        action;
74    }
75
76This improves readability and allows easy extension of the clause.
77
78For switch statements:
79
80    switch (condition) {
81    case 1:
82        action1;
83        break;
84
85    case 2:
86        action2;
87        break;
88
89    default:
90        defaultaction;
91        break;
92
93    }
94
95
96======================================================================
97Function Calls
98======================================================================
99
100Functions should be called with no spaces between the function name,
101the opening parenthesis, and the first parameter; spaces between commas
102and each parameter, and no space between the last parameter, the
103closing parenthesis, and the semicolon. Here's an example:
104
105    $var = foo($bar, $baz, $quux);
106
107As displayed above, there should be one space on either side of an
108equals sign used to assign the return value of a function to a
109variable. In the case of a block of related assignments, more space
110may be inserted to promote readability:
111
112    $short         = foo($bar);
113    $long_variable = foo($baz);
114
115
116======================================================================
117Function and Method Definitions
118======================================================================
119
120Function declaractions follow the "one true brace" convention:
121
122    function fooFunction($arg1, $arg2 = '')
123    {
124        if (condition) {
125            statement;
126        }
127        return $val;
128    }
129
130Arguments with default values go at the end of the argument list. Always
131attempt to return a meaningful value from a function if one is appropriate.
132
133Use lowerCamelCase for function and method names to distinguish from php
134internal functions which standard on underscore_space_style_names().
135
136
137======================================================================
138Return Values
139======================================================================
140
141When functions return boolean values, use 'return false;' or 'return true;'
142as opposed to 'return 0;' or 'return 1;' or 'return(-1);', except when
143boolean plurality is necessary.
144
145
146======================================================================
147String Concatenation
148======================================================================
149
150Always include a space before and after the concatenation operator '.' which
151improves readability and improves search-and-replace of adjacent elements.
152
153    $something = $blah . funky() . ".\".=" . $blab;
154
155is better than:
156
157    $something = $blah.funky().".\".=".$blab;
158
159
160======================================================================
161Quote Marks
162======================================================================
163
164Use the single quote marks ' to enclose simple strings whenever possible.
165Double quote marks " require extra parsing and thus slow things down, but
166are necessary if entities there must be swapped-out such as variables or
167control characters.
168
169    $var['singlequote'] = 'singlequote';
170    $var["doublequote-$i"] = "$vars and \n funny \t %s things need doublequotes";
171    $var['doublequote-' . $i] = $var . 'you can do this' . "\t %s" . $var2 .
172    'but it isn\'t any better';
173
174
175======================================================================
176Printing HTML
177======================================================================
178
179For large or complex blocks of HTML, using the following method is much faster
180and safer than echo because the php processor is bypassed and content goes
181directly to output:
182
183    <?php
184    if ($something) {
185        // Here comes multi-line HTML...
186        ?>
187        <div class="sc-tiny">
188            <a href="<?php echo $app->ohref('/contact.php') ?>">Contact us</a>
189        </div>
190        <?php
191    } else if ($somethingelse) {
192        ?><h1>Just a single-line of html</h1><?php
193    }
194    ?>
195
196
197======================================================================
198Comments
199======================================================================
200
201Function comments should follow the Javadoc standard, with detailed
202function comments and one-line pointers along the way:
203http://java.sun.com/products/jdk/javadoc/writingdoccomments/index.html
204
205Here is an example of the codebase method Email::validEmail():
206
207    <?php
208    /**
209     * Validates an email address based on the recommendations in RFC 3696.
210     * Is more loose than restrictive, to allow the many valid variants of
211     * email addresses while catching the most common mistakes. Checks an array too.
212     * http://www.faqs.org/rfcs/rfc822.html
213     * http://www.faqs.org/rfcs/rfc2822.html
214     * http://www.faqs.org/rfcs/rfc3696.html
215     * http://www.faqs.org/rfcs/rfc1035.html
216     *
217     * @access  public
218     * @param   mixed  $email  Address to check, string or array.
219     * @return  bool    Validity of address.
220     * @author  Quinn Comendant <quinn@strangecode.com>
221     * @since   30 Nov 2005 22:00:50
222     */
223    function validEmail($email)
224    {
225        $app =& App::getInstance();
226   
227        // If an array, check values recursively.
228        if (is_array($email)) {
229            foreach ($email as $e) {
230                if (!$this->validEmail($e)) {
231                    return false;
232                }
233            }
234            return true;
235        } else {
236            // To be valid email address must match regex and fit within the length constraints.
237            if (preg_match($this->getParam('regex'), $email, $e_parts) && mb_strlen($e_parts[2]) < 64 && mb_strlen($e_parts[3]) < 255) {
238                return true;
239            } else {
240                $app->logMsg(sprintf('Invalid email: %s', $email), LOG_INFO, __FILE__, __LINE__);
241                return false;
242            }
243        }
244    }
245    ?>
246
247Single line comments should be of the double-slash variety, and be on the line above the
248code being commented upon:
249
250    <?php
251    // If the last word in $var is peanuts, set $need_peanuts to TRUE.
252    $need_peanuts = preg_match('/peanuts$/i', $var);
253    ?>
254
255
256======================================================================
257Including Code
258======================================================================
259
260If you are including a class, function library, or anything else which would
261cause a parse error if included twice, always use include_once. This will
262ensure that no matter how many factory methods we use or how much dynamic
263inclusion we do, the library will only be included once.
264
265If you are including a static filename, such as a conf file or a template
266that is _always_ used, use require.
267
268If you are dynamically including a filename, or want the code to only be
269used conditionally (an optional template), use include.
270
271
272======================================================================
273PHP Code Tags
274======================================================================
275
276Always use <?php ?> to delimit PHP code, not the <? ?> shorthand. Even
277use <?php echo $name; ?> instead of <?=$name?>.
278
279
280======================================================================
281php.ini Settings
282======================================================================
283
284All code should work with register_globals = Off. This means using
285$_REQUEST, $_GET, $_POST, $_COOKIE, $_SESSION, $_SERVER, and $_ENV
286to access all request, get, post, cookie, session, server, and
287environment data, respectively.
288
289All code should work with error_reporting = E_ALL. Failure to do so would
290result in ugly output, error logs getting filled with lots of warning messages,
291or even downright broken scripts.
292
293All code should work regardless of the setting of magic_quotes_gpc.
294Form data should be passed through stripslashes() if necessary.
295
296No code should assume that '.' is in the include path. Always
297specify './' in front of a filename when you are including a file in
298the same directory. Or better yet, for less abiguity, use:
299include dirname(__FILE__) . '/include_me.inc.php';
300
301
302======================================================================
303XHTML 1.0 Compliance
304======================================================================
305
306All HTML should be valid XHTML 1.0 verified with the
307W3C Markup Validation Service: http://validator.w3.org/
308
309All tag names and parameters must be lower case including javascript
310event handlers:
311
312    <div class="mofogo">...</div>
313    <a href="http://www.example.com/" onmouseover="status=''" onmouseout="status=''">...</a>
314
315All tag parameters must be of a valid parameter="value" form (numeric
316values must also be surrounded by quotes).  For parameters that had no
317value in HTML, the parameter name is the value.  For example:
318
319    <input type="checkbox" checked="checked" />
320    <select name="example">
321        <option selected="selected" value="1">Example</option>
322    </select>
323    <td nowrap="nowrap">Example</td>
324
325All tags must be properly closed. Tags without a closing part must follow the
326XHTML convention and end with a space and a slash:
327
328    <br />
329    <hr />
330    <img src="example.gif" alt="Example" />
331    <input type="submit" value="Example" />
332
333All form definitions must be on their own line and either fully defined within
334a <td></td> pair or be outside table tags. Forms must also always have an action
335parameter:
336
337    <form method="post" action="http://example.com/example.cgi">
338    <table>
339        <tr><td>example</td></tr>
340    </table>
341    </from>
342
343    <table>
344        <tr><td>
345            <form action="javascript:void(0)" onsubmit="return false;">
346            </form>
347        </td></tr>
348    </table>
349
350All JavaScript tags must have a valid language and type parameters:
351
352    <script language="JavaScript" type="text/javascript">
353    <!--
354    ...
355    // -->
356    </script>
357
358Nothing may appear after </html>, therefore include any common footers after
359all other output.
360
361All images must have an alt parameter:
362
363    <img src="example.gif" alt="<?php echo _("Example"); ?>" />
364
365Input field of type "image" does not allow the border parameter, and may render
366with a border on some browsers.  Use the following instead:
367
368   <a href="" onclick="document.formname.submit(); return false;"><img src="example.gif" alt="<?php echo _("Example"); ?>" /></a>
369
370
371======================================================================
372Database Naming Conventions
373======================================================================
374
375All database tables need to make sure that their table and field names work in all
376databases. Many databases reserve words like 'uid', 'user', etc. for
377internal use, and forbid words that are SQL keywords (select, where,
378etc.). Adding '_tbl' to the end of the table name is a good idea for this reason
379and also improves searching for the table names in the code.
380
381A good way to do this for field names is to make the field name
382table_name_field_name.
383
384When building queries referencing two-or-more tables always preface columns
385with the table containing the column (admin_tbl.username, location_tbl.location_address).
386This method is much preferred over using aliases of table names (a.username, l.location_address).
387
388Table names should be singular (user_tbl instead of users_tbl).
Note: See TracBrowser for help on using the repository browser.