最近有一个需求,在现有生产系统上的人员库中增加一个此人员关键信息的二维码,支持文字版和跳转版两种方式,与报表工具关联,可打印。以windows服务方式,定时检查,只要发现某人员没有此二维码信息,就生成并写入人员库。

  决定使用Python。

  在此之前,没有用Python实现过其中的任何一个工作。对于习惯于微软开发环境下的程序员,使用开源系统,几乎一步一个坎,不过确实挺简单的。

  整体设想,主要工作有以下几个步骤:

1.生成二维码

2.建立连接,读取数据

3.根据读取的数据生成二维码

4.二维码写入数据库

5.与报表工具关联,显示在报表上

6.写日志

7.生成windows服务

下面分步叙述过程。

1.   生成二维码

使用QRCode

安装命令pip install QRCode,会自动下载并安装与当前版本匹配插件。

代码如下(来自网络,稍加改动,保留原作者声明,下同):

# coding: utf-8
"""
filename: qrcode.py
Created by Tacey Wong at 16-9-22 下午10:34
""" #import zbar
import qrcode
from PIL import Image
import os, sys def gen_qrcode(string, path, logo=""):
"""
生成中间带logo的二维码
需要安装qrcode, PIL库
@参数 string: 二维码字符串
@参数 path: 生成的二维码保存路径
@参数 logo: logo文件路径
@return: None
""" qr = qrcode.QRCode(
version=2,
error_correction=qrcode.constants.ERROR_CORRECT_H,
box_size=8,
border=1
)
qr.add_data(string)
qr.make(fit=True)
img = qr.make_image()
#img = img.convert("RGBA")
img = img.convert("RGB")
if logo and os.path.exists(logo):
try:
icon = Image.open(logo)
img_w, img_h = img.size
except(Exception) as e:
print(e)
sys.exit(1)
factor = 4
size_w = int(img_w / factor)
size_h = int(img_h / factor) icon_w, icon_h = icon.size
if icon_w > size_w:
icon_w = size_w
if icon_h > size_h:
icon_h = size_h
icon = icon.resize((icon_w, icon_h), Image.ANTIALIAS) w = int((img_w - icon_w) / 2)
h = int((img_h - icon_h) / 2)
#icon = icon.convert("RGBA") #png图像使用
icon = icon.convert("RGB")
img.paste(icon, (w, h), icon)
img.save(path)
# 调用系统命令打开图片
# xdg - open(opens a file or URL in the user's preferred application)
#os.system('xdg-open %s' % path) ##def decode_qrcode(path):
## """
## 解析二维码信息
## @参数 path: 二维码图片路径
## @return: 二维码信息
## """
## # 创建图片扫描对象
## scanner = zbar.ImageScanner()
## # 设置对象属性
## scanner.parse_config('enable')
## # 打开含有二维码的图片
## img = Image.open(path).convert('L')
## # 获取图片的尺寸
## width, height = img.size
## # 建立zbar图片对象并扫描转换为字节信息
## qrCode = zbar.Image(width, height, 'Y800', img.tobytes())
## scanner.scan(qrCode)
## # 组装解码信息
## data = ''
## for s in qrCode:
## data += s.data
## # 删除图片对象
## del img
## # 输出解码结果
## return data def SetQRCode(info,imgFileName=""):
#if __name__ == "__main__":
#info = """"""
#pic_path = "QR" + imgFileName + ".jpg"
pic_path = "QR.jpg"
icon_path = "logo.png"
logo_path = ""
gen_qrcode(info, pic_path,logo_path )
#print(decode_qrcode(pic_path))

2.   建立连接,读取数据

本步骤使用cx_Oracle,安装方法同上

>>>pip install cx_Oracle

需要oracle客户端,下载地址:https://oracle.github.io/odpi/doc/installation.html#windows,找到适合你的版本,下载zip版本以后,解压,把oracle客户端路径加到系统路径中。

代码如下:

import cx_Oracle
import logging
import inspect
import os #建立和数据库系统的连接 conn = cx_Oracle.connect('用户名', '密码', '数据库服务器IP/oracle服务名') #建立连接,3 个参数分开写 cursor = conn.cursor() def updateData(fid,value):
param={'fieldname1': fieldname1, 'fieldname2': fieldname2} cursor.execute("""UPDATE tablename
SET FQRCODE=:fieldname1
WHERE DICT_OID=:fieldname2 """,param)
#cursor.close();
conn.commit();
#conn.close(); def openImage(): file=open("qr.jpg",'rb');
img=file.read();
file.close() return img def searchAll(): import gqrcode cursor.execute('''
SELECT * FROM tablename n
''')
#personInfoTuple=cursor.fetchone() #获取一条 #personInfoTuple=cursor.fetchmany(2) #获取2条 personInfoTuple = cursor.fetchall() #获取全部 import datetime;
import time; listIds=[]
for x in personInfoTuple: authcode = x[5]
strInfo = "网址” now = datetime.datetime.now();
now = now.strftime('%Y%m%d%H%M%S%MS')
clock = time.clock();
filename=x[4]+now gqrcode.SetQRCode(strInfo) #生成二维码

