Skip to main content

Using Net Express 5.0, I'm trying to call a cobol program compiled as an EXE from an AJAX call in Javascript, passing the data to the program using POST.  If I pass the data with the URL, and I accept it in the cobol program from the command-line, everything works peachy.  However, I have an application where I want to POST a really long string, so I'm trying to do a proper post, and just do ACCEPT rather than ACCEPT ... FROM COMMAND-LINE.  When I try that, the program just hangs and I get a CGI timeout.

Here is the source of my test program:

      $set preprocess(htmlpp) endp
    
      *>****************************************************************
       identification division.
      *>****************************************************************
           program-id. "ajaxtest".

      *>****************************************************************
       environment division.
      *>****************************************************************

       configuration section.
       special-names.
           call-convention 8 is llnk.
       input-output section.
       file-control.

      *>****************************************************************
       data division.
      *>****************************************************************
       file section.
       working-storage section.

       01  cmd-string          pic x(80).
       01  cnt                 pic 999 value 0.

       01  OUTPUT-STRING       PIC X(500) VALUE SPACES.


       local-storage section.
       linkage section.

      *>****************************************************************
       Procedure Division.
      *>****************************************************************
       main section.

           accept cmd-string.

           STRING "THE INPUT DATA IS " CMD-STRING INTO OUTPUT-STRING.

           exec html
       :OUTPUT-STRING
           end-exec.

           exit program.
           stop run.

And here is my Javascript with the AJAX call:

function gobtn_onclick_func()                                                                       
   {                                                                                                
    with(document.form1)                                                                            
       {                                                                                            
        if (window.XMLHttpRequest)                                                                  
        {                                                                                           
            xmlhttp=new XMLHttpRequest();                                                           
        }                                                                                           
        else                                                                                        
        {                                                                                           
            xmlhttp=new ActiveXObject("Microsoft.XMLHTTP");                                         
        }                                                                                           
                                                                                                    
        var postdata = "un=" sessionID.value screenID.value userName.value companyID.value;
        xmlhttp.open("POST", "ajaxtest.exe", false);                                              
        xmlhttp.setRequestHeader("Content-type","application/text");                                
        xmlhttp.send(postdata);                                                                     
        document.write(xmlhttp.responseText);                                                       
       }                                                                                            
   }     

If, in the cobol program, if I change the the ACCEPT statement to:

   accept cmd-string from command-line

and, in the JavaScript, the send method to:

   xmlhttp.open("POST", "ajaxtest.exe?", postdata, false)

it works fine.

What do I need to change to be able to bring in the data from something other than the command line?



#Ajax
#COBOL
#JavaScript

Using Net Express 5.0, I'm trying to call a cobol program compiled as an EXE from an AJAX call in Javascript, passing the data to the program using POST.  If I pass the data with the URL, and I accept it in the cobol program from the command-line, everything works peachy.  However, I have an application where I want to POST a really long string, so I'm trying to do a proper post, and just do ACCEPT rather than ACCEPT ... FROM COMMAND-LINE.  When I try that, the program just hangs and I get a CGI timeout.

Here is the source of my test program:

      $set preprocess(htmlpp) endp
    
      *>****************************************************************
       identification division.
      *>****************************************************************
           program-id. "ajaxtest".

      *>****************************************************************
       environment division.
      *>****************************************************************

       configuration section.
       special-names.
           call-convention 8 is llnk.
       input-output section.
       file-control.

      *>****************************************************************
       data division.
      *>****************************************************************
       file section.
       working-storage section.

       01  cmd-string          pic x(80).
       01  cnt                 pic 999 value 0.

       01  OUTPUT-STRING       PIC X(500) VALUE SPACES.


       local-storage section.
       linkage section.

      *>****************************************************************
       Procedure Division.
      *>****************************************************************
       main section.

           accept cmd-string.

           STRING "THE INPUT DATA IS " CMD-STRING INTO OUTPUT-STRING.

           exec html
       :OUTPUT-STRING
           end-exec.

           exit program.
           stop run.

And here is my Javascript with the AJAX call:

function gobtn_onclick_func()                                                                       
   {                                                                                                
    with(document.form1)                                                                            
       {                                                                                            
        if (window.XMLHttpRequest)                                                                  
        {                                                                                           
            xmlhttp=new XMLHttpRequest();                                                           
        }                                                                                           
        else                                                                                        
        {                                                                                           
            xmlhttp=new ActiveXObject("Microsoft.XMLHTTP");                                         
        }                                                                                           
                                                                                                    
        var postdata = "un=" sessionID.value screenID.value userName.value companyID.value;
        xmlhttp.open("POST", "ajaxtest.exe", false);                                              
        xmlhttp.setRequestHeader("Content-type","application/text");                                
        xmlhttp.send(postdata);                                                                     
        document.write(xmlhttp.responseText);                                                       
       }                                                                                            
   }     

If, in the cobol program, if I change the the ACCEPT statement to:

   accept cmd-string from command-line

and, in the JavaScript, the send method to:

   xmlhttp.open("POST", "ajaxtest.exe?", postdata, false)

it works fine.

What do I need to change to be able to bring in the data from something other than the command line?



#Ajax
#COBOL
#JavaScript

When you are posting data to a CGI program you need to read the CONTENT-LENGTH environment variables etc. and read the standard in according to the length received.

The following is an example program that will determine if the method is GET or POST and will read the data accordingly using a binary file read on the CI: device which is the console input.

     $set preprocess(htmlpp) endp
      identification division.
      program-id. "testpost".
      data division.
      working-storage section.
      01 access-mode             pic x comp-x value 1.
      01 deny-mode               pic x comp-x value 3.
      01 device                  pic x comp-x value 0.
      01 flags                   pic x comp-x value 0.
      01  file-handle            pic x(4).
      01  offset-0               pic x(8) comp-x value 0.
      01 input-file-name         pic x(255) value spaces.
      01 env-value               pic x(4096).
      01 method-type             pic x(4).
      01 content-length          pic x(4) comp-x.
      01 content-type            pic x(100).
      01 sub1                    pic x(4) comp-x.
      01 temp-01                 pic x comp-x.
      01 temp-02                 pic x comp-x.
      01  mem-pointer            usage pointer value null.
      01  mem-length             pic x(4) comp-5.
      01  mem-flags              pic x(4) comp-5.
      01 alloc-mem-rtn           pic x(2) comp-5.
      01 tmp-01                  pic x(4) comp-x.
      01 tmp-02                  pic x(4) comp-x.
      linkage section.
      01 accept-record           pic x.
      procedure division.
      *>    call "cbl_debugbreak"
          move 18 to temp-01
          move 1 to temp-02
          call x"A7" using temp-01 temp-02
     * Use display and accept verbs to get the values of environment
     * variables set up by the web server.
          display "CONTENT_TYPE" upon environment-name
          accept content-type from Environment-value
          display "REQUEST_METHOD" upon environment-name
          accept env-value from environment-value
          if env-value = "GET"
              move "GET" to method-type
     * If the form method=GET, we cannot use the CONTENT_LENGTH
     * environment variable to determine the size of the data, so we
     * allocate a block of memory big enough to hold the data.
              move 4096 to content-length
              perform alloc-accept-record
              display "QUERY_STRING" upon environment-name
              accept accept-record(1:4096) from environment-value
              move 0 to sub1
     * The query string should be space-terminated, so we can determine
     * it's end and it's size.
              inspect accept-record(1:4096) tallying sub1
                      for characters before initial space
              move sub1 to content-length
          else
              move "POST" to method-type
              display "CONTENT_LENGTH" upon environment-name
              accept env-value from environment-value
              move 0 to sub1
              inspect env-value tallying sub1 for characters
                                before initial space
              move env-value (1:sub1) to content-length
              perform alloc-accept-record
     * Read data from stdin instead of query string.
              move ":CI:" to input-file-name
              call "CBL_OPEN_FILE"  using input-file-name
                                    access-mode
                                    deny-mode
                                    device
                                    file-handle
              call "CBL_READ_FILE" using file-handle
                                   offset-0
                                   content-length
                                   flags
                                   accept-record
              call "CBL_CLOSE_FILE" using file-handle
          end-if
     * Send html back to the web server/browser.
          display "Content-type: text/html" & x"0a" & x"0a"
          display "<html>" & x"0a"
          display "<head><title>"
          display "Test raw cobol cgi program"
          display "</title></head>" & x"0a"
          display "<body bgcolor=""#FFFFFF"">" x"0a"
          display "Content-type:" content-type x"0a"
          display "METHOD=" method-type
          display "<br>"
          display "CONTENT-LENGTH=" content-length x"0a"
          display "<br>"
          display "CGI-DATA=<PRE>"
          display accept-record(1:content-length) x"0a"
          display "</pre></body>" & x"0a"
          display "</html>" & x"0a"
          stop run.

      alloc-accept-record section.
     * Dynamically allocate memory to hold the form/url data.
          move 0 to mem-flags
          move content-length to mem-length
          call "CBL_ALLOC_MEM" using    mem-pointer
                               by value mem-length
                                        mem-flags
                              returning alloc-mem-rtn
          if alloc-mem-rtn not = 0
             display "alloc mem failed"
             stop run
          end-if
          set address of accept-record to mem-pointer.


