技术产品   

从LazyPhp说起

时间:2012-12-27 14:22:00

最近一周一直在看PHP. 开始慢慢梳理基本语法.顺便看了一个比较入门Php轻框架-LazyPhp.

在NetBeans上Coding 过程中深感Php作为弱语言在语法层次和perl有很多相似之处.当然现在也有很多动态网页脚本语言Perl,Asp,Jsp等.它里面的语法大量借鉴了C和Perl.首先Php是开源的.同样对于一个动态网站经典配置Php+Apache+MySQl这样完全免费并且跨平台的组合.成功构建类似MediaWiki[维基百科]和WordPress Blog系统就是很好例子.

如果你熟悉Perl你会发现Php的函数库远远多于Perl.最重要的是PHP中完全没有nameSpace命名空间的概念.这难免导致了在Coding时必须尽力避免模块间命名上冲突.Php在数据库访问上也几乎支持所有流行的数据库.Java是通过JDBC访问数据库.通过不同数据库厂商提供驱动访问数据库.相对来说接口比较统一.但我看了Php 在不同的数据库Demo发现时采用不同访问接口.数据访问这部分代码可通用性不高.

在底层运作上Php采用的是 Web服务器(Apache,Nginx)->Php 解析器解释脚本并回显. 而JSp采用的是Web服务器(Apache,Nginx)->容器->java虚拟机解析Servlet并回显.可以明显看到Php自身缺乏多层结构的支持.相对于已经具有成熟框架和开发工具支持的java.Php自身结构上缺陷。在大型复杂的项目开发和维护上显得比较困难.但反过来Php语法简单.更适合于快速开发.成本和学习曲线偏低.能够快速响应需求变化./Java在规模上则偏向于于开发大型的应用系统,易维护、可复用性较高特点..只能说尺有所短寸有所长.

看到有人在网上总结了目前动态网页脚本语言一些特点总结.比较同意 如下[用过Java/RoR]:

Php –Java – Ruby –Python:

Php: Quick and Dirty

Java: Beauty and Slowly

Ruby: Quick and Beauty

Python:Quick and Simple

曾使用过Asp.net,Jsp,Ruby Of Rails.当然给我体验最好莫过于ROR了.

在梳理Php基本语法同时.也看项目中使用一个比较入门LazyPhp框架.相对于Zend Php臃肿和庞大.LazyPhp则体现出一个小巧易用基于MVC特点.FrontController+Layout系统+20个常用函数就是全部.当然更多Lazyphp介绍请参考:

LazyPhp Home Page:http://ftqq.com/lazyphp/

LazyPhp3 Download At github: https://github.com/easychen/LazyPHP

从github下载源码.花费一个下去搞清楚里面执行流程.可能是因为LazyPhp太过于小众我一直没有找到很好的基于这个框架的一些Sample demo. 还好Github上下载源码其实就是采用Lazyphp构建第一个网站末班.唯一不同时没有任何内容.

在NetBeans打开LazyPhp源码代码结构如下:

2012-12-17_200226

从LazyPhp介绍来看.Index.php是当前站点所有请求的入口.源码如下:

   1:  <?php
   2:  /* lp app root */
   3:  // ↑____ for aoi . Do Not Delete it.
   4:  /****  load lp framework  ***/
   5:  define( 'DS' , DIRECTORY_SEPARATOR );
   6:  define( 'AROOT' , dirname( __FILE__ ) . DS  );
   7:   
   8:  //ini_set('include_path', dirname( __FILE__ ) . DS .'_lp' ); 
   9:  include_once( '_lp'.DS .'lp.init.php' );
  10:  /**** lp framework init finished ***/

首先在Index中定义两个常量.其中ARoot定义是网站所在的根目录.加载Lazyphp框架_Lp目录下lp.init.php文件.

   1:  <?php
   2:   
   3:  if( !defined('AROOT') ) die('NO AROOT!');
   4:  if( !defined('DS') ) define( 'DS' , DIRECTORY_SEPARATOR );
   5:   
   6:  // define constant
   7:  define( 'IN' , true );
   8:   
   9:  define( 'ROOT' , dirname( __FILE__ ) . DS );
  10:  define( 'CROOT' , ROOT . 'core' . DS  );
  11:   
  12:  // define 
  13:  error_reporting(E_ALL^E_NOTICE);
  14:  ini_set( 'display_errors' , true );
 

