Windows+GCC得到各种格式的文件正文(office文件,PDF,邮件,html,zip等)

 Graccvs组件智能分析提取其他各种文件中文本,为自然语言信息检索,机器学习等高端技术提供底层支持的技术组件,是Lucene/CLucene, Elasticsearch, Sphinx等全文检索工具,OA, ERP, CRM,网盘,文件管理等其他系统提供文件摘要及搜索前置服务。同时也可以为安全网关,邮件内容监控,内网安全等系统提供文件搜索及监控服务底层技术支持。

组件支持常见各种文件格式”.pdf", ".doc", ".odt", ".docx", ".dotm", ".docm", ".wps", ".xls", ".xlsx", ".xlsm", ".xltm", ".et", ".ppt", ".pptx", ".potm", ".pptm", ".ppsm", ".dps", ".ofd"(电子发票版式文件), ".rtf",".html", ".htm", ".mht", ".mhtml", ".eml", ".emmx", "xmind", "gmind", ".chm", ".zip" 等。组件速度快,效率高,调用非常简单。

Graccvs组件是以DLL格式动态链接库方式调用的, 点击这里下载DLL动态链接库,函数详细说明和调用示例点击这里下载

调用过程:
1:拷贝graccvs.h 和 graccvsDllTest.c到文件夹下。
2:拷贝 graccvs64.dll到工程中, 默认在exe输出位置。
3:编译即可 gcc graccvsDllTest.c -o graccvsDllTest.exe 。

头文件graccvs.h :

#include <stdio.h>
#include <stdlib.h>
  
//----------------------以下为函数说明----------------------
// 加载DLL,设置动态库需要的临时文件夹,且对此文件夹要有读写权限
typedef void (*LOAD)(char *tempDir);  
 
/*
  注册软件:
  方式1:输入参数,corp为公司名称licText为注册码
  方式2:把授权文件grauth.lic保存到动态库相同文件夹,调用TAuth函数(corp, licText都为空)系统自动加载grauth.lic
  返回值:
    0:免费版本许可为空
    1:许可正常
    2:序列号(公司授权名称)错误
    3:加密数据格式错误
    4:许可过期
    5:许可验证错误
    6:无效的许可
    7:未知错误
 
  注1:如果注册失败,系统变为免费版本
  注2:免费版也需要调用此函数,corp和licText都为空
*/
typedef int (*AUTH)(char *corp, char *licText);  
 
// 提取文件正文,并保存到目标文件
// inFilePtr文件名称指针, outFilePtr为TXT目标文件文件指针
typedef int (*TOTEXTFILE)(char *inFilePtr, char *outFilePtr);  
// 提取文件正文,返回字符串指针
// inFilePtr输入文件指针, 返回UTF-8编码字符串数据指针(此指针需要使用FREESTRING函数释放内存)
typedef char* (*TOSTRING)(char *inFilePtr);  
// 释放TOSTRING等函数的返回指针
typedef void (*FREESTRING)(char *p);  
// 得到最后的错误信息
typedef char* (*LASTERR)();  
 
// 提取Http/Https文件,返回字符串数据指针
// url=Http/Https地址
// fileExt=文件类型(比如:".pdf"),
// timeout=超时设置,超过此数值系统终止下载文件。单位为毫秒,默认为0(等待文件下载直到完成)
// httpParams=JSON格式header数据和cookie数据,默认为空
/*   
  JSON格式如下:
  {"headers":
  [{名称1: 值1},{名称2: 值2},...],
  "cookies":[
  {"name": 名称(字符串), "value": 值(字符串), "expires": 有效期(整数,单位毫秒),
  "path": 路径(字符串), "domain": 域名(字符串)},
  {"name": 名称(字符串), "value": 值(字符串), "expires": 有效期(整数,单位毫秒),
  "path": 路径(字符串), "domain": 域名(字符串)}
  ...
  ]}
  例如:
  {"headers":[{"client_id": "g01x9"}, {"client_secret": "e23c89cc9fe"}, {"client_index": 10092}],
  "cookies":[{"name": "ga", "value": "1020", "expires":36000000, "path": "/hx/", "domain":"www.gaya-soft.cn"},
  {"name": "xc3", "value": "10099", "expires":240000, "path": "", "domain":""}]}
*/   
// 返回UTF-8编码字符串数据指针(此指针需要使用FREESTRING函数释放内存)
typedef char* (*HTTPTOSTRING)(char *url, char *fileExt, int timeout, char *httpParams);  
 