Using Net Express 5.0, I'm trying to call a cobol program compiled as an EXE from an AJAX call in Javascript, passing the data to the program using POST.  If I pass the data with the URL, and I accept it in the cobol program from the command-line, everything works peachy.  However, I have an application where I want to POST a really long string, so I'm trying to do a proper post, and just do ACCEPT rather than ACCEPT ... FROM COMMAND-LINE.  When I try that, the program just hangs and I get a CGI timeout.

Here is the source of my test program:

      $set preprocess(htmlpp) endp
    
      *>****************************************************************
       identification division.
      *>****************************************************************
           program-id. "ajaxtest".

      *>****************************************************************
       environment division.
      *>****************************************************************

       configuration section.
       special-names.
           call-convention 8 is llnk.
       input-output section.
       file-control.

      *>****************************************************************
       data division.
      *>****************************************************************
       file section.
       working-storage section.

       01  cmd-string          pic x(80).
       01  cnt                 pic 999 value 0.

       01  OUTPUT-STRING       PIC X(500) VALUE SPACES.


       local-storage section.
       linkage section.

      *>****************************************************************
       Procedure Division.
      *>****************************************************************
       main section.

           accept cmd-string.

           STRING "THE INPUT DATA IS " CMD-STRING INTO OUTPUT-STRING.

           exec html
       :OUTPUT-STRING
           end-exec.

           exit program.
           stop run.

And here is my Javascript with the AJAX call:

function gobtn_onclick_func()                                                                       
   {                                                                                                
    with(document.form1)                                                                            
       {                                                                                            
        if (window.XMLHttpRequest)                                                                  
        {                                                                                           
            xmlhttp=new XMLHttpRequest();                                                           
        }                                                                                           
        else                                                                                        
        {                                                                                           
            xmlhttp=new ActiveXObject("Microsoft.XMLHTTP");                                         
        }                                                                                           
                                                                                                    
        var postdata = "un=" sessionID.value screenID.value userName.value companyID.value;
        xmlhttp.open("POST", "ajaxtest.exe", false);                                              
        xmlhttp.setRequestHeader("Content-type","application/text");                                
        xmlhttp.send(postdata);                                                                     
        document.write(xmlhttp.responseText);                                                       
       }                                                                                            
   }     

If, in the cobol program, if I change the the ACCEPT statement to:

   accept cmd-string from command-line

and, in the JavaScript, the send method to:

   xmlhttp.open("POST", "ajaxtest.exe?", postdata, false)

it works fine.

What do I need to change to be able to bring in the data from something other than the command line?



#Ajax
#COBOL
#JavaScript

     * If the form method=GET, we cannot use the CONTENT_LENGTH
     * environment variable to determine the size of the data, so we
     * allocate a block of memory big enough to hold the data.

It's illegal to send a message-body with a GET request - see RFC 2616 4.3 and 9.3. And CGI/1.1 only makes data available to the application on stdin if there's an entity-body, which there won't be if there's no message-body - see the draft CGI/1.1 standard. So the code in the section containing the comment above is never necessary; there won't be anything to read for a GET request.

For a GET request, the only information provided with the request is in the path, fragment, and query portions of the Request-URI (possibly including CGI path-info; again see the CGI/1.1 spec), and in request headers.