建表
在 blog 库下建表:
create table `user_info` (
`id` bigint unsigned not null auto_increment,
`name` varchar(45) not null default '',
primary key (`id`)
) engine = InnoDB default charset = utf8mb4;
直接执行组装后的 sql
注意,这种方式有sql注入风险,会影响数据安全!!
import pymysql
conn = pymysql.connect(host='127.0.0.1',
user='root',
password='123456',
port=3306,
database='blog')
cursor = conn.cursor(cursor=pymysql.cursors.DictCursor)
sql = '''INSERT INTO `user_info` (name) values('{}');'''.format('name001')
affect_rows = cursor.execute(sql)
print('影响行数: ', affect_rows)
print('插入数据对应的主键id: ', cursor.lastrowid)
conn.commit() # 必须加这个
cursor.close()
conn.close()
运行结果示例:
影响行数: 1
插入数据对应的主键id: 2
查询数据库中的数据:
mysql> select * from user_info;
+----+---------+
| id | name |
+----+---------+
| 2 | name001 |
+----+---------+
若不想每次都添加conn.commit()
,可以在创建数据库连接时,指定 autocommit 为 True。
示例:
import pymysql
conn = pymysql.connect(host='127.0.0.1',
user='root',
password='123456',
port=3306,
database='blog',
autocommit=True # 指定 autocommit 为 True
)
cursor = conn.cursor(cursor=pymysql.cursors.DictCursor)
sql = '''INSERT INTO `user_info` (name) values('{}');'''.format('name002')
affect_rows = cursor.execute(sql)
print('影响行数: ', affect_rows)
print('插入数据对应的主键id: ', cursor.lastrowid)
cursor.close()
conn.close()
使用参数化语句添加数据 - 使用元组/列表指定数据
这个和 Java jdbc 的 prepare statement 参数化声明不同。pymysql 的参数化语句本质上仍然是组装 sql,不过会对数据进行安全转义,以防止 sql 注入。
示例:
import pymysql
conn = pymysql.connect(host='127.0.0.1',
user='root',
password='123456',
port=3306,
database='blog',
autocommit=True
)
cursor = conn.cursor(cursor=pymysql.cursors.DictCursor)
affect_rows = cursor.execute('INSERT INTO `user_info` (name) values(%s);', ['name003'])
print('影响行数: ', affect_rows)
print('插入数据对应的主键id: ', cursor.lastrowid)
cursor.close()
conn.close()
使用参数化语句添加数据 - 使用字典指定数据
示例:
import pymysql
conn = pymysql.connect(host='127.0.0.1',
user='root',
password='123456',
port=3306,
database='blog',
autocommit=True
)
cursor = conn.cursor(cursor=pymysql.cursors.DictCursor)
affect_rows = cursor.execute('INSERT INTO `user_info` (name) values(%(name)s);', {'name': 'name004'})
print('影响行数: ', affect_rows)
print('插入数据对应的主键id: ', cursor.lastrowid)
cursor.close()
conn.close()
如何使用参数化声明
上面提到,pymysql 的参数化语句和 Java jdbc 的 prepare statement 参数化声明不同。pymysql 的参数化语句本质上仍然是组装 sql,不过会对数据进行安全转义,以防止 sql 注入。
MySQL 的官方 Python 库 mysql.connector
是支持的,具体可参考:
获取插入数据的主键 ID
插入数据后,通过cursor.lastrowid
可以获取对应数据的主键id。具体使用方式见上面的示例代码。
一次插入多条数据
使用 executemany 方法。
示例:
import pymysql
conn = pymysql.connect(host='127.0.0.1',
user='root',
password='123456',
port=3306,
database='blog',
autocommit=True
)
cursor = conn.cursor(cursor=pymysql.cursors.DictCursor)
affect_rows = cursor.executemany('INSERT INTO `user_info` (name) values(%(name)s);',
[
{'name': 'name005'},
{'name': 'name006'}
])
print('影响行数: ', affect_rows) # 输出 2
print('插入数据对应的主键id: ', cursor.lastrowid) # 这里只返回第一个数据的id
cursor.close()
conn.close()
运行结果示例:
影响行数: 2
插入数据对应的主键id: 6
根据注释,executemany 方法可以针对 insert、replace SQL语句使用。