Linux 获取特定软件的初始安装时间

这两天遭遇一个比较坑的需求:"获取(统计)特定软件的初次安装时间",Linux 中的软件有可能是随系统预装的、用户从商店里安装的、从仓库拉取的、自己拷贝(下载)deb 安装的;如果操作系统本身没有统一的接口来记录这一信息,有没有一种简单的方案来提取软件的安装时间? 查了一通API 没答案,乔老师和王老师都建议我去分析dpkg 的日志文件,据说debian系的软件包安装最终都会调dpkg 同时也会产生日志。但是当我们尝试读取其日志时发现日志量之大超乎想向。而且当日志达到一定量时就会将“过期”的日志文件打成压缩包,再产生新的日志。而新日志可能只是最新近期的记录。

今天在夏校长的指点下有了新的思路 /var/lib/dpkg/info/ 中有N 多 (扩展名).md5sums 文件,文件名都是软件包的名字,查看内容文件中记录的都是包中文件的 hash 值,这其实就是一个软件包的校验文件,为了保证包的完整性(文件未被外部修改过),打包时都会生产这个文件用于校验。产生的时间就是软件安装的时间,虽然文件中并没有记录时间。不过我们可以读取这个文件的时间戳。如我们平常查看文件属性时都能显示出文件的创建时间| 最后修改时间| 最后读取时间 ;这三个时间都可以通过文件操作函数获取。


详见代码:


struct AppInfo{

    QString Atype;
    QString pkgName;
    QString version;
    QString created;
    QString lastModified;
    QString lastRead;
};

QList<AppInfo> PCInfo::testDpkgInstallInfo( QStringList tzNameList ,int type ){

    qDebug() << "PCInfo::testDpkgInstallInfo()";

    QProcess *ps  = new QProcess;
    QStringList options;

    QList<AppInfo> AppInfoList;

    /** 列为要对比软件的特征名字 ( 后期应为可更新方式记录 )*/
    foreach (QString appname, tzNameList ) {

        options.clear();
        options << "-c";
        //options << "dpkg -l | grep wps";
        options << "dpkg -l | grep " + appname  ;

        ps->start( "/bin/bash", options );
        ps->waitForFinished();

        QString strTemp = "";
        QStringList tmpList;
        strTemp = QString::fromLocal8Bit( ps->readAllStandardOutput() );
        tmpList.clear();
        tmpList = strTemp.split("\n");
        QString Z = "";
        foreach( QString str,tmpList ){

           if ( str == ""  ){
               continue;
           }
           if ( str.indexOf( "grep "+ appname  ) < 0 ){
               qDebug()<< str;
               QStringList pkgInfo = str.replace(QRegExp("[\\s]+"), " ").split(" ");
               qDebug() <<"pkgName: " << pkgInfo[1];
               qDebug() <<"pkgVer: " << pkgInfo[2];
               /**
                 /var/lib/dpkg/info/wps-office.md5sums
               **/
               QString pkgVersion = pkgInfo[2];
               QString pkgName = pkgInfo[1];
               QString filename = "/var/lib/dpkg/info/" + pkgName + ".md5sums";
               QFileInfo fi(  filename  );
               if( fi.isFile() ){

                   AppInfo appinto;

                   qDebug() <<"fileName " << pkgName;//fi.fileName();
                   appinto.pkgName = pkgName;
                   appinto.version = pkgVersion;
                   qDebug() <<"size " << fi.size();
                   qDebug() <<"created " << fi.created().toString("yyyy-MM-dd hh:mm:ss");
                   appinto.created = fi.created().toString("yyyy-MM-dd hh:mm:ss");
                   qDebug() <<"lastModified " << fi.lastModified().toString("yyyy-MM-dd hh:mm:ss");
                   appinto.lastModified = fi.lastModified().toString("yyyy-MM-dd hh:mm:ss");
                   qDebug() <<"lastRead " << fi.lastRead().toString("yyyy-MM-dd hh:mm:ss");
                   appinto.lastRead = fi.lastRead().toString("yyyy-MM-dd hh:mm:ss");

                   appinto.Atype = QString::number(type);

                   AppInfoList.append(  appinto );
               }

               break;
           }else{
               //continue;
           }
        }
    }


    return AppInfoList;

}