使用 Postgres DB 的 Arquillian 的 Tomee 用户缺少权限或找不到对象

Posted

技术标签:

【中文标题】使用 Postgres DB 的 Arquillian 的 Tomee 用户缺少权限或找不到对象【英文标题】:Tomee with Arquillian using Postgres DB user lacks privilege or object not found 【发布时间】:2014-03-28 08:44:08 【问题描述】:

我在使用 tomee 对 postgres db 运行 arquillian 测试时遇到问题。 借助网络上的所有信息,我仍在努力解决问题。

javax.ejb.EJBException: The bean encountered a non-application exception; nested exception is: 
    Exception [EclipseLink-4002] (Eclipse Persistence Services - 2.3.2.v20111125-r10461): org.eclipse.persistence.exceptions.DatabaseException
Internal Exception: java.sql.SQLSyntaxErrorException: user lacks privilege or object not found: CREDENTIALS
Error Code: -5501
Call: SELECT ID, PASSWORD, USERNAME FROM credentials WHERE (USERNAME = ?)
    bind => [phil]

数据库:

名称:注册表

表:凭据

位于手动创建的架构下:postgres

目录src/main/resources下的persistence.xml

<?xml version="1.0" encoding="UTF-8"?>
<persistence version="2.0" xmlns="http://java.sun.com/xml/ns/persistence" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://java.sun.com/xml/ns/persistence http://java.sun.com/xml/ns/persistence/persistence_2_0.xsd">

  <persistence-unit name="registry" transaction-type="JTA">
    <jta-data-source>RegistryDS</jta-data-source>
    <non-jta-data-source>UnmanagedRegistryDS</non-jta-data-source>
    <provider>org.eclipse.persistence.jpa.PersistenceProvider</provider>
    <class>za.co.registry.client.login.Credentials</class>
    <properties>
      <property name="eclipselink.debug" value="OFF"/>
      <property name="eclipselink.weaving" value="static"/>
      <property name="eclipselink.logging.level.sql" value="FINE"/>
      <property name="eclipselink.logging.parameters" value="true"/>
      <property name="eclipselink.logging.logger" value="DefaultLogger"/>
    </properties>
  </persistence-unit>
</persistence>

tomee.xml

<Resource id="RegistryDS" type="DataSource">
          jdbcDriver=org.postgresql.Driver
          jdbcUrl=jdbc:postgresql://127.0.0.1:5432/registry
          userName=postgres 
          password=postgres 
          JtaManaged=true
</Resource>
<Resource id="UnmanagedRegistryDS" type="DataSource">
          jdbcDriver=org.postgresql.Driver
          jdbcUrl=jdbc:postgresql://127.0.0.1:5432/registry
          userName=postgres 
          password=postgres 
          JtaManaged=false
</Resource>

用于 arquillian 测试的 pom.xml 提取

<dependency>
    <groupId>org.apache.openejb</groupId>
    <artifactId>arquillian-tomee-embedded</artifactId>
    <version>1.6.0</version>
    <scope>test</scope>
</dependency> 

<dependency>
    <groupId>org.jboss.arquillian.junit</groupId>
    <artifactId>arquillian-junit-container</artifactId>
    <version>1.0.3.Final</version>
    <scope>test</scope>
</dependency>
<dependency>
    <groupId>junit</groupId>
    <artifactId>junit</artifactId>
    <version>4.11</version>
    <scope>test</scope>
</dependency>  

arquillian.xml 提取

<container qualifier="tomee" default="true">
    <configuration>
        <property name="httpPort">-1</property>
        <property name="stopPort">-1</property>
        <property name="dir">target/apache-tomee-remote</property>
        <property name="appWorkingDir">target/arquillian-test-working-dir</property>
        <property name="properties" />
    </configuration>
</container>

加载资源时的ServiceTest.java文件。

    @Deployment
    public static WebArchive createDeployment() 
        WebArchive webArchive = newArchive();
        webArchive.addClasses(Credentials.class);
        webArchive.addAsResource("META-INF/persistence.xml");
        webArchive.addAsResource("META-INF/beans.xml");
        return webArchive;
    

最后在ServiceTest.java中测试findCredentialsByUsernameTest方法

@Test
public void findCredentialsByUsernameTest() 
    Credentials login = LoginService.findByUsername("phil");
    Assert.assertNotNull(login);

我没有在测试类中开始或结束任何EntityTransaction

当服务中的数据库调用被删除时,它可以注入一个 EJB。 我在配置中遗漏了什么或做错了什么导致它不起作用?

【问题讨论】:

