标签: jdbc

MariaDB Java 客户端在多大程度上是 MySQL JDBC (Connector/J) 的完美替代品?

前提:我发布了一个 Java 应用程序,它将与 MySQL 数据库建立 JDBC 连接。(在撰写本文时,它可能是 5.1 或 5.5,但希望问题和答案不会严重依赖于版本。)

观察:显然,我可以使用 MySQL JDBC 驱动程序 ( Connector/J ) 或 MariaDB JDBC 驱动程序 ( MariaDB Java Client ) 连接到 MySQL 服务器。从 ISV 的角度来看,一个巨大的好处是 MariaDB 驱动程序是 LGPL 许可的,而 MySQL 驱动程序是 GPL 许可的。MariaDB 驱动程序的性能似乎非常好。

问题:MariaDB JDBC 驱动程序在多大程度上可以完美替代 MySQL JDBC 驱动程序?

我不是在寻找关于两者相对优点的辩论。但我希望有人可以按照以下方式之一回答:

  • MariaDB JDBC 驱动程序在 X 和 Y 方面存在重要问题,因此如果您使用其中任何一个,都会遇到麻烦。
  • 根据某些文章或规范或代码或其他证据,MariaDB JDBC 驱动程序完全实现了[至少] MySQL 驱动程序中可用的所有方法。你会没事的。

mysql mariadb jdbc

13
推荐指数
1
解决办法
7270
查看次数

在 JDBC 中禁用显式提交,在 SQL 中检测它们,或将数据库置于只读状态

背景:我在http://sqlfiddle.com 上工作(我的网站)上工作,并试图防止那里可能出现的一种滥用途径。我希望通过询问我目前正在解决的问题,我不会无意中使潜在的虐待变得更糟,但是你能做什么?我相信你们。

我想阻止任何用户在给定的事务块内发出显式的“提交”调用。从 SQL Fiddle 的上下文来看,事务块是在右侧面板上执行的代码。基本上,我正在循环执行一个纯文本 SQL 命令列表,并且我想确保它们所做的所有更改都将在批处理结束时回滚。通常,他们的更改会回滚,但有时文本中会有明确的“提交”语句,因此我的回滚当然不起作用。这种显式提交很可能来自用户试图破坏 SQL Fiddle 上的架构,因此其他人会看到错误。

主要期望结果:如果可能,我想在 JDBC 级别禁用显式提交。这是因为我要支持多个数据库后端供应商,当然每个供应商在低级别都有自己的怪癖。

回退选项:如果无法将 JDBC 配置为禁用显式提交,那么我愿意接受在为以下每个后端处理批处理时检测显式提交的解决方案:SQL Server、Oracle、MySQL 和 PostgreSQL。

对于 SQL Server,我想到了这个解决方案:在我执行它之前解析语句的 XML 查询计划,并检查是否存在与此 XPath 匹配的条目:

//*[@StatementType="COMMIT TRANSACTION"]
Run Code Online (Sandbox Code Playgroud)

我认为这对 SQL Server 非常有效。但是,这种方法不适用于其他数据库类型。Oracle 用于显式提交的 XML 执行计划输出并未提及您正在运行提交语句这一事实(而是简单地重复它提交的查询的执行计划输出)。PostgreSQL 和 MySQL 根本不为显式提交提供任何执行计划输出(XML 或其他)。

这让我需要检查“提交”一词的实际语句。这会起作用,除非可能有各种变化:

declare @sql varchar(50)
set @sql = 'com' + 'mit'
exec(@sql);
Run Code Online (Sandbox Code Playgroud)

上面是 SQL Server 的一个例子(我可以解决),但我猜想类似的事情对于 Oracle、MySQL 和 PostgreSQL 也是可能的。我在这个假设上错了吗?也许他们不允许“动态”提交语句?随意使用 SQL Fiddle(最好不是示例模式或其他人可能正在使用的模式)来查看是否可以在 Oracle、MySQL 和 PostgreSQL 中进行类似的操作。如果没有,也许简单的字符串检测可能适用于那些。

还有一种可能

我想到了另一个选择 - 如果您知道一种将这些数据库中的任何一个设置为只读模式的方法,例如在该模式下无法提交任何内容,那也可以。我仍然需要允许启动事务并在其中运行代码,只要在该模式下不能提交任何内容。那可能吗?

更新

我最近学到的 - 这实际上不是 PostgreSQL …

mysql postgresql oracle jdbc transaction

12
推荐指数
1
解决办法
1716
查看次数

大批量插入速度

在我的应用程序中,我的 INSERT 似乎占用了大部分时间。我在内存中有大量对象(~40-50,000),我想将它们插入到表中。

让我们拿一个样本表

CREATE TABLE bill (
id BIGINT(20) PRIMARY KEY,
amount INT(11) DEFAULT 0,
bill_date DATETIME DEFAULT NOW(),
INDEX (bill_date)
) ENGINE=InnoDB
Run Code Online (Sandbox Code Playgroud)

以 3 行作为我的批量大小,以下是我能想到的插入方法

方法 1 - 构建并触发 3 个原始插入

