在php 模仿登录我们需要使用curl_init函数,下面我来介绍利用 curl 模拟 post 登录discuz论坛并且实现自动顶帖功能。
其实模拟登录就那点事,无法就是获得相应的参数,然后模拟发送,把获得的COOKIE 带入下一步操作中去
discuzx 系列为防止灌水,一直在用 formhash() 这个函数:
1、下面来看下formhash 这个函数:
代码如下 |
复制代码 |
function formhash($specialadd = '') {
global $_G;
$hashadd = defined('IN_ADMINCP') ? 'Only For Discuz! Admin Control Panel' : '';
return substr(md5(substr($_G['timestamp'],0,-7).$_G['username'].$_G['uid'].$_G['authkey'].$hashadd.$specialadd), 8, 8);
}
|
注:生成方式:
1、截取的时间戳
2、用户名
3、用户ID
4、authkey
5、hashadd(定值)
6、specialadd(定值)
因为存在用户名和用户id ,所以 在登录前跟登录后的 产生的值是不同的,即:在登录前跟登录后你要2次来获得fromhash;
那么authkey又是个什么东西呢 ?
2、关于authkey
//代码位置:/source/class/discuz/discuz_application.php
代码如下 |
复制代码 |
if(empty($this->var['cookie']['saltkey'])) {
$this->var['cookie']['saltkey'] = random(8);//这一步不要去管
dsetcookie('saltkey', $this->var['cookie']['saltkey'], 86400 * 30, 1, 1);
}
$this->var['authkey'] = md5($this->var['config']['security']['authkey'].$this->var['cookie']['saltkey']);
|
在这里可以看到:authkey是根据配置文件的authkey 和cookie 里面的saltkey 来生成的
其实在这里就可以看出来了, 只要网站的$this->var['cookie']['saltkey'] 这个值始终保存在cookie里面就这样就可以保证 formhash 那里生成的值永远是一样的(永远是相对的)
这里还要说一点:
3 cookie系列
discuz 的cookie的前缀是随机生成的
代码位置:/source/class/discuz/discuz_application.php
代码如下 |
复制代码 |
$this->var['config']['cookie']['cookiepre'] = $this->var['config']['cookie']['cookiepre'].substr(md5($this->;var['config']['cookie']['cookiepath'].'|'.$this->;var['config']['cookie']['cookiedomain']), 0, 4).'_'; |
只要你登录下网站看看cookie 的设置这里就可以了,他的前缀确实hi一直不变的,当然改了配置文件那肯定会变
到底该怎么写呢:说下我实现的思路
1、登录下访问网站一下抓取网页返回的 saltkey(cookie),formhash(值) 这两个值(saltkey在下面一定要带上,而且上下文要一致)
2、构造登录的内容然后模拟post 提交 (一定要带上第一步抓取到的cookie跟formhash 这一个值)
3、如果登录成功,接着获取一个页面的 formhash 跟设置的cookie(这次获得到的formhash 就是你可以一直使用的了)
4、构造发帖还有顶帖的post 提交到页面 (cookie 跟formhash 还是重点 )
关于php 使用 crul 模拟 post 部分代码
代码如下 |
复制代码 |
$ch = curl_init($url); //初始化
curl_setopt($ch, CURLOPT_HEADER, 1); //不返回header部分
curl_setopt($ch, CURLOPT_POST, 1);//是否
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true); //返回字符串,而非直接输出
curl_setopt($ch,CURLOPT_REFERER,$refer);
curl_setopt($ch, CURLOPT_COOKIE, $tocookies); //存储cookies
curl_setopt($ch, CURLOPT_POSTFIELDS, $datas);
|
代码就不共享了,有能力的朋友自己写把; 这东西容易引起混乱
session_start启动慢是自己的机器使用了memcache来缓存session了,这样发现用户登录之后mysql查询超级慢了,下面我来介绍一个临时的解决办法。
下面是我们的测试页面,就几句
代码如下 |
复制代码 |
<?php
session_start();
echo '111';exit
?>
|
CPU,IO,磁盘,内存……这些没问题的,都有排查过,刚开始以为网络问题、被墙、过滤、内存……问题,最后确定都不是.应该不是硬件资源问题了.
现在用额外加段代码能解决这问题,治标不治本,还没找到是什么原因导致session_start启动慢.
先自动创建一PHPSESSID,不用session_start自动分配的.
代码如下 |
复制代码 |
if(!isset($_COOKIE['PHPSESSID']))
{
setcookie('PHPSESSID', time(), time()+60*60, '/' );
header('location:index.php');
exit;
}
|
最后的样子如下:
代码如下 |
复制代码 |
<?php
if(!isset($_COOKIE['zenid']) && $_SERVER['HTTP_USER_AGENT']!='UDROBOT')
{
setcookie('zenid', md5(md5(time().rand(999,1000)).rand(999,1000)), time()+60*60, '/' );
header('location:'.$_SERVER['REQUEST_URI']);
exit;
}
.....
?>
|
现在使用微信公众平台的商家越来越多了,微信公众平台为我提供了大量api接口他可以实现与我们网站数据对接,然后用户输入内容自动回复相关信息,下面我来介绍微信公众平台智能机器开发教程。
最近在做微信公众平台开发,一口气写了二十几个功能,挺有意思的~
今天来分享一下开发经验~
微信公众平台提供的接口很简单,先看看消息交互流程:
说的通俗一些,用户使用微信发送消息 -> 微信将数据发送给开发者 -> 开发者处理消息并返回数据至微信 -> 微信把返回数据发送给用户,期间数据交互通过XML完成,就这么简单。
下面写个实例,开发微信智能聊天机器人:
1. 注册微信公众平台账号
微信公众平台:
https://mp.weixin.qq.com/
注: 目前一张身份证只能注册两个账号,账号名称关乎加V认证,请慎重注册。
2. 申请服务器/虚拟主机
没有服务器/虚拟主机的童鞋可以使用BAE和SAE,不多介绍。
3. 开启开发者模式
微信公众平台有两个模式,一个是编辑模式(傻瓜模式),简单但功能单一。另一个是开发者模式,可以通过开发实现复杂功能。两个模式互斥,显而易见,登录微信公众平台并通过“高级功能”菜单开启开发者模式。
4. 填写接口配置信息
同样是在“高级功能”菜单中配置,需要配置两项参数:
URL: 开发者应用访问地址,目前仅支持80端口,以“http://www.你的域名.com/weixin/index.php”为例。
TOKEN: 随意填写,用于生成签名,以“你的域名”为例。
填写完把下面代码保存为index.php并上传至http://www.你的域名.com/weixin/目录,最后点击“提交”完成验证。
代码如下 |
复制代码 |
<?php
define("TOKEN", "你的域名"); //TOKEN值
$wechatObj = new wechat();
$wechatObj->valid();
class wechat {
public function valid() {
$echoStr = $_GET["echostr"];
if($this->checkSignature()){
echo $echoStr;
exit;
}
}
private function checkSignature() {
$signature = $_GET["signature"];
$timestamp = $_GET["timestamp"];
$nonce = $_GET["nonce"];
$token = TOKEN;
$tmpArr = array($token, $timestamp, $nonce);
sort($tmpArr);
$tmpStr = implode( $tmpArr );
$tmpStr = sha1( $tmpStr );
if( $tmpStr == $signature ) {
return true;
} else {
return false;
}
}
}
?>
|
这玩意儿就是微信公众平台校验URL是否正确接入,研究代码没有实质性意义,验证完即可删除文件,就不详细说明了,有兴趣的童鞋可以查看官方文档。
微信公众平台API文档:
http://mp.weixin.qq.com/wiki/index.php
5. 开发微信公众平台功能
OK,上面提到了,微信公众平台与开发者之间的数据交互是通过XML完成的,既然用到XML,当然得遵循规范,所以在着手开发之前先看看官方接口文档提供的XML规范,以文本消息为例:
当用户向微信公众账号发送消息时,微信服务器会POST给开发者一些数据:
代码如下 |
复制代码 |
<xml>
<!--开发者微信号-->
<ToUserName><![CDATA[toUser]]></ToUserName>
<!--发送方帐号(OpenID)-->
<FromUserName><![CDATA[fromUser]]></FromUserName>
<!--消息创建时间 (整型)-->
<CreateTime>12345678</CreateTime>
<!--消息类别 (text文本消息)-->
<MsgType><![CDATA1]></MsgType>
<!--消息内容-->
<Content><![CDATA[content]]></Content>
<!--消息ID (64位整型)-->
<MsgId>1234567890123456</MsgId>
</xml>
|
开发者在处理完消息后需要返回数据给微信服务器:
代码如下 |
复制代码 |
<xml>
<!--接收方帐号(OpenID)-->
<ToUserName><![CDATA[toUser]]></ToUserName>
<!--开发者微信号-->
<FromUserName><![CDATA[fromUser]]></FromUserName>
<!--消息创建时间 (整型)-->
<CreateTime>12345678</CreateTime>
<!--消息类别 (text文本消息)-->
<MsgType><![CDATA1]></MsgType>
<!--回复消息内容-->
<Content><![CDATA[content]]></Content>
<!--星标操作(位0x0001被标志时 星标刚收到的消息)-->
<FuncFlag>0</FuncFlag>
</xml>
|
除文本消息外,微信公众平台还支持用户发送图片消息、地理位置消息、链接消息、事件推送,而开发者还可以向微信公众平台回复音乐消息和图文消息,各类消息XML规范也可以参见官方文档。
来看看官方提供的一个PHP示例,我做了一些精简:
代码如下 |
复制代码 |
<?php
$wechatObj = new wechat();
$wechatObj->responseMsg();
class wechat {
public function responseMsg() {
//---------- 接 收 数 据 ---------- //
$postStr = $GLOBALS["HTTP_RAW_POST_DATA"]; //获取POST数据
//用SimpleXML解析POST过来的XML数据
$postObj = simplexml_load_string($postStr,'SimpleXMLElement',LIBXML_NOCDATA);
$fromUsername = $postObj->FromUserName; //获取发送方帐号(OpenID)
$toUsername = $postObj->ToUserName; //获取接收方账号
$keyword = trim($postObj->Content); //获取消息内容
$time = time(); //获取当前时间戳
//---------- 返 回 数 据 ---------- //
//返回消息模板
$textTpl = "<xml>
<ToUserName><![CDATA[%s]]></ToUserName>
<FromUserName><![CDATA[%s]]></FromUserName>
<CreateTime>%s</CreateTime>
<MsgType><![CDATA[%s]]></MsgType>
<Content><![CDATA[%s]]></Content>
<FuncFlag>0</FuncFlag>
</xml>";
$msgType = "text"; //消息类型
$contentStr = 'http://www.你的域名.com'; //返回消息内容
//格式化消息模板
$resultStr = sprintf($textTpl,$fromUsername,$toUsername,
$time,$msgType,$contentStr);
echo $resultStr; //输出结果
}
}
?>
|
把代码保存为index.php并上传至http://www.你的域名.com/weixin/目录,如果刚才没删除该文件,则直接覆盖。
现在用户通过微信公众平台发送任何消息公众账号均会返回一条内容为“http://www.你的域名.com”的消息。
接下来需要做的就是根据用户消息动态返回结果~
SimSimi(小黄鸡)是目前比较火的聊天机器人,我用CURL开发了一个免费的SimSimi(小黄鸡)接口,传入关键词会返回文本回复,这部分不是本文重点,就不多说明,直接上代码:
代码如下 |
复制代码 |
<?php
$wechatObj = new wechat();
$wechatObj->responseMsg();
class wechat {
public function responseMsg() {
//---------- 接 收 数 据 ---------- //
$postStr = $GLOBALS["HTTP_RAW_POST_DATA"]; //获取POST数据
//用SimpleXML解析POST过来的XML数据
$postObj = simplexml_load_string($postStr,'SimpleXMLElement',LIBXML_NOCDATA);
$fromUsername = $postObj->FromUserName; //获取发送方帐号(OpenID)
$toUsername = $postObj->ToUserName; //获取接收方账号
$keyword = trim($postObj->Content); //获取消息内容
$time = time(); //获取当前时间戳
//---------- 返 回 数 据 ---------- //
//返回消息模板
$textTpl = "<xml>
<ToUserName><![CDATA[%s]]></ToUserName>
<FromUserName><![CDATA[%s]]></FromUserName>
<CreateTime>%s</CreateTime>
<MsgType><![CDATA[%s]]></MsgType>
<Content><![CDATA[%s]]></Content>
<FuncFlag>0</FuncFlag>
</xml>";
$msgType = "text"; //消息类型
$contentStr = 'http://www.你的域名.com'; //返回消息内容
//格式化消息模板
$resultStr = sprintf($textTpl,$fromUsername,$toUsername,
$time,$msgType,$contentStr);
echo $resultStr; //输出结果
}
}
?>
|
把上面两段代码整合在一起就大功告成了,需要说明一点,微信服务器在5秒内收不到响应会断掉连接,通过此接口有可能会超时,且SimSimi已经屏蔽了BAE和SAE上的抓取请求,推荐使用SimSimi官方收费API,速度比较快~
本程序可以实现批量替换目录中所有文件中的内容或用于打量给挂了木马文件批量替换与更新了,希望文章对各位同学有所帮助。
代码如下 |
复制代码 |
<?php
/***************************************************************************
batch-replace, v1.1
***************************************************************************
file: batch-replace_utf8.php
functionality: 本程序可以扫描指定目录的所有文件,进行内容替换。可用于被批量挂马的删除以及批量更新页面某些内容。
本程序适用于对UTF-8的页面进行修改。
/***************************************************************************
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
***************************************************************************/
set_time_limit(3600);
if($_POST['Submit']=='开始执行操作'){
$dir = $_POST['searchpath'];
$shortname = $_POST['shortname'];
$isall = $_POST['isall'];
$isreg = $_POST['isreg'];
if (!get_magic_quotes_gpc()) {
$sstr = $_POST['sstr'];
$rpstr = $_POST['rpstr'];
} else {
$sstr = stripslashes($_POST['sstr']);
$rpstr = stripslashes($_POST['rpstr']);
}
//分析shortname
$arrext = explode ("|",$shortname);
if (!is_dir($dir)) return;
if ($sstr == '') return;
//把末尾的/去掉
if(substr($dir,-1)=='/') $dir = substr($dir,0,strrpos($dir,"/"));
//罗列所有目录
if ($isall == 1){
hx_dirtree($dir);
}else{
hx_dealdir($dir);
}
exit();
}
function hx_dirtree($path="."){
global $sstr,$rpstr,$isreg,$arrext;
$d = dir($path);
while(false !== ($v = $d->read())) {
if($v == "." || $v == "..") continue;
$file = $d->path."/".$v;
if(is_dir($file)) {
echo "<p>$v</p>"; hx_dirtree($file);
}else{
$ext=substr(strrchr($v,"."), 1);
if( in_array($ext , $arrext) ){
echo "<li>$file ";
$body = file_get_contents($file);
if($isreg == 1){
$body2 = preg_replace($sstr, $rpstr, $body);
}else{
$body2 = str_replace($sstr, $rpstr, $body);
}
if($body != $body2 && $body2 != ''){
tofile($file,$body2);
echo ' OK';
}else{
echo ' NO';
}
echo '</li>';
}
}
}
$d->close();
}
function hx_dealdir($dir){
global $sstr,$rpstr,$isreg,$arrext;
if ($dh = opendir($dir)) {
while (false !== ($file = readdir($dh))) {
if(filetype($dir.'/'.$file)=='file'){
$ext=substr(strrchr($file,"."), 1);
if( in_array($ext , $arrext) ){
echo "<li>$file ";
$body = file_get_contents($dir.'/'.$file);
if($isreg == 1){
$body2 = preg_replace($sstr, $rpstr, $body);
}else{
$body2 = str_replace($sstr, $rpstr, $body);
}
if($body != $body2 && $body2 != ''){
tofile($dir.'/'.$file,$body2);
echo ' OK';
}else{
echo ' NO';
}
echo '</li>';
}
}
}
closedir($dh);
}
}
//把生成文件的过程写出函数
function tofile($file_name,$file_content){
if (is_file ($file_name)){
@unlink ($file_name);
}
$handle = fopen ($file_name,"w");
if (!is_writable ($file_name)){
return false;
}
if (!fwrite ($handle,$file_content)){
return false;
}
fclose ($handle); //关闭指针
return $file_name;
}
?><!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>批量替换程序|木马批量删除_www.itlearner.com</title>
<style type="text/css">
body{background:#FFFFFF;color:#000;font-size:12px;}
#top{text-align:center;}
h1,p,form{margin:0;padding:0;}
h1{font-size;14px;}
</style>
</head>
<body>
<div id="top">
<h1>批量替换程序(UTF-8版)</h1>
<div>本程序可以扫描指定目录的所有文件,进行<strong>内容替换</strong>。可用于被批量挂马的删除以及批量更新页面某些内容。<br/>
在文件数量非常多的情况下,本操作比较占用服务器资源,请确脚本超时限制时间允许更改,否则可能无法完成操作。</div>
</div>
<form action="<?=$_SERVER['SCRIPT_NAME']?>" name="form1" target="stafrm" method="post">
<table width="95%" border="0" align="center" cellpadding="3" cellspacing="1" bgcolor="#666666">
<tr>
<td width="10%" bgcolor="#FFFFFF"><strong> 起始根路径:</strong></td>
<td width="90%" bgcolor="#FFFFFF"><input name="searchpath" type="text" id="searchpath" value="./test" size="20" />
点表示当前目录,末尾不要加/ <input type="checkbox" name="isall" value="1" />包含此目录下所有目录</td>
</tr>
<tr>
<td bgcolor="#FFFFFF"><strong> 文件扩展名:</strong></td>
<td bgcolor="#FFFFFF"><input name="shortname" type="text" id="shortname" size="20" value="php|htm" />
多个请用|隔开</td>
</tr>
<tr id="rpct">
<td height="64" colspan="2" bgcolor="#FFFFFF"><table width="100%" border="0" cellspacing="1" cellpadding="1">
<tr bgcolor="#EDFCE2">
<td colspan="4"><strong>内容替换选项:</strong> <input type="checkbox" name="isreg" value="1" />使用正则表达式</td>
</tr>
<tr>
<td colspan="4">替换内容类默认使用字符串替换,也可以使用正则表达式(需勾选)。"替换为"不填写的话,就表示删除"替换内容"。</td>
</tr>
<tr>
<td width="10%"> 替换内容:</td>
<td width="36%"><textarea name="sstr" id="sstr" style="width:90%;height:45px"></textarea></td>
<td width="10%">替 换 为:</td>
<td><textarea name="rpstr" id="rpstr" style="width:90%;height:45px"></textarea></td>
</tr>
</table></td>
</tr>
<tr>
<td colspan="2" height="20" align="center" bgcolor="#E2F5BC"><input type="submit" name="Submit" value="开始执行操作" class="inputbut" /></td>
</tr>
</table>
</form>
<table width="95%" border="0" align="center" cellpadding="3" cellspacing="1" bgcolor="#666666">
<tr bgcolor="#FFFFFF">
<td id="mtd">
<div id='mdv' style='width:100%;height:100;'>
<iframe name="stafrm" frameborder="0" id="stafrm" width="100%" height="100%"></iframe>
</div>
<script type="text/javascript">
document.all.mdv.style.pixelHeight = screen.height - 450;
</script> </td>
</tr>
</table>
</body>
</html>
|
网页截屏以前我们只能在asp.net中实现,下面我来介绍在linux中利用一个插件让php也可以实现网页截屏吧,希望对大家有帮助。
服务器端
为实现截图的程序必须借助服务器端程序:http://code.google.com/p/wkhtmltopdf/
可将网页转换为pdf或者图片,32和64位有区别,找个适合自己服务器的版本。
安装
安装过程十分简单:解压 -> 找个合适的路径放下…
执行
命令行调用1
代码如下 |
复制代码 |
/servers/app/qtwebkit/wkHtmlToImage 111cn.net www.111cn.net.png |
默认的清晰度比较高,图片会很大,生成图片需要一定的时间。
php
代码如下 |
复制代码 |
exec('/servers/app/qtwebkit/wkHtmlToImage 111cn.net www.111cn.net.png');
|
具体的使用方法
代码如下 |
复制代码 |
<?php
ob_start();
//如果将输出的文件名设置为'-',则直接返回文件数据流
passthru('/servers/app/qtwebkit/wkHtmlToImage --width 800 --height 600 -quality 85 weibo.com -');
$fileName = self::cachePath() . '/' . self::name();
$content = ob_get_clean();
//写入图片文件,备用
//file_put_contents($fileName, $content);
//直接输出为图片
header("Content-type: image/png");
echo $content;
?>
|
中文乱码问题
主要看服务器是否支持中文语言,如果截图中出现乱码,直接装个中文包就好了。
代码如下 |
复制代码 |
yum install fonts-chinese
|
标签:[!--infotagslink--]