Solved

Script to regularily check .txt document and send email if certain words appear

Posted on 2012-03-19
10
215 Views
Last Modified: 2014-07-26
We have a service that writes updates into a log .txt file.

I was wondering how to

A schedule a script to run every hour to
B check for certain words, ie fail, shutdown, and
C email if those words appear.

I'm quite new to scripting so please explain at an easy level if possible.
0
Comment
Question by:DavidSelby
  • 4
  • 3
10 Comments
 
LVL 10

Assisted Solution

by:Alan_White
Alan_White earned 250 total points
ID: 37738499
Hi David,

A) is straight forward, use Windows Task Scheduler to kick off the script every hour.
B) is not difficult either.  It's basically read the contents of the file, do and INSTR on the contents and then call the email bit.
c) CAN be more troublesome.  There are lots of code snippets out there for emailing from VBScript, I've had mixed results and have had to make changes to scripts when there have been infrastructure changes to the email environment in my organisation.  When you get one that works, you will be fine but finding that can be problematic.

A can have a crack at a script for you but my experience of EE is that someone will be along and post a fully working script before I can open an editor and get a FileSystemObject created.  But I'll keep an eye on this question and if a solution is not forthcoming, I'll get to work.

Can you tell us what kind of email infrastructure you have?  (eg Exchange 2007)
0
 
LVL 10

Expert Comment

by:Alan_White
ID: 37738615
Actually, I've just knocked up a very quick script for "B".  As you can hopefully see, I've left out the email bit, it just echo's it to screen at the moment.

You need to specify the path in the cInputFile line and you can add or change the keywords with the dKeyWords dictionary.

Having knocked this up, it has made me wonder about your specification.  Is it enough to know that one of your keyword is somewhere is the file or do you want a nearby chuck on log inculded in the email?  How should the script handle subsequent passes? Multiple instances of the same keyword?

Option Explicit

Dim dKeyWords
Set dKeyWords = CreateObject("Scripting.Dictionary")
dKeyWords.add "error", ""
dKeyWords.add "fault", ""

Const cInputFile = "C:\dev\EEPollFileForText\inputfile.txt"
Const forReading = 1

Dim oFSO, oFile, sContentsOfFile, dictionaryItem

Set oFSO = CreateObject("Scripting.FileSystemObject")
If oFSO.FileExists(cInputFile) Then
	Set oFile = oFSO.OpenTextFile(cInputFile, forReading)
	sContentsOfFile = oFile.ReadAll
	sContentsOfFile = LCase(sContentsOfFile)
	For Each dictionaryItem In dKeyWords
		If InStr(1,sContentsOfFile,LCase(dictionaryItem),vbTextCompare) <> 0 Then
			email "Found the word " & dictionaryItem & " in " & cInputFile
		End If
	Next
Else
	email "Input file not found!"
End If


Sub email(sText)
	WScript.Echo sText
End Sub

Open in new window

0
 
LVL 65

Expert Comment

by:RobSampson
ID: 37739939
Hi, I've added my email sub to your code.

Regards,

Rob.

Option Explicit

' Email variables:
Dim strServer, strTo, strFrom, strSubject, strBody
strServer = "mailhost.abc.com"
strTo = "john.doe@abc.com"
strFrom = "john.doe@abc.com"
strSubject = "Subject Here"
strBody = "This is the body:" & vbCrLf

Dim dKeyWords
Set dKeyWords = CreateObject("Scripting.Dictionary")
dKeyWords.add "error", ""
dKeyWords.add "fault", ""

Const cInputFile = "C:\dev\EEPollFileForText\inputfile.txt"
Const forReading = 1

Dim oFSO, oFile, sContentsOfFile, dictionaryItem

Set oFSO = CreateObject("Scripting.FileSystemObject")
If oFSO.FileExists(cInputFile) Then
	Set oFile = oFSO.OpenTextFile(cInputFile, forReading)
	sContentsOfFile = oFile.ReadAll
	sContentsOfFile = LCase(sContentsOfFile)
	For Each dictionaryItem In dKeyWords
		If InStr(1,sContentsOfFile,LCase(dictionaryItem),vbTextCompare) <> 0 Then
			SendEmail strServer, strTo, strFrom, "Words found in text file", "Found the word " & dictionaryItem & " in " & cInputFile, ""
		End If
	Next
Else
	SendEmail strServer, strTo, strFrom, "Text file not found", oInputFile & " was not found!"
End If

Sub SendEmail(strServer, strTo, strFrom, strSubject, strBody, strAttachment)
        Dim objMessage
        
        Set objMessage = CreateObject("CDO.Message")
        objMessage.To = strTo
        objMessage.From = strFrom
        objMessage.Subject = strSubject
        objMessage.TextBody = strBody
  		If strAttachment <> "" Then objMessage.AddAttachment strAttachment
  		
        '==This section provides the configuration information for the remote SMTP server.
        objMessage.Configuration.Fields.Item("http://schemas.microsoft.com/cdo/configuration/sendusing") = 2
        'Name or IP of Remote SMTP Server
        objMessage.Configuration.Fields.Item("http://schemas.microsoft.com/cdo/configuration/smtpserver") = strServer
        'Server port (typically 25)
        objMessage.Configuration.Fields.Item("http://schemas.microsoft.com/cdo/configuration/smtpserverport") = 25      
        objMessage.Configuration.Fields.Update
        '==End remote SMTP server configuration section==
 
        objMessage.Send
        Set objMessage = Nothing
End Sub

Open in new window

0
Master Your Team's Linux and Cloud Stack!