// 下载Http文件,并提取文本,保存到目标文件 
// outfile为TXT目标文件文件指针,其他参数和HTTPTOSTRING参数相同
typedef int (*HTTPTOTEXTFILE)(char *url, char *fileExt, char *outfile, int timeout, char *httpParams);  
 
//---------------------异步批量处理相关函数---------------------
// 增加一个文件提取异步任务, Infile输入文件地址, Outfile为TXT目标文件文件
// 如果提取某个文件错误,则目标文本文件的内容如下格式: @ErrCode:错误代码, ErrMessage:错误提示
typedef void (*ADDTASK)(char *inFilePtr, char * outTxtFilePtr);  
// 增加一个异步提取Http文件任务,参数同 HTTPTOTEXTFILE 函数
typedef void (*ADDHTTPTASK)(char * url, char *fileExt, char *outTxtFile, int timeout, char *httpParams);  
// 开始执行异步任务,返回值=1开始执行   
// =2 免费版不支持此功能,=3 没有可以执行的任务 ,=4 当前任务未完成
typedef int (*ASYNCSTART)();  
// 停止异步批量任务
typedef void (*ASYNCSTOP)();  
// 一直等待,直到全部异步任务结束
typedef void (*ASYNCWAIT)();  
// 得到执行异步任务的状态, =0 没开始, =1 正在处理中,=2 已中断, =99 处理完成
typedef int (*ASYNCSTATE)(); 
// 设置执行异步任务的并发数量(不大于软件授权数量),返回并发数量
typedef int (*ASYNCMAXPROCS)(int num);  
//---------------------异步批量处理相关函数---------------------
 
// 关闭动态库前调用此函数释放资源,否则关闭DLL会发生错误
typedef void (*UNLOAD)();   
//typedef void (*SAVESN)();  
 
//提取文本的错误类型
enum GrErrCode
{
  TFE_OK = 0,
  TFE_UNKNOW = 1,
  TFE_FILE_NOTEXIST = 2,
  TFE_SAVE_ERROR = 3,
  TFE_OUTSIZE = 4,
  TFE_UNSUPPORTED = 5,
  TFE_ERROR_INTERFACE = 6,
  TFE_HTTP_ERR = 7,
  TFE_HTTP_FILE_NULL = 8,
  TFE_LICENCE_ERR = 9 
};
  
 

测试CPP文件:

#define WINDOWS
#ifdef WINDOWS
#include <windows.h>
#else
#include <iconv.h>
#include <wctype.h>
#include <wchar.h>
#include <errno.h>
#endif
 
#include <ctype.h>
#include <stdio.h>
#include <stdlib.h>
#include <time.h>
#include "graccvs.h"
 
// 根据错误类型返回错误信息
char *codeText(unsigned int code)
{
    switch (code)
    {
    case TFE_OK:
        return "ok";
    case TFE_UNKNOW:
        return "未知错误";
    case TFE_FILE_NOTEXIST:
        return "提取源文件不存在";
    case TFE_SAVE_ERROR:
        return "保存目标文件失败";
    case TFE_OUTSIZE:
        return "提取的源文件超出设置的大小范围"; 
    case TFE_UNSUPPORTED:
        return "不支持的提取文件格式";
    case TFE_ERROR_INTERFACE:
        return "得到接口失败";
    case TFE_HTTP_ERR :
        return "HTTP下载文件失败";
    case TFE_HTTP_FILE_NULL :
        return "HTTP文件为空";
    case TFE_LICENCE_ERR:
        return "软件许可错误"; 
    default:
        return "未知错误2";
    }
}
 
