rray('fid' => $fid), array('rank' => 1), $page, $pagesize);
$arr = array_reverse($arr, TRUE);
$desc = FALSE;
}
}
$desc and $arr = thread_tid__find(array('fid' => $fid), array('rank' => -1), $page, $pagesize);
if (empty($arr)) return NULL;
return $arr;
}
// 查询用户uid下tid 主题数据详情
function well_thread_find_by_uid($uid, $page = 1, $pagesize = 20)
{
$key = 'well_thread_find_by_uid_' . $uid . '_' . $page . '_' . $pagesize;
static $cache = array();
if (isset($cache[$key])) return $cache[$key];
$arr = thread_tid_find_by_uid($uid, $page, $pagesize);
if (!$arr) return NULL;
$tidarr = arrlist_values($arr, 'tid');
$threadlist = well_thread_find($tidarr, $pagesize);
return $threadlist;
}
// tidarr 查询主题数据
// 主题状态0:通过 1~9审核:1待审核 10~19:10退稿 11逻辑删除
function well_thread_find($tidarr, $pagesize = 20, $desc = TRUE)
{
$orderby = TRUE == $desc ? -1 : 1;
$threadlist = well_thread__find(array('tid' => $tidarr), array('tid' => $orderby), 1, $pagesize);
if (!$threadlist) return NULL;
$i = 0;
foreach ($threadlist as &$thread) {
++$i;
$thread['i'] = $i;
well_thread_format($thread);
}
return $threadlist;
}
// tidarr 查询主题数据 不给mysql增加压力使用正序 倒叙可以使用array_reverse($threadlist, TRUE);
// 主题状态0:通过 1~9审核:1待审核 10~19:10退稿 11逻辑删除
function well_thread_find_asc($tidarr, $pagesize = 20)
{
$threadlist = well_thread__find(array('tid' => $tidarr), array('tid' => 1), 1, $pagesize);
if (!$threadlist) return NULL;
$i = 0;
foreach ($threadlist as $_tid => &$thread) {
++$i;
$thread['i'] = $i;
well_thread_format($thread);
}
return $threadlist;
}
function well_thread_find_by_tids($tidarr)
{
$threadlist = well_thread_find($tidarr, 1000);
return $threadlist;
}
// views + 1 大站可以单独剥离出来
function well_thread_inc_views($tid, $n = 1)
{
global $conf, $db;
$tablepre = $db->tablepre;
//if (!$conf['update_views_on']) return TRUE;
$sqladd = in_array($conf['cache']['type'], array('mysql', 'pdo_mysql')) ? ' LOW_PRIORITY' : '';
$r = db_exec("UPDATE$sqladd `{$tablepre}website_thread` SET views=views+$n WHERE tid='$tid'");
'mysql' != $conf['cache']['type'] and cache_update('website_thread_' . $tid, array('views+' => $n), 1800);
return $r;
}
function well_thread_read($tid)
{
if (empty($tid)) return NULL;
static $cache = array();
if (isset($cache[$tid])) return $cache[$tid];
$cache[$tid] = well_thread__read(array('tid' => $tid));
$cache[$tid] and well_thread_format($cache[$tid]);
return $cache[$tid];
}
// 只删除主题和缓存
function well_thread_delete($tid)
{
global $conf;
if (empty($tid)) return FALSE;
$r = well_thread__delete($tid);
if (FALSE === $r) return FALSE;
if ('mysql' != $conf['cache']['type']) {
if (is_array($tid)) {
foreach ($tid as $_tid) cache_delete('website_thread_' . $_tid);
} else {
cache_delete('website_thread_' . $tid);
runtime_set('articles-', 1);
}
}
return $r;
}
// 删除已经发布成功的主题 单独删除传tid 批量删除传tids array(1,2,3)
function well_thread_delete_all($tid)
{
global $gid, $uid, $time, $conf, $config, $forumlist;
if (empty($tid)) return FALSE;
set_time_limit(0);
$n = is_array($tid) ? count($tid) : 1;
$threadlist = well_thread__find(array('tid' => $tid), array('tid' => 1), 1, $n, 'tid');
if (empty($threadlist)) return FALSE;
$attach_dir_save_rule = array_value($conf, 'attach_dir_save_rule', 'Ym');
// 需要删除的tid
$tids = array();
$tagids = array();
$tagarr = array();
// 统计主题作者和数量 array('作者' => '内容数量')
$uidarr = array();
// 统计版块主题数量 array('版块' => '内容数量')
$fidarr = array();
// 统计版块置顶主题数量 array('版块' => '置顶数量')
$fidstickys = array();
// 统计置顶主题 array('tid')
$sticky_tids = array();
// 有附件的主题
$attach_tids = array();
// 有评论的主题
$post_tids = array();
// 统计主题属性
$flag_tids = array();
$attachs = 0; // 统计附件数量图片和其他文件
$posts = 0; // 统计评论数量
$index_stickys = 0; // 统计全局置顶数量
$flags = 0; // 统计属性数量
$operate_create = array();
$tagtids = array();
foreach ($threadlist as $thread) {
if (!$thread['fid']) continue;
if ($uid != $thread['uid'] && !forum_access_mod($thread['fid'], $gid, 'allowdelete')) continue;
$forum = array_value($forumlist, $thread['fid']);
switch ($forum['model']) {
/*case '0': // 删除文章
break;*/
}
// 删除主图
if ($thread['icon']) {
$day = date($attach_dir_save_rule, $thread['icon']);
$file = $conf['upload_path'] . 'thumbnail/' . $day . '/' . $thread['uid'] . '_' . $thread['tid'] . '_' . $thread['icon'] . '.jpeg';
is_file($file) and unlink($file);
}
$tids[] = $thread['tid'];
if ($thread['tag']) {
$tagtids[] = $thread['tid'];
$_tagarr = xn_json_decode($thread['tag']);
foreach ($_tagarr as $_tagid => $tagname) {
isset($tagarr[$_tagid]) ? $tagarr[$_tagid] += 1 : $tagarr[$_tagid] = 1;
}
}
if ($thread['images'] || $thread['files']) {
$attach_tids[] = $thread['tid'];
$attachs += $thread['images'] += $thread['files'];
}
if ($thread['posts']) {
$post_tids[] = $thread['tid'];
$posts += $thread['posts'];
}
if ($thread['sticky']) {
$sticky_tids[] = $thread['tid'];
if (3 == $thread['sticky']) {
$index_stickys += 1;
} else {
isset($fidstickys[$thread['fid']]) ? $fidstickys[$thread['fid']] += 1 : $fidstickys[$thread['fid']] = 1;
}
}
if ($thread['flags']) {
$flags += $thread['flags'];
$flag_tids[] = $thread['tid'];
}
isset($fidarr[$thread['fid']]) ? $fidarr[$thread['fid']] += 1 : $fidarr[$thread['fid']] = 1;
isset($uidarr[$thread['uid']]) ? $uidarr[$thread['uid']] += 1 : $uidarr[$thread['uid']] = 1;
// 删除日志
$operate_create[] = array('type' => 1, 'uid' => $uid, 'tid' => $thread['tid'], 'subject' => $thread['subject'], 'create_date' => $time);
flag_thread_delete_by_tid($thread['tid']);
cache_delete('website_thread_' . $thread['tid']);
}
// 删除标签主题表
if (!empty($tagtids)) {
$arlist = well_tag_thread_find_by_tid($tagtids, 1, count($tagtids) * 10);
if ($arlist) {
$ids = array();
foreach ($arlist as $val) $ids[] = $val['id'];
well_tag_thread_delete($ids);
}
}
// 更新tag统计
if (!empty($tagids)) {
$tagids = array_unique($tagids);
$update = array();
foreach ($tagarr as $tagid => $n) {
$update[$tagid] = array('count-' => $n);
}
tag_big_update(array('tagid' => $tagids), $update);
}
// 清理附件
if (!empty($attach_tids)) {
well_attach_delete_by_tids($attach_tids, $attachs);
}
// 删除评论
if (!empty($post_tids)) {
comment_delete_by_tids($post_tids, $posts);
}
if (!empty($sticky_tids)) {
cache_delete('sticky_thread_list');
sticky_thread__delete($sticky_tids);
}
if ($index_stickys) {
$config['index_stickys'] -= $index_stickys;
setting_set('conf', $config);
}
if (!empty($flag_tids)) {
flag_thread_delete_by_tids($flag_tids, $flags);
}
if ($tids) {
// 删除主题
well_thread__delete($tids);
// 删除内容
data__delete($tids);
// 删除主题附表
thread_tid_delete($tids);
runtime_set('articles-', count($tids));
}
// 更新版块统计主题数 置顶数
if (!empty($fidarr)) {
$fids = array();
$update = array();
foreach ($fidarr as $_fid => $n) {
$fids[] = $_fid;
$update[$_fid] = array('threads-' => $n);
isset($fidstickys[$_fid]) ? $update[$_fid]['tops-'] = $fidstickys[$_fid] : $update[$_fid]['tops-'] = 0;
}
forum_big_update(array('fid' => $fids), $update);
}
// 减少用户主题数
if (!empty($uidarr)) {
$uids = array();
$update = array();
foreach ($uidarr as $_uid => $n) {
$uids[] = $_uid;
$update[$_uid] = array('articles-' => $n);
'mysql' != $conf['cache']['type'] and cache_delete('user-' . $_uid);
}
user_big_update(array('uid' => $uids), $update);
}
!empty($operate_create) && function_exists('operate_big_insert') and operate_big_insert($operate_create);
return TRUE;
}
// 大数据量容易超时 删除用户时使用,删除主题 回复 栏目统计 附件 全站统计
function well_thread_delete_all_by_uid($uid)
{
// 用户主题数
$user = user_read_cache($uid);
set_time_limit(0);
// 删除所有回复
if ($user['comments']) {
$postist = comment_pid_find_by_uid($uid, 1, $user['comments'], FALSE);
$pidarr = array();
foreach ($postist as $val) {
$pidarr[] = $val['pid'];
}
unset($postist);
!empty($pidarr) and comment_delete_by_pids($pidarr);
}
if ($user['articles']) {
// 如果主题、附件和回复数量太大会超时
$tidlist = thread_tid_find_by_uid($uid, 1, $user['articles'], FALSE, 'tid', array('tid'));
$tidarr = array();
foreach ($tidlist as $val) {
$tidarr[] = $val['tid'];
}
unset($tidlist);
!empty($tidarr) and well_thread_delete_all($tidarr);
}
return TRUE;
}
// 搜索标题
function well_thread_find_by_keyword($keyword, $d = NULL)
{
if (empty($keyword)) return NULL;
$db = $_SERVER['db'];
$d = $d ? $d : $db;
if (!$d) return FALSE;
$threadlist = db_sql_find("SELECT * FROM `{$d->tablepre}website_thread` WHERE subject LIKE '%$keyword%' LIMIT 60;", 'tid', $d);
if ($threadlist) {
$threadlist = arrlist_multisort($threadlist, 'tid', FALSE);
foreach ($threadlist as &$thread) {
well_thread_format($thread);
// 关键词标色
//$thread['subject'] = comment_highlight_keyword($thread['subject'], $keyword);
}
}
return $threadlist;
}
// 查找 最后评论 lastpid
function well_thread_find_lastpid($tid)
{
$arr = comment_pid_read(array('tid' => $tid), array('pid' => -1), array('pid'));
$lastpid = empty($arr) ? 0 : $arr['pid'];
return $lastpid;
}
// 更新最后的 uid
function well_thread_update_last($tid)
{
if (empty($tid)) return FALSE;
$lastpid = well_thread_find_lastpid($tid);
if (empty($lastpid)) return FALSE;
$lastpost = comment_read($lastpid);
if (empty($lastpost)) return FALSE;
$r = well_thread_update($tid, array('lastuid' => $lastpost['uid']));
return $r;
}
function well_thread_maxid()
{
$n = db_maxid('website_thread', 'tid');
return $n;
}
// 主题状态 0:通过 1~9 审核:1待审核 10~19:10退稿 11逻辑删除
function well_thread_format(&$thread)
{
global $gid, $uid, $forumlist;
$conf = _SERVER('conf');
if (empty($thread)) return;
$thread['create_date_fmt'] = humandate($thread['create_date']);
$thread['last_date_fmt'] = humandate($thread['last_date']);
$thread['create_date_fmt_ymd'] = date('Y-m-d', $thread['create_date']);
$thread['last_date_fmt_ymd'] = date('Y-m-d', $thread['last_date']);
$user = user_read_cache($thread['uid']);
$onlinelist = online_user_list_cache();
$user['online_status'] = isset($onlinelist[$user['uid']]) ? 1 : 0;
$thread['username'] = $user['username'];
$thread['user_avatar_url'] = array_value($user, 'avatar_url');
$thread['user'] = user_safe_info($user);
unset($user);
$forum = array_value($forumlist, $thread['fid']);
$thread['forum_name'] = array_value($forum, 'name');
$thread['forum_url'] = array_value($forum, 'url');
if ($thread['last_date'] == $thread['create_date']) {
$thread['last_date_fmt'] = '';
$thread['lastuid'] = 0;
$thread['lastusername'] = '';
} else {
$lastuser = $thread['lastuid'] ? user_read_cache($thread['lastuid']) : array();
$thread['lastusername'] = $thread['lastuid'] ? $lastuser['username'] : lang('guest');
$thread['lastuser'] = $thread['lastuid'] ? user_safe_info($lastuser) : array();
unset($lastuser);
}
$thread['url'] = url('read-' . $thread['tid'], '', FALSE);
$thread['user_url'] = url('user-' . $thread['uid']);
$thread['sticky_class'] = '';
if ($thread['sticky'] > 0) {
if (1 == $thread['sticky']) {
$thread['sticky_class'] = 'success';
} elseif (2 == $thread['sticky']) {
$thread['sticky_class'] = 'warning';
} elseif (3 == $thread['sticky']) {
$thread['sticky_class'] = 'danger';
}
}
$nopic = view_path() . 'img/nopic.png';
if ($thread['icon']) {
$attach_dir_save_rule = array_value($conf, 'attach_dir_save_rule', 'Ym');
$day = date($attach_dir_save_rule, $thread['icon']);
$thread_format_icon_default = 1;
if (1 == $thread_format_icon_default) {
// 本地文件绝对路径
$destfile = $conf['upload_path'] . 'thumbnail/' . $day . '/' . $thread['uid'] . '_' . $thread['tid'] . '_' . $thread['icon'] . '.jpeg';
// 本地
$thread['icon_fmt'] = is_file($destfile) ? file_path($thread['attach_on']) . 'thumbnail/' . $day . '/' . $thread['uid'] . '_' . $thread['tid'] . '_' . $thread['icon'] . '.jpeg' : $nopic;
if (1 == $conf['attach_on'] && 1 == $thread['attach_on']) {
// 云储存
$thread['icon_fmt'] = file_path($thread['attach_on']) . 'thumbnail/' . $day . '/' . $thread['uid'] . '_' . $thread['tid'] . '_' . $thread['icon'] . '.jpeg';
} elseif (2 == $conf['attach_on'] && 2 == $thread['attach_on']) {
// 图床 未上传成功 本地图片在的话使用本地,不在则默认
$thread['icon_fmt'] = $thread['image_url'] ? $thread['image_url'] : $thread['icon_fmt'];
}
}
} else {
$thread['icon_fmt'] = $nopic;
}
// 回复页面
$thread['pages'] = ceil($thread['posts'] / $conf['comment_pagesize']);
$thread['tag_fmt'] = $thread['tag'] ? xn_json_decode($thread['tag']) : '';
// 权限判断
$thread['allowupdate'] = ($uid == $thread['uid']) || forum_access_mod($thread['fid'], $gid, 'allowupdate');
$thread['allowdelete'] = (group_access($gid, 'allowuserdelete') and $uid == $thread['uid']) || forum_access_mod($thread['fid'], $gid, 'allowdelete');
$thread['allowtop'] = forum_access_mod($thread['fid'], $gid, 'allowtop');
$thread = well_thread_safe_info($thread);
}
function well_thread_format_last_date(&$thread)
{
if ($thread['last_date'] != $thread['create_date']) {
$thread['last_date_fmt'] = humandate($thread['last_date']);
} else {
$thread['create_date_fmt'] = humandate($thread['create_date']);
}
}
// 对 $threadlist 权限过滤
function well_thread_list_access_filter(&$threadlist, $gid)
{
global $forumlist;
if (empty($threadlist)) return NULL;
foreach ($threadlist as $tid => $thread) {
if (empty($forumlist[$thread['fid']]['accesson'])) continue;
if ($thread['sticky'] > 0) continue;
if (!forum_access_user($thread['fid'], $gid, 'allowread')) {
unset($threadlist[$tid]);
}
}
}
function well_thread_safe_info($thread)
{
unset($thread['userip'], $thread['user']['threads'], $thread['user']['posts'], $thread['user']['credits'], $thread['user']['golds'], $thread['user']['money']);
empty($thread['user']) || $thread['user'] = user_safe_info($thread['user']);
return $thread;
}
// 过滤安全数据
function well_thread_filter(&$val)
{
unset($val['userip'], $val['fid'], $val['flagid'], $val['type'], $val['user'], $val['create_date']);
}
//------------------------ 其他方法 ------------------------
// 集合主题tid,统一拉取,避免多次查询thread表
function thread_unified_pull($arr)
{
global $gid, $fid;
$stickylist = array_value($arr, 'stickylist', array());
$tidlist = array_value($arr, 'tidlist', array());
//$fid = array_value($arr, 'fid');
// 合并过滤空数组
//$tidlist = array_filter($stickylist + $tidlist);
$tidarrlist = $tidlist = $stickylist + $tidlist;
// 版块自定义
list($flaglist, $flagtids) = flag_thread_by_fid($fid);
empty($flagtids) || $tidarrlist += $flagtids;
unset($flagtids);
// 在这之前合并所有二维数组 tid值为键/array('tid值' => tid值)
$tidarr = empty($tidarrlist) ? array() : arrlist_values($tidarrlist, 'tid');
// 在这之前使用array_merge()前合并所有一维数组 tid/array(1,2,3)
if (empty($tidarr)) return NULL;
$tidarr = array_unique($tidarr);
// 主题相关统一遍历后再归类
$arrlist = well_thread_find($tidarr, count($tidarr));
// 过滤没有权限访问的主题 / filter no permission thread
well_thread_list_access_filter($arrlist, $gid);
$threadlist = array();
foreach ($arrlist as $_tid => &$_thread) {
$_thread = well_thread_safe_info($_thread);
// 归类列表数据
isset($tidlist[$_thread['tid']]) and $threadlist[$_tid] = $_thread;
// flag thread
if (!empty($flaglist)) {
foreach ($flaglist as $key => $val) {
if (isset($val['tids']) && in_array($_thread['tid'], $val['tids'])) {
$flaglist[$key]['list'][array_search($_thread['tid'], $val['tids'])] = $_thread;
ksort($flaglist[$key]['list']);
}
}
}
}
// 按之前tidlist排序
$threadlist = array2_sort_key($threadlist, $tidlist, 'tid');
unset($arrlist, $tidlist);
$arr = array('threadlist' => $threadlist, 'flaglist' => $flaglist);
return $arr;
}
// read.php 详情页其他主题调用,集合tid统一拉取数据,最后归类
function thread_other_pull($thread)
{
global $forumlist, $gid;
$fid = array_value($thread, 'fid');
$forum = array_value($forumlist, $fid);
if (empty($forum)) return NULL;
//$tid = array_value($thread, 'tid');
//$tag_fmt = array_value($thread, 'tag_fmt');
$arrlist = array();
$tidlist = array();
// 版块自定义
list($flaglist, $flagtids) = flag_thread_by_fid($fid);
empty($flagtids) || $tidlist += $flagtids;
unset($flagtids);
$randoms = thread_random_get($forum['randoms']);
// 在这之前合并所有二维数组 tid值为键/array('tid值' => tid值)
$tidarr = empty($tidlist) ? array() : arrlist_values($tidlist, 'tid');
// 在这之前使用array_merge()前合并所有一维数组 tid/array(1,2,3)
$randoms AND $tidarr = array_merge($tidarr, $randoms);
if (empty($tidarr)) return NULL;
$tidarr = array_unique($tidarr);
// 主题相关统一遍历后再归类
$threadlist = well_thread_find($tidarr, count($tidarr));
// 过滤没有权限访问的主题 / filter no permission thread
well_thread_list_access_filter($threadlist, $gid);
foreach ($threadlist as &$_thread) {
$_thread = well_thread_safe_info($_thread);
if ($randoms) {
in_array($_thread['tid'], $randoms) AND $arrlist['randomlist'][$_thread['tid']] = $_thread;
}
// flag thread
if (!empty($flaglist)) {
foreach ($flaglist as $key => $val) {
if (isset($val['tids']) && in_array($_thread['tid'], $val['tids'])) {
$flaglist[$key]['list'][array_search($_thread['tid'], $val['tids'])] = $_thread;
ksort($flaglist[$key]['list']);
}
}
}
}
unset($threadlist);
if (!empty($flaglist)) {
foreach ($flaglist as &$val) {
$i = 0;
if (!isset($val['list'])) continue;
foreach ($val['list'] as &$v) {
++$i;
$v['i'] = $i;
}
}
$arrlist['flaglist'] = $flaglist;
unset($flaglist);
}
return $arrlist;
}
//--------------------------cache--------------------------
// 已格式化 从缓存中读取,避免重复从数据库取数据
function well_thread_read_cache($tid)
{
global $conf;
$key = 'website_thread_' . $tid;
static $cache = array(); // 用静态变量只能在当前 request 生命周期缓存,跨进程需要再加一层缓存:redis/memcached/xcache/apc
if (isset($cache[$key])) return $cache[$key];
if ('mysql' == $conf['cache']['type']) {
$r = well_thread_read($tid);
} else {
$r = cache_get($key);
if (NULL === $r) {
$r = well_thread_read($tid);
$r and cache_set($key, $r, 1800);
}
}
$cache[$key] = $r ? $r : NULL;
return $cache[$key];
}
?>