0

我编写了一个 OSS 插件来在 Maven 构建过程中启动/停止 Derby。该插件在普通的旧单个模块中工作正常。但是,如果我有几个模块的聚合器并且其中多个模块具有与数据库相关的测试,我似乎遇到了一些奇怪的问题。

我正在调用插件的startstop目标(分别在process-resourcestest阶段),如下所示:

        <plugin>
            <groupId>org.carlspring.maven</groupId>
            <artifactId>derby-maven-plugin</artifactId>
            <version>1.4</version>

            <configuration>
                <failIfAlreadyRunning>false</failIfAlreadyRunning>
            </configuration>

            <executions>
                <execution>
                    <id>start-derby</id>
                    <phase>process-resources</phase>
                    <goals>
                        <goal>start</goal>
                    </goals>
                </execution>
                <execution>
                    <id>stop-derby</id>
                    <phase>test</phase>
                    <goals>
                        <goal>stop</goal>
                    </goals>
                </execution>
            </executions>
        </plugin>

问题在于,在第二次尝试启动 Derby(内存中)服务器时,Derby 似乎仍在运行,或者已经从第一个模块加载了数据库内容。我可以这么说是因为聚合器中的第一个模块在表中创建并填充了一些数据。我的期望是,一旦我关闭 Derby 并从另一个模块重新启动它,它将是一个没有任何现有内容的新数据库。

这是我在插件中处理关闭 Derby 的代码:

try
{
    try
    {
        server.ping();
    }
    catch (Exception e)
    {
        if (failIfNotRunning)
        {
            throw new MojoExecutionException("Failed to stop the Derby server, no server running!", e);
        }

        getLog().error("Derby server was already stopped.");
        return;
    }

    server.shutdown();

    while (true)
    {
        Thread.sleep(1000);
        try
        {
            server.ping();
        }
        catch (Exception e)
        {
            getLog().info("Derby has stopped!");
            return;
        }
    }
}
catch (Exception e)
{
    throw new MojoExecutionException(e.getMessage(), e);
}

这个相当简单的插件的完整源代码可以在 GitHub 上查看或查看

4

1 回答 1

0

我最终做了以下事情:

try
{
    try
    {
        server.ping();
    }
    catch (Exception e)
    {
        if (failIfNotRunning)
        {
            throw new MojoExecutionException("Failed to stop the Derby server, no server running!", e);
        }

        getLog().error("Derby server was already stopped.");
        return;
    }

    try
    {
        DriverManager.getConnection(getConnectionURL());
        DriverManager.getConnection("jdbc:derby:;shutdown=true");
    }
    catch (SQLException e)
    {
        // Apparently this prints out a bunch of stuff we're not currently interested in,
        // we just want it to shutdown properly.
        // Perhaps further handling might be required at a future point in time.
    }

    server.shutdown();

    while (true)
    {
        Thread.sleep(1000);
        try
        {
            server.ping();
        }
        catch (Exception e)
        {
            getLog().info("Derby has stopped!");
            break;
        }
    }

    System.getProperties().remove("derby.system.home");
}
catch (Exception e)
{
    throw new MojoExecutionException(e.getMessage(), e);
}

这不是我期望的必须完成的方式。

于 2012-06-29T12:52:57.687 回答