SeaQL / sea-orm

🐚 An async & dynamic ORM for Rust
https://www.sea-ql.org/SeaORM/
Apache License 2.0
6.56k stars 459 forks source link

Regression of 1.0.0-rc.6 when inserting with binary column #2266

Closed wtdcode closed 6 days ago

wtdcode commented 1 week ago

Description

There is a regression of 1.0.0-rc.6 with encoding the query. 1.0.0-rc.5 works well.

Steps to Reproduce

Schema:

create table TestTable(
`id` INTEGER PRIMARY KEY NOT NULL AUTO_INCREMENT,
`bn` BINARY(4) NOT NULL
);

Code

src/models/logs.rs

//! `SeaORM` Entity, @generated by sea-orm-codegen 1.0.0-rc.5

use sea_orm::entity::prelude::*;

#[derive(Clone, Debug, PartialEq, DeriveEntityModel, Eq)]
#[sea_orm(table_name = "TestTable")]
pub struct Model {
    #[sea_orm(primary_key, auto_increment = true)]
    pub id: i32,
    #[sea_orm(column_type = "Binary(4)")]
    pub bn: Vec<u8>
}

#[derive(Copy, Clone, Debug, EnumIter, DeriveRelation)]
pub enum Relation {}

impl ActiveModelBehavior for ActiveModel {}

#[cfg(test)]
mod test {
    use sea_orm::{sea_query::{Iden, MySqlQueryBuilder, OnConflict, Query}, ActiveValue::NotSet, Database, EntityTrait, QueryTrait, Set};
    use sea_orm::Iterable;
    use itertools::Itertools;

    #[tokio::test]
    async fn test() {
        let db = Database::connect("mysql://127.0.0.1:3306/test").await.unwrap();
        let model = crate::models::logs::ActiveModel {
            id: NotSet,
            bn: Set(vec![0xffu8;4])
        };

        println!("{}", crate::models::logs::Entity::insert(model.clone()).build(sea_orm::DatabaseBackend::MySql).to_string());

        crate::models::logs::Entity::insert(model).exec(&db).await.unwrap();
    }
}

src/models/mod.rs

mod logs;

src/main.rs

mod models;
fn main() {
    println!("Hello, world!");
}

Cargo.toml

[package]
name = "seaorm-repro"
version = "0.1.0"
edition = "2021"

[dependencies]
itertools = "0.13.0"
sea-orm = { version = "1.0.0-rc.6", features = ["sqlx-mysql", "runtime-tokio-rustls", "macros", "with-json", "with-chrono" ] }
tokio = {version = "1.36.0", features = ["full"]}

Expected Behavior

The built query is correct but the query sent to MySQL is wrong.

The built query is:

INSERT INTO `TestTable` (`bn`) VALUES (x'FFFFFFFF')

However, from MYSQL logging, it gets:

INSERT INTO `TestTable` (`bn`) VALUES ('\\xFF\\xFF\\xFF\\xFF')

Note the difference of the length of the data:

mysql> select length('\\xFF\\xFF\\xFF\\xFF');
+--------------------------------+
| length('\\xFF\\xFF\\xFF\\xFF') |
+--------------------------------+
|                             16 |
+--------------------------------+
1 row in set (0.00 sec)
mysql> select length(x'FFFFFFFF');
+---------------------+
| length(x'FFFFFFFF') |
+---------------------+
|                   4 |
+---------------------+
1 row in set (0.00 sec)

Actual Behavior

The sent query should be the same with the built query??

Reproduces

Yes

Workarounds

Revert to 1.0.0-rc5

Reproducible Example

See above

Versions

See above

tyt2y3 commented 1 week ago

umm. I don't recall anything changed between rc5 & 6 that might have caused this problem

wtdcode commented 1 week ago

Hmm, weird. I can no longer reproduce this???

tyt2y3 commented 6 days ago

May I close this? you can reopen when you found something