数据库连接池与SQL工具类
数据库连接池与SQL工具类
1.数据库连接池
依赖包
- pymysql
- dbutils
# -*- coding: utf-8 -*-
'''
@Time : 2021/11/19 16:45
@Author : ziqingbaojian
@File : MySql.py
''' # 依赖第三发包:pymysql,dbutils import pymysql
from dbutils.pooled_db import PooledDB MYSQL_DB_POOL=PooledDB(
creator=pymysql,
maxconnections=50,
mincached=2,
maxcached=3,
blocking=True,
setsession=[],
ping=0,
host='127.0.0.1',
port=3306,
user='root',
password='1234567',
database='testlearn',
charset='utf8'
)
源码解释

使用连接池

使用多线程进行测试
# 使用连接池
def task():
# 连接池获取连接
conn=MYSQL_DB_POOL.connection()
cursor=conn.cursor()
cursor.execute("select * from student where sname='逻辑'")
result=cursor.fetchall()
print(result)
conn.close()#将连接还给连接池
# task() '''使用多线程进行测试'''
def run():
for i in range(10):
t=threading.Thread(target=task)
t.start() if __name__ == '__main__':
# 开启10个线程进行测试
run()

2.SQL工具类
2.1 单利模式的方式实现
- 注意:本单利模式并未封装异常处理的功能,各位可以根据情况在封装中添加,也可以在使用时直接将对象进行异常的检测处理;
# -*- coding: utf-8 -*-
'''
@Time : 2021/11/19 17:11
@Author : ziqingbaojian
@File : db.py
'''
import pymysql
from dbutils.pooled_db import PooledDB class DBHelper(object): def __init__(self):
self.pool=PooledDB(
creator=pymysql,
maxconnections=50,
mincached=2,
maxcached=3,
blocking=True,
setsession=[],
ping=0,
host='127.0.0.1',
port=3306,
user='root',
password='1234567',
database='testlearn',
charset='utf8'
)
def get_conn_cursor(self):
conn=self.pool.connection()
cursor=conn.cursor(pymysql.cursors.DictCursor)
return conn,cursor
def get_conn_cursor_nodict(self):
conn=self.pool.connection()#向连接池中请求连接
cursor=conn.cursor()#不写入字典的 参数
return conn,cursor def close_conn_cursor(self,*args):
for item in args:
item.close()
# 由于插入,删除,修改的语句一样因此,不在分开编写,增加简洁程度;
def exec(self,sql,**kwargs):
# 获取连接与游标
conn,cursor=self.get_conn_cursor()
cursor.execute(sql,kwargs)
conn.commit()# 提交事务,只有增删改才需要提交事务,可能与对应的排它锁有关系
self.close_conn_cursor(conn,cursor)
def fetch_one(self,sql,**kwargs):
conn,cursor=self.get_conn_cursor()
cursor.execute(sql,kwargs)
result =cursor.fetchone()
self.close_conn_cursor()
return result
def fetch_all(self,sql,**kwargs):
conn,cursor=self.get_conn_cursor()
cursor.execute(sql,kwargs)
reusult=cursor.fetchall()
return reusult
def fetch_one_nodict(self,sql,**kwargs):
conn,cursor=self.get_conn_cursor_nodict()
cursor.execute(sql, kwargs)
result = cursor.fetchone()
self.close_conn_cursor()
return result
def fetch_all_nodict(self,sql,**kwargs):
conn,cursor=self.get_conn_cursor()
cursor.execute(sql, kwargs)
reusult = cursor.fetchall()
return reusult
db=DBHelper()
补充:什么是单利模式
- 单例模式(Singleton Pattern)是一种常用的软件设计模式,该模式的主要目的是确保某一个类只有一个实例存在。当你希望在整个系统中,某个类只能出现一个实例时,单例对象就能派上用场。
实现单利模式的方式
- Python 的模块就是天然的单例模式,因为模块在第一次导入时,会生成
.pyc文件,当第二次导入时,就会直接加载.pyc文件,而不会再次执行模块代码。因此,我们只需把相关的函数和数据定义在一个模块中,就可以获得一个单例对象了。如果我们真的想要一个单例类,可以像上述类一样,使用时直接导入文件中的对象,这个对象就是单利模式的对象
- Python 的模块就是天然的单例模式,因为模块在第一次导入时,会生成
使用
# -*- coding: utf-8 -*-
'''
@Time : 2021/11/20 8:24
@Author : ziqingbaojian
@File : testpy.py
'''
from db import db '''使用单利模式进行操作'''
res=db.fetch_one("select * from student where sname='%s'"%("逻辑"))
print(res) ''''''
单利模式使用效果