定义两个常量.其中Root框架根目录,CRoot为框架核心目录.并设置当前PHP报错级别为Notice.

   1:  include_once( CROOT . 'lib' . DS . 'core.function.php' );
   2:  @include_once( AROOT . 'lib' . DS . 'app.function.php' );
   3:   
   4:  include_once( CROOT . 'config' .  DS . 'core.config.php' );
   5:  include_once( AROOT . 'config' . DS . 'app.config.php' );

载入框架核心函数即[core.function.php]文件.和站点自定义函数[app.function.php]. 并载入Lazyphp框架当前配置[core.config.php] 站点自身对应配置[app.config.php]文件.

   1:   
   2:  $c = $GLOBALS['c'] = v('c') ? v('c') : c('default_controller');
   3:  $a = $GLOBALS['a'] = v('a') ? v('a') : c('default_action');
   4:   
   5:  $c = basename(strtolower( z($c) ));
   6:  $a =  basename(strtolower( z($a) ));
   7:   
   8:  $post_fix = '.class.php';
   9:   
  10:  $cont_file = AROOT . 'controller'  . DS . $c . $post_fix;
  11:  $class_name = $c .'Controller' ; 
  12:  if( !file_exists( $cont_file ) )
  13:  {
  14:      $cont_file = CROOT . 'controller' . DS . $c . $post_fix;
  15:      if( !file_exists( $cont_file ) ) die('Can\'t find controller file - ' . $c . $post_fix );
  16:  } 

读取请求中对应参数C和A对应Controller&Action.然后在ARoot也就是站点Controller目录下找对应名称Class.php文件.并判断是否存在?如果不存在则调用CRoot也就是Lazyphp框架默认的Controller目录对应的Default.class.php文件.对应的default_controller和default_action值可以再_lp->core->config->core.config.php文件中修改 默认值如下:

   1:  <?php
   2:   
   3:  $GLOBALS['config']['default_controller'] = 'default';
   4:  $GLOBALS['config']['default_action'] = 'index';
   5:  $GLOBALS['config']['default_language'] = 'zh_cn';
   6:   
   7:   

回到lp.init.php中来继续之往下执行:

   1:  require_once( $cont_file );
   2:  if( !class_exists( $class_name ) ) die('Can\'t find class - '   .  $class_name );
   3:   
   4:   
   5:  $o = new $class_name;
   6:  if( !method_exists( $o , $a ) ) die('Can\'t find method - '   . $a . ' ');
   7:   
   8:   
   9:  if(strpos($_SERVER['HTTP_ACCEPT_ENCODING'], 'gzip') !== FALSE)  ob_start("ob_gzhandler");
  10:  call_user_func( array( $o , $a ) );

当前站点如果存在对应Controller类文件则会立即载入.并判断当前文件是否存在类?[是一个必须继承app_controller类定义]. 如果不存在则提示…同样对应要执行类方法也如此.当根据找到的Contrller类和对应名称的Action的方法执行代码.

如果在index.php请求如下链接:http://localhost/index.php 会看到如下页面:

2012-12-17_205100

