开发者

How can I map multiple contexts to the same war file in Jetty?

Is it possible to map multiple contextPaths to one WAR file in Jetty? For example

${jetty.home}/webapp/bookstore.war

And then I'd like to have two different contexts pointing to this war. The reason being some configuration differences depending which URL is reached.

<Configure class="org.eclipse.jetty.webapp.WebAppContext">
    <Set name="contextPath">/开发者_高级运维magazines</Set>
    <Set name="war"><SystemProperty name="jetty.home" default="."/>/webapps/bookstore.war</Set>
</Configure>

<Configure class="org.eclipse.jetty.webapp.WebAppContext">
    <Set name="contextPath">/books</Set>
    <Set name="war"><SystemProperty name="jetty.home" default="."/>/webapps/bookstore.war</Set>
</Configure>


Here is how I did it, and I was also set up different SSL certs for each site (not shown). I don't claim to understand all I know but this is working for me in several installations. You need a "jetty.xml" and a "contexts.xml" file for each instance.

Assume jetty is installed in /opt/Jetty...

Launch two instances of the server referencing two versions of jetty.xml (this can be done in a single script, as shown, or in two separate launch scripts)

start.sh...

cd /opt/Jetty 
java -jar start.jar etc/jetty.xml etc/jetty2.xml

If you have a server with multiple ip's you can use the context.xml files to specify different ip's or hostnames in the connector section of each jetty.xml file. If you only have one ip, then you will use the context path setting in context xml to differentiate between the two instances.

in jetty.xml, refer to the ip or host, and the directory to contain the context.xml for the 1st instance:

<Call name="addConnector">
   <Arg>
       <New class="org.mortbay.jetty.nio.SelectChannelConnector">
         <Set name="host">HOST OR IP FOR FIRST INSTANCE</Set>
         <Set name="port"><SystemProperty name="jetty.port" default="80"/></Set>
         <Set name="maxIdleTime">30000</Set>
         <Set name="Acceptors">2</Set>
         <Set name="statsOn">false</Set>
         <Set name="confidentialPort">443</Set>
         <Set name="lowResourcesConnections">5000</Set>
         <Set name="lowResourcesMaxIdleTime">5000</Set>
       </New>
   </Arg>
 </Call>
 <Call name="addLifeCycle">
   <Arg>
     <New class="org.mortbay.jetty.deployer.ContextDeployer">
       <Set name="contexts"><Ref id="Contexts"/></Set>
       <Set name="configurationDir"><SystemProperty name="jetty.home" default="."/>/contexts/directory_for_FIRST_instance</Set>
       <Set name="scanInterval">5</Set>
     </New>
   </Arg>
 </Call>

in jetty.xml, refer to the ip or host, and the directory to contain the context.xml for the 2nd instance:

<Call name="addConnector">
   <Arg>
       <New class="org.mortbay.jetty.nio.SelectChannelConnector">
         <Set name="host">HOST OR IP FOR SECOND INSTANCE</Set>
         <Set name="port"><SystemProperty name="jetty.port" default="80"/></Set>
         <Set name="maxIdleTime">30000</Set>
         <Set name="Acceptors">2</Set>
         <Set name="statsOn">false</Set>
         <Set name="confidentialPort">443</Set>
         <Set name="lowResourcesConnections">5000</Set>
         <Set name="lowResourcesMaxIdleTime">5000</Set>
       </New>
   </Arg>
 </Call>
 <Call name="addLifeCycle">
   <Arg>
     <New class="org.mortbay.jetty.deployer.ContextDeployer">
       <Set name="contexts"><Ref id="Contexts"/></Set>
       <Set name="configurationDir"><SystemProperty name="jetty.home" default="."/>/contexts/directory_for_SECOND_instance</Set>
       <Set name="scanInterval">5</Set>
     </New>
   </Arg>
 </Call>

If defined as shown above, you can reload the war file and restart the application by touching the context xml file.

Put separate context files in separate subdirectories of the context directory, each pointing to the same war file, but with different context paths and different virtual hosts.

/opt/Jetty/contexts/subdirectory_for_first_instance/context_first.xml
/opt/Jetty/contexts/subdirectory_for_second_instance/context_second.xml

in context_first.xml - you can specify a node (firstapp) that will always link to your first app

