Javascript Stack class

January 8, 2010 Comments off

Notice: This class is subject to change.

class Stack:


<script type="text/javascript">

/*[ Creates a new Stack. A Stack is a LIFO (last-in-first-out) data structure. ]*/
var Stack = function()
{
	/*[ Inner array ]*/
	var stack = [];

	/*[ Adds an element to the Stack ]*/
	this.add = function(element) {
		stack.push(element);
		return this;
	};

	/*[ Retrieve the last element from the Stack ]*/
	this.get = function() {
		return stack.pop();
	};

	/*[ Remove the first element from the Stack ]*/
	this.remove = function() {
		stack.pop();
		return this;
	};

	/*[ Retrieve the size of the Stack ]*/
	this.size = function() {
		return stack.length;
	};

	/*[ Check to see whether or not the Stack is empty ]*/
	this.isEmpty = function() {
		return (stack.length == 0);
	};

	/*[ Retrieve the Stack's content ]*/
	this.getStack = function() {
		return stack;
	};
};

</script>
Categories: JavaScript Tags: ,

Javascript Queue class

January 8, 2010 Comments off

Notice: This class is subject to change.

class Queue:


<script type="text/javascript">

/*[ Creates a new Queue. A Queue is a FIFO (first-in-first-out) data structure. ]*/
var Queue = function()
{
	/*[ Inner array ]*/
	var queue = [];

	/*[ Adds an element to the Queue ]*/
	this.add = function(element) {
		queue.push(element);
		return this;
	};

	/*[ Adds an element to the Queue ]*/
	this.get = function(element) {
		return queue.shift();
	};

	/*[ Remove the first element from the Queue ]*/
	this.remove = function() {
		queue.shift();
		return this;
	};

	/*[ Retrieve the size of the Queue ]*/
	this.size = function() {
		return queue.length;
	};

	/*[ Check to see whether or not the Queue is empty ]*/
	this.isEmpty = function() {
		return (queue.length == 0);
	};

	/*[ Retrieve the Queue's content ]*/
	this.getQueue = function() {
		return queue;
	};
};

</script>
Categories: JavaScript Tags: ,

class Syndication

December 19, 2009 Comments off

Notice: This class is subject to change.

interface ISyndication:

<?php

interface ISyndication
{
	function GetBaseTags();
	function GetTitles( $maxLimit );
	function GetEntries( $maxLimit );
}

?>

class FeedReaderBase:

The base class for parsing xml feeds.


<?php

	require_once __DIR__.DIRECTORY_SEPARATOR.'interface.isyndication.php';
/**
 * class FeedReaderBase
 *
 * The base class for parsing xml feeds.
 *
 * @author     	Costin Trifan 
 * @copyright  	2009 Costin Trifan
 * @licence    	MIT License:	http://en.wikipedia.org/wiki/MIT_License
 * @last update	Dec. 2009
 * @version    	1.0
 */
class FeedReaderBase implements ISyndication
{
	private function __clone(){}
	private function __sleep(){}
	private function __wakeup(){}

	final public function __get( $name ) { throw new Exception('Method: "__get" is not allowed in class: '.__CLASS__); }
	final public function __set( $name, $value ) { throw new Exception('Method: "__set" is not allowed in class: '.__CLASS__); }

	/*[[ MUST OVERRIDE ]]*/
	public function GetBaseTags(){}
	public function GetTitles( $maxLimit ){}
	public function GetEntries( $maxLimit ){}
}
/*[ end class ]*/

?>

Read more…

Categories: PHP Tags: ,

Clib – a basic javascript library

December 17, 2009 Comments off

Notice: This class is subject to change.


/**
* Clib - a basic javascript library
*
* @author     Costin Trifan 
* @copyright  2009 Costin Trifan
* @licence    MIT License http://en.wikipedia.org/wiki/MIT_License
* @version    1.0
* 
* Permission is hereby granted, free of charge, to any person
* obtaining a copy of this software and associated documentation
* files (the "Software"), to deal in the Software without
* restriction, including without limitation the rights to use,
* copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the
* Software is furnished to do so, subject to the following
* conditions:
* 
* The above copyright notice and this permission notice shall be
* included in all copies or substantial portions of the Software.
* 
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
* OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
* NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
* HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
* WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
* FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
* OTHER DEALINGS IN THE SOFTWARE.
============================================================*/


/**
 * PROTOTYPES
 *
 * @see $().ajax()
 */
if ( ! Array.prototype.inArray )
{
    Array.prototype.inArray = function ( theArray ) {
	    var i;
	    for (i=0; i < this.length; i++) {
		    if (this[i] === theArray) {
			    return true;
		    }
	    }
	    return false;
    };
}





/**
 * Clib library - Simple Ajax/Dom/Events/Cookie library
 *
 */
