Пример #1
0
 function parse($path, array $var = array(), $maxDepth = null)
 {
     $file = $this->basePath . '/' . ltrim($path, '/');
     $meta = array();
     foreach (array(dirname(dirname($file)), dirname($file)) as $v) {
         $v .= '/_meta.txt';
         if (file_exists($v)) {
             $meta = array_merge_recursive($meta, $this->parseArr($this->getContent($v), $maxDepth));
         }
     }
     $content = $this->getContent($file);
     // parse here doc
     $hereDoc = array();
     $content = preg_replace_callback('/<<<(.+)>>>/sm', function (&$node) use(&$hereDoc) {
         $hereDoc[] = $node[1];
         return '\\d' . (count($hereDoc) - 1);
     }, $content);
     $arr = $this->parseArr($content, $maxDepth);
     if (array_key_exists('_meta', $arr)) {
         if (!empty($arr['_meta'])) {
             $meta = array_merge_recursive($meta, $arr['_meta']);
         }
         unset($arr['_meta']);
     }
     if (!empty($meta['_unset'])) {
         Arrays::unsetr($meta, $meta['_unset']);
         unset($meta['_unset']);
     }
     foreach ($arr as $k => $v) {
         if (null == $v) {
             unset($arr[$k]);
             continue;
         }
         $parent = $meta;
         // unset
         if (!empty($v['_unset'])) {
             Arrays::unsetr($parent, $v['_unset']);
             unset($v['_unset']);
         }
         // default
         if (!empty($parent['default'])) {
             list($v, $temp) = array($parent['default'], $v);
             Arrays::merger($v, $temp);
         }
         // replace
         Arrays::pregReplacer('/^\\\\k$/', $k, $v);
         // key clean
         Arrays::pregReplaceKeyr('/^\\\\s(\\d+)$/', '\\1', $v);
         // prefix
         if (!empty($parent['prefix'])) {
             Arrays::prefixr($v, $parent['prefix']);
         }
         // suffix
         if (!empty($parent['suffix'])) {
             Arrays::suffixr($v, $parent['suffix']);
         }
         // wraper
         if (!empty($parent['wraper'])) {
             Arrays::wraperr($v, $parent['wraper']);
         }
         // var replace
         if (!empty($var)) {
             array_walk_recursive($v, function (&$v, $k, $var) {
                 if (is_string($v)) {
                     preg_match_all('/\\{\\$(\\w+)\\}/', $v, $matches);
                     if (!empty($matches[1])) {
                         foreach ($matches[1] as $v1) {
                             if (isset($var[$v1])) {
                                 $v = str_replace('{$' . $v1 . '}', $var[$v1], $v);
                             }
                         }
                     }
                 }
             }, $var);
         }
         // \d recover
         $search = $replace = array();
         for ($i = 0; $i < count($hereDoc); $i++) {
             $search[] = '/^\\\\d' . $i . '$/';
             $replace[] = $hereDoc[$i];
         }
         Arrays::pregReplacer($search, $replace, $v);
         $arr[$k] = $v;
     }
     // \h self inherit
     $funcH = function (array &$subject) use(&$funcH, $arr) {
         foreach ($subject as $k => &$v) {
             if ('\\h' === $k) {
                 $key = explode(' ', $v);
                 $value = \Arrays::current($arr, $key);
                 $key = array_pop($key);
                 $subject[$key] = $value;
                 unset($subject[$k]);
             } elseif (is_array($v)) {
                 call_user_func_array($funcH, array(&$v));
             }
         }
     };
     $funcH($arr);
     // \i include
     $dir = dirname($file) . '/_inc';
     Arrays::pregReplaceCallbackr('/\\\\i(.+)/', function ($node) use($dir) {
         $file = $dir . '/' . trim($node[1]);
         if (file_exists($file)) {
             return file_get_contents($file);
         }
     }, $arr);
     return $arr;
 }
