49. 面向对象的LotusScript(十五)之Log4Dom下
Log4Dom是模仿Log4J的思想建立的。Log4J能够向多种记录媒介以统一的格式写入各种级别的日志信息(包括错误、调试和信息等),还可以籍配置文件在运行时方便地修改记入日志的级别。Log4Dom提供了类似的功能。现在我们就来看看它的各部分元素和代码。
1. 记录日志的文档所用的表单
2. 用于配置日志级别的表单
3. 日志文档视图
第一列按创建日期分类,第二列是文档序号,第三列是创建时间,最后一列是日志名称。还有一个操作可以编辑配置文档。
4. 日志类代码
'*version 1.2-18th March 2008
'*added Log4Dom profile,
'*simplified the usage and renamed some methods,
'*deleted unnecessary log document size check
'*added several features e.g. logging generated error message, expanding the log message
'*argument to variant
'*corrected several bugs
'*@author Starrow Pan
'/**
'* class for the domino implementation of a logger in a similar format
'* as log4J (http://jakarta.apache.org/log5j/
'* @author tony.palmer@ing.com.au
'* @version 1.0 - 4th November 2003
'*/
Private Const CUSTOM_ERR=10000
Private Const CUSTOM_ERROR="CUSTOM ERROR: " ' debugging levels 0 - 5 system, 6 - 10 custom
Const LEVEL_DEBUG = 5
Const LEVEL_DEBUG_STRING = "DEBUG"
Const LEVEL_INFO = 4
Const LEVEL_INFO_STRING="INFO"
Const LEVEL_WARN = 3
Const LEVEL_WARN_STRING = "WARN"
Const LEVEL_ERROR = 2
Const LEVEL_ERROR_STRING = "ERROR"
Const LEVEL_FATAL = 1
Const LEVEL_FATAL_STRING = "FATAL"
Const LEVEL_NONE = 0 ' destination types
Const DEST_TYPE_DB = 0 '/ notes database
Const DEST_TYPE_FILE = 1 '/ text file
Const DEST_TYPE_STATUS = 2 '/ notes status bar
Const DEST_TYPE_PROMPT = 3 '/ message box prompts Class Log4Dom
public logLevel As Integer
public module As String 'module 'the Log Destination, set as a variant then depending on the log type,
'set as either a LogDB, logNotesFile, logStatus or logPrompt
Private logFile As Variant Private m_sess As NotesSession
Private m_curdb As NotesDatabase 'current database
Private m_profile As NotesDocument 'Log4Dom profile document
public logName As String 'log name from the profile Sub New ()
Set m_sess=New NotesSession
logLevel = LEVEL_DEBUG
End Sub %REM
Add a log destination.
As the de facto only used log destination is Notes DB,
I didn't handle the case of multiple log destinations of different types.
%END REM
Public Function AddLogFile(file As Variant)
Set logFile = file If TypeName(file)="LOGDB" then
'read parameter from Log4Dom profile by starrow
Set m_curdb=m_sess.CurrentDatabase
Set m_profile=m_curdb.GetProfileDocument("Log4DomProfile")
If Not m_profile Is Nothing Then
If m_profile.GetItemValue("LogLevel")(0)><"" then
logLevel=m_profile.GetItemValue("LogLevel")(0)
End if
logName=m_profile.GetItemValue("LogName")(0)
End If
'if no parameter provided, try the agent name
If logName="" Then
If Not m_sess.CurrentAgent Is Nothing Then
logName=m_sess.CurrentAgent.Name
End If
End If logFile.LogName=logName
End if
End Function 'logging at the different levels, INFO, WARN etc
Public Function info(message As variant) As Integer
info = WriteLog(LEVEL_INFO, message)
End Function Public Function warn(message As variant) As Integer
warn = WriteLog(LEVEL_WARN, message)
End Function Public Function debug(message As variant) As Integer
debug = WriteLog(LEVEL_DEBUG, message)
End Function Public Function LogError(message As variant) As Integer 'can't use error as its a reserved word
If message="" Then
'LSI_THREAD_CALLMODULE=11, LSI_THREAD_CALLPROC=10
message = GetThreadInfo(11) & ">" & GetThreadInfo(10) & ": " & _
"Error(" & Err() & "): " & Error() & " at line "& Erl()
End If
LogError = WriteLog(LEVEL_ERROR, message)
End Function Public Function fatal(message As variant) As Integer
fatal = WriteLog(LEVEL_FATAL, message)
End Function 'user level logging, for specific level logging
'@param level integer - the level 10 is the most detail, 1 the lowest level
Public Function WriteLog(level As Integer, message As variant) As Integer
Dim theDate As String
Dim theLevel As String
Dim theMessage As String
theDate = Cstr(Now)
theLevel = "["+GetLevelString(level)+"] "
theMessage = theDate+" "+theLevel+" "+module+" - "+message
' check that logging is turned on for this level
' otherwise there is no need to log
If level <= logLevel Then
Call logFile.writelog(theMessage)
End If
End Function 'closes the log, saves notes doc or closes file
Public Function Close
logFile.close
End Function 'convert from level numbers into string
Private Function GetLevelString(level As Integer) As String
Select Case level
Case LEVEL_INFO : GetLevelString = LEVEL_INFO_STRING
Case LEVEL_DEBUG : GetLevelString = LEVEL_DEBUG_STRING
Case LEVEL_WARN : GetLevelString = LEVEL_WARN_STRING
Case LEVEL_ERROR : GetLevelString = LEVEL_ERROR_STRING
Case LEVEL_FATAL : GetLevelString = LEVEL_FATAL_STRING
Case Else : GetLevelString = "LEVEL "+Cstr(level)
End Select
End Function End Class '/**
'* Set Log destination as a domino database
'*/
Class LogDB
Private m_sess As NotesSession
Private m_dbLog As NotesDatabase 'nsf if destination is db
Private m_docLog As NotesDocument 'document that the log gets appended to
Private m_rtitem As NotesRichTextItem 'rtf
public logName As String Sub New(db As NotesDatabase)
Set m_sess=New NotesSession
If db Is Nothing Then
Set m_dbLog = m_sess.currentdatabase
Else
Set m_dbLog = db
If m_dbLog.isOpen = False Then
Error CUSTOM_ERR, CUSTOM_ERROR & "Could not open the log Database."
End If
End If
End Sub 'get the log document as some calling program may need access it e.g. mail it.
Public Property Get LogDocument As NotesDocument
Set LogDocument=m_docLog
End Property '/**
'* method for logging to a notes document
'*/
Public Function writeLog(message As String) As Integer
If m_docLog Is Nothing Then
' create a new log document
Set m_docLog = m_dbLog.createDocument
Call m_docLog.ReplaceItemValue("LogName",logName)
If m_sess.IsOnServer Then
Call m_docLog.ReplaceItemValue("ScriptRunOn","Server")
Else
Call m_docLog.ReplaceItemValue("ScriptRunOn","Workstation")
End If
Set m_rtitem = New NotesRichTextItem(m_docLog, "logBody")
End If
'currently each log line is in one paragraph, no limits will be violated
m_rtitem.appendtext(message)
m_rtitem.addnewline(1) writeLog= True
End Function '/**
'* closes the log, saves notes doc
'*/
Public Function Close
If Not(m_docLog Is Nothing) Then
m_docLog.Form="log"
Call m_docLog.Save(True,True)
End If
End Function
End Class 'Get a logger instance that writes to the specified db.
Public Function GetLogger(db As NotesDatabase) As log4Dom
Dim logger As log4dom
Set logger = New log4dom()
Dim logFile As New LogDB(db)
Call logger.AddLogFile(logFile)
Set GetLogger=logger
End Function
上述代码的各个方法都有注释。使用的时候像上一篇文章里所示样例一样,只需初始化一个logger实例并添加目标数据库(若为当前数据库,就传入Nothing),之后就可以调用Info()、Debug()、LogError()等各种方法写入日志。传入LogError()方法的如果是空字符串,它就会试图记录最近发生的错误的详细信息,因此可以用作处理错误的语句。最后要调用Close()方法,记录日志的文档才会被保存。
原来版本所具的其他日志目标媒介类,实际上都极少用到。Notes文档和视图的现成功能使其很适宜用来记录和查询日志。文本文件比起来不那么方便,而要写到状态栏或者用对话框显示直接用LotusScript对应的语句即可。
49. 面向对象的LotusScript(十五)之Log4Dom下的更多相关文章
- java 面向对象(二十五):内部类:类的第五个成员
内部类:类的第五个成员 1.定义: Java中允许将一个类A声明在另一个类B中,则类A就是内部类,类B称为外部类.2.内部类的分类:成员内部类(静态.非静态 ) vs 局部内部类(方法内.代码块内.构 ...
- java 面向对象(三十五):泛型在继承上的体现
泛型在继承上的体现: /* 1. 泛型在继承方面的体现 虽然类A是类B的父类,但是G<A> 和G<B>二者不具备子父类关系,二者是并列关系. 补充:类A是类B的父类,A< ...
- How tomcat works 读书笔记十五 Digester库 下
在这一节里我们说说ContextConfig这个类. 这个类在很早的时候我们就已经使用了(之前那个叫SimpleContextConfig),但是在之前它干的事情都很简单,就是吧context里的co ...
- 性能测试十五:liunx下搭建(tomcat+项目+jmete命令行)
单机 准备工作: 1.压力机安装并配置好JDK,输入java和javac验证环境变量 2.上传jmeter到liunx下: 准备好jmeter的压缩包 在第三方工具中对linux文件上传下载(需先装好 ...
- 马凯军201771010116《面向对象与程序设计Java》第十五周学习知识总结
实验十五 GUI编程练习与应用程序部署 一.知识学习部分 清单文件 每个JAR文件中包含一个用于描述归档特征的清单文件(manifest).清单文件被命名为MANIFEST.MF,它位于JAR文件的 ...
- “全栈2019”Java第三十五章:面向对象
难度 初级 学习时间 10分钟 适合人群 零基础 开发语言 Java 开发环境 JDK v11 IntelliJ IDEA v2018.3 文章原文链接 "全栈2019"Java第 ...
- 201271050130-滕江南-《面向对象程序设计(java)》第十五周学习总结
201271050130-滕江南-<面向对象程序设计(java)>第十五周学习总结 博文正文开头格式:(2分) 项目 内容 这个作业属于哪个课程 https://www.cnblogs.c ...
- 201871010111-刘佳华《面向对象程序设计(java)》第十五周学习总结
201871010111-刘佳华<面向对象程序设计(java)>第十五周学习总结 实验十三 Swing图形界面组件(二) 实验时间 2019-12-6 第一部分:理论知识总结 5> ...
- 201871010123-吴丽丽《面向对象程序设计(Java)》第十五周学习总结
201871010123-吴丽丽<面向对象程序设计(Java)>第十五周学习总结 项目 内容 这个作业属于哪个课程 https://www.cnblogs.com/nwnu-daizh/ ...
随机推荐
- java多线程总结一:线程的两种创建方式及优劣比较
1.通过实现Runnable接口线程创建 (1).定义一个类实现Runnable接口,重写接口中的run()方法.在run()方法中加入具体的任务代码或处理逻辑. (2).创建Runnable接口实现 ...
- Spread 之自定义对角线cellType源码: DiagonalCellType
最新的SpreadWinform提供了多达24种CellType类型,下面的这2篇博文对新增了GcTextBoxCellType和GcDateTimeCellType单元格格式做了比较详细的说明. & ...
- ios 获取字符串所需要占用的label的高度
// 设置字体大小 UIFont *fnt=[UIFont systemFontOfSize:16]; NSDictionary *attribute = @{NSFontAttributeNa ...
- 【html】【8】div布局[子div在父div居底]
从今天起 开始细话div布局 思路及要点: 父div的位置设置成相对的,即“position: relative;”. 而子div的位置设置成绝对的,并且下边缘设为0,即“position: ab ...
- 01顺序栈_Stack---(栈与队列)
#include "stdio.h" #include "stdlib.h" #include "io.h" #include " ...
- sea.js总结
SeaJS是一个遵循CommonJS规范的JavaScript模块加载框架. 参考以下网址进行详细学习: https://segmentfault.com/a/1190000000357191?pag ...
- Java多线程的安全问题
/*多线程的安全问题1.为什么会出现安全问题?因为程序在运行时,会出现一个线程在判断条件满足后,具备了执行资格,但没有运行代码后一个线程也判断了条件,也具备了执行资格,后一个线程运行了代码,但这时候, ...
- OpenJudge/Poj 1753 Flip Game
1.链接地址: http://bailian.openjudge.cn/practice/1753/ http://poj.org/problem?id=1753 2.题目: 总时间限制: 1000m ...
- OpenJudge 2980 大整数乘法
链接地址:http://bailian.openjudge.cn/practice/2980/ 题目: 总时间限制: 1000ms 内存限制: 65536kB 描述 求两个不超过200位的非负整数的积 ...
- Google设计理念
Google的十大信条 我们首次拟就这“十大信条”还是在Google刚刚成立没几年的时候.此后,我们时常重新审视这份清单,看看它是否依然适用.我们希望这些信条永不过时,而您也可以监督我们是否遵守了这些 ...