(function()
{

/******************************
*       AJAX RELATED
******************************/

    var xhr = null; /*[ will hold the instance of the XmlHttp object ]*/

    var _createRequest = function()
    {
        try { return new XMLHttpRequest ; } catch(e) {}
        try { return new ActiveXObject('MSXML2.XMLHTTP.3.0') ; } catch(e) {}
        try { return new ActiveXObject('MSXML2.XMLHTTP') ; } catch(e) {}
        try { return new ActiveXObject('Microsoft.XMLHTTP') ; } catch(e) { throw new Error("Details: AJAX is not supported!"); }
    };

    /**
     * Create an image loader
     * @return object   the created DOM Element
     */
    var _createImageLoader = function( imgSrc, parentCtl, loadingText )
    {
        var el = document.createElement("img");
        with (el)
        {
            setAttribute("src", imgSrc);
            setAttribute("title", loadingText);
            setAttribute("alt", loadingText);
            style.width = 'auto';
            style.height = 'auto';
            style.display = 'block';
        }
        parentCtl.appendChild(el);
        return el;
    };

/*>> End AJAX related stuff *******************************************************************************/




    /**
     * Populate the this.elements array
     * @access private
     */
    function _$( els )
    {
        this.elements = [];

        for (var i= 0; i < els.length; ++i)
        {
            var e = els[i];
            if (typeof(e) === "string") {
                e = document.getElementById(e);
            }
            this.elements.push(e);
        }

    }

    _$.prototype =
    {

/*==============================
 * UTILITY
==============================*/


        /**
         * Check to see whether the provided object is an array
         * @return bool
         */
        isArray : function ( obj )
        {
           return (obj.constructor.toString().indexOf("Array") >= 0 );
        },


        /**
         * Execute a given function for each of the elements from the this.elements array
         * @return this
         */
        each : function( fn )
        {
            if (this.elements.length == 0) { return this; }

            for (var i= 0; i < this.elements.length; ++i)
            {
                fn.call(this, this.elements[i]);
            }
            return this;
        },



/*==============================
 * COOKIE
==============================*/

        /*[ Source: http://www.dustindiaz.com/top-ten-javascript/ ]*/
        getCookie : function( name )
        {
	        var start = document.cookie.indexOf( name + "=" );
	        var len = start + name.length + 1;
	        if ( ( !start ) && ( name != document.cookie.substring( 0, name.length ) ) ) {
		        return null;
	        }
	        if ( start == -1 ) return null;
	        var end = document.cookie.indexOf( ';', len );
	        if ( end == -1 ) { end = document.cookie.length; }
	        return unescape( document.cookie.substring( len, end ) );
        },

        setCookie : function( name, value, expires, path, domain, secure )
        {
	        var today = new Date();
	        today.setTime( today.getTime() );
	        if ( expires ) { expires = expires * 1000 * 60 * 60 * 24; }
	        var expires_date = new Date( today.getTime() + (expires) );

	        document.cookie = name+'='+escape( value )
		                        + ( expires ? ';expires='+expires_date.toGMTString() : '' )
		                        + ( path ? ';path=' + path : '' )
		                        + ( domain ? ';domain=' + domain : '' )
		                        + ( secure ? ';secure' : '' );
        },

        deleteCookie : function( name, path, domain )
        {
	        if ( this.getCookie( name ) )
	        {
	            document.cookie = name + '=' +
			        ( (path) ? ';path=' + path : '') +
			        ( (domain) ? ';domain=' + domain : '' ) +
			        ';expires=Thu, 01-Jan-1970 00:00:01 GMT';
            }
        },




/*==============================
 * EVENTS
==============================*/
        
        /**
         * Attach an event listener to each of the elements from the this.elements array
         * @return this
         */
        on : function( type, fn )
        {
            var _add = function( el )
            {
                if (window.addEventListener) {
                    el.addEventListener(type, fn, false);
                }
                else if (window.attachEvent) {
                    el.attachEvent("on"+type, fn);
                }
            };
            this.each(function(el) { _add(el); });
            return this;
        },


        /**
         * Remove an event listener from each of the elements of the this.elements array
         * @return this
         */
        removeEvent : function( type, fn )
        {
            var _remove = function( el )
            {
                if (window.removeEventListener) {
                    el.removeEventListener(type, fn, false);
                }
                else if (window.detachEvent) {
                    el.detachEvent("on"+type, fn);
                }
            };
            this.each(function(el) { _remove(el); });
            return this;
        },


        /**
         * Prevent the default action from occurring
         * @return this
         */
        preventDefault : function( ev )
        {
            ev = ev || window.event;
            if (ev.preventDefault) {
                ev.preventDefault();
            }
            else {
                ev.returnValue = false;
            }
            return this;
        },


        /**
         * Stop the propagation of the event
         * @return this
         */
        stopPropagation : function( ev )
        {
            ev = ev || window.event;
            if (ev.stopPropagation) {
                ev.stopPropagation();
            }
            else {
                ev.cancelBubble = true;
            }
            return this;
        },


        /**
         * Prevent the default action from occurring
         * @return this
         */
        stopEvent : function( ev )
        {
            this.preventDefault( ev );
            this.stopPropagation( ev );
            return this;
        },





/*==============================
 * DOM
==============================*/


        /**
         * Check to see whether or not a given element has a class applied
         * @return bool
         */
        hasClass : function( cssClass )
        {
            var pattern = new RegExp("(^| )" +cssClass+ "( |$)");

            this.each(function(el) {
                if (pattern.test(el.className)) { return true; }
            });
            return false;
        },

        /**
         * Remove a class from the selected objects
         * @return this
         */
        removeClass : function( cssClass )
        {
            var pattern = new RegExp("(^| )" +cssClass+ "( |$)");
            this.each(function(el) {
                el.className = el.className.replace(pattern, "$1");
                el.className = el.className.replace(/ $/, "");
            });
            return this;
        },

        /**
         * Add a given class to selected elements
         * @return this
         */
        addClass : function( cssClass )
        {
            var self = this;
            this.each(function(el) {
                if ( ! self.hasClass(cssClass))
                {
                    if (el.className == "") { el.className = cssClass; }
                    else { el.className += " " + cssClass; }
                }
            });
            return this;
        },


        /**
         * Replace all elements from the this.elements array with the ones that match the regex pattern
         * @return this
         */
        getByClass : function( searchClass, parent, searchInTag )
        {
            // reset main array
            this.elements = [];

            if ( parent == null ) {
                parent = document;
            }
            if ( searchInTag == null ) {
                searchInTag = '*';
            }

            var els = parent.getElementsByTagName(searchInTag);
            var elsLen = els.length;
            var pattern = new RegExp('(^|\\\\s)'+searchClass+'(\\\\s|$)');

            for (i = 0, j = 0; i < elsLen; i++)
            {
                if ( pattern.test(els[i].className) )
                {
                    this.elements.push( els[i] );
                    j++;
                }
            }
            return this;
        },


        /**
         * Replace all elements from the this.elements array with the ones that match the regex pattern
         * @return this
         */
        getByTags : function( /*[ as Array ]*/searchTags, /*[ as Object ]*/parent )
        {
            if ( ! this.isArray(searchTags)) {
                throw new Error("The getByTags function expects the first argument to be an Array!");
            }

            if (searchTags.length == 0) { return this; }

            // temp array - holds the elements that match the regex
            var tempArr = [];

            // reset main array
            this.elements = [];

            if ( parent == null ) { parent = document; }


            for (var i= 0; i < searchTags.length; ++i)
            {
                var tag = searchTags[i];

                var els = parent.getElementsByTagName(tag);
            }



            var elsLen = els.length;
            var pattern = new RegExp('(^|\\\\s)'+searchClass+'(\\\\s|$)');

            for (i = 0, j = 0; i < elsLen; i++)
            {
                if ( pattern.test(els[i].className) )
                {
                    this.elements.push( els[i] );
                    j++;
                }
            }
            return this;
        },


        /**
         * Set the inner text to all of the elements from this.elements array
         * @return this
         */
        text : function( txt )
        {
            /*[ SET ]*/
            if (txt)
            {
                this.each(function(e) {
                    e.innerHTML = txt;
                });
                return this;
            }
            /*[ GET ]*/
            else { return this.elements[0].innerHTML; }
        },


        /**
         * Set/Get the value to all of the elements from this.elements array
         * @return this | mixed
         */
        value : function( txt )
        {
            /*[ SET ]*/
            if (txt)
            {
                this.each(function(e) {
                    e.value = txt;
                });
                return this;
            }
            /*[ GET ]*/
            else { return this.elements[0].value; }
        },

        /**
         * Set the css style property to all of the elements from this.elements array
		 *
		 * @param object properties	A key value pair object literal with the properties and values to apply to the selected object
         * @return this
         */
        css : function( /*[ as object ]*/properties )
        {
            this.each(function(el) {
				for (var p in properties)
                	el.style[ p ] = properties[ p ];
            });
            return this;
        },


        /**
         * Set the css style property to an element
         * @return this
         */
        setStyle : function( element, property, value )
        {
            element.style[ property ] = value;
            return this;
        },


        /**
         * Retrieve the computed style attribute of the element
         * @return string
         */
        getStyle : function( element, property )
        {
            var comp_style = null;

            if (window.getComputedStyle) {
                comp_style = window.getComputedStyle(element,null).getPropertyValue(property);
            }
            else {
                if (typeof(element) != "undefined") {
                    comp_style = element.currentStyle;
                    return comp_style[property];
                }
            }
            return comp_style;
        },






/*==============================
 * AJAX
==============================*/


        /**
         * Abort the active request
         * @return this
         */
        _abort : function( xhr )
        {
            xhr.abort();
			xhr = null;
            return this;
        },


        ajax : function( method, uri, /*[ as object ]*/options, onSuccess, onFailure )
        {
            method = method.toUpperCase();

			var self = this;

            /*[ Check and validate method ]*/
            var allow_methods = ["GET", "HEAD", "POST"];

            if ( ! allow_methods.inArray(method)) {
                throw new Error("The provided method: "+ method.toString() +" is not supported!");
            }


            xhr = _createRequest();

            if (xhr == null) { return this; }


            if ( ! options ) { options = {}; }
            /*[ Set options ]
            
                options = {
                    async       : false | true (default)
                    timeout     : null | 3000 (default)
                    postData    : string | null (default) // when making POST requests
                    label       : string | null (default) // when making HEAD requests
                    cache       : true | false (default)  // when making GET requests, whether or not to cache server's response
                    showLoader  : true | false (default)
                    imgSrc      : string | null (default) // the path to the image to be displayed
                    parentCtl   : DOMElement | null (default)  // the element that will append the image loader
                    loadingText : 'Loading...' (default) // the alternate text for the image loader
                }
            */
            if ( options.async == null )    { options.async = true; }
            if ( ! options.timeout )        { options.timeout  = 3000; }
            if ( ! options.postData )       { options.postData = null; }
            if ( ! options.label )          { options.label = null; }
            if ( ! options.cache )          { options.cache = false; }
            if ( ! options.showLoader )     { options.showLoader  = false; }
            if ( ! options.imgSrc )         { options.imgSrc  = null; }
            if ( ! options.parentCtl )      { options.parentCtl = null; }
            if ( ! options.loadingText )    { options.loadingText = "Loading..."; }


            /*[ Create the ajax loader ]*/
            var img_loader = null;
            if (options.showLoader)
            {
                /*[ Clear content first ]*/
                options.parentCtl.innerHTML = '';

                img_loader = _createImageLoader(options.imgSrc, options.parentCtl, options.loadingText);
            }


            /*[ Set timeout ]*/
            var _timer = setTimeout(function() { self._abort(xhr); }, options.timeout);


            /*[ Handle the state of the request ]*/
            xhr.onreadystatechange = function()
            {
                if (xhr.readyState == 4)
                {
                    /*[ Clear timeout ]*/
                    clearTimeout(_timer);

                    if (xhr.status == 200 || xhr.status == 304)
                    {
                        /*[ Clear the loading image ]*/
                        if (img_loader != null) { options.parentCtl.removeChild(img_loader); }

                        /*[ Retrieve response ]*/
                        if (method == "HEAD")
                        {
                            /*[ If a header label was provided ]*/
                             if (options.label) {
                                onSuccess( xhr.getResponseHeader(options.label) );
                             }
                             else {
                                onSuccess( xhr.getAllResponseHeaders() );
                             }
                        }
                        /*[ Common GET request ]*/
                        else { onSuccess( xhr.responseText, xhr.responseXML ); }
                    }
                    else {
                        /*[ Clear the loading image ]*/
                        if (img_loader != null)
                        {
                            try { options.parentCtl.removeChild(img_loader); }
                            catch(e){}
                        }

                        if (onFailure) { onFailure(xhr.statusText); self._abort(xhr); }
                        else {
                            /*[ Default error message ]*/
                            throw new Error("An error has occurred while executing the request.\r\nStatus: "+xhr.statusText);
                        }
                    }
                }
            };

            if ( ! options.cache)
            {
                var rand_no = Math.ceil(1000*Math.random());

                if (uri.indexOf('?') >= 0) {
                    uri += "&xyxz_rand="+rand_no;
                }
                else { uri += "?xyxz_rand="+rand_no; }
            }

            xhr.open(method, uri, options.async);

            if (method == "POST")
            {
                xhr.setRequestHeader("Content-Type", "application/x-www-form-urlencoded");

                if (options.postData) {
                    if (options.postData.indexOf("?") < 0) {
                        options.postData = "?" + options.postData;
                    }
                }
            }
            xhr.send(options.postData);

            return this;
        }


    };
    /*[ end _$.prototype ]*/


    /**
     * Map the $ object to the library's main function
     * return object
     */
    window.Clib = window.$ = function() {
        return new _$(arguments);
    };


})();