Пример #2
0
 function indexAction()
 {
     $path = trim($this->getRequest()->getQuery('path', ''), ' /');
     if ('.txt' == substr($path, -4)) {
         $this->forward('detail', array('path' => $path));
         return false;
     }
     $out = array();
     $model = DocModel::getInstance();
     $out['list'] = $model->getList($path, 4);
     // set version list in inverted order
     $sort = function (&$v) {
         if (is_array($v)) {
             reset($v);
             $k1 = key($v);
             $v1 = current($v);
             next($v);
             $k2 = key($v);
             $v2 = current($v);
             $pattern = '/^v\\d\\.\\d\\.\\d/';
             if (preg_match($pattern, $k1) && preg_match($pattern, $k2)) {
                 uksort($v, function ($a, $b) {
                     return $a < $b;
                 });
             }
             if (is_string($v1) && is_string($v2)) {
                 if (preg_match($pattern, $v1) && preg_match($pattern, $v2)) {
                     uasort($v, function ($a, $b) {
                         return $a < $b;
                     });
                 }
             }
         }
     };
     $sort($out['list']);
     Arrays::walkr($out['list'], function (&$v) use($sort) {
         $sort($v);
     });
     $mapKey = array();
     $mapValue = array();
     Arrays::pregReplaceKeyr('/.+/', function ($match) use(&$mapKey) {
         if (0 === strpos(PHP_OS, 'WIN')) {
             $enc = mb_convert_encoding($match[0], "UTF-8", "GBK");
         } else {
             $enc = $match[0];
         }
         $mapKey[$enc] = urlencode($match[0]);
         return $enc;
     }, $out['list']);
     Arrays::pregReplacer('/.+/', function ($match) use(&$mapValue) {
         if (0 === strpos(PHP_OS, 'WIN')) {
             $enc = mb_convert_encoding($match[0], "UTF-8", "GBK");
         } else {
             $enc = $match[0];
         }
         $mapValue[$enc] = urlencode($match[0]);
         return $enc;
     }, $out['list']);
     $out['map'] = $mapKey;
     $out['mapVal'] = $mapValue;
     $this->getView()->assign($out);
 }
