如何使用 Lotus Notes C API 接口得到 DDM 的事件信息

如何使用 Lotus Notes C API 接口得到 DDM 的事件信息

 

徐 文霞, 软件工程师, EMC

 

简介: 本文简单介绍了 Lotus 事件的基本概念和分类,并详细介绍了 Lotus Notes C/C++ API 中与事件有关的接口。最后,给出了利用事件接口来开发一个监控程序的示例。

 

 

发布日期: 2010 年 5 月 31 日 
级别: 初级 
访问情况 250 次浏览 
建议: 0 (添加评论)

1 star 2 stars 3 stars 4 stars 5 stars  平均分 (共 2 个评分 )

 

编者按:想亲自动手试一试?请立即下载 IBM Lotus 软件试用版

下载试用版:IBM Lotus Notes 和 Domino Administrator 客户端软件  |   Lotus Domino 和 Lotus iNotes 服务器软件

前言

在 IBM Lotus Domino 服务器里面所发生的事都可以理解成为事件。事件可以表示系统运行良好,正在处理数据,执行任务;也可以表示系统运转市场,也许无法处理数据信息或者执行被要求的任务。

Domino 系统连续地生成事件。因此,要有效地监控 Domino 系统,用户必须决定那类事件是其所关心的。例如,每次文件在一个指定的服务器自我复制时,产生“复制文件(服务器名称)”的事件。用户可以根据自定义的事件重要程度,配置其所关注的事件。要配置一个事件,用户需要定义三种关键信息:事件类型,事件严重程度,需要处理的方式。

事件类型

根据事件源的不同,事件分为九种不同的类型:应用代码、数据库、目录、消息、操作系统、复制、安全、服务器、网络。

事件严重等级

在 DDM 中定义了五种不同的事件严重等级:致命、失败、警告(高级)、警告(低级)和正常。以下将列出不同严重程度的事件定义:

  • 致命:最高的严重级别, 被视为最严重的错误。
  • 失败:第二高级的严重级别。归类到这一个级别的事件仍然被视为系统的主要问题。
  • 警告(高级):通常用于配置好的事件发生或者一些低级错误产生时。
  • 警告(低级):通常用于配置好的事件发生,不重要的错误,或者是信息类型的事件发生。
  • 正常:大部分时候用于清理来自于事件队列的问题;

事件接口

集合服务器收集两类事件信息,增强事件类和简单事件类。一个简单事件是不和任何具体对象信息有关也不包含任何具体对象信息的事件。例如,在 Domino 服务器控制台的事件所显示的事件大多是简单事件。通过以下事件的 API,所有的 DDM 的事件可以被捕获。

  • EventQueueAlloc:创建具有制定名字的事件队列
  • EventQueueFree:销毁一个事件队列。
  • EventQueuePut: 将一个事件放入事件队列中。
  • EventQueueGet:从一个事件队列删除某个事件;
  • EventRegisterEventRequest:指定一个事件消费者所要处理的事件类型和严重程度
  • EventDeregisterEventRequest:不再接受某类事件的通知。

开发用于监控事件的插件(add-in)

Lotus Notes add-in 程序容易开发,安装和部署到 lotus 客户。监控事件的插件利用 Lotus Notes C/C++ API 的接口,可以获得所有的事件信息,保存在某个磁盘文件中。

