当守护程序= True时,通过Thread删除并替换Windows Service。应该行吗?!
不到一年前,我使用Python 2.7
和py2exe
和另一个exe制作了Windows Service exe,并将其作为线程触发
从该服务中将其替换为新服务。程序效果很好!
同时,我读了很多有关Python Threadnig的文章,但现在我不明白什么是正确的,或者为什么它根本不起作用?!
s_service.exe
作为Windows服务安装并启动。这行得通。w_update.exe
与s_service.exe
位于同一个目录中。s_service.exe
(称为s_service.exe v2.0
):[ProjectPy]
[Download]
s_service.exe
s_service.exe <--- This one is active as Windows Service
w_update.exe
关于服务:
为简便起见,我们假设s_service.exe
只有一项任务-每30秒将w_update.exe
作为守护程序运行。
if (time_is_right):
t = threading.Thread(target=run_exe, args=["w_update.exe"])
t.daemon = True # <--------- SEE THIS!
t.start()
def run_exe(tool):
proggie = os.path.join(some_path, tool)
if os.path.exists(proggie):
process = subprocess.Popen(proggie, stdout=subprocess.PIPE, shell=False, creationflags=0x08000000)
process.wait()
关于更新程序:
Updater按此顺序执行以下操作:
1. Stop the service s_service.exe
2. Wait 5 sec
3. Remove service from Windows
4. Wait 5 sec
5. Move ProjectPy\Download\s_service.exe to ProjectPy\s_service.exe (overwrites old s_service.exe v1.0 with new s_service.exe v2.0)
6. Install service s_service.exe to Windows
7. Wait 5 sec
8. Start service
(下面是代码摘录,省略了控制结构)
service_name = "MyPythonService"
print("Stop Service...")
win32serviceutil.StopService(service_name)
time.sleep(5)
print("Remove Service...")
win32serviceutil.RemoveService(service_name)
time.sleep(5)
print("Move: ", download_dir_filename, current_dir_filename)
shutil.move(download_dir_filename, current_dir_filename)
print("Install Service")
win32serviceutil.InstallService(None, service_name, "My Python Service Display Name", startType=win32service.SERVICE_AUTO_START, exeName=current_dir_filename, description=service_description)
time.sleep(5)
print("Start Service")
win32serviceutil.StartService(service_name)
我的问题是:为什么行得通?!
来自各种资源:
可以将线程标记为“守护程序线程”。该标志的含义是整个Python程序在仅保留守护程序线程时退出。
设置thread.daemon = True
将允许主程序退出。 应用程序通常要等到所有子线程完成后再。
非守护程序线程在主程序未死亡时会阻止其退出。守护程序线程在运行时不会阻止主程序退出。并且当主程序退出时,关联的守护程序线程也会被杀死。
守护线程的要点是它在主线程关闭时继续运行。
守护程序线程不会阻止主线程退出并继续在后台运行。
堆栈溢出问题:尽管主程序完成了,后台驻留程序线程仍未退出
https://www.youtube.com/watch?v=OKedlEeBxU8-“ 当主程序终止时,守护线程也将终止”
守护程序线程是即使脚本的其余部分已停止,仍将继续运行的线程。这意味着将线程守护程序设置为true意味着它将在主线程完成(或退出)后继续运行。
a)有人说,当主线程完成时,守护程序线程也会终止。
如果这是真的,我的守护线程w_update.exe
应该在步骤1. Stop the service s_service.exe
之后或步骤3. Remove service from Windows
之后被杀死
并且无法继续执行步骤5、6和8。
但是它正确地(重新)安装并(重新)启动(新)服务-全部8个步骤。
b)有人说即使脚本的其余部分已经停止,该线程也将继续运行。
这是我的情况。
其他信息:由于存在错误,一旦我在MS Windows Server 2008上遇到问题:
任务管理器中一个s_service.exe
的实例,
超过350个w_update.exe
实例(以及所有其他守护程序线程实例)
当我停止s_service.exe
时,所有w_update.exe
实例(以及所有其他守护线程实例)都被自动删除。
因此这有利于a)有人说,当主线程完成时-守护程序线程也会终止。
我是否缺少某些内容,或者Python版本之间或Windows OS-es之间的行为是否有所不同? 我很困惑...