使用 WorkManager 在 Jetty 上启用编程并发

Enable programmatic concurrency on Jetty with WorkManager

我设法将 CommonJ - JSR 237 Timer & WorkManager API (http://commonj.myfoo.de) 的自定义实现配置为 Jetty 6 和 8 上的 JNDI 资源,但它仅在全球范围内工作。
使用此解决方案 JNDI 资源名称为 wm/WorkManager,我需要它为 java:comp/env/wm/WorkManager,但由于限制,我不能在全局 JNDI 名称中使用 java:comp/env,因为它是保留给应用程序范围内的资源。
我创建了一个名为 {jetty.home}/etc/jetty-wtm.xml 的新配置文件并添加到 {jetty.home}/start.ini.
这是 Jetty 6 的 jetty-wtm.xml 内容,对于更高的版本,它有点不同,但也有效:

<!-- =============================================================== -->
<!-- Configure Server Time and Work Managers                         -->
<!-- =============================================================== -->

<Configure id="Server" class="org.mortbay.jetty.Server">


    <New id="WorkManager" class="org.mortbay.jetty.plus.naming.Resource">
        <Arg>wm/WorkManager</Arg>
        <Arg>
            <New class="de.myfoo.commonj.work.FooWorkManager">
                <Arg>
                    <New id="threadPool" class="de.myfoo.commonj.util.ThreadPool">
                        <Arg type="int">0</Arg>
                        <Arg type="int">10</Arg>
                        <Arg type="int">2</Arg>
                    </New>
                </Arg>
            </New>
        </Arg>
    </New>

    <New id="TimeManager" class="org.mortbay.jetty.plus.naming.Resource">
        <Arg>tm/TimeManager</Arg>
        <Arg>
            <New class="de.myfoo.commonj.timers.FooTimerManager">
                <Arg>
                    <New id="threadPool" class="de.myfoo.commonj.util.ThreadPool">
                        <Arg type="int">0</Arg>
                        <Arg type="int">10</Arg>
                        <Arg type="int">2</Arg>
                    </New>
                </Arg>
            </New>
        </Arg>
    </New>
</Configure>

我需要跨服务器维护标准 JNDI 命名 java:comp/env/{RESOURCE},特别是 java:comp/env/wm/MyWorkManager,但是标准 WEB-INF\jetty-env.xml 配置文件不起作用。 有什么想法吗?

更新: 我已经在 J​​etty 9 中测试了 jetty-env.xml 本地配置文件,它按预期工作。似乎在 9 JNDI 以下的版本中没有得到完全支持。下面是配置文件内容:

<Configure id="wac" class="org.eclipse.jetty.webapp.WebAppContext">

<New id="WorkManager" class="org.eclipse.jetty.plus.jndi.Resource">
        <Arg><Ref id="wac"/></Arg>
        <Arg>wm/MyWorkManager</Arg>
        <Arg>
            <New class="de.myfoo.commonj.work.FooWorkManager">
                <Arg>
                    <New id="threadPool" class="de.myfoo.commonj.util.ThreadPool">
                        <Arg type="int">0</Arg>
                        <Arg type="int">10</Arg>
                        <Arg type="int">2</Arg>
                    </New>
                </Arg>
            </New>
        </Arg>
    </New>
</Configure>

你检查过了吗this,

Sometimes it is useful to pass configuration information to a web app at runtime that you either cannot or cannot conveniently code into a web.xml . In such cases, you can use org.eclipse.jetty.plus.jndi.EnvEntry, and even override an entry of the same name in web.xml.

<New class="org.eclipse.jetty.plus.jndi.EnvEntry">
  <Arg></Arg>
  <Arg>mySpecialValue</Arg>
  <Arg type="java.lang.Integer">4000</Arg>
  <Arg type="boolean">true</Arg>
</New>

This example defines a virtual env-entry called mySpecialValue with value 4000 that is unique within the whole JVM. It is put into JNDI at java:comp/env/mySpecialValue for every web app deployed. Moreover, the boolean argument indicates that this value overrides an env-entry of the same name in web.xml. If you don't want to override, then omit this argument, or set it to false.

对于 etc 内自定义文件中的资源,文档指出

Assume the following naming entry is in $JETTY_HOME/etc/jetty-myjndi.xml:

 <New  id="jdbc/myds"  class="org.eclipse.jetty.plus.jndi.Resource">
     <Arg></Arg>
     <Arg>jdbc/myds</Arg>
     <Arg>
       <New  class="com.mysql.jdbc.jdbc2.optional.MysqlConnectionPoolDataSource">
         <Set  name="Url">jdbc:mysql://localhost:3306/chat</Set>
         <Set  name="User">root</Set>
         <Set  name="Password">sillyness</Set>
       </New>
     </Arg>
  </New>

Then you can link jdbc/myds into your webapp's namespace as java:comp/env/jdbc/myfoo by using a WEB-INF/jetty-env.xml file:

   <Call class="org.eclipse.jetty.plus.jndi.NamingEntryUtil" name="bindToENC">
       <Arg></Arg>    <!-- scope of naming entry, ie same as first argument to your naming entry definition, in this case, null -->
       <Arg>jdbc/myfoo</Arg>
       <Arg>jdbc/myds</Arg>
   </Call>

Note that you must use a WEB-INF/jetty-env.xml file to call the "bindToENC" method and not a context xml file, as the latter is not interpreted at the correct phase of the webapp's deployment to have the java:comp/env namespace created.