3.   根据读取的数据生成二维码

此处需要安装PIL,即pillow

>>>pip install pillow

 imgStream=openImage(); #以二进制流打开图片

 listIds.append(x[0])

4.   二维码写入数据库

        updateData(x[0], imgStream);#入库

5.   与报表工具关联,显示在报表上

以二进制流的方式入库以后,在报表工具中,以图片控件读取字段即可,大多数报表工具都支持。我用的是如意报表。

6.   写日志

Python里面另有loggning模块,因为任务的时间紧迫,我没有仔细研究,直接写文本文件。
//日志
def logger(msg):
try:
logFileName="logging_test.log"
logging.basicConfig(filename=logFileName,filemode='a',level=logging.DEBUG)
logging.debug(msg)
except Exception as ex:
logging.debug(ex);

7.   生成windows服务

这一步我浪费了很多时间。启动服务时,在有些机器上报错,有些不报错,没有找到规律,如果有人在事件查看器中发现“等待服务的连接超时(30000)毫秒”,我没有解决。

这一步需要安装pywin32,理论上用pip install pywin32即可,但是,我用的是p3.6.3,PyInstaller的官方网站似乎没有此版本,我没找到。我在CSDN上找到的此版本,说是官方的。链接:http://download.csdn.net/download/battlewolf_hua/9827297

我为了检测此服务需要多少内存,需要下载安装psutil

>>>pip install psutil

代码如下:

#encoding=utf-8
import win32serviceutil
import win32service
import win32event
import os
import logging
import inspect
import servicemanager
import sys
import datetime
import oracleTest
import psutil class ServiceTest (win32serviceutil.ServiceFramework): info = psutil.virtual_memory()
_totalMemory = round(info.total /1024 /1024/1024,2) #总内存GB _thisMemory = psutil.Process(os.getpid()).memory_info().rss #本程序使用内存KB _now = datetime.datetime.now();
_prefix = _now.strftime('%Y%m%d')
_svc_name_ = "ConstructorNoBuildingService" #服务名
#_svc_name_ = "PythonService" #服务名 _svc_display_name_ = "ServiceTest" #服务在windows系统中显示的名称
_svc_description_ = "二维码服务" #服务的描述 def __init__(self, args):
win32serviceutil.ServiceFramework.__init__(self, args)
self.hWaitStop = win32event.CreateEvent(None, 0, 0, None)
self.logger = self._getLogger() self.run = True def _getLogger(self): logger = logging.getLogger('[ServiceTest]') this_file = inspect.getfile(inspect.currentframe())
dirpath = os.path.abspath(os.path.dirname(this_file))
handler = logging.FileHandler(os.path.join(dirpath, "service" + self._prefix + ".log")) formatter = logging.Formatter('%(asctime)s %(name)-12s %(levelname)-8s %(message)s')
handler.setFormatter(formatter) logger.addHandler(handler)
logger.setLevel(logging.DEBUG) return logger _hour = _now.strftime('%H')
def SvcDoRun(self):
import time ## self.logger.info("service is run....")
while self.run :
## self.logger.info("I am runing....") listUpdatedIds = oracleTest.searchAll()
if(len(listUpdatedIds)==0):
self.logger.info("无数据,服务空载")
else:
self.logger.info(listUpdatedIds) self.logger.info("使用内存"+str(self._thisMemory/1024)+"KB")
time.sleep(30) #执行任务间隔,相当于timer控件中的interval def SvcStop(self):
self.logger.info("service was stopped.")
self.ReportServiceStatus(win32service.SERVICE_STOP_PENDING)
win32event.SetEvent(self.hWaitStop)
self.run = False if __name__=='__main__':
print("主程序启动")
## print(len(sys.argv));
logger(len(sys.argv));
if len(sys.argv) == 1:
try:
evtsrc_dll = os.path.abspath(servicemanager.__file__)
servicemanager.PrepareToHostSingle(ServiceTest)
servicemanager.Initialize(ServiceTest, evtsrc_dll)
servicemanager.StartServiceCtrlDispatcher()
except win32service.error as details:
import winerror
if details == winerror.ERROR_FAILED_SERVICE_CONTROLLER_CONNECT:
print("错误发生")
win32serviceutil.usage()
else:
print("否则,执行win32serviceutil.HandleCommandLine(ServiceTest)")
try:
win32serviceutil.HandleCommandLine(ServiceTest)
except Exception as e:
print(e)
win32serviceutil.usage()

8.   安装服务

命令行,源文件所在目录

Python serviceTest.py install

Good luck