Usage:


<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
    <meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
    <title>Clib - a basic javascript library</title>

	<script type="text/javascript" src="bin/c-lib.js"></script>
    <script type="text/javascript">
    
		// Clib == $
	
		Clib(window).on('load', function(event)
		{
			/*[ AJAX - GET ]*/
			Clib("call_server_button").on('click', function(ev)
			{
				// $().stopEvent(ev); /*[ if the default action should be prevented ]*/

				Clib().ajax("GET", "app_code/server.php?myname="+$('name_textbox').value(),
					/*[ OPTIONS ]*/
					{
						"cache"         : false,
						"showLoader"    : true,
						"imgSrc"        : 'bin/ajax-loader.gif',
						"parentCtl"     : document.getElementById('container')
					},
					/*[ ON SUCCESS ]*/
					function(txt, xml) {
						Clib("container").css({"background":"#f00", 'color':'#ff0'}).text(txt);
					}
				);
			});
			/*[ end ajax - get ]*/
		});
    </script>
</head>
<body>
	<h2>Ajax library</h2>


	<div>
    	<input type="text" id="name_textbox" />
    	<input type="button" id="call_server_button" value="Call server" />
    </div>
    <div id="container" style="margin: 25px; width: 400px;"></div>
</body>
</html>
Categories: JavaScript Tags: ,