<Set name="contextPath">/firstapp</Set>

in context_second.xml - you can specify a node (firstapp) that will always link to your second app

<Set name="contextPath">/secondapp</Set>

(The above is necessary (two different context paths) if you want to run them from the same ip, i believe)

Then define the two virtual hosts (must map the url which is being used by the browser) in the separate context files:
In context_first.xml:

<Set name="virtualHosts">
  <Array type="String">
    <Item>www.my_first_app.com</Item>
  </Array>
</Set>

And in context_second.xml

<Set name="virtualHosts">
  <Array type="String">
    <Item>www.my_second_app.com</Item>
  </Array>
</Set>

Note: if you have two ip's or host names, you can set the context path of both apps to "/"
if you have only one ip, the context path will determine which application is accessed

Also, and importantly, you can send context parameters to your application so that it can determine which instance it is, if necessary.

Example of context parameters to send unique values to each instance:

 <!-- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -->
 <!-- Custom context configuration                                  -->
 <!-- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -->
 <Set name="initParams">
   <New class="java.util.HashMap">
    <Put name="customer">Joes Fish Store</Put>
    <Put name="ShowPanelNames">N</Put>
    <Put name="FiscalYearStartMonth">10</Put>
    <Put name="LiveEmail">Y</Put>
   </New>
 </Set>


You could simply copy the war file and rename it.


I realize this is old but since the answers provided don't really answer the question, for future reference you can achieve multiple WebappContexts using the same .war by adding an id attribute to Configure.

<Configure id="magazinesContext" class="org.eclipse.jetty.webapp.WebAppContext">
    <Set name="contextPath">/magazines</Set>
    <Set name="war"><SystemProperty name="jetty.home" default="."/>/webapps/bookstore.war</Set>
    <Set name="extractWAR">true</Set>
</Configure>

<Configure id="booksContext" class="org.eclipse.jetty.webapp.WebAppContext">
    <Set name="contextPath">/books</Set>
    <Set name="war"><SystemProperty name="jetty.home" default="."/>/webapps/bookstore.war</Set>
    <Set name="extractWAR">true</Set>
</Configure>

Note however that all naming Resources defined in the context must be either assigned to the context using

<Arg>
    <Ref id="magazinesContext" />
</Arg>

So if you have dbcp pooling resource "pg_conn", without the Arg with the reference to the id of the WebappContext (in this case either "magazinesContext" or "booksContext") the Resource will be globally defined, ie the last WebAppContext loaded wins.

Take for example the following WebappContext definition where "pg_conn" is globally defined:

<Configure id="magazinesContext" class="org.eclipse.jetty.webapp.WebAppContext">
    <Set name="contextPath">/magazines</Set>
    <Set name="war"><SystemProperty name="jetty.home" default="."/>/webapps/bookstore.war</Set>
    <Set name="extractWAR">true</Set>
    <New id="pg_conn" class="org.mortbay.jetty.plus.naming.Resource">
        <Arg>jdbc/db</Arg>
        <Arg>
            <New class="org.apache.commons.dbcp.BasicDataSource">
                <Set name="driverClassName">org.postgresql.Driver</Set>
                <Set name="url">jdbc:postgresql://localhost:5432/test_db</Set>
                <Set name="username">test</Set>
                <Set name="password">*****</Set>
            </New>
        </Arg>
    </New>
</Configure>

and this one, where it is defined for the instance of WebappContext:

<Configure id="magazinesContext" class="org.eclipse.jetty.webapp.WebAppContext">
    <Set name="contextPath">/magazines</Set>
    <Set name="war"><SystemProperty name="jetty.home" default="."/>/webapps/bookstore.war</Set>
    <Set name="extractWAR">true</Set>
    <New id="pg_conn" class="org.mortbay.jetty.plus.naming.Resource">
        <Arg>
            <Ref id="magazinesContext" />
        </Arg>
        <Arg>jdbc/db</Arg>
        <Arg>
            <New class="org.apache.commons.dbcp.BasicDataSource">
                <Set name="driverClassName">org.postgresql.Driver</Set>
                <Set name="url">jdbc:postgresql://localhost:5432/test_db</Set>
                <Set name="username">test</Set>
                <Set name="password">*****</Set>
            </New>
        </Arg>
    </New>
</Configure>
0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