blob: d8bdd05317d95e44692fc3746679620ddacf740e [file] [log] [blame]
Derek Jones619b1222011-10-10 16:26:27 -05001###############
2PHP Style Guide
3###############
4
Derek Jones8ede1a22011-10-05 13:34:52 -05005
6The following page describes the use of coding rules adhered to when
7developing CodeIgniter.
8
9.. contents:: Table of Contents
10
11File Format
12===========
13
14Files should be saved with Unicode (UTF-8) encoding. The BOM should
15*not* be used. Unlike UTF-16 and UTF-32, there's no byte order to
16indicate in a UTF-8 encoded file, and the BOM can have a negative side
17effect in PHP of sending output, preventing the application from being
18able to set its own headers. Unix line endings should be used (LF).
19
20Here is how to apply these settings in some of the more common text
21editors. Instructions for your text editor may vary; check your text
22editor's documentation.
23
24TextMate
25''''''''
26
27#. Open the Application Preferences
28#. Click Advanced, and then the "Saving" tab
29#. In "File Encoding", select "UTF-8 (recommended)"
30#. In "Line Endings", select "LF (recommended)"
31#. *Optional:* Check "Use for existing files as well" if you wish to
32 modify the line endings of files you open to your new preference.
33
34BBEdit
35''''''
36
37#. Open the Application Preferences
38#. Select "Text Encodings" on the left.
39#. In "Default text encoding for new documents", select "Unicode (UTF-8,
40 no BOM)"
41#. *Optional:* In "If file's encoding can't be guessed, use", select
42 "Unicode (UTF-8, no BOM)"
43#. Select "Text Files" on the left.
44#. In "Default line breaks", select "Mac OS X and Unix (LF)"
45
46PHP Closing Tag
47===============
48
49The PHP closing tag on a PHP document **?>** is optional to the PHP
50parser. However, if used, any whitespace following the closing tag,
51whether introduced by the developer, user, or an FTP application, can
52cause unwanted output, PHP errors, or if the latter are suppressed,
53blank pages. For this reason, all PHP files should **OMIT** the closing
54PHP tag, and instead use a comment block to mark the end of file and
55it's location relative to the application root. This allows you to still
56identify a file as being complete and not truncated.
57
Derek Jones129c1812011-10-05 17:15:44 -050058**INCORRECT**::
Derek Jones8ede1a22011-10-05 13:34:52 -050059
Derek Jones129c1812011-10-05 17:15:44 -050060 <?php
61
62 echo "Here's my code!";
63
64 ?>
65
66**CORRECT**::
67
68 <?php
69
70 echo "Here's my code!";
71
72 /* End of file myfile.php */
73 /* Location: ./system/modules/mymodule/myfile.php */
Derek Jones8ede1a22011-10-05 13:34:52 -050074
75Class and Method Naming
76=======================
77
78Class names should always start with an uppercase letter. Multiple words
79should be separated with an underscore, and not CamelCased. All other
80class methods should be entirely lowercased and named to clearly
81indicate their function, preferably including a verb. Try to avoid
82overly long and verbose names.
83
Derek Jones129c1812011-10-05 17:15:44 -050084**INCORRECT**::
Derek Jones8ede1a22011-10-05 13:34:52 -050085
Derek Jones129c1812011-10-05 17:15:44 -050086 class superclass
87 class SuperClass
88
89**CORRECT**::
90
91 class Super_class
Derek Jones8ede1a22011-10-05 13:34:52 -050092
93::
94
Derek Jones129c1812011-10-05 17:15:44 -050095 class Super_class {
Derek Jones8ede1a22011-10-05 13:34:52 -050096
Derek Jones129c1812011-10-05 17:15:44 -050097 function __construct()
98 {
Derek Jones8ede1a22011-10-05 13:34:52 -050099
Derek Jones129c1812011-10-05 17:15:44 -0500100 }
101 }
102
103Examples of improper and proper method naming:
104
105**INCORRECT**::
106
107 function fileproperties() // not descriptive and needs underscore separator
108 function fileProperties() // not descriptive and uses CamelCase
109 function getfileproperties() // Better! But still missing underscore separator
110 function getFileProperties() // uses CamelCase
111 function get_the_file_properties_from_the_file() // wordy
112
113**CORRECT**::
114
115 function get_file_properties() // descriptive, underscore separator, and all lowercase letters
Derek Jones8ede1a22011-10-05 13:34:52 -0500116
117Variable Names
118==============
119
120The guidelines for variable naming is very similar to that used for
121class methods. Namely, variables should contain only lowercase letters,
122use underscore separators, and be reasonably named to indicate their
123purpose and contents. Very short, non-word variables should only be used
124as iterators in for() loops.
125
Derek Jones129c1812011-10-05 17:15:44 -0500126**INCORRECT**::
Derek Jones8ede1a22011-10-05 13:34:52 -0500127
Derek Jones129c1812011-10-05 17:15:44 -0500128 $j = 'foo'; // single letter variables should only be used in for() loops
129 $Str // contains uppercase letters
130 $bufferedText // uses CamelCasing, and could be shortened without losing semantic meaning
131 $groupid // multiple words, needs underscore separator
132 $name_of_last_city_used // too long
133
134**CORRECT**::
135
136 for ($j = 0; $j < 10; $j++)
137 $str
138 $buffer
139 $group_id
140 $last_city
Derek Jones8ede1a22011-10-05 13:34:52 -0500141
142Commenting
143==========
144
145In general, code should be commented prolifically. It not only helps
146describe the flow and intent of the code for less experienced
147programmers, but can prove invaluable when returning to your own code
148months down the line. There is not a required format for comments, but
149the following are recommended.
150
151`DocBlock <http://manual.phpdoc.org/HTMLSmartyConverter/HandS/phpDocumentor/tutorial_phpDocumentor.howto.pkg.html#basics.docblock>`_
152style comments preceding class and method declarations so they can be
153picked up by IDEs::
154
Derek Jones129c1812011-10-05 17:15:44 -0500155 /**
156 * Super Class
157 *
158 * @package Package Name
159 * @subpackage Subpackage
160 * @category Category
161 * @author Author Name
162 * @link http://example.com
163 */
164 class Super_class {
Derek Jones8ede1a22011-10-05 13:34:52 -0500165
166::
167
Derek Jones129c1812011-10-05 17:15:44 -0500168 /**
169 * Encodes string for use in XML
170 *
171 * @access public
172 * @param string
173 * @return string
174 */
175 function xml_encode($str)
Derek Jones8ede1a22011-10-05 13:34:52 -0500176
177Use single line comments within code, leaving a blank line between large
178comment blocks and code.
179
180::
181
Derek Jones129c1812011-10-05 17:15:44 -0500182 // break up the string by newlines
183 $parts = explode("\n", $str);
184
185 // A longer comment that needs to give greater detail on what is
186 // occurring and why can use multiple single-line comments. Try to
187 // keep the width reasonable, around 70 characters is the easiest to
188 // read. Don't hesitate to link to permanent external resources
189 // that may provide greater detail:
190 //
191 // http://example.com/information_about_something/in_particular/
192
193 $parts = $this->foo($parts);
Derek Jones8ede1a22011-10-05 13:34:52 -0500194
195Constants
196=========
197
198Constants follow the same guidelines as do variables, except constants
199should always be fully uppercase. *Always use CodeIgniter constants when
200appropriate, i.e. SLASH, LD, RD, PATH_CACHE, etc.*
201
Derek Jones129c1812011-10-05 17:15:44 -0500202**INCORRECT**::
Derek Jones8ede1a22011-10-05 13:34:52 -0500203
Derek Jones129c1812011-10-05 17:15:44 -0500204 myConstant // missing underscore separator and not fully uppercase
205 N // no single-letter constants
206 S_C_VER // not descriptive
207 $str = str_replace('{foo}', 'bar', $str); // should use LD and RD constants
208
209**CORRECT**::
210
211 MY_CONSTANT
212 NEWLINE
213 SUPER_CLASS_VERSION
214 $str = str_replace(LD.'foo'.RD, 'bar', $str);
Derek Jones8ede1a22011-10-05 13:34:52 -0500215
216TRUE, FALSE, and NULL
217=====================
218
219**TRUE**, **FALSE**, and **NULL** keywords should always be fully
220uppercase.
221
Derek Jones129c1812011-10-05 17:15:44 -0500222**INCORRECT**::
Derek Jones8ede1a22011-10-05 13:34:52 -0500223
Derek Jones129c1812011-10-05 17:15:44 -0500224 if ($foo == true)
225 $bar = false;
226 function foo($bar = null)
227
228**CORRECT**::
229
230 if ($foo == TRUE)
231 $bar = FALSE;
232 function foo($bar = NULL)
Derek Jones8ede1a22011-10-05 13:34:52 -0500233
234Logical Operators
235=================
236
237Use of **\|\|** is discouraged as its clarity on some output devices is
238low (looking like the number 11 for instance). **&&** is preferred over
239**AND** but either are acceptable, and a space should always precede and
240follow **!**.
241
Derek Jones129c1812011-10-05 17:15:44 -0500242**INCORRECT**::
Derek Jones8ede1a22011-10-05 13:34:52 -0500243
Derek Jones129c1812011-10-05 17:15:44 -0500244 if ($foo || $bar)
245 if ($foo AND $bar) // okay but not recommended for common syntax highlighting applications
246 if (!$foo)
247 if (! is_array($foo))
248
249**CORRECT**::
250
251 if ($foo OR $bar)
252 if ($foo && $bar) // recommended
253 if ( ! $foo)
254 if ( ! is_array($foo))
255
Derek Jones8ede1a22011-10-05 13:34:52 -0500256
257Comparing Return Values and Typecasting
258=======================================
259
260Some PHP functions return FALSE on failure, but may also have a valid
261return value of "" or 0, which would evaluate to FALSE in loose
262comparisons. Be explicit by comparing the variable type when using these
263return values in conditionals to ensure the return value is indeed what
264you expect, and not a value that has an equivalent loose-type
265evaluation.
266
267Use the same stringency in returning and checking your own variables.
268Use **===** and **!==** as necessary.
Derek Jones8ede1a22011-10-05 13:34:52 -0500269
Derek Jones129c1812011-10-05 17:15:44 -0500270**INCORRECT**::
Derek Jones8ede1a22011-10-05 13:34:52 -0500271
Derek Jones129c1812011-10-05 17:15:44 -0500272 // If 'foo' is at the beginning of the string, strpos will return a 0,
273 // resulting in this conditional evaluating as TRUE
274 if (strpos($str, 'foo') == FALSE)
Derek Jones8ede1a22011-10-05 13:34:52 -0500275
Derek Jones129c1812011-10-05 17:15:44 -0500276**CORRECT**::
277
278 if (strpos($str, 'foo') === FALSE)
279
280**INCORRECT**::
281
282 function build_string($str = "")
283 {
284 if ($str == "") // uh-oh! What if FALSE or the integer 0 is passed as an argument?
285 {
286
287 }
288 }
289
290**CORRECT**::
291
292 function build_string($str = "")
293 {
294 if ($str === "")
295 {
296
297 }
298 }
Derek Jones8ede1a22011-10-05 13:34:52 -0500299
300
301See also information regarding
302`typecasting <http://us3.php.net/manual/en/language.types.type-juggling.php#language.types.typecasting>`_,
303which can be quite useful. Typecasting has a slightly different effect
304which may be desirable. When casting a variable as a string, for
305instance, NULL and boolean FALSE variables become empty strings, 0 (and
306other numbers) become strings of digits, and boolean TRUE becomes "1"::
307
308 $str = (string) $str; // cast $str as a string
309
310Debugging Code
311==============
312
313No debugging code can be left in place for submitted add-ons unless it
314is commented out, i.e. no var_dump(), print_r(), die(), and exit()
315calls that were used while creating the add-on, unless they are
316commented out.
317
318::
319
320 // print_r($foo);
321
322Whitespace in Files
323===================
324
325No whitespace can precede the opening PHP tag or follow the closing PHP
326tag. Output is buffered, so whitespace in your files can cause output to
327begin before CodeIgniter outputs its content, leading to errors and an
328inability for CodeIgniter to send proper headers. In the examples below,
329select the text with your mouse to reveal the incorrect whitespace.
330
Derek Jones8ede1a22011-10-05 13:34:52 -0500331
332Compatibility
333=============
334
335Unless specifically mentioned in your add-on's documentation, all code
336must be compatible with PHP version 5.1+. Additionally, do not use PHP
337functions that require non-default libraries to be installed unless your
338code contains an alternative method when the function is not available,
339or you implicitly document that your add-on requires said PHP libraries.
340
341Class and File Names using Common Words
342=======================================
343
344When your class or filename is a common word, or might quite likely be
345identically named in another PHP script, provide a unique prefix to help
346prevent collision. Always realize that your end users may be running
347other add-ons or third party PHP scripts. Choose a prefix that is unique
348to your identity as a developer or company.
349
Derek Jones129c1812011-10-05 17:15:44 -0500350**INCORRECT**::
Derek Jones8ede1a22011-10-05 13:34:52 -0500351
Derek Jones129c1812011-10-05 17:15:44 -0500352 class Email pi.email.php
353 class Xml ext.xml.php
354 class Import mod.import.php
355
356**CORRECT**::
357
358 class Pre_email pi.pre_email.php
359 class Pre_xml ext.pre_xml.php
360 class Pre_import mod.pre_import.php
Derek Jones8ede1a22011-10-05 13:34:52 -0500361
362Database Table Names
363====================
364
365Any tables that your add-on might use must use the 'exp\_' prefix,
366followed by a prefix uniquely identifying you as the developer or
367company, and then a short descriptive table name. You do not need to be
368concerned about the database prefix being used on the user's
369installation, as CodeIgniter's database class will automatically convert
370'exp\_' to what is actually being used.
371
Derek Jones129c1812011-10-05 17:15:44 -0500372**INCORRECT**::
Derek Jones8ede1a22011-10-05 13:34:52 -0500373
Derek Jones129c1812011-10-05 17:15:44 -0500374 email_addresses // missing both prefixes
375 pre_email_addresses // missing exp_ prefix
376 exp_email_addresses // missing unique prefix
Derek Jones8ede1a22011-10-05 13:34:52 -0500377
Derek Jones129c1812011-10-05 17:15:44 -0500378**CORRECT**::
379
380 exp_pre_email_addresses
381
382.. note:: Be mindful that MySQL has a limit of 64 characters for table
383 names. This should not be an issue as table names that would exceed this
384 would likely have unreasonable names. For instance, the following table
385 name exceeds this limitation by one character. Silly, no?
386 **exp_pre_email_addresses_of_registered_users_in_seattle_washington**
387
Derek Jones8ede1a22011-10-05 13:34:52 -0500388One File per Class
389==================
390
391Use separate files for each class your add-on uses, unless the classes
392are *closely related*. An example of CodeIgniter files that contains
393multiple classes is the Database class file, which contains both the DB
394class and the DB_Cache class, and the Magpie plugin, which contains
395both the Magpie and Snoopy classes.
396
397Whitespace
398==========
399
400Use tabs for whitespace in your code, not spaces. This may seem like a
401small thing, but using tabs instead of whitespace allows the developer
402looking at your code to have indentation at levels that they prefer and
403customize in whatever application they use. And as a side benefit, it
404results in (slightly) more compact files, storing one tab character
405versus, say, four space characters.
406
407Line Breaks
408===========
409
410Files must be saved with Unix line breaks. This is more of an issue for
411developers who work in Windows, but in any case ensure that your text
412editor is setup to save files with Unix line breaks.
413
414Code Indenting
415==============
416
417Use Allman style indenting. With the exception of Class declarations,
418braces are always placed on a line by themselves, and indented at the
419same level as the control statement that "owns" them.
420
Derek Jones129c1812011-10-05 17:15:44 -0500421**INCORRECT**::
Derek Jones8ede1a22011-10-05 13:34:52 -0500422
Derek Jones129c1812011-10-05 17:15:44 -0500423 function foo($bar) {
424 // ...
425 }
426
427 foreach ($arr as $key => $val) {
428 // ...
429 }
430
431 if ($foo == $bar) {
432 // ...
433 } else {
434 // ...
435 }
436
437 for ($i = 0; $i < 10; $i++)
438 {
439 for ($j = 0; $j < 10; $j++)
440 {
441 // ...
442 }
443 }
Timothy Warren82c83072012-01-26 19:02:05 -0500444
445 try {
446 // ...
447 }
448 catch() {
449 // ...
450 }
Derek Jones129c1812011-10-05 17:15:44 -0500451
452**CORRECT**::
453
454 function foo($bar)
455 {
456 // ...
457 }
458
459 foreach ($arr as $key => $val)
460 {
461 // ...
462 }
463
464 if ($foo == $bar)
465 {
466 // ...
467 }
468 else
469 {
470 // ...
471 }
472
473 for ($i = 0; $i < 10; $i++)
474 {
475 for ($j = 0; $j < 10; $j++)
476 {
477 // ...
478 }
479 }
Timothy Warren82c83072012-01-26 19:02:05 -0500480
481 try
482 {
483 // ...
484 }
485 catch()
486 {
487 // ...
488 }
Derek Jones8ede1a22011-10-05 13:34:52 -0500489
490Bracket and Parenthetic Spacing
491===============================
492
493In general, parenthesis and brackets should not use any additional
494spaces. The exception is that a space should always follow PHP control
495structures that accept arguments with parenthesis (declare, do-while,
496elseif, for, foreach, if, switch, while), to help distinguish them from
497functions and increase readability.
498
Derek Jones129c1812011-10-05 17:15:44 -0500499**INCORRECT**::
Derek Jones8ede1a22011-10-05 13:34:52 -0500500
Derek Jones129c1812011-10-05 17:15:44 -0500501 $arr[ $foo ] = 'foo';
502
503**CORRECT**::
504
505 $arr[$foo] = 'foo'; // no spaces around array keys
506
507**INCORRECT**::
508
509 function foo ( $bar )
510 {
511
512 }
513
514**CORRECT**::
515
516 function foo($bar) // no spaces around parenthesis in function declarations
517 {
518
519 }
520
521**INCORRECT**::
522
523 foreach( $query->result() as $row )
524
525**CORRECT**::
526
527 foreach ($query->result() as $row) // single space following PHP control structures, but not in interior parenthesis
Derek Jones8ede1a22011-10-05 13:34:52 -0500528
529Localized Text
530==============
531
532Any text that is output in the control panel should use language
533variables in your lang file to allow localization.
534
Derek Jones129c1812011-10-05 17:15:44 -0500535**INCORRECT**::
Derek Jones8ede1a22011-10-05 13:34:52 -0500536
Derek Jones129c1812011-10-05 17:15:44 -0500537 return "Invalid Selection";
538
539**CORRECT**::
540
541 return $this->lang->line('invalid_selection');
Derek Jones8ede1a22011-10-05 13:34:52 -0500542
543Private Methods and Variables
544=============================
545
546Methods and variables that are only accessed internally by your class,
547such as utility and helper functions that your public methods use for
548code abstraction, should be prefixed with an underscore.
549
550::
551
Derek Jones129c1812011-10-05 17:15:44 -0500552 convert_text() // public method
553 _convert_text() // private method
Derek Jones8ede1a22011-10-05 13:34:52 -0500554
555PHP Errors
556==========
557
558Code must run error free and not rely on warnings and notices to be
559hidden to meet this requirement. For instance, never access a variable
560that you did not set yourself (such as $_POST array keys) without first
561checking to see that it isset().
562
563Make sure that while developing your add-on, error reporting is enabled
564for ALL users, and that display_errors is enabled in the PHP
565environment. You can check this setting with::
566
Derek Jones129c1812011-10-05 17:15:44 -0500567 if (ini_get('display_errors') == 1)
568 {
569 exit "Enabled";
570 }
Derek Jones8ede1a22011-10-05 13:34:52 -0500571
572On some servers where display_errors is disabled, and you do not have
573the ability to change this in the php.ini, you can often enable it with::
574
575 ini_set('display_errors', 1);
576
577**NOTE:** Setting the
578`display_errors <http://us.php.net/manual/en/ref.errorfunc.php#ini.display-errors>`_
579setting with ini_set() at runtime is not identical to having it enabled
580in the PHP environment. Namely, it will not have any effect if the
581script has fatal errors
582
583Short Open Tags
584===============
585
586Always use full PHP opening tags, in case a server does not have
587short_open_tag enabled.
588
Derek Jones129c1812011-10-05 17:15:44 -0500589**INCORRECT**::
Derek Jones8ede1a22011-10-05 13:34:52 -0500590
Derek Jones129c1812011-10-05 17:15:44 -0500591 <? echo $foo; ?>
592
593 <?=$foo?>
594
595**CORRECT**::
596
597 <?php echo $foo; ?>
Derek Jones8ede1a22011-10-05 13:34:52 -0500598
599One Statement Per Line
600======================
601
602Never combine statements on one line.
603
Derek Jones129c1812011-10-05 17:15:44 -0500604**INCORRECT**::
Derek Jones8ede1a22011-10-05 13:34:52 -0500605
Derek Jones129c1812011-10-05 17:15:44 -0500606 $foo = 'this'; $bar = 'that'; $bat = str_replace($foo, $bar, $bag);
607
608**CORRECT**::
609
610 $foo = 'this';
611 $bar = 'that';
612 $bat = str_replace($foo, $bar, $bag);
Derek Jones8ede1a22011-10-05 13:34:52 -0500613
614Strings
615=======
616
617Always use single quoted strings unless you need variables parsed, and
618in cases where you do need variables parsed, use braces to prevent
619greedy token parsing. You may also use double-quoted strings if the
620string contains single quotes, so you do not have to use escape
621characters.
622
Derek Jones129c1812011-10-05 17:15:44 -0500623**INCORRECT**::
Derek Jones8ede1a22011-10-05 13:34:52 -0500624
Derek Jones129c1812011-10-05 17:15:44 -0500625 "My String" // no variable parsing, so no use for double quotes
626 "My string $foo" // needs braces
627 'SELECT foo FROM bar WHERE baz = \'bag\'' // ugly
628
629**CORRECT**::
630
631 'My String'
632 "My string {$foo}"
633 "SELECT foo FROM bar WHERE baz = 'bag'"
Derek Jones8ede1a22011-10-05 13:34:52 -0500634
635SQL Queries
636===========
637
638MySQL keywords are always capitalized: SELECT, INSERT, UPDATE, WHERE,
639AS, JOIN, ON, IN, etc.
640
641Break up long queries into multiple lines for legibility, preferably
642breaking for each clause.
643
Derek Jones129c1812011-10-05 17:15:44 -0500644**INCORRECT**::
Derek Jones8ede1a22011-10-05 13:34:52 -0500645
Derek Jones129c1812011-10-05 17:15:44 -0500646 // keywords are lowercase and query is too long for
647 // a single line (... indicates continuation of line)
648 $query = $this->db->query("select foo, bar, baz, foofoo, foobar as raboof, foobaz from exp_pre_email_addresses
649 ...where foo != 'oof' and baz != 'zab' order by foobaz limit 5, 100");
650
651**CORRECT**::
652
653 $query = $this->db->query("SELECT foo, bar, baz, foofoo, foobar AS raboof, foobaz
654 FROM exp_pre_email_addresses
655 WHERE foo != 'oof'
656 AND baz != 'zab'
657 ORDER BY foobaz
658 LIMIT 5, 100");
Derek Jones8ede1a22011-10-05 13:34:52 -0500659
660Default Function Arguments
661==========================
662
663Whenever appropriate, provide function argument defaults, which helps
664prevent PHP errors with mistaken calls and provides common fallback
665values which can save a few lines of code. Example::
666
667 function foo($bar = '', $baz = FALSE)
668