.Net驱动提问

您好 , 我是一名 Net开发者. 目前我部署了 OBServer3.1.3的生产集群. 但是目前遇到一些问题.

经测试: MySQL官方提供的 MySQL.Data连接器 无法正常执行SQL Nuget包版本 从6.9.12(2018年5月4日)至8.0.29(最新2022年4月26日) 均不能正常工作.
期待能探讨方案来解决这个问题 :grinning:

完整的测试代码如下(网络上相关案例曾因字符集问题导致出现过类似错误 , 但我已在连接串中指定了正确的字符集. 连接MySQL8测试 正常)

根据MySQL官方文档显示 MySQL.Data连接器似乎与MySQL版本无强制联系 , 当前8.0.29版本向下兼容MySQL5.7服务器协议.
https://dev.mysql.com/doc/connector-net/en/connector-net-versions.html

1 个赞

这是我完整的测试代码

你能用5.7的驱动吗?8.0目前有点问题

5.7驱动对应的是 MySQL.Data哪个版本呢 , 看MySQL连接器的官网资料 貌似是向下兼容的

1 个赞

MySQL Connector/NET 似乎并不受 MySQL C client library版本影响

这个问题在Issue有人提到过 utf8_bin is not exists in oceanbase · Issue #155 · oceanbase/oceanbase · GitHub
后来他是怎么解决的呢

感谢 @jiangxianfu 大佬提供的帮助 , 我先尝试下解决这个问题. 期待OceanBase能提供解决方案 :grinning:

2 个赞

如果你直接连接串指定utf8mb4而不是utf8的话可以试试么


mysql的默认utf8并不是标准的utf8定义,现在一般都配置utf8mb4
如果你还在用三字节的utf8,这个问题可以关注一下(以下截图来自百度)

指定了哈 不可以的

因为自己的ecs linux环境不好.net的环境,直接分析mysql-connector-net的源码,发现只要指定了charset应该不会走里面的判断逻辑,会不会是你的连接串写法有问题, 没使用过.net,不过网上找到可能要大写?CharSet=utfmb4 or CharSet =‘utfmb4’?

补充源码图片

当不为空时不需要去使用ConnectionCharSetIndex的值,我理解,后续我会看看怎么在我的linux上搭个.net环境再复现试试

这个问题似乎是 OceanBase提供的ConnectionCharSetIndex和MySQL的不一致造成的 按照 @jiangxianfu 提供的方案目前可以临时解决

ob提供utf8_bin的id是为了其他的兼容性,但没有考虑到.net的驱动会用这个index去作判断,在查映射的时候利用从ob的show collation得到的字符集判断的确就会出错,因为ob实际只提供utf8mb4

2 个赞

:smile: 赞 感谢深入分析

您的分析将对未来一段时间的Net开发者提供非常大的帮助 :smiley_cat:

测试中遇到了相同的问题,但是在连接串上直接添加CharSet=utf8并未解决:

            string constr = "server=10.0.0.71;port=2881;user=username;password=pass_word;Database=dtt;CharSet=utf8";
            MySqlConnection mycon = new MySqlConnection(constr);
            mycon.Open();

            string mysqlStr = "select 1 tid";
            MySqlCommand myslComm = new MySqlCommand(mysqlStr, mycon);

            
            MySqlDataReader mysqldr = myslComm.ExecuteReader();

            while (mysqldr.Read())
            {
                Console.WriteLine(mysqldr[0].ToString());
            }

            Console.ReadLine();
            mycon.Close();

Unhandled exception. System.Collections.Generic.KeyNotFoundException: The given key ‘83’ was not present in the dictionary.
at System.Collections.Generic.Dictionary`2.get_Item(TKey key)
at MySql.Data.MySqlClient.MySqlField.SetFieldEncoding()
at MySql.Data.MySqlClient.MySqlField.set_CharacterSetIndex(Int32 value)
at MySql.Data.MySqlClient.MySqlField.SetTypeAndFlags(MySqlDbType type, ColumnFlags flags)
at MySql.Data.MySqlClient.NativeDriver.GetColumnData(MySqlField field)
at MySql.Data.MySqlClient.NativeDriver.GetColumnsData(MySqlField[] columns)
at MySql.Data.MySqlClient.Driver.GetColumns(Int32 count)
at MySql.Data.MySqlClient.ResultSet.LoadColumns(Int32 numCols)
at MySql.Data.MySqlClient.ResultSet…ctor(Driver d, Int32 statementId, Int32 numCols)
at MySql.Data.MySqlClient.Driver.NextResult(Int32 statementId, Boolean force)
at MySql.Data.MySqlClient.MySqlDataReader.NextResult()
at MySql.Data.MySqlClient.MySqlCommand.ExecuteReader(CommandBehavior behavior)
at test1.EmptyClass.Main(String[] args) in /Users/sunpeng/Projects/mysqlacc/mysqlacc/EmptyClass.cs:line 32