您好,欢迎访问一九零五行业门户网

Python语言编写电脑时间自动同步小工具

话不多说,小工具需求如下:
功能需求 -- 电脑开机后自动执行时间同步
非功能需求 -- 安装执行简单,无需安装额外环境
一、代码实现
基于以上需求,思路如下:访问网络获取北京时间,然后调用命令行来设置系统时间。程序写成windows service,并设置为开机自动运行。正好前段时间在学习python,所以打算用python来写这个工具。具体代码如下:
获取网络时间
代码如下:
def getbeijintime():
获取北京时间
try:
         conn = httplib.httpconnection(www.beijing-time.org)
         conn.request(get, /time.asp)
         response = conn.getresponse()
         print response.status, response.reason
         if response.status == 200:
             #解析响应的消息
             result = response.read()
             logging.debug(result)
             data = result.split(\r\n)
             year = data[1][len(nyear)+1 : len(data[1])-1]
             month = data[2][len(nmonth)+1 : len(data[2])-1]
             day = data[3][len(nday)+1 : len(data[3])-1]
             #wday = data[4][len(nwday)+1 : len(data[4])-1]
             hrs = data[5][len(nhrs)+1 : len(data[5])-1]
             minute = data[6][len(nmin)+1 : len(data[6])-1]
             sec = data[7][len(nsec)+1 : len(data[7])-1]
beijintimestr = %s/%s/%s %s:%s:%s % (year, month, day, hrs, minute, sec)
             beijintime = time.strptime(beijintimestr, %y/%m/%d %x)
             return beijintime
     except:
         logging.exception(getbeijintime except)
         return none
同步本地系统时间
代码如下:
def synclocaltime():
同步本地时间
logging.info(current local time is: %d-%d-%d %d:%d:%d % time.localtime()[:6])
beijintime = getbeijintime()
     if beijintime is none:
         logging.info(get beijintime is none, will try again in 30 seconds...)
         timer = threading.timer(30.0, synclocaltime)
         timer.start();
     else:
         logging.info(get beijintime is: %d-%d-%d %d:%d:%d % beijintime[:6])
tm_year, tm_mon, tm_mday, tm_hour, tm_min, tm_sec = beijintime[:6]
         import os
         os.system(date %d-%d-%d % (tm_year, tm_mon, tm_mday))     #设置日期
         os.system(time %d:%d:%d.0 % (tm_hour, tm_min, tm_sec))    #设置时间
         logging.info(synclocaltime complete, current local time: %d-%d-%d %d:%d:%d \n % time.localtime()[:6])
二、部署安装
为了让python程序能以windows服务的方式运行,需要用到py2exe(用来把python程序编译成exe)和python win32 extensions 。(py2exe把python代码编译成winodws服务时依赖此组件)下载并安装这两个组件。安装完毕后,在python的安装目录下找到py2exe的windows service示例({pythonroot}\lib\site-packages\py2exe\samples\advanced\myservice.py)。然后仿照这个示例将上面的代码完善一下。
windows服务示例
代码如下:
import win32serviceutil
 import win32service
 import win32event
 import win32evtlogutil
class synctimeservice(win32serviceutil.serviceframework):
     _svc_name_ = synctime
     _svc_display_name_ = synctime
     _svc_description_ = synchronize local system time with beijin time
    _svc_deps_ = [eventlog]
def __init__(self, args):
        win32serviceutil.serviceframework.__init__(self, args)
        self.hwaitstop = win32event.createevent(none, 0, 0, none)
    def svcstop(self):
        self.reportservicestatus(win32service.service_stop_pending)
        win32event.setevent(self.hwaitstop)
    def svcdorun(self):
        import servicemanager
# write a 'started' event to the event log...
        win32evtlogutil.reportevent(self._svc_name_,
                                    servicemanager.pys_service_started,
                                    0, # category
                                    servicemanager.eventlog_information_type,
                                    (self._svc_name_, ''))
        # wait for beeing stopped...
        win32event.waitforsingleobject(self.hwaitstop, win32event.infinite)
        # and write a 'stopped' event to the event log.
        win32evtlogutil.reportevent(self._svc_name_,
                                    servicemanager.pys_service_stopped,
                                    0, # category
                                    servicemanager.eventlog_information_type,
                                    (self._svc_name_, ''))  
if __name__ == '__main__':
    # note that this code will not be run in the 'frozen' exe-file!!!
    win32serviceutil.handlecommandline(synctimeservice)
之后,再编写一个steup.py文件用来生成安装文件。setup.py
代码如下:
from distutils.core import setup
 import py2exe
setup(
     # the first three parameters are not required, if at least a
     # 'version' is given, then a versioninfo resource is built from
     # them and added to the executables.
     version = 0.0.1,
     description = synchroniz local system time with beijin time,
     name = sysctime,
# targets to build
     # console = [synctime.py],
     service=[synctime]
 )
编译生成windows程序,如下图:
然后在控制台中运行:setup.py py2exe ,一切顺利的话会在当前目录下生成build和dist目录。
控制台目录切换到dist目录,找到synctime.exe,在命令行中运行:
synctime.exe –install (-remove)  安装或移除时间同步服务。
现在可以运行services.msc查看服务运行情况
可以看到服务并没有启动,而且启动方式为手动。在这里可以右击服务选择属性手动把服务启动起来,并且设置为服务自动启动。
好吧,我承认。这样操作跟上面的需求有点出入了,略显麻烦。为了解决这个问题,自然想到的是用批处理来做。在dist目录下分别建两个批处理文件:
installservice.bat
代码如下:
@echo off
:: 安装windows服务
 echo 正在安装服务,请稍候...
 synctime.exe -install
:: 设置服务自动启动
 echo 正在启动服务...
 sc config synctime start= auto
:: 启动服务
sc start synctime
echo 服务启动成功, 按任意键继续...
pause
removeserivce.bat
代码如下:
@echo off
:: 停止服务
echo 正在停止服务,请稍候...
sc stop synctime
echo 正在卸载服务...
:: 删除windows服务
synctime.exe -remove
echo 服务卸载完成,请按任意键继续剩余卸载...
pause
好了,现在可以把dist打个包发给老妈用了。但是,这样发个一个压缩包,看起来也太不专业了。解决的办法是打一个安装包,把bat脚本打到安装包里,在安装程序时由安装包调用。这里我用的是nisi(使用hm vnisedit打包向导来生成打包脚本非常方便)。
三、最终安装效果图
四、结尾
遗留的问题:
1、从上面的截图可以看到,安装程序在调用批处理时会显示出控制台窗口。这个问题我在网上查找资料,nsis有相关的插件可以隐藏控制台窗口调用bat文件。
2、我源代码中有写日志文件的操作,但是以windows服务的方式运行后,日志文件不能写了,不知道有没有好的解决办法。
3、360 ...真是要人命啊....orz..
时间同步工具及源代码:http://www.bitscn.com/softs/74865.html
编译方法:
第一步: 安装python环境(什么?还没有python环境?... - -!)
第二步: 安装依赖组件
1、py2exe (目前只支持到python2.7)
2、python win32 extensions
第三步(可选):安装nsis环境,用来编译脚本
第四步:将synctime.py编译成windows程序
1、在当前目录下运行setup.py py2exe,顺利的话会在当前目录下生成dist和build目录
第五步: 运行,有两种运行方式:
1、将installservice.bat 和 removeservice.bat 拷贝到dist中运行即可
2(依赖第三步)、使用nsis编译synctime.nsi脚本,生成安装包, 安装后运行(推荐)
其它类似信息

推荐信息