Edoceo Code Standards

edoceo: Latin "to inform fully, instruct thoroughly"

The standards and styles are broken down by language, in alphabetical order, with common set of standards listed first. Where possible consistency across language boundaries has been chosen over native language style. Alternatives are given when necessary and for backwards compatibility.

Code spread should be minimized, this means keeping the relevant code in one place and in one language when possible. If there is "more than one way to do it" (and there frequently is) the methodology that will communicate the functionality of the code clearest must be chosen. Processor cycles are relatively inexpensive compared to development team hours dedicated to hunting bugs.

Common

These standards used across all code environments unless specifically defined in a language standard.

$Id$ SubVersion Keyword
Must include this keyword in the top five lines of the code file
2 Space Tab
Use two space characters in place of tab. i.e. not ASCII \0x09 but \0x20\0x20.
Use the one true brace style
Conditionals, inline functions (language permitting), loops, nested elements (markup only) and other similar code blocks. Functions (methods) and Class definitions use drop brace.
Comments
Must be placed in every file to describe it's base functionality and must be placed above any class, function or subroutine definition (use cobj: or func:). Extra comments are encouraged, a list of standard comment phrases is listed below, use // @code: comment style.
Constants
Use UPPER_CASE_WIDE_VALUES to define constant values
Functions, Statics and Variables
Use the under_score character, or wide_names rather than CamelCase
Classes and Objects
Use CamelCase for class names and under_score character, or wide_names for methods and properties.

