我正在编写一个(批处理文件或VBScript)来很好地关闭Windows服务器上所有正在运行的WebSphere JVM,但需要一些文本处理方面的帮助。我希望脚本运行并解析“serverstatus”命令的输出,以获取框中 应用程序服务器 的名称,并存储匹配项(带回车符)用于脚本其余部分的变量。
示例命令输出:
C:\WebSphere\AppServer\bin>serverstatus -all
ADMU0116I: Tool information is being logged in file
C:\WebSphere\AppServer\profiles\MySrv01\logs\serverStatus.log
ADMU0128I: Starting tool with the MySrv01 profile
ADMU0503I: Retrieving server status for all servers
ADMU0505I: Servers found in configuration:
ADMU0506I: Server name: MyCluster_MySrv01
ADMU0506I: Server name: MyCluster_MySrv01_1
ADMU0506I: Server name: MyNextCluster_MySrv04
ADMU0506I: Server name: MyNextCluster_MySrv04_1
ADMU0506I: Server name: nodeagent
ADMU0508I: The Application Server "MyCluster_MySrv01" is STARTED
ADMU0508I: The Application Server "MyCluster_MySrv01_1" is STARTED
ADMU0508I: The Application Server "MyNextCluster_MySrv04" is STARTED
ADMU0509I: The Application Server "MyNextCluster_MySrv04_1" cannot be
reached. It appears to be stopped.
ADMU0508I: The Node Agent "nodeagent" is STARTED
* nodeagent不应该匹配。对于我是否要针对所有应用服务器或只是那些状态为“已启动”的应用服务器,评审团仍然没有考虑。
答案 0 :(得分:1)
使用RegExp切断输入中的引用名称;添加上下文 - 服务器,已启动 - 微调结果集。在代码中:
Option Explicit
Function q(s) : q = "'" & s & "'" : End Function
Dim sInp : sInp = Join(Array( _
"ADMU0116I: Tool information is being logged in file C:\WebSphere\AppServer\profiles\MySrv01\logs\serverStatus.log" _
, "ADMU0128I: Starting tool with the MySrv01 profile" _
, "ADMU0503I: Retrieving server status for all servers" _
, "ADMU0505I: Servers found in configuration:" _
, "ADMU0506I: Server name: MyCluster_MySrv01" _
, "ADMU0506I: Server name: MyCluster_MySrv01_1" _
, "ADMU0506I: Server name: MyNextCluster_MySrv04" _
, "ADMU0506I: Server name: MyNextCluster_MySrv04_1" _
, "ADMU0506I: Server name: nodeagent" _
, "ADMU0508I: The Application Server ""MyCluster_MySrv01"" is STARTED" _
, "ADMU0508I: The Application Server ""MyCluster_MySrv01_1"" is STARTED" _
, "ADMU0508I: The Application Server ""MyNextCluster_MySrv04"" is STARTED" _
, "ADMU0509I: The Application Server ""MyNextCluster_MySrv04_1"" cannot be reached. It appears to be stopped." _
, "ADMU0508I: The Node Agent ""nodeagent"" is STARTED" _
), vbCrLf)
Dim aRes : aRes = Array( _
Array("all quoted names", """([^""]+)""") _
, Array("all quoted started servers", "Server ""([^""]+)"" is STARTED") _
)
Dim aRE
For Each aRe In aRes
WScript.Echo "----------------", q(aRe(0)), q(aRe(1))
Dim re : Set re = New RegExp
re.Global = True
re.Pattern = aRe(1)
Dim oMTS : Set oMTS = re.Execute(sInp)
ReDim a(oMTS.Count - 1)
Dim i
For i = 0 To UBound(a)
a(i) = q(oMTS(i).SubMatches(0))
Next
WScript.Echo " =>", Join(a)
Next
输出:
cscript 20984738.vbs
---------------- 'all quoted names' '"([^"]+)"'
=> 'MyCluster_MySrv01' 'MyCluster_MySrv01_1' 'MyNextCluster_MySrv04' 'MyNextCluster_MySrv04_1' 'nodeagent'
---------------- 'all quoted started servers' 'Server "([^"]+)" is STARTED'
=> 'MyCluster_MySrv01' 'MyCluster_MySrv01_1' 'MyNextCluster_MySrv04'
答案 1 :(得分:1)
这是使用Regex的替代方法。它只是读取stdout并处理所有已启动的应用服务器 - 应用服务器存储在名为AppServers的数组中。在W2K3上测试过。 编辑:我们添加了一种方法,通过添加日志写入函数将输出记录到文件中(不要忘记在我们刚刚添加到此答案的脚本开头添加const ForAppending)。日志写入功能采用以下格式:
Logwrite "some text to write - delete file if exists", "c:\Path\filename.txt", 1
Logwrite "some text to write - append to file, don't delete", "c:\path\filename.txt", 0
这是一个粗略的功能,但你做的是什么。我希望有所帮助。 :)
option explicit
Const ForAppending = 8
Dim objShell, objWshScriptExec, objStdOut
Dim objCmdString, strLine, appServers(), maxAppServers
Dim x
' File Path / Location to serverstatus.bat ----
objCmdString = "C:\WebSphere\AppServer\bin\serverstatus.bat -all"
Set objShell = CreateObject("WScript.Shell")
Set objWshScriptExec = objShell.Exec(objCmdString)
Set objStdOut = objWshScriptExec.StdOut
MaxAppServers = -1
' While we're looping through the response from the serverstatus command, look for started application servers
' and store them in an ever expanding array AppServers.
' The Variable MaxAppServers should always contain the highest number of AppServers (ie: ubound(AppServers))
While Not objStdOut.AtEndOfStream
strLine = objStdOut.ReadLine
If InStr(LCase(strLine), "admu0508i: the application server """) Then
MaxAppServers = MaxAppServers + 1
ReDim Preserve AppServers(MaxAppServers)
AppServers(MaxAppServers) = wedge(strLine, Chr(34))
End If
Wend
If MaxAppServers => 0 then
For x = 0 To ubound(AppServers) ' You could just use For x = 1 to MaxAppServers in this case.
' Add your instructions here.........
' ... We are simply echoing out the AppServer name below as an example to a log file as requested below.
Logwrite AppServers(x), "c:\Output.log", 0
Next
End If
Function Wedge(wStr, wOpr)
' This clunky function simply grabs a section of a string the is encapsulated by wOpr.
' NOTE: This function expects wOpr to be a single character (eg; for our purpose, it is pulling data between double quotes).
Dim wFlag, wCount, wFinish
wflag = False
wFinish = False
wCount = 1
Wedge = ""
Do Until wCount > Len(wStr) Or wFinish
If Mid(wStr, wCount, 1) = wOpr Then
If wFlag Then
wFinish = True
Else
wFlag = True
End If
Else
If wFlag Then Wedge = Wedge & Mid(wStr, wCount, 1)
End If
wCount = wCount + 1
Loop
End Function
Function logwrite (lstrtxt, lwLogfile, lwflag)
Dim lwObjFSO, lwObjFile, fstr, lwcounter, lwc
fstr = lstrtxt
Set lwObjFSO = CreateObject("Scripting.FileSystemObject")
If lwflag=1 And lwObjFSO.FileExists(lwLogFile) Then lwObjfso.deletefile(lwLogFile)
If lwObjFSO.FileExists(lwLogFile) then
On Error Resume next
Set lwObjFile = lwObjFSO.OpenTextFile(lwLOgFile, ForAppending)
lwCounter = 20000
Do While Err.number = 70 And lwCounter > 0
wscript.echo "ERROR: Retrying output - Permission denied; File may be in use!"
For lwc = 1 To 1000000
Next
Err.clear
Set lwObjFile = lwObjFSO.OpenTextFile(lwLogFile, ForAppending)
lwCounter = lwCounter-1
Loop
If Err.number <> 0 Then
wscript.echo "Error Number: "&Err.number
wscript.quit
End If
On Error goto 0
Else
Set lwObjFile = lwObjFSO.CreateTextFile(lwLogFile)
End If
wscript.echo (fstr)
lwObjFile.Write (fstr) & vbcrlf
lwObjFile.Close
Set lwObjFSO=Nothing
Set lwObjfile=Nothing
End Function