configureWebserverDefinition.jacl

Per Web
server plug-in installation doc (step 19)
, we should copy the
configureweb_server_name.bat script, generated by
the plugin installer, to the WAS_HOME/bin directory and run it
in order to map the installed applications to the Web server. This was giving us problems on Windows 2003, such as this:

Configuration save is not complete, exception = com.ibm.ws.scripting.ScriptingException:
com.ibm.websphere.management.exception.ConfigServiceException:
WKSP0008E RepositoryException while checking the state of
cells/mycell/applications/application.ear/deployments/application/foo.jar/META-INF/ibm-ejb-jar-ext.xmi
in the master repository -com.ibm.ws.sm.workspace.WorkSpaceException:
WKSP0016E Error get digest for cells/mycell/applications/application.ear/deployments/application/foo.jar/META-INF/ibm-ejb-jar-ext.xmi.workspace_save – java.io.IOException: The system cannot find the specified file, either the filename is too long on Windows system or run out of file descriptor on UNIX platform. java.io.FileNotFoundException: D:optWebSphereAppServerprofilesAppSrv01wstempScript10afa2477bfworkspacecellsmycellapplicationsapplication.eardeploymentsapplicationfoo.jarMETA-INFibm-ejb-jar-ext.xmi.workspace_save (The handle is invalid.)

WASX7309W: No “save” was performed before the script “D:optWebSphereAppServerbinconfigureWebserverDefinition.jacl” exited; configuration changes will not be saved.

What is happening is twofold.

First, the
configureWebserverDefinition.jacl does a save only at the end, which fails for all installed applications. To narrow the problem down, I put $AdminConfig reset after foreach Application $ApplicationList {, and moved the

 if {[catch {$AdminConfig save} result]} {
 puts "Configuration save is not complete, exception = $result"
 } else {
 puts "Configuration save is complete."
 }
 

block from the end of the script into the else clause of

 if {[catch {$AdminApp edit $Application [subst {-MapModulesToServers {$targetMapList } } ]} result]} {
 puts "Target mapping is not updated for the application $Application, exception = $result"
 } else {
 puts "Target mapping is updated for the application $Application"
 ...
 

I think saving this per-application is better, at least for narrowing the problematic apps down, but I suppose it’s a matter of preference…

Now we see that all applications except for two are being updated. Without digging into what exactly is special about those two, it’s enough to go to the “Map modules to servers” in WAS console for any other app to see that the JACL script mapped all modules to the web server – including the EJB modules. Not only is that silly and useless, but also is causing “the filename is too long” thing. So we add another condition into the configureWebserverDefinition.jacl to only map Web modules to the web server, by
changing the block where we set targetMapList as follows:

 #--------------------------------------------------------------
 # Check if web server is already defined as the target
 #--------------------------------------------------------------
 set index [string first $newTarget $currentTargets]
 
 set targetMapList "$targetMapList { {$moduleName} $moduleUri $currentTargets }"
 if {($index < 0) } {
 set isWebModule [string first ".war,WEB-INF/web.xml" $moduleUri]
 if {( $isWebModule < 0)} {
 puts "$moduleUri is not a Web module, skipping..."
 } else { 
 puts "Will map $moduleUri to $newTarget"
 set targetMapList "$targetMapList { {$moduleName} $moduleUri $currentTargets+$newTarget }" 
 }
 }
 

The configureWebserverDefinition.jacl modified as above is at
Misc
module of jSewer project on SourceForge
.

ReflectiveVisitor

Inigo Surguy presents< an implementation of Visitor pattern based on reflection. I found useful a slight modification of it, that allows for visiting not only the narrowest type, but every type possible , based on the visitAll flag: ReflectiveVisitor.java. This functionality comes in quite handy for tasks such as, for instance, validation. For example, if one has a complex class hierarchy (especially with multiple< inheritance) and different types have different requirements for it to be valid, and a concrete instance may implement a number of those, these validations can be well separated out.

See also:

  1. Visiting Collection elements
  2. Depth-first polymorphism