XLog – php logging class

December 17, 2009 1 comment

Notice: This class is subject to change.


<?php
/**
* class XLog
*
* The XLog is a PHP 5 oriented object class to log messages into one or multiple files.
* 
* @category   Log
* @author     Costin Trifan 
* @copyright  2009 Costin Trifan
* @licence    MIT License http://en.wikipedia.org/wiki/MIT_License
* @version    1.0
* 
* Copyright (c) 2009 Costin Trifan 
* 
* Permission is hereby granted, free of charge, to any person
* obtaining a copy of this software and associated documentation
* files (the "Software"), to deal in the Software without
* restriction, including without limitation the rights to use,
* copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the
* Software is furnished to do so, subject to the following
* conditions:
* 
* The above copyright notice and this permission notice shall be
* included in all copies or substantial portions of the Software.
* 
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
* OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
* NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
* HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
* WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
* FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
* OTHER DEALINGS IN THE SOFTWARE.
*/
class XLog
{
	private function __clone() {}
	private function __wakeup() {}

	protected
		$log_file 	= '',	# The absolute path to the log file.
		$message 	= '',	# The message to write into the log file
		$line		= '',	# The line where the error has occurred [ ie: __LINE__ ]
		$file 		= '';	# The file where the error has occurred [ ie: __FILE__ ]

	# Error messages
	protected
		$error_file_not_found 	= "Error: Although you have enabled error logging, the log file could not be found!",
		$error_file_open 	= "Error: Couldn't open the log file. Check for permissions!",
		$error_no_message       = "Error: The content to write into the log file is missing...";



