Option Public Option Declare Sub Initialize %REM This agent demonstrates how to use the "-xml" option when calling a Domino 6 console command (this option will return the data in XML format) and then parse the XML to display it in your own custom format. I'm simply iterating through the XML nodes here, but if you're clever you could use XSLT for the transformation as well. If you're running this as a local agent, just to see what happens, you need to have "Full Remote Console Administrators" privileges on the server you are running against. If this is an agent that is running on a server, and is making calls to the local server to get console command output, then the user who signs the agent must have "Run unrestricted methods and operations" rights, and the agent must have a runtime security level of at least "2. Allow restricted operations". Also, this example just outputs the nodes in an HTML bullet list format; however, there are several libraries that are available on the Internet to easily convert a bulleted list to something more visually appealing, like a tree view or a menu of some sort. For example, here's an easy tree control to implement: http://www.silverstripe.com/downloads/tree/ I just downloaded and unzipped "tree.zip", copied the "tree" folder to the /data/domino/html directory on my server, renamed it as "silvertree", and referenced it in the output (see the 2 lines that are commented out at the bottom of the Initialize section of this agent). Anyway, once you have the data as parsable XML, you can do anything you'd like to with it. Be creative. Julian Robichaux http://www.nsftools.com version 1.0 -- 29 June 2006 %END REM Dim session As New NotesSession Dim serverName As String Dim commandString As String Dim returnString As String '** call the console command on the selected server, using the "-xml" switch '** to return the output as XML serverName = "" commandString = "show tasks -xml" returnString = session.SendConsoleCommand(serverName, commandString) '** if we got some output, try to process it as XML Dim inputStream As NotesStream Dim outputStream As NotesStream Dim domParser As NotesDOMParser Dim docNode As NotesDOMDocumentNode Dim taskNode As NotesDOMNode Dim taskdataNode As NotesDOMNode Dim taskName As String Dim taskDesc As String Dim taskAddinName As String Dim taskPid As String Dim taskTid As String Dim taskList List As String Dim pidtid As String Dim crlf As String crlf = Chr(13) & Chr(10) '** load it up into a DOM parser Set inputStream = session.CreateStream Call inputStream.WriteText(returnString) inputStream.Position = 0 Set outputStream = session.CreateStream Set domParser=session.CreateDOMParser(inputStream, outputStream) domParser.Process '** all of the tasks should be contained within a single <tasks> '** node, as separate <taskdata></taskdata> entries. Set docNode = domParser.Document '** find the <tasks> node Set taskNode = findChildNode(docNode, "tasks") '** if we didn't find anything, tell the user and exit If (taskNode.IsNull) Then Print "Sorry, I didn't find any <task> nodes. Here's what I found:<p><hr><p>" Print "<pre>" & returnString & "</pre>" Exit Sub End If '** if we did find the <task> node, get data from each of the <taskdata> nodes Set taskdataNode = taskNode.FirstChild Do Until (taskdataNode.IsNull) If (taskdataNode.NodeType = DOMNODETYPE_ELEMENT_NODE) And _ (taskdataNode.NodeName = "taskdata") Then taskName = getNodeText(findChildNode(taskdataNode, "name")) taskDesc = getNodeText(findChildNode(taskdataNode, "description")) taskAddinName = getAttributeText(taskdataNode, "addin") taskPid = getAttributeText(taskdataNode, "pid") taskTid = getAttributeText(taskdataNode, "tid") If (taskAddinName <> "") Then taskName = taskName & " (" & taskAddinName & ")" End If '** set this to "" if you don't care about the process ID and task ID pidtid = "<ul><li>pid: " & taskPid & "</li><li>tid: " & taskTid & "</li></ul>" '** I'm doing quite a bit of formatting here -- obviously you can '** do whatever you want with the data. One interesting thing to '** try would be loading it all up into a custom Class or Type, '** and working with it later. It's easier to do the formatting right '** here in this case, since we're aggregating values. taskList(taskName) = taskList(taskName) & "<li class='closed'>" & taskDesc & _ pidtid & "</li>" & crlf End If Set taskdataNode = taskdataNode.NextSibling Loop '** maybe use a tree control like http://www.silverstripe.com/downloads/tree/ '** to make the resulting list look prettier... 'Print |<link rel="stylesheet" type="text/css" media="all" href="/silvertree/tree.css" />| 'Print |<script type="text/javascript" src="/silvertree/tree.js"></script>| '** in any case, here's our tree If (serverName = "") Then Dim sname As New NotesName(session.CurrentDatabase.Server) serverName = sname.Abbreviated End If Print |<ul class='tree'><h3>Task List for Server | & serverName & |</h3>| Forall task In taskList Print "<li class='closed'><b>" & Listtag(task) & "</b>" & crlf & "<ul>" & task & "</ul></li>" End Forall Print |</ul>| End Sub Function getNodeText (node As NotesDOMNode) As String '** get the text of the given node Dim child As NotesDOMNode Dim childText As String If (node Is Nothing) Then Exit Function Elseif (node.IsNull) Then Exit Function End If Set child = node.FirstChild Do Until (child.IsNull) If (child.NodeType = DOMNODETYPE_TEXT_NODE) Then childText = childText + child.NodeValue Elseif (child.NodeType = DOMNODETYPE_CDATASECTION_NODE) Then childText = childText + child.NodeValue End If Set child = child.NextSibling Loop getNodeText = childText End Function Function getAttributeText (node As NotesDOMNode, attrName As String) As String '** get the text of a given attribute Dim attrList As NotesDOMNamedNodeMap Dim attr As NotesDOMNode Dim attrValue As String Dim i As Integer If (node Is Nothing) Then Exit Function Elseif (node.IsNull) Then Exit Function End If Set attrList = node.Attributes For i = 1 To attrList.NumberOfEntries Set attr = attrList.GetItem(i) If (attr.NodeName = attrName) Then attrValue = attr.NodeValue End If Next getAttributeText = attrValue End Function Function findChildNode (node As NotesDOMNode, childName As String) As NotesDOMNode '** get the first child node with the given name Dim child As NotesDOMNode If (node Is Nothing) Then Exit Function Elseif (node.IsNull) Then Exit Function End If Set child = node.FirstChild Do Until (child.IsNull) If (child.NodeName = childName) Then Exit Do End If Set child = child.NextSibling Loop Set findChildNode = child End Function
This LotusScript was converted to HTML using the ls2html routine,
provided by Julian Robichaux at nsftools.com.