杰瑞科技汇

Python MySQL如何获取插入后的自增ID?

  1. 获取 INSERT 操作后,新记录的自增 ID
  2. 查询操作后,获取满足条件的记录的 ID

下面我将详细讲解这两种情况,并提供完整的代码示例。


准备工作:安装 mysql-connector-python

你需要安装官方的 MySQL Python 驱动,如果还没有安装,请在终端或命令行中运行:

pip install mysql-connector-python

获取 INSERT 操作后的自增 ID

当你向一个带有自增主键(AUTO_INCREMENT)的表中插入新数据时,如何获取这个新生成的 ID 呢?

关键方法:cursor.lastrowid

这是最直接、最常用的方法,在你执行 INSERT 语句并提交事务后,可以通过游标的 lastrowid 属性来获取最后一条插入记录的 ID。

重要前提:

  • 必须使用 cursor.execute() 来执行 INSERT 语句。
  • 必须在执行 INSERT 之后、关闭游标或连接之前调用 cursor.lastrowid
  • 表的主键必须是 AUTO_INCREMENT 的。

完整示例代码

import mysql.connector
from mysql.connector import Error
def insert_user_and_get_id(username, email):
    """
    向数据库中插入一个新用户,并返回其自增ID。
    如果插入失败,返回 None。
    """
    connection = None
    cursor = None
    try:
        # 1. 建立数据库连接
        # 请替换为你的实际数据库信息
        connection = mysql.connector.connect(
            host='localhost',
            database='your_database',
            user='your_username',
            password='your_password'
        )
        if connection.is_connected():
            cursor = connection.cursor()
            # 2. 定义插入数据的 SQL 语句
            # 使用 %s 作为占位符,防止 SQL 注入
            sql_insert_query = "INSERT INTO users (username, email) VALUES (%s, %s)"
            # 3. 准备数据元组
            user_data = (username, email)
            # 4. 执行 SQL 语句
            cursor.execute(sql_insert_query, user_data)
            # 5. 提交事务,使数据持久化到数据库
            connection.commit()
            # 6. 获取最后插入行的 ID
            last_id = cursor.lastrowid
            print(f"成功插入用户,ID 为: {last_id}")
            return last_id
    except Error as e:
        print(f"插入数据时出错: {e}")
        # 如果出错,回滚事务
        if connection:
            connection.rollback()
        return None
    finally:
        # 7. 关闭游标和连接
        if cursor:
            cursor.close()
        if connection and connection.is_connected():
            connection.close()
# --- 调用函数 ---
# 假设我们有一个 users 表,结构如下:
# CREATE TABLE users (
#     id INT AUTO_INCREMENT PRIMARY KEY,
#     username VARCHAR(50) NOT NULL,
#     email VARCHAR(100) NOT NULL
# );
new_user_id = insert_user_and_get_id('john_doe', 'john.doe@example.com')
if new_user_id:
    print(f"新用户的ID是: {new_user_id}")

查询操作后获取记录的 ID

当你执行 SELECT 语句时,你会得到一个结果集,你需要遍历这个结果集来获取每条记录的 ID。

关键方法:cursor.fetchall()cursor.fetchone()

  • cursor.fetchall(): 获取所有查询结果,返回一个包含元组的列表,每个元组代表一行数据。
  • cursor.fetchone(): 只获取下一行结果,返回一个元组。

你需要在 SQL 查询语句中明确指定要获取的列,包括 id

完整示例代码

import mysql.connector
from mysql.connector import Error
def find_user_id_by_username(username):
    """
    根据用户名查询用户ID。
    如果找到,返回ID;如果未找到,返回None。
    """
    connection = None
    cursor = None
    try:
        # 1. 建立数据库连接
        connection = mysql.connector.connect(
            host='localhost',
            database='your_database',
            user='your_username',
            password='your_password'
        )
        if connection.is_connected():
            cursor = connection.cursor()
            # 2. 定义查询 SQL 语句
            # 一定要在 SELECT 中明确写出 id
            sql_select_query = "SELECT id, username, email FROM users WHERE username = %s"
            # 3. 准备查询参数
            search_param = (username,)
            # 4. 执行 SQL 语句
            cursor.execute(sql_select_query, search_param)
            # 5. 获取所有结果
            records = cursor.fetchall()
            # 6. 遍历结果
            for row in records:
                # row 是一个元组,(1, 'john_doe', 'john.doe@example.com')
                # id 是第一个元素 (索引 0)
                user_id = row[0]
                print(f"找到用户: {row[1]}, ID: {user_id}")
                return user_id # 返回找到的第一个ID
            # 如果循环结束没有返回,说明没有找到
            return None
    except Error as e:
        print(f"查询数据时出错: {e}")
        return None
    finally:
        # 7. 关闭游标和连接
        if cursor:
            cursor.close()
        if connection and connection.is_connected():
            connection.close()
# --- 调用函数 ---
user_to_find = 'john_doe'
found_id = find_user_id_by_username(user_to_find)
if found_id:
    print(f"查询成功,用户 '{user_to_find}' 的 ID 是: {found_id}")
else:
    print(f"未找到用户名为 '{user_to_find}' 的记录。")

最佳实践和注意事项

  1. 使用上下文管理器 (with 语句):为了更安全、更简洁地管理数据库连接和游标,强烈推荐使用 with 语句,它会自动处理资源的关闭。

    # 使用 with 语句的示例
    try:
        with mysql.connector.connect(
            host='localhost',
            database='your_database',
            user='your_username',
            password='your_password'
        ) as connection:
            with connection.cursor() as cursor:
                cursor.execute("INSERT INTO users (username) VALUES (%s)", ('test_user',))
                connection.commit()
                print(f"新ID: {cursor.lastrowid}")
    except Error as e:
        print(f"数据库错误: {e}")

    使用 with 后,你不需要手动写 cursor.close()connection.close(),代码更清晰。

  2. 防止 SQL 注入:永远不要使用 Python 的字符串格式化(如 f"INSERT ... VALUES ({username})")来构建 SQL 查询,这极易导致 SQL 注入攻击。始终使用 %s 占位符和参数化查询,如代码示例中所示。

  3. 事务管理INSERT, UPDATE, DELETE 操作后,必须调用 connection.commit() 来保存更改,如果发生错误,调用 connection.rollback() 可以撤销未提交的操作。

  4. 游标类型:对于需要返回大量数据的查询,可以使用 dictionary=True 的游标,这样结果会以字典形式返回,列名就是键,更易读。

    # 使用字典游标
    with connection.cursor(dictionary=True) as cursor:
        cursor.execute("SELECT id, username FROM users")
        for row in cursor.fetchall():
            print(f"ID: {row['id']}, Username: {row['username']}")

希望这个详细的解释和示例能帮助你完全理解如何在 Python 中使用 MySQL 获取 ID!

分享:
扫描分享到社交APP
上一篇
下一篇