	/**
	* Constructor
	*
	* @param string $log_file The absolute path to the log file.
	*/
	public function __construct( $log_file='' )
	{
		$this->SetLogFile($log_file);
	}


	/**
	* Set the active log file.
	*
	* @access private
	* @return void
	*/
	private function SetLogFile( $log_file='' )
	{
		if ($log_file)
			$this->log_file = $log_file;
	}


	/**
	* Check to see whether or not the log file exists.
	*
	* @access private
	* @return boolean
	*/
	private function FileExists( $log_file )
	{
		return file_exists($log_file);
	}


	/**
	* Clear the log file
	*/
	public function Clear( $log_file='' )
	{
		if (!$log_file)
			$log_file = $this->log_file;

		if (!$this->FileExists($log_file))
			$this->ExitWithError($this->error_file_not_found);
	
		if (($h = fopen($log_file, "w")) !== FALSE)
			fclose($h);
		else
			$this->ExitWithError($this->error_file_open);
	}


	/**
	* Show the content from the log file
	*
	* @param string $log_file The absolute path to the log file.
	* @return string
	*/
	public function GetContent( $log_file='' )
	{
		if (!$log_file)
			$log_file = $this->log_file;

		if (!$this->FileExists($log_file))
			$this->ExitWithError($this->error_file_not_found);

		# Check if the file is php; if it is, remove php's tags and comments
		$info = pathinfo($log_file);
		$file_extension  = strtoupper($info['extension']);


		if (($h = @fopen($log_file, "r")) !== FALSE)
		{
			# Get content
			$content = file_get_contents($log_file);
			@fclose($h);

			if ($file_extension == 'PHP')
			{
				$begin_file = '';

				$content_length 	= strlen($content);
				$begin_file_length 	= strlen($begin_file);
				$end_file_length 	= strlen($end_file);
				# Strip php's tags and comments
				$content 			= substr($content, $begin_file_length, -$end_file_length);
			}
		}
		return html_entity_decode($content, ENT_QUOTES, "UTF-8");
	}


	/**
	* Write into the log file
	*
	* @param string $message The message to write into the log file.
	* @param string $file  The file where the error has occurred [ ie: __FILE__ ].
	* @param number $line The line where the error has occurred [ ie: __LINE__ ].
	* @param boolean $clear_before Whether or not to delete the existent content from the log file before writting the new one.
	* @param string $log_file The absolute path to the log file.
	*
	* @return void
	*/
	public function Write($message='', $file=NULL, $line=NULL, $clear_before=FALSE, $log_file='')
	{
		if (!$message) $this->ExitWithError($this->error_no_message);
	
		# Setup arguments
		$this->message  = htmlentities($message, ENT_QUOTES, "UTF-8");
		$this->file		= $file;
		$this->line		= $line;
	
		if ($log_file)
			$this->log_file = $log_file;

		if (!$this->FileExists($this->log_file))
			$this->ExitWithError($this->error_file_not_found);

		if ($clear_before)
			$this->Clear($this->log_file);

		# Detect the file's extension so the appropriate function can be called
		$info = pathinfo($this->log_file);
		$file_extension  = strtoupper($info['extension']);

		switch ($file_extension)
		{
			case 'INI' 	: $this->WriteIni(); break;
			case 'PHP' 	: $this->WritePhp(); break;
			default 	: $this->WriteAny(); break;
		}
	}


	/**
	* Write log into an ini file
	*
	* @access protected
	*/
	protected function WriteIni()
	{
		if (($h = fopen($this->log_file, "r+")) !== FALSE)
		{
			$initial_content = file_get_contents($this->log_file);
		
			$br = "\r\n";
			$content  = $br.";---------------------------------------------------------------------------------------".$br;
			$content .= "Date \t= ".date("M d Y H:i:s", time()).$br;
			$content .= "IP \t= ".$_SERVER['REMOTE_ADDR'].$br;
			$content .= "Page \t= ".$_SERVER['HTTP_HOST'].$_SERVER['REQUEST_URI'].$br;
			$content .= "File \t= ".$this->file.$br;
			$content .= "Line \t= ".$this->line.$br;
			$content .= "Error \t= ".$this->message.$br;
			$content .= ";---------------------------------------------------------------------------------------".$br;
			$content .= $br.$initial_content;

			$content = trim($content);
			@fwrite($h, $content, strlen($content));
			@fclose($h);
		}
		else $this->ExitWithError($this->error_file_open);
	}


	/**
	* Write log into a php file
	*
	* @access protected
	*/
	protected function WritePhp()
	{
		if (($h = fopen($this->log_file, "r+")) !== FALSE)
		{
			$br 		= "\r\n";
			$begin_file = '';

			$initial_content = trim(file_get_contents($this->log_file));

			$content_length 	= strlen($initial_content);
			$begin_file_length 	= strlen($begin_file);
			$end_file_length 	= strlen($end_file);
			# Strip php's tags and comments
			$initial_content 	= substr($initial_content, $begin_file_length, -$end_file_length);


			$content  = "[".date("M d Y H:i:s", time())."]".$br;
			$content .= "---------------------------------------------------------------------------------------".$br;
			$content .= "IP: \t".$_SERVER['REMOTE_ADDR'].$br;
			$content .= "Page: \t".$_SERVER['HTTP_HOST'].$_SERVER['REQUEST_URI'].$br;
			$content .= "File: \t".$this->file.$br;
			$content .= "Line: \t".$this->line.$br;
			$content .= "Error: \t".$this->message.$br;
			$content .= "---------------------------------------------------------------------------------------".$br;
			$content .= $initial_content;

			$content = trim($content);
			$content = $begin_file.$br.$content.$br.$end_file;
			@fwrite($h, $content, strlen($content));
			@fclose($h);
		}
		else $this->ExitWithError($this->error_file_open);
	}


