/src/lib/engines/simple_parser_engine.php
PHP | 157 lines | 101 code | 31 blank | 25 comment | 42 complexity | 100e2a3e602928e7c283823b7bed463d MD5 | raw file
Possible License(s): MIT, CC0-1.0
- <?php
- /**
- * Simple Parser Engine
- * Finds text between given delimiters and evaluates the enclosed buffer.
- * ---
- * Written by Jose Carlos Nieto <xiam@menteslibres.org>
- * Copyright (c) 2007 Astrata Software S.A. de C.V.
- *
- * Licensed under The MIT License
- * Redistributions of files must retain the above copyright notice.
- *
- * @author Jose Carlos Nieto <xiam@menteslibres.org>
- * @copyright Copyright (c) 2007-2008, Astrata Software S.A. de C.V.
- * @link http://opensource.astrata.com.mx Astrata Open Source Projects
- * @version $Revision: $
- * @modifiedby $LastChangedBy: $
- * @lastmodified $Date: $
- * @license http://www.opensource.org/licenses/mit-license.php The MIT License
- *
- */
- class simple_parser_engine extends tm_object {
-
- public $escape_char = null;
- public $delimiters = array();
- public $use_stack = false;
- public $recursive = true;
-
- public function set_delimiters($arr) {
- $this->delimiters = $arr;
- }
- public function eval_enclosed($buff, $delimiter) {
- return $buff;
- }
- public function parse(&$buff) {
- $stack = array();
- $search_for_index = -1;
- for ($i = 0; isset($buff[$i]); $i++) {
- foreach ($this->delimiters as $index => $delimiter) {
- if ($search_for_index == -1 || $search_for_index == $index) {
- // escape sequences
- if ($search_for_index == -1 && $this->escape_char) {
- if ($buff[$i] == $this->escape_char && isset($buff[$i+1])) {
- $break = false;
- // checking if this escape sequence is before a delimiting character
- for ($j = 0; $break == false && $j <= 1; $j++) {
- if ($buff[$i+1] == $delimiter[$j]{0}) {
- $buff = substr($buff, 0, $i).substr($buff, $i + 1);
- $break = true;
- }
- }
- if ($break) {
- break;
- }
- }
- }
- // lenght of start delimiter
- $len = strlen($delimiter[0]);
- $match = ($len > 0);
- if ($match && isset($buff[$i+$len-1])) {
- for ($j = 0; $match && $j < $len; $j++) {
- if ($buff[$i+$j] != $delimiter[0][$j]) {
- $match = false;
- }
- }
- if ($match) {
- if (!$stack) {
- $search_for_index = $index;
- }
- array_push($stack, $i);
- $i = $i + $len;
- $i = $i - 1;
- break;
- }
- }
- if ($stack) {
-
- // length of ending delimiter
- $len = strlen($delimiter[1]);
- $match = ($len > 0);
- if ($match && isset($buff[$i+$len-1])) {
- for ($j = 0; $match && $j < $len; $j++) {
- if ($buff[$i+$j] != $delimiter[1][$j]) {
- $match = false;
- }
- }
- if ($match) {
- // what did we close?
- $start = array_pop($stack);
- if (substr($buff, $start, strlen($delimiter[0])) == $delimiter[0]) {
-
- $i = $i + $len;
- $portion = substr($buff, $start, $i - $start);
- if ($this->recursive) {
- if ($stack) {
- // silently discarding this break point
- $i -= 1;
- break;
- } else {
- $portion = substr($portion, strlen($delimiter[0]), -1*strlen($delimiter[1]));
- if ($this->parse($portion)) {
- $portion = $delimiter[0].$portion.$delimiter[1];
- $search_for_index = -1;
- } else {
- debug('PANIC!');
- return false;
- }
- }
- }
- $portion = $this->eval_enclosed($portion, $delimiter);
- $search_for_index = -1;
- $buff = substr($buff, 0, $start).$portion.substr($buff, $i);
- $i = $start + strlen($portion);
-
- $i = $i - 1;
- } else {
- array_push($stack, $start);
- }
- }
- }
- }
- }
- }
- }
- if ($stack) {
- debug("Filter syntax error near '".substr($buff, array_pop($stack), 60)."'");
- return false;
- }
- return true;
- }
- }
- ?>