INSERT INTO bill (amount, bill_date) VALUES (10, '2012-01-01 00:00:00');
INSERT INTO bill (amount, bill_date) VALUES (20, '2012-01-02 00:00:00');
INSERT INTO bill (amount, bill_date) VALUES (40, '2013-02-05 00:00:00');
Run Code Online (Sandbox Code Playgroud)

方法 2 - 将值合并到 1 个查询中

INSERT INTO bill (amount, bill_date) VALUES 
(10, '2012-01-01 00:00:00'),
(20, '2012-01-02 00:00:00'),
(40, '2013-02-05 …
Run Code Online (Sandbox Code Playgroud)

mysql innodb insert jdbc java

11
推荐指数
1
解决办法
1万
查看次数

为什么 MySQL 说我内存不足?

我试图INSERT...SELECT用 JDBC 在 MySQL 中执行一个相当大的,我得到以下异常:

Exception in thread "main" java.sql.SQLException: Out of memory (Needed 1073741824 bytes)
at com.mysql.jdbc.SQLError.createSQLException(SQLError.java:1073)
Run Code Online (Sandbox Code Playgroud)

由于我实际上并没有返回 ResultSet 对象,因此我认为 Java 堆空间应该不是问题。但是,无论如何我都试图提高它,但没有任何好处。然后我尝试在 MySQL Workbench 中执行该语句,我得到了基本相同的结果:

Error Code 5: Out of memory (Needed 1073741816 bytes)
Run Code Online (Sandbox Code Playgroud)

我应该有足够的 RAM 来完成这些操作(足以容纳我从中选择的整个表格),但我猜我需要调整各种设置以利用我的所有内存。我正在使用Windows Server 2008 AMI运行 Amazon EC2高内存双超大实例。我尝试摆弄 my.ini 文件以使用更好的设置,但据我所知,我可能会让事情变得更糟。这是该文件的转储:

[client]
port=3306
[mysql]
default-character-set=latin1
[mysqld]
port=3306
basedir="C:/Program Files/MySQL/MySQL Server 5.5/"
datadir="C:/ProgramData/MySQL/MySQL Server 5.5/Data/"
character-set-server=latin1
default-storage-engine=INNODB
sql-mode="STRICT_TRANS_TABLES,NO_AUTO_CREATE_USER,NO_ENGINE_SUBSTITUTION"
max_connections=100
query_cache_size=1024M
table_cache=256
tmp_table_size=25G
thread_cache_size=8
myisam_max_sort_file_size=100G
myisam_repair_threads = 2
myisam_sort_buffer_size=10G
key_buffer_size=5000M
bulk_insert_buffer_size = 4000M
read_buffer_size=8000M …
Run Code Online (Sandbox Code Playgroud)

mysql windows memory jdbc configuration

9
推荐指数
1
解决办法
4万
查看次数

如何将“COPY”命令与 JDBC 结合使用

所以我一直在使用 postgre 数据库,我注意到当我尝试读取 csv 文件并远程复制到表时,它有时会抛出错误。当我使用缓冲阅读器时它工作得很好,但我试图看看是否有办法让我使用数据库 COPY FROM 方法来工作。它在数据库所在的计算机上运行良好,但我的另一台计算机出现错误。

这一行出现错误:

st.execute("COPY inputdata FROM 'C:\\Users\\JAMES\\Downloads\\V24_Mike_110217_RemovedReturnTrips\\RyderCombiner\\AllNonMatchingWithColNames.csv' CSV HEADER DELIMITER ',';");
Run Code Online (Sandbox Code Playgroud)

这是我连接到数据库的地方:

Class.forName("org.postgresql.Driver");
Connection conn = DriverManager.getConnection("jdbc:postgresql://192.168.1.15:5432/postgres", "postgres", "pass");
Run Code Online (Sandbox Code Playgroud)

我在网上读到也许 STDIN 可以帮助我,但我无法让它工作,并且大多数在线示例都使用 pqsl。有没有办法让它工作或者我需要返回缓冲读者?

更新

因此,我尝试使用 CopyManager API,但在尝试使用 DBUtil 建立连接时出现错误,因为即使我从以下网站下载了 jar 文件,它也无法识别:http ://commons.apache.org/proper/ commons-dbutils/download_dbutils.cgi

代码:

    Connection connection = DBUtil.getConnection("POSTGRES");
    String sql = "COPY inputdata FROM 'C:\\Users\\JAMES\\Downloads\\V24_Mike_110217_RemovedReturnTrips\\RyderCombiner\\AllNonMatchingWithColNames.csv' CSV HEADER DELIMITER ','";
    CopyManager copyManager = new CopyManager((BaseConnection)connection); 
    copyManager.copyIn(sql);
Run Code Online (Sandbox Code Playgroud)

我在 DBUtil 的第一行收到错误...导入 jar 文件是使 jdbc 识别此变​​量的唯一方法吗?

更新2

再次感谢大家,我最终通过遵循给定的链接和一些调整使复制工作正常。

public static void readInputData(String inputDataFile, Statement st) …
Run Code Online (Sandbox Code Playgroud)

postgresql jdbc copy

7
推荐指数
1
解决办法
2万
查看次数

为什么要减少MySQL中的wait_timeout配置参数?

问题

我正在开发一个使用 Apache Tomcat 中的连接池与 MySQL 进行通信的应用程序。我想知道为什么要使用比默认值 28,800 秒更小的wait_timeout ?我发现减少等待超时有很多缺点,但是有什么优点呢?

背景

参数wait_timeout定义为

服务器在关闭非交互式连接之前等待该连接上的活动的秒数。

问题

如果我将 wait_timeout 设置得太小,那么 MySQL 将终止我的 Web 应用程序正在使用的连接池中仍然有效的连接。在我的情况下,我是当前在任何时候使用该应用程序的唯一人,因此当我不测试它时,数据库连接自然会处于空闲状态。我可以通过简单地将 MySQL 上的 wait_timeout 延长到非常大的值来解决这个问题,这样即使我离开办公桌 2 周,池也永远不会返回死连接。

问题

  • 为什么有人想要更短的 wait_time?
  • 存储连接的开销有那么糟糕吗?
  • 尽管我了解连接池减轻了创建连接的开销,但将空闲连接保留在内存中是否是一个问题?

mysql jdbc waits

6
推荐指数
1
解决办法
2万
查看次数

有没有办法通过 JDBC 在 SQL Server 中检索“消息”?

“消息”是指下图中的“消息”选项卡,其中包括“警告”、“受影响的 n 行”以及下图中的执行时间。在 JDBC 中,ResultSet 类用于检索“结果”。有没有办法通过JDBC获取“消息”选项卡中的所有信息?

在此处输入图片说明

sql-server jdbc java

6
推荐指数
1
解决办法
5612
查看次数

对等连接重置:套接字写入错误

我们有一个开发 Java (JDBC) 应用程序的供应商说他们收到了错误

对等连接重置:套接字写入错误

他们坚持认为 SQL Server (SQL Server 2012) 出于某种原因强行断开了他们的应用程序服务器。我已经运行 Profiler 跟踪来收集注意力和用户错误消息事件,但没有发现任何帮助。我检查了环形缓冲区并且只有失败的登录 - 没有断开连接。

SELECT CAST(record AS XML) FROM sys.dm_os_ring_buffers
WHERE ring_buffer_type = 'RING_BUFFER_CONNECTIVITY'
Run Code Online (Sandbox Code Playgroud)

Windows 日志没有显示任何有用的信息。这是我应该能够在 SQL Server 中跟踪的错误,还是纯粹是需要网络跟踪或其他什么的网络错误?有任何想法吗?

sql-server jdbc sql-server-2012 connectivity

6
推荐指数
1
解决办法
2万
查看次数

日期时间小数秒

我正在阅读Sybase ASE 15.7 文档中对datetime数据类型的描述:

datetime 列包含 1753 年 1 月 1 日和 9999 年 12 月 31 日之间的日期。在支持此粒度级别的平台上,日期时间值精确到 1/300 秒。

我觉得上面的内容很混乱。首先,这是唯一添加了“在支持这种粒度级别的平台上”警告的数据类型。这究竟是什么意思,我如何确定我的平台是否是“支持这种粒度级别”的平台之一?

此外,我不清楚能够有效地准确存储 1/300 秒意味着什么。我正在使用 JDBC 访问数据库,其中唯一合理的类型是java.sql.Timestamp。这种类型允许我检索到纳秒的精度。但考虑到在一般情况下,除以 300 需要十进制系统中的无限位数,实际上需要小数纳秒(具有无限十进制数字)来保持表示为 1/300 秒的值。所以,这意味着我无法在不损失一些精度的情况下获取存储在服务器中的值,但可以忽略不计。

最后,当我执行以下查询时:

SELECT convert(char(32), submission_date, 139) FROM some..table
Run Code Online (Sandbox Code Playgroud)

我看到如下值:

Jan  6 2014 12:36:12.420000     
Sep 12 2013 13:44:57.100000     
Sep 10 2014 13:47:02.240000     
Sep 10 2014 13:47:07.850000     
Sep 10 2014 13:47:13.346000     
Sep 10 2014 13:47:19.033000     
Sep 10 2014 13:47:24.533000     
Sep 10 2014 13:47:30.030000     
Sep 10 2014 13:47:35.636000 …
Run Code Online (Sandbox Code Playgroud)

sybase jdbc sybase-ase sybase-ase-15.7

6
推荐指数
1
解决办法
4642
查看次数

在连接之间保留 H2 内存数据库

我使用 Java 中的以下代码创建并使用内存中的 H2 数据库(不写入存储)进行演示和快速测试:

 Connection conn = DriverManager.getConnection( "jdbc:h2:mem:example_db" ) ;
Run Code Online (Sandbox Code Playgroud)

这第一次有效,但随后数据库似乎消失了,无法进行进一步的工作。如何随着时间的推移使用相同的内存数据库?

jdbc java h2 in-memory-database connections

5
推荐指数
1
解决办法
1万
查看次数