0

以下 python 2.5 脚本有效,但由于我是初学者,我想知道是否有任何明显的错误,或者是否有更好的方法来实现我想要实现的目标?

目的是打开当天的日志 - '/Library/Application Support/Perceptive Automation/Indigo 5/Logs/' 并提取包含错误一词的行并仅通过电子邮件发送新错误。提取错误行后,将计算 ( prenumLines) 中的行数tmp.txt。然后将提取的行写入tmp.txt文件并再次计算行数 ( postnumLines)。大于 的行号prenumLines将打印到“theBody”并通过电子邮件发送。

from datetime import date
import linecache

fileDate = str(date.today())

theBody = []

tmpFile = open('/Library/Application Support/Perceptive Automation/Indigo 5/Logs/tmp.txt')

prenumLines = sum(1 for line in tmpFile)

log= open( '/Library/Application Support/Perceptive Automation/Indigo 5/Logs/' + fileDate + ' Events.txt', 'r' )

tmpFile = open('/Library/Application Support/Perceptive Automation/Indigo 5/Logs/tmp.txt', 'w')

for line in log:
    if 'Error' in line: 
    tmpFile.write(line )
log.close()
tmpFile.close() 

postnumLines = sum(1 for line in open('/Library/Application Support/Perceptive Automation/Indigo 5/Logs/tmp.txt'))

lineNum  = prenumLines

while lineNum < postnumLines:
    theBody.append(linecache.getline( '/Library/Application Support/Perceptive Automation/Indigo 5/Logs/tmp.txt', lineNum + 1) )
    lineNum = lineNum + 1
tmpFile.close() 

theBody =  "".join(theBody)  

#theBody is the body of  an email which is sent next
#print theBody
4

2 回答 2

0

根据我的经验,您确实应该考虑进行一些更改(我使用must,但这仍然只是一个建议),还有一些更符合我个人风格的更改(我使用should)。

在元级别上:您的问题最初仅被标记为,这可能是它没有得到任何关注的原因,您必须使用在 SO 上有更多追随者的

不能在文件中使用 TAB 和空格字符。因此,您的来源实际上在 SO 上的缩进不正确。行: tmpFile.write(line)应该在if它上面的语句下面缩进一级。

不能四次使用相同的字符串作为文件名,将其替换为变量。并使用从公共基目录创建该变量os.path.join()

应该考虑遵循PEP8的 Python 风格指南。

如果您第一次尝试,您的程序将不会运行,因为“tmp.txt”不存在。以 0 的 prenumLines 优雅地失败(但是我根本不再使用它,见下文):

try:
    # open the file
    # count the lines
except:
    prenumLines = 0

我实际上想知道您是否声明您的代码有效,因为您覆盖tmp.txt并仅写入最后一次登录的错误行。当你tmpFile再次分配到的那一刻,第一个开放阅读就关闭了。然后关闭tmpFile打开的两次写入(Python 不会抛出错误)。如果昨天的日志有一个错误,今天有三个,您的电子邮件将只显示两行。要附加到文件,请使用 open(filename, 'a')

应该考虑使用with语句(Python 2.5 中的新语句),这样就可以省去(错误.close()语句)。

应该考虑创建theBody为字符串并附加行。首先使用列表并加入它们可能会更快,但此脚本每天只运行一次。

无需计算行数,而是附加错误行,然后重新读取它们并将它们存储在 中theBody,您应该省去第一部分和第三部分,一次完成所有操作:

from __future__ import with_statement

import os
from datetime import date

baseDir = '/Library/Application Support/Perceptive Automation/Indigo 5/Logs'
tmpFileName = os.path.join(baseDir, 'tmp.txt')

fileDate = str(date.today())
eventFileName = os.path.join(baseDir, fileDate + ' Events.txt')

theBody = ''

with open(tmpFileName, 'a') as tmpFile:
    with open( eventFileName, 'r' ) as log:
        for line in log:
            if 'Error' in line:
                tmpFile.write(line)
                theBody += line

# theBody is the body of  an email which is sent next
print theBody
于 2013-03-23T07:22:43.237 回答
0

Anthon - 再次感谢您抽出宝贵时间回复。生成日志的软件是 Perceptive Automation Indigo,一个家庭自动化程序。它使用每天生成的新日志不断地写入日志。我设置 python 脚本每 10 分钟解析一次日志并查找错误,然后通过电子邮件将它们发送给我。我面临的挑战是只将新错误通过电子邮件发送给我,并避免以前发送的错误。我这样做的方法是计算 tmp.text 中的行数,然后添加新的错误,如果之前写过任何错误,它们将被覆盖,正如你提到的。因此,如果 tmp.txt 中有 5 行并添加了 3 行,它只会向我发送 3 个新行。我做了一些您建议的更改,即使用 with 语句缩短了脚本并摆脱了 close 语句。我还用变量替换了文件名。完成此操作后,脚本运行良好,但由于软件设计的原因,我无法使用包含“with statements”的脚本。我现在必须重写脚本以删除 with 语句。你帮了我很大的忙,我非常感谢你。

于 2013-03-26T12:57:14.413 回答