	/**
	* Write log into any other file type
	*
	* @access protected
	*/
	protected function WriteAny()
	{
		if (($h = fopen($this->log_file, "r+")) !== FALSE)
		{
			$initial_content = file_get_contents($this->log_file);
		
			$br = "\r\n";
			$content  = "[".date("M d Y H:i:s", time())."]".$br;
			$content .= "---------------------------------------------------------------------------------------".$br;
			$content .= "IP: \t".$_SERVER['REMOTE_ADDR'].$br;
			$content .= "Page: \t".$_SERVER['HTTP_HOST'].$_SERVER['REQUEST_URI'].$br;
			$content .= "File: \t".$this->file.$br;
			$content .= "Line: \t".$this->line.$br;
			$content .= "Error: \t".$this->message.$br;
			$content .= "---------------------------------------------------------------------------------------".$br;
			$content .= $br.$initial_content;

			$content = trim($content);
			@fwrite($h, $content, strlen($content));
			@fclose($h);
		}
		else $this->ExitWithError($this->error_file_open);
	}


	/**
	* Get the size of the log file.
	* Original source code: http://www.php.net/manual/en/function.filesize.php#84034
	*
	* @return string
	*/
	public function GetFileSize( $log_file='', $round=0 , $add_space=TRUE)
	{
		if (!$log_file)
			$log_file = $this->log_file;

		$size 	= filesize($log_file);
		$sizes 	= array('B', 'KB', 'MB', 'GB');
		$total 	= count($sizes);

		for ($i=0; $size > 1024 && $i < $total; $i++)
			$size /= 1024;

		if ($add_space)
			return round($size,$round).' '.$sizes[$i];
		else
			return round($size,$round).$sizes[$i];
	}


	/**
	* Display the error message
	*
	* @param string $error_message The message to be displayed in case of an error.
	* @access protected
	* @return void
	*/
	protected function ExitWithError( $error_message='' )
	{
		exit("".$error_message."");
	}

}
/*[ end class ]*/
?>

Usage:


<?php
include "class.XLog.php";

$log = new XLog();

# SET THE PATH TO THE LOG FILE
$log_file_php 	= $_SERVER['DOCUMENT_ROOT'].'/xlog/logs/log.php';

# The message
$msg_php 	= "A log entry into a php file";

# Log messages in a php file
$log->Write($msg_php, __FILE__, __LINE__, FALSE, $log_file_php);
?>

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
	<meta http-equiv="Content-Type" content="text/html; charset=iso-8859-1" />
	<title>Using the XLog class</title>
</head>
<body>

<h4 style="font-weight: normal;">The content of the log file <strong><?php echo $log_file_php;?></strong> is displayed below:</h4>

<p>The size of the log file is: <strong><?php echo $log->GetFileSize($log_file_php);?></strong></p>

<div style="margin: 25px; border: solid 1px #ccc; padding: 5px;">
	<pre><?php echo $log->GetContent($log_file_php);?></pre>
</div>

</body>
</html>
Categories: PHP Tags: ,

Class Cache

December 17, 2009 1 comment

Notice: This class is not for public usage and is subject to change.


<?php
/**
 * Class Cache. A caching class. Requires PHP 5+
 *
 * @package    		Cache
 * @category   		Caching
 * @author     		Costin Trifan 
 * @copyright  		2009 Costin Trifan
 * @licence    		Attribution-NonCommercial-NoDerivs 2.5	http://creativecommons.org/licenses/by-nc-nd/2.5/legalcode
 * @version    		1.0
 * @last-update		dec.2009
 *
 * THE WORK (AS DEFINED BELOW) IS PROVIDED UNDER THE TERMS OF THIS CREATIVE COMMONS PUBLIC LICENSE ("CCPL" OR "LICENSE").
 * THE WORK IS PROTECTED BY COPYRIGHT AND/OR OTHER APPLICABLE LAW. ANY USE OF THE WORK OTHER THAN AS AUTHORIZED UNDER THIS
 * LICENSE OR COPYRIGHT LAW IS PROHIBITED.
 * 
 * BY EXERCISING ANY RIGHTS TO THE WORK PROVIDED HERE, YOU ACCEPT AND AGREE TO BE BOUND BY THE TERMS OF THIS LICENSE.
 * THE LICENSOR GRANTS YOU THE RIGHTS CONTAINED HERE IN CONSIDERATION OF YOUR ACCEPTANCE OF SUCH TERMS AND CONDITIONS. 
 *
 *	http://creativecommons.org/licenses/by-nc-nd/2.5/legalcode
 */
class Cache
{

	private function __clone(){}
	private function __sleep(){}
	private function __wakeup(){}

	public function __get( $name ) { return null; }
	public function __set( $name, $value ) { }


# PROTECTED PROPERTIES
#======================

	protected
		 $_cacheDir = "cache/"
		,$_cacheLifetime = 3600
		;

