This is another thread from our forums which we are closing down soon.
This script will count the number of lines in all of your source files recursively. Just place it in any folder and point your browser to it and it will count all the lines including sub directories.
It might run out of memory if your application is huge and your PHP memory limit is low. For me, it counted 97,000 lines in our last project with no problems.
You also have an option to exclude file extensions and directories.
The other thing about this script is that it is a great little example of composite design pattern in action; every directory is an object that will count all the lines (in the files) in it and asks it’s sub directories to do the same, then the sub directories also repeat the same process.
<?php /** * Counts the lines of code in this folder and all sub folders * You may not sell this script or remove these header comments * @author Hamid Alipour, http://blog.code-head.com/ **/ define('SHOW_DETAILS', true); class Folder { var $name; var $path; var $folders; var $files; var $exclude_extensions; var $exclude_files; var $exclude_folders; function Folder($path) { $this -> path = $path; $this -> name = array_pop( array_filter( explode(DIRECTORY_SEPARATOR, $path) ) ); $this -> folders = array(); $this -> files = array(); $this -> exclude_extensions = array('gif', 'jpg', 'jpeg', 'png', 'tft', 'bmp', 'rest-of-the-file-extensions-to-exclude'); $this -> exclude_files = array('count_lines.php', 'rest-of-the-files-to-exclude'); $this -> exclude_folders = array('_private', '_vti_bin', '_vti_cnf', '_vti_log', '_vti_pvt', '_vti_txt', 'rest-of-the-folders-to-exclude'); } function count_lines() { if( defined('SHOW_DETAILS') ) echo "/Folder: {$this -> path}...\n"; $total_lines = 0; $this -> get_contents(); foreach($this -> files as $file) { if( in_array($file -> ext, $this -> exclude_extensions) || in_array($file -> name, $this -> exclude_files) ) { if( defined('SHOW_DETAILS') ) echo "#---Skipping File: {$file -> name};\n"; continue; } $total_lines += $file -> get_num_lines(); } foreach($this -> folders as $folder) { if( in_array($folder -> name, $this -> exclude_folders) ) { if( defined('SHOW_DETAILS') ) echo "#Skipping Folder: {$folder -> name};\n"; continue; } $total_lines += $folder -> count_lines(); } if( defined('SHOW_DETAILS') ) echo "\n Total lines in {$this -> name}: $total_lines;\n\n"; return $total_lines; } function get_contents() { $contents = $this -> _get_contents(); foreach($contents as $key => $value) { if( $value['type'] == 'Folder' ) { $this -> folders[] = new Folder($value['item']); } else { $this -> files[] = new File ($value['item']); } } } function _get_contents() { $folder = $this -> path; if( !is_dir($folder) ) { return array(); } $return_array = array(); $count = 0; if( $dh = opendir($folder) ) { while( ($file = readdir($dh)) !== false ) { if( $file == '.' || $file == '..' ) continue; $return_array[$count]['item'] = $folder .$file .(is_dir($folder .$file) ? DIRECTORY_SEPARATOR : ''); $return_array[$count]['type'] = is_dir($folder .$file) ? 'Folder' : 'File'; $count++; } closedir($dh); } return $return_array; } } // Class class File { var $name; var $path; var $ext; function File($path) { $this -> path = $path; $this -> name = basename($path); $this -> ext = array_pop( explode('.', $this -> name) ); } function get_num_lines() { $count_lines = count(file($this -> path)); if( defined('SHOW_DETAILS') ) echo "|---File: {$this -> name}, lines: $count_lines;\n"; return $count_lines; } } // Class $path_to_here = dirname(__FILE__) .DIRECTORY_SEPARATOR; $folder = new Folder($path_to_here); echo 'Total lines of code: ' .$folder -> count_lines() ."\n\n"; ?>
Hamid Alipour is a partner in Codehead, LLP with his wife, Tess. Hamid speaks 12 markup and programming languages [Yes, 12: PHP, CSS, Ajax, JavaScript, HTML/XHTML, Java, Python, C/C++, ASP, Visual Basic, Scheme and Action Script]; has a penchant for solving the unsolvable; an affinity for clean, hand-written code and is a Zend Certified 
Hamid,
Nice script, but would be even better if it could separately count commented lines (and blank lines) vs. actual lines of PHP source.
-Dave
Comment
Hi Dave, thanks, and I agree, I might write a new one that works like that, I need the time first
Comment