void wcharToUtf8(const wchar_t *src, char *dest, int destSize)
{
    int ik = WideCharToMultiByte(CP_UTF8, 0, src, wcslen(src), dest, destSize, NULL, NULL);
    for (int i = ik; i < destSize; i++)
    {
        dest[i] = 0;
    }
}
 
// ------------------------提取正文并保存为文本文件------------------------
void testToTextFile(HINSTANCE handle, LASTERR lastErr)
{
    TOTEXTFILE toTextFile = (TOTEXTFILE)GetProcAddress(handle, "ToTextFile"); 
    if (toTextFile == NULL) {
        return;
    }
 
    static char inFileName[255]; // 根据实际情况分配长度
    wcharToUtf8(L"test\\graccvs文件正文提取接口.pdf", &inFileName[0], 255);
    static char outFileName[255];
    wcharToUtf8(L"test\\out001.txt", &outFileName[0], 255);
    // 调用DLL函数得到文件正文
    int code = toTextFile(&inFileName[0], &outFileName[0]);
    //TFE_OK为提取完成,其他code调用codeText返回相同错误
    if (code != TFE_OK)
    {
        // 方式1: 根据R值调用函数ErrText得到具体错误信息, 此方式速度快
        char *e = codeText(code);
        printf("error from code: %s\n", e);
 
        // 方式2:调用DLL函数,得到具体错误信息, 此方式错误信息更加准确 
        char *p = lastErr();
        printf("error from dll: %s\n", p);
    }
    else
    { 
        printf("testToTextFile end\n"); 
    }
}
 
// ------------------------提取正文,返回字符串指针------------------------
void testToString(HINSTANCE handle, FREESTRING freeString)
{
    TOSTRING toString = (TOSTRING)GetProcAddress(handle, "ToString");  
    if  (toString == NULL || freeString == NULL){
        return;
    }
 
    static char inFileName2[255];
    wcharToUtf8(L"test\\简可信模板OCR识别工具帮助.docx", &inFileName2[0], 255);
    char *p = toString(&inFileName2[0]); //返回UTF-8编码字符串
    printf("text=\n%s\n", p);
    freeString(p); // 务必调用freeString函数释放字符串内存
}
 
// ------------------------HTTP提取正文并保存为文本文件------------------------
void testHttpToTextFile(HINSTANCE handle)
{
    HTTPTOTEXTFILE httpToTextFile = (HTTPTOTEXTFILE)GetProcAddress(handle, "HttpToTextFile"); 
    if (httpToTextFile == NULL) {
        return;
    }
 
    static char rul[255], ext[6], outFile[128];  
    wcharToUtf8(L"https://www.gaya-soft.cn/dfs/v2/简可信模板OCR识别工具帮助.docx", &rul[0], 255); 
    wcharToUtf8(L".docx", &ext[0], 6); 
    wcharToUtf8(L"test\\out002.txt", &outFile[0], 128);
    // 调用DLL函数得到文件正文
    int timeout = 0; //超时设置,单位毫秒, 默认为0 
    int code = httpToTextFile(&rul[0], &ext[0], &outFile[0], timeout, NULL);
    //TFE_OK为提取完成,其他code调用codeText返回相同错误
    if (code != TFE_OK)
    { 
        char *e = codeText(code);
        printf("error from code: %s\n", e); 
    }
    else
    { 
        printf("testHttpToTextFile end\n"); 
    }
}
  