	private $_cacheFileExt = '.php';



# PUBLIC METHODS
#======================

	public function __construct( $cacheDir, $createCacheDir = false, $cacheLifetime = 3600 )
	{
		if ( ! is_dir($cacheDir) )
		{
			if ($createCacheDir) {
				mkdir($cacheDir, 0775);
			}
			else exit('The cache directory was not found!');
		}
		if ( is_writable($cacheDir) ) {
			$this->SetCacheDir($cacheDir);
		}
		else { exit("The cache directory '$cacheDir' is not writable! Check permissions."); }

		$this->SetCacheLifetime($cacheLifetime);
	}


	public function Cache( $file )
	{
		$savefilepath = $this->_setFilePath($file);

		if ( ! file_exists($file)) { return $this; }

/*
 *	TODO:
 *
 * :: execute php code inside templates
---------------------------------------
		$data = '';
		ob_start();
			include_once $file;
			$data = ob_get_contents();
		ob_end_clean();


*/
		$data = file_get_contents($file, false);
		$data = htmlentities($data, ENT_QUOTES);
		file_put_contents($savefilepath, $data);
		return $this;
	}


	public function CacheBlock( $file, $content )
	{
		$savefilepath = $this->_setFilePath($file);

		if ( ! file_exists($file)) { return $this; }

		$data = htmlentities($content, ENT_QUOTES);
		file_put_contents($savefilepath, $data);

		return $this;
	}


	public function Get( $file )
	{
		$fpath = $this->_setFilePath($file);

		$data = '';

		if ( $this->_isCached($fpath) )
		{
			$data = file_get_contents($fpath);
			$data = html_entity_decode($data, ENT_QUOTES);
		}
		return $data;
	}


	/**
	 * Att! Not to be used internally!
	 * Use the private _IsCached($file) instead!!
	 */
	public function IsCached( $file )
	{
		return $this->_IsCached($this->_setFilePath($file));
	}


	/**
	* Delete all files from the cache directory.
	*
	* return $this
	*/
	public function EmptyDirectory()
	{
		$files = $this->_getCachedFiles();
		if (count($files) > 0) {
			foreach ($files as $file)
				unlink($file);
		}
		return $this;
	}

	/**
	* Delete a cached template.
	*
	* param string $fileNames  The name(s) of the file(s) to delete.
	* return $this
	*/
	public function Delete(/* [ $fileName, $fileName,...] */)
	{
		$files = func_get_args();
		if (count($files) > 1) {
			foreach ($files as $file) {
				$_file = $this->_setFilePath($file);
				if (file_exists($_file)) {
					unlink($_file);
				}
			}
		}
		return $this;
	}



	public function SetCacheDir( $dir )
	{
		$this->_cacheDir = $dir;
                return $this;
	}

	public function GetCacheDir()
	{
		return $this->_cacheDir;
	}

	public function SetCacheLifetime( $seconds )
	{
		if (is_numeric($seconds)) {
			$this->_cacheLifetime = $seconds;
		}
		return $this;
	}

	public function GetCacheLifetime()
	{
		return $this->_cacheLifetime;
	}






# PRIVATE METHODS
#======================

	private function _encodeName( $file )
	{
		return md5(basename($file));
	}


	private function _setFilePath( $file )
	{
		$file = $this->_cacheDir.$this->_encodeName($file).$this->_cacheFileExt;
		return $file;
	}


	private function _isCached( $file )
	{
		$_cached = false;

		if (file_exists($file)) /*[ requires $file to be encoded !! ]*/
		{
			clearstatcache();

			if (filemtime($file) > (time() - $this->_cacheLifetime)) {
				$_cached = true;
			}
		}
		return $_cached;
	}


	/**
	* Get all files from the cache directory.
	* access protected
	* return array
	*/
	private function _getCachedFiles()
	{
		$fileList = array();
		$fileCount = 0;

		if ($dir = opendir($this->_cacheDir))
		{
			while ($file = readdir($dir))
			{
				if ($file != '.' && $file != '..')
				{
					$finfo = pathinfo($file);
					$fext = '.' . $finfo['extension'];

					if (strcasecmp($fext, $this->_cacheFileExt) == 0)
					{
						array_push($fileList, $file);
						$fileCount++;
					}
				}
			}
			closedir($dir);
		}
		return $fileList;
	}


}
/*[ end class ]*/
?>
Categories: PHP Tags: ,

Template Engine class

December 16, 2009 Comments off

Notice: This class is not for public usage and is subject to change.


<?php
/**
 * Class Template. A template engine class. Requires PHP 5+
 *
 * @package    		Template
 * @category   		Template
 * @author     		Costin Trifan 
 * @copyright  		2009 Costin Trifan
 * @licence    		Attribution-NonCommercial-NoDerivs 2.5	http://creativecommons.org/licenses/by-nc-nd/2.5/legalcode
 * @version    		1.0
 * @last-update		dec.2009
 *
 * THE WORK (AS DEFINED BELOW) IS PROVIDED UNDER THE TERMS OF THIS CREATIVE COMMONS PUBLIC LICENSE ("CCPL" OR "LICENSE").
 * THE WORK IS PROTECTED BY COPYRIGHT AND/OR OTHER APPLICABLE LAW. ANY USE OF THE WORK OTHER THAN AS AUTHORIZED UNDER THIS
 * LICENSE OR COPYRIGHT LAW IS PROHIBITED.
 * 
 * BY EXERCISING ANY RIGHTS TO THE WORK PROVIDED HERE, YOU ACCEPT AND AGREE TO BE BOUND BY THE TERMS OF THIS LICENSE.
 * THE LICENSOR GRANTS YOU THE RIGHTS CONTAINED HERE IN CONSIDERATION OF YOUR ACCEPTANCE OF SUCH TERMS AND CONDITIONS. 
 *
 *	http://creativecommons.org/licenses/by-nc-nd/2.5/legalcode
 */