补充:Python其他实现单利模式的方法
参考文献:
https://blog.csdn.net/weixin_44239343/article/details/893767961.使用装饰器
def Singleton(cls):
_instance = {}
def _singleton(*args, **kargs):
if cls not in _instance:
_instance[cls] = cls(*args, **kargs)
return _instance[cls]
return _singleton @Singleton
class A(object):
a = 1 def __init__(self, x=0):
self.x = x
a1 = A(2)
a2 = A(3)
基于__new__方法实现(推荐使用,方便)
当我们实例化一个对象时,是先执行了类的__new__方法(我们没写时,默认调用object.new),实例化对象;然后再执行类的__init__方法,对这个对象进行初始化,所有我们可以基于这个,实现单例模式
import threading
class Singleton(object):
_instance_lock = threading.Lock() def __init__(self):
pass def __new__(cls, *args, **kwargs):
if not hasattr(Singleton, "_instance"):
with Singleton._instance_lock:
if not hasattr(Singleton, "_instance"):
Singleton._instance = object.__new__(cls)
return Singleton._instance
还可以基于类或者metaclass方式实现,此处不在逐个详细解释,请参考参考文献深度学习;
2.2上下文管理
让类支持with 语句的格式,进行使用
with 获取连接() as obj:
# 执行语句
代码
# -*- coding: utf-8 -*-
'''
@Time : 2021/11/20 8:07
@Author : ziqingbaojian
@File : db_context.py
''' import pymysql
from dbutils.pooled_db import PooledDB POOL=PooledDB(
creator=pymysql,
maxconnections=50,
mincached=2,
maxcached=3,
blocking=True,
setsession=[],
ping=0,
host='127.0.0.1',
port=3306,
user='XXXXX',
password='XXXXXX',
database='testlearn',
charset='utf8'
) class Connect(object):
def __init__(self):
self.conn=conn=POOL.connection()#获取连接
self.cursor=conn.cursor(pymysql.cursors.DictCursor)#字典游标,此处不在创键非字典游标,本人使用非字典游标较少,如有需要时可以将字典单参数删除即可 def __enter__(self):
return self def __exit__(self, exc_type, exc_val, exc_tb):
self.cursor.close()
self.conn.close()#通常都是先关游标再关闭连接,此处是将连接归还连接池 def exec(self,sql,**kwargs):
self.cursor.execute(sql,kwargs)
self.conn.commit() def fetch_one(self,sql,**kwargs):
self.cursor.execute(sql,kwargs)
result=self.cursor.fetchone()
return result def fetch_all(self,sql,**kwargs):
self.cursor.execute(sql,kwargs)
result=self.cursor.fetchall()
return result使用效果

补充上下文管理器
参考文献:
https://www.cnblogs.com/wongbingming/p/10519553.html基本语法
with EXPR as VAR:
BLOCK
上下文表达式:with open('test.txt') as f:
上下文管理器:open('test.txt')
f 不是上下文管理器,应该是资源对象。
编写上下文管理器
要自己实现这样一个上下文管理,要先知道上下文管理协议。
简单点说,就是在一个类里,实现了
__enter__和__exit__的方法,这个类的实例就是一个上下文管理器。例如上述的类就采取了这种方式;
在编写代码时,可以将资源的连接或者获取放在
__enter__中,而将资源的关闭写在__exit__中。

