• 如何监控一个日志文件并验证,用tail的原理实现


    最近在做网页爬虫的测试,需要通过apache的access-log来验证爬虫的行为,就想到了用类似linux的tail命令实现方式来实现。这里先把代码贴出来:

    #include <stdio.h>
    #include 
    <stdlib.h>
    #include 
    <unistd.h>
    #include 
    <malloc.h>
    #include 
    <sys/stat.h>

    static size_t filesize(const char *filename) {
        
    struct stat sb;

        
    if (!stat(filename, &sb))
            
    return sb.st_size;
        
    return 0;
    }

    static void tailf(const char *filename, int lines) {
        
    char **buffer;
        
    int head = 0;
        
    int tail = 0;
        FILE 
    *str;
        
    int i;

        
    if (!(str = fopen(filename, "r"))) {
            fprintf(stderr, 
    "Cannot open \"%s\" for read\n", filename);
            perror(
    "");
            exit(
    1);
        }

        buffer 
    = (char **) malloc(lines * sizeof(*buffer));
        
    for (i = 0; i < lines; i++)
            buffer[i] 
    = (char *) malloc(BUFSIZ + 1);

        
    while (fgets(buffer[tail], BUFSIZ, str)) {
            
    if (++tail >= lines) {
                tail 
    = 0;
                head 
    = 1;
            }
        }

        
    //the method here is very smart, if variable head is set, that is to say the file is longer than 10 lines,
        
    //and the first line of the last 10 lines is start from the index tail, and the last line is at index tail-1

        
    if (head) {
            
    for (i = tail; i < lines; i++)
                fputs(buffer[i], stdout);
            
    for (i = 0; i < tail; i++)
                fputs(buffer[i], stdout);
        } 
    else {
            
    for (i = head; i < tail; i++)
                fputs(buffer[i], stdout);
        }
        fflush(stdout);

        
    for (i = 0; i < lines; i++)
            free(buffer[i]);
        free(buffer);
    }

    int main(int argc, char **argv) {
        
    char buffer[BUFSIZ];
        size_t osize, nsize;
        FILE 
    *str;
        
    const char *filename;
        
    int count;

        
    if (argc != 2) {
            fprintf(stderr, 
    "Usage: tailf logfile\n");
            exit(
    1);
        }

        filename 
    = argv[1];

        tailf(filename, 
    10);

        
    for (osize = filesize(filename);;) {
            nsize 
    = filesize(filename);
            
    if (nsize != osize) {
                
    if (!(str = fopen(filename, "r"))) {
                    fprintf(stderr, 
    "Cannot open \"%s\" for read\n", filename);
                    perror(argv[
    0]);
                    exit(
    1);
                }
                
    if (!fseek(str, osize, SEEK_SET))
                    
    while ((count = fread(buffer, 1sizeof(buffer), str)) > 0)
                        fwrite(buffer, 
    1, count, stdout);
                fflush(stdout);
                fclose(str);
                osize 
    = nsize;
            }
            usleep(
    250000); /* 250mS */
        }
        
    return 0;

    } 

  • 相关阅读:
    OilPaint(转载/实验)
    UE4 3D artist
    render pipeline about (翻译)
    Python 相对导入 碎碎念
    USF, USH Grammar
    JZ19 顺时针打印矩阵
    JZ49 把字符串转换成整数
    JZ45 扑克牌顺子
    JZ53 表示数值的字符串
    JZ48 不用加减乘除做加法
  • 原文地址:https://www.cnblogs.com/welkinwalker/p/2088403.html
Copyright © 2020-2023  润新知