根据请求链接.发现没有指定任何Controller和Action定义也就是对应请求参数[?c=xxx&a=xxx].那么则对应执行的是LazyPhp框架默认的Control目录default.class.php文件和该文件定义Index方法.代码如下:

   1:  class defaultController extends appController
   2:  {
   3:      function __construct()
   4:      {
   5:          parent::__construct();
   6:      }
   7:      
   8:      function index()
   9:      {
  10:          $data['title'] = $data['top_title'] = '首页';              
  11:          render( $data );
  12:      }

defaultController类的index方法看起来非常简单,不过是设置了数组$data['titile']的值为'首页',然后就调用render()函数,并将数组$data作为调用参数.走到这你会发现.Index.php本质就是一个FrontController[前段控制器].所有动态请求都会经过FC.FC拿到请求后根据Controller和Action对请求进行分组,并调用对应的Controller模块下Action方法来进行处理.实质上所有请求的分发是通过是通过气请求参数C->指定对应Controller和A->Controller定义对应Action方法:

/index.php?c=user&a=login

在netbeans中快捷Ctrl=B 继续查看render函数定义发现

2012-12-17_210813

发现两个定义找到LazyPhp3下文件 Render函数定义如下:

   1:  // render functiones
   2:  function render($data = NULL, $layout = NULL, $sharp = 'default') {
   3:      if ($layout == null) {
   4:          if (is_ajax_request()) {
   5:              $layout = 'ajax';
   6:          } elseif (is_mobile_request()) {
   7:              $layout = 'mobile';
   8:          } else {
   9:              $layout = 'web';
  10:          }
  11:      }
  12:   
  13:      $GLOBALS['layout'] = $layout;
  14:      $GLOBALS['sharp'] = $sharp;
  15:   
  16:      $layout_file = AROOT . 'view/layout/' . $layout . '/' . $sharp . '.tpl.html';
  17:      if (file_exists($layout_file)) {
  18:          @extract($data);
  19:          require( $layout_file );
  20:      } else {
  21:          $layout_file = CROOT . 'view/layout/' . $layout . '/' . $sharp . '.tpl.html';
  22:          if (file_exists($layout_file)) {
  23:              @extract($data);
  24:              require( $layout_file );
  25:          }
  26:      }
  27:  }

首先判断所有采用站点采用布局类型.默认值是Web.则找到对应ARoot站点定义的View/Layout/Web目录下.$sharp对应默认值为default.被载入的网页模板内容被显示出来了.如上就是整个Lazyphp框架处理请求执行流程.在来看看PhpLazy3 文件结构目录:

2012-12-17_211738

对应目录设置如下:

   1:  LazyPHP
   2:  │  index.php    //项目入口文件
   3:  │  README.md    //LazyPHP说明文件,Markdown格式
   4:  
   5:  ├─config        //项目配置
   6:  │      app.config.php           //项目配置文件
   7:  │      db.config.php            //项目数据库配置文件
   8:  
   9:  ├─controller    //项目逻辑控制所在文件夹
  10:  │      app.class.php            //类
  11:  default.class.php        //项目默认控制器
  12:  
  13:  ├─lib           //项目函数库
  14:  │      app.function.php         //函数库
  15:  
  16:  ├─local         //项目本地化配置
  17:  │      zh_cn.lang.php           //中文
  18:  
  19:  ├─model         //项目模块
  20:  │      README            //说明,空文件
  21:  
  22:  ├─view          //项目页面显示模板(详细文件列表略)
  23:  
  24:  ├─static        //项目静态文件,包括css,js代码及图像.
  25:  
  26:  ├─test          //JSUnit及PHPUnit测试框架文件(详细文件列表略)
  27:  
  28:  └─_lp           //LazyPHP3框架
  29:      │  lp.init.php              //框架入口
  30:      │  st.init.php              //simpleTest的入口
  31:  
  32:      ├─core      //框架核心
  33:      │  ├─config
  34:      │  │      core.config.php   //框架配置文件
  35:      │  │      
  36:      │  ├─controller
  37:      │  │      core.class.php    //框架逻辑控制类
  38:      │  │      
  39:      │  ├─lib
  40:      │  │      core.function.php //核心函数库
  41:      │  │      db.function.php   //数据库操作函数
  42:      │  │      db.sae.function.php  //sae数据库操作函数
  43:      │  │      
  44:      │  ├─model   //模块
  45:      │  │      README
  46:      │  │      
  47:      │  └─view    //框架默认模板(详细文件列表略)
  48:  
  49:      └─simpletest //框架测试文件(详细文件列表略)

如上Mark up For Lazy Php

 

来源:PHPchina

Notice: Constant RUNTIME already defined in /srv/html/srccn/news/config.php on line 15 Notice: Constant ROOTDIR already defined in /srv/html/srccn/news/config.php on line 16 Notice: Constant SITEDIR already defined in /srv/html/srccn/news/config.php on line 17 Notice: Constant DATAURL already defined in /srv/html/srccn/news/config.php on line 20 Notice: Constant VERSION already defined in /srv/html/srccn/news/system/kernel.php on line 17 Notice: Constant COREDIR already defined in /srv/html/srccn/news/system/kernel.php on line 18 Fatal error: require(): Cannot redeclare class mysql in /srv/html/srccn/news/system/kernel.php on line 22