MS-SQL Server,JDBC和XA事务的exception
我尝试执行XA事务时,在日志中遇到以下exception:
javax.transaction.xa.XAException:com.microsoft.sqlserver.jdbc_SQLServerException:无法创建XA控件连接。 错误:“对象’xp_sqljdbc_xa_init_ex’,数据库’master’架构’dbo’上的EXECUTE权限被拒绝
我按照这些教程了解XA事务和如何使MSSQL Server XA数据源工作? 在完成第一个教程之后,我还在SSMS中运行了以下命令:
使用主GO
EXEC sp_addrolemember [SqlJDBCXAUser],’MyUserName’GO
我还要补充说我跑了
使用主GO EXEC sp_grantdbaccess’MyUserName’,’MyUserName’GO
validation用户是否有权访问主数据库,并且出现“用户已存在于当前数据库中”的错误。 最后,我通过SSMSvalidation了角色SqlJDBCXAUser
确实具有关于xp_sqljdbc_xa_init_ex
EXECUTE。
我使用的数据库显然不是master
而是myDBName
。 关于这个问题,两者之间唯一的关联是MyUserName
是myDBName
的所有者,并且作为master
的用户存在。
我的服务器在Windows XP SP3上运行(因此第一个教程中提到的修补程序不相关,因为它适用于XP SP2及其下,我知道当我尝试运行此修补程序时)。
有人遇到过这个问题吗? 我真的很感激一些线索。
谢谢,
以太
更新:
我再次看了Microsoft
的第一个教程,有两个段落,我不确定它们是什么意思,它们可能包含解决方案:
在将参与分布式事务的每个SQL Server实例上执行数据库脚本xa_install.sql。 此脚本安装由sqljdbc_xa.dll调用的扩展存储过程。 这些扩展存储过程实现了Microsoft SQL Server JDBC驱动程序的分布式事务和XA支持。 您需要以SQL Server实例的管理员身份运行此脚本。
当他们说SQL Server instance
,他们是否意味着包含几个数据库的sql server,包括master
和myDBName
(我习惯于oracle术语有点不同)? 我按照给出的那样运行了一次xa_install.sql
脚本,并指出use master
。
这是第二段:
配置用户定义的角色
要授予特定用户使用JDBC驱动程序参与分布式事务的权限,请将用户添加到SqlJDBCXAUser角色。 例如,使用以下Transact-SQL代码将名为“shelby”的用户(名为“shelby”的SQL标准登录用户)添加到SqlJDBCXAUser角色:
USE master GO EXEC sp_grantdbaccess 'shelby', 'shelby' GO EXEC sp_addrolemember [SqlJDBCXAUser], 'shelby'
SQL用户定义的角色是按数据库定义的 。 要出于安全目的创建自己的角色,您必须在每个数据库中定义角色,并以每个数据库的方式添加用户。 SqlJDBCXAUser角色在master数据库中严格定义,因为它用于授予对驻留在master中的SQL JDBC扩展存储过程的访问权限。 您必须首先授予单个用户访问master的权限,然后在登录master数据库时授予他们访问SqlJDBCXAUser角色的权限。
我不确定,但我认为上面的粗体句子说SqlJDBCXAUser
角色应该只在master
上定义,并且访问myDBName
其他用户应该被授予master
访问权限,然后添加到角色中,这将以某种方式 (不是)知道如何使用myDBName
数据库来使用xa包。
更新2:这是来自SSMS的SqlJDBCXAUser角色下存储过程的安全设置的屏幕截图
我们只需要做以下事情:
USE [master] GO CREATE USER [UserName] FOR LOGIN [UserName] WITH DEFAULT_SCHEMA=[dbo] use [master] GO GRANT EXECUTE ON [dbo].[xp_sqljdbc_xa_commit] TO [UserName] GRANT EXECUTE ON [dbo].[xp_sqljdbc_xa_end] TO [UserName] GRANT EXECUTE ON [dbo].[xp_sqljdbc_xa_forget] TO [UserName] GRANT EXECUTE ON [dbo].[xp_sqljdbc_xa_forget_ex] TO [UserName] GRANT EXECUTE ON [dbo].[xp_sqljdbc_xa_init] TO [UserName] GRANT EXECUTE ON [dbo].[xp_sqljdbc_xa_init_ex] TO [UserName] GRANT EXECUTE ON [dbo].[xp_sqljdbc_xa_prepare] TO [UserName] GRANT EXECUTE ON [dbo].[xp_sqljdbc_xa_prepare_ex] TO [UserName] GRANT EXECUTE ON [dbo].[xp_sqljdbc_xa_recover] TO [UserName] GRANT EXECUTE ON [dbo].[xp_sqljdbc_xa_rollback] TO [UserName] GRANT EXECUTE ON [dbo].[xp_sqljdbc_xa_rollback_ex] TO [UserName] GRANT EXECUTE ON [dbo].[xp_sqljdbc_xa_start] TO [UserName] GO
已经有一段时间了,因为我已经将Java与SQL服务器一起使用了,但是我发现你的T-SQL中有些东西可能没有你想要的那样。 片段:
use master GO; EXEC sp_addrolemember [SqlJDBCXAUser], 'MyUserName' GO;
仅将[SqlJDBCXAUser]应用于master数据库中的用户名。 如果您的数据库位于另一个实例中,则还必须在那里添加该角色。 我假设的另一个是拼写错误(’sp_gratdbaccess’应该是’sp_grantdbaccess’)。
我假设您必须在所有参与服务器中运行的’xa_install.sql’脚本成功运行,并且您没有收到任何错误消息? 检查脚本以查找它定义的角色,以确保您键入的内容与所需内容相匹配。
更新:
只是一些健全性检查:
- SQL Server是Windows XP(为什么?)服务器? 然后你有一个修补程序: http : //support.microsoft.com/kb/922668
- SQL Server是否位于带有Microsoft分布式事务处理协调器(MS DTC)的Windows 2003机器上? 你有一个修补程序: http : //support.microsoft.com/kb/899756
- 请查看http://msdn.microsoft.com/en-us/library/aa342335.aspx,了解您可能遇到的其他限制:特别是如果您使用的是MS DTC。
当它将事物称为“实例”时,微软是不明确的,特别是因为它们将它应用于数据库实例(您的数据库)以及SQL Server实例。 一台物理服务器可以同时运行多个SQL服务器副本,同时监听不同的端口。 其中每个都有自己的Master数据库实例。 通过其他语句的上下文(即XA事务支持位于master数据库中),他们正在讨论您运行的每个SQL Server副本。 如果您的应用程序的数据库分布在SQL Server的4个实例(安装)中,则必须在所有四个安装上执行XA安装步骤。
确保角色采用并正确应用于系统的最后一步是使用管理控制台打开master数据库。 您希望确保您的用户位于Databases / master / Security / Users文件夹中,并且它已启用SqlJDBCXAUser角色(角色的复选框)。
接下来,转到正在抱怨的违规存储过程,并确保所有安全设置都包含SqlJDBCXAUser角色。 角色名称不应区分大小写(因为SQL本身不是),但确保角色案例是相同的情况也不会有什么坏处 – 以防万一。
如果失败,还要在MyDatabase实例中运行“xa_install.sql”脚本。 我个人讨厌这种模棱两可,但很可能就是他们的意思。 但在此之前,请确保您不需要任何热修复或具有无法正常工作的配置。 撤消复杂的SQL脚本所做的事情可能是一个很大的痛苦。 这就是我建议最后这样做的原因。