PHP实时统计在线用户数及IP地理位置分布实例

沿途有光
沿途有光
发布时间:2026-10-14 | 4人浏览过
原创

本文详细介绍如何使用PHP结合MySQL和新浪IP查询接口,实现一个简单的网站在线访客统计功能。该功能不仅能显示当前在线总人数,还能根据IP识别访客所在省份并进行区域分布展示。

效果预览

技术架构与准备条件

该方案采用前后端分离的轻量级交互模式,整体流程如下:

  1. 数据标识:服务器为访客分配包含省份信息的 cookie。
  2. 持久化存储:每次页面刷新时,将访客的真实IP、省份及时间戳存入MySQL数据库。
  3. 活跃判定:当访客下次访问时,若数据库中已有记录则更新访问时间;若超过设定时间(如10分钟)未活动,则自动清理过期数据。
  4. 异步交互:前端通过jQuery发起AJAX请求,获取在线总数并渲染地域分布下拉列表。

第一步:数据库准备

我们需要创建一张 online 表来存储用户的在线状态。为保证高并发下的写入效率,本例使用MyISAM引擎,主要记录唯一标识IP以及最后在线时间戳。

CREATE TABLE IF NOT EXISTS `online` (
 `id` int(11) NOT NULL AUTO_INCREMENT,
 `ip` varchar(30) NOT NULL,
 `province` varchar(64) NOT NULL,
 `addtime` int(10) NOT NULL DEFAULT '0',
 PRIMARY KEY (`id`)
) ENGINE=MyISAM DEFAULT CHARSET=utf8;

第二步:编写后端记录脚本 (online.php)

这是核心处理逻辑文件。它负责获取访客IP、调用外部API获取省份(如果本地无缓存),并在数据库中执行“存在即更新,不存在即插入”的操作。同时,脚本会定期清理掉长时间不活跃的访客记录。

include_once('connect.php'); // 确保已连接数据库
$ip = get_client_ip(); // 获取真实IP
$time = time();

// 检查当前IP是否在数据库中
$query = mysql_query("select id from online where ip='$ip'");
if(!mysql_num_rows($query)){
 // 若不存在新记录,则需确定其省份信息
 if(isset($_COOKIE['geoData']) && $_COOKIE['geoData']){
 $province = $_COOKIE['geoData'];
 } else {
 // 调用新浪IP接口查询(仅取回JSON字符串解析)
 $api = "http://int.dpool.sina.com.cn/iplookup/iplookup.php?format=json&ip=$ip";
 $json = file_get_contents($api);
 $arr = json_decode($json, true);
 $province = $arr['province'] ?? '未知';
 setcookie('geoData', $province, $time+600); // 设置Cookie有效期10分钟
 }
 // 新增记录
 mysql_query("insert into online (ip,province,addtime) values ('$ip','$province','$time')");
} else {
 // 已存在,则更新其最后活动时间
 mysql_query("update online set addtime='$time' where ip='$ip'");
}

// 清除过期数据(超过10分钟/600秒无活动的视为离线)
$outtime = $time-600;
mysql_query("delete from online where addtime<$outtime");

// 统计当前有效在线数
list($totalOnline) = mysql_fetch_array(mysql_query("select count(*) from online"));
echo $totalOnline;
mysql_close();

获取真实客户端IP函数

在代理服务器或负载均衡环境下,直接获取IP可能不准,建议封装以下函数:

function get_client_ip() {
 if (getenv("HTTP_CLIENT_IP") && strcasecmp(getenv("HTTP_CLIENT_IP"), "unknown")) 
   $ip = getenv("HTTP_CLIENT_IP"); 
 else if (getenv("HTTP_X_FORWARDED_FOR") && strcasecmp(getenv("HTTP_X_FORWARDED_FOR"), "unknown")) 
   $ip = getenv("HTTP_X_FORWARDED_FOR"); 
 else if (getenv("REMOTE_ADDR") && strcasecmp(getenv("REMOTE_ADDR"), "unknown")) 
   $ip = getenv("REMOTE_ADDR"); 
 else if (isset ($_SERVER['REMOTE_ADDR']) && $_SERVER['REMOTE_ADDR'] && strcasecmp($_SERVER['REMOTE_ADDR'], "unknown")) 
   $ip = $_SERVER['REMOTE_ADDR']; 
 else $ip = "unknown"; 
 return ($ip);
}

第三步:编写地区分布数据接口 (geo.php)

此接口供前端下拉列表读取。它从数据库中按省份分组统计人数,并以 JSON 格式返回。

include_once('connect.php');
// 查询各省份人数并排序
$sql = "select province,count(*) as total from online group by province order by total desc";
$result = mysql_query($sql);
$list = array();
while($row = mysql_fetch_array($result)){
 $list[] = array(
 'province' => $row['province'],
 'total' => $row['total']
 );
}
echo json_encode($list);

第四步:前端页面结构与样式 (HTML/CSS)

首先构建页面框架,一个显示总数的容器和一个默认隐藏的下拉列表。

<div class="demo"> 
  <div id="total">当前在线:<span id="onlinenum"></span></div> 
  <ul id="onlinelist"> 
    <li>加载中...</li> 
  </ul>
</div>

CSS 用于美化提示框及下划线动画:

.demo{width:150px; margin:20px auto; font-size:14px; position:relative;}
#total{padding:6px 10px; background:#090 url(arr.png) no-repeat right top; color:#fff; cursor:pointer; border-radius:5px; box-shadow:0 0 3px #ccc;}
#onlinelist{background:#f7f7f7; border:1px solid #d3d3d3; display:none; border-radius:5px; padding:0;margin:0; list-style:none; width:100%;position:absolute;top:100%;left:0;z-index:10;}
#onlinelist li{height:20px; line-height:20px;padding:4px 6px;border-bottom:1px dotted #d9d3d3}
#onlinelist li span{float:right}

第五步:jQuery 异步加载逻辑

页面加载完毕后初始化在线人数;鼠标悬停于统计栏时触发 AJAX 请求,动态生成省份分布列表。

$(function(){ 
 // 初次加载在线总数
 $("#onlinenum").load("online.php");

 $(".demo").hover(function(){ 
   $("#onlinelist").slideDown("fast");
   var str = '';
   $.getJSON("geo.php",function(json){ 
     $.each(json,function(index,array){ 
       str += "<li><span>"+array['total']+"</span>"+array['province']+"</li>";
     });
     $("#onlinelist").html(str);
   });
 },function(){
   $("#onlinelist").slideUp("fast");
 });
});

注意引入 jQuery 库以支持上述 AJAX 操作。以上就是PHP统计当前在线用户数的详细内容,更多关于PHP网页开发技巧的资料请关注本站其它相关文章!

相关标签:

本站声明

本文内容仅供参考,不代表本站观点。转载或引用请注明出处。如发现内容问题,请通过联系我们页面反馈。

Python 相关产品和应用

全部下载

专题列表