Comments (You can't grep dead trees)

Comments are necessary to document what is happening and for regulatory compliance for the present and future. The use of comments is used in favour of extraneous external documentation. These methods are designed to allow the code to create it's own documentation in the future with simple usage of phpDocumentor and grep.

This sample below describes the comment codes that are encouraged, they are not case sensitive. Comments should be inserted by starting the comment line according to the language specification for a single line comment, followed by a space, a code from the list below including the trailing colon, a space then the text of the comment.

@versionOriginal author's name, subsequent authors place their name directly below this. Include a date in this option as shown below.
@packageName of the project.
@linkPoint to the projects home page.
@sincePunch in the version the modifications were started in.
@todoNotes for required future development of the code.
@deprecatedWhen code pieces are being phased out.
These are not part of phpDocumentor
@hack:This gets the job done now but should not be in the released code, requires futuer cleanup.
@ideaNotes on how to improve the code, deferred feature request.
@specDescirbes a certian code or business logic specification in effect, point to RFCs, policy, etc.
@fsffThis code is terrible or non-functional but highly desired, refactor/fix as necessary - soon!
@copyrightCopyright, if any, on the files contents.

Common commenting techniques will ensure easy to follow and document code.

# find whats wrong
grep -Enr ' fsff: | idea: | note: | todo: ' *

# find useful information
grep -Enr ' @todo | @hack | @idea | @spec '

# Find API notes
grep -Enr ' @param | @method | @return | @var ' *

# What to do next
grep -Enr ' @fsff | @todo | @hack ' *

Examples specific to each language are shown and should clarify use of this methodolgy.

C/C++

Place the required items at the top, follow with any #includes. Prototype every function - small apps should have main() near the top of the core code file with sub routines below.

// $Id$
// auth: Edoceo Developer - 27 May 2003
// file: Example of documentation methods

// note: includes a bunch of PHP like utility functions, make C like script almost
#include "phplikeapi.c"

// func: do_something_neat(int arg1, char* arg2) - Does something really great!
// argv: int arg1 - Number of times to do it
// argv: int arg2 - path of file to do it to
void function do_something_neat(int arg1, char* arg2)
{
	int i = 0;
	
	while (i < arg1)
	{
		... cool code ...
	}
}

// func: main() - we don't take no stinking arguments
int main()
{
	// note: only input is from specific files
	if (pla_is_file("/tmp/cs.xml"))
	{
		do_something_neat(30,"/tmp/cs.xml");
	}
	// note: never errors
	return 0;
}

CSS

Always use the @media directive, always. Place grouped element styles, then specific element styles, then IDs then element classes then general classes. Put one line of white space between the groupings Definitions for element groups, single elements, IDs, element classes and general classes must be in alphabetical order. CSS directives should be placed on one line in alphabetical order. Any comments about a specific element, ID or class should be placed directly above the item.

@media screen
{
  /* Define Element Group Styles */
  a,h1,h2 { border: 1px solid #f00; }

  /* Define Element Styles */
  body { background-color: #fff; margin: 5px; }
  pre { border: 1px solid #ccc; margin: 0px; padding: 0px; }

  /* Then IDs */
  #nav { margin: 20px; }
  #sub { background-color: #333; font-weight: 700; }

  /* Element Classes */
  a.bar { color: #00f; }

  /* General Classes */
  .bf { text-align: center; }
  /* note: field label for forms */
  .fl { text-align: right; white-space: nobreak; }
  .foo { font-weight: 700; }
}

@media print,projection
{
  .br { display: none; visibility: hidden; }
}

HTML, XHTML and XML

  • Must pass basic XML validation
  • If a DTD is present for the document it, of course, must pass this validation.
<Root>
  <Child>TextValue</Child>
</Root>

Java

We rarely originate projects in Java. Use project originators style, fallback to C/C++ and Common.

JavaScript

  • Delcare all global vars at the top and indicate usage, g_ prefix is nice.
  • Ensure cross browser functionality if needed, favour Mozilla DOM
// $Id$
// auth: email@address.com - 2005-05-20
// file: javascript.js - sitewide javascript routines

var g_active_menu; // (int) indicates which is active

function do_some_activity(e,n)
{
	alert('Event ' + e + ' on node ' + n);
	n.style.display = 'none';
	n.style.visibility = 'hidden';
}

PHP

  • Develop with error_reporting(E_ALL)
  • A custom error handler is encouraged
  • Use {require,include}_once, require preferred over include
// $Id$
// auth: email@address.com - 2005-05-20
// file: sample.php - returns the php info output

error_reporting(E_ALL);
require_once('PEAR.php');
require_once('./my_include.php');

phpinfo();

function some_func($one,$two)
{
  if ($one) $x = some_sub_func($one,$two);
  elseif ($two)
  {
    $x = $one + $two;
    other_foo_func($x,$one);
  }
  return $x;
}

PERL

  • use strict; is required
  • Script should run with no warnings under perl -w
  • Define sub's at the top and implement main below.
  • __BEGIN__ and other constructs are placed after the use statements and before any sub's
#!/usr/bin/perl -w
# file: sample.pl - this script does some stuff
use strict;

# note: i like cookies
my $x = get_fresh_baked_cookies('CC');

# func: get_fresh_baked_cookies - returns a new batch of cookies of the specified type
sub get_fresh_baked_cookies
{
  my ($p) = @_;
  my @ret = ();
  # note: spin up a batch of cookies
  for (my $i=0;$i<12;$i++)
  { # this is a dropped brace
    push @ret, $p;
  }
  return @ret;
}

Shell

Most commonly these will be in a BASH shell, Windows scripting should be done in VBScript.

#!/bin/bash
# note: variables are commonly put in all caps in shell scripts
VAR=somevalue

# func: somefunc - does something
function somefunc
{
  return 1
}

VBScript/ASP

  • Must use 'Option Explicit'
  • Use of _ is prefered over CamelCase (for consistency with other languages)
  • VBScript is not case-sensitive so code in lower case
Option Explicit
' file: sample.asp - copies the data from there to here via bits on a wire
dim var,x
set var = server.createobject("something")
' todo: handle the values less than zero
do while (var.condition=true)
  x = var.operation
  if (x.value > 0) then
    ' idea: do something should be error checked
    do_some_function(x)
  end if
loop

' func: do_some_function() reads data and returns a copy
function do_some_function(byref y)
  do_some_function = x + 15
end function

Appendix

File Locations

Unless otherwise necessary in-house software should be created in /opt/edoceo or c:\Program Files\Edoceo, Inc. depending on platform. Library files are component binaries or scripts, aka DLLs and WSC files. Temporary files are ones that can be killed anytime, not important, not sensitive Web files are any content or code to be visible over http.

  • Executeable Files - ./bin
  • Library Files - ./lib/
  • Temporary Files - Use the System location
  • Web Files - System specific location

See Also