| @@ -446,12 +446,6 @@ $actionSearch[10] = array( | |||||
| 'purview' =>'sys_data', | 'purview' =>'sys_data', | ||||
| 'linkurl' =>'sys_sql_query.php' | 'linkurl' =>'sys_sql_query.php' | ||||
| ), | ), | ||||
| 13 => array( | |||||
| 'title' =>'文件校验[S]', | |||||
| 'description' =>'文件校验将检查本站文件是否和dedecms原始文件是否完全一致', | |||||
| 'purview' =>'sys_verifies', | |||||
| 'linkurl' =>'sys_verifies.php' | |||||
| ), | |||||
| 14 => array( | 14 => array( | ||||
| 'title' =>'病毒扫描[S]', | 'title' =>'病毒扫描[S]', | ||||
| 'description' =>'以DedeCMS开发模式为标准对现有的文件进行扫描并进行判断', | 'description' =>'以DedeCMS开发模式为标准对现有的文件进行扫描并进行判断', | ||||
| @@ -72,7 +72,6 @@ $adminMenu2 = "<m:top item='7_' name='模板管理' display='none' rank='temp_On | |||||
| <m:item name='计划任务管理' link='sys_task.php' rank='sys_Task' target='main' /> | <m:item name='计划任务管理' link='sys_task.php' rank='sys_Task' target='main' /> | ||||
| <m:item name='数据库备份/还原' link='sys_data.php' rank='sys_Data' target='main' /> | <m:item name='数据库备份/还原' link='sys_data.php' rank='sys_Data' target='main' /> | ||||
| <m:item name='SQL命令行工具' link='sys_sql_query.php' rank='sys_Data' target='main' /> | <m:item name='SQL命令行工具' link='sys_sql_query.php' rank='sys_Data' target='main' /> | ||||
| <m:item name='文件校验[S]' link='sys_verifies.php' rank='sys_verify' target='main' /> | |||||
| <m:item name='病毒扫描[S]' link='sys_safetest.php' rank='sys_verify' target='main' /> | <m:item name='病毒扫描[S]' link='sys_safetest.php' rank='sys_verify' target='main' /> | ||||
| <m:item name='系统错误修复[S]' link='sys_repair.php' rank='sys_verify' target='main' /> | <m:item name='系统错误修复[S]' link='sys_repair.php' rank='sys_verify' target='main' /> | ||||
| </m:top> | </m:top> | ||||
| @@ -123,7 +123,6 @@ $menusMain = " | |||||
| <m:item name='计划任务管理' link='sys_task.php' rank='sys_Task' target='main' /> | <m:item name='计划任务管理' link='sys_task.php' rank='sys_Task' target='main' /> | ||||
| <m:item name='数据库备份/还原' link='sys_data.php' rank='sys_Data' target='main' /> | <m:item name='数据库备份/还原' link='sys_data.php' rank='sys_Data' target='main' /> | ||||
| <m:item name='SQL命令行工具' link='sys_sql_query.php' rank='sys_Data' target='main' /> | <m:item name='SQL命令行工具' link='sys_sql_query.php' rank='sys_Data' target='main' /> | ||||
| <m:item name='文件校验[S]' link='sys_verifies.php' rank='sys_verify' target='main' /> | |||||
| <m:item name='病毒扫描[S]' link='sys_safetest.php' rank='sys_verify' target='main' /> | <m:item name='病毒扫描[S]' link='sys_safetest.php' rank='sys_verify' target='main' /> | ||||
| <m:item name='系统错误修复[S]' link='sys_repair.php' rank='sys_verify' target='main' /> | <m:item name='系统错误修复[S]' link='sys_repair.php' rank='sys_verify' target='main' /> | ||||
| </m:top> | </m:top> | ||||
| @@ -45,13 +45,12 @@ if($dopost=='savetag') | |||||
| { | { | ||||
| $fulltag = addslashes($fulltag); | $fulltag = addslashes($fulltag); | ||||
| $tagname = "auto"; | $tagname = "auto"; | ||||
| $inQuery = " | |||||
| INSERT INTO #@__mytag(typeid,tagname,timeset,starttime,endtime,normbody,expbody) | |||||
| $inQuery = "INSERT INTO `#@__mytag`(typeid,tagname,timeset,starttime,endtime,normbody,expbody) | |||||
| VALUES('0','$tagname','0','0','0','$fulltag',''); | VALUES('0','$tagname','0','0','0','$fulltag',''); | ||||
| "; | "; | ||||
| $dsql->ExecuteNoneQuery($inQuery); | $dsql->ExecuteNoneQuery($inQuery); | ||||
| $id = $dsql->GetLastID(); | $id = $dsql->GetLastID(); | ||||
| $dsql->ExecuteNoneQuery("UPDATE #@__mytag SET tagname='{$tagname}_{$id}' WHERE aid='$id'"); | |||||
| $dsql->ExecuteNoneQuery("UPDATE `#@__mytag` SET tagname='{$tagname}_{$id}' WHERE aid='$id'"); | |||||
| $fulltag = "{dede:mytag name='{$tagname}_{$id}' ismake='yes'/}"; | $fulltag = "{dede:mytag name='{$tagname}_{$id}' ismake='yes'/}"; | ||||
| } | } | ||||
| include DedeInclude('templets/mytag_tag_guide_ok.htm'); | include DedeInclude('templets/mytag_tag_guide_ok.htm'); | ||||
| @@ -13,13 +13,13 @@ CheckPurview('sys_plus'); | |||||
| $aid = preg_replace("#[^0-9]#", "", $aid); | $aid = preg_replace("#[^0-9]#", "", $aid); | ||||
| if($dopost=="show") | if($dopost=="show") | ||||
| { | { | ||||
| $dsql->ExecuteNoneQuery("UPDATE #@__plus SET isshow=1 WHERE aid='$aid';"); | |||||
| $dsql->ExecuteNoneQuery("UPDATE `#@__plus` SET isshow=1 WHERE aid='$aid';"); | |||||
| ShowMsg("成功启用一个插件,请刷新导航菜单!","plus_main.php"); | ShowMsg("成功启用一个插件,请刷新导航菜单!","plus_main.php"); | ||||
| exit(); | exit(); | ||||
| } | } | ||||
| else if($dopost=="hide") | else if($dopost=="hide") | ||||
| { | { | ||||
| $dsql->ExecuteNoneQuery("UPDATE #@__plus SET isshow=0 WHERE aid='$aid';"); | |||||
| $dsql->ExecuteNoneQuery("UPDATE `#@__plus` SET isshow=0 WHERE aid='$aid';"); | |||||
| ShowMsg("成功禁用一个插件,请刷新导航菜单!","plus_main.php"); | ShowMsg("成功禁用一个插件,请刷新导航菜单!","plus_main.php"); | ||||
| exit(); | exit(); | ||||
| } | } | ||||
| @@ -44,17 +44,17 @@ else if($dopost=="delete") | |||||
| } | } | ||||
| else if($job=="yes") //操作 | else if($job=="yes") //操作 | ||||
| { | { | ||||
| $dsql->ExecuteNoneQuery("DELETE FROM #@__plus WHERE aid='$aid';"); | |||||
| $dsql->ExecuteNoneQuery("DELETE FROM `#@__plus` WHERE aid='$aid';"); | |||||
| ShowMsg("成功删除一个插件,请刷新导航菜单!","plus_main.php"); | ShowMsg("成功删除一个插件,请刷新导航菜单!","plus_main.php"); | ||||
| exit(); | exit(); | ||||
| } | } | ||||
| } | } | ||||
| else if($dopost=="saveedit") //保存更改 | else if($dopost=="saveedit") //保存更改 | ||||
| { | { | ||||
| $inquery = "UPDATE #@__plus SET plusname='$plusname',menustring='$menustring',filelist='$filelist' WHERE aid='$aid';"; | |||||
| $inquery = "UPDATE `#@__plus` SET plusname='$plusname',menustring='$menustring',filelist='$filelist' WHERE aid='$aid';"; | |||||
| $dsql->ExecuteNoneQuery($inquery); | $dsql->ExecuteNoneQuery($inquery); | ||||
| ShowMsg("成功更改插件的配置!","plus_main.php"); | ShowMsg("成功更改插件的配置!","plus_main.php"); | ||||
| exit(); | exit(); | ||||
| } | } | ||||
| $row = $dsql->GetOne("SELECT * FROM #@__plus WHERE aid='$aid'"); | |||||
| $row = $dsql->GetOne("SELECT * FROM `#@__plus` WHERE aid='$aid'"); | |||||
| include DedeInclude('templets/plus_edit.htm'); | include DedeInclude('templets/plus_edit.htm'); | ||||
| @@ -13,7 +13,7 @@ CheckPurview('sys_plus'); | |||||
| require_once(DEDEINC."/datalistcp.class.php"); | require_once(DEDEINC."/datalistcp.class.php"); | ||||
| setcookie("ENV_GOBACK_URL",$dedeNowurl,time()+3600,"/"); | setcookie("ENV_GOBACK_URL",$dedeNowurl,time()+3600,"/"); | ||||
| $sql = "SELECT aid,plusname,writer,isshow FROM #@__plus ORDER BY aid ASC"; | |||||
| $sql = "SELECT aid,plusname,writer,isshow FROM `#@__plus` ORDER BY aid ASC"; | |||||
| $dlist = new DataListCP(); | $dlist = new DataListCP(); | ||||
| $dlist->SetTemplet(DEDEADMIN."/templets/plus_main.htm"); | $dlist->SetTemplet(DEDEADMIN."/templets/plus_main.htm"); | ||||
| $dlist->SetSource($sql); | $dlist->SetSource($sql); | ||||
| @@ -22,7 +22,7 @@ if($cid!=0) | |||||
| $whereSql = " AND arc.typeid IN (".GetSonIds($cid).")"; | $whereSql = " AND arc.typeid IN (".GetSonIds($cid).")"; | ||||
| } | } | ||||
| $query = "SELECT arc.*,tp.typename FROM `#@__archives` AS arc | $query = "SELECT arc.*,tp.typename FROM `#@__archives` AS arc | ||||
| LEFT JOIN #@__arctype AS tp ON arc.typeid = tp.id | |||||
| LEFT JOIN `#@__arctype` AS tp ON arc.typeid = tp.id | |||||
| WHERE arc.arcrank = '-2' $whereSql order by arc.id desc"; | WHERE arc.arcrank = '-2' $whereSql order by arc.id desc"; | ||||
| $dlist = new DataListCP(); | $dlist = new DataListCP(); | ||||
| $dlist->SetTemplet(DEDEADMIN."/templets/recycling.htm"); | $dlist->SetTemplet(DEDEADMIN."/templets/recycling.htm"); | ||||
| @@ -84,7 +84,7 @@ function GetKeywordList($dsql,$pageno,$pagesize,$orderby='aid') | |||||
| echo $printhead; | echo $printhead; | ||||
| if($orderby=='result') $orderby = $orderby." ASC"; | if($orderby=='result') $orderby = $orderby." ASC"; | ||||
| else $orderby = $orderby." DESC"; | else $orderby = $orderby." DESC"; | ||||
| $dsql->SetQuery("SELECT * FROM #@__search_keywords ORDER BY $orderby LIMIT $start,$pagesize "); | |||||
| $dsql->SetQuery("SELECT * FROM `#@__search_keywords` ORDER BY $orderby LIMIT $start,$pagesize "); | |||||
| $dsql->Execute(); | $dsql->Execute(); | ||||
| while($row = $dsql->GetArray()) | while($row = $dsql->GetArray()) | ||||
| { | { | ||||
| @@ -26,7 +26,7 @@ if($do=='add') | |||||
| $price = '0.00'; | $price = '0.00'; | ||||
| } | } | ||||
| $des = cn_substrR($des,255); | $des = cn_substrR($des,255); | ||||
| $InQuery = "INSERT INTO #@__shops_delivery(`dname`,`price`,`des`) VALUES ('$dname','$price','$des');"; | |||||
| $InQuery = "INSERT INTO `#@__shops_delivery`(`dname`,`price`,`des`) VALUES ('$dname','$price','$des');"; | |||||
| $result = $dsql->ExecuteNoneQuery($InQuery); | $result = $dsql->ExecuteNoneQuery($InQuery); | ||||
| if($result) | if($result) | ||||
| { | { | ||||
| @@ -40,7 +40,7 @@ if($do=='add') | |||||
| } else if ($do == 'del') | } else if ($do == 'del') | ||||
| { | { | ||||
| $id = intval($id); | $id = intval($id); | ||||
| $dsql->ExecuteNoneQuery("DELETE FROM #@__shops_delivery WHERE pid='$id'"); | |||||
| $dsql->ExecuteNoneQuery("DELETE FROM `#@__shops_delivery` WHERE pid='$id'"); | |||||
| ShowMsg("已删除当前配送方式!","shops_delivery.php"); | ShowMsg("已删除当前配送方式!","shops_delivery.php"); | ||||
| exit(); | exit(); | ||||
| } else if ($do == 'edit') | } else if ($do == 'edit') | ||||
| @@ -48,7 +48,7 @@ if($do=='add') | |||||
| foreach($pid as $id) | foreach($pid as $id) | ||||
| { | { | ||||
| $id = intval($id); | $id = intval($id); | ||||
| $row = $dsql->GetOne("SELECT pid,dname,price,des FROM #@__shops_delivery WHERE pid='$id' LIMIT 0,1"); | |||||
| $row = $dsql->GetOne("SELECT pid,dname,price,des FROM `#@__shops_delivery` WHERE pid='$id' LIMIT 0,1"); | |||||
| if(!is_array($row)) | if(!is_array($row)) | ||||
| { | { | ||||
| continue; | continue; | ||||
| @@ -73,22 +73,22 @@ if($do=='add') | |||||
| { | { | ||||
| $des = cn_substrR($des,255); | $des = cn_substrR($des,255); | ||||
| } | } | ||||
| $dsql->ExecuteNoneQuery("UPDATE #@__shops_delivery SET dname='$dname',price='$price',des='$des' WHERE pid='$id'"); | |||||
| $dsql->ExecuteNoneQuery("UPDATE `#@__shops_delivery` SET dname='$dname',price='$price',des='$des' WHERE pid='$id'"); | |||||
| } | } | ||||
| ShowMsg("成功修改配送方式!","shops_delivery.php"); | ShowMsg("成功修改配送方式!","shops_delivery.php"); | ||||
| exit(); | exit(); | ||||
| } | } | ||||
| $deliveryarr = array(); | $deliveryarr = array(); | ||||
| $dsql->SetQuery("SELECT pid,dname,price,des FROM #@__shops_delivery ORDER BY orders ASC"); | |||||
| $dsql->SetQuery("SELECT pid,dname,price,des FROM `#@__shops_delivery` ORDER BY orders ASC"); | |||||
| $dsql->Execute(); | $dsql->Execute(); | ||||
| while($row = $dsql->GetArray()) | while($row = $dsql->GetArray()) | ||||
| { | { | ||||
| $deliveryarr[] = $row; | $deliveryarr[] = $row; | ||||
| } | } | ||||
| $dlist = new DataListCP(); | $dlist = new DataListCP(); | ||||
| $dlist->pageSize = 25; //设定每页显示记录数(默认25条) | |||||
| $dlist->pageSize = 25; //设定每页显示记录数(默认25条) | |||||
| //这两句的顺序不能更换 | //这两句的顺序不能更换 | ||||
| $dlist->SetTemplate(DEDEADMIN."/templets/shops_delivery.htm"); //载入模板 | $dlist->SetTemplate(DEDEADMIN."/templets/shops_delivery.htm"); //载入模板 | ||||
| $dlist->SetSource("SELECT `pid`,`dname`,`price`,`des` FROM #@__shops_delivery ORDER BY `orders` ASC"); //设定查询SQL | |||||
| $dlist->Display(); //显示 | |||||
| $dlist->SetSource("SELECT `pid`,`dname`,`price`,`des` FROM `#@__shops_delivery` ORDER BY `orders` ASC"); // 设定查询SQL | |||||
| $dlist->Display(); //显示 | |||||
| @@ -24,7 +24,7 @@ if(isset($dopost)) | |||||
| if($wh=='') $wh = " WHERE oid='$n' "; | if($wh=='') $wh = " WHERE oid='$n' "; | ||||
| else $wh .= " OR oid='$n' "; | else $wh .= " OR oid='$n' "; | ||||
| } | } | ||||
| $sql="UPDATE #@__shops_orders SET `state`='1' $wh "; | |||||
| $sql="UPDATE `#@__shops_orders` SET `state`='1' $wh "; | |||||
| $dsql->ExecuteNoneQuery($sql); | $dsql->ExecuteNoneQuery($sql); | ||||
| } | } | ||||
| else if ($dopost == 'push') | else if ($dopost == 'push') | ||||
| @@ -36,7 +36,7 @@ if(isset($dopost)) | |||||
| if($wh=='') $wh = " WHERE oid='$n' "; | if($wh=='') $wh = " WHERE oid='$n' "; | ||||
| else $wh .= " OR oid='$n' "; | else $wh .= " OR oid='$n' "; | ||||
| } | } | ||||
| $sql="UPDATE #@__shops_orders SET `state`='2' $wh "; | |||||
| $sql="UPDATE `#@__shops_orders` SET `state`='2' $wh "; | |||||
| $dsql->ExecuteNoneQuery($sql); | $dsql->ExecuteNoneQuery($sql); | ||||
| } | } | ||||
| else if ($dopost == 'ok') | else if ($dopost == 'ok') | ||||
| @@ -48,7 +48,7 @@ if(isset($dopost)) | |||||
| if($wh=='') $wh = " WHERE oid='$n' "; | if($wh=='') $wh = " WHERE oid='$n' "; | ||||
| else $wh .= " OR oid='$n' "; | else $wh .= " OR oid='$n' "; | ||||
| } | } | ||||
| $sql="UPDATE #@__shops_orders SET `state`='4' $wh "; | |||||
| $sql="UPDATE `#@__shops_orders` SET `state`='4' $wh "; | |||||
| $dsql->ExecuteNoneQuery($sql); | $dsql->ExecuteNoneQuery($sql); | ||||
| } | } | ||||
| else if ($dopost == 'delete') | else if ($dopost == 'delete') | ||||
| @@ -87,7 +87,7 @@ if(isset($sta)) | |||||
| { | { | ||||
| $addsql = "WHERE s.`state`='$sta'"; | $addsql = "WHERE s.`state`='$sta'"; | ||||
| } | } | ||||
| $sql = "SELECT s.`oid`,s.`cartcount`,s.`price`,s.`state`,s.`stime`,s.priceCount,s.dprice,s.paytype,u.`consignee`,u.`tel`,s.`userid` FROM #@__shops_orders AS s LEFT JOIN #@__shops_userinfo AS u ON s.oid=u.oid $addsql ORDER BY `stime` DESC"; | |||||
| $sql = "SELECT s.`oid`,s.`cartcount`,s.`price`,s.`state`,s.`stime`,s.priceCount,s.dprice,s.paytype,u.`consignee`,u.`tel`,s.`userid` FROM `#@__shops_orders` AS s LEFT JOIN `#@__shops_userinfo` AS u ON s.oid=u.oid $addsql ORDER BY `stime` DESC"; | |||||
| $dlist = new DataListCP(); | $dlist = new DataListCP(); | ||||
| $dlist->SetParameter("oid",$oid); | $dlist->SetParameter("oid",$oid); | ||||
| @@ -127,7 +127,7 @@ function GetsType($pid) | |||||
| { | { | ||||
| global $dsql; | global $dsql; | ||||
| $pid = intval($pid); | $pid = intval($pid); | ||||
| $row = $dsql->GetOne("SELECT name FROM #@__payment WHERE id='$pid'"); | |||||
| $row = $dsql->GetOne("SELECT name FROM `#@__payment` WHERE id='$pid'"); | |||||
| if(is_array($row)) | if(is_array($row)) | ||||
| { | { | ||||
| return $row['name']; | return $row['name']; | ||||
| @@ -142,7 +142,7 @@ function GetMemberID($mid) | |||||
| { | { | ||||
| global $dsql; | global $dsql; | ||||
| if($mid==0) return '0'; | if($mid==0) return '0'; | ||||
| $row = $dsql->GetOne("SELECT userid FROM #@__member WHERE mid='$mid' "); | |||||
| $row = $dsql->GetOne("SELECT userid FROM `#@__member` WHERE mid='$mid' "); | |||||
| if(is_array($row)) | if(is_array($row)) | ||||
| { | { | ||||
| return "<a href='member_view.php?id={$mid}'>".$row['userid']."</a>"; | return "<a href='member_view.php?id={$mid}'>".$row['userid']."</a>"; | ||||
| @@ -16,8 +16,8 @@ if(!isset($oid)) exit("<a href='javascript:window.close()'>无效操作!</a>"); | |||||
| $oid = preg_replace("#[^-0-9A-Z]#", "", $oid); | $oid = preg_replace("#[^-0-9A-Z]#", "", $oid); | ||||
| if(empty($oid)) exit("<a href='javascript:window.close()'>无效订单号!</a>"); | if(empty($oid)) exit("<a href='javascript:window.close()'>无效订单号!</a>"); | ||||
| $row = $dsql->GetOne("SELECT * FROM #@__shops_userinfo WHERE oid='$oid'"); | |||||
| $sql="SELECT o.*,p.title,p.price as uprice,d.dname FROM #@__shops_orders as o left join #@__shops_products as p on o.oid=p.oid left join #@__shops_delivery as d on d.pid=o.pid WHERE o.oid='$oid'"; | |||||
| $row = $dsql->GetOne("SELECT * FROM `#@__shops_userinfo` WHERE oid='$oid'"); | |||||
| $sql="SELECT o.*,p.title,p.price as uprice,d.dname FROM `#@__shops_orders` as o left join `#@__shops_products` as p on o.oid=p.oid left join `#@__shops_delivery` as d on d.pid=o.pid WHERE o.oid='$oid'"; | |||||
| $dlist = new DataListCP(); | $dlist = new DataListCP(); | ||||
| $dlist->pageSize = 20; | $dlist->pageSize = 20; | ||||
| @@ -30,8 +30,8 @@ $dlist->Close(); | |||||
| function GetSta($sta,$oid) | function GetSta($sta,$oid) | ||||
| { | { | ||||
| global $dsql; | global $dsql; | ||||
| $row = $dsql->GetOne("SELECT paytype FROM #@__shops_orders WHERE oid='$oid'"); | |||||
| $payname = $dsql->GetOne("SELECT name,fee FROM #@__payment WHERE id='{$row['paytype']}'"); | |||||
| $row = $dsql->GetOne("SELECT paytype FROM `#@__shops_orders` WHERE oid='$oid'"); | |||||
| $payname = $dsql->GetOne("SELECT name,fee FROM `#@__payment` WHERE id='{$row['paytype']}'"); | |||||
| if($sta==0) | if($sta==0) | ||||
| { | { | ||||
| return $payname['name']." 手续费:".$payname['fee']."元"; | return $payname['name']." 手续费:".$payname['fee']."元"; | ||||
| @@ -14,16 +14,16 @@ if(!isset($oid)) exit("<a href='javascript:window.close()'>无效操作!</a>"); | |||||
| $oid = preg_replace("#[^-0-9A-Z]#", "", $oid); | $oid = preg_replace("#[^-0-9A-Z]#", "", $oid); | ||||
| if(empty($oid)) exit("<a href='javascript:window.close()'>无效订单号!</a>"); | if(empty($oid)) exit("<a href='javascript:window.close()'>无效订单号!</a>"); | ||||
| $rows = $dsql->GetOne("SELECT * FROM #@__shops_userinfo WHERE oid='$oid' LIMIT 0,1"); | |||||
| $rows = $dsql->GetOne("SELECT * FROM `#@__shops_userinfo` WHERE oid='$oid' LIMIT 0,1"); | |||||
| if(!is_array($rows)){ | if(!is_array($rows)){ | ||||
| $dsql->Close(); | $dsql->Close(); | ||||
| exit("<a href='javascript:window.close()'>该订单下没相关用户信息!</a>"); | exit("<a href='javascript:window.close()'>该订单下没相关用户信息!</a>"); | ||||
| } | } | ||||
| $row = $dsql->GetOne("SELECT pid,dprice FROM #@__shops_orders WHERE oid='$oid'"); | |||||
| $row = $dsql->GetOne("SELECT pid,dprice FROM `#@__shops_orders` WHERE oid='$oid'"); | |||||
| if(is_array($row)) | if(is_array($row)) | ||||
| { | { | ||||
| $rs = $dsql->GetOne("SELECT dname FROM #@__shops_delivery WHERE pid='$row[pid]'"); | |||||
| $rs = $dsql->GetOne("SELECT dname FROM `#@__shops_delivery` WHERE pid='$row[pid]'"); | |||||
| $rows['dname'] = $rs['dname']; | $rows['dname'] = $rs['dname']; | ||||
| $rows['dprice'] = $row['dprice']; | $rows['dprice'] = $row['dprice']; | ||||
| } | } | ||||
| @@ -1,4 +1,5 @@ | |||||
| <?php | <?php | ||||
| /** | /** | ||||
| * 安全检测 | * 安全检测 | ||||
| * | * | ||||
| @@ -8,130 +9,130 @@ | |||||
| * @license https://www.dedebiz.com/license | * @license https://www.dedebiz.com/license | ||||
| * @link https://www.dedebiz.com | * @link https://www.dedebiz.com | ||||
| */ | */ | ||||
| require_once(dirname(__FILE__).'/config.php'); | |||||
| require_once(dirname(__FILE__) . '/config.php'); | |||||
| CheckPurview('sys_Edit'); | CheckPurview('sys_Edit'); | ||||
| if(empty($action)) $action = ''; | |||||
| if(empty($message)) $message = '尚未进行检测……'; | |||||
| if(empty($filetype)) $filetype = 'php|inc'; | |||||
| if(empty($info)) $info = 'eval|cmd|_GET|_POST'; | |||||
| $safefile = "data/common.inc.php | |||||
| index.php | |||||
| dede/config.php | |||||
| dede/index_body.php | |||||
| dede/member_do.php | |||||
| dede/sys_info_pay.php | |||||
| dede/mychannel_main.php | |||||
| group/postform.php | |||||
| group/reply.php | |||||
| include/common.inc.php | |||||
| include/mail.class.php | |||||
| include/Lurd.class.php | |||||
| include/payment/alipay.php | |||||
| include/payment/bank.php | |||||
| include/payment/cod.php | |||||
| include/payment/yeepay.php | |||||
| include/helpers/debug.helper.php | |||||
| include/request.class.php | |||||
| include/dedecollection.class.php | |||||
| include/dedetag.class.php | |||||
| include/dialog/config.php | |||||
| include/taglib/php.lib.php | |||||
| include/FCKeditor/fckeditor.php | |||||
| include/smtp.class.php | |||||
| include/zip.class.php | |||||
| install/common.inc.php | |||||
| include/json.class.php | |||||
| include/sphinxclient.class.php | |||||
| plus/bshare.php | |||||
| install/index.php"; | |||||
| $adminDir = preg_replace("#(.*)[\/\\\\]#", "", dirname(__FILE__)); | |||||
| $safefile = trim(str_replace('dede/',$adminDir.'/',$safefile)); | |||||
| $safefiles = preg_split("#[\r\n]{1,}#", $safefile); | |||||
| if (empty($action)) $action = ''; | |||||
| if (empty($message)) $message = '尚未进行检测……'; | |||||
| if (empty($filetype)) $filetype = 'php|inc'; | |||||
| if (empty($info)) $info = 'eval|cmd|system|exec|_GET|_POST|_REQUEST|base64_decode'; | |||||
| $fileHashURL = "https://cdn.dedebiz.com/release/{$cfg_version_detail}.json"; | |||||
| $del = new DedeHttpDown(); | |||||
| $del->OpenUrl($fileHashURL); | |||||
| $filelist = $del->GetJSON(); | |||||
| $offFiles = array(); | |||||
| foreach ($filelist as $key => $ff) { | |||||
| $offFiles[$ff->filename] = $ff->hash; | |||||
| } | |||||
| $alter = ""; | |||||
| if (count($offFiles) == 0) { | |||||
| $alter = <<<EOT | |||||
| <div class="alert alert-danger maintable mb-2" style="margin:0 auto;" role="alert"> | |||||
| 无法同官方网站文件服务器通信,校验时候无法保证本地文件是否同官方服务器文件是否一致。 | |||||
| </div> | |||||
| EOT;; | |||||
| } | |||||
| function TestOneFile($f) | function TestOneFile($f) | ||||
| { | { | ||||
| global $message, $info; | |||||
| global $message, $info,$offFiles; | |||||
| $str = ''; | $str = ''; | ||||
| //排除safefile和data/tplcache目录 | //排除safefile和data/tplcache目录 | ||||
| if(NotCheckFile($f) || preg_match("#data/tplcache|.svn#", $f)) return -1; | |||||
| if (preg_match("#data/tplcache|.svn|data/cache#", $f)) return -1; | |||||
| $fp = fopen($f, 'r'); | $fp = fopen($f, 'r'); | ||||
| while(!feof($fp)) { $str .= fgets($fp,1024); } | |||||
| while (!feof($fp)) { | |||||
| $str .= fgets($fp, 1024); | |||||
| } | |||||
| fclose($fp); | fclose($fp); | ||||
| if(preg_match("#(".$info.")[ \r\n\t]{0,}([\[\(])#i", $str)) | |||||
| { | |||||
| $trfile = preg_replace("#^".DEDEROOT."#", '', $f); | |||||
| $message .= "<div style='clear:both;border-bottom:1px dotted #B8E6A2;line-height:24px'> | |||||
| if (preg_match("#(" . $info . ")[ \r\n\t]{0,}([\[\(])#i", $str)) { | |||||
| $trfile = preg_replace("#^" . DEDEROOT . "#", '', $f ); | |||||
| $oldTrfile = $trfile; | |||||
| $trfile = substr(str_replace("/","\\",$trfile) ,1); | |||||
| $localFilehash = md5_file($f); | |||||
| $remoteFilehash = isset($offFiles[$trfile])? $offFiles[$trfile] : ''; | |||||
| if ($localFilehash === $remoteFilehash) { | |||||
| return 0; | |||||
| } | |||||
| $message .= "<div style='clear:both;'> | |||||
| <div style='width:350px;float:left'>可疑文件:{$trfile}</div> | <div style='width:350px;float:left'>可疑文件:{$trfile}</div> | ||||
| <div style='float:left'>[<a href='file_manage_view.php?fmdo=del&filename=$trfile&activepath=' target='_blank'><u>删除</u></a>] | |||||
| [<a href='file_manage_view.php?fmdo=edit&filename=$trfile&activepath=' target='_blank'><u>查看源码</u></a>] | |||||
| </div></div>\r\n"; | |||||
| <a class='btn btn-secondary btn-sm' href='sys_safetest.php?action=viewdiff&filename=$oldTrfile' target='_blank'>更改记录</a> | |||||
| <a class='btn btn-secondary btn-sm' href='file_manage_view.php?fmdo=del&filename=$oldTrfile&activepath=' target='_blank'>删除</a> | |||||
| <a class='btn btn-secondary btn-sm' href='file_manage_view.php?fmdo=edit&filename=$oldTrfile&activepath=' target='_blank'>查看源码</a> | |||||
| </div></div><hr>\r\n"; | |||||
| return 1; | return 1; | ||||
| } | } | ||||
| return 0; | return 0; | ||||
| } | } | ||||
| function NotCheckFile($f) | |||||
| { | |||||
| global $safefiles, $safefile; | |||||
| if($safefile != '') | |||||
| { | |||||
| foreach($safefiles as $v) | |||||
| { | |||||
| //if(empty($v)) continue; | |||||
| if( preg_match("#".$v."#i", $f) ) return TRUE; | |||||
| } | |||||
| } | |||||
| return false; | |||||
| } | |||||
| function TestSafe($tdir) | function TestSafe($tdir) | ||||
| { | { | ||||
| global $filetype; | global $filetype; | ||||
| $dh = dir($tdir); | $dh = dir($tdir); | ||||
| while($fname=$dh->read()) | |||||
| { | |||||
| $fnamef = $tdir.'/'.$fname; | |||||
| if(@is_dir($fnamef) && $fname != '.' && $fname != '..') | |||||
| { | |||||
| while ($fname = $dh->read()) { | |||||
| $fnamef = $tdir . '/' . $fname; | |||||
| if (@is_dir($fnamef) && $fname != '.' && $fname != '..') { | |||||
| TestSafe($fnamef); | TestSafe($fnamef); | ||||
| } | } | ||||
| if(preg_match("#\.(" . $filetype . ")#i", $fnamef)) | |||||
| { | |||||
| if (preg_match("#\.(" . $filetype . ")#i", $fnamef)) { | |||||
| TestOneFile($fnamef); | TestOneFile($fnamef); | ||||
| } | } | ||||
| } | } | ||||
| } | } | ||||
| //检测 | //检测 | ||||
| if($action=='test') | |||||
| { | |||||
| $message = ''; | |||||
| AjaxHead(); | |||||
| TestSafe(DEDEROOT); | |||||
| if($message=='') $message = "<font color='green' style='font-size:14px'>没发现可疑文件!</font>"; | |||||
| echo $message; | |||||
| exit(); | |||||
| if ($action == 'test') { | |||||
| $message = '<link rel="stylesheet" href="../static/css/bootstrap.min.css"><link href="../static/font-awesome/css/font-awesome.min.css" rel="stylesheet">'; | |||||
| AjaxHead(); | |||||
| TestSafe(DEDEROOT); | |||||
| if ($message == '') $message = "<font color='green' style='font-size:14px'>没发现可疑文件!</font>"; | |||||
| echo $message; | |||||
| exit(); | |||||
| } | } | ||||
| else if($action =='viewdiff'){ | |||||
| $filename = isset($filename)? $filename : ""; | |||||
| if (empty($filename)) { | |||||
| ShowMsg("没有选择对应的文件", "-1"); | |||||
| exit; | |||||
| } | |||||
| $baseFile = "https://cdn.dedebiz.com/release/{$cfg_version_detail}$filename"; | |||||
| $del = new DedeHttpDown(); | |||||
| $del->OpenUrl($baseFile); | |||||
| $base = $del->GetHTML(); | |||||
| $file = "$cfg_basedir/$filename"; | |||||
| $new = ""; | |||||
| if(is_file($file)) | |||||
| { | |||||
| $fp = fopen($file,"r"); | |||||
| $new = fread($fp,filesize($file)); | |||||
| fclose($fp); | |||||
| } | |||||
| include(dirname(__FILE__) . '/templets/sys_safetest_viewdiff.htm'); | |||||
| exit(); | |||||
| } | |||||
| //清空模板缓存 | //清空模板缓存 | ||||
| else if($action=='clear') | |||||
| { | |||||
| else if ($action == 'clear') { | |||||
| global $cfg_tplcache_dir; | global $cfg_tplcache_dir; | ||||
| $message = ''; | $message = ''; | ||||
| $d = DEDEROOT.$cfg_tplcache_dir; | |||||
| $d = DEDEROOT . $cfg_tplcache_dir; | |||||
| AjaxHead(); | AjaxHead(); | ||||
| sleep(1); | sleep(1); | ||||
| if(preg_match("#data\/#", $cfg_tplcache_dir) && file_exists($d) && is_dir($d)) | |||||
| { | |||||
| if (preg_match("#data\/#", $cfg_tplcache_dir) && file_exists($d) && is_dir($d)) { | |||||
| $dh = dir($d); | $dh = dir($d); | ||||
| while($filename = $dh->read()) | |||||
| { | |||||
| if($filename=='.'||$filename=='..'||$filename=='index.html') continue; | |||||
| @unlink($d.'/'.$filename); | |||||
| while ($filename = $dh->read()) { | |||||
| if ($filename == '.' || $filename == '..' || $filename == 'index.html') continue; | |||||
| @unlink($d . '/' . $filename); | |||||
| } | } | ||||
| } | } | ||||
| $message = "<font color='green' style='font-size:14px'>成功清空模板缓存!</font>"; | $message = "<font color='green' style='font-size:14px'>成功清空模板缓存!</font>"; | ||||
| @@ -139,4 +140,4 @@ else if($action=='clear') | |||||
| exit(); | exit(); | ||||
| } | } | ||||
| include(dirname(__FILE__).'/templets/sys_safetest.htm'); | |||||
| include(dirname(__FILE__) . '/templets/sys_safetest.htm'); | |||||
| @@ -1,470 +0,0 @@ | |||||
| <?php | |||||
| /** | |||||
| * 系统文件校验 | |||||
| * | |||||
| * @version $Id: sys_verifies.php 1 23:07 2010年7月20日Z tianya $ | |||||
| * @package DedeCMS.Administrator | |||||
| * @copyright Copyright (c) 2020, DedeBIZ.COM | |||||
| * @license https://www.dedebiz.com/license | |||||
| * @link https://www.dedebiz.com | |||||
| */ | |||||
| require_once(dirname(__FILE__)."/config.php"); | |||||
| CheckPurview('sys_Edit'); | |||||
| @set_time_limit(0); | |||||
| require(DEDEINC.'/dedehttpdown.class.php'); | |||||
| $action = isset($action) ? trim($action) : ''; | |||||
| //当前软件版本锁定文件 | |||||
| $verLockFile = DEDEDATA.'/admin/ver.txt'; | |||||
| //当前软件指纹码锁定文件 | |||||
| $verifiesLockFile = DEDEDATA.'/admin/verifies.txt'; | |||||
| $fp = fopen($verLockFile,'r'); | |||||
| $upTime = trim(fread($fp,64)); | |||||
| fclose($fp); | |||||
| $updateTime = substr($upTime,0,4).'-'.substr($upTime,4,2).'-'.substr($upTime,6,2); | |||||
| $verifiesTime = "未同步过指纹码"; | |||||
| if(file_exists($verifiesLockFile)) | |||||
| { | |||||
| $fp = fopen($verifiesLockFile,'r'); | |||||
| $upTime = trim(fread($fp,64)); | |||||
| fclose($fp); | |||||
| $verifiesTime = substr($upTime,0,4).'-'.substr($upTime,4,2).'-'.substr($upTime,6,2); | |||||
| } | |||||
| $tmpdir = substr(md5($cfg_cookie_encode),0,16); | |||||
| //重定义file_get_contents来兼容不支持此函数的PHP | |||||
| //因为有个别地方用fgets读文件生成校验码不兼容 | |||||
| if(!function_exists('file_get_contents')) | |||||
| { | |||||
| function file_get_contents($fname) | |||||
| { | |||||
| if(!file_exists($fname) || is_dir($fname)) | |||||
| { | |||||
| return ''; | |||||
| } | |||||
| else | |||||
| { | |||||
| $fp = fopen($fname, 'r'); | |||||
| $ct = fread($fp, filesize($fname)); | |||||
| fclose($fp); | |||||
| return $ct; | |||||
| } | |||||
| } | |||||
| } | |||||
| if($action == '') | |||||
| { | |||||
| include(DEDEADMIN.'/templets/sys_verifies.htm'); | |||||
| exit(); | |||||
| } | |||||
| /*---------------- | |||||
| 校验文件 | |||||
| function _verify() { } | |||||
| ----------------*/ | |||||
| else if($action == 'verify') | |||||
| { | |||||
| $dsql->SetQuery("SELECT * FROM `#@__verifies` "); | |||||
| $dsql->Execute(); | |||||
| $filelist = array(); | |||||
| while($row = $dsql->GetArray()) | |||||
| { | |||||
| $turefile = str_replace('../dede', '.', $row['filename']); | |||||
| //跳过不存在的文件 | |||||
| if(!file_exists($turefile)) { | |||||
| continue; | |||||
| } | |||||
| if( filesize($turefile)==0 ) { | |||||
| continue; | |||||
| } | |||||
| $ct = file_get_contents($turefile); | |||||
| $ct = preg_replace("/\/\*\*[\r\n]{1,}(.*)[\r\n]{1,} \*\//sU", '', $ct); | |||||
| $cthash = md5($ct); | |||||
| if($cthash != $row['cthash']) | |||||
| { | |||||
| $row['localhash'] = $cthash; | |||||
| $row['mtime'] = MyDate('Y-m-d H:i:s', filemtime($turefile)); | |||||
| $row['turefile'] = $turefile; | |||||
| $filelist[] = $row; | |||||
| } | |||||
| } | |||||
| if(!isset($filelist[0])) | |||||
| { | |||||
| ShowMsg("所有文件都通过效验证,核心文件没有被改动过!","sys_verifies.php"); | |||||
| } | |||||
| else | |||||
| { | |||||
| include(DEDEADMIN.'/templets/sys_verifies_verify.htm'); | |||||
| } | |||||
| exit(); | |||||
| } | |||||
| /*-------------------- | |||||
| 查看单个本地文件 | |||||
| function _view() { } | |||||
| ----------------------*/ | |||||
| else if ($action == 'view') | |||||
| { | |||||
| require_once(DEDEINC."/oxwindow.class.php"); | |||||
| $filetxt = ''; | |||||
| if( !preg_match("#data(.*)common.inc.php#i", $filename) ) | |||||
| { | |||||
| $fp = fopen($filename, 'r'); | |||||
| $filetxt = fread($fp, filesize($filename)); | |||||
| fclose($fp); | |||||
| } | |||||
| $filetxt = str_replace('textarea', '!textarea', $filetxt); | |||||
| $wintitle = "文件效验::查看文件"; | |||||
| $wecome_info = "<a href='sys_verifies.php'><u>文件效验</u></a>::查看文件"; | |||||
| $win = new OxWindow(); | |||||
| $win->Init(); | |||||
| $win->AddTitle("以下为文件 $filename 的内容,请检查是否可疑:"); | |||||
| $winform = $win->GetWindow("hand","<textarea name='filetxt' style='width:100%;height:450px;word-wrap: break-word;word-break:break-all;'>".$filetxt."</textarea>"); | |||||
| $win->Display(); | |||||
| exit(); | |||||
| } | |||||
| /*----------------- | |||||
| 管理指纹码 | |||||
| function _manage() { } | |||||
| -------------------*/ | |||||
| else if ($action == 'manage') | |||||
| { | |||||
| $dsql->SetQuery("SELECT * FROM `#@__verifies` "); | |||||
| $dsql->Execute(); | |||||
| $filelist = array(); | |||||
| while($row = $dsql->GetArray()) | |||||
| { | |||||
| $filelist[] = $row; | |||||
| } | |||||
| include(DEDEADMIN.'/templets/sys_verifies_manage.htm'); | |||||
| exit(); | |||||
| } | |||||
| /*----------------------- | |||||
| 下载文件 | |||||
| function _getfiles() | |||||
| ------------------------*/ | |||||
| else if ($action == 'getfiles') | |||||
| { | |||||
| if(!isset($refiles)) | |||||
| { | |||||
| ShowMsg("你没进行任何操作!","sys_verifies.php"); | |||||
| exit(); | |||||
| } | |||||
| $cacheFiles = DEDEDATA.'/modifytmp.inc'; | |||||
| $fp = fopen($cacheFiles, 'w'); | |||||
| fwrite($fp, '<'.'?php'."\r\n"); | |||||
| fwrite($fp, '$tmpdir = "'.$tmpdir.'";'."\r\n"); | |||||
| $dirs = array(); | |||||
| $i = -1; | |||||
| $adminDir = preg_replace("#(.*)[\/\\\\]#", "", dirname(__FILE__)); | |||||
| foreach($refiles as $filename) | |||||
| { | |||||
| $filename = substr($filename,3,strlen($filename)-3); | |||||
| if(preg_match("#^dede/#i", $filename)) | |||||
| { | |||||
| $curdir = GetDirName( preg_replace("#^dede/#i", $adminDir.'/', $filename) ); | |||||
| } else { | |||||
| $curdir = GetDirName($filename); | |||||
| } | |||||
| if( !isset($dirs[$curdir]) ) | |||||
| { | |||||
| $dirs[$curdir] = TestIsFileDir($curdir); | |||||
| } | |||||
| $i++; | |||||
| fwrite($fp, '$files['.$i.'] = "'.$filename.'";'."\r\n"); | |||||
| } | |||||
| fwrite($fp, '$fileConut = '.$i.';'."\r\n"); | |||||
| fwrite($fp, '?'.'>'); | |||||
| fclose($fp); | |||||
| $dirinfos = ''; | |||||
| if($i > -1) | |||||
| { | |||||
| $dirinfos = '<tr bgcolor="#ffffff"><td colspan="2">'; | |||||
| $dirinfos .= "本次升级需要在下面文件夹写入更新文件,请注意文件夹是否有写入权限:<br />\r\n"; | |||||
| foreach($dirs as $curdir) | |||||
| { | |||||
| $dirinfos .= $curdir['name']." 状态:".($curdir['writeable'] ? "[√正常]" : "<font color='red'>[×不可写]</font>")."<br />\r\n"; | |||||
| } | |||||
| $dirinfos .= "</td></tr>\r\n"; | |||||
| } | |||||
| $doneStr = "<iframe name='stafrm' src='sys_verifies.php?action=down&curfile=0' frameborder='0' id='stafrm' width='100%' height='100%'></iframe>\r\n"; | |||||
| include(DEDEADMIN.'/templets/sys_verifies_getfiles.htm'); | |||||
| exit(); | |||||
| } | |||||
| /*----------------------- | |||||
| 下载文件 | |||||
| function _down() | |||||
| ------------------------*/ | |||||
| else if($action=='down') | |||||
| { | |||||
| $cacheFiles = DEDEDATA.'/modifytmp.inc'; | |||||
| require_once($cacheFiles); | |||||
| if($fileConut==-1 || $curfile > $fileConut) | |||||
| { | |||||
| ShowMsg("已下载所有文件<br /><a href='sys_verifies.php?action=apply'>[直接替换文件]</a> <a href='#'>[我自己手动替换文件]</a>","javascript:;"); | |||||
| exit(); | |||||
| } | |||||
| //检查临时文件保存目录是否可用 | |||||
| MkTmpDir($tmpdir, $files[$curfile]); | |||||
| $downfile = UPDATEHOST.$cfg_soft_lang.'/source/'.$files[$curfile]; | |||||
| $dhd = new DedeHttpDown(); | |||||
| $dhd->OpenUrl($downfile); | |||||
| $dhd->SaveToBin(DEDEDATA.'/'.$tmpdir.'/'.$files[$curfile]); | |||||
| $dhd->Close(); | |||||
| ShowMsg("成功下载文件:{$files[$curfile]}; 继续下载下一个文件。","sys_verifies.php?action=down&curfile=".($curfile+1)); | |||||
| exit(); | |||||
| } | |||||
| /*----------------------- | |||||
| 修改效验方式 | |||||
| function _modify() | |||||
| ------------------------*/ | |||||
| else if($action=='modify') | |||||
| { | |||||
| if(!isset($modifys)) | |||||
| { | |||||
| ShowMsg("没选定要修改的文件!","-1"); | |||||
| exit(); | |||||
| } | |||||
| else | |||||
| { | |||||
| foreach($modifys as $fname) | |||||
| { | |||||
| if($method=='local') | |||||
| { | |||||
| $tureFilename = str_replace('../dede','./',$fname); | |||||
| if(file_exists($tureFilename)) | |||||
| { | |||||
| $fp = fopen($tureFilename,'r'); | |||||
| $ct = fread($fp,filesize($tureFilename)); | |||||
| fclose($fp); | |||||
| $cthash = md5($ct); | |||||
| $dsql->ExecuteNoneQuery("UPDATE `#@__verifies` SET `method`='local',cthash='$cthash' WHERE filename='$fname' "); | |||||
| } | |||||
| } | |||||
| else | |||||
| { | |||||
| $dsql->ExecuteNoneQuery("UPDATE `#@__verifies` SET `method`='offical' WHERE filename='$fname' "); | |||||
| } | |||||
| } | |||||
| } | |||||
| if($method=='local') | |||||
| { | |||||
| ShowMsg("成功修改指定文件的验证方式!","sys_verifies.php?action=manage"); | |||||
| } | |||||
| else | |||||
| { | |||||
| ShowMsg("成功修改指定文件的验证方式!<br /> 由于你修改了文件为远程验证方式,因此需进行更新操作<br /> <a href='sys_verifies.php?action=update'>[更新]</a> <a href='sys_verifies.php?action=manage'>[返回]</a>","javascript:;"); | |||||
| } | |||||
| exit(); | |||||
| } | |||||
| /*----------------------- | |||||
| 还原文件 | |||||
| function _applyRecover() | |||||
| ------------------------*/ | |||||
| else if ($action == 'apply') | |||||
| { | |||||
| $cacheFiles = DEDEDATA.'/modifytmp.inc'; | |||||
| require_once($cacheFiles); | |||||
| $sDir = DEDEDATA."/$tmpdir"; | |||||
| $tDir = DEDEROOT; | |||||
| $badcp = 0; | |||||
| $adminDir = preg_replace("#(.*)[\/\\\\]#", "", dirname(__FILE__)); | |||||
| if(isset($files) && is_array($files)) | |||||
| { | |||||
| foreach($files as $f) | |||||
| { | |||||
| if(preg_match("#^dede#", $f)) $tf = preg_replace("#^dede#", $adminDir, $f); | |||||
| else $tf = $f; | |||||
| if(file_exists($sDir.'/'.$f)) | |||||
| { | |||||
| //还原文件前先进行文件效验 | |||||
| $ct = file_get_contents($sDir.'/'.$f); | |||||
| $ct = preg_replace("/\/\*\*[\r\n]{1,}(.*)[\r\n]{1,} \*\//sU", '', $ct); | |||||
| $newhash = md5($ct); | |||||
| $row = $dsql->GetOne("SELECT * FROM `#@__verifies` WHERE filename='../{$f}' "); | |||||
| if(is_array($row) && $row['cthash'] != $newhash) | |||||
| { | |||||
| $badcp++; | |||||
| } else { | |||||
| $rs = @copy($sDir.'/'.$f, $tDir.'/'.$tf); | |||||
| if($rs) unlink($sDir.'/'.$f); | |||||
| else $badcp++; | |||||
| } | |||||
| } | |||||
| } | |||||
| } | |||||
| $badmsg = '!'; | |||||
| if($badcp > 0) | |||||
| { | |||||
| $badmsg = ",其 {$badcp} 个文件效验码不正确或复制失败,<br />请从临时目录[../data/{$tmpdir}]中取出这几个文件手动还原。"; | |||||
| } | |||||
| ShowMsg("成功完成还原指定文件{$badmsg}", "javascript:;"); | |||||
| exit(); | |||||
| } | |||||
| /*--------------- | |||||
| 在线更新指纹码 | |||||
| function _update() | |||||
| -----------------*/ | |||||
| else if($action == 'update') | |||||
| { | |||||
| $rmFile = UPDATEHOST.$cfg_soft_lang.'/verifys.txt'; | |||||
| $dhd = new DedeHttpDown(); | |||||
| $dhd->OpenUrl($rmFile); | |||||
| $ct = $dhd->GetHtml(); | |||||
| $dhd->Close(); | |||||
| $cts = split("[\r\n]{1,}",$ct); | |||||
| foreach($cts as $ct) | |||||
| { | |||||
| $ct = trim($ct); | |||||
| if(empty($ct)) continue; | |||||
| list($nameid, $cthash, $fname) = explode("\t", $ct); | |||||
| $row = $dsql->GetOne("SELECT * FROM `#@__verifies` WHERE nameid='$nameid' "); | |||||
| if(!is_array($row) || ($row['method']=='official' && $row['cthash']!=$cthash )) | |||||
| { | |||||
| $dsql->ExecuteNoneQuery("REPLACE INTO `#@__verifies`(nameid,cthash,method,filename) VALUES ('$nameid','$cthash','official','$fname'); "); | |||||
| } | |||||
| } | |||||
| $fp = fopen($verifiesLockFile,'w'); | |||||
| fwrite($fp, MyDate('Ymd',time())); | |||||
| fclose($fp); | |||||
| ShowMsg("完成效验码更新,是否马上进行效验操作?<br /> <a href='sys_verifies.php?action=verify'>[开始效验]</a> <a href='sys_verifies.php?action=manage'>[管理]</a> <a href='sys_verifies.php'>[返回]</a>","javascript:;"); | |||||
| exit(); | |||||
| } | |||||
| /*----------------- | |||||
| 生成指纹码 | |||||
| function _make() { } | |||||
| -------------------*/ | |||||
| else if ($action == 'make') | |||||
| { | |||||
| $fp = fopen(DEDEROOT.'/../verifys.txt','w'); | |||||
| foreach (preg_ls ('../', TRUE, "/.*\.(php|htm|html|js)$/i", 'CVS,data,html,uploads,templets,special') as $onefile) | |||||
| { | |||||
| $nameid = md5($onefile); | |||||
| $ctbody = file_get_contents(DEDEADMIN.'/'.$onefile); | |||||
| $ctbody = preg_replace("/\/\*\*[\r\n]{1,}(.*)[\r\n]{1,} \*\//sU", '', $ctbody); | |||||
| $cthash = md5($ctbody); | |||||
| fwrite($fp,"{$nameid}\t{$cthash}\t{$onefile}\r\n"); | |||||
| } | |||||
| fclose($fp); | |||||
| ShowMsg("操作成功!","sys_verifies.php"); | |||||
| exit(); | |||||
| } | |||||
| //获取所有文件列表 | |||||
| function preg_ls($path=".", $rec=FALSE, $pat="/.*/", $ignoredir='') | |||||
| { | |||||
| while (substr ($path,-1,1) =="/") | |||||
| { | |||||
| $path=substr ($path,0,-1); | |||||
| } | |||||
| if (!is_dir ($path) ) | |||||
| { | |||||
| $path=dirname ($path); | |||||
| } | |||||
| if ($rec!==TRUE) | |||||
| { | |||||
| $rec=FALSE; | |||||
| } | |||||
| $d=dir ($path); | |||||
| $ret=Array (); | |||||
| while (FALSE!== ($e=$d->read () ) ) | |||||
| { | |||||
| if ( ($e==".") || ($e=="..") ) | |||||
| { | |||||
| continue; | |||||
| } | |||||
| if ($rec && is_dir ($path."/".$e) && ($ignoredir == '' || strpos($ignoredir,$e ) === FALSE)) | |||||
| { | |||||
| $ret = array_merge ($ret, preg_ls($path."/".$e, $rec, $pat, $ignoredir)); | |||||
| continue; | |||||
| } | |||||
| if (!preg_match ($pat, $e) ) | |||||
| { | |||||
| continue; | |||||
| } | |||||
| $ret[] = $path."/".$e; | |||||
| } | |||||
| return (empty ($ret) && preg_match ($pat,basename($path))) ? Array ($path."/") : $ret; | |||||
| } | |||||
| function TestWriteAble($d) | |||||
| { | |||||
| $tfile = '_dedet.txt'; | |||||
| $fp = @fopen($d.$tfile, 'w'); | |||||
| if(!$fp) | |||||
| { | |||||
| return FALSE; | |||||
| } | |||||
| else { | |||||
| fclose($fp); | |||||
| $rs = @unlink($d.'/'.$tfile); | |||||
| return TRUE; | |||||
| } | |||||
| } | |||||
| function GetDirName($filename) | |||||
| { | |||||
| $dirname = '../'.preg_replace("#[\\\\\/]{1,}#", '/', $filename); | |||||
| $dirname = preg_replace("#([^\/]*)$#", '', $dirname); | |||||
| return $dirname; | |||||
| } | |||||
| function TestIsFileDir($dirname) | |||||
| { | |||||
| $dirs = array('name'=>'','isdir'=>FALSE,'writeable'=>FALSE); | |||||
| $dirs['name'] = $dirname; | |||||
| if(is_dir($dirname)) | |||||
| { | |||||
| $dirs['isdir'] = TRUE; | |||||
| $dirs['writeable'] = TestWriteAble($dirname); | |||||
| } | |||||
| return $dirs; | |||||
| } | |||||
| function MkTmpDir($tmpdir,$filename) | |||||
| { | |||||
| $basedir = DEDEDATA.'/'.$tmpdir; | |||||
| $dirname = trim(preg_replace("#[\\\\\/]{1,}#", '/', $filename)); | |||||
| $dirname = preg_replace("#([^\/]*)$#", "", $dirname); | |||||
| if(!is_dir($basedir)) | |||||
| { | |||||
| mkdir($basedir, 0777); | |||||
| } | |||||
| if($dirname=='') | |||||
| { | |||||
| return TRUE; | |||||
| } | |||||
| $dirs = explode('/', $dirname); | |||||
| $curdir = $basedir; | |||||
| foreach($dirs as $d) | |||||
| { | |||||
| $d = trim($d); | |||||
| if(empty($d)) continue; | |||||
| $curdir = $curdir.'/'.$d; | |||||
| if(!is_dir($curdir)) | |||||
| { | |||||
| mkdir($curdir,0777) or die($curdir); | |||||
| } | |||||
| } | |||||
| return TRUE; | |||||
| } | |||||
| @@ -5,8 +5,8 @@ | |||||
| <head> | <head> | ||||
| <meta http-equiv="Content-Type" content="text/html; charset=<?php echo $cfg_soft_lang; ?>"> | <meta http-equiv="Content-Type" content="text/html; charset=<?php echo $cfg_soft_lang; ?>"> | ||||
| <title>木马自检程序</title> | <title>木马自检程序</title> | ||||
| <link rel="stylesheet" href="../static/css/bootstrap.min.css"> | |||||
| <link href="../static/font-awesome/css/font-awesome.min.css" rel="stylesheet"> | |||||
| <link rel="stylesheet" href="../static/css/bootstrap.min.css"> | |||||
| <link href="../static/font-awesome/css/font-awesome.min.css" rel="stylesheet"> | |||||
| <link href="css/base.css" rel="stylesheet" type="text/css" /> | <link href="css/base.css" rel="stylesheet" type="text/css" /> | ||||
| <link rel="stylesheet" type="text/css" href="css/indexbody.css" /> | <link rel="stylesheet" type="text/css" href="css/indexbody.css" /> | ||||
| <style type="text/css"> | <style type="text/css"> | ||||
| @@ -48,6 +48,7 @@ | |||||
| <div class="bodytitleleft"></div> | <div class="bodytitleleft"></div> | ||||
| <div class="bodytitletxt" style="padding-left:10px;">用户安全中心</div> | <div class="bodytitletxt" style="padding-left:10px;">用户安全中心</div> | ||||
| </div> | </div> | ||||
| <?php echo $alter;?> | |||||
| <table width="98%" border="0" cellpadding="1" cellspacing="1" align="center" class="table maintable" | <table width="98%" border="0" cellpadding="1" cellspacing="1" align="center" class="table maintable" | ||||
| style="background:#CFCFCF;"> | style="background:#CFCFCF;"> | ||||
| <tr> | <tr> | ||||
| @@ -70,7 +71,7 @@ | |||||
| <input name="filetype" type="text" id="filetype" value="php|inc" style="width:420px" /> | <input name="filetype" type="text" id="filetype" value="php|inc" style="width:420px" /> | ||||
| 要检查的文件类型</p> | 要检查的文件类型</p> | ||||
| <p>代码特征: | <p>代码特征: | ||||
| <input name="info" type="text" id="info" value="eval|cmd|system|exec|_GET|_POST" style="width:420px" /> | |||||
| <input name="info" type="text" id="info" value="eval|cmd|system|exec|_GET|_POST|_REQUEST|base64_decode" style="width:420px" /> | |||||
| 特征代码</p> | 特征代码</p> | ||||
| </td> | </td> | ||||
| </tr> | </tr> | ||||
| @@ -0,0 +1,95 @@ | |||||
| <!doctype html> | |||||
| <html> | |||||
| <head> | |||||
| <meta charset="utf-8"> | |||||
| <meta http-equiv="X-UA-Compatible" content="IE=Edge,chrome=1"> | |||||
| <title>查看差异</title> | |||||
| <link rel="stylesheet" type="text/css" href="../static/css/diffview.css" /> | |||||
| <script type="text/javascript" src="../static/js/jquery.js"></script> | |||||
| <script type="text/javascript" src="../static/js/diffview.js"></script> | |||||
| <script type="text/javascript" src="../static/js/difflib.js"></script> | |||||
| <style type="text/css"> | |||||
| body { | |||||
| font-size: 12px; | |||||
| font-family: Sans-Serif; | |||||
| } | |||||
| h2 { | |||||
| margin: 0.5em 0 0.1em; | |||||
| text-align: center; | |||||
| } | |||||
| .top { | |||||
| text-align: center; | |||||
| } | |||||
| .textInput { | |||||
| display: block; | |||||
| width: 49%; | |||||
| float: left; | |||||
| } | |||||
| textarea { | |||||
| width: 100%; | |||||
| height: 300px; | |||||
| } | |||||
| label:hover { | |||||
| text-decoration: underline; | |||||
| cursor: pointer; | |||||
| } | |||||
| .spacer { | |||||
| margin-left: 10px; | |||||
| } | |||||
| .viewType { | |||||
| font-size: 16px; | |||||
| clear: both; | |||||
| text-align: center; | |||||
| padding: 1em; | |||||
| } | |||||
| #diffoutput { | |||||
| width: 100%; | |||||
| } | |||||
| </style> | |||||
| <script type="text/javascript"> | |||||
| function diffUsingJS(viewType) { | |||||
| "use strict"; | |||||
| var base = difflib.stringAsLines($("#baseText").val()), | |||||
| newtxt = difflib.stringAsLines($("#newText").val()), | |||||
| sm = new difflib.SequenceMatcher(base, newtxt), | |||||
| opcodes = sm.get_opcodes(), | |||||
| diffoutputdiv = $("#diffoutput"); | |||||
| diffoutputdiv.html("") | |||||
| diffoutputdiv.html(diffview.buildView({ | |||||
| baseTextLines: base, | |||||
| newTextLines: newtxt, | |||||
| opcodes: opcodes, | |||||
| baseTextName: "官方服务器文件", | |||||
| newTextName: "本地文件", | |||||
| viewType: 0 | |||||
| })); | |||||
| } | |||||
| </script> | |||||
| </head> | |||||
| <body> | |||||
| <textarea id="baseText" style="display: none;"><?php echo $base ;?></textarea> | |||||
| <textarea id="newText" style="display: none;"><?php echo $new ;?></textarea> | |||||
| <div id="diffoutput"> </div> | |||||
| <script> | |||||
| $(document).ready(function () { | |||||
| diffUsingJS(1); | |||||
| }); | |||||
| </script> | |||||
| </body> | |||||
| </html> | |||||
| @@ -1,78 +0,0 @@ | |||||
| <!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=<?php echo $cfg_soft_lang; ?>"> | |||||
| <title>文件校验</title> | |||||
| <link href='css/base.css' rel='stylesheet' type='text/css' /> | |||||
| <link rel="stylesheet" type="text/css" href="css/indexbody.css" /> | |||||
| <script language='javascript'> | |||||
| function Loading(surl) | |||||
| { | |||||
| document.getElementById('loaddiv').style.display = 'block'; | |||||
| location = surl; | |||||
| } | |||||
| </script> | |||||
| </head> | |||||
| <body background='images/allbg.gif' leftmargin='8' topmargin='8'> | |||||
| <div id='loaddiv' style='display:none'> | |||||
| <p align='center' style='padding-top:200px'><img src='images/loadinglit.gif' /> 请稍后,正在处理中...</p> | |||||
| </div> | |||||
| <table width="98%" border="0" align="center" cellpadding="3" cellspacing="1" bgcolor="#D6D6D6"> | |||||
| <tr> | |||||
| <td height="19" background="images/tbg.gif"> | |||||
| <table width="96%" border="0" cellspacing="1" cellpadding="1"> | |||||
| <tr> | |||||
| <td width="24%"><strong>文件校验操作:</strong></td> | |||||
| <td width="76%" align="right"> | |||||
| </td> | |||||
| </tr> | |||||
| </table> | |||||
| </td> | |||||
| </tr> | |||||
| <tr> | |||||
| <td height="200" bgcolor="#FFFFFF" valign="top"> | |||||
| <table width="100%" border="0" cellspacing="4" cellpadding="2"> | |||||
| <tr> | |||||
| <td height="53" align="center"> </td> | |||||
| <td> | |||||
| 您的系统最后升级时间:<b><?php echo $updateTime; ?></b>;指纹码最后同步时间:<b><?php echo $verifiesTime; ?></b> | |||||
| <br /> | |||||
| 第一次效验文件时或您的系统已经升级过,请先点击“在线获取最新指纹码” | |||||
| <br /> | |||||
| (文件校验将检查本站文件是否和DedeCMS原始文件是否完全一致,如果要替换差异文件,必须按提示设置被更改文件的目录有可写入权限) | |||||
| </td> | |||||
| <tr> | |||||
| <td height="53" align="center"> </td> | |||||
| <td> | |||||
| <div style='width:80%;background:#F9FCEF;border-bottom: 1px dashed #A7BA87;padding:3px;'> <b>效对操作:</b></div> | |||||
| <div style='padding:10px 0px 20px 0px;'> | |||||
| <a href="javascript:Loading('sys_verifies.php?action=update');" class='np coolbg'>在线获取最新指纹码==></a> | |||||
| | |||||
| <a href="javascript:Loading('sys_verifies.php?action=verify');" class='np coolbg'>效对本地文件==></a> | |||||
| | |||||
| 下载差异文件==> | |||||
| | |||||
| 替换差异文件==> | |||||
| </div> | |||||
| <div style='width:80%;background:#F9FCEF;border-bottom: 1px dashed #A7BA87;padding:3px;'> <b>管理指纹码:</b>(对于您自己修改过的文件,您可以在列表中屏蔽,下次忽略这些文件的效验)</div> | |||||
| <div style='padding:10px 0px 180px 0px;'> | |||||
| <a href="javascript:Loading('sys_verifies.php?action=manage');" class='np coolbg'>管理现有的指纹码</a> | |||||
| </div> | |||||
| <!-- | |||||
| <div style='width:80%;background:#D9E1CA;border-bottom: 1px dashed #A7BA87;padding:3px;'> <b>生成指纹码:</b></div> | |||||
| <div style='padding:10px 0px 20px 0px;'> | |||||
| <a href="javascript:Loading('sys_verifies.php?action=make');" class='np coolbg'>生成指纹码(官方使用)</a> | |||||
| </div> | |||||
| --> | |||||
| <br /> | |||||
| <br /> | |||||
| <br /> | |||||
| </td> | |||||
| </tr> | |||||
| </table> | |||||
| </td> | |||||
| </tr> | |||||
| </table> | |||||
| </body> | |||||
| </html> | |||||
| @@ -1,56 +0,0 @@ | |||||
| <!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=<?php echo $cfg_soft_lang; ?>"> | |||||
| <title>文件效验程序--下载更新文件</title> | |||||
| <link href="css/base.css" rel="stylesheet" type="text/css"> | |||||
| </head> | |||||
| <body background='images/allbg.gif' leftmargin='8' topmargin='8'> | |||||
| <table width="98%" border="0" cellpadding="3" cellspacing="1" bgcolor="#D6D6D6" align="center"> | |||||
| <tr> | |||||
| <td height="28" colspan="2" background='images/tbg.gif'> | |||||
| <div style="float:left"> | |||||
| <strong><a href='sys_verifies.php'><b>文件校验操作</b></a> >> 下载差异文件</strong> | |||||
| </div> | |||||
| <div style="float:right;padding-right:6px;"> | |||||
| <a href='index_body.php' class='np coolbg'>返回系统主页</a> | |||||
| </div> | |||||
| </td> | |||||
| </tr> | |||||
| <tr bgcolor="#ffffff"> | |||||
| <td height="20" colspan="2"> | |||||
| 下载的文件临时存放在文件夹(<font color='red'>../data/<?php echo $tmpdir; ?></font>)内,如果某些基础类有重要的改动导致更新中途中错,您可以从这文件夹提取文件手工更新。 | |||||
| </td> | |||||
| </tr> | |||||
| <?php echo $dirinfos; ?> | |||||
| <tr bgcolor="#F8FEDA"> | |||||
| <td height="20" colspan="2"> | |||||
| <table width="100%"> | |||||
| <tr> | |||||
| <td width="74%">进行状态: </td> | |||||
| <td width="26%" align="right"> | |||||
| <script language='javascript'> | |||||
| function ResizeDiv(obj,ty) | |||||
| { | |||||
| if(ty=="+") document.all[obj].style.pixelHeight += 50; | |||||
| else if(document.all[obj].style.pixelHeight>80) document.all[obj].style.pixelHeight = document.all[obj].style.pixelHeight - 50; | |||||
| } | |||||
| </script> | |||||
| [<a href='#' onClick="ResizeDiv('mdv','+');">增大</a>] [<a href='#' onClick="ResizeDiv('mdv','-');">缩小</a>] | |||||
| </td> | |||||
| </tr> | |||||
| </table> | |||||
| </td> | |||||
| </tr> | |||||
| <tr bgcolor="#FFFFFF"> | |||||
| <td colspan="2" id="mtd"> | |||||
| <div id='mdv' style='width:100%;height:350px;'> | |||||
| <?php | |||||
| echo $doneStr; | |||||
| ?> | |||||
| </div> | |||||
| </td> | |||||
| </tr> | |||||
| </table> | |||||
| </body> | |||||
| </html> | |||||
| @@ -1,74 +0,0 @@ | |||||
| <!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=<?php echo $cfg_soft_lang; ?>"> | |||||
| <title>文件校验</title> | |||||
| <link href='css/base.css' rel='stylesheet' type='text/css'> | |||||
| </head> | |||||
| <body background='images/allbg.gif' leftmargin='8' topmargin='8'> | |||||
| <table width="98%" border="0" align="center" cellpadding="3" cellspacing="1" bgcolor="#D6D6D6"> | |||||
| <tr> | |||||
| <td height="19" background="images/tbg.gif"> | |||||
| <table width="96%" border="0" cellspacing="1" cellpadding="1"> | |||||
| <tr> | |||||
| <td width="24%"> | |||||
| <strong><a href='sys_verifies.php'><b>文件校验</b></a> >> 文件效验管理</strong> | |||||
| </td> | |||||
| <td width="76%" align="right"> | |||||
| </td> | |||||
| </tr> | |||||
| </table> | |||||
| </td> | |||||
| </tr> | |||||
| <tr> | |||||
| <td height="200" bgcolor="#FFFFFF" valign="top"> | |||||
| <table width="100%" border="0" cellspacing="0" cellpadding="0"> | |||||
| <form action="sys_verifies.php?action=modify" method="post"> | |||||
| <tr> | |||||
| <td colspan="4" class='bline2' style="color:red"> 说明:这里是系统文件列表,如果本地对某些文件做过修改,但又不希望同官方服务器上面的镜像版本(发布版本)对应文件进行同步,可将文件校验方式修改为“本地(local)”,以确保不会重新下载文件修复。</td> | |||||
| </tr> | |||||
| <tr> | |||||
| <td class='bline2'> 修改? </td> | |||||
| <td class='bline2'> 文件名(用 Ctrl+F 搜索) </td> | |||||
| <td class='bline2'> 文件HASH </td> | |||||
| <td class='bline2'> 校验方式 </td> | |||||
| </tr> | |||||
| <?php | |||||
| foreach ($filelist as $key => $file) | |||||
| { | |||||
| ?> | |||||
| <tr> | |||||
| <td class='bline'> | |||||
| <input type="checkbox" name="modifys[]" value="<?php echo $file['filename'];?>" /> | |||||
| </td> | |||||
| <td class='bline'> | |||||
| <?php echo $file['filename'];?> | |||||
| </td> | |||||
| <td class='bline'> | |||||
| <?php echo $file['cthash'];?> | |||||
| </td> | |||||
| <td class='bline'> | |||||
| <?php echo $file['method'];?> | |||||
| </td> | |||||
| </tr> | |||||
| <?php | |||||
| } | |||||
| ?> | |||||
| <tr> | |||||
| <td colspan="20" height='28'> | |||||
| <label><input type="radio" name="method" value="offical" />官方(official)</label> | |||||
| <label><input type="radio" name="method" value="local" checked='1' />本地(local)</label> | |||||
| </td> | |||||
| </tr> | |||||
| <tr> | |||||
| <td colspan="20" height='36'> | |||||
| <input type="submit" name="submit" value="修改要文件的校验方式" class='np coolbg' /> | |||||
| </td> | |||||
| </tr> | |||||
| </form> | |||||
| </table> | |||||
| </td> | |||||
| </tr> | |||||
| </table> | |||||
| </body> | |||||
| </html> | |||||
| @@ -1,73 +0,0 @@ | |||||
| <!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=<?php echo $cfg_soft_lang; ?>"> | |||||
| <title>文件校验</title> | |||||
| <link href='css/base.css' rel='stylesheet' type='text/css'> | |||||
| </head> | |||||
| <body background='images/allbg.gif' leftmargin='8' topmargin='8'> | |||||
| <table width="98%" border="0" align="center" cellpadding="3" cellspacing="1" bgcolor="#D6D6D6"> | |||||
| <tr> | |||||
| <td height="19" background="images/tbg.gif"> | |||||
| <table width="96%" border="0" cellspacing="1" cellpadding="1"> | |||||
| <tr> | |||||
| <td width="24%"> | |||||
| <a href='sys_verifies.php'><b>文件效验</b></a> | |||||
| >> | |||||
| <strong>校验结果:</strong> 共有 <?php echo count($filelist); ?> 个文件不同 | |||||
| </td> | |||||
| <td width="76%" align="right"> | |||||
| </td> | |||||
| </tr> | |||||
| </table> | |||||
| </td> | |||||
| </tr> | |||||
| <tr> | |||||
| <td height="200" bgcolor="#FFFFFF" valign="top"> | |||||
| <table width="100%" border="0" cellspacing="0" cellpadding="0"> | |||||
| <form action="sys_verifies.php?action=getfiles" method="post"> | |||||
| <tr> | |||||
| <td class='bline2'> 恢复? </td> | |||||
| <td class='bline2'> 文件名(Ctrl+F查找) </td> | |||||
| <td class='bline2'> 校验方式 </td> | |||||
| <td class='bline2'> 最后修改时间 </td> | |||||
| <td class='bline2'> 指纹码/点击可浏览文件内容 </td> | |||||
| </tr> | |||||
| <?php | |||||
| foreach ($filelist as $key => $file) | |||||
| { | |||||
| ?> | |||||
| <tr> | |||||
| <td class='bline'> | |||||
| <input type="checkbox" name="refiles[]" value="<?php echo $file['filename'];?>" checked='1' /> | |||||
| </td> | |||||
| <td class='bline'> | |||||
| <?php echo $file['filename']; ?> | |||||
| </td> | |||||
| <td class='bline'> | |||||
| <?php echo $file['method']; ?> | |||||
| </td> | |||||
| <td class='bline'> | |||||
| <?php echo $file['mtime']; ?> | |||||
| </td> | |||||
| <td class='bline'> | |||||
| <a href="sys_verifies.php?action=view&filename=<?php echo $file['turefile']; ?>" target="_blank" class='coolbg' title="标准效验码为: <?php echo $file['cthash']; ?>"> | |||||
| <?php echo $file['localhash']; ?> | |||||
| </a> | |||||
| </td> | |||||
| </tr> | |||||
| <?php | |||||
| } | |||||
| ?> | |||||
| <tr> | |||||
| <td colspan="20" height='42'> | |||||
| <input type="submit" name="submit" value="从官方下载选中的文件并恢复" class='np coolbg' /> | |||||
| </td> | |||||
| </tr> | |||||
| </table> | |||||
| </form> | |||||
| </td> | |||||
| </tr> | |||||
| </table> | |||||
| </body> | |||||
| </html> | |||||
| @@ -283,6 +283,24 @@ class DedeHttpDown | |||||
| return $this->m_html; | return $this->m_html; | ||||
| } | } | ||||
| function GetJSON() | |||||
| { | |||||
| if ($this->m_html != '') { | |||||
| return json_decode($this->m_html); | |||||
| } | |||||
| if (!$this->IsText()) { | |||||
| return ''; | |||||
| } | |||||
| if (!$this->m_fp || @feof($this->m_fp)) { | |||||
| return ''; | |||||
| } | |||||
| while (!feof($this->m_fp)) { | |||||
| $this->m_html .= fgets($this->m_fp, 256); | |||||
| } | |||||
| @fclose($this->m_fp); | |||||
| return json_decode($this->m_html); | |||||
| } | |||||
| /** | /** | ||||
| * 开始HTTP会话 | * 开始HTTP会话 | ||||
| * | * | ||||
| @@ -0,0 +1,83 @@ | |||||
| /* | |||||
| This is part of jsdifflib v1.0. <http://github.com/cemerick/jsdifflib> | |||||
| Copyright 2007 - 2011 Chas Emerick <cemerick@snowtide.com>. All rights reserved. | |||||
| Redistribution and use in source and binary forms, with or without modification, are | |||||
| permitted provided that the following conditions are met: | |||||
| 1. Redistributions of source code must retain the above copyright notice, this list of | |||||
| conditions and the following disclaimer. | |||||
| 2. Redistributions in binary form must reproduce the above copyright notice, this list | |||||
| of conditions and the following disclaimer in the documentation and/or other materials | |||||
| provided with the distribution. | |||||
| THIS SOFTWARE IS PROVIDED BY Chas Emerick ``AS IS'' AND ANY EXPRESS OR IMPLIED | |||||
| WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND | |||||
| FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL Chas Emerick OR | |||||
| CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR | |||||
| CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR | |||||
| SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON | |||||
| ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING | |||||
| NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF | |||||
| ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. | |||||
| The views and conclusions contained in the software and documentation are those of the | |||||
| authors and should not be interpreted as representing official policies, either expressed | |||||
| or implied, of Chas Emerick. | |||||
| */ | |||||
| table.diff { | |||||
| border-collapse:collapse; | |||||
| border:1px solid darkgray; | |||||
| white-space:pre-wrap | |||||
| } | |||||
| table.diff tbody { | |||||
| font-family:Courier, monospace | |||||
| } | |||||
| table.diff tbody th { | |||||
| font-family:verdana,arial,'Bitstream Vera Sans',helvetica,sans-serif; | |||||
| background:#EED; | |||||
| font-size:11px; | |||||
| font-weight:normal; | |||||
| border:1px solid #BBC; | |||||
| color:#886; | |||||
| padding:.3em .5em .1em 2em; | |||||
| text-align:right; | |||||
| vertical-align:top | |||||
| } | |||||
| table.diff thead { | |||||
| border-bottom:1px solid #BBC; | |||||
| background:#EFEFEF; | |||||
| font-family:Verdana | |||||
| } | |||||
| table.diff thead th.texttitle { | |||||
| text-align:left | |||||
| } | |||||
| table.diff tbody td { | |||||
| padding:0px .4em; | |||||
| padding-top:.4em; | |||||
| vertical-align:top; | |||||
| } | |||||
| table.diff .empty { | |||||
| background-color:#DDD; | |||||
| } | |||||
| table.diff .replace { | |||||
| background-color:#FD8 | |||||
| } | |||||
| table.diff .delete { | |||||
| background-color:#E99; | |||||
| } | |||||
| table.diff .skip { | |||||
| background-color:#EFEFEF; | |||||
| border:1px solid #AAA; | |||||
| border-right:1px solid #BBC; | |||||
| } | |||||
| table.diff .insert { | |||||
| background-color:#9E9 | |||||
| } | |||||
| table.diff th.author { | |||||
| text-align:right; | |||||
| border-top:1px solid #BBC; | |||||
| background:#EFEFEF | |||||
| } | |||||
| @@ -0,0 +1,411 @@ | |||||
| /*** | |||||
| This is part of jsdifflib v1.0. <http://snowtide.com/jsdifflib> | |||||
| Copyright (c) 2007, Snowtide Informatics Systems, Inc. | |||||
| All rights reserved. | |||||
| Redistribution and use in source and binary forms, with or without modification, | |||||
| are permitted provided that the following conditions are met: | |||||
| * Redistributions of source code must retain the above copyright notice, this | |||||
| list of conditions and the following disclaimer. | |||||
| * Redistributions in binary form must reproduce the above copyright notice, | |||||
| this list of conditions and the following disclaimer in the documentation | |||||
| and/or other materials provided with the distribution. | |||||
| * Neither the name of the Snowtide Informatics Systems nor the names of its | |||||
| contributors may be used to endorse or promote products derived from this | |||||
| software without specific prior written permission. | |||||
| THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY | |||||
| EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES | |||||
| OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT | |||||
| SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, | |||||
| INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED | |||||
| TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR | |||||
| BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN | |||||
| CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN | |||||
| ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH | |||||
| DAMAGE. | |||||
| ***/ | |||||
| /* Author: Chas Emerick <cemerick@snowtide.com> */ | |||||
| __whitespace = {" ":true, "\t":true, "\n":true, "\f":true, "\r":true}; | |||||
| difflib = { | |||||
| defaultJunkFunction: function (c) { | |||||
| return __whitespace.hasOwnProperty(c); | |||||
| }, | |||||
| stripLinebreaks: function (str) { return str.replace(/^[\n\r]*|[\n\r]*$/g, ""); }, | |||||
| stringAsLines: function (str) { | |||||
| var lfpos = str.indexOf("\n"); | |||||
| var crpos = str.indexOf("\r"); | |||||
| var linebreak = ((lfpos > -1 && crpos > -1) || crpos < 0) ? "\n" : "\r"; | |||||
| var lines = str.split(linebreak); | |||||
| for (var i = 0; i < lines.length; i++) { | |||||
| lines[i] = difflib.stripLinebreaks(lines[i]); | |||||
| } | |||||
| return lines; | |||||
| }, | |||||
| // iteration-based reduce implementation | |||||
| __reduce: function (func, list, initial) { | |||||
| if (initial != null) { | |||||
| var value = initial; | |||||
| var idx = 0; | |||||
| } else if (list) { | |||||
| var value = list[0]; | |||||
| var idx = 1; | |||||
| } else { | |||||
| return null; | |||||
| } | |||||
| for (; idx < list.length; idx++) { | |||||
| value = func(value, list[idx]); | |||||
| } | |||||
| return value; | |||||
| }, | |||||
| // comparison function for sorting lists of numeric tuples | |||||
| __ntuplecomp: function (a, b) { | |||||
| var mlen = Math.max(a.length, b.length); | |||||
| for (var i = 0; i < mlen; i++) { | |||||
| if (a[i] < b[i]) return -1; | |||||
| if (a[i] > b[i]) return 1; | |||||
| } | |||||
| return a.length == b.length ? 0 : (a.length < b.length ? -1 : 1); | |||||
| }, | |||||
| __calculate_ratio: function (matches, length) { | |||||
| return length ? 2.0 * matches / length : 1.0; | |||||
| }, | |||||
| // returns a function that returns true if a key passed to the returned function | |||||
| // is in the dict (js object) provided to this function; replaces being able to | |||||
| // carry around dict.has_key in python... | |||||
| __isindict: function (dict) { | |||||
| return function (key) { return dict.hasOwnProperty(key); }; | |||||
| }, | |||||
| // replacement for python's dict.get function -- need easy default values | |||||
| __dictget: function (dict, key, defaultValue) { | |||||
| return dict.hasOwnProperty(key) ? dict[key] : defaultValue; | |||||
| }, | |||||
| SequenceMatcher: function (a, b, isjunk) { | |||||
| this.set_seqs = function (a, b) { | |||||
| this.set_seq1(a); | |||||
| this.set_seq2(b); | |||||
| } | |||||
| this.set_seq1 = function (a) { | |||||
| if (a == this.a) return; | |||||
| this.a = a; | |||||
| this.matching_blocks = this.opcodes = null; | |||||
| } | |||||
| this.set_seq2 = function (b) { | |||||
| if (b == this.b) return; | |||||
| this.b = b; | |||||
| this.matching_blocks = this.opcodes = this.fullbcount = null; | |||||
| this.__chain_b(); | |||||
| } | |||||
| this.__chain_b = function () { | |||||
| var b = this.b; | |||||
| var n = b.length; | |||||
| var b2j = this.b2j = {}; | |||||
| var populardict = {}; | |||||
| for (var i = 0; i < b.length; i++) { | |||||
| var elt = b[i]; | |||||
| if (b2j.hasOwnProperty(elt)) { | |||||
| var indices = b2j[elt]; | |||||
| if (n >= 200 && indices.length * 100 > n) { | |||||
| populardict[elt] = 1; | |||||
| delete b2j[elt]; | |||||
| } else { | |||||
| indices.push(i); | |||||
| } | |||||
| } else { | |||||
| b2j[elt] = [i]; | |||||
| } | |||||
| } | |||||
| for (var elt in populardict) { | |||||
| if (populardict.hasOwnProperty(elt)) { | |||||
| delete b2j[elt]; | |||||
| } | |||||
| } | |||||
| var isjunk = this.isjunk; | |||||
| var junkdict = {}; | |||||
| if (isjunk) { | |||||
| for (var elt in populardict) { | |||||
| if (populardict.hasOwnProperty(elt) && isjunk(elt)) { | |||||
| junkdict[elt] = 1; | |||||
| delete populardict[elt]; | |||||
| } | |||||
| } | |||||
| for (var elt in b2j) { | |||||
| if (b2j.hasOwnProperty(elt) && isjunk(elt)) { | |||||
| junkdict[elt] = 1; | |||||
| delete b2j[elt]; | |||||
| } | |||||
| } | |||||
| } | |||||
| this.isbjunk = difflib.__isindict(junkdict); | |||||
| this.isbpopular = difflib.__isindict(populardict); | |||||
| } | |||||
| this.find_longest_match = function (alo, ahi, blo, bhi) { | |||||
| var a = this.a; | |||||
| var b = this.b; | |||||
| var b2j = this.b2j; | |||||
| var isbjunk = this.isbjunk; | |||||
| var besti = alo; | |||||
| var bestj = blo; | |||||
| var bestsize = 0; | |||||
| var j = null; | |||||
| var j2len = {}; | |||||
| var nothing = []; | |||||
| for (var i = alo; i < ahi; i++) { | |||||
| var newj2len = {}; | |||||
| var jdict = difflib.__dictget(b2j, a[i], nothing); | |||||
| for (var jkey in jdict) { | |||||
| if (jdict.hasOwnProperty(jkey)) { | |||||
| j = jdict[jkey]; | |||||
| if (j < blo) continue; | |||||
| if (j >= bhi) break; | |||||
| newj2len[j] = k = difflib.__dictget(j2len, j - 1, 0) + 1; | |||||
| if (k > bestsize) { | |||||
| besti = i - k + 1; | |||||
| bestj = j - k + 1; | |||||
| bestsize = k; | |||||
| } | |||||
| } | |||||
| } | |||||
| j2len = newj2len; | |||||
| } | |||||
| while (besti > alo && bestj > blo && !isbjunk(b[bestj - 1]) && a[besti - 1] == b[bestj - 1]) { | |||||
| besti--; | |||||
| bestj--; | |||||
| bestsize++; | |||||
| } | |||||
| while (besti + bestsize < ahi && bestj + bestsize < bhi && | |||||
| !isbjunk(b[bestj + bestsize]) && | |||||
| a[besti + bestsize] == b[bestj + bestsize]) { | |||||
| bestsize++; | |||||
| } | |||||
| while (besti > alo && bestj > blo && isbjunk(b[bestj - 1]) && a[besti - 1] == b[bestj - 1]) { | |||||
| besti--; | |||||
| bestj--; | |||||
| bestsize++; | |||||
| } | |||||
| while (besti + bestsize < ahi && bestj + bestsize < bhi && isbjunk(b[bestj + bestsize]) && | |||||
| a[besti + bestsize] == b[bestj + bestsize]) { | |||||
| bestsize++; | |||||
| } | |||||
| return [besti, bestj, bestsize]; | |||||
| } | |||||
| this.get_matching_blocks = function () { | |||||
| if (this.matching_blocks != null) return this.matching_blocks; | |||||
| var la = this.a.length; | |||||
| var lb = this.b.length; | |||||
| var queue = [[0, la, 0, lb]]; | |||||
| var matching_blocks = []; | |||||
| var alo, ahi, blo, bhi, qi, i, j, k, x; | |||||
| while (queue.length) { | |||||
| qi = queue.pop(); | |||||
| alo = qi[0]; | |||||
| ahi = qi[1]; | |||||
| blo = qi[2]; | |||||
| bhi = qi[3]; | |||||
| x = this.find_longest_match(alo, ahi, blo, bhi); | |||||
| i = x[0]; | |||||
| j = x[1]; | |||||
| k = x[2]; | |||||
| if (k) { | |||||
| matching_blocks.push(x); | |||||
| if (alo < i && blo < j) | |||||
| queue.push([alo, i, blo, j]); | |||||
| if (i+k < ahi && j+k < bhi) | |||||
| queue.push([i + k, ahi, j + k, bhi]); | |||||
| } | |||||
| } | |||||
| matching_blocks.sort(difflib.__ntuplecomp); | |||||
| var i1 = j1 = k1 = block = 0; | |||||
| var non_adjacent = []; | |||||
| for (var idx in matching_blocks) { | |||||
| if (matching_blocks.hasOwnProperty(idx)) { | |||||
| block = matching_blocks[idx]; | |||||
| i2 = block[0]; | |||||
| j2 = block[1]; | |||||
| k2 = block[2]; | |||||
| if (i1 + k1 == i2 && j1 + k1 == j2) { | |||||
| k1 += k2; | |||||
| } else { | |||||
| if (k1) non_adjacent.push([i1, j1, k1]); | |||||
| i1 = i2; | |||||
| j1 = j2; | |||||
| k1 = k2; | |||||
| } | |||||
| } | |||||
| } | |||||
| if (k1) non_adjacent.push([i1, j1, k1]); | |||||
| non_adjacent.push([la, lb, 0]); | |||||
| this.matching_blocks = non_adjacent; | |||||
| return this.matching_blocks; | |||||
| } | |||||
| this.get_opcodes = function () { | |||||
| if (this.opcodes != null) return this.opcodes; | |||||
| var i = 0; | |||||
| var j = 0; | |||||
| var answer = []; | |||||
| this.opcodes = answer; | |||||
| var block, ai, bj, size, tag; | |||||
| var blocks = this.get_matching_blocks(); | |||||
| for (var idx in blocks) { | |||||
| if (blocks.hasOwnProperty(idx)) { | |||||
| block = blocks[idx]; | |||||
| ai = block[0]; | |||||
| bj = block[1]; | |||||
| size = block[2]; | |||||
| tag = ''; | |||||
| if (i < ai && j < bj) { | |||||
| tag = 'replace'; | |||||
| } else if (i < ai) { | |||||
| tag = 'delete'; | |||||
| } else if (j < bj) { | |||||
| tag = 'insert'; | |||||
| } | |||||
| if (tag) answer.push([tag, i, ai, j, bj]); | |||||
| i = ai + size; | |||||
| j = bj + size; | |||||
| if (size) answer.push(['equal', ai, i, bj, j]); | |||||
| } | |||||
| } | |||||
| return answer; | |||||
| } | |||||
| // this is a generator function in the python lib, which of course is not supported in javascript | |||||
| // the reimplementation builds up the grouped opcodes into a list in their entirety and returns that. | |||||
| this.get_grouped_opcodes = function (n) { | |||||
| if (!n) n = 3; | |||||
| var codes = this.get_opcodes(); | |||||
| if (!codes) codes = [["equal", 0, 1, 0, 1]]; | |||||
| var code, tag, i1, i2, j1, j2; | |||||
| if (codes[0][0] == 'equal') { | |||||
| code = codes[0]; | |||||
| tag = code[0]; | |||||
| i1 = code[1]; | |||||
| i2 = code[2]; | |||||
| j1 = code[3]; | |||||
| j2 = code[4]; | |||||
| codes[0] = [tag, Math.max(i1, i2 - n), i2, Math.max(j1, j2 - n), j2]; | |||||
| } | |||||
| if (codes[codes.length - 1][0] == 'equal') { | |||||
| code = codes[codes.length - 1]; | |||||
| tag = code[0]; | |||||
| i1 = code[1]; | |||||
| i2 = code[2]; | |||||
| j1 = code[3]; | |||||
| j2 = code[4]; | |||||
| codes[codes.length - 1] = [tag, i1, Math.min(i2, i1 + n), j1, Math.min(j2, j1 + n)]; | |||||
| } | |||||
| var nn = n + n; | |||||
| var group = []; | |||||
| var groups = []; | |||||
| for (var idx in codes) { | |||||
| if (codes.hasOwnProperty(idx)) { | |||||
| code = codes[idx]; | |||||
| tag = code[0]; | |||||
| i1 = code[1]; | |||||
| i2 = code[2]; | |||||
| j1 = code[3]; | |||||
| j2 = code[4]; | |||||
| if (tag == 'equal' && i2 - i1 > nn) { | |||||
| group.push([tag, i1, Math.min(i2, i1 + n), j1, Math.min(j2, j1 + n)]); | |||||
| groups.push(group); | |||||
| group = []; | |||||
| i1 = Math.max(i1, i2-n); | |||||
| j1 = Math.max(j1, j2-n); | |||||
| } | |||||
| group.push([tag, i1, i2, j1, j2]); | |||||
| } | |||||
| } | |||||
| if (group && !(group.length == 1 && group[0][0] == 'equal')) groups.push(group) | |||||
| return groups; | |||||
| } | |||||
| this.ratio = function () { | |||||
| matches = difflib.__reduce( | |||||
| function (sum, triple) { return sum + triple[triple.length - 1]; }, | |||||
| this.get_matching_blocks(), 0); | |||||
| return difflib.__calculate_ratio(matches, this.a.length + this.b.length); | |||||
| } | |||||
| this.quick_ratio = function () { | |||||
| var fullbcount, elt; | |||||
| if (this.fullbcount == null) { | |||||
| this.fullbcount = fullbcount = {}; | |||||
| for (var i = 0; i < this.b.length; i++) { | |||||
| elt = this.b[i]; | |||||
| fullbcount[elt] = difflib.__dictget(fullbcount, elt, 0) + 1; | |||||
| } | |||||
| } | |||||
| fullbcount = this.fullbcount; | |||||
| var avail = {}; | |||||
| var availhas = difflib.__isindict(avail); | |||||
| var matches = numb = 0; | |||||
| for (var i = 0; i < this.a.length; i++) { | |||||
| elt = this.a[i]; | |||||
| if (availhas(elt)) { | |||||
| numb = avail[elt]; | |||||
| } else { | |||||
| numb = difflib.__dictget(fullbcount, elt, 0); | |||||
| } | |||||
| avail[elt] = numb - 1; | |||||
| if (numb > 0) matches++; | |||||
| } | |||||
| return difflib.__calculate_ratio(matches, this.a.length + this.b.length); | |||||
| } | |||||
| this.real_quick_ratio = function () { | |||||
| var la = this.a.length; | |||||
| var lb = this.b.length; | |||||
| return _calculate_ratio(Math.min(la, lb), la + lb); | |||||
| } | |||||
| this.isjunk = isjunk ? isjunk : difflib.defaultJunkFunction; | |||||
| this.a = this.b = null; | |||||
| this.set_seqs(a, b); | |||||
| } | |||||
| }; | |||||
| @@ -0,0 +1,194 @@ | |||||
| /* | |||||
| This is part of jsdifflib v1.0. <http://github.com/cemerick/jsdifflib> | |||||
| Copyright 2007 - 2011 Chas Emerick <cemerick@snowtide.com>. All rights reserved. | |||||
| Redistribution and use in source and binary forms, with or without modification, are | |||||
| permitted provided that the following conditions are met: | |||||
| 1. Redistributions of source code must retain the above copyright notice, this list of | |||||
| conditions and the following disclaimer. | |||||
| 2. Redistributions in binary form must reproduce the above copyright notice, this list | |||||
| of conditions and the following disclaimer in the documentation and/or other materials | |||||
| provided with the distribution. | |||||
| THIS SOFTWARE IS PROVIDED BY Chas Emerick ``AS IS'' AND ANY EXPRESS OR IMPLIED | |||||
| WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND | |||||
| FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL Chas Emerick OR | |||||
| CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR | |||||
| CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR | |||||
| SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON | |||||
| ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING | |||||
| NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF | |||||
| ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. | |||||
| The views and conclusions contained in the software and documentation are those of the | |||||
| authors and should not be interpreted as representing official policies, either expressed | |||||
| or implied, of Chas Emerick. | |||||
| */ | |||||
| diffview = { | |||||
| /** | |||||
| * Builds and returns a visual diff view. The single parameter, `params', should contain | |||||
| * the following values: | |||||
| * | |||||
| * - baseTextLines: the array of strings that was used as the base text input to SequenceMatcher | |||||
| * - newTextLines: the array of strings that was used as the new text input to SequenceMatcher | |||||
| * - opcodes: the array of arrays returned by SequenceMatcher.get_opcodes() | |||||
| * - baseTextName: the title to be displayed above the base text listing in the diff view; defaults | |||||
| * to "Base Text" | |||||
| * - newTextName: the title to be displayed above the new text listing in the diff view; defaults | |||||
| * to "New Text" | |||||
| * - contextSize: the number of lines of context to show around differences; by default, all lines | |||||
| * are shown | |||||
| * - viewType: if 0, a side-by-side diff view is generated (default); if 1, an inline diff view is | |||||
| * generated | |||||
| */ | |||||
| buildView: function (params) { | |||||
| var baseTextLines = params.baseTextLines; | |||||
| var newTextLines = params.newTextLines; | |||||
| var opcodes = params.opcodes; | |||||
| var baseTextName = params.baseTextName ? params.baseTextName : "Base Text"; | |||||
| var newTextName = params.newTextName ? params.newTextName : "New Text"; | |||||
| var contextSize = params.contextSize; | |||||
| var inline = (params.viewType == 0 || params.viewType == 1) ? params.viewType : 0; | |||||
| if (baseTextLines == null) | |||||
| throw "Cannot build diff view; baseTextLines is not defined."; | |||||
| if (newTextLines == null) | |||||
| throw "Cannot build diff view; newTextLines is not defined."; | |||||
| if (!opcodes) | |||||
| throw "Canno build diff view; opcodes is not defined."; | |||||
| function celt (name, clazz) { | |||||
| var e = document.createElement(name); | |||||
| e.className = clazz; | |||||
| return e; | |||||
| } | |||||
| function telt (name, text) { | |||||
| var e = document.createElement(name); | |||||
| e.appendChild(document.createTextNode(text)); | |||||
| return e; | |||||
| } | |||||
| function ctelt (name, clazz, text) { | |||||
| var e = document.createElement(name); | |||||
| e.className = clazz; | |||||
| e.appendChild(document.createTextNode(text)); | |||||
| return e; | |||||
| } | |||||
| var tdata = document.createElement("thead"); | |||||
| var node = document.createElement("tr"); | |||||
| tdata.appendChild(node); | |||||
| if (inline) { | |||||
| node.appendChild(document.createElement("th")); | |||||
| node.appendChild(document.createElement("th")); | |||||
| node.appendChild(ctelt("th", "texttitle", baseTextName + " vs. " + newTextName)); | |||||
| } else { | |||||
| node.appendChild(document.createElement("th")); | |||||
| node.appendChild(ctelt("th", "texttitle", baseTextName)); | |||||
| node.appendChild(document.createElement("th")); | |||||
| node.appendChild(ctelt("th", "texttitle", newTextName)); | |||||
| } | |||||
| tdata = [tdata]; | |||||
| var rows = []; | |||||
| var node2; | |||||
| /** | |||||
| * Adds two cells to the given row; if the given row corresponds to a real | |||||
| * line number (based on the line index tidx and the endpoint of the | |||||
| * range in question tend), then the cells will contain the line number | |||||
| * and the line of text from textLines at position tidx (with the class of | |||||
| * the second cell set to the name of the change represented), and tidx + 1 will | |||||
| * be returned. Otherwise, tidx is returned, and two empty cells are added | |||||
| * to the given row. | |||||
| */ | |||||
| function addCells (row, tidx, tend, textLines, change) { | |||||
| if (tidx < tend) { | |||||
| row.appendChild(telt("th", (tidx + 1).toString())); | |||||
| row.appendChild(ctelt("td", change, textLines[tidx].replace(/\t/g, "\u00a0\u00a0\u00a0\u00a0"))); | |||||
| return tidx + 1; | |||||
| } else { | |||||
| row.appendChild(document.createElement("th")); | |||||
| row.appendChild(celt("td", "empty")); | |||||
| return tidx; | |||||
| } | |||||
| } | |||||
| function addCellsInline (row, tidx, tidx2, textLines, change) { | |||||
| row.appendChild(telt("th", tidx == null ? "" : (tidx + 1).toString())); | |||||
| row.appendChild(telt("th", tidx2 == null ? "" : (tidx2 + 1).toString())); | |||||
| row.appendChild(ctelt("td", change, textLines[tidx != null ? tidx : tidx2].replace(/\t/g, "\u00a0\u00a0\u00a0\u00a0"))); | |||||
| } | |||||
| for (var idx = 0; idx < opcodes.length; idx++) { | |||||
| code = opcodes[idx]; | |||||
| change = code[0]; | |||||
| var b = code[1]; | |||||
| var be = code[2]; | |||||
| var n = code[3]; | |||||
| var ne = code[4]; | |||||
| var rowcnt = Math.max(be - b, ne - n); | |||||
| var toprows = []; | |||||
| var botrows = []; | |||||
| for (var i = 0; i < rowcnt; i++) { | |||||
| // jump ahead if we've alredy provided leading context or if this is the first range | |||||
| if (contextSize && opcodes.length > 1 && ((idx > 0 && i == contextSize) || (idx == 0 && i == 0)) && change=="equal") { | |||||
| var jump = rowcnt - ((idx == 0 ? 1 : 2) * contextSize); | |||||
| if (jump > 1) { | |||||
| toprows.push(node = document.createElement("tr")); | |||||
| b += jump; | |||||
| n += jump; | |||||
| i += jump - 1; | |||||
| node.appendChild(telt("th", "...")); | |||||
| if (!inline) node.appendChild(ctelt("td", "skip", "")); | |||||
| node.appendChild(telt("th", "...")); | |||||
| node.appendChild(ctelt("td", "skip", "")); | |||||
| // skip last lines if they're all equal | |||||
| if (idx + 1 == opcodes.length) { | |||||
| break; | |||||
| } else { | |||||
| continue; | |||||
| } | |||||
| } | |||||
| } | |||||
| toprows.push(node = document.createElement("tr")); | |||||
| if (inline) { | |||||
| if (change == "insert") { | |||||
| addCellsInline(node, null, n++, newTextLines, change); | |||||
| } else if (change == "replace") { | |||||
| botrows.push(node2 = document.createElement("tr")); | |||||
| if (b < be) addCellsInline(node, b++, null, baseTextLines, "delete"); | |||||
| if (n < ne) addCellsInline(node2, null, n++, newTextLines, "insert"); | |||||
| } else if (change == "delete") { | |||||
| addCellsInline(node, b++, null, baseTextLines, change); | |||||
| } else { | |||||
| // equal | |||||
| addCellsInline(node, b++, n++, baseTextLines, change); | |||||
| } | |||||
| } else { | |||||
| b = addCells(node, b, be, baseTextLines, change); | |||||
| n = addCells(node, n, ne, newTextLines, change); | |||||
| } | |||||
| } | |||||
| for (var i = 0; i < toprows.length; i++) rows.push(toprows[i]); | |||||
| for (var i = 0; i < botrows.length; i++) rows.push(botrows[i]); | |||||
| } | |||||
| tdata.push(node = document.createElement("tbody")); | |||||
| for (var idx in rows) rows.hasOwnProperty(idx) && node.appendChild(rows[idx]); | |||||
| node = celt("table", "diff" + (inline ? " inlinediff" : "")); | |||||
| for (var idx in tdata) tdata.hasOwnProperty(idx) && node.appendChild(tdata[idx]); | |||||
| return node; | |||||
| } | |||||
| }; | |||||