开源CMS \ discuz \ 【discuz x3】如何将头像和帖内等附件分离到远程服务器?

【discuz x3】如何将头像和帖内等附件分离到远程服务器?

总点击109
简介:一、修改uc_server/control/user.php文件,代码如下: <?php /* [UCenter](C)2001-2099ComsenzInc.

一、修改uc_server/control/user.php文件,代码如下:

<?php

/*

[UCenter] (C)2001-2099 Comsenz Inc.

This is NOT a freeware,use is subject to license terms

$Id: user.php 1059 2011-03-01 07:25:09Z monkey $

*/

!defined('IN_UC') && exit('Access Denied');

define('UC_USER_CHECK_USERNAME_FAILED',-1);

define('UC_USER_USERNAME_BADWORD',-2);

define('UC_USER_USERNAME_EXISTS',-3);

define('UC_USER_EMAIL_FORMAT_ILLEGAL',-4);

define('UC_USER_EMAIL_ACCESS_ILLEGAL',-5);

define('UC_USER_EMAIL_EXISTS',-6);

class usercontrol extends base {

function __construct() {

$this->usercontrol();

}

function usercontrol() {

parent::__construct();

$this->load('user');

}

// -1 未开启

function onsynlogin() {

$this->init_input();

$uid = $this->input('uid');

if($this->app['synlogin']) {

if($this->user = $_ENV['user']->get_user_by_uid($uid)) {

$synstr = '';

foreach($this->cache['apps'] as $appid => $app) {

if($app['synlogin']) {

$synstr .= '<script type="text/javascript" src="'.$app['url'].'/api/'.$app['apifilename'].'?time='.$this->time.'&code='.urlencode($this->authcode('action=synlogin&username='.$this->user['username'].'&uid='.$this->user['uid'].'&password='.$this->user['password']."&time=".$this->time,'ENCODE',$app['authkey'])).'" reload="1"></script>';

if(is_array($app['extra']['extraurl'])) foreach($app['extra']['extraurl'] as $extraurl) {

$synstr .= '<script type="text/javascript" src="'.$extraurl.'/api/'.$app['apifilename'].'?time='.$this->time.'&code='.urlencode($this->authcode('action=synlogin&username='.$this->user['username'].'&uid='.$this->user['uid'].'&password='.$this->user['password']."&time=".$this->time,$app['authkey'])).'" reload="1"></script>';

}

}

}

return $synstr;

}

}

return '';

}

function onsynlogout() {

$this->init_input();

if($this->app['synlogin']) {

$synstr = '';

foreach($this->cache['apps'] as $appid => $app) {

if($app['synlogin']) {

$synstr .= '<script type="text/javascript" src="'.$app['url'].'/api/'.$app['apifilename'].'?time='.$this->time.'&code='.urlencode($this->authcode('action=synlogout&time='.$this->time,$app['authkey'])).'" reload="1"></script>';

if(is_array($app['extra']['extraurl'])) foreach($app['extra']['extraurl'] as $extraurl) {

$synstr .= '<script type="text/javascript" src="'.$extraurl.'/api/'.$app['apifilename'].'?time='.$this->time.'&code='.urlencode($this->authcode('action=synlogout&time='.$this->time,$app['authkey'])).'" reload="1"></script>';

}

}

}

return $synstr;

}

return '';

}

function onregister() {

$this->init_input();

$username = $this->input('username');

$password = $this->input('password');

$email = $this->input('email');

$questionid = $this->input('questionid');

$answer = $this->input('answer');

$regip = $this->input('regip');

if(($status = $this->_check_username($username)) < 0) {

return $status;

}

if(($status = $this->_check_email($email)) < 0) {

return $status;

}

$uid = $_ENV['user']->add_user($username,$password,$email,$questionid,$answer,$regip);

return $uid;

}

function onedit() {

$this->init_input();

$username = $this->input('username');

$oldpw = $this->input('oldpw');

$newpw = $this->input('newpw');

$email = $this->input('email');

$ignoreoldpw = $this->input('ignoreoldpw');

$questionid = $this->input('questionid');

$answer = $this->input('answer');

if(!$ignoreoldpw && $email && ($status = $this->_check_email($email,$username)) < 0) {

return $status;

}

$status = $_ENV['user']->edit_user($username,$oldpw,$newpw,$ignoreoldpw,$answer);

if($newpw && $status > 0) {

$this->load('note');

$_ENV['note']->add('updatepw','username='.urlencode($username).'&password=');

$_ENV['note']->send();

}

return $status;

}

function onlogin() {

$this->init_input();

$isuid = $this->input('isuid');

$username = $this->input('username');

$password = $this->input('password');

$checkques = $this->input('checkques');

$questionid = $this->input('questionid');

$answer = $this->input('answer');

if($isuid == 1) {

$user = $_ENV['user']->get_user_by_uid($username);

} elseif($isuid == 2) {

$user = $_ENV['user']->get_user_by_email($username);

} else {

$user = $_ENV['user']->get_user_by_username($username);

}

$passwordmd5 = preg_match('/^w{32}$/',$password) ? $password : md5($password);

if(empty($user)) {

$status = -1;

} elseif($user['password'] != md5($passwordmd5.$user['salt'])) {

$status = -2;

} elseif($checkques && $user['secques'] != '' && $user['secques'] != $_ENV['user']->quescrypt($questionid,$answer)) {

$status = -3;

} else {

$status = $user['uid'];

}

$merge = $status != -1 && !$isuid && $_ENV['user']->check_mergeuser($username) ? 1 : 0;

return array($status,$user['username'],$user['email'],$merge);

}

function oncheck_email() {

$this->init_input();

$email = $this->input('email');

return $this->_check_email($email);

}

function oncheck_username() {

$this->init_input();

$username = $this->input('username');

if(($status = $this->_check_username($username)) < 0) {

return $status;

} else {

return 1;

}

}

function onget_user() {

$this->init_input();

$username = $this->input('username');

if(!$this->input('isuid')) {

$status = $_ENV['user']->get_user_by_username($username);

} else {

$status = $_ENV['user']->get_user_by_uid($username);

}

if($status) {

return array($status['uid'],$status['username'],$status['email']);

} else {

return 0;

}

}

function ongetprotected() {

$protectedmembers = $this->db->fetch_all("SELECT uid,username FROM ".UC_DBTABLEPRE."protectedmembers GROUP BY username");

return $protectedmembers;

}

function ondelete() {

$this->init_input();

$uid = $this->input('uid');

return $_ENV['user']->delete_user($uid);

}

function ondeleteavatar() {

$this->init_input();

$uid = $this->input('uid');

$_ENV['user']->delete_useravatar($uid);

}

function onaddprotected() {

$this->init_input();

$username = $this->input('username');

$admin = $this->input('admin');

$appid = $this->app['appid'];

$usernames = (array)$username;

foreach($usernames as $username) {

$user = $_ENV['user']->get_user_by_username($username);

$uid = $user['uid'];

$this->db->query("REPLACE INTO ".UC_DBTABLEPRE."protectedmembers SET uid='$uid',username='$username',appid='$appid',dateline='{$this->time}',admin='$admin'",'SILENT');

}

return $this->db->errno() ? -1 : 1;

}

function ondeleteprotected() {

$this->init_input();

$username = $this->input('username');

$appid = $this->app['appid'];

$usernames = (array)$username;

foreach($usernames as $username) {

$this->db->query("DELETE FROM ".UC_DBTABLEPRE."protectedmembers WHERE username='$username' AND appid='$appid'");

}

return $this->db->errno() ? -1 : 1;

}

function onmerge() {

$this->init_input();

$oldusername = $this->input('oldusername');

$newusername = $this->input('newusername');

$uid = $this->input('uid');

$password = $this->input('password');

$email = $this->input('email');

if(($status = $this->_check_username($newusername)) < 0) {

return $status;

}

$uid = $_ENV['user']->add_user($newusername,$uid);

$this->db->query("DELETE FROM ".UC_DBTABLEPRE."mergemembers WHERE appid='".$this->app['appid']."' AND username='$oldusername'");

return $uid;

}

function onmerge_remove() {

$this->init_input();

$username = $this->input('username');

$this->db->query("DELETE FROM ".UC_DBTABLEPRE."mergemembers WHERE appid='".$this->app['appid']."' AND username='$username'");

return NULL;

}

function _check_username($username) {

$username = addslashes(trim(stripslashes($username)));

if(!$_ENV['user']->check_username($username)) {

return UC_USER_CHECK_USERNAME_FAILED;

} elseif(!$_ENV['user']->check_usernamecensor($username)) {

return UC_USER_USERNAME_BADWORD;

} elseif($_ENV['user']->check_usernameexists($username)) {

return UC_USER_USERNAME_EXISTS;

}

return 1;

}

function _check_email($email,$username = '') {

if(!$_ENV['user']->check_emailformat($email)) {

return UC_USER_EMAIL_FORMAT_ILLEGAL;

} elseif(!$_ENV['user']->check_emailaccess($email)) {

return UC_USER_EMAIL_ACCESS_ILLEGAL;

} elseif(!$this->settings['doublee'] && $_ENV['user']->check_emailexists($email,$username)) {

return UC_USER_EMAIL_EXISTS;

} else {

return 1;

}

}

function ongetcredit($arr) {

$this->init_input();

$appid = $this->input('appid');

$uid = $this->input('uid');

$credit = $this->input('credit');

$this->load('note');

$this->load('misc');

$app = $this->cache['apps'][$appid];

$apifilename = isset($app['apifilename']) && $app['apifilename'] ? $app['apifilename'] : 'uc.php';

if($app['extra']['apppath'] && @include $app['extra']['apppath'].'./api/'.$apifilename) {

$uc_note = new uc_note();

return $uc_note->getcredit(array('uid' => $uid,'credit' => $credit),'');

} else {

$url = $_ENV['note']->get_url_code('getcredit',"uid=$uid&credit=$credit",$appid);

return $_ENV['misc']->dfopen($url,'',1,$app['ip'],UC_NOTE_TIMEOUT);

}

}

//返回的内容为保存该文件的临时位置,camera.swf会通过返回的网址来读取图片

function onuploadavatar() {

@header("Expires: 0");

@header("Cache-Control: private,post-check=0,pre-check=0,max-age=0",FALSE);

@header("Pragma: no-cache");

//header("Content-type: application/xml; charset=utf-8");

$this->init_input(getgpc('agent','G'));

$uid = $this->input('uid');

if(empty($uid)) {

return -1;

}

if(empty($_FILES['Filedata'])) {

return -3;

}

list($width,$height,$type,$attr) = getimagesize($_FILES['Filedata']['tmp_name']);

if(!in_array($type,array(1,2,3,6))) {

@unlink($_FILES['Filedata']['tmp_name']);

return -4;

}

$imgtype = array(1 => '.gif',2 => '.jpg',3 => '.png');

$filetype = $imgtype[$type];

if(!$filetype) $filetype = '.jpg';

//头像临时存放路径

$tmpavatar = UC_DATADIR.'./tmp/upload'.$uid.$filetype;

file_exists($tmpavatar) && @unlink($tmpavatar);

if(@copy($_FILES['Filedata']['tmp_name'],$tmpavatar) || @move_uploaded_file($_FILES['Filedata']['tmp_name'],$tmpavatar)) {

@unlink($_FILES['Filedata']['tmp_name']);

list($width,$attr) = getimagesize($tmpavatar);

if($width < 10 || $height < 10 || $type == 4) {

@unlink($tmpavatar);

return -2;

}

} else {

@unlink($_FILES['Filedata']['tmp_name']);

return -4;

}

$avatarurl = UC_DATAURL.'/tmp/upload'.$uid.$filetype;

//返回临时头像的url路径

return $avatarurl;

}

function onrectavatar() {

@header("Expires: 0");

@header("Cache-Control: private,FALSE);

@header("Pragma: no-cache");

header("Content-type: application/xml; charset=utf-8");

$this->init_input(getgpc('agent'));

$uid = $this->input('uid');

if(empty($uid)) {

return '<root><message type="error" value="-1" /></root>';

}

$home = $this->get_home($uid);//返回头像的三个目录:"00/00/12","/avatar/"."00/00/12"."/45_small.jpg"

if(!is_dir(UC_DATADIR.'./avatar/'.$home)) {

$this->set_home($uid,UC_DATADIR.'./avatar/');//如果没有的话,则创建目录

}

$avatartype = getgpc('avatartype','G') == 'real' ? 'real' : 'virtual';

//UC_DATADIR:d:/wamp/www/discuz3/uc_server/data/

//获取大中小头像的全路径

$bigavatarfile = UC_DATADIR.'./avatar/'.$this->get_avatar($uid,'big',$avatartype);

$middleavatarfile = UC_DATADIR.'./avatar/'.$this->get_avatar($uid,'middle',$avatartype);

$smallavatarfile = UC_DATADIR.'./avatar/'.$this->get_avatar($uid,'small',$avatartype);

//getgpc:获取 $_GET、$_POST、$_COOKIE中数据

$bigavatar = $this->flashdata_decode(getgpc('avatar1','P'));//$_POST

$middleavatar = $this->flashdata_decode(getgpc('avatar2','P'));

$smallavatar = $this->flashdata_decode(getgpc('avatar3','P'));

if(!$bigavatar || !$middleavatar || !$smallavatar) {

return '<root><message type="error" value="-2" /></root>';

}

$success = 1;

//写入二进制数据到图片文件,$bigavatar:二进制数据内容

$fp = @fopen($bigavatarfile,'wb');

@fwrite($fp,$bigavatar);

@fclose($fp);

$fp = @fopen($middleavatarfile,$middleavatar);

@fclose($fp);

$fp = @fopen($smallavatarfile,$smallavatar);//将二进制头像数据信息写入头像文件

@fclose($fp);

/******************************************************************/

$ftps=new Ftp();//实例化一个ftp对象,下面有这个类的定义 //上传头像成功的同时将头像同步到远程服务器

$ftps->connect("127.0.0.1","ftp的用户名","ftp的密码","ftp的端口",true,false);//true-开启了被动模式 false-没有使用ssl连接

$ftps->put("/domains/goodbaobao.taobao.com/public_html/data/avatar/".$this->get_avatar($uid,$avatartype),$bigavatarfile);

$ftps->put("/domains/goodbaobao.taobao.com/public_html/data/avatar/".$this->get_avatar($uid,$middleavatarfile);

$ftps->put("/domains/goodbaobao.taobao.com/public_html/data/avatar/".$this->get_avatar($uid,$smallavatarfile);

$ftps->close();

/******************************************************************/

$biginfo = @getimagesize($bigavatarfile);

$middleinfo = @getimagesize($middleavatarfile);

$smallinfo = @getimagesize($smallavatarfile);

if(!$biginfo || !$middleinfo || !$smallinfo || $biginfo[2] == 4 || $middleinfo[2] == 4 || $smallinfo[2] == 4) {

file_exists($bigavatarfile) && unlink($bigavatarfile);

file_exists($middleavatarfile) && unlink($middleavatarfile);

file_exists($smallavatarfile) && unlink($smallavatarfile);

$success = 0;

}

$filetype = '.jpg';

@unlink(UC_DATADIR.'./tmp/upload'.$uid.$filetype);

if($success) {

return '<?xml version="1.0" ?><root><face success="1"/></root>';

} else {

return '<?xml version="1.0" ?><root><face success="0"/></root>';

}

}

function flashdata_decode($s) {

$r = '';

$l = strlen($s);

for($i=0; $i<$l; $i=$i+2) {

$k1 = ord($s[$i]) - 48;

$k1 -= $k1 > 9 ? 7 : 0;

$k2 = ord($s[$i+1]) - 48;

$k2 -= $k2 > 9 ? 7 : 0;

$r .= chr($k1 << 4 | $k2);

}

return $r;

}

}

//ftp类:头像上传成功的同时将头像同步上传到远程服务器

class Ftp {

//FTP 连接资源

private $link;

//FTP连接时间

public $link_time;

//错误代码

private $err_code = 0;

//传送模式{文本模式:FTP_ASCII,二进制模式:FTP_BINARY}

public $mode = FTP_BINARY;

/**

* 连接FTP服务器

* @param string $host 服务器地址

* @param string $username用户名

* @param string $password密码

* @param integer $port 服务器端口,默认值为21

* @param boolean $pasv 是否开启被动模式

* @param boolean $ssl 是否使用SSL连接

* @param integer $timeout 超时时间

*/

public function connect($host,$username = '',$password = '',$port = '21',$pasv = false,$ssl = false,$timeout = 30) {

$start = time();

if ($ssl) {

if (!$this->link = @ftp_ssl_connect($host,$port,$timeout)) {

$this->err_code = 1;

return false;

}

} else {

if (!$this->link = @ftp_connect($host,$timeout)) {

$this->err_code = 1;

return false;

}

}

if (@ftp_login($this->link,$username,$password)) {

if ($pasv)

ftp_pasv($this->link,true);

$this->link_time = time() - $start;

return true;

} else {

$this->err_code = 1;

return false;

}

register_shutdown_function(array(&$this,'close'));

}

/**

* 创建文件夹

* @param string $dirname 目录名,

*/

public function mkdir($dirname) {

if (!$this->link) {

$this->err_code = 2;

return false;

}

$dirname = $this->ck_dirname($dirname);

$nowdir = '/';

foreach ($dirname as $v) {

if ($v && !$this->chdir($nowdir . $v)) {

if ($nowdir)

$this->chdir($nowdir);

@ftp_mkdir($this->link,$v);

}

if ($v)

$nowdir .= $v . '/';

}

return true;

}

/**

* 上传文件

* @param string $remote 远程存放地址

* @param string $local 本地存放地址

*/

public function put($remote,$local) {

if (!$this->link) {

$this->err_code = 2;

return false;

}

$dirname = pathinfo($remote,PATHINFO_DIRNAME);

if (!$this->chdir($dirname)) {

$this->mkdir($dirname);

}

if (@ftp_put($this->link,$remote,$local,$this->mode)) {

return true;

} else {

$this->err_code = 7;

return false;

}

}

/**

* 删除文件夹

* @param string $dirname 目录地址

* @param boolean $enforce 强制删除

*/

public function rmdir($dirname,$enforce = false) {

if (!$this->link) {

$this->err_code = 2;

return false;

}

$list = $this->nlist($dirname);

if ($list && $enforce) {

$this->chdir($dirname);

foreach ($list as $v) {

$this->f_delete($v);

}

} elseif ($list && !$enforce) {

$this->err_code = 3;

return false;

}

@ftp_rmdir($this->link,$dirname);

return true;

}

/**

* 删除指定文件

* @param string $filename 文件名

*/

public function f_delete($filename) {

if (!$this->link) {

$this->err_code = 2;

return false;

}

if (@ftp_delete($this->link,$filename)) {

return true;

} else {

$this->err_code = 4;

return false;

}

}

/**

* 返回给定目录的文件列表

* @param string $dirname 目录地址

* @return array 文件列表数据

*/

public function nlist($dirname) {

if (!$this->link) {

$this->err_code = 2;

return false;

}

if ($list = @ftp_nlist($this->link,$dirname)) {

return $list;

} else {

$this->err_code = 5;

return false;

}

}

/**

* 在 FTP 服务器上改变当前目录

* @param string $dirname 修改服务器上当前目录

*/

public function chdir($dirname) {

if (!$this->link) {

$this->err_code = 2;

return false;

}

if (@ftp_chdir($this->link,$dirname)) {

return true;

} else {

$this->err_code = 6;

return false;

}

}

/**

* 获取错误信息

*/

public function get_error() {

if (!$this->err_code)

return false;

$err_msg = array(

'1' => 'Server can not connect',

'2' => 'Not connect to server',

'3' => 'Can not delete non-empty folder',

'4' => 'Can not delete file',

'5' => 'Can not get file list',

'6' => 'Can not change the current directory on the server',

'7' => 'Can not upload files'

);

return $err_msg[$this->err_code];

}

/**

* 检测目录名

* @param string $url 目录

* @return 由 / 分开的返回数组

*/

private function ck_dirname($url) {

$url = str_replace('','/',$url);

$urls = explode('/',$url);

return $urls;

}

/**

* 关闭FTP连接

*/

public function close() {

return @ftp_close($this->link);

}

}

?>


二、uc_server/avatar.php文件代码如下:

<?php

/*

[UCenter] (C)2001-2099 Comsenz Inc.

This is NOT a freeware,use is subject to license terms

$Id: avatar.php 1059 2011-03-01 07:25:09Z monkey $

*/

error_reporting(0);

define('UC_API',strtolower(($_SERVER['HTTPS'] == 'on' ? 'https' : 'http').'://'.$_SERVER['HTTP_HOST'].substr($_SERVER['PHP_SELF'],strrpos($_SERVER['PHP_SELF'],'/'))));

$uid = isset($_GET['uid']) ? $_GET['uid'] : 0;

$size = isset($_GET['size']) ? $_GET['size'] : '';

$random = isset($_GET['random']) ? $_GET['random'] : '';

$type = isset($_GET['type']) ? $_GET['type'] : '';

$check = isset($_GET['check_file_exists']) ? $_GET['check_file_exists'] : '';

$avatar = './data/avatar/'.get_avatar($uid,$size,$type);

if(my_file_exists('http://www.jiaoyuonline.com'.$avatar)) {//weiyanhui添加了一层dirname

if($check) {

echo 1;

exit;

}

$random = !empty($random) ? rand(1000,9999) : '';

$avatar_url = empty($random) ? $avatar : $avatar.'?random='.$random;

} else {

if($check) {

echo 0;

exit;

}

$size = in_array($size,array('big','small')) ? $size : 'middle';

$avatar_url = 'images/noavatar_'.$size.'.gif';

}

if(empty($random)) {

header("HTTP/1.1 301 Moved Permanently");

header("Last-Modified:".date('r'));

header("Expires: ".date('r',time() + 86400));

}

header('Location: '.'http://www.aaaa.com/'.$avatar_url);//返回的远程服务器上的头像信息

exit;

function get_avatar($uid,$size = 'middle',$type = '') {

$size = in_array($size,'small')) ? $size : 'middle';

$uid = abs(intval($uid));

$uid = sprintf("%09d",$uid);

$dir1 = substr($uid,3);

$dir2 = substr($uid,2);

$dir3 = substr($uid,5,2);

$typeadd = $type == 'real' ? '_real' : '';

return $dir1.'/'.$dir2.'/'.$dir3.'/'.substr($uid,-2).$typeadd."_avatar_$size.jpg";

}

function my_file_exists($file)

{

if(preg_match('/^http:///',$file)){

//远程文件

if(ini_get('allow_url_fopen')){

if(@fopen($file,'r')) return true;

}

else{

$parseurl=parse_url($file);

$host=$parseurl['host'];

$path=$parseurl['path'];

$fp=fsockopen($host,80,$errno,$errstr,10);

if(!$fp)return false;

fputs($fp,"GET {$path} HTTP/1.1 rnhost:{$host}rnrn");

if(preg_match('/HTTP/1.1 200/',fgets($fp,1024))) return true;

}

return false;

}

return file_exists($file);

}

?>


三、后台设置远程附件:

【discuz x3】如何将头像和帖内等附件分离到远程服务器?

四、sql修改:

update pre_forum_attachment_0 set remote = '1';

update pre_forum_attachment_1 set remote = '1';

update pre_forum_attachment_2 set remote = '1';

update pre_forum_attachment_3 set remote = '1';

update pre_forum_attachment_4 set remote = '1';

update pre_forum_attachment_5 set remote = '1';

update pre_forum_attachment_6 set remote = '1';

update pre_forum_attachment_7 set remote = '1';

update pre_forum_attachment_8 set remote = '1';

update pre_forum_attachment_9 set remote = '1';

update pre_portal_article_title set remote=1;

update pre_portal_attachment set remote=1;

update pre_portal_topic_pic set remote=1;

update pre_home_pic set remote=remote+1;


五、效果如下:


【discuz x3】如何将头像和帖内等附件分离到远程服务器?

意见反馈 常见问题 官方微信 返回顶部