KEMBAR78
Best practices tekx | ODP
Best Practices Matthew Weier O'Phinney Zend Framework Lorna Jane Mitchell Ibuildings @lornajane @weierophinney
The Plan Source Control
Coding Standards
Design Patterns
Documentation
Testing
Quality and Continuous Integration
Deployment
Source Control
Source Control Features Version history of all files
Collaboration tool
Authoritative version of a project
Integration point
Using Source Control Create a repository, add project
Check out project
Make changes
Update to get other changes
Commit changes to repo
svn log ------------------------------------------------------------------------ r3 | lornajane | 2010-04-25 10:32:09 +0100 (Sun, 25 Apr 2010) | 1 line adding documentation notes ------------------------------------------------------------------------ r2 | lornajane | 2010-04-22 09:07:56 +0100 (Thu, 22 Apr 2010) | 1 line outlining source control and design patterns sections ------------------------------------------------------------------------ r1 | weierophinney | 2010-03-30 17:37:27 +0100 (Tue, 30 Mar 2010) | 1 line Added readme with outline ------------------------------------------------------------------------
svn diff Index: README.txt =================================================================== --- README.txt  (revision 3) +++ README.txt  (revision 4) @@ -31,12 +35,20 @@ to share ideas to raise profile to be told you're doing it wrong! +  (pulling up examples off our own blogs, if connection allows) Testing (Matthew) QA tools and CI including code analysis, mess detection, etc (Lorna - QA tools; Matthew - CI) +  Static analysis +  code sniffer +  demo examples, find a suitable small codebase (joindin?) +  mess detector +  demo examples +  what else? + Deployment
Source Control Tools Subversion (svn) http://subversion.apache.org/ Git (git) http://git-scm.com/ Bazaar (bzr) http://bazaar.canonical.com/ Mercurial (hg) http://mercurial.selenic.com/
Accessing Source Control IDE Plugins
Trac ( http://trac.edgewall.org/ )
TortoiseSVN TortoiseGit
TortoiseBzr
TortoiseHg
Centralised Source Control user repo user user user
Centralised Source Control Single repo (repository)
Always commit to central
Can branch centrally
Repository Structure (Feature Branches)
Repository Structure (Long-Lived Branches)
Repository Structure (Release Branches)
Distributed Source Control repo repo repo repo repo
Distributed Source Control Many repos
Commit to local repo
Share changes between anywhere
No central point
The Changing Landscape Very active development area
Today's conclusions not valid for long!
Bridges git-svn http://www.kernel.org/pub/software/scm/git/docs/git-svn.html bzr-svn https://launchpad.net/bzr-svn Check out from SVN to local repo
Make as many changes/branches as you like
Push back to SVN
Hosted Solutions GitHub http://github.com/ git Bitbucket http://bitbucket.org/ hg Google Code http://code.google.com/ svn, hg Launchpad https://launchpad.net/ bzr SourceForge http://sourceforge.net/ svn, bzr, hg, git (and cvs)
What If I Don't Have Source Control? Get some :)
Install subversion
Use a hosted solution
Resources Talks at TEK-X Subversion in a Distributed World, Lorna Mitchell
Getting Git, Travis Swicegood (who literally wrote the book)
Both Wednesday afternoon Subversion book http://svnbook.red-bean.com/ Comparison of tools http://en.wikipedia.org/wiki/Comparison_of_revision_control_software
Coding Standards
You don't have a standard when … You always reformat code you get from others
Code you wrote 6 months ago looks different than what you wrote today
Modifying old code often introduces new syntax errors
Answer the following questions: Can you read your own code?
Can others read your code?
Can you read other's code?
Can you switch between code bases easily?
Analogy "Elements of Style" :: Writing Coding Standard :: Development
In sum, coding standards assist in: Maintainability
Collaboration
How CS aids maintainability: Code is structured predictably
How CS aids collaboration Any developer can pick up and easily read existing code
…   which in turn means they can maintain it
…   which de-centralizes who is responsible for the code
…   which means issues and reature requests are resolved faster
It  democratizes  code maintenance
Two pillars of a Coding Standard: Consistency of  file system  layout
Consistency of  code  layout
Ancillary goal: Consistency in naming
Use Public Standards NIH has no place with CS You and your project's needs are not unique
What if you need to consume and potentially help maintain 3rd party libraries?
Benefit from collective knowledge and empirical discoveries
Need more reasons? Objectivity Choices are no longer based on subjective preferences, but on empirical experience. Requirement when hiring or outsourcing Easily judge the candidate's experience and code quality. Compatibility Use a standard that follows that of the libraries you use.
Choices Horde/PEAR/Zend Framework Also: Solar, AdoDB, Doctrine 2, Symfony 2, and more... eZcomponents/ZetaComponents
PHPLIB
Example <?php /** * In Foo/Bar.php */ class   Foo_Bar { const   BAZ   =   'baz' ; protected   $_bat ; public   $bas ; public function   bazBat( $someVar ) { if   ( $someVar ) { echo   'Found' ; } } }
Resources PEAR http://pear.php.net/manual/en/standards.php
http://pear.php.net/manual/en/pear2cs.php Zend Framework http://framework.zend.com/manual/en/coding-standard.html
Design Patterns
A Design Pattern Is ... NOT rocket science
A common way to describe a common problem
Shared language
A problem and solution which is repeated many times
Common across programming languages
Heavily OOP
Some Common Patterns Factory
Registry
Adapter
Decorator
Observer
Factory Has methods to create and return objects
May return different objects
May use complex (and maintainable) logic to work out what to do
Factory Example: Hat Types 1  < ?php 2  3  require_once ( 'hat.php' ); 4  5  class   HatFactory   { 6  public   function   getHat ( $type   =   'woolly' ) { 7  // perform any logic you like here 8  return   new   Hat ( $type ); 9  } 10  } http://www.flickr.com/photos/91524358@N00/2260054061/
Registry Can be a singleton  (but this is not a requirement!)
Register objects here, access from elsewhere
Often a factory/registry combination
Registry Example: Hat Storage 1  < ?php 2  3  class   HatRegistry   { 4  private   $registry ; 5  6  public   function   __construct () { 7  $this -> registry   =   array (); 8  } 9  10  public   function   registerHat ( $key ,   $hat ) { 11  $this -> registry [ $key ] =   $hat ; 12  } 13  14  public   function   fetchHat ( $key ) { 15  return   $this -> registry [ $key ]; 16  } 17  }
Adapter Adapts  a specific interface to fit something else; typically, to provide a common API to related classes/components that have divergent APIs.
Allows the class wrapped by the adapter to exist independently from the component consuming the adapter.
Adapter Example: SOAP to REST Real life example
Client project to deliver SOAP
PHP SOAP 1  < ?php 2  3  require_once ( 'lib/myClass.php' ); 4  5  $server   =   new   SoapServer ( null ,  $options ); 6  $server -> setClass ( &quot;MyClass&quot; ); 7  $server -> handle ();
Adapter Example: SOAP to REST Real life example
Client project to deliver SOAP
Service part-built
Client reads textbook(?)
Client requests REST
Adapter class to the rescue!
Adapter Example: SOAP to REST myClass index.php
Adapter Example: SOAP to REST myClass index.php Adapter
Decorator Wraps another class in order to modify its behavior
Target class doesn't change
Decorating class often implements the same interface(s)
Can be  visually  decorative, not always
Decorator Example 1  < ?php 2  3  interface LabelInterface   { 4  public   function   render (); 5  } 6  7  class   BasicLabel implements LabelInterface   { 8  public   function   render () { 9  return   $this -> label ; 10  } 11  }
Decorator Example 13  abstract   class   LabelDecorator implements LabelInterface   { 14  public   function   __construct ( LabelInterface   $label ) { 15  $this -> label   =   $label ; 16  } 17  } 18  19  class   LabelStarDecorator   extends   LabelDecorator   { 20  public   function   render () { 21  return   '** '  .   $this -> label -> render ()   .   ' **' ; 22  } 23  } 24  25  class   LabelNewLineDecorator   extends   LabelDecorator   { 26  public   function   render () { 27  return   $this -> label -> render ()   .   &quot; \n &quot; ; 28  } 29  } 30  31  class   LabelHyphenDecorator   extends   LabelDecorator   { 32  public   function   render () { 33  return str_replace ( ' ' , '-' , $this -> label -> render ()); 34  } 35  }

Best practices tekx