用户缺少权限或找不到对象:CREDENTIALS”是不是 Postgres 错误消息(相应的 Postgres 错误将是“未找到关系“凭据””)。但是,错误消息对于 HSQLDB 来说是典型的。您确定要连接到正确的数据库吗? 嗨@a_horse_with_no_name,我指出Postgres,因为它是场景和我的环境的一部分。标题读起来可能有点搞笑。我想我正在连接到正确的数据库,但这就是为什么我提供了上面的所有信息以供某人帮助,看看我是否正确地进行了配置。 好吧,如果您要连接到嵌入式 HSQLDB,那么正确设置 Postgres 数据库将无济于事。 我不确定我的配置是否正确。据我所知,在进行测试时,我无法连接到嵌入式数据库。使用 Arquillian/Integration 测试时必须连接到嵌入式数据库吗?我认为当我有 arquillian tomee 嵌入式设置时,它也会使用数据源进行测试。 【参考方案1】:

好吧,我想我知道我做错了什么。

我需要针对嵌入式数据库运行测试。

我为使 Arquillian 测试与嵌入式数据库一起工作所遵循的步骤;

从 tomee.xml 中删除了非托管数据源,我添加它是因为我想将它用于我的测试。另一个数据源仍然存在,因为它在部署到 tomee 以连接到 postgres db 时使用。

<Resource id="UnmanagedRegistryDS" type="DataSource">
          jdbcDriver=org.postgresql.Driver
          jdbcUrl=jdbc:postgresql://127.0.0.1:5432/registry
          userName=postgres 
          password=postgres 
          JtaManaged=false
</Resource>

我要连接到 HSQLDB。

HSQLDB (HyperSQL DataBase) is the leading SQL relational database software written in Java. It offers a small, fast multithreaded and transactional database engine with in-memory and disk-based tables and supports embedded and server modes

接下来我在 src/test/resources 中创建第二个 persistence.xml,名为 test-persistence.xml。请记住将在 arquillian.xml 文件中使用的持久性单元名称 testDatabase

<?xml version="1.0" encoding="UTF-8"?>
<persistence xmlns="http://java.sun.com/xml/ns/persistence"
             xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
             xsi:schemaLocation="http://java.sun.com/xml/ns/persistence http://java.sun.com/xml/ns/persistence/persistence_2_0.xsd"
             version="2.0">
    <persistence-unit name="test" transaction-type="JTA">
        <jta-data-source>testDatabase</jta-data-source>
        <class>za.co.registry.client.login.Credentials</class>
        <properties>
            <property name="openejb.jpa.init-entitymanager" value="true" />
            <property name="openjpa.jdbc.SynchronizeMappings" value="buildSchema(ForeignKeys=true)" />
        </properties>
    </persistence-unit>
</persistence>

arquillian.xml,我正在文件中设置 testDatabase 持久性单元属性。请参阅下面的属性。

<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<arquillian
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xsi:schemaLocation="http://jboss.org/schema/arquillian http://jboss.org/schema/arquillian/arquillian_1_0.xsd">
    <container qualifier="openejb-embedded" default="true">
        <configuration>
            <property name="httpPort">-1</property>
            <property name="stopPort">-1</property>
            <property name="dir">target/apache-tomee-remote</property>
            <property name="appWorkingDir">target/arquillian-test-working-dir</property>
            <property name="properties">
                testDatabase = new://Resource?type=DataSource
                testDatabase.JdbcUrl = jdbc:hsqldb:mem:my-datasource
             </property>
        </configuration>
    </container>
</arquillian>

配置我的 ServiceTest.java 文件以包含新的 persistence.xml 文件。

webArchive.addAsWebInfResource("META-INF/test-persistence.xml", "persistence.xml");
webArchive.addAsResource("META-INF/beans.xml");

现在我可以运行findCredentialsByUsernameTest 方法了。

    @Test
    public void findCredentialsByUsernameTest() 
        //create credentials first
        Credentials newCredentials = loginService.newCredentials(new Credentials("john", "password"));

        //search for credentails
        Credentials login = loginService.findByUsername("john");
        Assert.assertNotNull(login);
        Assert.assertEquals(newCredentials.getUsername(), login.getUsername());
    

【讨论】:

以上是关于使用 Postgres DB 的 Arquillian 的 Tomee 用户缺少权限或找不到对象的主要内容,如果未能解决你的问题,请参考以下文章

Spring Batch 无法通过 DB (postgres) 获取作业锁

Flask-Sqlalchemy 使用 postgres 创建视图

如何使用 python 通过 ssh 连接 aws postgres db

无法使用 Postgres、Docker Compose 和 Psycopg2 将主机名“db”转换为地址

postgres和h2 db中名称中的#字符问题

尝试使用 django 从 postgres DB 中按顺序获取下一个值