将列名作为参数传递给 mySQL 中的存储过程

Passing a column name as parameter to a stored procedure in mySQL(将列名作为参数传递给 mySQL 中的存储过程)
本文介绍了将列名作为参数传递给 mySQL 中的存储过程的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在创建一些存储过程来管理我的数据库.特别是,我想创建一个存储过程来编辑特定行的列,但我想动态地进行,将列名作为参数传递.

I'm creating some stored procedures to manage my DB. In particular, i want to create a stored procedore to edit a column, of a specific row, but i want to do it dinamically, passing the column name as an argument.

这就是我想做的事情

CREATE PROCEDURE myDB.edit_myTable(
    IN key CHAR(16), 
    IN col VARCHAR(100), 
    new_value VARCHAR(200)
)
UPDATE myDB.myTable SET col = new_value

使用参数key我在myTable中找到我想要编辑的特定行,我想使用参数col只编辑我想要的列.

Using the parameter keyi find the specific row in myTablethat i want to edit, and i want to use the parameter col to edit just the column that i want.

我已经尝试过使用 CONCATE() 或定义局部变量,正如我在其他主题上阅读的那样,但我没有找到解决方案.

I've already tried using CONCATE()or defining local variables, as i read on other topic, but i haven't find a solution.

有什么帮助吗?

推荐答案

你需要使用动态SQL:

DELIMITER //
CREATE PROCEDURE myDB.edit_myTable(
    IN key CHAR(16), 
    IN col VARCHAR(100), 
    new_value  VARCHAR(200)
)
BEGIN
    SET @s = CONCAT(
        'UPDATE myDB.myTable SET `', 
         col, '` = ', QUOTE(new_value),
         ' WHERE key = ', QUOTE(key)
    );
    PREPARE stmt FROM @s;
    EXECUTE stmt;
    DEALLOCATE PREPARE stmt;
END
//
DELIMITER;

请注意,正如 Paul Spiegel 所评论的,使用变量作为列名会产生 SQL 风险注射.提高安全性的一种解决方案是使用 MySQL 信息模式确保输入 col 确实存在于目标表中:

Please note that, as commented by Paul Spiegel, using a variable for column name creates a risk of SQL injection. One solution for improve security would be to make sure that the input col does exists in the target table, using MySQL information schema :

DELIMITER //
CREATE PROCEDURE myDB.edit_myTable(
    IN key CHAR(16), 
    IN col VARCHAR(100), 
    new_value  VARCHAR(200)
)
BEGIN
    DECLARE col_exists INT;

    SELECT COUNT(*) INTO col_exists 
    FROM  information_schema.COLUMNS
    WHERE TABLENAME = 'mytable' AND COLUMN_NAME = col;

    IF (col_exists != 1) THEN
        SIGNAL SQLSTATE '45000'
        SET MESSAGE_TEXT = CONCAT('Column ', col, ' does not exist in table mytable');
    END IF;

    SET @s = CONCAT(
        'UPDATE myDB.myTable SET `', 
         col, '` = ', QUOTE(new_value),
         ' WHERE key = ', QUOTE(key)
    );
    PREPARE stmt FROM @s;
    EXECUTE stmt;
    DEALLOCATE PREPARE stmt;
END
//
DELIMITER;

这篇关于将列名作为参数传递给 mySQL 中的存储过程的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持编程学习网!

本站部分内容来源互联网,如果有图片或者内容侵犯您的权益请联系我们删除!

相关文档推荐

Execute complex raw SQL query in EF6(在EF6中执行复杂的原始SQL查询)
Hibernate reactive No Vert.x context active in aws rds(AWS RDS中的休眠反应性非Vert.x上下文处于活动状态)
Bulk insert with mysql2 and NodeJs throws 500(使用mysql2和NodeJS的大容量插入抛出500)
Flask + PyMySQL giving error no attribute #39;settimeout#39;(FlASK+PyMySQL给出错误,没有属性#39;setTimeout#39;)
auto_increment column for a group of rows?(一组行的AUTO_INCREMENT列?)
Sort by ID DESC(按ID代码排序)