An MVC Framework
An MVC Framework

The Controller


For every action, there is an equal and opposite reaction.
- Newton's Third Law of Motion

In the HTTP domain space every Request has a Response. And whether it's explicit or implied, every HTTP server has a Controller.

This Framework as a split Controller. The first part is the Dispatcher which processes the Request, sets the appropriate environment and calls the Action. The second part is the actual Action.

The Dispatcher

description coming soon ...

Initialize Defaults

	
	// track process time
	$tm_in = microtime(true);
	
	chdir(dirname(__FILE__));
	chdir("..");
	
	// set UTF-8 mode
	mb_internal_encoding("UTF-8");
	mb_http_output("UTF-8");
	mb_http_input("UTF-8");
	mb_language("uni");
	mb_regex_encoding("UTF-8");
	
	// set built-in defaults
	$GLOBALS["basepath"] = getcwd();
	$GLOBALS["default_action"] = "IndexAction";
	$GLOBALS["default_func"] = "index";
	$GLOBALS["template"] = "index.html";
	$GLOBALS["wrapper_template"] = "wrapper.html";
	$GLOBALS["title"] = "Site Name";
	$GLOBALS["submit_button_name"] = "submitbtn";
	$GLOBALS["param_separator"] = "/";
	$GLOBALS["timezone"] = "America/New_York";
	$GLOBALS["require_session"] = false;
	$GLOBALS["require_valid_user"] = false;
	// ----- $GLOBALS["DEBUG"] = true;
	//define("DEBUG", true);
	define("LOGTIME", true);
	
	// initialize global metadata array
	$GLOBALS["metadata"] = array();
	$GLOBALS["metadata"]["Databases"] = array();	
	@include 'database.cfg.inc';	// load database connection info

	@include 'default.cfg.inc';	// used to override built-in defaults
	include 'cntlrs/utils.inc';
	
	$GLOBALS["actions"] = array();
	@include 'actions.inc';		// add in any predefined actions
	
	$GLOBALS["url_map"] = array();
	@include 'url_map.inc';

	// set request metadata
	$GLOBALS["method"] = $_SERVER["REQUEST_METHOD"];
	$GLOBALS["uri"] = $_SERVER["REQUEST_URI"];
	$GLOBALS["referer"] = $_SERVER["HTTP_REFERER"];
	$GLOBALS["remote_addr"] = $_SERVER["REMOTE_ADDR"];
	$GLOBALS["user_agent"] = $_SERVER["HTTP_USER_AGENT"];
	$GLOBALS["https"] = @$_SERVER["HTTPS"];
	$GLOBALS["call_stack"] = array();
	$GLOBALS["stylesheets"] = array();
	$GLOBALS["javascripts"] = array();
	$GLOBALS["in_save"] = array();
	$GLOBALS["in_validate"] = array();
	
	// load default timezone
	date_default_timezone_set($GLOBALS["timezone"]);
	

Load up $_GET

	// load $_GET since it was bypassed on fastcgi
	$pos = strpos( $_SERVER["REQUEST_URI"], "?");
	
	if( $pos !== false ) {
		
		$uri = substr( $_SERVER["REQUEST_URI"], 0, ($pos) );
		
		$tmp = explode("&", substr($_SERVER["REQUEST_URI"], $pos+1 ));
		foreach( $tmp as $pair) {
			$pos = strpos($pair, "=");
			if( $pos !== false ) {
				$_GET[substr($pair, 0, $pos)] = urldecode(substr($pair, $pos+1));
			} else {
				$_GET[$pair] = true;
			}
		}
	} else {
	
		
		$uri = substr( $_SERVER["REQUEST_URI"], 0 );
	}
	

