/** * default action */ function action($item) { //! create a fake page parameter $name = "layoutadd"; $_SESSION['cms_param'][sha1("layoutadd_")] = new \PHPPE\AddOn\layoutadd([], $name, $name); //! if layout not given if (empty($item)) { //! check if we have to activate a sitebuild if (!empty($_REQUEST['set'])) { DS::exec("UPDATE " . Views::$_table . " SET id=sitebuild WHERE sitebuild!='' AND id='frame'"); DS::exec("UPDATE " . Views::$_table . " SET id='frame' WHERE sitebuild=?", trim($_REQUEST['set'])); Http::redirect(); } //! load layouts and sitebuilds $this->layouts = Views::find([], "sitebuild=''", "name"); $this->sitebuilds = Views::find([], "sitebuild!=''", "name"); } else { //! load layout $this->layout = new Views($item); if (!empty($this->layout->jslib)) { foreach ($this->layout->jslib as $j) { View::jslib($j); } } if (!empty($this->layout->css)) { foreach ($this->layout->css as $c) { View::css($c); } } $this->numPages = Page::getNum($item); //! get user input $layout = Core::req2arr("layout"); //! merge the new data with the loaded layout's properties if (!empty($this->layout->sitebuild) && !empty($layout)) { Core::$core->noframe = 1; $layout['sitebuild'] = $layout['id']; } if (Core::isTry("layout")) { //! delete a layout if (!empty($layout['delete'])) { $this->layout->delete(); } else { unset($layout['delete']); //! renamed? if ($this->layout->id != $layout['id']) { DS::exec("UPDATE " . Views::$_table . " SET id=? WHERE id=?", [$layout['id'], $this->layout->id]); Core::log('A', sprintf("Layout %s renamed to %s by %s", $this->layout->id, $layout['id'], Core::$user->name), "cmsaudit"); } //! save new data foreach ($layout as $k => $v) { $this->layout->{$k} = $v; } $this->layout->save(); } Http::redirect("cms/layouts"); } } }
function edit() { View::jslib("wyswyg.js", "pe.wyswyg.init();", 8); View::css("wyswyg.css"); if (empty($this->args[0])) { $this->args[0] = $this->adjust; } return "<textarea id='" . $this->fld . "' name='" . $this->fld . "' class='" . $this->css . " wyswyg' dir='ltr' data-conf='" . htmlspecialchars(urlencode(json_encode($this->args))) . "'>" . htmlspecialchars($this->value) . "</textarea>"; }
function edit() { if (!Core::isTry()) { $page = new Page(); $page->template = "simple"; View::assign("page", $page); } $quickhelp = !Core::lib("CMS")->expert; View::assign("quickhelp", $quickhelp); return View::template("cms_pageinfo"); }
function action() { if (isset($_REQUEST['clearbenchmark'])) { Benchmark::clear(); Http::redirect(); } $this->data = Benchmark::stats(); foreach ($this->data as $u => $v) { $this->urls[] = $u . " (" . sprintf(L("%d samples"), reset($v)['cnt']) . ")"; } View::js("choosediv(value)", "var divs=document.querySelectorAll('DIV.benchmark');for(var i in divs) divs[i].style.display=divs[i].id=='url'+value?'block':'none';"); }
function load(&$app) { if (!is_array($this->value)) { $page = View::getval("page"); if (!empty($page->data['meta'])) { $this->value = $page->data['meta']; } } if (!is_array($this->value)) { $this->value = []; } }
function action($item) { //make lang happy: L("OK") L("FAIL") L("SKIP") L("None") if (Core::$core->output != "html") { printf(chr(27) . "[96m%-20s%-9s%-9s%-21s%s\n------------------- -------- -------- -------------------- ----------" . chr(27) . "[0m\n", L("Test boundle"), L("Avg.time"), L("#Tests"), L("Last run"), L("Result")); foreach ($this->testCases as $t) { printf("%-20s" . chr(27) . "[90m%0.4fs %3d /%3d %s " . chr(27) . "[%sm%s" . chr(27) . "[0m\n", $t['name'], $t['avg'], $t['executed'], $t['asserts'], date("Y-m-d H:i:s", $t['time']), $t['ret'] == "OK" ? "92" : ($t['ret'] == "None" ? "96" : "91"), L($t['ret'])); } die; } View::js("runtest(t)", "document.getElementById('testsdiv').style.display='none';document.getElementById('loadingdiv').style.display='block';document.location.href='" . url() . "run/'+t;"); View::css("test.css"); }
public function testConvert() { setlocale(LC_NUMERIC, 'en_US.utf-8'); \PHPPE\Core::validate("obj.phone", "phone", false); \PHPPE\Core::validate("obj.chk.me", "check", true); \PHPPE\Core::validate("obj.file", "file", false); $_FILES['obj_file']['error'] = 1; $_REQUEST['obj_phone'] = "+361234567"; $obj = \PHPPE\Core::req2obj("obj"); $this->assertInstanceOf("stdClass", $obj, "req2obj"); $this->assertFalse(\PHPPE\Core::isError("obj.phone"), "validator"); $_REQUEST['obj_phone'] = "abc"; $obj2 = \PHPPE\Core::req2arr("obj"); $this->assertInternalType("array", $obj2, "req2arr"); $this->assertTrue(\PHPPE\Core::isError("obj.chk.me"), "validator"); $obj = new \stdClass(); $obj->field1 = "field1"; $obj->field2 = "field2's"; $obj->field3 = 3; $obj->field4 = 1.2; $this->assertEmpty(\PHPPE\Core::arr2str("aaa"), "arr2str str"); $this->assertEquals("field1='field1' field2='field2\\'s' field3='3' field4='1.2'", \PHPPE\Core::arr2str($obj), "arr2str"); $this->assertEquals("field1='field1' field2='field2\\'s' field3='3' field4='1.2'", \PHPPE\Core::obj2str($obj), "obj2str space"); $this->assertEquals("field1='field1',field2='field2\\'s',field3='3',field4='1.2'", str_replace("''", "\\'", \PHPPE\Core::obj2str($obj, "", ",")), "obj2str comma"); $this->assertEquals("field1='field1' field4='1.2'", \PHPPE\Core::obj2str($obj, "field2,field3"), "obj2str skip"); $obj2 = new \stdClass(); $obj2->test = "a:b:c"; $obj2->test2 = ["a", "b", "c"]; \PHPPE\View::assign("obj2", $obj2); $this->assertEquals("[\"a:b:c\"]", json_encode(\PHPPE\Core::val2arr("obj2.test")), "val2arr #1"); $this->assertEquals("[\"a\",\"b\",\"c\"]", json_encode(\PHPPE\Core::val2arr("obj2.test2")), "val2arr #2"); $this->assertEquals("[1,2]", json_encode(\PHPPE\Core::val2arr([1, 2])), "val2arr #3"); $this->assertEquals("[\"a\",\"b\",\"c\"]", json_encode(\PHPPE\Core::val2arr("obj2.test", ":")), "val2arr #4"); $this->assertEquals("[]", json_encode(\PHPPE\Core::val2arr("")), "val2arr #5"); $tree = [["id" => 1, "name" => "1"], ["id" => 2, "name" => "2", "_" => [["id" => 21, "name" => "21"], ["id" => 22, "name" => "22", "_" => [["id" => 221, "name" => "221"], ["id" => 222, "name" => "222"]]], ["id" => 23, "name" => "23"], ["id" => 24, "name" => "24"]]]]; $this->assertEquals('[{"id":1,"name":"1"},{"id":2,"name":"2"},{"id":21,"name":" 21"},{"id":22,"name":" 22"},{"id":221,"name":" 221"},{"id":222,"name":" 222"},{"id":23,"name":" 23"},{"id":24,"name":" 24"}]', json_encode(\PHPPE\Core::tre2arr($tree)), "tre2arr selectbox #1"); $this->assertEquals('[{"id":1,"name":"1"},{"id":2,"name":"2"},{"id":21,"name":" 21"},{"id":22,"name":" 22"},{"id":221,"name":" 221"},{"id":222,"name":" 222"},{"id":23,"name":" 23"},{"id":24,"name":" 24"}]', json_encode(\PHPPE\Core::tre2arr($tree, " ")), "tre2arr selectbox #2"); $this->assertEquals('[{"id":1,"name":"1"},{"id":2,"name":"2\\n<div id=\'tree2_1\' style=\'padding-left:10px;\'>"},{"id":21,"name":"21"},{"id":22,"name":"22\\n<div id=\'tree2_3\' style=\'padding-left:10px;\'>"},{"id":221,"name":"221"},{"id":222,"name":"222\\n<\\/div>"},{"id":23,"name":"23"},{"id":24,"name":"24\\n<\\/div>"}]', json_encode(\PHPPE\Core::tre2arr($tree, "<div id='tree2_%d' style='padding-left:10px;'>", "</div>")), "tre2arr DOM"); $tree = json_decode('[{"id":1,"name":"1"},{"id":2,"name":"2","_":[{"id":3,"name":"3"}]}]'); $this->assertEquals('[{"id":1,"name":"1"},{"id":2,"name":"2"},{"id":3,"name":" 3"}]', json_encode(\PHPPE\Core::tre2arr($tree)), "tre2arr stdClass selectbox"); $this->assertEquals('[{"id":1,"name":"1"},{"id":2,"name":"2\\n<div id=\'tree2_1\' style=\'padding-left:10px;\'>"},{"id":3,"name":"3\\n<\\/div>"}]', json_encode(\PHPPE\Core::tre2arr($tree, "<div id='tree2_%d' style='padding-left:10px;'>", "</div>")), "tre2arr stdClass DOM"); }
function edit() { $lists = ["pages_list" => L("Page list"), "img_list" => L("Picture list"), "doc_list" => L("Document list")]; $v = is_array($this->value) ? $this->value : json_decode($this->value, true); $r = "<input type='hidden' name='" . $this->fld . "'><table width='100%'><tr><td></td><td>" . L("SELECT") . "</td><td>" . L("FROM") . "</td><td>" . L("WHERE") . "</td><td>" . L("GROUP BY") . "</td><td>" . L("ORDER BY") . "</td></tr>"; if (!empty($v)) { foreach ($v as $k => $m) { $r .= "<tr><td width='1' style='min-width:100px;border:1px solid #202020;padding:2px;background:rgba(160,160,160,0.5);'>" . $k . "</td>"; $l = explode(" ", $m[1])[0]; $f = $h = ""; if (!empty($lists[$l])) { $f = "<select onchange='cms_listhide(this);' onblur='cms_listhide(this);' style='width:95%;margin-left:0px;' class='input form-control'><option value=''>*</option>"; foreach ($lists as $n => $li) { $f .= "<option value='" . htmlspecialchars($n) . "'" . ($l == $n ? " selected" : "") . ">" . $li . "</option>"; } $f .= "</select>"; $h = 1; } foreach ($m as $idx => $val) { $r .= "<td width='*' style='padding:0px;'>" . $f . "<input style='width:95%;margin-left:0px;" . ($h ? "display:none;" : "") . "' class='input form-control' name='" . $this->fld . "[" . $k . "][" . $idx . "]' value=\"" . htmlspecialchars(!empty($val) ? $val : '') . "\"" . ($f ? " onkeydown='cms_listshow(this);'" : "") . "></td>"; $f = ""; } $r .= "<td><nobr><img src='images/cms/pagedel.png' onclick='cms_cleardds(this);' style='cursor:pointer;padding:2px;'><img src='images/cms/pageadd.png' onclick='cms_clonedds(this);' style='cursor:pointer;padding:2px;'></nobr></td></tr>"; } } $r .= "<tr><td width='1' style='padding-right:3px;'><input style='min-width:100px;' class='input form-control' name='" . $this->fld . "[_][name]' value=''></td>"; for ($m = 0; $m < 5; $m++) { $r .= "<td width='*' style='padding:0px;'><input style='width:95%;margin-left:0px;' class='input form-control' name='" . $this->fld . "[_][" . $m . "]' value=''></td>"; } $r .= "<td style='width:37px;'> </td></tr>"; $r .= "</table>"; View::js("cms_cleardds(obj)", "obj.parentNode.parentNode.parentNode.getElementsByTagName('INPUT')[0].value='';" . "obj.parentNode.parentNode.parentNode.style.display='none';"); View::js("cms_clonedds(obj)", "var i,tbl=obj.parentNode;" . "while(tbl.tagName!='TABLE') tbl=tbl.parentNode;" . "var inps=tbl.rows[tbl.rows.length-1].getElementsByTagName('INPUT');" . "var orig=obj.parentNode.parentNode.parentNode.getElementsByTagName('INPUT');" . "for(i=0;i<orig.length;i++) inps[i+1].value=orig[i].value;" . "inps[0].value='New'; inps[0].select(); inps[0].focus();"); View::js("cms_listhide(obj)", "var i,orig=obj.parentNode.parentNode.getElementsByTagName('INPUT');console.log('value',obj.selectedIndex,obj.value);" . "if(obj.selectedIndex==0||obj.value==null||obj.value==''){" . "obj.setAttribute('style','display:none;');for(i=0;i<orig.length;i++) orig[i].style.display='block';" . "}else{" . "if(obj.value=='pages_list'){orig[0].value='b.*';orig[1].value='pages_list a left join pages b on a.page_id=b.id and b.created=(SELECT MAX(c.created) FROM pages c WHERE c.id=b.id)';orig[2].value=\"a.list_id='@ID'\";orig[3].value='';orig[4].value='ordering';}" . "if(obj.value=='img_list'){orig[0].value='id';orig[1].value='img_list';orig[2].value=\"list_id='@ID'\";orig[3].value='';orig[4].value='ordering';}" . "if(obj.value=='doc_list'){orig[0].value='id';orig[1].value='doc_list';orig[2].value=\"list_id='@ID'\";orig[3].value='';orig[4].value='ordering';}" . "}"); View::js("cms_listshow(obj)", "var i,orig=obj.parentNode.parentNode.getElementsByTagName('INPUT');" . "if(obj.value==null||obj.value==''){" . "obj.previousSibling.setAttribute('style','display:block;');for(i=0;i<orig.length;i++) orig[i].style.display='none';}"); return $r; }
function edit() { $quickhelp = !Core::lib("CMS")->expert; View::assign("quickhelp", $quickhelp); return View::template("cms_layoutadd"); }
function init() { View::jslib("resptable.js", "pe.resptable.init();"); }
/** * default action, loaded via AJAX */ function action($item) { //! assets if (!empty($_REQUEST['assetn'])) { list($d, $f) = explode("/", $_REQUEST['assetn']); $fn = ".tmp/" . session_id() . "/" . $d . "/" . $f; if (file_exists($fn)) { header("Content-type: " . ($d == "i" ? "image/png" : ($d == "c" ? "text/css" : ($d == "j" ? "text/javascript" : "application/octet-stream")))); die(file_get_contents($fn) . ""); } } //! sitebuild import Core::$core->noframe = true; $import = Core::req2arr("import"); //! uncompress uploaded archive if (!empty($import['file']['tmp_name'])) { @Tools::rmdir(".tmp/" . session_id()); @mkdir(".tmp/" . session_id() . "/i", 0750, true); @mkdir(".tmp/" . session_id() . "/c", 0750, true); @mkdir(".tmp/" . session_id() . "/j", 0750, true); @mkdir(".tmp/" . session_id() . "/f", 0750, true); @mkdir(".tmp/" . session_id() . "/h", 0750, true); Tools::untar($import['file']['tmp_name'], function ($name, $body) { $fn = ""; if (substr($name, -4) == ".htm" || substr($name, -5) == ".html") { self::$success = true; $fn = "h/" . basename($name); } else { if (in_array(substr($name, -4), [".gif", ".png", ".pnm", ".jpg", ".svg"])) { $fn = "i/" . basename($name); } else { if (in_array(substr($name, -4), [".eot", ".ttf"]) || substr($name, -5) == ".woff" || substr($name, -6) == ".woff2") { $fn = "f/" . basename($name); } else { if (substr($name, -4) == ".css") { $fn = "c/" . basename($name); } else { if (substr($name, -3) == ".js") { $fn = "j/" . basename($name); } } } } } if (!empty($fn)) { file_put_contents(".tmp/" . session_id() . "/" . $fn, $body); } }); if (!self::$success) { Core::error("Bad archive"); return; } } //! choose a html $this->htmls = glob(".tmp/" . session_id() . "/h/*"); if (count($this->htmls) == 1) { $item = 1; } if (intval($item) > 0 && !empty($this->htmls[$item - 1])) { $html = $this->htmls[$item - 1]; unset($this->htmls); } if (empty($html)) { if (intval($item) > 0) { Core::error("Bad archive"); } return; } //! choose application area $data = preg_replace("/<script.*?\\/script>/ims", "", file_get_contents($html)); $files = glob(".tmp/" . session_id() . "/*/*"); $assets = ["i" => "images", "c" => "css", "j" => "js", "f" => "fonts"]; //! replace urls with temporary ones for the uploaded files foreach ($files as $f) { if (!empty($assets[basename(dirname($f))])) { $data = preg_replace("/[^=\\ \t\r\n\\'\",\\(\\[]+" . basename($f) . "/ims", url("cms/sitebuild") . "?assetn=" . basename(dirname($f)) . "/" . basename($f), $data); } if (basename(dirname($f)) == "c") { View::css(url("cms/sitebuild") . "?assetn=" . basename(dirname($f)) . "/" . basename($f)); } else { if (basename(dirname($f)) == "j") { View::jslib(url("cms/sitebuild") . "?assetn=" . basename(dirname($f)) . "/" . basename($f)); } } } //! get the main application tag $this->content = CMS::taghtml($data); if (empty($_REQUEST['chooseid']) && preg_match("/(<[^<>]*?id=[\\'\"]?content[^>]*?>)/ims", $this->content, $m) && !empty($m[0]) && preg_match("/data\\-chooseid=[\\'\"]?([0-9]+)/ims", $m[0], $M)) { $_REQUEST['chooseid'] = $M[1]; } if (!empty($_REQUEST['chooseid'])) { //! replace with <!app> $t = CMS::splithtml($this->content, $_REQUEST['chooseid'], 0) . "<!app>" . CMS::splithtml($this->content, $_REQUEST['chooseid'], 2); //! replace temporary urls with final ones preg_match_all("/[^=\\ \t\r\n\\'\",\\(\\[]+\\?assetn=([a-z])\\/([^=\\ \t\r\n\\'\",\\)\\]]+)/ims", $t, $m, PREG_SET_ORDER); foreach ($m as $M) { $t = str_replace($M[0], $assets[$M[1]] . "/" . $M[2], $t); } //! figure out sitebuild name $name = strtr(basename($html), [".html" => "", ".htm" => ""]); if ($name == "index" || $name == "frame" || $name == "simple" || $name == "default") { $name = "sitebuild" . Core::$core->now; } $views = Views::find($name); if (!empty($views)) { $name .= Core::$core->now; } //! save sitebuild $view = new Views(); $view->id = $name; $view->name = $name; $view->sitebuild = $name; $view->data = preg_replace("/<!\\-\\-.*?\\-\\->/ms", "", $t); $view->created = date("Y-m-d H:i:s", Core::$core->now); foreach ($files as $f) { if (empty($assets[basename(dirname($f))])) { continue; } if (basename(dirname($f)) == "c") { $view->css[] = basename($f); } if (basename(dirname($f)) == "j") { $view->jslib[] = basename($f); } } if ($view->save(true)) { //! copy temporary files to public directory foreach ($assets as $k => $v) { chdir(".tmp/" . session_id() . "/" . $k); Tools::copy(glob("*"), "public/" . $v); chdir("../../.."); } //! clean up @Tools::rmdir(".tmp/" . session_id()); //! redirect user to the fresh new sitebuild layout Http::redirect("cms/layouts/" . $name); } Core::error("Unable to save sitebuild!"); } }
public function edit() { return '<input' . @View::v($this, $this->attrs[1], $this->attrs[0]) . " type='datetime-local' value=\"" . htmlspecialchars(trim($this->value)) . '">'; }
/** * default action, loaded via AJAX */ function action($item) { //! available tags $list = ["/form" => "*variable [url [onsubmitjs", "/if" => "*expression", "else" => "*", "/foreach" => "*dataset", "/template" => "*", "include" => "*view", "app" => "*", "dump" => "variable", "cms" => "*addon ) variable", "=" => "expression", "L" => "label", "date" => "expression", "time" => "expression", "difftime" => "expression", "var" => "*addon ) variable", "field" => "*addon ) variable", "widget" => "*addon ) variable"]; //! Add-Ons $d = array_merge(get_declared_classes(), array_keys(ClassMap::$map)); foreach ($d as $c) { if (strtolower(substr($c, 0, 12)) == "phppe\\addon\\") { $F = new $c([], "dummy", $c, []); if (isset($F->conf) && $F->conf != "*") { $list["_" . strtolower(substr($c, 12))] = $F->conf; } unset($F); } } if (!empty($item)) { //! edit form $acl = $widget = ""; $req = $needsel = 0; if (substr($item, 0, 2) != "<!") { die(View::e("E", L("Unknown tag"))); } else { $d = ""; $c = ""; foreach ($list as $k => $v) { if ($k[0] == "_") { continue; } if (substr($item, 2, strlen($k)) == $k || "/" . substr($item, 2, strlen($k) - 1) == $k) { $d = $k[0] == "/" ? substr($k, 1) : $k; $c = $v[0] == '*' ? substr($v, 1) : $v; } } if (empty($d)) { die(View::e("E", L("Unknown tag"))); } if ($d == "=") { $d = "eval"; $a = [substr($item, 3, strlen($item) - 4)]; } else { $a = str_getcsv(preg_replace("/[\\ ]+/", " ", strtr(substr($item, 2, strlen($item) - 3), ["(," => " - ", "(" => " ", ")" => " )", ",," => " - ", "," => " "])), " "); array_shift($a); } if (substr($c, 0, 5) == "addon") { if (@$a[0][0] == "@") { $acl = substr($a[0], 1); array_shift($a); } if (@$a[0][0] == "*") { $req = 1; $a[0] = substr($a[0], 1); } $widget = array_shift($a); if (empty($widget)) { $widget = "hidden"; } $needsel = 1; } echo "<b>" . L(!empty($widget) && !empty(Core::$l[$widget]) ? $widget : "help_" . $d) . "</b><br/>\n<div id='tageditor' style='padding:5px;'><input type='hidden' name='tag' value='" . htmlspecialchars($d) . "'>\n"; if (substr($c, 0, 5) == "addon") { $t = $d == "cms" ? L("Show value") : L("Required value"); echo "<input type='checkbox' class='input' name='required' onchange='pe.cms.settag(\"tageditor\");' title=\"" . htmlspecialchars($t) . "\" value='*'" . ($req ? " checked" : "") . ">\n"; echo "<select class='input' name='widget' onchange='pe.cms.settag(\"tageditor\");pe.wyswyg.popup(event,\"layout_data\",\"cms/tag?item=" . urlencode("<!" . $d . " " . ($req ? "*" : "")) . "\"+this.value+\">\",true);' onmouseover='pe_w();'>"; foreach ($list as $k => $v) { if ($k[0] != "_") { continue; } echo "<option value='" . htmlspecialchars(substr($k, 1)) . "'" . (substr($k, 1) == $widget ? " selected" : "") . " onmouseover='pe_w();'>" . L(substr($k, 1)) . "</option>\n"; } echo "</select>\n<input type='text' class='input smallinput' name='acl' onkeydown='if(event.key==\"Enter\"){event.preventDefault();pe_p();}' onkeyup='pe.cms.settag(\"tageditor\");event.preventDefault();' onchange='pe.cms.settag(\"tageditor\");' title=\"" . L("Access filters") . "\" placeholder=\"" . L("Access filters") . "\" value=\"" . htmlspecialchars($acl) . "\" list='filters'>"; echo "<datalist id='filters'>"; foreach (ClassMap::ace() as $b) { echo "<option value='" . $b . "'>" . L($b) . "</option>"; } echo "<option value='siteadm|webadm'>" . L("Administrator") . "</option>"; echo "</datalist><br/>\n"; $c = @$list["_" . $widget]; } if (empty($c) || @$item[2] == "/") { die(L("Not configurable")); } if ($c[0] == "*") { $c = substr($c, 1); } $c = str_getcsv(preg_replace("/[\\ ]+/", " ", strtr($c, ["(" => "( ", ")" => " ) ", "[" => " [ ", "]" => "", "," => " "])), " "); if (in_array(")", $c)) { if (!in_array(")", $a)) { array_unshift($a, ")"); } array_shift($c); } if ($c[0] != ")" && in_array(")", $a)) { echo "(<input type='hidden' value='('><br/><div style='padding-left:10px;'>"; } elseif ($c[0] == ")") { array_shift($c); } $i = 0; $optional = ""; $f = 1; $js = 0; foreach ($c as $k => $v) { if ($v == "[") { $optional = " optional"; continue; } if ($v == ")") { echo "</div>)<input type='hidden' value=')'><br/>\n"; while ($a[$i] != ")" && !empty($a[$i])) { $i++; } $i++; $optional = ""; continue; } if (empty($optional) && $f) { $optional = " focus"; $f = 0; } switch ($v) { case "": $i++; break; case "view": $views = Views::find([], "sitebuild=''", "id", "id,name"); foreach (array_merge(glob("app/views/*.tpl"), glob("vendor/phppe/Core/views/*.tpl")) as $view) { $w = str_replace(".tpl", "", basename($view)); if ($w != "frame") { $views[] = ['id' => $w, 'name' => ucfirst($w)]; } } if ($a[$i] == ")") { $i--; } echo "<select class='input" . $optional . "' name='arg" . $k . "' data-type='" . htmlspecialchars($v) . "' " . "onchange='pe.cms.settag(\"tageditor\");' title=\"" . L($v) . "\">"; $w = 0; foreach ($views as $view) { echo "<option value='" . htmlspecialchars($view['id']) . "'" . ($view['id'] == $a[$i] ? " selected" : "") . ">" . L($view['name'] ? $view['name'] : $view['id']) . "</option>"; if ($view['id'] == $a[$i]) { $w = 1; } } if (!$w) { echo "<option value='" . htmlspecialchars($a[$i]) . "' selected>" . (!empty($a[$i]) ? L($a[$i]) : "*") . "</option>"; } echo "</select>\n"; $i++; break; case "min": case "max": case "maxlen": case "rows": case "size": case "picturesize": case "iconheight": case "iconwidth": case "itemheight": case "itemwidth": case "num": echo "<input type='number' class='input" . $optional . "' name='arg" . $k . "' data-type='" . htmlspecialchars($v) . "' " . "onkeyup='pe.cms.settag(\"tageditor\");' onkeydown='if(event.key==\"Enter\"){event.preventDefault();pe_p();}' onchange='pe.cms.settag(\"tageditor\");' title=\"" . L($v) . "\" placeholder=\"" . L($v) . "\" " . "value=\"" . htmlspecialchars(@$a[$i] == ")" ? "" : @$a[$i++]) . "\"><br/>\n"; break; default: echo "<input type='text' class='input" . $optional . "' name='arg" . $k . "' data-type='" . htmlspecialchars($v) . "' " . "onkeyup='pe.cms.settag(\"tageditor\");' onkeydown='if(event.key==\"Enter\"){event.preventDefault();pe_p();}' onchange='pe.cms.settag(\"tageditor\");' title=\"" . L($v) . "\" placeholder=\"" . L($v) . "\" " . "value=\"" . htmlspecialchars(@$a[$i] == ")" ? "" : @$a[$i++]) . "\"" . ($v == "label" || $v == "cssclass" || $v == "dataset" || $v == "listopts" ? " list=\"" . ($v == "listopts" ? "dataset" : $v) . "s\"" : (substr($v, -2) == "js" ? " list='jss'" : "")) . "><br/>\n"; if (substr($v, -2) == "js" && $js == 0) { //! filled in by JavaScript echo "<datalist id=\"jss\"></datalist>\n"; $js = 1; } if ($v == "label" || $v == "cssclass") { //! filled in by JavaScript echo "<datalist id=\"" . $v . "s\"></datalist>\n"; } if ($v == "dataset" || $v == "listopts") { echo "<datalist id=\"datasets\">\n"; $pages = Page::find([], "", "created DESC", "dds", "id"); $dds = []; foreach ($pages as $p) { $g = @json_decode(@$p['dds'], true); if (!empty($g) && is_array($g)) { foreach ($g as $G => $w) { $dds[$G] = $G; } } } ksort($dds); foreach ($dds as $G) { echo "<option value=\"" . htmlspecialchars($G) . "\">" . L($G) . "</option>"; } echo "</datalist>\n"; } } if ($optional == "focus") { $optional = ""; } } } die("</div>\n<small>" . L(!empty(Core::$l['_' . $d]) ? '_' . $d : "") . "</small>"); } else { // tag chooser $onlywidget = strpos($_SERVER['HTTP_REFERER'], "/cms/layouts/") === false; echo "<input type='text' style='width:98%;' placeholder='" . L("Search") . "' onkeyup='pe.wyswyg.search(this,this.nextSibling);'>"; echo "<div class='wyswyg_tag wyswyg_scroll'>\n"; foreach ($list as $tag => $cfg) { if ($cfg[0] == '*' && $onlywidget) { continue; } if (substr($tag, 0, 1) == "_") { $tag = ($onlywidget ? "widget" : "field") . " " . substr($tag, 1); } else { if (substr($tag, 0, 1) == "/") { echo "<img class='wyswyg_icon' src='js/wyswyg.js.php?item=" . urlencode("<!" . substr($tag, 1) . ">") . "' alt=\"" . strtr("<!" . substr($tag, 1) . ">", ["<" => "<", ">" => ">", "\"" => """]) . "\">\n"; } } echo "<img class='wyswyg_icon' src='js/wyswyg.js.php?item=" . urlencode("<!" . $tag . ">") . "' alt=\"" . strtr("<!" . $tag . ">", ["<" => "<", ">" => ">", "\"" => """]) . "\">\n"; } die("</div>"); } }
} //! file import helper if (isset($_REQUEST['impform'])) { $err = $choose = ""; if (!empty($_FILES['upload'])) { if ($_FILES['upload']['type'] == "text/plain") { $choose = @file_get_contents($_FILES['upload']['tmp_name']); } elseif ($_FILES['upload']['type'] == "text/html") { $d = @file_get_contents($_FILES['upload']['tmp_name']); preg_match_all("|<body[^>]*>(.*?)<\\/body|ims", $d, $b, PREG_SET_ORDER); $choose = !empty($b[0][1]) ? $b[0][1] : $d; } else { $err = L("wyswyg_htmlonly"); } } die("<html><head><meta charset='utf-8'/></head><body>" . ($choose ? "<div>" . $choose . "</div><script type='text/javascript'>parent.pe.wyswyg.importdone(\"" . $_REQUEST['impform'] . "\");</script>" : View::_t("<!form>") . "<input type='hidden' name='impform' value='" . $_REQUEST['impform'] . "'>" . "<input type='file' name='upload' onchange='this.form.submit();' id='" . $_REQUEST['impform'] . ":import'>" . ($err ? "alert('" . $err . "');" : "") . "</form>") . "</body></html>"); } $bs = Core::isInst("bootstrap"); //! get toolbars $toolbar = []; $libs = Core::lib(); foreach ($libs as $l) { if (!empty($l->wyswyg_toolbar)) { $toolbar = array_merge($toolbar, $l->wyswyg_toolbar); } } ?> pe.wyswyg = { <?php if ($bs) { ?>
function save($params) { $page = View::getval("page"); $page->setParameter($this->name, str_getcsv($params['value'], ',')[0]); return $page->save(); }
public function testPicture() { $testImg = "vendor/phppe/Developer/images/test.jpg"; if (!function_exists("gd_info") || !file_exists($testImg)) { $this->markTestSkipped(); } //! not image @unlink("data/test1.png"); @unlink("data/test2.png"); \PHPPE\View::picture("no/such/file", "data/test1.png", 64, 64, true, true, "", 64); $this->assertFileNotExists("data/test1.png", "No file"); \PHPPE\View::picture(__FILE__, "data/test1.png", 64, 64, true, true, "", 64); $this->assertFileExists("data/test1.png", "Bad file"); unlink("data/test1.png"); //! test image \PHPPE\View::picture($testImg, "data/test1.png", 64, 64, true, true, "", 64); $this->assertFileExists("data/test1.png", "Thumbnail"); @($im = imagecreatefrompng("data/test1.png")); $this->assertNotNull($im, "Format png"); $this->assertEquals(imagesx($im), 64, "Width"); $this->assertEquals(imagesy($im), 64, "Height"); $this->assertLessThanOrEqual(65536, filesize("data/test1.png"), "Size"); unlink("data/test1.png"); \PHPPE\View::picture($testImg, "data/test1.jpg", 1024, 768, false, false, "", 128); $this->assertFileExists("data/test1.jpg", "Large"); @($im = imagecreatefromjpeg("data/test1.jpg")); $this->assertNotNull($im, "Format jpeg"); $this->assertEquals(imagesx($im), 432, "Width"); $this->assertEquals(imagesy($im), 768, "Height"); $this->assertLessThanOrEqual(131072, filesize("data/test1.jpg"), "Size"); unlink("data/test1.jpg"); //! watermark \PHPPE\View::picture($testImg, "data/test1.jpg", 1024, 768, false, false, "vendor/phppe/Developer/preview", 128); $this->assertFileExists("data/test1.jpg", "Watermark #1"); \PHPPE\View::picture($testImg, "data/test1.jpg", 1024, 768, false, false, "no/such/file", 128); $this->assertFileExists("data/test1.jpg", "Watermark #2"); unlink("data/test1.jpg"); //! portait $im = imagecreatetruecolor(128, 512); $c = 0; for ($y = 0; $y < imagesy($im); $y += floor(imagesy($im) / 255)) { imagefilledrectangle($im, 0, $y, imagesx($im), $y + floor(imagesy($im) / 255), imagecolorallocate($im, $c, $c, $c++)); } imagepng($im, "data/test1.png", 9); \PHPPE\View::picture("data/test1.png", "data/test2.png", 128, 64, true); $this->assertFileExists("data/test2.png", "Portait crop"); @($im = imagecreatefrompng("data/test2.png")); $this->assertNotNull($im, "Format png"); $this->assertEquals(imagesx($im), 128, "Width"); $this->assertEquals(imagesy($im), 64, "Height"); \PHPPE\View::picture("data/test1.png", "data/test2.png", 1024, 1024, false); $this->assertFileExists("data/test2.png", "Portait resize"); @($im = imagecreatefrompng("data/test2.png")); $this->assertNotNull($im, "Format png"); $this->assertEquals(imagesx($im), 256, "Width"); $this->assertEquals(imagesy($im), 1024, "Height"); unlink("data/test1.png"); unlink("data/test2.png"); //! landscape $im = imagecreatetruecolor(512, 128); $c = 0; for ($x = 0; $x < imagesx($im); $x += floor(imagesx($im) / 255)) { imagefilledrectangle($im, $x, 0, $x + floor(imagesx($im) / 255), imagesy($im), imagecolorallocate($im, $c, $c, $c++)); } imagepng($im, "data/test1.png", 9); \PHPPE\View::picture("data/test1.png", "data/test2.png", 64, 128, true); $this->assertFileExists("data/test2.png", "Landscape crop"); @($im = imagecreatefrompng("data/test2.png")); $this->assertNotNull($im, "Format png"); $this->assertEquals(imagesx($im), 64, "Width"); $this->assertEquals(imagesy($im), 128, "Height"); \PHPPE\View::picture("data/test1.png", "data/test2.png", 1024, 1024, false); $this->assertFileExists("data/test2.png", "Landscape resize"); @($im = imagecreatefrompng("data/test2.png")); $this->assertNotNull($im, "Format png"); $this->assertEquals(imagesx($im), 1024, "Width"); $this->assertEquals(imagesy($im), 256, "Height"); unlink("data/test1.png"); unlink("data/test2.png"); }
/** * default action */ function action($item) { //! omit frame and panel and disable cache Core::$core->noframe = true; Core::$core->nopanel = true; Core::$core->nocache = true; //! if not called as it should, return if (empty($item) || $item != sha1("pageadd_") && (empty($_SESSION['cms_url']) || empty($_SESSION['cms_param'][$item]))) { Core::$core->template = "403"; return; } //! get height $this->height = intval(@$_REQUEST['height']); $this->adjust = intval(@$_REQUEST['adjust']); //! save current scroll position to session so that on next //! page load pe.cms.init() will use it if (isset($_REQUEST['scrx'])) { $_SESSION['cms_scroll'] = [$_REQUEST['scrx'], $_REQUEST['scry']]; } //! get available access control entries $this->ace = ClassMap::ace(); foreach ($this->ace as $k => $v) { $this->ace[$k] = "@" . $v; } $this->ace[] = "@siteadm|webadm"; $this->ace[] = "loggedin"; $this->ace[] = "csrf"; $this->ace[] = "get"; $this->ace[] = "post"; //! get the field we're editing $F = clone $_SESSION["cms_param"][$item]; $F->fld = "page_value"; if (get_class($F) == "PHPPE\\AddOn\\wyswyg") { $F->args = [0, "pe.cms.image"]; } if (method_exists($F, 'init')) { $F->init(); } $this->fieldTitle = $F->name; $this->heightClass = @$F->heightClass; $this->boxHeight = $this->height - @$F->headerHeight; //! get the page we're editing //! if parameter name starts with "frame", load frame page instead $page = new Page(substr($F->name, 0, 6) == "frame." ? "frame" : @$_SESSION['cms_url']); $this->editable = $page->lock(); View::assign("page", $page); $n = substr($F->name, 0, 6) == "frame." ? substr($F->name, 6) : (substr($F->name, 0, 4) == "app." ? substr($F->name, 4) : $F->name); if (!empty($page->data[$n])) { $F->value = $page->data[$n]; } //! load extra data if any if (method_exists($F, 'load')) { $F->load($this); } //! save page parameter $param = Core::req2arr("page"); if (!empty($param) && $this->editable) { //! if there was no validation error if (!Core::isError()) { if (method_exists($F, "save")) { //! if it's a special field with it's own save mechanism $param['pageid'] = $page->id; if (!$F->save($param)) { Core::error(L("Unable to save page!")); } } else { //! otherwise standard page parameter $page->setParameter($F->name, $param['value']); if (!$page->save()) { Core::error(L("Unable to save page!")); } } //! close the modal if save was successful if (!Core::isError()) { //! release the page lock $page->release(); die("<html><script>parent.pe.cms.close(true);</script></html>"); } } //! copy the form data. normally you don't need to do that //! but here form name and object name differs, so it's not automatic foreach ($param as $k => $v) { $page->{$k} = $v; } } //! get the input(s) if (method_exists($F, 'edit')) { $this->field = $F->edit(); } else { //! fallback to a simple input field. Should never happen $this->field = "<input type='text' class='input" . (Core::isError("page.value") ? " errinput" : "") . "' name='page_value' value=\"" . htmlspecialchars($F->value) . "\">"; } //! focus first input View::js("init()", "var inp=document.querySelector('.reqinput,.input');if(inp!=null){inp.focus();inp.selectionStart=inp.selectionEnd=(inp.value!=null?inp.value:inp.innerHTML).length;}", true); }
public function testCache() { \PHPPE\Core::$core->nocache = false; $dir = "vendor/phppe/Developer"; \PHPPE\View::setPath($dir); \PHPPE\Core::$user->id = ""; //test if there's no cache $mc = \PHPPE\Cache::$mc; $cache = new \PHPPE\Cache("files"); $cache->set('aaa', 1); $cache->get('aaa'); \PHPPE\Cache::$mc = null; $cache->set('aaa', 1); $cache->get('aaa'); \PHPPE\Cache::$mc = $mc; //use memcached cache if otherwise not configured if (empty($mc) || empty(\PHPPE\Core::$core->cache)) { $mem = new \PHPPE\Cache("127.0.0.1:11211"); } \PHPPE\Core::$core->nocache = false; if (empty(\PHPPE\Cache::$mc)) { $mem = new \PHPPE\Cache("files"); } if (empty(\PHPPE\Cache::$mc)) { $this->markTestSkipped(); } $this->assertNotEmpty(\PHPPE\Cache::$mc, "Cache initialized"); $var = "t_00" . time(); \PHPPE\Core::$core->nocache = true; $this->assertFalse(\PHPPE\Cache::set($var, "aaa"), "Set with nocache"); $this->assertNull(\PHPPE\Cache::get($var), "Get with nocache"); \PHPPE\Core::$core->nocache = false; $this->assertNotFalse(\PHPPE\Cache::set($var, "aaa"), "Set"); $this->assertEquals("aaa", \PHPPE\Cache::get($var), "Get"); $tn = 't_' . sha1(\PHPPE\Core::$core->base . "_cachetest"); \PHPPE\Cache::set($tn, "", 1); $txt = \PHPPE\View::template("cachetest", ["var" => "value"]); $this->assertNotEmpty(\PHPPE\Cache::get($tn), "Template caching {$tn}"); $sha = \PHPPE\Core::$core->base . "tests/http/cachetest/" . \PHPPE\Core::$user->id . "/" . \PHPPE\Core::$client->lang; $N = 'p_' . sha1($sha); \PHPPE\Cache::set($N, "", 1); $this->assertEmpty(\PHPPE\View::fromCache($N), "Page cache #1 " . $N); $url = url("tests", "http") . "cachetest"; if (trim(@file_get_contents($url)) == '') { $url = str_replace("public/", "", $url); } file_get_contents($url); //make sure the output gets to the cache $d1 = file_get_contents($url); //this must be served from cache $this->assertNotEmpty(\PHPPE\View::fromCache($N), "Page cache #2 (Configure cache '127.0.0.1:11211' in config.php if fails)"); $d2 = file_get_contents($url . "?skipcache=1"); //trigger nocache flag set in constructor $this->assertNotFalse(strpos($d1, ", mc -->"), "Output cache #1"); $this->assertFalse(strpos($d1, "NOCACHE"), "Output cache #2"); $this->assertFalse(strpos($d2, ", mc -->"), "Output cache #3"); $this->assertNotFalse(strpos($d2, "NOCACHE"), "Output cache #4"); if (method_exists(\PHPPE\Cache::$mc, "cronMinute")) { \PHPPE\Cache::$mc->cronMinute(""); } }
function edit() { return View::template("cms_pagehist"); }
/** * default action */ function action($item) { //! check access rights if (!Core::$user->has("siteadm|webadm")) { Http::redirect("403"); } //! if we have to delete a page version if (isset($_REQUEST['pagedel'])) { if (!empty($_REQUEST['created'])) { Page::delete($item, $_REQUEST['created']); } Http::redirect($item); } //! revert to an old version of the page if (isset($_REQUEST['revert'])) { if (!empty($_REQUEST['created'])) { Core::log('A', sprintf("Page %s reverted to %s by %s", $item, $_REQUEST['created'], Core::$user->name), "cmsaudit"); DS::exec("UPDATE pages set created=CURRENT_TIMESTAMP,modifyd=CURRENT_TIMESTAMP,modifyid=? WHERE id=? AND (lang='' OR lang=?) AND created=?", [Core::$user->id, $item, Core::$client->lang, $_REQUEST['created']]); } Http::redirect($item); } //! get the latest public version's date if (empty($_REQUEST['created'])) { $_REQUEST['created'] = DS::field("created", "pages", "(id=? OR ? LIKE id||'/%') AND (lang='' OR lang=?) AND publishid!=0", "", "id DESC,created DESC", [$item, $item, Core::$client->lang]); if (empty($_REQUEST['created'])) { $_REQUEST['created'] = DS::field("created", "pages", "(id=? OR ? LIKE id||'/%') AND (lang='' OR lang=?)", "", "id DESC,created ASC", [$item, $item, Core::$client->lang]); } } //! load frame page for page parameters and dds $frame = DS::fetch("data,dds", "pages", "id='frame' AND (lang='' OR lang=?) AND created<=?", "", "", [Core::$client->lang, $_REQUEST['created']]); $frame['dss'] = @json_decode($frame['dds'], true); $frame['data'] = @json_decode($frame['data'], true); View::assign("frame", $frame['data']); //! load archive version //! normally you would use Model, but that would only return the latest version $page = DS::fetch("*", "pages", "(id=? OR ? LIKE id||'/%') AND (lang='' OR lang=?) AND created=?", "", "id DESC,created DESC", [$item, $item, Core::$client->lang, $_REQUEST['created']]); $this->title = $page['name']; $title = L("ARCHIVE") . " " . $page['name']; if (is_string($page['data'])) { $page['data'] = @json_decode($page['data'], true); } if (is_array($page['data'])) { foreach ($page['data'] as $k => $v) { $this->{$k} = $v; } } foreach (["id", "name", "lang", "filter", "template", "pubd", "expd", "dds", "ownerid", "created"] as $k) { $this->{$k} = $page[$k]; } $p = @array_merge($frame['dds'], @json_decode($page['dds'], true)); if (is_array($p)) { foreach ($p as $k => $c) { if ($k != "dds") { try { $this->{$k} = DS::query($c[0], $c[1], @$c[2], @$c[3], @$c[4], @$c[5], View::getval(@$c[6])); } catch (\Exception $e) { Core::log("E", $item . " " . $e->getMessage() . " " . implode(" ", $c), "dds"); } } } } $old = View::template($this->template); //! if we have to compare to an older (or the latest) version if (isset($_REQUEST['diff'])) { include_once "vendor/phppe/CMS/libs/simplediff.php"; //! load current version $frame = DS::fetch("data,dds", "pages", "id='frame' AND (lang='' OR lang=?) AND publishid!=0", "", "created DESC", [Core::$client->lang]); $frame['dss'] = @json_decode($frame['dds'], true); $frame['data'] = @json_decode($frame['data'], true); View::assign("frame", $frame['data']); $page = DS::fetch("*", "pages", "id=? OR ? LIKE id||'/%'", "", "id DESC,created DESC", [$item, $item]); if (is_string($page['data'])) { $page['data'] = @json_decode($page['data'], true); } if (is_array($page['data'])) { foreach ($page['data'] as $k => $v) { $this->{$k} = $v; } } foreach (["id", "name", "lang", "filter", "template", "pubd", "expd", "dds", "ownerid", "created"] as $k) { $this->{$k} = $page[$k]; } $p = @array_merge($frame['dds'], @json_decode($page['dds'], true)); if (is_array($p)) { foreach ($p as $k => $c) { if ($k != "dds") { try { $this->{$k} = DS::query($c[0], $c[1], @$c[2], @$c[3], @$c[4], @$c[5], View::getval(@$c[6])); } catch (\Exception $e) { Core::log("E", $item . " " . $e->getMessage() . " " . implode(" ", $c), "dds"); } } } } $this->title = $page['name']; $curr = View::template($this->template); //! make sure diff splits on tag end $this->result = htmlDiff(preg_replace("/>([^\\ \t\n])/m", "> \\1", $old), preg_replace("/>([^\\ \t\n])/m", "> \\1", $curr)); //! remove diff inside tags $this->result = preg_replace("/(<[^<>]+)<ins>.*?<\\/ins>([^<>]*>)/ims", "\\1\\2", $this->result); $this->result = preg_replace("/(<[^<>]+)<del>(.*?)<\\/del>([^<>]*>)/ims", "\\1\\2\\3", $this->result); } else { $this->result = $old; } $this->title = $title; }
public function testTemplater() { $this->assertNotFalse(strpos(\PHPPE\View::template("test1"), "TOOMNY"), "Template #1"); $this->assertNotEmpty(\PHPPE\View::template("404"), "Template #2"); $this->assertEmpty(\PHPPE\View::template("nosuchtemplate"), "Template #3"); $obj = new \stdClass(); $obj->dynamicname = "dyntest"; $obj->arr = ["a", "b", "c"]; $obj->arr2 = [["A" => "a"], ["A" => "b"], ["A" => "c"]]; $obj->now = time(); $obj->singlearr = ["a"]; $obj->arrs = unserialize('a:2:{i:0;a:2:{s:2:"id";s:5:"frame";s:4:"name";s:7:"Default";}i:1;a:2:{s:2:"id";s:6:"simple";s:4:"name";s:6:"Simple";}}'); $obj->objs = unserialize('a:2:{i:0;O:8:"stdClass":2:{s:2:"id";s:5:"frame";s:4:"name";s:5:"Frame";}i:1;O:8:"stdClass":2:{s:2:"id";s:6:"simple";s:4:"name";s:6:"Simple";}}'); $obj->spec[0] = new \stdClass(); $obj->spec[0]->id = 1; $obj->spec[0]->name = [1, 2, 3]; $obj->emptyStr = ""; \PHPPE\View::assign("obj", $obj); \PHPPE\View::assign("app", $obj); \PHPPE\View::assign("core", \PHPPE\Core::$core); $this->assertEquals("dynamic name", \PHPPE\View::_t("<!include dynamicname>"), "Dynamic name"); $this->assertEquals("<!-- not removed -->test", \PHPPE\View::_t("<!-- not removed -->test"), "Comment"); $this->assertEquals("<!app>", \PHPPE\View::_t("<!app>"), "App tag"); $this->assertEquals(\PHPPE\Core::$core->now . "", \PHPPE\View::_t("<!=core.now>"), "Expression #1"); $this->assertNotFalse(strpos(\PHPPE\View::_t("<!=core.now=1>"), "INP"), "Expression #2"); $this->assertEquals("aa\"bb", \PHPPE\View::_t('<!="aa\\"bb">'), "Expression #3"); $this->assertFalse(strpos(\PHPPE\View::_t("<!=sprintf('aaabbb')>"), "BADFNC"), "Expression #4"); \PHPPE\View::$C = []; \PHPPE\Core::$core->allowed = ["number_format"]; $this->assertNotFalse(strpos(\PHPPE\View::_t("<!=sprintf('aaabbb')>"), "BADFNC"), "Expression #5"); \PHPPE\Core::$core->allowed = []; unset(\PHPPE\Core::$l['aaa_bbb']); $this->assertEquals("aaa bbb", \PHPPE\View::_t('<!L aaa_bbb>'), "Language"); $this->assertNotFalse(strpos(\PHPPE\View::_t("<!notag>"), "UNKTAG"), "Unknown tag"); $this->assertNotFalse(strpos(\PHPPE\View::_t('<!var noSuchAddon>'), "UNKADDON"), "Unknown AddOn"); \PHPPE\Core::$l['min'] = "m"; \PHPPE\Core::$l['mins'] = "ms"; \PHPPE\Core::$l['hour'] = "h"; \PHPPE\Core::$l['hours'] = "hs"; \PHPPE\Core::$l['day'] = "d"; \PHPPE\Core::$l['days'] = "ds"; $this->assertEquals("0 m", \PHPPE\View::_t('<!difftime 1>'), "Difftime #1"); $this->assertEquals("1 m", \PHPPE\View::_t('<!difftime 60>'), "Difftime #2"); $this->assertEquals("2 ms", \PHPPE\View::_t('<!difftime 120>'), "Difftime #3"); $this->assertEquals("1 h", \PHPPE\View::_t('<!difftime 3600>'), "Difftime #4"); $this->assertEquals("1 h, 1 m", \PHPPE\View::_t('<!difftime 3660>'), "Difftime #5"); $this->assertEquals("2 hs, 2 ms", \PHPPE\View::_t('<!difftime 3660*2>'), "Difftime #6"); $this->assertEquals("1 d", \PHPPE\View::_t('<!difftime 3600*24>'), "Difftime #7"); $this->assertEquals("2 ds", \PHPPE\View::_t('<!difftime 3600*48>'), "Difftime #8"); $this->assertEquals("2 ds", \PHPPE\View::_t('<!difftime 3600*50>'), "Difftime #9"); $this->assertEquals("- 2 ms", \PHPPE\View::_t('<!difftime -120>'), "Difftime #10"); $this->assertEquals("1 m", \PHPPE\View::_t('<!difftime 3660 3600>'), "Difftime #11"); $this->assertEquals("-", \PHPPE\View::_t('<!difftime obj.emptyStr 10>'), "Difftime #12"); $this->assertEquals("aaa", \PHPPE\View::_t("<!template>aaa<!/template>"), "Reentrant #1"); $this->assertEquals(\PHPPE\Core::$core->now, \PHPPE\View::_t("<!template><%=core.now><!/template>"), "Reentrant #2"); $this->assertEquals("011a120b231c", \PHPPE\View::_t("<!foreach arr><!=KEY><!=IDX><!=ODD><!=VALUE><!/foreach>"), "Foreach #1"); $this->assertEquals("abc", \PHPPE\View::_t("<!foreach obj.arr2><!=A><!/foreach>"), "Foreach #2"); $this->assertNotFalse(strpos(\PHPPE\View::_t("!foreach obj.arr2><!=A><!/foreach>"), "UNCLS"), "Foreach #3"); $this->assertEquals("0a0b0c1a1b1c2a2b2c", \PHPPE\View::_t("<!foreach arr><!foreach obj.arr2><!=parent.KEY><!=A><!/foreach><!/foreach>"), "Foreach #4"); $this->assertEquals("01101a00102b01103c11001a10002b11003c21101a20102b21103c01111a00112b01113c11011a10012b11013c21111a20112b21113c01121a00122b01123c11021a10022b11023c21121a20122b21123c", \PHPPE\View::_t("<!foreach arr><!foreach obj.arr><!foreach obj.arr2><!=parent.KEY><!=ODD><!=parent.ODD><!=parent.parent.KEY><!=IDX><!=A><!/foreach><!/foreach><!/foreach>"), "Foreach #5"); $this->assertEquals("a0framea0framea1simplea1simple", \PHPPE\View::_t("<!foreach obj.arrs><!foreach VALUE>a<!=parent.KEY><!=parent.id><!/foreach><!/foreach>"), "Foreach #6"); $this->assertEquals("frameFramesimpleSimple", \PHPPE\View::_t("<!foreach obj.objs><!=id><!=name><!=none><!/foreach>"), "Foreach #7"); $this->assertEquals("A", \PHPPE\View::_t("<!if true>A<!else>B<!/if>"), "If true"); $this->assertEquals("B", \PHPPE\View::_t("<!if false>A<!else>B<!/if>"), "If false"); $this->assertEquals(1, preg_match("|<form name='a' action='[^']+' class='form-vertical' method='post' enctype='multipart/form-data'><input type='hidden' name='MAX_FILE_SIZE' value='[0-9]+'><input type='hidden' name='pe_s' value='[a-fA-F0-9]*'><input type='hidden' name='pe_f' value='a'>|ims", \PHPPE\View::_t("<!form a>")), "Form #1"); $this->assertEquals(1, preg_match("|<form name='a' action='([^']+)' class='form-vertical' method='post' enctype='multipart/form-data'><input type='hidden' name='MAX_FILE_SIZE' value='[0-9]+'><input type='hidden' name='pe_s' value='[a-fA-F0-9]*'><input type='hidden' name='pe_f' value='a'>|ims", \PHPPE\View::_t("<!form a form-vertical b/c>"), $m), "Form #2"); $this->assertEquals("b/c/", substr($m[1], -4), "Form #2 url"); $this->assertEquals(1, preg_match("|<form role='form' name='a' action='([^']+)' class='form-vertical' method='post' enctype='multipart/form-data' onsubmit=\"d\\(\\)\"><input type='hidden' name='MAX_FILE_SIZE' value='[0-9]+'><input type='hidden' name='pe_s' value='[a-fA-F0-9]*'><input type='hidden' name='pe_f' value='a'>|ims", \PHPPE\View::_t("<!form a - b/c d() role>"), $m), "Form #3"); $this->assertEquals("b/c/", substr($m[1], -4), "Form #3 url"); $this->assertEquals(1, preg_match("|<form name='a' action='([^']+)' class='form-vertical' method='post' enctype='multipart/form-data' onsubmit=\"d\\(\\)\"><input type='hidden' name='MAX_FILE_SIZE' value='[0-9]+'><input type='hidden' name='pe_s' value='[a-fA-F0-9]*'><input type='hidden' name='pe_f' value='a'>|ims", \PHPPE\View::_t("<!form a - - d()>")), "Form #4"); $_SESSION['pe_c'] = $_SESSION['pe_e'] = false; $this->assertEquals("show1", \PHPPE\View::_t('<!var test1 test>'), "var tag (pe_c=0,pe_e=0,show)"); $this->assertEquals("show1", \PHPPE\View::_t('<!widget test1 test>'), "widget tag (pe_c=0,pe_e=0,show)"); $this->assertEquals("edit1", \PHPPE\View::_t('<!field test1 test>'), "field tag (pe_c=0,pe_e=0,edit)"); $_SESSION['pe_c'] = true; $this->assertEquals("show1", \PHPPE\View::_t('<!var test1 test>'), "var tag (pe_c=1,pe_e=0,show)"); $this->assertEquals("edit1", \PHPPE\View::_t('<!widget test1 test>'), "widget tag (pe_c=1,pe_e=0,edit)"); $this->assertEquals("edit1", \PHPPE\View::_t('<!field test1 test>'), "field tag (pe_c=1,pe_e=0,edit)"); $_SESSION['pe_c'] = false; $_SESSION['pe_e'] = true; $this->assertEquals("edit1", \PHPPE\View::_t('<!var test1 test>'), "var tag (pe_c=0,pe_e=1,edit)"); $this->assertEquals("show1", \PHPPE\View::_t('<!widget test1 test>'), "widget tag (pe_c=0,pe_e=1,show)"); $this->assertEquals("edit1", \PHPPE\View::_t('<!field test1 test>'), "field tag (pe_c=0,pe_e=1,edit)"); $_SESSION['pe_c'] = $_SESSION['pe_e'] = false; $this->assertNotFalse(strpos(\PHPPE\View::_t('<!field *text test>'), "required"), "field tag (required)"); \PHPPE\Core::$user->id = 1; $this->assertEmpty(\PHPPE\View::_t('<!var @noacl test1 test>'), "var tag (noacl)"); $this->assertEmpty(\PHPPE\View::_t('<!field @noacl test1 test>'), "field tag (noacl)"); \PHPPE\Core::$user->id = -1; $this->assertEquals("show1", \PHPPE\View::_t('<!var @noacl test1 test>'), "var tag (noacl admin)"); $this->assertEquals("edit1", \PHPPE\View::_t('<!field @noacl test1 test>'), "field tag (noacl admin)"); $u = \PHPPE\Core::$user->id; \PHPPE\Core::$user->id = 0; $this->assertEquals("", \PHPPE\View::_t('<!cms test1 test>'), "cms tag #1"); $this->assertEquals("show1", \PHPPE\View::_t('<!cms *test1 test>'), "cms tag #2"); \PHPPE\Core::$user->id = -1; $app = new \PHPPE\Content(); \PHPPE\View::assign("app", $app); $this->assertNotFalse(strpos(\PHPPE\View::_t('<!cms test1 test>'), "cms.edit"), "cms tag #3"); \PHPPE\Core::$user->id = $u; $this->assertEquals("show3", \PHPPE\View::_t('<!var test3 test>'), "Addon init"); \PHPPE\Core::$l['dateformat'] = "Y-m-d"; \PHPPE\Core::$l['testdate'] = "2001-02-03 04:05:06"; date_default_timezone_set("UTC"); $this->assertEquals("2001-02-03", \PHPPE\View::_t('<!date L("testdate")>'), "Date #1"); $this->assertEquals("2001-02-03 04:05:06", \PHPPE\View::_t('<!time L("testdate")>'), "Time #1"); $this->assertEquals("1970-01-01", \PHPPE\View::_t('<!date 1>'), "Date #2"); $this->assertEquals(1, preg_match("/1970-01-01 [0-9]+:00:01/", \PHPPE\View::_t("<!time 1>")), "Time #2"); \PHPPE\Core::$core->runlevel = 0; $this->assertEmpty(\PHPPE\View::_t('<!dump obj>'), "Dump #1"); \PHPPE\Core::$core->runlevel = 1; $this->assertEquals(1, preg_match("/stdClass Object/", \PHPPE\View::_t("<!dump obj>")), "Dump #2"); \PHPPE\Core::$core->runlevel = 2; $d = \PHPPE\View::_t("<!dump obj>"); $this->assertEquals(1, preg_match("/string\\(7\\) \"dyntest\"/", $d) || preg_match("/var\\-dump/", $d), "Dump #3"); $this->assertEquals(0, preg_match("/pe_u/", \PHPPE\View::_t("<!dump _SESSION>")), "Dump #4"); \PHPPE\Core::$core->noframe = false; \PHPPE\Core::$core->output = "html"; \PHPPE\Core::$user->id = -1; $this->assertEquals(1, preg_match("/bbb/", \PHPPE\View::generate("test1", "t_" . sha1(\PHPPE\Core::$core->base . "_test1"))), "Generate"); \PHPPE\Cache::$mc = null; ob_start(); $txt = "TEST"; @\PHPPE\View::output($txt); $this->assertEquals(1, preg_match("/TEST/", ob_get_clean()), "Output #1"); \PHPPE\Cache::$mc = new \PHPPE\Cache\Files("files"); \PHPPE\Core::$core->nocache = false; \PHPPE\Core::$core->noaggr = false; $obj->favicon = "favicon.png"; $_SESSION['pe_ls'] = ["en" => "en"]; \PHPPE\View::menu("aaa", "aaa/bbb"); \PHPPE\View::menu("ccc", ["ccc" => "ccc/ddd"]); //save it to cache $sha = \PHPPE\Core::$core->base . \PHPPE\Core::$core->url . "/" . \PHPPE\Core::$user->id . "/" . \PHPPE\Core::$client->lang; \PHPPE\Cache::set("c_" . sha1($sha . "_css"), ""); \PHPPE\Cache::set("c_" . sha1($sha . "_js"), ""); ob_start(); @\PHPPE\View::output($txt); $this->assertEquals(1, preg_match("/div class='menu'/", ob_get_clean()), "Output #2"); //read from cache ob_start(); @\PHPPE\View::output($txt); $this->assertEquals(1, preg_match("/div class='menu'/", ob_get_clean()), "Output #3"); ob_start(); @\PHPPE\View::output($txt, "aaa"); $this->assertEquals(1, preg_match("/<\\/span><span class='menu_a'>/", ob_get_clean()), "Active menu #1"); ob_start(); @\PHPPE\View::output($txt, "ccc"); $this->assertEquals(1, preg_match("/class='menu_a' onclick/", ob_get_clean()), "Active menu #2"); }
function edit() { View::jslib("setsel.js", "pe.setsel.search('" . addslashes($this->fld) . "');"); View::css("setsel.css"); $out = [0 => "", 1 => ""]; $a = $this->attrs; $opts = !empty($a[0]) && $a[0] != "-" ? View::getval($a[0]) : []; if (is_string($opts)) { $opts = str_getcsv($opts, ","); } if (!is_array($opts)) { $opts = ""; } if (is_string($this->value)) { $val = explode(",", $this->value); } elseif (isset($this->value[0]['id'])) { $val = []; foreach ($this->value as $k => $v) { $val[$k] = $v['id']; } } else { $val = $this->value; } if (empty($val)) { $val = []; } $i = @array_flip($val); $b = []; if (!empty($this->args[2])) { if (!is_array($this->args[2])) { $f = @array_flip(explode(",", $this->args[2])); } else { $f = $this->args[2]; } } else { $f = []; } $flt = []; $filters = []; $idx = []; foreach ($f as $k => $v) { $d = explode(":", $k); if (!empty($d[1])) { $filters[$d[0]] = $v; $idx[$d[0]] = $d[1]; } else { $filters[$d[0]] = $v; } } foreach ($opts as $k => $v) { $id = $k; $name = $v; $title = ""; $blk = "<div"; $rep = !empty($this->args[3]) ? $this->args[3] : "%name%"; $rep = str_ireplace("%KEY%", $k, $rep); if (is_array($v) || is_object($v)) { foreach ($v as $K => $V) { if (isset($filters[$K])) { $flt[$K][$V] = !empty($idx[$K]) && !empty($v[$idx[$K]]) ? $v[$idx[$K]] : $V; } if (!is_scalar($V)) { continue; } $rep = str_ireplace("%" . $K . "%", $V . "", $rep); if (!empty($this->args[5]) && $K == trim($this->args[5])) { $title = $V; } if ($K == "name") { $name = $V; } else { if ($K == "id") { $id = $V; } else { $blk .= " data-" . $K . "=\"" . htmlspecialchars($V) . "\""; } } } } else { $rep = str_ireplace("%VALUE%", $v, $rep); } $blk .= " class='setsel_item" . (!empty($this->args[0]) && isset($i[$id]) ? " setsel_itemactive" : "") . (!empty($a[2]) && $a[2] != "-" ? " " . $a[2] : "") . "'"; if ($title) { $blk .= " title='" . htmlspecialchars($title) . "'"; } $blk .= " data-id='" . htmlspecialchars($id) . "' draggable='false' onmousedown='return pe.setsel." . (empty($this->args[0]) ? "drag" : "select") . "(event,\"" . $this->fld . "\");':display>" . $rep . "</div>"; if (isset($i[$id])) { $b[$i[$id]] = str_replace(":display", "", $blk); } $blk = str_replace(":display", empty($this->args[0]) && isset($i[$id]) ? " data-inlist='1' style='display:none;'" : "", $blk); if (empty($this->args[0]) || !isset($i[$id])) { $out[1] .= $blk; } else { $out[1] = $blk . $out[1]; } } if (empty($this->args[0])) { ksort($b); } else { $out[1] .= "<div class='setsel_item" . (!empty($this->args[0]) && empty($b) ? " setsel_itemactive" : "") . (!empty($a[2]) && $a[2] != "-" ? " " . $a[2] : "") . "' data-id='' onmousedown='return pe.setsel.select(event,\"" . $this->fld . "\");' style='text-align:center;font-style:italic;'> * " . L("None") . " *</div>"; } if (isset($flt['lang'])) { unset($flt['lang']); foreach ($_SESSION['pe_ls'] as $l => $v) { $flt['lang'][$l] = $l . " " . L($l); } } $flthtml = !empty($a[3]) ? $a[3] : ""; foreach ($filters as $f => $v) { if ($f) { $flthtml .= "<select class='setsel_input' name='" . $f . "' onchange='pe.setsel.search(\"" . $this->fld . "\");' style='margin-right:5px;'><option value=''>*</option>"; if (is_array($flt[$f])) { foreach ($flt[$f] as $F => $V) { if (!empty($F) && !empty($V)) { $flthtml .= "<option value=\"" . htmlspecialchars($F) . "\"" . (@$_REQUEST['setsel_' . $f] == $F ? " selected" : "") . ">" . L($V) . "</option>"; } } } $flthtml .= "</select>"; } } $out[0] = implode("", $b); return "<div class='setsel'><input type='hidden' id='" . $this->fld . "' name='" . $this->fld . "' value='" . htmlspecialchars(@implode(",", $val)) . "'>" . "<div id='" . $this->fld . ":filters' class='setsel_filters'>" . (!empty($this->args[4]) ? "<span class='setsel_title' style='float:left;line-height:22px !important;'>" . $this->args[4] . "</span>" : "") . $flthtml . "<input name='search' class='setsel_input' type='text' placeholder='" . L("Search") . "' onchange='pe.setsel.search(\"" . $this->fld . "\");' onkeyup='pe.setsel.search(\"" . $this->fld . "\");'>" . "<span style='font-size:20px;padding-left:5px;padding-right:5px;'>⌕</span><br style='clear:both;'/></div>\n" . "<div class='" . $this->css . " " . (!empty($a[1]) && $a[1] != "-" ? $a[1] : "") . " setsel_box' onmouseup=\"pe.dnd.drop(event,pe.setsel.remove);\" id='" . $this->fld . ":all' style='height:" . intval(!empty($this->args[1]) ? $this->args[1] : 128) . "px;" . (!empty($this->args[0]) ? "width:100% !important;" : "") . "box-sizing:border-box;overflow:auto;'>" . $out[1] . "</div>" . (empty($this->args[0]) ? "<div class='" . $this->css . " " . (!empty($a[1]) && $a[1] != "-" ? $a[1] : "") . " setsel_box' onmouseover='pe.setsel.droparea(event);' onmouseup=\"pe.dnd.drop(event,pe.setsel.add);\" id='" . $this->fld . ":inlist' style='height:" . intval(!empty($this->args[1]) ? $this->args[1] : 128) . "px;padding-bottom:64px;box-sizing:border-box;overflow:auto;'>" . $out[0] . "</div>" : "") . "</div>"; }
function action($item) { Core::$core->template = ""; View::js("init()", "pe.extensions.init();", true); }