Пример #3
0
 /**
  * parse doc file and relative files
  *
  * @param string $path
  * @param array $var
  *            replacement in doc
  * @param int $maxDepth
  * @return mixed
  */
 function parse($path, array $var = array(), $maxDepth = null)
 {
     $file = $this->basePath . '/' . ltrim($path, '/');
     // replace var
     $funcVarReplace = function ($arr, $var) {
         if (!empty($var)) {
             $flag = false;
             if (is_string($arr)) {
                 $flag = true;
                 $arr = array($arr);
             }
             array_walk_recursive($arr, function (&$v, $k, $var) {
                 if (is_string($v)) {
                     preg_match_all('/\\{\\$(\\w+)\\}/', $v, $matches);
                     if (!empty($matches[1])) {
                         foreach ($matches[1] as $v1) {
                             if (isset($var[$v1])) {
                                 $v = str_replace('{$' . $v1 . '}', $var[$v1], $v);
                             }
                         }
                     }
                 }
             }, $var);
         }
         if ($flag) {
             $arr = $arr[0];
         }
         return $arr;
     };
     $i = 0;
     $meta = array();
     // merge _meta.txt
     foreach (array(dirname(dirname($file)), dirname($file)) as $v) {
         $v .= '/_meta.txt';
         if (file_exists($v)) {
             $metaCurrent = $this->parseArr($this->getContent($v), $maxDepth);
             $lastUnset = array();
             if (!empty($metaCurrent['_unset'])) {
                 $lastUnset = $metaCurrent['_unset'];
                 unset($metaCurrent['_unset']);
             }
             // meta inherit
             $metaFile = $v;
             while (!empty($metaCurrent['inherit'])) {
                 if ($i++ > 10) {
                     // break;
                 }
                 // replace version in _meta.txt
                 $metaFile = dirname($metaFile) . '/' . $metaCurrent['inherit'];
                 unset($metaCurrent['inherit']);
                 if (false !== strpos($metaFile, '{$version}')) {
                     preg_match('/v\\d\\.\\d\\.\\d/', $metaFile, $metaFileVersion);
                     if (!empty($metaFileVersion[0])) {
                         $metaFile = str_replace('{$version}', $metaFileVersion[0], $metaFile);
                     }
                 }
                 $metaInherit = $this->parseArr($this->getContent($metaFile), $maxDepth);
                 $metaCurrent = Arrays::merger($metaInherit, $metaCurrent);
             }
             $meta = Arrays::merger($meta, $metaCurrent);
             $meta = Arrays::unsetr($meta, $lastUnset);
             if (!empty($meta['_unset']) || !empty($lastUnset)) {
                 if (empty($meta['_unset'])) {
                     $meta['_unset'] = array();
                 }
                 $lastUnset = array_merge_recursive($lastUnset, $meta['_unset']);
                 unset($meta['_unset']);
             }
         }
     }
     // merge var in doc
     if (!empty($meta['var'])) {
         $var = Arrays::merger($var, $meta['var']);
         unset($meta['var']);
     }
     $content = $this->getContent($file);
     // parse here doc
     $hereDoc = array();
     $content = preg_replace_callback('/<<<(.+)>>>/sm', function (&$node) use(&$hereDoc) {
         $hereDoc[] = $node[1];
         return '\\d' . (count($hereDoc) - 1);
     }, $content);
     // parse content
     $arr = $this->parseArr($content, $maxDepth);
     // inline _meta
     if (!empty($arr['_meta'])) {
         // process inherit first
         $fileCurrent = $file;
         $lastUnset = array();
         if (!empty($arr['_unset'])) {
             $lastUnset = $arr['_unset'];
             unset($arr['_unset']);
         }
         while (!empty($arr['_meta']['inherit'])) {
             if (is_string($arr['_meta']['inherit'])) {
                 $inheritFile = $arr['_meta']['inherit'];
                 $inheritKeys = null;
             } elseif (is_array($arr['_meta']['inherit'])) {
                 $inheritFile = $arr['_meta']['inherit'][0];
                 $inheritKeys = $arr['_meta']['inherit'];
                 array_shift($inheritKeys);
             } else {
                 user_error('inherit file is invalid', E_USER_ERROR);
             }
             unset($arr['_meta']['inherit']);
             $inheritFile = dirname($fileCurrent) . '/' . $funcVarReplace($inheritFile, $var);
             $fileCurrent = $inheritFile;
             $arrInherit = $this->parseArr($this->getContent($inheritFile), $maxDepth);
             if (isset($inheritKeys)) {
                 foreach ($arrInherit as $k => $v) {
                     if (!in_array($k, $inheritKeys)) {
                         unset($arrInherit[$k]);
                     }
                 }
             }
             $arrInherit = Arrays::unsetr($arrInherit, $lastUnset);
             if (!empty($arrInherit['_unset']) || !empty($lastUnset)) {
                 if (empty($arrInherit['_unset'])) {
                     $arrInherit['_unset'] = array();
                 }
                 $lastUnset = array_merge_recursive($lastUnset, $arrInherit['_unset']);
                 unset($arrInherit['_unset']);
             }
             $arrInherit = Arrays::merger($arrInherit, $arr);
             $arr = $arrInherit;
         }
         if (array_key_exists('_meta', $arr)) {
             $meta = array_merge_recursive($meta, $arr['_meta']);
         }
         unset($arr['_meta']);
     }
     // do _meta definitions
     foreach ($arr as $k => $v) {
         if (null == $v) {
             unset($arr[$k]);
             continue;
         }
         $metaReplace = $meta;
         // default
         if (!empty($metaReplace['default'])) {
             list($v, $temp) = array($metaReplace['default'], $v);
             $v = Arrays::merger($v, $temp);
         }
         // replace
         Arrays::pregReplacer('/^\\\\k$/', $k, $v);
         // key clean
         Arrays::pregReplaceKeyr('/^\\\\s(\\d+)$/', '\\1', $v);
         // prefix
         if (!empty($metaReplace['prefix'])) {
             Arrays::prefixr($v, $metaReplace['prefix']);
         }
         // suffix
         if (!empty($metaReplace['suffix'])) {
             Arrays::suffixr($v, $metaReplace['suffix']);
         }
         // wraper
         if (!empty($metaReplace['wraper'])) {
             Arrays::wraperr($v, $metaReplace['wraper']);
         }
         // var replace
         $v = $funcVarReplace($v, $var);
         // \d recover
         $search = $replace = array();
         for ($i = 0; $i < count($hereDoc); $i++) {
             $search[] = '/^\\\\d' . $i . '$/';
             $replace[] = $hereDoc[$i];
         }
         Arrays::pregReplacer($search, $replace, $v);
         $arr[$k] = $v;
     }
     // \h self inherit
     $funcInherit = function (array &$subject) use(&$funcInherit, $arr) {
         foreach ($subject as $k => &$v) {
             if ('\\h' === $k) {
                 if (is_string($v)) {
                     $key = array($v);
                 } else {
                     $key = $v;
                 }
                 $value = Arrays::current($arr, $key);
                 $key = array_pop($key);
                 $subject[$key] = $value;
                 unset($subject[$k]);
             } elseif (is_array($v)) {
                 call_user_func_array($funcInherit, array(&$v));
             }
         }
     };
     $funcInherit($arr);
     // \i include
     $dir = dirname($file);
     Arrays::pregReplacer('/\\\\i(.+)/', function ($node) use($dir) {
         $file = $dir . '/' . trim($node[1]);
         if (file_exists($file)) {
             return file_get_contents($file);
         }
     }, $arr);
     // sort param
     foreach ($arr as &$v) {
         if (!empty($v['params']['httpPost'])) {
             uasort($v['params']['httpPost'], function ($a, $b) {
                 return $a[0] < $b[0];
             });
         }
         if (!empty($v['params']['httpGet'])) {
             uasort($v['params']['httpGet'], function ($a, $b) {
                 return $a[0] < $b[0];
             });
         }
     }
     // sort value
     foreach ($arr as &$v) {
         if (!empty($v['return']['data']['value']['data']['data'])) {
             uksort($v['return']['data']['value']['data']['data'], function ($a, $b) {
                 return $a > $b;
             });
         }
     }
     return $arr;
 }