一次使用Python连接数据库生成二维码并安装为windows服务的工作任务的更多相关文章

  1. 使用 Python 生成二维码

    在“一带一路”国际合作高峰论坛举行期间, 20 国青年投票选出中国的“新四大发明”:高铁.扫码支付.共享单车和网购.其中扫码支付指手机通过扫描二维码跳转到支付页面,再进行付款.这种新的支付方式,造就二 ...

  2. jenkins 安卓打包生成二维码下载

    先来张图看看吧 构思 jenkins gradle 打包apk文件,python myqr 模块生成二维码 放入nginx 访问图片的路径,apk安装包放在 nginx 下载目录. 环境 centos ...

  3. 第三百二十节,Django框架,生成二维码

    第三百二十节,Django框架,生成二维码 用Python来生成二维码,需要qrcode模块,qrcode模块依赖Image 模块,所以首先安装这两个模块 生成二维码保存图片在本地 import qr ...

  4. 使用MyQR生成二维码

    from MyQR import myqr # 主要用到以下几个参数 # words:文本,可以是一个链接,或者你想说的话 # picture:你用到的图片,作为背景,不然只是一个光秃秃的二维码 # ...

  5. 十八 Django框架,生成二维码

    用Python来生成二维码,需要qrcode模块,qrcode模块依赖Image 模块,所以首先安装这两个模块 生成二维码保存图片在本地 import qrcode img = qrcode.make ...

  6. QrenCode : 命令行下生成二维码图片

    对于二维码大家应该并不陌生,英文名为 2-dimensional bar code 或 QR Code,是一种用图形记载信息的技术,最常见的是应用在手机应用上.用户通过手机摄像头扫描二维码或输入二维码 ...

  7. QrenCode : linux命令行下生成二维码图片

    原文链接:http://wowubuntu.com/qrencode.html # 作者:riku/ / 本文采用CC BY-NC-SA 2.5协议授权,转载请注明本文链接. 对于二维码大家应该并不陌 ...

  8. Python 创建本地服务器环境生成二维码

    一. 需求 公司要做一个H5手机端适配页面,因技术问题所以H5是外包的,每次前端给我们源码,我们把源码传到服务器让其他人访问看是否存在bug,这个不是很麻烦吗?有人说,可以让前端在他们的服务器上先托管 ...

  9. Python生成二维码脚本

    简单的记录下二维码生成和解析的Python代码 依赖下面三个包: PIL(图像处理包,安装:pip install PIL) qrcode(二维码生成包,安装:pip install qrcode) ...

随机推荐

  1. JavaScript 词法、静态、动态作用域初级理解

    开始之前 由于本人也是JavaScript初学者,记录学习经过,怕以后会忘记. 对于JavaScript 初学者来说,最难的不是代码部分,而是对很多书籍中的术语的理解,大多时候想要理解一段JavaSc ...

  2. 【转】WCF OpenTimeout, CloseTimeout, SendTimeout, ReceiveTimeout

    关于这四个属性,在MSDN中的解释有点敷衍了事.Open/Close/Receive/Send本是HTTP/TCP/SOCKET的概念,Read/Write Operation则是Web Servic ...

  3. Windows程序执行过程

    Windows应用程序: WinMain函数(入口函数): 1. 设计窗体类,注冊窗体类.WNDCLASS 2. 创建窗体,显示及更新窗体. 3. 消息循环. 窗体过程函数(回调函数):WindowP ...

  4. LHC大神问的矩阵转置问题

    数学中线性代数中提到的矩阵转置,其实在我们的业务场景中也有需要的地方,比如LHC大神问到的这个问题 那么如何进行行列转换呢? 代码如下: <?php $array=array( '部门1'=&g ...

  5. Nginx(九)-- Nginx实际使用配置

    1.由于在nginx中需要配置很多东西,就会使得nginx.conf配置文件过于臃肿,所以我们会将配置文件合理的切分.大体的配置依然在nginx.conf中,其他的配置会放在etc下面的目录中. 2. ...

  6. redis资料

    http://snowolf.iteye.com/blog/1630697  征服redis配置 http://redis.readthedocs.org/en/latest/  redis命令参考 ...

  7. Ansible 管理任务计划

    ansible 使用 cron 模块来管理任务计划: [root@localhost ~]$ ansible 192.168.119.134 -m cron -a "name='test c ...

  8. Maven编译出现“[ERROR] java.lang.OutOfMemoryError: Java heap space”

    Windows下添加环境变量MAVEN_OPTS的value为-Xms1024m -Xmx1024m -Xss1m Linux下可修改.profile或者.bash_profile文件,并做如下设置: ...

  9. flask路由中增加正则表达式

    #coding=utf-8 from flask import Flask from werkzeug.routing import BaseConverter class RegexConverte ...

  10. 说说C与汇编之间的互相联系(转)

    在嵌入式系统开发中,目前使用的主要编程语言是C和汇编,C++已经有相应的编译器,但是现在使用还是比较少的.在稍大规模的嵌入式软件中,例如含有OS,大部分的代码都是用C编写的,主要是因为C语言的结构比较 ...