在 写
__exit__函数时,需要注意的事,它必须要有这三个参数:- exc_type:异常类型
- exc_val:异常值
- exc_tb:异常的错误栈信息
当主逻辑代码没有报异常时,这三个参数将都为None。
理解并使用 contextlib#
在上面的例子中,我们只是为了构建一个上下文管理器,却写了一个类。如果只是要实现一个简单的功能,写一个类未免有点过于繁杂。这时候,我们就想,如果只写一个函数就可以实现上下文管理器就好了。
这个点Python早就想到了。它给我们提供了一个装饰器,你只要按照它的代码协议来实现函数内容,就可以将这个函数对象变成一个上下文管理器。
我们按照 contextlib 的协议来自己实现一个打开文件(with open)的上下文管理器。
import contextlib @contextlib.contextmanager
def open_func(file_name):
# __enter__方法
print('open file:', file_name, 'in __enter__')
file_handler = open(file_name, 'r') # 【重点】:yield
yield file_handler # __exit__方法
print('close file:', file_name, 'in __exit__')
file_handler.close()
return with open_func('/Users/MING/mytest.txt') as file_in:
for line in file_in:
print(line)在被装饰函数里,必须是一个生成器(带有yield),而yield之前的代码,就相当于
__enter__里的内容。yield 之后的代码,就相当于__exit__里的内容。上面这段代码只能实现上下文管理器的第一个目的(管理资源),并不能实现第二个目的(处理异常)。
如果要处理异常,可以改成下面这个样子。
import contextlib @contextlib.contextmanager
def open_func(file_name):
# __enter__方法
print('open file:', file_name, 'in __enter__')
file_handler = open(file_name, 'r') try:
yield file_handler
except Exception as exc:
# deal with exception
print('the exception was thrown')
finally:
print('close file:', file_name, 'in __exit__')
file_handler.close() return with open_func('/Users/MING/mytest.txt') as file_in:
for line in file_in:
1/0
print(line)
复制知识点的参考文献较多,主要是为了解释编写的数据库使用的工具类中的知识点;
- 手敲不易,转载请指明出处
数据库连接池与SQL工具类的更多相关文章
- 基于Druid数据库连接池的DBUtil工具类
工具类 DruidUtil.java package com.zzuli.util; import com.alibaba.druid.pool.DruidDataSourceFactory; imp ...
- PHP文件上传,下载,Sql工具类!
PHP文件上传,下载,Sql工具类! 对文件大小,文件类型 同名覆盖 中文转码的操作,可直接使用 前台 upload.html <!DOCTYPE html> <html> & ...
- 【知了堂学习心得】浅谈c3p0连接池和dbutils工具类的使用
1. C3P0概述 C3P0是一个开源的JDBC连接池,它实现了数据源和JNDI绑定,支持JDBC3规范和JDBC2的标准扩展.目前使用它的开源项目有Hibernate,Spring等. 2. C3P ...
- spring boot:配置druid数据库连接池(开启sql防火墙/使用log4j2做异步日志/spring boot 2.3.2)
一,druid数据库连接池的功能? 1,Druid是阿里巴巴开发的号称为监控而生的数据库连接池 它的优点包括: 可以监控数据库访问性能 SQL执行日志 SQL防火墙 2,druid的官方站: http ...
- Excel生成Oracle数据库表sql工具类
1.解决问题: 开发文档中字段比较多的时候,建表sql(Oracle下划线命名规范)比较麻烦,容易出错~~ (主要是懒) 特意手写一个工具,根据excel字段,生成建表的sql语句. ~~~末尾附Gi ...
- mysql连接池的使用工具类代码示例
mysql连接池代码工具示例(scala): import java.sql.{Connection,PreparedStatement,ResultSet} import org.apache.co ...
- java学习笔记37(sql工具类:JDBCUtils)
在之前的内容中,我们发现,当我们执行一条语句时,每新建一个方法,就要重新连接一次数据库,代码重复率很高,那么能不能把这些重复代码封装成一个类呢,我们学习方法时,就学习到方法就是为了提高代码的利用率,所 ...
- SQL工具类
package com.ebizwindow.crm.utils; import java.util.List; import com.ebizwindow.crm.constants.SqlCons ...
- sql 工具类function
--判断是否为整数 create or replace function is_number(param VARCHAR2) return NUMBER is v_num NUMBER; begin ...
随机推荐
- python13day
昨日回顾 生成器:生成器就是迭代器,生成器是自己用python代码构建的 生成器函数 生成器表达式 python内部提供的 如何判断函数和生成器函数 yield yield return 吃包子的区别 ...
- eclipse的web项目导入IDE报错
问题:eclipse的web项目导入IDE报错 第一个问题: 解决:点击enable即可 第二个问题: 解决: 解决方法: 切换文件的编码 : from UTF-8 to GBK to UTF-8 参 ...
- linux下使用openssl生成 csr crt CA证书
证书文件生成:一.服务器端1.生成服务器端 私钥(key文件);openssl genrsa -des3 -out server.key 1024运行时会提示输入密码,此密码用于加密key文件( ...
- ios 类别和扩展-赵小波
类别 @interface ClassName ( CategoryName ) // method declarations @end Category在iOS开发中使用非常频繁.尤其是在为系统类进 ...
- Ubuntu 16.04 更改系统语言为简体中文 #####避坑指南
大家跟着我的步骤一步一步来,肯定不会出现问题的 我这里说明两点,一是切换到管理员用户,二是更新网络源! 且待大家走一遍安装流程 一.安装时报错 原因:以访客的身份进入的会报错,改为管理员进入即可. p ...
- LeetCode随缘刷题之最长回文子串
这一题我用的相对比较笨的方法. 相对于大佬们用的动态规划法,比较复杂.但却更容易理解,我主要是通过记录下标来确定最长回文串的. package leetcode.day_12_06; /** * 给你 ...
- Node介绍
https://segmentfault.com/a/1190000006121183 一. 概述 Node.js是基于Chrome JavaScript运行时建立的一个平台,实际上它是对Google ...
- 2021美团安洵暗泉re部分复现
typora-copy-images-to: ./ 安洵杯 sign_in 贪吃蛇 虽然没啥用 smc解密拿一下flag相关的部分 倒着看看sub_40105F 和sub_401055函数 写出解密算 ...
- 操作系统发展史 & 进程
今日内容 UDP协议 操作系统发展史 进程 单核情况下的进程调度 进程三状态图 同步异步 阻塞非阻塞 内容详细 一.UDP协议 1.什么是UDP协议 UDP是传输层的协议,功能即为在IP的数据报服务之 ...
- Dubbo的前世今生
搜索关注微信公众号"捉虫大师",后端技术分享,架构设计.性能优化.源码阅读.问题排查.踩坑实践. 本文已收录 https://github.com/lkxiaolou/lkxiao ...