// ------------------------HTTP提取正文,返回字符串指针------------------------
void testHttpToString(HINSTANCE handle, FREESTRING freeString)
{
    HTTPTOSTRING httpToString = (HTTPTOSTRING)GetProcAddress(handle, "HttpToString");  
    if  (httpToString == NULL || freeString == NULL){
        return;
    }
 
    static char rul[255], ext[6], params[512];
    wcharToUtf8(L"https://www.gaya-soft.cn/dfs/v2/graccvs文件正文提取接口.pdf", &rul[0], 255); 
    wcharToUtf8(L".pdf", &ext[0], 6);  
    wchar_t *a_params = L"{\"headers\":[{\"client_id\": \"g01x9\"}, {\"client_secret\": \"e23c89cc9fe\"}], \"cookies\":[{\"name\": \"ga\", \"value\": \"1020\", \"expires\":36000000, \"path\": \"/\"}]}";
    wcharToUtf8(a_params, ¶ms[0], 512);
    int timeout = 60 * 1000; //超时设置,单位毫秒 
    //
    char *p = httpToString(&rul[0], &ext[0], timeout, ¶ms[0]);
    printf("text=\n%s\n", p);
    freeString(p); // 务必调用freeString函数释放字符串内存
}
 
// ---------------异步批量文件提取,适合多线程处理很多文件---------------
// 文件提取任务 
void asyncAddTask(HINSTANCE handle)
{  
    ADDTASK addTask = (ADDTASK)GetProcAddress(handle, "AddTask");  
    if (addTask==NULL){
        return;
    }
 
    // -----可以增加N个任务 
    static char inFn[255], inFn2[255], outFn[255], outFn2[255];  
    wcharToUtf8(L"test\\graccvs文件正文提取接口.pdf", &inFn[0], 255); 
    wcharToUtf8(L"test\\asyncOut001.txt", &outFn[0], 255);  
    addTask(&inFn[0], &outFn[0]); // 一个文件任务
 
    wcharToUtf8(L"test\\Adobe Intro.ofd", &inFn2[0], 255); 
    wcharToUtf8(L"test\\asyncOut002.txt", &outFn2[0], 255); 
    addTask(&inFn2[0], &outFn2[0]);  // 一个文件任务
}
 
// Http文件提取任务 
void asyncAddHttpTask(HINSTANCE handle)
{
    ADDHTTPTASK addHttpTask = (ADDHTTPTASK)GetProcAddress(handle, "AddHttpTask"); 
    if (addHttpTask==NULL){
        return;
    }
    // 可以增加N个任务
    static char rul[255], ext[6], outFn[255];  
    wcharToUtf8(L"https://www.gaya-soft.cn/dfs/v2/简可信模板OCR识别工具帮助.docx", &rul[0], 255);
    wcharToUtf8(L".docx", &ext[0], 6);
    wcharToUtf8(L"test\\asyncOut003.txt", &outFn[0], 255);
    int timeout = 90 * 1000; //超时设置,单位毫秒, 默认为0
    addHttpTask(&rul[0], &ext[0], &outFn[0], timeout, NULL);
}
 
// 方式1:开始任务,等待全部任务完成
void asyncRun1(HINSTANCE handle, ASYNCSTART asyncStart)
{ 
    ASYNCWAIT asyncWait = (ASYNCWAIT)GetProcAddress(handle, "AsyncWait"); 
    if (asyncWait==NULL) {
        return;
    }
    // 开始任务
    int r = asyncStart(); 
    if (r == 1){  
        asyncWait(); // 等待任务全部结束
        printf("方式1--任务完成\n"); 
    }else if (r == 2){
        printf("免费版不支持此功能\n");
    }else if (r == 3){
        printf("没有可以执行的任务\n");
    }else if (r == 4){
        printf("当前任务未完成\n");
    }
}
 
// 方式2:判断执行情况,超时退出,主动结束任务
void asyncRun2(HINSTANCE handle, ASYNCSTART asyncStart)
{ 
    ASYNCSTOP asyncStop = (ASYNCSTOP)GetProcAddress(handle, "AsyncStop");  
    ASYNCSTATE asyncState = (ASYNCSTATE)GetProcAddress(handle, "AsyncState"); 
    if (asyncStop==NULL || asyncState==NULL) {
        return;
    }
 
    // 开始任务
    BOOL isOver = FALSE;
    int r = asyncStart(); 
    if (r == 1){   
        //clock_t start_t = clock();
        time_t start_tm; 
        time(&start_tm);
        // 5分钟后结束任务
        while(TRUE){ 
            time_t n;
            time(&n);
            // 5分钟后中断
            if (difftime(n, start_tm) > 5 * 60){
                break;
            }
            // 判断任务情况, =0 没开始, =1 正在处理中,=2 已中断, =99 处理完成
            int x = asyncState();
            if (x == 1){
                Sleep(500); 
            }else if (x == 99){
                isOver = TRUE; // 处理完成
                break;
            }else{
                break;
            }
        }
        //
        if (!isOver){
           asyncStop(); // 结束任务 
        }   
        printf("方式2--任务完成\n"); 
    }else if (r == 2){
        printf("免费版不支持此功能\n");
    }else if (r == 3){
        printf("没有可以执行的任务\n");
    }else if (r == 4){
        printf("当前任务未完成\n");
    }
}
 
