Calling a livecode executable -ui from LC server and get back a result.

Richard Gaskin ambassador at fourthworld.com
Fri May 5 12:11:56 EDT 2017


I think I see the problem here:

Any program that can read from stdin and write to stdout can be used as 
a CGI, and this includes LC standalones...

- BUT -

LC Server scripts are incompatible with LC Script on the desktop.

In fact, it's that incompatibility that made me switch back to using 
standalones for server work many years ago, so it's possible to test and 
debug scripts locally without needing to run them in a server 
configuration and pray that I never need to debug them. ;)

But switching back to what Jacque and I like to think of as "LC Classic 
CGI" means updating scripts that had been written for LC Server's unique 
syntax to be compatible with LC Script as implemented in the desktop.

The upside is that LC Script as implemented in the standalone engine is 
of course fully compatible with the IDE, leading us to just one rule 
that may clarify issues when porting scripts from LC Server:

    If you can run it on your desktop, you can run it on your server.
    And if you can't run in on your desktop, it won't run on your server.

Using the desktop engine facelessly on the server gives us all the 
flexibility we enjoy with LC, which also means we have many ways things 
can be set up to execute.  Too many to write here.

If you have only one script you'll ever need, you can put it in a 
startup handler in the standalone itself.

But I find I use LC standalones so often that I prefer to make a 
standalone that's very slender, containing only enough code to read 
whatever library stack file is specified in the CGI file called, and 
then the standalone runs "start using" with that, and the library 
handles everything from there in a libraryStack handler.

Whether the code is in the standalone itself or in a separate stack 
file, either way you can't use LC Server's "<?lc" and "?>" tags in any 
normal LC Script execution other than in LC Server.

So one way to port your LC Server script below to normal LC Script which 
can be run from the IDE or a standalone would be:


--===========================================--
local sOutputBuffer

on startup
    cgiStart
    DoTheDeed
    cgiEnd
end startup


on cgiStart
    -- Here you load any libs you need, read any CGI environment
    -- variables you might need, etc.:

end cgiStart

on DoTheDeed
    set the shellCommand to "CMD"
    put "<html>" into sOutputBuffer
    put the time  after sOutputBuffer
    put "<br />" after sOutputBuffer
    put Quote & "thes.exe" & Quote &&"-ui" into tShell
    try
       get shell(tShell)
       put "Result:" && the result & cr &"It:" && it after sOutputBuffer
       put "<br />" after sOutputBuffer
       open process tShell for binary read
      read from process tShell until EOF
      put "Result:" && the result & cr &"It:" && it after sOutputBuffer
      put "<br />" after sOutputBuffer
   catch theErr
      put theErr
  end try
  put cr after sOutputBuffer
  put the time after sOutputBuffer
  put "</html>" after sOutputBuffer
end DoTheDeed


on cgiEnd
   put len( sOutputBuffer ) into tLen
   --  Send header:
   put "Content-Type: text/html" & cr &\
      "Date:" && the internet date & cr &\
      "Host:" && $SERVER_NAME & cr &\
      "Content-Length:"&& tLen &cr&cr into tHeader
   put tHeader
   --  Send body:
   put sOutputBuffer
   -- All done:
   quit
end cgiEnd


Note a couple of key difference between normal LC Script here and the 
specialized form usable only in LC Server:

- Here the "put" command writes immediately to stdout, whereas
   in LC Server it writes to an internal buffer.

- LC Server writes the required HTTP header for us, whereas we need
   to write that ourselves when using the desktop engine.

So as you see above, rather than using naked "put" commands we instead 
put into sOutputBuffer, and then write our header before sending it.

There are other differences as well, such as the enhanced implicit merge 
operation done automatically with LC Server files vs. the need to 
explicitly call the more limited merge function when processing files 
that mix code and HTML.  But since you're not doing that we can leave 
that for another time.

Keep us posted with how it goes.  I use standalones on a wide range of 
systems, including one that needs to exchange data with a client's auth 
server, so I know the sorts of things you want to do are quite 
achievable once you get oriented to moving back to normal LC Script for 
standalones.


Tip: For local development it takes only a couple minutes to create a 
sort of "server emulator", which sets up any environment variables your 
script will be able to get from Apache by just loading them with useful 
values yourself.  In my setup I use a global in lieu of a socket 
connection in my emulator, so I can pass in POST data and get back the 
reply all within the IDE, and with complete debugging capabilities.

-- 
  Richard Gaskin
  Fourth World Systems


Malte Brill wrote:

> has anybody successfully done this? Especially on Windows? I would
> like to launch a livecode built application from a liveCode server
> script and get the output back (on a Server that I control) Is that
> possible? If so, how?
>
> I tried a couple of things to no avail:
>
> <?lc
>   set the shellCommand to "CMD"
>   put "<html>"
>   put the time
>   put "<br />"
>   put Quote & "thes.exe" & Quote &&"-ui" into tShell
>   try
>     get shell(tShell)
>     put "Result:" && the result & cr &"It:" && it
>     put "<br />"
>     open process tShell for binary read
>    read from process tShell until EOF
>    put "Result:" && the result & cr &"It:" && it
>    put "<br />"
>   catch theErr
>   put theErr
> end try
> put cr
> put the time
> put "</html>"
> ?>
>
> the helper app: In the stack script:
>
> on startup
>   send "boo" to me in 500 millisecs
>   — to make sure all libs are loaded
> end startup
>
> on boo
>   quit
> end boo
>
> on shutdown
>   write "boo" to stdout
> end shutdown
>
> Thanks for all input I can get…
>
> Malte






More information about the use-livecode mailing list