class Template
{

	private function __clone(){}
	private function __sleep(){}
	private function __wakeup(){}

	/**
	 * RESTRICT ACCESS TO CLASS'S GLOBAL VARIABLES
	 (=============================================)
	 */

	public function __get( $name )
	{
		if (isset($this->_vars[$name]) and !empty($this->_vars[$name]))
		{
			return $this->_vars[ $name ];
		}
		else return null;
	}

	public function __set( $name, $value )
	{
		$this->_vars[$name] = $value;
	}



	private
		 $_tplDir = 'tpl/'		# The name of the folder where the template files are supposed to be stored.
		,$_vars = array()		# The class's variables array.
		,$_leftDel = '{'		# The left delimiter to use in the templates files to mark a template variable.
		,$_rightDel = '}'		# The right delimiter to use in the templates files to mark a template variable.
		,$_cacheObj = null		# Holds the instance of the ClibCache class
			;


	/**
	 * .ctor
	 */
	public function __construct( $tplDir = '', $cacheObj = null, $leftDelimiter = '{', $rightDelimiter = '}' )
	{
		if (isset($tplDir) and trim($tplDir) != '') {
			$this->_tplDir = $tplDir;
		}
		if (isset($cacheObj) and (! is_null($cacheObj)) ) {
			$this->_cacheObj = $cacheObj;
		}
		if (isset($leftDelimiter) and trim($leftDelimiter) != '{') {
			$this->_leftDel = $leftDelimiter;
		}
		if (isset($rightDelimiter) and trim($rightDelimiter) != '}') {
			$this->_rightDel = $rightDelimiter;
		}
	}



	/**
	* Add a variable to the vars array. This variable will be replaced in a template.
	*
	* param string $name  The name of the variable to store in the vars array.
	* param mixed $value  The value of the variable.
	* return $this
	*/
	public function SetVar( $name, $value )
	{
		$this->__set( $name, $value );
		return $this;
	}


	/**
	* Get a variable from the vars array.
	*
	* param string $name  The name of the variable to retrieve from the vars array.
	* return mixed
	*/
	public function GetVar( $name )
	{
		return $this->__get( $name );
	}


	/**
	* Delete all variables from the vars array.
	*
	* return $this
	*/
	public function ClearVars()
	{
		$this->_vars = array();
		return $this;
	}


	/**
	* Get all variables from the vars array.
	*
	* return array
	*/
	public function GetAllVars()
	{
		return $this->_vars;
	}



	/**
	* Retrieve the content of a template.
	*
	* param string $template  	The name of the template file to load.
	* param bool $getCached  	Whether or not to load the chached version of the $template
	* return string  The template's html content.
	*/
	function GetFile( $fileName, $getCached = false )
	{
		$data = '';

		$dir = ( $getCached ) ? $this->_cacheObj->GetCacheDir() : $this->_tplDir;

		if ($getCached) { $data = $this->_cacheObj->Get($dir.$fileName); }
		else {
			$file = $dir.$fileName;
			if ( file_exists($file) ) {
				$data = $this->Parse( $file );
			}
		}
		return $data;
	}


	/**
	* Outputs the template's html content.
	*
	* param string $fileName  The name of the template file to load.
	* param bool $getCached  	Whether or not to load the chached version of the $fileName
	* return $this
	*/
	function Display( $fileName, $getCached = false )
	{
		echo $this->GetFile( $fileName, $getCached );
		return $this;
	}




	/**
	* Replaces the variables from the specified template file.
	*
	* access protected
	* param string $file  The name of the template file to load.
	* return string  The template's parsed content.
	*/
	protected function Parse ( $file )
	{
		$content = '';

		ob_start();
			include_once $file;
			$content = ob_get_contents();
		ob_end_clean();

		if ($content == '') { return $content; }

		// make sure there is something to parse
		if ( ($pos = strpos($content, $this->_leftDel)) === FALSE ) { return $content; }

		if (count($this->_vars) > 0)
		{
			foreach($this->_vars as $name => $value)
			{
				if (is_string($value))
				{
					$var = $this->_leftDel. $name .$this->_rightDel;
					$content = str_ireplace($var, $value, $content);
				}
			}
		}
		return $content;
	}



	/**
	* Replaces the variables from the specified content block.
	*
	* access protected
	* param string $block  The content to be parsed.
	* return string  The parsed content.
	*/
	private function _parseBlock ( $data )
	{
		$content = '';

		if ($data == '') { return $content; }

		// make sure there is something to parse
		if ( ($pos = strpos($content, $this->_leftDel)) === FALSE ) { return $content; }

		if (count($this->_vars) > 0)
		{
			foreach($this->_vars as $name => $value)
			{
				if (is_string($value))
				{
					$var = $this->_leftDel. $name .$this->_rightDel;
					$content = str_ireplace($var, $value, $content);
				}
			}
		}
		return $content;
	}

}
/*[ end class ]*/
?>
Categories: PHP Tags: ,