请选择 进入手机版 | 继续访问电脑版
绿茶科技社区

PHP实现linux命令tail -f

2019-1-22 14:50
8582

马上注册,结交更多好友,享用更多功能,让你轻松玩转社区。

您需要 登录 才可以下载或查看,没有帐号?立即注册

x
tail 命令从指定点开始将文件写到标准输出.使用tail命令的-f选项可以方便的查阅正在改变的日志文件,tail -f filename会把filename里最尾部的内容显示在屏幕上,并且不但刷新,使你看到最新的文件内容.接下来通过本文给大家介绍PHP实现linux命令tail -f,需要的朋友参考下
tail 命令从指定点开始将文件写到标准输出.使用tail命令的-f选项可以方便的查阅正在改变的日志文件,tail -f filename会把filename里最尾部的内容显示在屏幕上,并且不但刷新,使你看到最新的文件内容.
1.命令格式;
tail[必要参数][选择参数][文件]
2.命令功能:
用于显示指定文件末尾内容,不指定文件时,作为输入信息进行处理。常用查看日志文件。
3.命令参数:
-f 循环读取
-q 不显示处理信息
-v 显示详细的处理信息
-c<数目> 显示的字节数
-n<行数> 显示行数
--pid=PID 与-f合用,表示在进程ID,PID死掉之后结束.
-q, --quiet, --silent 从不输出给出文件名的首部
-s, --sleep-interval=S 与-f合用,表示在每次反复的间隔休眠S秒
今天突然想到之前有人问过我的一个问题,如何通过PHP实现linux中的命令tail -f,这里就来分析实现下。

这个想一想也挺简单,通过一个循环检测文件,看文件的大小是否有变化,如果有变化,输出文件变化的部分,当然了这里面会有好多的细节,这里具体分析下。

如果初始文件太大或者改变内容太多

这个时候一下输出好多内容可能看不清,因此我这里设置了一个阈值8192,当内容长度超过这个阈值的时候,只输出最后面的8192个字节,这样就不会出现大面积的刷新导致看不清的问题。

如何检测文件大小的变化

这个问题是这个程序的核心,能不能成功,性能的好坏就靠这部分了。
我在这里的实现是下面这样:
•打开文件句柄$fp,这里要注意,这里的文件句柄全程需中只打开一次关闭一次,因此要将他放在循环的外面。
•初始化当前文件大小file_size和file_size_new都为0。 •循环里面更新file_size_new文件大小,这里要注意,php中获取文件大小之前一定要运行函数clearstatcache(),清除文件状态缓存,否则获取文件大小可能会有偏差。

•计算add_size = file_size_new - file_size,看文件大小是否有变化,如果有变化,将文件指针移动到指定位置,然后输出新加的内容,更新file_size值为new_file_size。
•usleep(50000),睡眠1/20秒。

代码实现

  1. #!/usr/bin/env php  
  2. <?php
  3. if(2 != count($argv)){
  4. fwrite(
  5. STDERR,
  6. "调用格式错误!使用格式 ./tail filename".PHP_EOL
  7. );  
  8. return 1;
  9. }
  10. $file_name = $argv[1];
  11. define("MAX_SHOW", 8192);
  12. $file_size = 0;
  13. $file_size_new = 0;
  14. $add_size = 0;
  15. $ignore_size = 0;
  16. $fp = fopen($file_name, "r");
  17. while(1){
  18. clearstatcache();
  19. $file_size_new = filesize($file_name);
  20. $add_size = $file_size_new - $file_size;
  21. if($add_size > 0){  
  22. if($add_size > MAX_SHOW){
  23. $ignore_size = $add_size - MAX_SHOW;
  24. $add_size = MAX_SHOW;
  25. fseek($fp, $file_size + $ignore_size);
  26. }  
  27. fwrite(
  28. STDOUT,
  29. fread($fp, $add_size)
  30. );  
  31. $file_size = $file_size_new;
  32. }
  33. usleep(50000);
  34. }
  35. fclose($fp);
复制代码
代码实现这里第一行的#!/usr/bin/env php 是告诉可执行文件,可执行文件php在系统PATH中查找,这样的好处就是移植性好。


下面是结果


下文给大家介绍如何实现Linux下高亮关键字的tail -f功能
公司内部一哥们发布到邮件列表中的一个小tip,挺有意思,属于程序员的“奇淫技巧”类吧,值得记录一下。
如果你在linux下工作,那用tail -f跟踪一个日志文件的输出内容应该是家常便饭了。
但是,有时你更关心的是一些敏感字词,希望能够在动态跟踪的同时,把这些字词高亮出来,比如日志中的ERROR关键字。
那么,一种思路就是把你tail输出的东西再做一次包装处理,这个很符合linux管道处理的思想。以高亮Log中的ERROR为例,你可以这样:

Shell代码
  1. tail -f xxx.log | perl -pe 's/(ERROR)/\e[1;31m$1\e[0m/g'
复制代码
其中,xxx.log是你要跟踪的文件。这里假设了你的Linux的PATH中有perl。perl在这里干的事情,就是通过命令行的方式进行动态的替换ERROR字符串的操作,替换过程中,主要使用了Linux的console_codes的语法结构。(具体关于console_codes的细节,可以通过man console_codes进行了解)这里,\e主要进行转移说明。
如果你手头有server log之类的日志,试试上面的命令,是不是把ERROR全部标红了。
利用这个原理,你完全可以按照你所需要的颜色高亮你感兴趣的输出,具体的颜色说明,可以在man console_codes中查到。
另外,less本身也支持类似于tail -f的操作,就是在你用less打开一个文件之后,按住SHIFT+F键,这样就直接进入follow的模式了。看上去跟tail -f效果是一致的。利用这点,你想达到高亮的tail -f的效果,就拢共分为以下3步了:
  1. less xxx.log
  2. 中/${key_work}的方式搜索你要高亮的关键字。(即使目前文件中没有也没关系)
  3. SHIFT+F,进入follow模式
复制代码




分享到 :
0 人收藏

2 个回复

倒序浏览
EtherDream  高级会员 | 2019-1-22 15:05:47
楼下的接上
老翅寒暑  高级会员 | 2019-2-14 15:12:20
鼎力支持!!
您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

举报|Archiver|手机版|小黑屋|Lvchakeji Inc.  

Powered by Discuz! X3.3 © 2001-2016 Comsenz Inc.

返回顶部