【问题标题】:Daemon Output not being written to a TXT守护程序输出未写入 TXT
【发布时间】:2016-02-10 09:06:15
【问题描述】:

我有一个从守护程序服务器调用函数的脚本。守护程序服务器每次完成其工作时都会生成一个输出。守护进程主要从外部服务器下载文件。守护程序源代码已关闭(由外部公司编码)。

文件下载完成后的守护进程输出示例:

Saved to /home/ubuntu/Daemon/downloads/download_1024000003.pdf

我正在使用的脚本从 TXT 文件中获取下载的 ID,从用户字段中获取 PC 的用户名,并将它们放在一个数组中,然后从守护进程中调用它们获取文件,然后在 a 中写入日志txt 文件。

日志样本应该是:

Documnent ID= 3
From User = DomainCon
Saved to /home/ubuntu/Daemon/downloads/download_1024000003.pdf

我面临的问题是 Saved to /home/ubuntu/Daemon/downloads/download_1024000003.pdf 守护程序服务器在每次下载完成时生成的文件有时会在 TXT 中丢失。 p>

问题示例:

Documnent ID= 2
From User = DomainCon
Documnent ID= 3
In Chat = DomainCon
ANSWER 78
Saved to /home/ubuntu/Daemon/downloads/download_1024000003.pdf

日志文件中的输出应该是:

Documnent ID= 2
From User = DomainCon
ANSWER 96
Saved to /home/ubuntu/Daemon/downloads/download_1024000002.pdf
Documnent ID= 3
In Chat = DomainCon
ANSWER 78
Saved to /home/ubuntu/Daemon/downloads/download_1024000003.pdf

这是我正在使用的脚本,包括 cmets:

for i in range(len(ids)):\\ ids is the array that contains the documents that should be downloaded.
       cmdping = "sleep 5; echo load_document "+ids[i][0]+"| nc -w 4 127.0.0.1 1234 | tee >> "+logtxt \\ Perpare the Echo  command to the daemon to start the download tee to save the output of the daemon into the log text
       print("\033[1;31m~~~Documnent~~~NB~~~"+str(i+1)+"\033[1;m")
       print ("Documnent ID= "+ids[i][0])\\ Just Print on screen for Debbuging Purpose
       print ("From User= "+ids[i][1])\\Just Print on screen for Debbuging Purpose
       logfile = open(logtxt, "a") \\ Open the TXT where the log is gonna be saved.
       logfile.write("Documnent ID= "+ids[i][0]+"\n")\\Write the Document ID in the File.
       logfile.write("From User = "+ids[i][1]+"\n")\\\\Write the From User in the File.
       logfile.close()\\Close the logfile
       if (i==len(ids)-1):
          p=subprocess.Popen(cmdping, shell=True, stderr=subprocess.PIPE)\\ Start the proccess that was prepared before.
          #time.sleep(1)
          check=""
          s=1
          skip=0
          while (s==1):
              check=checkfile(srcdir)
              if (check!="no"):
                 s=2
              if(check=="skip"):
                 skip=1
          if(skip!=1):
             if(checksize(srcdir+check) == "done"):
                print(check+"\n \033[1;32mFinished Downloading moving to the next download\033[1;m")
          p.terminate()
          user_dir=rootdir+"/document/"+ids[i][1];
          checkandcopy(download,user_dir)

【问题讨论】:

  • 这可能是竞争条件吗?如果checkfile() 和/或checksize()在您的守护程序写入文件之前返回预期值,然后它在写入日志之前被p.terminate() 终止,该怎么办? “有时有效,有时无效”听起来像是典型的竞争条件行为......
  • 守护程序一旦开始下载就创建一个文件,检查文件检查文件是否创建如果没有检查文件返回跳过,因为文件有时在服务器上不可用,那么守护程序返回ID无效,如果文件可用检查大小获取检查文件位置并继续检查文件是否变大(按大小)当它停止变大时它返回 2 打破循环然后终止进程,你建议我添加一个计时器.sleep 循环退出后?
  • cmdping 不应该在nc 连接的另一端关闭后自行退出?如果没有,sleep 可能对您有用,但这本身并不能真正解决竞争条件。例如如果您的网络出现问题,文本可能会在文件完成后很长时间才会出现,并且可能比您的 sleep...
  • 另一端 NC 永远不会关闭它是一个 24/7 持续运行的守护进程,是的,我认为问题出在网络掉线......你知道我该如何解决这个问题吗?

标签: python linux ubuntu


【解决方案1】:

您可以考虑改用套接字。这里有一些灵感:

import re
import socket
for i, (doc_id, user) in enumerate(ids):
    s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
    print("\033[1;31m~~~Documnent~~~NB~~~"+str(i+1)+"\033[1;m")
    s.connect(('127.0.0.1', 1234))
    s.sendall('load_document {}\n'.format(doc_id))
    buf = []
    while True:
        r = s.recv(4096).strip()
        print('Got {} for socket'.format(r))
        buf.append(r)
        if r.endswith('.pdf'):
            print('Done')
            break
    result = '\n'.join(buf)
    s.close()
    with open(logtxt, 'a') as f:
        f.write('Document ID= {}\n'.format(doc_id))
        f.write('From User = {}\n'.format(user))
        f.write('{}\n'.format(result))
    filename = re.search('Saved to (.+)$', result).group(1)
    checkandcopy(filename, userdir)

【讨论】:

  • 能否请您稍微解释一下代码,我对python上的socketing不熟悉,谢谢。
  • 文件可以是任何格式,而不仅仅是 PDF,无论如何我认为我可以修复这部分。
  • @Z.Kiwan 我把你的代码中的nc ... | tee 部分用python 代替了。 s.connect 连接,sendall 发送 load document 命令,recv(4096).strip() 从连接中获取输出。 Strip 通常会删除任何过多的空格和换行符。当您收到预期的内容(例如以 .pdf 或类似结尾的行)时,请关闭连接并将输出写入 logtxt。
  • 对不起,我错过了这里的理解,s.recv(4096).strip() 只是“保存到 blablabla.pdf”,而不是真正的 PDF,对吗?因为当你发送命令 load_document 将守护进程自动下载数据保存到 /home/ubuntu/Daemon/downloads/ 我无法更改此路径,你怎么知道下载完成?
  • 它没有。当您向其写入“加载文档”时,它只会读取服务器写回的内容。
猜你喜欢
  • 2011-10-06
  • 2015-03-27
  • 2012-10-08
  • 2019-02-09
  • 2014-04-13
  • 2010-09-16
  • 1970-01-01
  • 2019-08-13
  • 2013-11-17
相关资源
最近更新 更多