void asyncTest(HINSTANCE handle)
{
    ASYNCMAXPROCS asyncMaxProcs = (ASYNCMAXPROCS)GetProcAddress(handle, "AsyncMaxProcs");  
    ASYNCSTART asyncStart = (ASYNCSTART)GetProcAddress(handle, "AsyncStart"); 
    
    //
    if( asyncMaxProcs==NULL || asyncStart==NULL){
        return;
    }
    //
    asyncMaxProcs(8); // 同时运行8个任务
    //
    asyncAddTask(handle);  // 文件提取任务 
    asyncAddHttpTask(handle); // Http文件提取任务
    // 执行任务--方式1
    asyncRun1(handle, asyncStart);
 
    // 执行任务--方式2
    asyncAddTask(handle); 
    asyncAddHttpTask(handle); 
    asyncRun2(handle, asyncStart);
}
// ---------------异步批量文件提取,适合多线程处理很多文件---------------
 
/*
void saveSn(HINSTANCE handle)
{
    SAVESN saveSn = (SAVESN)GetProcAddress(handle, "SaveSn"); 
    saveSn(); 
}
*/
 
int main()
{
    printf("graccvs dll test\n");
    //
    HINSTANCE handle = LoadLibraryA("graccvs64.dll"); //默认64位系统,32位DLL或者接口更新请到官网 
    if (handle <= 0)
    {
        return 0;
    }
  
    LOAD load = (LOAD)GetProcAddress(handle, "Load");
    AUTH auth = (AUTH)GetProcAddress(handle, "Auth");
    FREESTRING freeString = (FREESTRING)GetProcAddress(handle, "FreeString");
    LASTERR lastErr = (LASTERR)GetProcAddress(handle, "LastErr");
    UNLOAD unload = (UNLOAD)GetProcAddress(handle, "Unload");
    if (load != NULL && auth != NULL && lastErr != NULL && unload != NULL)
    {
        // DLL加载,提取文本需要的临时文件夹,且对此文件夹要有读写权限
        static char tempPath[128];
        wcharToUtf8(L"test\\", &tempPath[0], 128); 
        load(&tempPath[0]);
        printf("init over\n");
 
        // 设置软件许可,免费版都为空
        static char corp[128], licText[1024];
        wcharToUtf8(L"Beij Gaya", &corp[0], 128); 
        wcharToUtf8(L"", &licText[0], 1024); //企业版这里设置授权文本
        auth(&corp[0], &licText[0]); 
  
        // 提取正文并保存为文本文件
        testToTextFile(handle, lastErr); 
        // 提取正文,返回字符串指针
        testToString(handle, freeString); 
 
       
        // 提取HTTP提取正文, 并保存为文本文件
        testHttpToTextFile(handle);
        // 提取HTTP提取正文, 返回字符串指针
        testHttpToString(handle, freeString);
         
        // 异步批量文件提取测试
        asyncTest(handle);
         
        //调用此函数,卸载DLL参数,和load对应使用
        unload();
    }
 
    Sleep(800);
    FreeLibrary(handle);
    Sleep(200);
    printf("all over\n");
 
    return 1;
}
 
// gcc graccvsDllTest.c -o graccvsDllTest.exe

上一篇:Python | BitMap算法及其实现


下一篇:IPython交互模式下的退出