以下示例程序将一步步引导进行最简单的监控事件插件的开发。

  1. 所有的插件程序都是从 AddInMain() 主方法开始执行的,在 AddInMain() 方法中可以调用 Lotus Notes C/C++ 所提供的程序接口。 

    清单 1. 插件程序的程序入口点
    						
    STATUS LNPUBLIC AddInMain (HMODULE hModule, int argc, char *argv[]) 
    { 
      // add-in entry 
      // user code execution 
    }; 
    
  2. 声明于保存事件队列的相关的一系列变量; 

    清单 2. 声明事件相关变量;
    						
    char QueueName[] = "DATABASE_EVENT_QUEUE"; /* Name of queue that will be created. */ 
    char InputDestName[] = "EVENT.NSF"; /* A database name to associate with */ 
    /* events of a certain type. */ 
    char OutputDestName[20];     /* A buffer in which to read the name */ 
    /* associated with a certain event. */ 
    /* (Probably will be the same as */ 
    /* InputDestName, but this is defined */ 
    /* seperately for demonstration purposes). */ 
    BOOL bDestNameReturned; /* TRUE if a name returned by call to EventGetDestName. */ 
    DHANDL E hEventData;         /* A handle to event specific data. */ 
    STATUS sError; 
    BYTE far *pBuf;  
    EVENT_DATA far *pEventData; 
    BYTE DataBuf[5120];          /* A temp buf to hold event data. */ 
    BYTE MessageBuf[5120];       /* A buffer in which to build log msgs. */ 
    FILE *EventFile;             /* A file in which to keep the event information*/
    
  3. 利用 EventQueueAlloc 创建具有已声明名称的事件队列,错误返回错误代码;否则,向下执行; 

    清单 3. 创建事件队列
    						
    if (sError = EventQueueAlloc(QueueName)) 
        return (ERR(sError)); 
    
  4. 注册已将创建好的事件队列,错误返回错误代码;如正确,向下执行; 

    清单 4. 注册事件队列
    						
    if (sError = EventRegisterEventRequest(EVT_DATABASE, SEV_NORMAL, QueueName, 
        InputDestName)) 
        return (ERR(sError)); 
    
  5. 进入插件程序循环体,检查我们关注的队列中是否收到事件;如果没有收到事件,不做任何事情;如果有收到事件,使用事件句柄进行处理; 

    清单 5. 循环检测是否产生了用户所注册的事件
    						
    while (!AddInIdle()) 
    { 
    /* Check to see if there is an event we're interested in the queue. 
    * If no events in the queue, don't do anything.*/ 
    } 
    
  6. 当检测到有用户所预定义的事件产生时 , 使用 EventQueueGet() 取出队列,并将事件保存在缓存区中: 

    清单 6. 读取事件
    						
    sError = EventQueueGet(QueueName, &hEventData); 
    if (sError == ERR_EVTQUEUE_EMPTY) 
        continue; 
    if (sError == NOERROR) 
    { 
        pBuf = OSLockObject(hEventData); 
        pEventData = (EVENT_DATA far *)pBuf; 
        memmove(DataBuf, &pEventData->EventSpecificData, pEventData->EventDataLength); 
        DataBuf[pEventData->EventDataLength] = '/0'; 
        /*Write the events in event queue to event file.*/ 
    }
    
  7. 将读取好的事件信息写入到磁盘文件中: 

    清单 7. 在磁盘文件中保存事件信息
    						
    if((EventFile = fopen("Event.txt","a t")) == NULL) 
    { 
        printf("cannot open source file./n"); 
        exit(1); 
    } else { 
        fwrite(DataBuf, sizeof( BYTE ),pEventData->EventDataLength, EventFile); 
        fwrite("/n",sizeof( char ),1, EventFile); 
        fclose(EventFile); 
    }
    
  8. 用户可以根据具体的事件类型和严重等级对事件进行不同的处理;根据实际的监控需要,进行灵活性的扩展; 

    清单 8. 返回特定类型和严重等级的事件
    						
     bDestNameReturned = EventGetDestName(EVT_DATABASE, SEV_NORMAL, 
     QueueName, OutputDestName, sizeof(OutputDestName)); 
     /* 
     * Here, the event consumer could do something with the name 
     * returned by EventGetDestName - If a database name was specified 
     * when the event was registered, the consumer could update the 
     * database appropriately. If a user name was specified during 
     * registration, the event consumer could send mail to notify 
     * the user that the event occurred. 
     */ 
    
  9. 注销事件队列并销毁; 

    清单 9. 注销事件队列并销毁
    						
    /* Destroy the event queue. */ 
    sError = EventDeregisterEventRequest(EVT_DATABASE, SEV_NORMAL, QueueName); 
    EventQueueFree(QueueName); 
    
  10. 退出插件程序; 

    清单 10. 插件程序退出
    						
    /* End of add-in task. We must "return" here rather than "exit". */ 
    return (NOERROR); 
    

结束语

利用 Lotus Notes C/C++ API 来获取事件,可以根据客户自己的需要,获得自己所关注的事件列表,进行有用的事件处理,也可以和 DDM 自身的监控管理相结合,体现更强的灵活性。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值