This document is a portal into the Micro Focus community documentation on JVM COBOL web services. Web Services in Visual COBOL 2.2 This section covers the web service tutorials, technologies and best practices as they apply to Micro Focus Visual COBOL 2.2. Visual COBOL 2.2 - JSP Web Services Tutorial : This tutorial covers the creation of a JSP web service that uses a procedural JVM COBOL program to implement the business logic. Visual COBOL 2.2 - REST Web Services Tutorial : This tutorial covers the creation of a REST web service that uses a procedural JVM COBOL program to implement the business logic. It uses JQuery to implement a web client for the service. Visual COBOL 2.2 - SOAP Web Services Tutorial : This tutorial covers the creation of a SOAP web service that uses a procedural JVM COBOL program to implement the business logic. Visual COBOL 2.2 - SOAP Web Services Client Tutorial : This tutorial covers the creation of a SOAP web service client that uses the SOAP Web Service. Visual COBOL 2.2 - Building Web Services from a Build Infrastructure . This shows how web services can be build outside Eclipse from the command line or part of a larger build system. Web Services in Visual COBOL 2.1 This section covers the web service tutorials, technologies and best practices as they apply to Micro Focus Visual COBOL 2.1. Visual COBOL 2.1 - JSP Web Services Tutorial : This tutorial covers the creation of a JSP web service that uses a procedural JVM COBOL program to implement the business logic.
↧
Wiki Page: Visual COBOL - JVM Web Services Portal
↧
Wiki Page: Building JVM COBOL Web Service Applications from a Build Infrastructure
Introduction In the Visual COBOL 2.2 - JSP Web Services Tutorial [2] we created a JSP Web Service Application using JVM COBOL and Java in Visual COBOL for Eclipse. If you want to build the application outside of Eclipse as part of a larger automated build infrastructure, then this article shows how to use ant to build the complete application ready to be deployed. One of the advantages of using ant is the XML file used to control the build process can be the same for Windows and UNIX. The COBOL projects created by Eclipse use ant under the covers and by re-using this, you get the build of your COBOL code for free with no need to maintain a separate set of batch, shell or make files. Ant also contains tasks which make building the rest of the application straight forward, compiling the Java source code and creating the W eb application AR chive file or WAR for short. This article provides a template build.xml which can be adapted for similar shaped Web Service Applications involving JVM COBOL. Some familiarity with ant is assumed. See the reference section for more information on ant [1]. Build.xml This article walks you through creating an ant build.xml. The build.xml file will build a COBOL project and Java source code, and then combine them, plus any additional files, into a WAR file. If you want to work with the build.xml in Eclipse then we recommend adding it to the Java project. The rest of the article assumes it has been added to the JSPBookDemo project. Building the JVM COBOL Project Many customers have already asked how to build the . cobolBuild ant file which is created when an Eclipse COBOL project is created[ 3]. For our purposes we want to have ant call this as part of our overall build.xml file. This is done simply by using the ant task. property name= "COBOLProject" value= "" / target name= "buildCOBOL" ant antfile= ".cobolBuild" dir= "${COBOLProject}" / /target The Property COBOLProject can be hard coded into the file or set via the command line. Because the . cobolBuild XML file contains Micro Focus custom ant tasks the Micro Focus ant libraries which provide the functionality for these task need to be made available to ant. This is a fragment of the command line. ant - lib "%COBDIR%\bin\mfant.jar" - lib "%COBDIR%\bin\ant- contrib -1.0b3.jar" - DCOBOLProject =..\ CobolBook Command Line This example command line specifies the Micro Focus custom ant task libraries, setting up the COBOL project name, specifying the war file name and an application server specific directory for jar files which are needed for the servlet or other APIs. It is assumed that it is executed in the Java Project directory and hence the COBOL Project contains a relative path. Ant looks for a default of build.xml. If you wish to call the ant file something else then use the ant –f option to specify the XML file. Execute from a Visual COBOL prompt on Windows or run $COBDIR/bin/ cobsetenv on UNIX. Make sure ant is on your PATH. ant - lib "%COBDIR%\bin\mfant.jar" - lib "%COBDIR%\bin\ant- contrib -1.0b3.jar" - Dappservercp = application server libraries directory - DCOBOLProject =..\ CobolBook - Dappname = JSPBookDemo Ant will search CLASSPATH for anything it needs, so one could also specify the jars on the CLASSPATH. Building the Java Source Code The Java ant task javac is used to build the Java source code. It has the advantage that you can just point it at the package directory structure and it works out the rest. The path element allows the build up of the required CLASSPATH for the javac task. This includes specifying the location of the JVM COBOL class files as well as the application server API libraries. path id= "appclasspath" fileset dir= "${appservercp}" include name= "**/*.jar" / /fileset pathelement path= "${COBOLProject}/bin" / /path target name= "buildJava" depends= "buildCOBOL" javac srcdir= "${JAVAProject}/src" classpathref= "appclasspath" / /target Building the WAR File The architecture of a war file can be found from the application server documentation [4] and additional requirements may be required depending on application server. It is easy enough to update this task to include additional files. To build the deployment WAR file and include all the classes from the various projects plus additional configuration files the war ant task is used. target name= "buildWar" depends= "init,buildJava,buildCOBOL" war destfile= "${appname}.war" webXML= "${JAVAProject}/WebContent/WEB-INF/web.XML" classes dir= "${JAVAProject}/${JAVAclasses}" include name= "**/*.class" / include name= "**/*.properties" / /classes classes dir= "${COBOLProject}/${COBOLclasses}" include name= "**/*.class" / include name=" **/*.cbldat" / include name= "**/*.properties" / /classes lib dir= "${COBDIR}/${libdir}" include name= "**/mfcobol.jar" / include name= "**/mfcobolrts.jar" / include name= "**/mfsqljvm.jar" / /lib fileset dir= "${JAVAProject}/WebContent" include name= "**/*.jsp" / /fileset /war /target classes denotes the WAR classes directory, lib denotes the WAR lib directory and fileset includes files at the top level. Also of note is the inclusion of the MF JVM COBOL Runtime System. If you don’t use SQL, you can remove this line include name= "**/mfsqljvm.jar" / Deployment See your web server documentation for the vendor specific deployment steps. Deployment tools are usually made available or auto-deploy directories you can copy war files straight into. The Complete Build.XML All these elements have been combined to form a complete ant XML file. The additional elements take settings from the environment and configure items which are OS specific. The first target to be executed by and is specified in the attribute default= " buildWar " . Then there is a small depends chain which makes sure the target nodes get executed in the correct order. If you want to add new ones make sure they are chained together properly. Properties can be given specific values and overridden from the command line using – Dproperty -name=property-value. project name= "WebApp" default= "buildWar" basedir= "." !-- ****************************** -- !-- * Initialisation * -- !-- ****************************** -- target name= "init" depends= "os.init,os.init.windows,os.init.unix" !-- Properties from the environment -- property environment= "env" / property name= "COBDIR" value= "${env.COBDIR}" / !-- Application Server specific libraries -- property name= "appservercp" value= "" / !-- Name of war file -- property name= "appname" value= "JSPBookDemo" / !-- Project directores -- property name= "COBOLProject" value= "" / property name= "JAVAProject" value= "${basedir}" / !-- Location of class files in each project directory -- property name= "COBOLclasses" value= "bin" / property name= "JAVAclasses" value= "build/classes" / /target !-- ****************************** -- !-- * OS-specific initialisation * -- !-- ****************************** -- target name= "os.init" condition property= "windows" os family= "windows" / /condition condition property= "unix" os family= "unix" / /condition /target target name= "os.init.windows" if= "windows" property name= "libdir" value= "bin" / /target target name= "os.init.unix" if= "unix" property name= "libdir" value= "lib" / /target !-- ****************************** -- !-- * Build COBOL Project * -- !-- ****************************** -- target name= "buildCOBOL" ant antfile= ".cobolBuild" dir= "${COBOLProject}" / /target !-- ****************************** -- !-- * Build Java Source code * -- !-- ****************************** -- path id= "appclasspath" fileset dir= "${appservercp}" include name= "**/*.jar" / /fileset pathelement path= "${COBOLProject}/bin" / /path target name= "buildJava" depends= "buildCOBOL" javac srcdir= "${JAVAProject}/src" classpathref= "appclasspath" / /target !-- ****************************** -- !-- * Build War file * -- !-- ****************************** -- target name= "buildWar" depends= "init,buildJava,buildCOBOL" war destfile= "${appname}.war" webxml= "${JAVAProject}/WebContent/WEB-INF/web.xml" classes dir= "${JAVAProject}/${JAVAclasses}" include name= "**/*.class" / include name= "**/*.properties" / /classes classes dir= "${COBOLProject}/${COBOLclasses}" include name= "**/*.class" / include name= "**/*.cbldat" / include name= "**/*.properties" / /classes lib dir= "${COBDIR}/${libdir}" include name= "**/mfcobol.jar" / include name= "**/mfcobolrts.jar" / include name= "**/mfsqljvm.jar" / /lib fileset dir= "${JAVAProject}/WebContent" include name= "**/*.jsp" / /fileset /war /target /project Conclusion The . cobolBuild ant file which is created when any Visual COBOL for Eclipse COBOL project is created can easily be integrated into a build infrastructure which does not require the Eclipse IDE. This means you don’t need to worry about trying to replicate and deal with the subtleties of the class structure of a JVM COBOL project. Other ant tasks are easy to use and this build.XML can be scaled up to include additional projects in the workspace. References 1. Apache Ant Manual 2. Visual COBOL 2.2 JSP Web Services Tutorial 3. Build JVM COBOL by ant 4. War Directory Structure (Oracle WebLogic )
↧
↧
Forum Post: Story Status
You can change the story status from "Completed" to "Accepted". What is the difference between the two? Would "Completed" indicate that work was completed by the developer and "Accepted" indicate that it was accepted by the Stakeholder? That's my guess... but I would like to confirm.
↧
Forum Post: RE: Difference in Configuration settings of MF Enterprise Server 6.0 with Netexpress 5.1 and Enterprise Server with Enterprise Developer 2.2
Thanks Michael for your response. Current setup is used only for JCL execution and no CICS is involved. I will let you know if this solution works.
↧
Forum Post: RE: Story Status
Yes, that is correct. Correct status would typically be when the developer is finished. Then if the story is deemed to meet acceptance criteria set it is marked as Accepted. When a story has been accepted, it becomes read only and any remaining task hours are removed from the burndown calculation.
↧
↧
Forum Post: RE: Story Status
some further information for you.. community.microfocus.com/.../24500.story-acceptance.aspx community.microfocus.com/.../23209.how-to-accept-stories.aspx
↧
Wiki Page: Error in loading Security manager list
Problem: The customer has MF COBOL installed on a machine where both dev1 and dev2 regions are running. The machine also has an OpenLDAP client installed. OpenLDAP server is running on another server. On this server, the user created a standard MF application containers and added default MFDS users, user groups and resources. When they added mldap_esm in Enterprise server as external security manager they are getting a connection error. SF0027E Error 16/101/4 SAFMGR initialization failed: Error reported by ESM Module Journal.txt show: 8301:4112513904 SA0203C ESM Module "LDAP" initialization failed (code 4) 8301:4112513904 SA1010E ESM1: Could not connect to LDAP server 8301:4112513904 SA1020E ESM1: Could not connect to LDAP Server at "camdv2lmfc01:389" and the ldapsearch command executed successfully from LDAP client to LDAP server: /usr/bin/ldapsearch -x -b 'dc=cammis-xerox,dc=com' -h camdv2lmfc01 -D "cn=admin,dc=cammis-xerox,dc=com" -w "0p3nld@p" schema.txt We did search if their client has any openldap directory, and the only place is in /lib64. /lib64/libldap-2.4.so.2 /lib64/libldap-2.4.so.2.5.6 /lib64/libldap_r-2.4.so.2 /lib64/libldap_r-2.4.so.2.5.6 Solution: As the above messages show, the ES attempted to connect to the LDAP server, and it failed. From the find command results that is used to locate openldap files on a Unix, it appears that the user only have the 64bit LDAP client libraries installed. If the DEV region is 32bit, then the LDAP libraries that we will call will need to be 32bit as well. After installing 32 bit openLDAP libraries, the user was able to connect LDAP server with openLDAP.
↧
Wiki Page: User mfuser not authorized to start ES "DEVA1CA1", region terminating.
Problem: MFDS is being run under External security manager MLDAP. A problem is seen when starting the regions DEVA and DEVB. Console log shows "User mfuser not authorized to start ES "DEVA1CA1", region terminating.". Note that mfuser has been assigned to the group #GAdmin and #DSAdmin. Console.log: 140204 08322959 31451 DEVA1CA1 ESFMI0200I Loaded module mldap_esm for ESM (1) "MLDAP": MLDAP ESM version 1.16.2 08:32:29 140204 08322966 31451 DEVA1CA1 CASSE0033E User mfuser not authorized to start ES "DEVA1CA1", region terminating. 08:32:29 Solution: As the above messages show, they are getting permission error when starting a region using casstart. The error message means that default user mfuser needs to be added to external security module. The mfuser must exist and must be part of the OPERCMDS group (this is the group that allows you to run casstart/casstop). Alternatively they can use another user that is already part of that group using /u /p (if they are using the command-line to start the region or via the user password fields in ES Admin) Ex. casstart /rREGION /uSYSAD /pSYSAD
↧
Forum Post: RE: Starting Enterprise server after fresh install- Facing CASSI4002W
Dear Michael, Thanks for your quick response. The product is Microfocus Enterprise Server with eclipse as IDE and the operating system is windows xp. I pinged the hostname and it is getting resolved in ip address and as you mentioned I am able to see MFDS so there should be no issue with firewall. Still facing the same issue. Do I need to setup some user profiles for E.S and MFDS to make this work?
↧
↧
Forum Post: How to create a drop down using MF CObol and unix
Hi , I want to create a drop down using MF Cobol in unix environment. Is is possible?. I am trying to accept a char by using "HGETCH" and I am passing that char to file as input to read the record. Is it possible to keep getch in standby to accept another key from key board. Let me know
↧
Forum Post: RE: Starting Enterprise server after fresh install- Facing CASSI4002W
What version of Micro Focus Enterprise Server are you running? It's not clear to me exactly what you're using. Enteprise Server itself doesn't use an IDE; only the development products (Net Express, Studio, Enterprise Developer, etc) have an IDE. And I don't recall any of our development products supporting both Eclipse and Windows XP. If you haven't changed the sample configuration installed with the product, then you don't need to modify any settings. It should be possible to start the ESDEMO region out of the box. Being able to view the Enterprise Server Administration site doesn't guarantee there are no firewall issues - the firewall could be allowing TCP but blocking UDP. Only TCP is required for the admin UI, but both TCP and UDP must be allowed for the region to start. If your system has multiple network interfaces, MFDS could be telling CAS to use the wrong one. Try the following: Using the Start menu, open an Enterprise Server 32-bit command prompt. There should be a shortcut for that in the Enterprise Sever folder in the Programs menu (possibly under "Tools" or some such). In that window, run the "casstart" command. If the region starts successfully, then the problem has something to do with what parameters MFDS is passing to casstart when you try to start the region from the GUI. That requires further investigation (and you should probably open a support incident for it). If the region doesn't start, we'll need to see the CAS log. That's a file named "console.log". I don't remember where this is created by default under XP, and in any case I don't know what product you're actually running, so you'll have to search for it, I'm afraid.
↧
Forum Post: RE: How to create a drop down using MF CObol and unix
Which Micro Focus product are you using, OCDS, Server Express, Visual COBOL? The getch is a C function to return a character entered at the console. If you just want to check if a character exists in a loop you could try something like shown in the article here : Thanks
↧
Forum Post: RE: Progress Bar Example - Wpf
Hey Werner, That would be great if you could work that into the solution you sent before. Thanks.
↧
↧
Forum Post: DLL IN PROJECT
I have a program that is included in one Project which is compiled as DLL. This same DLL is called from a lot of other programs. Every thing Works perfectly, but how can I find out in a simple way in which Project is included the source file? Of course one way is to open all my APP files and look at the Project window, where this source file appears. But is there not an easier way, because I have many APP thanks
↧
Forum Post: RE: Having Problems With Rumba 8.2 in Windows 7 - Macros not working correctly.
The issue turned out to be the use of the profile file from the earlier version of Rumba. When I upgraded to 8.2 I saved my profile file from the prior version and used that to start up 8.2. Something in the old profile prevented the message macro command from working. I started with a new profile and set it up the same as the old one using the proper menu selections and the message macro command has worked fine ever since. So the lesson here is that you must build up your profile from scratch when you upgrade to a newer version of Rumba. If you try to carry your old profile file forward you may have unexpected results. Perhaps Micro Focus might consider creating a profile converter and making it available as a download for folks who upgrade. Depending on the amount of customizing, recreating a profile from scratch can be very lengthly and tedious.
↧
Forum Post: RE: slow performance with concurrent users
Hi, First lot of thanks for the answers. - We open files with I-O, due to that users have to make modifications on the file - Opportunistic lock is desactivated in our installations on the server machine. - Talking about acuserver, I'm asking if my company will have to buy a special license or just with the wrun32 license we have right to use acuserver. Thanks again!
↧
Wiki Page: Visual COBOL 2.2 - JSP Web Services Tutorial
Document Support Material This document depends upon many different technologies. While it tries to cover the material as completely as possible it is not viable to present an exhaustive view of the topic. The material listed below references any extra material that is related to the topic. It should not be necessary to complete the tutorial but will make it easier to understand the material. Java - Java is used to implement our web service and call out to our COBOL code that implements the core functionality of the service. At least a rudimentary understanding of Java is required for this tutorial. Java Servlets - Java Servlets are the core technology in the Java Enterprise Edition stack for handling web services. This tutorial aims to demonstrate the reuse of traditional COBOL programs in a JVM JSP application. The tutorial will use Visual COBOL 2.2. Version 2.5 of the servlet API will be used. The tutorial will be created with Tomcat version 7 in mind though it will be possible to use it with any supported servlet container. To complete this application we will create a JVM COBOL project containing our traditional COBOL program. We will create an Eclipse Web Tool Platform (WTP) Dynamic Web project. This web project will call the COBOL program using the Micro Focus smart linkage facility. It will cover development and debugging of the application. We will create the JSP view and dispatch code in Java. The sole usage of COBOL will be in the original unchanged COBOL program. There is an attached source code archive for this tutorial. You can acquire it here . You should download this and store it on your machine. The location it is stored at will be referred to as SRC_DIR in this tutorial. First Time Setup If this is your first time doing this tutorial you will need to setup your environment to run JVM COBOL JSP applications. You will need to install and setup Micro Focus Visual COBOL for Eclipse 2.2. You also need to install your servlet container/Java Enterprise Edition server (Tomcat, JBoss, etc) and setup the Micro Focus JVM COBOL runtime to be accessible in that environment. Links to those steps are below: Micro Focus COBOL: Windows UNIX Servlet Containers Create Workspace The first thing you need to do is create the workspace that will contain all the projects. Open Micro Focus Visual COBOL for Eclipse and pick an appropriate path as the workspace when prompted (the tutorial will refer to this location as WORKSPACE or just as 'the workspace'). Click Ok and Eclipse will create the workspace at that location automatically if it doesn't already exist. We will be adding several projects to this workspace to create the application. JVM COBOL Project Firstly we will create a project to contain our procedural COBOL program and make it available for execution from a Java program. The steps to do this are as follows: Click File - New - Other. Expand the Micro Focus COBOL node and select COBOL JVM Project . Click Next . Set the Project name field to "CobolBook". Ensure Use default location is checked. Ensure that the JRE is set up to use a Java 6 VM. Click Finish . This will create a blank JVM COBOL project which can contain our procedural COBOL program and be imported into our web application later. If it asks you to switch to the COBOL perspective then do so. To change perspectives later you can click on the appropriate option in the top right of the Eclipse main window (see the image below). In general any action that uses the CobolBook project will be expected to be executed in the COBOL perspective unless otherwise specified. The dynamic web project that comes later will expect actions to be executed in the Java EE perspective. The Eclipse Perspective Bar One aspect of Java it is necessary to adapt our program to is the Java packaging system. By default COBOL programs will be placed in the default root Java package. JVM servlet containers do not always allow root package classes to be loaded so we will need to set up a package for our program. For reference the Java package system is equivalent to the JVM COBOL namespace system. These two terms are interchangeable. To do set up the package right click on src in the CobolBook project of the COBOL Explorer in the top left of Eclipse. Now select New- COBOL JVM Package . In the dialog insert the text "com.microfocus.book" into the Name text field. Click Finish to create the package. This will create a directory structure in our workspace in which we can store our COBOL program. If you have the source code attached to this project you can copy SRC_DIR /CobolBook/src/com/microfocus/book/book.cbl to the equivalent directory in WORKSPACE . You should also copy SRC_DIR /src/book-rec.cpy to the equivalent location in the workspace. If you do not have the source archive you can create these files as follows. Right click on src in the CobolBook project in the COBOL Explorer tab and select New- COBOL Copybook . Ensure the Containing project text box contains "CobolBook/src". If not alter it so it does. Then in the New file name text box enter "book-rec.cpy". Click finish to create the copybook. Now replace the entire content of the opened file with the text in book-rec.cpy . Similarly to create book.cbl right click on src/com/microfocus/book in the CobolBook project. Select New- COBOL Program . Ensure the Containing project text box contains "CobolBook/src" again. The Package text box should contain "com.microfocus.book". Enter "book.cbl" in the Name text box. Click finish to create the COBOL program. Now replace the entire content of the opened program with the text in book.cbl . Putting the program in the right directory structure is only half the requirement to put it in the right package. You need to alter the program to specify the correct namespace as a qualified program name. Alternatively you can set a compiler directive either globally to the project or in the program using the $set syntax. For this tutorial we will set a global compiler directive. We have only one program so no need for program specific directives. This also allows us to avoid altering our COBOL program. In other situations it may make more sense to make your programs use different namespaces. In that case you should use program local directives or a qualified program name. Regardless to set compiler directives open the project properties for CobolBook by right clicking on the CobolBook node and clicking Properties . Expand Micro Focus COBOL and choose Build Configuration . At the bottom there is a box which is labelled as Additional directives . Here we will enter our project global directives. Add the line "ilnamespace(com.microfocus.book)" to that text box. Click OK to save the new directives. This will now generate a COBOL program that is in the specified namespace. When you import this into Java the namespace will interact appropriately with Java packages. Now look in the directory bin/com/microfocus/book in the COBOL Explorer . In there you will see a BookLegacy.class and a BookLegacy.cbldat file. These together form your COBOL program specified by book.cbl. There is one other facility we will use to make life easier when calling the book demo program from Java. That is Micro Focus Smartlinkage. This is a tool that converts between traditional COBOL group item types and Java types. So a pic x(99) will be exposed as a Java String. A comp-5 item will become a Java int. This makes calling COBOL programs from Java much easier. There are three compiler directives we will be adding to support this. Add the compiler directive "ilsmartlinkage" on a new line in the Build Configuration dialog as before. If you save and close this configuration you will notice additional files in bin/com/microfocus/book . These are LnkBDetails.class , LnkFilename.class and LnkFileStatus.class . These are classes generated to represent the linkage items in our book.cbl program. The BookLegacy class will now have an entry point that takes these wrapper classes rather than just taking a generic reference class that gives direct byte access. This simplifies access. If you open book.cbl and hit F4 you will inline any copy books that are copied into this program. If you navigate down to the linkage section you will note the existence of the group items lnk-filename , lnk-file-status and lnk-b-details . These map directly onto the generated classes mentioned above. However we'd prefer to remove the prefixes commonly used in COBOL programs when working in Java. There is a directive to do this. Add the directives "ilcutprefix(lnk-b-)" and "ilcutprefix(lnk-)" to the Build Configuration . When you save and close the dialog your COBOL will be rebuilt. If you look in bin/com/microfocus/book once more you'll note that the prefixes have been removed from the generated class files. This finalises the JVM COBOL project and we will now move onto incorporating this into a web application. Dynamic Web Project Now we will create the JSP component of the application. This project will import the previous project as a dependency. It will be composed of in total: The CobolBook project. A JSP/Bean view that will form our web page. A wrapper interface that will manage our program's interaction with servlet session life cycles. A servlet class that will dispatch to that interface based upon the POST method arguments. A web.xml deployment descriptor. RunUnits and Sessions Before we continue it is useful to talk in more detail about point 3. Many COBOL applications may be single user programs. To adapt these programs into a multi user setting like a web application can be problematic. You will get issues like file locking and memory isolation breaking down because suddenly the same resource set is being used by multiple users. Usually fixing this requires a significant rewrite. Micro Focus has a better solution for this problem. We have a construct known as a RunUnit. This is specified by the JVM COBOL runtime class "com.microfocus.cobol.runtimeservices.RunUnit". Each RunUnit is a new session object. Each contains its own memory space and file lock table. A JVM COBOL program in one RunUnit will not normally access the memory of a program in another RunUnit. There is isolation between them. Also file locks are held per RunUnit. If a program in one RunUnit holds a file lock it will not be accessible to a file handling program in another RunUnit in the same process. This facility makes it easier for us to establish isolation between single user COBOL programs that are being migrated into a multi user environment. To further this we have the concept of a RunUnitManager. Each such manager is designed to manage the life cycle of RunUnit objects in environments with a notion of a session. A RunUnitManager provides a number of services: The creation of a RunUnit when a session starts. The retrieval of a RunUnit already attached to a session. Ensuring that a RunUnit is safelty stopped, and its resources cleaned up, when a session ends. Of particular relevance to this tutorial is the class "com.microfocus.cobol.runtimeservices.servlet.ServletRunUnitManager". This class in the JVM COBOL runtime is set up specifically to handle the life cycle of RunUnits in the context of servlet API HttpSession objects. Creating the Project The steps to create the dynamic web project are as follows: Click File- New- Other . Expand the Web node and select Dynamic Web Project . Click Next . Set the Project name field to "JSPBookDemo". Ensure Use default location is checked. In the Target runtime field either select an already existing servlet container runtime or set one up by clicking New Runtime . To set up a runtime appropriate to your servlet container see here . Set the Dynamic web module version to 2.5. Click Finish . This may ask you to open the Java EE perspective. Do so. As before all commands involving the JSPBookDemo will be expected in the Java EE perspective. Now we need to add appropriate references to the previous project and to the JVM COBOL runtime system. There are two places this must be done: in the build options, so the Java compiler can find the appropriate classes to build against; and in the deployment assembly so that the JVM COBOL program and runtime will be exported into the created web archive. To set up the Java Build Path complete the following: Open the project Properties for the JSPBookDemo as with the CobolBook project. Select Java Build Path . Select the Projects tab. Click the Add... button, check the CobolBook box and click OK . Select the Libraries tab. Click the Add Library... button, select COBOL JVM Runtime System , click Next and finally Finish . Now we need to set up the Deployment Assembly complete the following: In the Properties dialog select Deployment Assembly . Click Apply if asked to save any build path changes. Click Add , select Project and click Next . Select CobolBook and click Finish . Click Add , select Java Build Path Entries and click Next . Select COBOL JVM Runtime System and click Finish . Click OK to exit the Properties dialog. Creating the View The standard way to create a view in a JSP application is to have a JSP page that takes a Java bean (which is an ordinary Java data class) as an attribute. The JSP will then insert the properties from that bean into the appropriate places in the output HTML. Lets start with the JSP page. Right click on the WebContent node in the JSPBookDemo project. Select New- JSP File . Set the File name text box to say BookJsp.jsp. Finally click Finish . You can copy the contents of this file from BookJsp.jsp . If we look at BookJsp.jsp you will see numerous elements that contain text like ${book.stockno} . That states that the JSP will insert the value contained in the stockno property of the book attribute at this point. There are also other such elements like ${rununitid}. These are more direct text attributes that are not directly related to a book entry so have been kept separate. In this case we are passing in the RunUnit ID so we can display it in the title. Once all the ${} entries have been processed the JSP just becomes a simple HTML page containing a form. We will now create the book bean that goes along with this view. Right click on Java Resources and select New- Class . Enter the package "com.microfocus.book" and the class name "BookBean". Click Finish to create the BookBean class. Now enter the code in BookBean This class will contain the information that will be displayed in our JSP view. The dispatch servlet will bind an appropriate bean to the attribute book before calling the JSP. For instance in the previous book.stockno example it will call the getStockno method on BookBean and insert the return value into the JSP output. Converting Status Codes to Exceptions Error handling is very different in Java to procedural languages like COBOL. In Java it is normal to use exceptions rather than error codes to deal with failure and unexpected conditions. Given that our book demo returns a status code we need to convert this into an exception to make it a more natural fit for the JVM. Let's create our exception. As with the bean create a new Java class. Use the same package but call it JavaBookException. Change the superclass to be "java.lang.Exception". Enter the code in JavaBookException . This class is relatively simple. The serialVersionUId is used by the Java serialization mechanism to distinguish between different versions of a class. It has no impact on our program. We have a constructor that takes a String. The status item in the COBOL is a pic xx which will be mapped to a String in Java. So we are taking the status code directly in the constructor when converting the error. We have a Map String, String which relates known status codes to appropriate error messages. We also have a static String for unknown error in case something beyond the expected errors occurs. We pass on the appropriate error message to the superclass constructor and store the status code in a field. Creating the BookInterface The following class really is the most relevant to accessing JVM COBOL from a JSP web application. It will handle the session management and provide a clean interface to Java applications that wish to call the program. It will also handle marshalling between the view bean and the smart linkage Details class from the COBOL program. Firstly create a new Java class as before. Put it in the "com.microfocus.book" package. Give it the name BookInterface. Add the contents from BookInterface . This class is what will handle our session management and integration into a Java environment. Of particular interest are the two constructors listed below. public final IRunUnit runUnit; public final BookLegacy bookLegacy; public BookInterface(HttpSession session) { this(ServletRunUnitManager.getManager().GetSessionRunUnit(session)); } public BookInterface(IRunUnit runUnit) { this.runUnit = runUnit; BookLegacy bookLegacy = (BookLegacy) runUnit.GetInstance(BookLegacy.class); if(bookLegacy == null) { bookLegacy = new BookLegacy(); runUnit.Add(bookLegacy); } this.bookLegacy = bookLegacy; } These constructors handle two separate issues. The lower one handles tying this interface class into a RunUnit. It stores away the RunUnit and gets the program instance of BookLegacy. The upper constructor deals with the servlet's HttpSession object and the ServletRunUnitManager. The interaction here is quite simple. Get the ServletRunUnitManager (which is a singleton) and then call GetSessionRunUnit with the session object. The manager will create a RunUnit if this is the first call with this particular session. It will also manage the shutdown handling routines so that when this session is invalidated the manager will call StopRun on the RunUnit attached to that session. In this short section of code we've managed both the issue of program isolation and that of session life cycles. Not bad for a few lines of code in two constructors. Another interesting line of code is the BOOK_FILE constant near the top of the class. This constant specifies where the bookfile.dat file that contains our book database is on how hard drive. The relevant file is stored in the source archive attached to this tutorial. Store it somewhere on your local drive and update the constant to point to it. The rest of the code is pretty straight forward. We've split the function parameter into separate method calls on this interface. We also have some short code to handle whether we have an error or not. Creating the Servlet The last functional piece of code that needs to be written for this tutorial is the servlet that interprets the incoming POST and GET requests and dispatches to the appropriate interface method. It will then bind the output BookBean into the request and forward that request to the JSP for response. Create a new Java class as before. Put it in the "com.microfocus.book" package. Give it the name BookServlet. Add the contents from BookServlet . There are four interesting parts to this class. The interpretation of the appropriate POST parameters. The resulting calls into BookInterface. The binding of an output BookBean into the request attributes and finally forwarding the request onto our JSP so it can create the response. Lets look at some code in the doProcessing method. String subValue = req.getParameter(SUBMIT_PARAMETER); ... if(subValue.equals(READ_PARAMETER)) { performRead(req, res); } else if(subValue.equals(ADD_PARAMETER)) { performAdd(req, res); } else if(subValue.equals(DELETE_PARAMETER)) { performDelete(req, res); } This code simply grabs the value of the submit parameter from the request object. Then we compare the submit parameter to various known values that perform the appropriate functionality for each function the application provides. Now look in some detail at performRead . BookInterface bookInterface = getBookInterface(req.getSession()); String bookId = BookBean.getStockno(req, res); try { BookBean book = bookInterface.readBook(bookId); outputBook(req, res, book); } catch (JavaBookException e) { outputBookException(req, res, e); } catch (Exception e) { outputException(req, res, e); } This creates a BookInterface by passing in the session object from the request object. Then it gets the stock number from the request parameters. Then it makes a call to readBook on our interface. Finally outputting the BookBean object it gets back by calling outputBook . Lets examine that method. if(book != null) { req.setAttribute("book", book); } else { req.setAttribute("book", BookBean.msgBook("ERROR! book is null in output book")); } This very simply binds the book as a request attribute. Binding it to the name book which was the name used in our JSP view. The JSP will unpack this book object and output its values as described previously. The final part of interest is back in doProcessing RequestDispatcher dispatcher = getServletContext().getRequestDispatcher(VIEW_URL); try { dispatcher.forward(req, res); } catch(Exception e) { throw new RuntimeException(e); } This gets a dispatch object for our view which is the BookJsp.jsp. Then it forwards the request to it. With all the necessary attributes set up this can output our book record correctly. The Deployment Descriptor (web.xml) There is one last file we need to modify before we have a complete web application. The deployment descriptor is the file used by the servlet container to define which servlets match up with which URLs. It also defines which servlet or resource provides the landing page for the root of the service. If it doesn't already exist create the file web.xml in the JSPBookDemo project. To do so right click on WebContent- WEB-INF then click New- File . Enter "web.xml" in the Filename text field and click Finish . Open the file and ensure it is in source mode by clicking the tab at the bottom left hand side of the editor window. Enter the content below. ?xml version="1.0" encoding="UTF-8"? web-app xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns="http://java.sun.com/xml/ns/javaee" xmlns:web="http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd" xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd" version="2.5" display-name JSPBookDemo /display-name servlet servlet-name BookServlet /servlet-name servlet-class com.microfocus.book.BookServlet /servlet-class /servlet servlet-mapping servlet-name BookServlet /servlet-name url-pattern /view /url-pattern /servlet-mapping welcome-file-list welcome-file view /welcome-file /welcome-file-list /web-app This is a straight forward servlet deployment descriptor. The attributes for the web-app element are used to define the specific version of the servlet API in use. The display-name defines the internal name of this web application that will appear in the servlet container management system. The servlet element binds a name to a particular servlet class. In this case our BookServlet. The servlet-mapping element binds a particular servlet to a URL from the root of our servlet. So any call to say "localhost:8080/JSPBookDemo/view" will be directed to BookServlet. The last element is the welcome-file-list . This just defines a set of files that will be used as the landing page for the servlet. In this case we are setting the view to be our landing page. Running and Debugging Now that we have a complete application it is time to run it. To run it right click on JSPBookDemo in the explorer and select Run As- Run on Server . Eclipse will give you a window containing the servlet containers it knows about. Select the one you want to deploy to and click Finish . This will launch the servlet container, build our web application and deploy it to the server. It will then open up a web browser page displaying our application. To test it type in stock number "1111" and click Read . This should bring up the relevant book from the book file. To debug we should first set some break points. To set a breakpoint double click in the left hand margin of Eclipse next to a line you want to stop at. Set a break point in the servlet in the performRead call. Set another in the readBook method of the BookInterface. Set a third in book.cbl in the do-read-record section. To launch the debugger click the drop down arrow next to the debug icon on the tool bar (see image below). Then select Debug As and Debug on Server . If it asks to open the debug perspective let it do so. The Eclipse Debug Button When you get the interface popped up try to read book "1111" and it should hit your break points. Hit F8 to continue running. It should hit the following break points and eventually go from Java into the COBOL. Click the red box at the top left to stop the session. Appendix book.cbl ******************************************************************************************************** * * Copyright (C) Micro Focus (IP) Limited 2011. * All rights reserved. * * This sample code is supplied for demonstration purposes only on an "as is" basis and "is for use at * your own risk". * ******************************************************************************************************** $set retrylock program-id. BookLegacy. environment division. input-output section. file-control. select bookfile assign to filename file status is ls-file-status organization is indexed access mode is dynamic record key is b-stockno alternate record key is b-title with duplicates alternate record key is b-author with duplicates . data division. file section. FD bookfile. copy "book-rec.cpy" replacing ==(prefix)== by ==b==. working-storage section. 01 ls-file-status pic xx. 01 ls-call-status pic x(2) comp-5. linkage section. 01 lnk-filename pic x(256). 01 lnk-function pic x. 88 read-record value "1". 88 add-record value "2". 88 delete-record value "3". 88 next-record value "4". 01 lnk-file-status pic xx. 78 no-key-error value "B1". copy "book-rec.cpy" replacing ==(prefix)== by ==lnk-b==. procedure division using by value lnk-function by reference lnk-b-details by reference lnk-file-status. main section. call "CBL_TOUPPER" using lnk-b-text-details by value length lnk-b-text-details returning ls-call-status evaluate true when read-record perform do-read-record when add-record perform do-add-record when delete-record perform do-delete-record when next-record perform do-next-record end-evaluate exit program . do-read-record section. open input bookfile if ls-file-status "00" initialize lnk-b-details move all '*' to lnk-b-text-details move ls-file-status to lnk-file-status exit section end-if evaluate true when lnk-b-stockno spaces move lnk-b-stockno to b-stockno read bookfile when lnk-b-title spaces move lnk-b-title to b-title read bookfile key is b-title when lnk-b-author spaces move lnk-b-author to b-author read bookfile key is b-author when other * ------------No key specified - return unsuccessful read move no-key-error to ls-file-status end-evaluate move ls-file-status to lnk-file-status if ls-file-status = "00" move b-title to lnk-b-title move b-type to lnk-b-type move b-author to lnk-b-author move b-stockno to lnk-b-stockno move b-isbn to lnk-b-isbn move b-retail to lnk-b-retail move b-onhand to lnk-b-onhand move b-sold to lnk-b-sold else initialize lnk-b-details move all '*' to lnk-b-text-details end-if close bookfile . do-next-record section. open input bookfile if ls-file-status "00" initialize lnk-b-details move all '*' to lnk-b-text-details move ls-file-status to lnk-file-status exit section end-if move lnk-b-stockno to b-stockno start bookfile key b-stockno read bookfile next move ls-file-status to lnk-file-status if ls-file-status = "00" move b-title to lnk-b-title move b-type to lnk-b-type move b-author to lnk-b-author move b-stockno to lnk-b-stockno move b-isbn to lnk-b-isbn move b-retail to lnk-b-retail move b-onhand to lnk-b-onhand move b-sold to lnk-b-sold else initialize lnk-b-details move all '*' to lnk-b-text-details end-if close bookfile . do-add-record section. open i-o bookfile evaluate ls-file-status when "05" * -------File not created yet when "00" continue when other move ls-file-status to lnk-file-status exit section end-evaluate move lnk-b-stockno to b-stockno read bookfile if ls-file-status = "00" * Record already exists - so error move "99" to ls-file-status else move lnk-b-isbn to b-isbn move lnk-b-title to b-title move lnk-b-type to b-type move lnk-b-author to b-author move lnk-b-retail to b-retail move lnk-b-onhand to b-onhand move lnk-b-sold to b-sold write b-details end-if move ls-file-status to lnk-file-status close bookfile . do-delete-record section. open i-o bookfile if ls-file-status "00" move ls-file-status to lnk-file-status exit section end-if evaluate true when lnk-b-stockno spaces move lnk-b-stockno to b-stockno read bookfile delete bookfile record when lnk-b-title spaces move lnk-b-title to b-title read bookfile key is b-title delete bookfile record when lnk-b-author spaces move lnk-b-author to b-author read bookfile key is b-author delete bookfile record when other * ------------No key specified - return unsuccessful read move no-key-error to ls-file-status end-evaluate move ls-file-status to lnk-file-status close bookfile . set-filename section. entry "SET_FILENAME" using lnk-filename. move lnk-filename to filename goback. book-rec.cpy ****************************************************************** * * Copyright (C) Micro Focus 2010-2012. All rights reserved. * * This sample code is supplied for demonstration purposes only * on an "as is" basis and is for use at your own risk. * ****************************************************************** 01 (prefix)-details. 03 (prefix)-text-details. 05 (prefix)-title pic x(50). 05 (prefix)-type pic x(20). 05 (prefix)-author pic x(50). 03 (prefix)-stockno pic x(4). 03 (prefix)-isbn pic 9(13). 03 (prefix)-retail pic 99v99. 03 (prefix)-onhand pic 9(5). 03 (prefix)-sold pic 9(5) comp-3. BookBean.java package com.microfocus.book; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse; public class BookBean { private final String _stockno; private final String _isbn; private final String _title; private final String _author; private final String _type; private final String _price; private final String _onhand; private final String _sold; private final String _stockval; public static final String STOCK_NO_ATTRIBUTE = "stockno"; public static final String TITLE_ATTRIBUTE = "title"; public static final String AUTHOR_ATTRIBUTE = "author"; public static final String TYPE_ATTRIBUTE = "type"; public static final String ISBN_ATTRIBUTE = "isbn"; public static final String PRICE_ATTRIBUTE = "price"; public static final String ONHAND_ATTRIBUTE = "onhand"; public static final String SOLD_ATTRIBUTE = "sold"; private static final String ERROR_VALUE = "ERROR"; BookBean(String stockno, String isbn, String title, String author, String type, String price, String onhand, String sold, String stockval) { this._stockno = stockno; this._isbn = isbn; this._title = title; this._author = author; this._type = type; this._price = price; this._onhand = onhand; this._sold = sold; this._stockval = stockval; } public String getStockno() { return _stockno; } public String getIsbn() { return _isbn; } public String getTitle() { return _title; } public String getAuthor() { return _author; } public String getType() { return _type; } public String getPrice() { return _price; } public String getOnhand() { return _onhand; } public String getSold() { return _sold; } public String getStockval() { return _stockval; } public static BookBean blankBook() { return msgBook("*************************************"); } public static BookBean msgBook(String msg) { String stockno = "****"; String isbn = "*************"; String title = msg; String author = "*************************************"; String type = "****"; String price = "****"; String onhand = "****"; String sold = "****"; String stockval = "****"; return new BookBean(stockno, isbn, title, author, type, price, onhand, sold, stockval); } public static BookBean getBook(HttpServletRequest req, HttpServletResponse res) { return new BookBean(getStockno(req, res), getIsbn(req, res), getTitle(req, res), getAuthor(req, res), getType(req, res), getPrice(req, res), getOnhand(req, res), getSold(req, res), ""); } private static String getAttribute(HttpServletRequest req, HttpServletResponse res, String attribute) { String stockNoStr; stockNoStr = req.getParameter(attribute); if (stockNoStr == null) { stockNoStr = ERROR_VALUE; } return stockNoStr; } public static String getStockno(HttpServletRequest req, HttpServletResponse res) { String output = getAttribute(req, res, BookBean.STOCK_NO_ATTRIBUTE); if (output == null) { output = ERROR_VALUE; } return output; } private static String getTitle(HttpServletRequest req, HttpServletResponse res) { return getAttribute(req, res, BookBean.TITLE_ATTRIBUTE); } private static String getAuthor(HttpServletRequest req, HttpServletResponse res) { return getAttribute(req, res, BookBean.AUTHOR_ATTRIBUTE); } private static String getType(HttpServletRequest req, HttpServletResponse res) { return getAttribute(req, res, BookBean.TYPE_ATTRIBUTE); } private static String getIsbn(HttpServletRequest req, HttpServletResponse res) { return getAttribute(req, res, BookBean.ISBN_ATTRIBUTE); } private static String getPrice(HttpServletRequest req, HttpServletResponse res) { return getAttribute(req, res, BookBean.PRICE_ATTRIBUTE); } private static String getOnhand(HttpServletRequest req, HttpServletResponse res) { return getAttribute(req, res, BookBean.ONHAND_ATTRIBUTE); } private static String getSold(HttpServletRequest req, HttpServletResponse res) { return getAttribute(req, res, BookBean.SOLD_ATTRIBUTE); } } BookInterface.java package com.microfocus.book; import javax.servlet.http.HttpSession; import com.microfocus.cobol.program.IObjectControl; import com.microfocus.cobol.program.ScaledInteger; import com.microfocus.cobol.runtimeservices.IRunUnit; import com.microfocus.cobol.runtimeservices.servlet.ServletRunUnitManager; public class BookInterface { private static final String READ_RECORD = "1"; private static final String ADD_RECORD = "2"; private static final String DELETE_RECORD = "3"; private static final String NEXT_RECORD = "4"; private final IRunUnit runUnit; private final BookLegacy bookLegacy; private static final String BOOK_FILE = "C:/work/JavaWebServicesDemos/COBOLJSPDemo/CobolBook/bookfile.dat"; public BookInterface(HttpSession session) { this(ServletRunUnitManager.getManager().GetSessionRunUnit(session)); } public BookInterface(IRunUnit runUnit) { this.runUnit = runUnit; BookLegacy bookLegacy = (BookLegacy) runUnit.GetInstance(BookLegacy.class); if (bookLegacy == null) { bookLegacy = new BookLegacy(); runUnit.Add(bookLegacy); } this.bookLegacy = bookLegacy; } public BookBean readBook(String stockNo) throws JavaBookException { setFileName(BOOK_FILE); Details details = getObject(Details.class); FileStatus status = getObject(FileStatus.class); details.setStockno(stockNo); bookLegacy.BookLegacy(READ_RECORD, details, status); throwExceptionIfError(status); return bookBeanFromDetails(details); } public BookBean addBook(BookBean book) throws JavaBookException { setFileName(BOOK_FILE); Details details = getObject(Details.class); FileStatus status = getObject(FileStatus.class); bookBeanToDetails(book, details); bookLegacy.BookLegacy(ADD_RECORD, details, status); throwExceptionIfError(status); return bookBeanFromDetails(details); } public BookBean deleteBook(String stockNo) throws JavaBookException { setFileName(BOOK_FILE); Details details = getObject(Details.class); FileStatus status = getObject(FileStatus.class); details.setStockno(stockNo); bookLegacy.BookLegacy(DELETE_RECORD, details, status); throwExceptionIfError(status); return bookBeanFromDetails(details); } public BookBean nextBook(String stockNo) throws JavaBookException { setFileName(BOOK_FILE); Details details = getObject(Details.class); FileStatus status = getObject(FileStatus.class); details.setStockno(stockNo); bookLegacy.BookLegacy(NEXT_RECORD, details, status); throwExceptionIfError(status); return bookBeanFromDetails(details); } private void setFileName(String filename) { bookLegacy.SET_FILENAME(getFilenameObject(filename)); } private static void bookBeanToDetails(BookBean bean, Details details) { details.setStockno(bean.getStockno()); details.setIsbn(Long.parseLong(bean.getIsbn())); details.setTitle(bean.getTitle()); details.setAuthor(bean.getAuthor()); details.setType(bean.getType()); details.setRetail(ScaledInteger.parseScaledInteger(bean.getPrice())); int onHandInt = Integer.parseInt(bean.getOnhand()); if (onHandInt 0) throw new RuntimeException( "The number of books on hand must be 0 or positive"); details.setOnhand(onHandInt); int soldInt = Integer.parseInt(bean.getSold()); if (soldInt 0) throw new RuntimeException( "The number of books sold must be 0 or positive"); details.setSold(soldInt); } private static BookBean bookBeanFromDetails(Details details) { String stockno = details.getStockno().trim(); String isbn = "" + details.getIsbn(); String title = details.getTitle().trim(); String author = details.getAuthor().trim(); String type = details.getType().trim(); String price = details.getRetail().toString(); String onhand = "" + details.getOnhand(); String sold = "" + details.getSold(); ScaledInteger stockvalInt = details.getRetail().multiply( new ScaledInteger(details.getOnhand(), 0)); String stockval = stockvalInt.toString(); return new BookBean(stockno, isbn, title, author, type, price, onhand, sold, stockval); } private static void throwExceptionIfError(FileStatus statusCode) throws JavaBookException { throwExceptionIfError(statusCode.getFileStatus().trim()); } private static void throwExceptionIfError(String statusCode) throws JavaBookException { if (!"00".equals(statusCode) && !"02".equals(statusCode)) { throw new JavaBookException(statusCode); } } private Filename getFilenameObject(String filename) { Filename output = getObject(Filename.class); output.setFilename(filename); return output; } private T extends IObjectControl T getObject(Class T cls) { try { T output = cls.newInstance(); runUnit.Add(output); return output; } catch (Throwable t) { throw new RuntimeException(t); } } } BookServlet.java package com.microfocus.book; import java.io.PrintWriter; import java.io.StringWriter; import javax.servlet.RequestDispatcher; import javax.servlet.http.HttpServlet; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse; import javax.servlet.http.HttpSession; import com.microfocus.cobol.runtimeservices.IRunUnit; import com.microfocus.cobol.runtimeservices.servlet.ServletRunUnitManager; public class BookServlet extends HttpServlet { /** * */ private static final long serialVersionUID = -3563065100184185678L; public static final String STATUS_ATTRIBUTE = "status"; public static final String RUN_UNIT_ID_ATTRIBUTE = "rununitid"; public static final String SUBMIT_PARAMETER = "submit"; public static final String READ_PARAMETER = "Read"; public static final String ADD_PARAMETER = "Add"; public static final String DELETE_PARAMETER = "Delete"; public static final String NEXT_PARAMETER = "Next"; public static final String END_PARAMETER = "End Session"; public static final String DEFAULT_VALUE = "DEFAULT"; public static final String VIEW_URL = "/BookJsp.jsp"; protected void doProcessing(HttpServletRequest req, HttpServletResponse res, boolean isGet) { String subValue = req.getParameter(SUBMIT_PARAMETER); if (subValue == null) { subValue = DEFAULT_VALUE; } setRunUnitId(req); if (subValue.equals(READ_PARAMETER)) { performRead(req, res); } else if (subValue.equals(ADD_PARAMETER)) { performAdd(req, res); } else if (subValue.equals(DELETE_PARAMETER)) { performDelete(req, res); } else if (subValue.equals(NEXT_PARAMETER)) { performNext(req, res); } else if (subValue.equals(END_PARAMETER)) { performEndSession(req, res); } else { outputBlankBook(req, res); } RequestDispatcher dispatcher = getServletContext().getRequestDispatcher( VIEW_URL); try { dispatcher.forward(req, res); } catch (Exception e) { throw new RuntimeException(e); } } @Override protected void doGet(HttpServletRequest req, HttpServletResponse res) { doProcessing(req, res, true); } @Override protected void doPost(HttpServletRequest req, HttpServletResponse res) { doProcessing(req, res, false); } private void performRead(HttpServletRequest req, HttpServletResponse res) { BookInterface bookInterface = getBookInterface(req.getSession()); String bookId = BookBean.getStockno(req, res); try { BookBean book = bookInterface.readBook(bookId); outputBook(req, res, book); } catch (JavaBookException e) { outputBookException(req, res, e); } catch (Exception e) { outputException(req, res, e); } } private void performAdd(HttpServletRequest req, HttpServletResponse res) { BookInterface bookInterface = getBookInterface(req.getSession()); try { BookBean book = BookBean.getBook(req, res); book = bookInterface.addBook(book); outputBook(req, res, book); } catch (JavaBookException e) { outputBookException(req, res, e); } catch (Exception e) { outputException(req, res, e); } } private void performDelete(HttpServletRequest req, HttpServletResponse res) { BookInterface bookInterface = getBookInterface(req.getSession()); String bookId = BookBean.getStockno(req, res); try { BookBean book = bookInterface.deleteBook(bookId); outputBook(req, res, book); } catch (JavaBookException e) { outputBookException(req, res, e); } catch (Exception e) { outputException(req, res, e); } } private void performNext(HttpServletRequest req, HttpServletResponse res) { BookInterface bookInterface = getBookInterface(req.getSession()); String bookId = BookBean.getStockno(req, res); try { BookBean book = bookInterface.nextBook(bookId); outputBook(req, res, book); } catch (JavaBookException e) { outputBookException(req, res, e); } catch (Exception e) { outputException(req, res, e); } } private void performEndSession(HttpServletRequest req, HttpServletResponse res) { HttpSession session = req.getSession(); session.invalidate(); outputError(req, res, "Session invalidated"); } private void outputBlankBook(HttpServletRequest req, HttpServletResponse res) { outputBook(req, res, BookBean.blankBook()); } private void outputBookException(HttpServletRequest req, HttpServletResponse res, JavaBookException jbe) { outputError(req, res, jbe.getMessage()); } private void outputException(HttpServletRequest req, HttpServletResponse res, Exception e) { String msg = e.getClass().getName() + " [" + e.getMessage() + "]"; StringWriter strWriter = new StringWriter(); PrintWriter printWriter = new PrintWriter(strWriter); e.printStackTrace(printWriter); req.setAttribute(STATUS_ATTRIBUTE, strWriter.toString()); outputError(req, res, msg); } private void outputBook(HttpServletRequest req, HttpServletResponse res, BookBean book) { if (book != null) { req.setAttribute("book", book); } else { req.setAttribute("book", BookBean.msgBook("ERROR! book is null in output book")); } } private void outputError(HttpServletRequest req, HttpServletResponse res, String msg) { outputBook(req, res, BookBean.msgBook(msg)); } private IRunUnit getRunUnit(HttpSession session) { return ServletRunUnitManager.getManager().GetSessionRunUnit(session); } private void setRunUnitId(HttpServletRequest req) { HttpSession session = req.getSession(); IRunUnit runUnit = getRunUnit(session); String ruid = "" + runUnit.getRunUnitID(); req.setAttribute(RUN_UNIT_ID_ATTRIBUTE, ruid); } private BookInterface getBookInterface(HttpSession session) { BookInterface output = new BookInterface(session); return output; } } JavaBookException.java package com.microfocus.book; import java.util.*; public class JavaBookException extends Exception { /** * */ private static final long serialVersionUID = -3882735817601888938L; private static final Map String, String messages; private static final String unknownErrorMessage = "Unknown Error: "; public final String statusCode; public JavaBookException(String statusCode) { super(messages.containsKey(statusCode) ? messages.get(statusCode) : unknownErrorMessage + statusCode); this.statusCode = statusCode; } static { messages = new HashMap String, String (); messages.put("35", "Error: Data file not found"); messages.put("23", "Error: Stock item not found"); messages.put("46", "No more items left"); messages.put("99", "Error: Item already exists"); messages.put("01", "Error: File error"); messages.put("B1", "Error: No key entered"); } } BookJsp.jsp %@ page language="java" contentType="text/html; charset=ISO-8859-1" pageEncoding="ISO-8859-1"% !DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd" html head meta http-equiv="Content-Type" content="text/html; charset=ISO-8859-1" title JSP Book Demo - Run Unit ID: ${rununitid} /title /head body form name="input" action="/JSPBookDemo/view" method="post" table border="0" tr td Stock Number: /td td colspan="7" input type="text" name="stockno" value="${book.stockno}"/ /td /tr tr td ISBN: /td td colspan="7" input type="text" name="isbn" value="${book.isbn}"/ /td /tr tr td Title: /td td colspan="7" input type="text" size="120" name="title" value="${book.title}"/ /td /tr tr td Author: /td td colspan="7" input type="text" size="120" name="author" value="${book.author}"/ /td /tr tr td Type: /td td colspan="7" input type="text" size="120" name="type" value="${book.type}"/ /td /tr tr td Price: /td td input type="text" name="price" value="${book.price}"/ /td td On Hand: /td td input type="text" name="onhand" value="${book.onhand}"/ /td td Sold: /td td input type="text" name="sold" value="${book.sold}"/ /td td Stock Value: /td td input type="text" readonly="readonly" name="stockval" value="${book.stockval}"/ /td /tr tr td colspan="8" input type="submit" name="submit" value="Read" / input type="submit" name="submit" value="Add" / input type="submit" name="submit" value="Delete" / input type="submit" name="submit" value="Next" / input type="submit" name="submit" value="End Session" / /td /tr !-- tr td Status: /td td colspan="7" ${status} /td /tr -- /table /form /body /html
↧
↧
Wiki Page: Configuring SSL Certificates
KB Template Summary Configuring new SSL Certificates How to configure SSL Certificates Using SSL Certificates Replacing demo certificates with secure certificates Environment Orbix 3.3 All supported platforms Question/Problem Description This article described the configuration settings required to use SSL certificates in an Orbix 3.3 environment Resolution The Orbix 3.3 SSL configuration settings can be found in the file: Orbix Home /config/orbixssl.cfg In particular, the following three configuration variables set the location of the new certificates and trusted CA list: IT_CERTIFICATE_PATH Specifies the directory in which the certificate file is stored in the file system. IT_CERTIFICATE_FILE Specifies the name of the server’s certificate file. IT_CA_LIST_FILE Specifies a list of CAs that the application should trust. The above variables should be set inside the relevant scope for your application\service. The name of this scope can be set in the server application's code, using the operation "IT_SSL::initScope()". We will now consider three different scenarios: - Making Private Keys Available to Server applications - Making a Private Keys Available to Orbix servers - Making a Private Keys Available to the Orbix Daemon Making Private Keys Available to Server applications By default, Orbix SSL expects the private key associated with a certificate to be appended to the certificate file. That is, the private key should be stored in encrypted Privacy Enhanced Mail (PEM) format. Please see the Orbix SSL demonstration certificates for an example of certificates with appended private keys in this format. Making a Private Key Available to Orbix Naming Service The Orbix Naming Service requires that the private key associated with a certificate is available in a separate file. The private key can also be appended to the certificate file, but the Orbix Naming Service ignores this appended key. The separate private key associated with the certificate, is specified with the configuration variable "IT_PRIVATEKEY_FILE" Making a Private Key Available to the Orbix Daemon As with other processes, the certificate used by the Orbix Daemon is set using the configuration variable "IT_CERTIFICATE_FILE". The pass-phrase used by the Orbix Daemon for its certificate is set with the utility "update". For example, on UNIX use the following command: update orbixd "passphrase" 0 On Windows, use the following command: update orbixd.exe "passphrase" 0
↧
Forum Post: RE: slow performance with concurrent users
If you are not already using these two Runtime configuration settings then you should test them out: NT_OPP_LOCK_STATUS FAST V_LOCK_METHOD 1
↧
Forum Post: RE: slow performance with concurrent users
You have to purchase a separate license for AcuServer. I have used AcuServer for years and its a great product and certainly addresses performance issues. I suggest you try out a demo license. Its easy to setup and test.
↧