MySQL 布尔值和存储过程

MySQL Booleans and stored procedures

我正在尝试通过 NodeJS 的存储过程在 MySQL table 中保存一些布尔值,并使用 mysql2.

执行它

重要提示:我SET @@global.sql_mode= '';禁用了严格模式。

假设我有这个 table

DROP TABLE IF EXISTS `test_table`;
CREATE TABLE IF NOT EXISTS `test_table` (
`id` INT(11) NOT NULL AUTO_INCREMENT,
`booleanField` BOOLEAN,
PRIMARY KEY (`id`)
);

我想添加一个新行 { someBoolean: true }:

DROP PROCEDURE IF EXISTS test_procedure;
DELIMITER $$

CREATE PROCEDURE test_procedure(
    IN DATA JSON
)

BEGIN

  SET @someBoolean      = JSON_UNQUOTE(JSON_EXTRACT(DATA, '$.someBoolean'));

  INSERT INTO test_table (
    booleanField
  ) VALUES (
    @someBoolean
  );

  SELECT 
    @someBoolean AS receivedValue,
    id,
    booleanField
  FROM test_table;


END $$
DELIMITER ;

然后我执行它:

CALL test_procedure('{"someBoolean": true}');

结果是一个新行,其中包含一些有趣的结果:

运行 MySQL 终端客户端中的所有代码我收到了这个:

+---------------+----+--------------+
| receivedValue | id | booleanField |
+---------------+----+--------------+
| true          |  1 |            0 |
+---------------+----+--------------+

所以即便如此,接收到的值也是true,布尔字段被设置为0

我可以检查 @someBoolean 是否为字符串 "true",并将其设置为 TRUE,等等

DROP PROCEDURE IF EXISTS test_procedure;
DELIMITER $$

CREATE PROCEDURE test_procedure(
    IN DATA JSON
)

BEGIN
  DECLARE CASTED_VOTE INT; -- NEW
  SET @someBoolean      = JSON_UNQUOTE(JSON_EXTRACT(DATA, '$.someBoolean'));

  -- NEW
  IF      @someBoolean = "true"  THEN SET  CASTED_VOTE = 1;
  ELSEIF  @someBoolean = "false" THEN SET  CASTED_VOTE = 0;
  ELSE SET                          CASTED_VOTE = NULL;
  END IF;
  -- END NEW

  INSERT INTO test_table (
    booleanField
  ) VALUES (
    CASTED_VOTE
  );

  SELECT 
    CASTED_VOTE, -- NEW
    @someBoolean AS receivedValue,
    id,
    booleanField
  FROM test_table;


END $$
DELIMITER ;

再次执行…

CALL test_procedure('{"someBoolean": true}');

瞧瞧:

+-------------+---------------+----+--------------+
| CASTED_VOTE | receivedValue | id | booleanField |
+-------------+---------------+----+--------------+
|           1 | true          |  1 |            1 |
+-------------+---------------+----+--------------+

但这意味着我必须在所有查询中一遍又一遍地做同样的事情。 我做错了什么?我错过了什么吗?

CREATE PROCEDURE test_procedure(
    IN DATA JSON
)

BEGIN

  SET @someBoolean      = JSON_UNQUOTE(JSON_EXTRACT(DATA, '$.someBoolean'));

  INSERT INTO test_table (
    booleanField
  ) VALUES (
    @someBoolean = 'true'
  );

  SELECT 
    @someBoolean AS receivedValue,
    id,
    booleanField
  FROM test_table;


END

CREATE PROCEDURE test_procedure(
    IN DATA JSON
)

BEGIN

  SET @someBoolean := JSON_UNQUOTE(JSON_EXTRACT(DATA, '$.someBoolean')) = 'true';

  INSERT INTO test_table (
    booleanField
  ) VALUES (
    @someBoolean
  );

  SELECT 
    @someBoolean AS receivedValue,
    id,
    booleanField
  FROM test_table;


END

fiddle


what if I want to pass null? CALL test_procedure('{"someBoolean": "null"}'); – Emille C.

SET @someBoolean := CASE JSON_UNQUOTE(JSON_EXTRACT(DATA, '$.someBoolean'))
                    WHEN 'true' THEN 1
                    WHEN 'false' THEN 0
                    END;

'true''false' 之外的任何值(包括参数缺失)都将被视为(当然也被分配)为 NULL

fiddle