The average business loses $13.5M per year to ineffective training (per 1,000 employees). Keep ahead of the competition and combine in-person quality with online cost and flexibility by training with Linux Academy.

 
LVL 65

Expert Comment

by:RobSampson
ID: 37739942
One thing you might want to do though, rather than email for *each* word found, is toggle a flag so that you can email only once if *any* word is found....let me know if you want that, and I'll adjust it for you.

Regards,

Rob.
0
 

Author Comment

by:DavidSelby
ID: 37758804
Hi Alan and Rob

Thanks for your reply, sorry its taken me a while to look at it, This is really helpful and definitly along the right lines

Our log gets automatically truncated when it gets long enough, and I dont wan't to interfere with that process. It happens every few days.

With that in mind is it possible to have the script check the timestamp for the line and compare that to the current system time so that its only looking at the last 2 hours?

timestamp format is: 2012-03-23 19:00:37.

If you guys can get it to do that, Im pretty sure that will meet my needs.

Many thanks

Dave
0
 
LVL 65

Accepted Solution

by:
RobSampson earned 250 total points
ID: 37764375
Is the timestamp included at the start of every line, like
[2012-03-23 19:00:37] some message is written here

This also complicates things in that instead of reading the entire file at once, and looking for the words, you would need to read each line, and test it, and send an email.

Anyway, I think I've covered that scenario with this code.

Regards,

Rob.

Option Explicit

' Email variables:
Dim strServer, strTo, strFrom, strSubject, strBody
strServer = "mailhost.abc.com"
strTo = "john.doe@abc.com"
strFrom = "john.doe@abc.com"
strSubject = "Subject Here"
strBody = "This is the body:" & vbCrLf

Dim strTimeStamp
Dim dKeyWords
Set dKeyWords = CreateObject("Scripting.Dictionary")
dKeyWords.add "error", ""
dKeyWords.add "fault", ""

Const cInputFile = "C:\dev\EEPollFileForText\inputfile.txt"
Const forReading = 1

Dim oFSO, oFile, sLine, dictionaryItem, blnFound

blnFound = False
Set oFSO = CreateObject("Scripting.FileSystemObject")
If oFSO.FileExists(cInputFile) Then
	Set oFile = oFSO.OpenTextFile(cInputFile, forReading)
	While Not oFile.AtEndOfStream
		sLine = oFile.ReadLine
		For Each dictionaryItem In dKeyWords
			If InStr(1,sLine,LCase(dictionaryItem),vbTextCompare) <> 0 Then
				If Left(sLine, 1) = "[" Then
					strTimeStamp = Mid(sLine, 2)
					strTimeStamp = Left(sLine, InStr(sLine, "]") - 1)
					If DateDiff("n", DateAdd("h", -2, Now), strTimeStamp) < 120 Then
						strBody = strBody & "Found the word " & dictionaryItem & " in " & cInputFile & vbCrLf
						blnFound = True
					End If
				End If
			End If
		Next
	Wend
	oFile.Close
	If blnFound = True Then SendEmail strServer, strTo, strFrom, "Words found in text file", strBody, ""
Else
	SendEmail strServer, strTo, strFrom, "Text file not found", oInputFile & " was not found!"
End If

Sub SendEmail(strServer, strTo, strFrom, strSubject, strBody, strAttachment)
        Dim objMessage
        
        Set objMessage = CreateObject("CDO.Message")
        objMessage.To = strTo
        objMessage.From = strFrom
        objMessage.Subject = strSubject
        objMessage.TextBody = strBody
  		If strAttachment <> "" Then objMessage.AddAttachment strAttachment
  		
        '==This section provides the configuration information for the remote SMTP server.
        objMessage.Configuration.Fields.Item("http://schemas.microsoft.com/cdo/configuration/sendusing") = 2
        'Name or IP of Remote SMTP Server
        objMessage.Configuration.Fields.Item("http://schemas.microsoft.com/cdo/configuration/smtpserver") = strServer
        'Server port (typically 25)
        objMessage.Configuration.Fields.Item("http://schemas.microsoft.com/cdo/configuration/smtpserverport") = 25      
        objMessage.Configuration.Fields.Update
        '==End remote SMTP server configuration section==
 
        objMessage.Send
        Set objMessage = Nothing
End Sub

Open in new window

0
 
LVL 10

Expert Comment

by:Alan_White
ID: 37764640
Nice one Rob.  Beat me to it.  I'm only an expert Monday to Friday :-)
0
 
LVL 65

Expert Comment

by:RobSampson
ID: 37768231
No problem. Yesterday was Monday for me, so I'm ahead of you!  It's bright and early Tuesday morning here now....the sun's not even up yet !!  How sad :-(
0

Featured Post

Master Your Team's Linux and Cloud Stack

Come see why top tech companies like Mailchimp and Media Temple use Linux Academy to build their employee training programs.

Question has a verified solution.

If you are experiencing a similar issue, please ask a related question

Suggested Solutions

In this tutorial I will show you how to provide a dynamic RTF document on your website generated with data from your database. For this tutorial you will need Microsoft Word or WordPad, WhizBase and Microsoft Access. In this tutorial I will show …
It is a general practice to get rid of old user profiles on a computer  in a LAN environment. As I have been working with a company in a LAN environment where users move from one place to some other place at times. This will make many user profil…
Learn the basics of strings in Python: declaration, operations, indices, and slicing. Strings are declared with quotations; for example: s = "string": Strings are immutable.: Strings may be concatenated or multiplied using the addition and multiplic…
The viewer will learn how to count occurrences of each item in an array.

777 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question