Announcement Announcement Module
Collapse
No announcement yet.
Spring Batch Admin UI with Grails? Page Title Module
Move Remove Collapse
X
Conversation Detail Module
Collapse
  • Filter
  • Time
  • Show
Clear All
new posts

  • Spring Batch Admin UI with Grails?

    Hi guys,

    I've been trying to wire up the Batch Admin UI with my Grails app but so far have had limited success.

    We have an Integration/Batch job running in our Grails app. I'd like to see the Batch Admin UI to look at the status and outcomes of the job as they run.

    I've followed the steps outlined here: http://stackoverflow.com/questions/6...ng-application

    When I go to \myapp\batch I get the Batch Admin homepage, but if I click on any of the other links like \jobs\, I get a 404 error and it looks like the Grails application is looking for it in \views\jobs\. Could I use the UrlMappings.groovy file in Grails to fix this, perhaps?

    Below is my configuration, it'd be great if someone could let me know if there is anything wrong with it, or even if it is possible to use this UI in Grails. I'm using the 1.2.2 snapshot version of spring batch admin manager since I was already using spring integration 2.1.

    Thanks,
    Tony


    web.xml (generated by the Grails command for install-templates)

    Code:
    <servlet>
            <servlet-name>Batch Servlet</servlet-name>
            <servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
            <init-param>
                <param-name>contextConfigLocation</param-name>
                <param-value>classpath*:/org/springframework/batch/admin/web/resources/servlet-config.xml,classpath*:/org/springframework/batch/admin/web/resources/webapp-config.xml</param-value>
            </init-param>
            <load-on-startup>1</load-on-startup>
    </servlet>
    
    <servlet-mapping>
    	<servlet-name>Batch Servlet</servlet-name>
    	<url-pattern>/batch/*</url-pattern>
    </servlet-mapping>
    applicationContext.xml

    Code:
    <bean id="resourceService" class="org.springframework.batch.admin.web.resources.DefaultResourceService">
    	   <property name="servletPath" value="/batch" />
    </bean>

  • #2
    Quick update: If I navigate directly (type it in the URL bar) to myapp/batch/jobs/1 (i.e. if I give it an index) it will show a plain text page saying

    "There is no such job (1) "

    And give a few other Spring links, but the page has no formatting or styling whatsoever. Same is true if I navigate to myapp/jobs/executions/1

    This actually does show details of the job (so that is good news I suppose!), but again, there is no styling on the page, just plain text.

    Any ideas on how I can get the links working, and the styling working?

    Thanks,
    Tony

    Comment


    • #3
      So looking at the html source, it seems the links in the Batch Admin pages are all pointing at /myapp/<spring batch admin page> or /myapp/resources/styles/<various spring batch admin css files> whereas it should be pointing at /myapp/batch/<spring batch admin page> or /myapp/batch/resources/styles/<various spring batch admin css files>

      How do these links get generated? It looks like everywhere they use the "myapp" variable, I have to replace it with "myapp/batch" and I'll be good to go. Anyone know where this is read in from?

      Cheers,
      Tony

      Comment


      • #4
        Judging by the silence I'm going to take it that this can't work with Grails, and that the page's links are hard-coded or something. If any Spring people are viewing this thread, it'd be a nice integration/feature if you could get it working with Grails.

        Cheers,
        Tony

        Comment


        • #5
          The URLs are generated prefixed with the "servletPath". That servlet path can be configured via the DefaultResourceService. By default, that prefix should be empty. You can override it per the override instructions http://static.springsource.org/sprin...g-started.html (Overriding Components from Spring Batch Admin). You should be able to configure your own DefaultResourceService and inject the context you want.

          Comment


          • #6
            Thanks for the reply mminella, I'll give this a try and hopefully it'll sort out my issue.

            I haven't any files in the META-INF folder yet, they are all stored in my Grails conf/spring folder, so should I stick with the directions above and use the META-INF, or will I create a folder called conf/spring/override within grails-app?

            Thanks again for your help,
            Tony

            Comment


            • #7
              In order for admin to pick up your override configuration, the file must be at that path.

              Comment


              • #8
                Hi mminella,

                I did what you suggested and moved the declaration of the DefaultResourceService bean from my spring xml file in conf/spring to a file called override-context.xml in META-INF/spring/batch/override but it had no affect.

                The URLs in the source of the pages generated are still looking for resources at /myapp/whatever instead of /myapp/batch/whatever. Below is my entire override-context.xml file.

                Have you any idea why this file isn't being picked up?

                Many Thanks,
                Tony

                Code:
                <?xml version="1.0" encoding="UTF-8"?>
                <!DOCTYPE beans PUBLIC "-//SPRING//DTD BEAN//EN"
                   "http://www.springframework.org/dtd/spring-beans.dtd">
                
                <beans>
                	<bean id="resourceService" class="org.springframework.batch.admin.web.resources.DefaultResourceService">
                	    <property name="servletPath" value="/batch" />
                	</bean>
                </beans>

                Comment


                • #9
                  So a work-around here is to make a META-INF/spring/batch/override/ folder structure underneath the conf section in your Grails project. If you put the override context in here it picks it up!

                  All the job and execution pages are now visible correctly, which is great.

                  The one outstanding piece is the links on the very top menu, the links labeled "Home", "Jobs", "Executions", and "Files" are still not working correctly.

                  Looking at the page source, I can see they are pointing at:

                  Code:
                  <li><a href="/myapp/batch">Home</a></li>
                  <li><a href="/myapp/batch/jobs">Jobs</a></li>
                  <li><a href="/myapp/batch/jobs/executions">Executions</a></li>
                  <li><a href="/myapp/batch/files">Files</a></li>
                  Which I would have thought is correct, but clicking on, for instance the "Jobs" link gives me a 404:

                  HTTP Status 404 - /myapp/WEB-INF/grails-app/views/jobs.jsp

                  So it still looks like for some pages, Grails is tryingto take over and look for a jobs page in Views. Which is strange because I have my servlet mapping set to the following in my web.xml:

                  Code:
                  <servlet-mapping>
                  	<servlet-name>Batch Servlet</servlet-name>
                  	<url-pattern>/batch/*</url-pattern>
                  </servlet-mapping>
                  Any advice would be great. I'll keep updating if I find out more.

                  Cheers,
                  Tony

                  Comment


                  • #10
                    What is the servlet mapping for the grails servlet? It's been a while since I played with this type of thing but I'm wondering if it's more broadly mapped so the request is going there instead. Just brainstorming...

                    Comment


                    • #11
                      Hey mminella,

                      I generated the web.xml using the install-templates command. It's at src/war/web.xml

                      The only other servlet mapping in there besides the one I put in for my batch servlet is the gsp one. There doesn't seem to be any for the grails servlet:

                      Code:
                          <servlet-mapping>
                              <servlet-name>gsp</servlet-name>
                              <url-pattern>*.gsp</url-pattern>
                          </servlet-mapping>
                      The actual servlets are defined above it then:

                      Code:
                          <!-- Grails dispatcher servlet -->
                          <servlet>
                              <servlet-name>grails</servlet-name>
                              <servlet-class>org.codehaus.groovy.grails.web.servlet.GrailsDispatcherServlet</servlet-class>
                              <load-on-startup>1</load-on-startup>
                          </servlet>
                      
                          <!-- The Groovy Server Pages servlet -->
                          <servlet>
                              <servlet-name>gsp</servlet-name>
                              <servlet-class>org.codehaus.groovy.grails.web.pages.GroovyPagesServlet</servlet-class>
                          </servlet>
                      Maybe I should add one for the grails servlet? A simple "/"? But I woulda thought my Batch pattern of "/batch/*" would still work.

                      I'll add in another mapping and see what happens. If you think of anything else, let me know, and thanks for your help so far, too.

                      Tony

                      Comment


                      • #12
                        I added in the following servlet mapping to the web.xml:

                        Code:
                                <servlet-mapping>
                        		<servlet-name>grails</servlet-name>
                        		<url-pattern>/*</url-pattern>
                        	</servlet-mapping>
                        Now it doesn't seem to be going to /grails-app/views/ anymore but I still get a 404 just saying that "the requested resource () is not available" when I hit any of the links at the top of the batch admin pages:

                        Code:
                        <li><a href="/myapp/batch">Home</a></li>
                        <li><a href="/myapp/batch/jobs">Jobs</a></li>
                        <li><a href="/myapp/batch/jobs/executions">Executions</a></li>
                        <li><a href="/myapp/batch/files">Files</a></li>
                        So it's like the pages are actually missing.

                        Does anyone know what page it should redirect to when it goes to, say: /myapp/batch/jobs? Like, is it /myapp/batch/jobs/index.jsp? Or /myapp/batch/jobs/home.jsp?

                        What's also strange is that if I go to /myapp/batch I get a 404 (this is the "Home" link above), but /myapp/batch/ works fine!

                        Cheers,
                        Tony

                        Comment


                        • #13
                          I turned on extra logging and it does look like the grails servlet is still having an effect.

                          Here is the stack trace for the sample batch admin project when the jobs page is rendered correctly:

                          Code:
                          15:04:59,191 DEBUG tomcat-http--5 datasource.DataSourceUtils:110 - Fetching JDBC Connection from DataSource
                          15:04:59,192 DEBUG tomcat-http--5 datasource.DataSourceUtils:332 - Returning JDBC Connection to DataSource
                          15:04:59,193 DEBUG tomcat-http--5 freemarker.AjaxFreeMarkerView:328 - Added model object 'body' of type [java.lang.String] to request in view with name 'jobs'
                          15:04:59,194 DEBUG tomcat-http--5 freemarker.AjaxFreeMarkerView:328 - Added model object 'titleText' of type [java.lang.String] to request in view with name 'jobs'
                          15:04:59,194 DEBUG tomcat-http--5 freemarker.AjaxFreeMarkerView:328 - Added model object 'jobs' of type [java.util.ArrayList] to request in view with name 'jobs'
                          15:04:59,194 DEBUG tomcat-http--5 freemarker.AjaxFreeMarkerView:328 - Added model object 'titleCode' of type [java.lang.String] to request in view with name 'jobs'
                          15:04:59,195 DEBUG tomcat-http--5 freemarker.AjaxFreeMarkerView:328 - Added model object 'totalJobs' of type [java.lang.Integer] to request in view with name 'jobs'
                          15:04:59,195 DEBUG tomcat-http--5 freemarker.AjaxFreeMarkerView:328 - Added model object 'endJob' of type [java.lang.Integer] to request in view with name 'jobs'
                          15:04:59,196 DEBUG tomcat-http--5 freemarker.AjaxFreeMarkerView:328 - Added model object 'startJob' of type [java.lang.Integer] to request in view with name 'jobs'
                          15:04:59,196 DEBUG tomcat-http--5 freemarker.AjaxFreeMarkerView:328 - Added model object 'springMacroRequestContext' of type [org.springframework.web.servlet.support.RequestContext] to request in view with name 'jobs'
                          15:04:59,196 DEBUG tomcat-http--5 freemarker.AjaxFreeMarkerView:328 - Added model object 'jobName' of type [java.lang.String] to request in view with name 'jobs'
                          15:04:59,197 DEBUG tomcat-http--5 freemarker.AjaxFreeMarkerView:328 - Added model object 'servletPath' of type [java.lang.String] to request in view with name 'jobs'
                          15:04:59,197 DEBUG tomcat-http--5 freemarker.AjaxFreeMarkerView:279 - Rendering FreeMarker template [/layouts/html/standard.ftl] in FreeMarkerView 'jobs'
                          And here is the output from myapp when I try to access the jobs page. Note that the Freemarker output is looking for a view with name 'null' now instead of a view with name 'jobs':

                          Code:
                          2012-12-04 14:57:57,182 ["http-bio-8080"-exec-4] DEBUG datasource.DataSourceUtils  - Fetching JDBC Connection from DataSource
                          2012-12-04 14:57:57,185 ["http-bio-8080"-exec-4] DEBUG datasource.DataSourceUtils  - Returning JDBC Connection to DataSource
                          2012-12-04 14:57:57,203 ["http-bio-8080"-exec-4] DEBUG servlet.DispatcherServlet  - Rendering view [org.springframework.web.servlet.view.JstlView: unnamed; URL [/WEB-INF/grails-app/views//jobs.jsp]] in DispatcherServlet with name 'Batch Servlet'
                          2012-12-04 14:57:57,204 ["http-bio-8080"-exec-4] DEBUG view.JstlView  - Added model object 'jobs' of type [java.util.ArrayList] to request in view with name 'null'
                          2012-12-04 14:57:57,204 ["http-bio-8080"-exec-4] DEBUG view.JstlView  - Added model object 'totalJobs' of type [java.lang.Integer] to request in view with name 'null'
                          2012-12-04 14:57:57,204 ["http-bio-8080"-exec-4] DEBUG view.JstlView  - Added model object 'jobName' of type [java.lang.String] to request in view with name 'null'
                          2012-12-04 14:57:57,204 ["http-bio-8080"-exec-4] DEBUG view.JstlView  - Added model object 'endJob' of type [java.lang.Integer] to request in view with name 'null'
                          2012-12-04 14:57:57,204 ["http-bio-8080"-exec-4] DEBUG view.JstlView  - Added model object 'startJob' of type [java.lang.Integer] to request in view with name 'null'
                          2012-12-04 14:57:57,209 ["http-bio-8080"-exec-4] DEBUG view.JstlView  - Forwarding to resource [/WEB-INF/grails-app/views//jobs.jsp] in InternalResourceView 'null'
                          2012-12-04 14:57:57,212 ["http-bio-8080"-exec-4] DEBUG support.DefaultListableBeanFactory  - Returning cached instance of singleton bean 'pluginManager'
                          2012-12-04 14:57:57,212 ["http-bio-8080"-exec-4] DEBUG support.DefaultListableBeanFactory  - Returning cached instance of singleton bean 'grailsApplication'
                          2012-12-04 14:57:57,214 ["http-bio-8080"-exec-4] DEBUG annotation.RequestMappingHandlerMapping  - Looking up handler method for path /WEB-INF/grails-app/views/jobs.jsp
                          2012-12-04 14:57:57,214 ["http-bio-8080"-exec-4] DEBUG annotation.RequestMappingHandlerMapping  - Did not find handler method for [/WEB-INF/grails-app/views/jobs.jsp]
                          2012-12-04 14:57:57,214 ["http-bio-8080"-exec-4] WARN  servlet.PageNotFound  - No mapping found for HTTP request with URI [/myapp/WEB-INF/grails-app/views/jobs.jsp] in DispatcherServlet with name 'grails'
                          2012-12-04 14:57:57,215 ["http-bio-8080"-exec-4] DEBUG servlet.DispatcherServlet  - Successfully completed request
                          It is trying to render /WEB-INF/grails-app/views/jobs.jsp (even tho the servlet mentioned is the Batch Servlet and not the grails one) instead of the normal jobs.ftl freemarker layout page.

                          I think I'm close to giving up on this. Btw, I also explicitly added freemarker version 2.3.19 to my buildconfig but no dice.

                          Tony

                          Comment

                          Working...
                          X