Log Request

	// TODO - extract out variables that should be persistent and move to COOKIES
	
	// log request ---------------------------------------------------------------
	$fdlog = fopen("logs/process.php.log", "a");
	if( $fdlog !== false ) {
		$string = "[" . date("r") . "] | ";
		$string .= $_SERVER["REMOTE_ADDR"] . "," . @$_SERVER["HTTP_X_FORWARDED_FOR"] . "," . @$_SERVER["HTTP_CLIENT_IP"];
		if( isset($_COOKIE["PHPSESSID"]) ) {
			$string .= " :" . $_COOKIE["PHPSESSID"];
		}
		$string .= " | ";
		$string .= $_SERVER["HTTP_REFERER"] . " | ";
		if( $GLOBALS["https"] == "on" ) {
			$string .= "HTTPS:";
		}
		$string .= $_SERVER["REQUEST_METHOD"];
		if( $_SERVER["REQUEST_METHOD"] == "POST" ) {
			$string .= "[" . @$_POST[$GLOBALS["submit_button_name"]] . "]";
		}
		$string .= " " . $_SERVER["SERVER_NAME"];
		$string .= $_SERVER["REQUEST_URI"];
		$string .= "\n";
		fwrite($fdlog, $string);
		fclose($fdlog);
	}
	// ----------------------------------------------------------------------------
	

Process Request

	// process request
	
		// ******** Setup environment and load all required classes *****
		// load required core classes
		require 'cntlrs/response.class.inc';
		require 'cntlrs/view.class.inc';
		require 'cntlrs/action.class.inc';
		require 'cntlrs/crud.action.class.inc';
		require 'cntlrs/index_action.class.inc';
		
		// load User model
		//require 'models/user.class.inc';	// now done with _autoload()
		// create "Anonymous" user
		$GLOBALS["User"] = new User();
		$GLOBALS["User"]->data["username"] = "Anonymous";
		// **************************************************************
			
		// ********* Check for an API call ******************************
		$api_flag = false;
		// strip "api:" if found
		if( strpos( $uri, "api:") !== false ) {
			$api_flag = true;
			$uri = str_replace("api:", "", $uri);	// str_replace was chosen over substr for
													// flexibility in the event "api:" wasn't in front
		}
		// TODO - check for USER_AGENT is XMLHTTP or WebSocket
		// also an indicator of "api:"
		
		// **************************************************************
		
		// ********* Check for an iFrame call ******************************
		$iframe_flag = false;
		// strip "iframe:" if found
		if( strpos( $uri, "iframe:") !== false ) {
			$iframe_flag = true;
			$uri = str_replace("iframe:", "", $uri);	// str_replace was chosen over substr for
													    // flexibility in the event "iframe:" wasn't in front
		}
		// **************************************************************
		
	

Decode Request URI and Call Action

	$action = "";
// ***** match URI to URI_Table ***************************************
	
	foreach( $GLOBALS["url_map"] as $urltag => $urlaction ) {

		if( strncmp( $urltag, $uri, strlen($urltag)) == 0 ) {
			$action = $urlaction;
			
			$uri = substr( $uri, strlen($urltag));
			
			$GLOBALS["call_stack"] = array_merge( $GLOBALS["call_stack"], array_values( array_filter( explode($GLOBALS["param_separator"], $urltag))) );
		}

	}
	
	// gen tokens from URI
	$tmp = explode($GLOBALS["param_separator"], $uri);
	if( is_array($tmp) ) {
		$tokens = array_values( array_filter($tmp) );
	} else {
		$tokens = array();
	}

	if( empty($action) ) {
		// no action found in URI_Table
		$action = $GLOBALS["default_action"];
	}
// ********************************************************************

	echo callAction( $action, $tokens, $GLOBALS["method"], $api_flag, $iframe_flag )->GetResponse();
	
	if( LOGTIME ) {
		$tm_out = microtime(true);
		$tm_diff = $tm_out - $tm_in;
		error_log("Process time: " . $tm_diff . " secs.");
	}
	
	

The Action Class

description coming soon ...

The CrudAction Class

description coming soon ...



Back to Top
Top

© 2012 and beyond Lawrence L Hovind - All Rights Reserved