The difficulty with websockets is that an application must always return to an 
idle state (FYI websockets are different than sockets and introduced with 
j801).  The async handler appears mandatory.  For a pure server that serves 
only one type of content, that might actually be easier.

The code you posted earlier, for windows timer callbacks, is useful for 
replacing any non websockets related looping code in an application.  Instead 
of looping continuously, restart one/a few loop on each timer tick, and so that 
keeps the application returning to idle.

I'm not sure of crossplatform solutions, but google suggests that SDL provides 
such a callback, even though it may be heavyweight.

Seems like a big scaffolding effort overall, though.





----- Original Message -----
From: Raul Miller <rauldmil...@gmail.com>
To: Programming forum <programm...@jsoftware.com>
Cc: 
Sent: Thursday, February 13, 2014 11:40:17 AM
Subject: Re: [Jprogramming] Qt websockets and doevents

Here's a J implementation of code to fetch a web page from a web server.
This is code lifted from the j602 lab "Sockets and the Internet".
(Currently, the j602 labs are the most mature.)

I removed the wd progress indicator code, renamed everything to use an http
prefix (though, technically, only the first two routines assume http
protocol) and added a phrase to discard the protocol part of the url (the
j602 implementation assumes the host name is separated from the path by the
first '/' character).

Perhaps you can pattern your work after this model? Or do you specifically
need asynchronous handling? If you need to support multiple overlapping
communications streams, I'd probably start you with
http://jsoftware.com/jwiki/JWebServer/EventHandler

Thanks,

-- 
Raul

load 'socket'
coinsert 'jsocket'

httpget=: 3 : 0
  'host path'=. (({.;}.)~ i.&'/') ({.~ 1 i.~ '//' E. ])&.|. y
  host=. 2{.<;._1 ':',host,':80'
  if. 0=#$x=. ('HEAD ',path,' HTTP/1.0',CR,LF,CR,LF) httpreq host=.
({.host),".&.>{:host do. x return. end.
  if. -.'HTTP/1.1 2'-:10{.>{.x=. <;._2 x-.CR do. >{.x return. end.
  len=. ".>{:;:>{.(((<'content-length:')-:&>
15{.&.>tolower&.>x)#x),<'Content-length: _1'
  if. 0~:{.sk=. httpconn host do. {.sk return. end.
  ('GET ',path,CR,LF) httpsend sk=. {:sk
  z=. ''
  while. 1 do.
    sdcheck sdselect sk;'';'';60000
    if.0=#n=. >{. sdcheck sdrecv sk,10240,0 do. break. end.
    z=. z,n
  end.
  z[sdclose sk
)

httpreq=: 4 : 0
  y=. (;&80)^:(0:=L.) y
  if. 0~:{.sk=. httpconn y do. {.sk return. end.
  x httpsend sk=. {:sk
  (sdclose]httprecvall) sk
)

httpconn=: 3 : 0
  'host port'=. y
  if. 0~:s=. >{.x=. sdgethostbyname host do. s return. end.
  s=. >{.sdcheck sdsocket''
  sdconnect s;(}.x),<port
  0,s[sdioctl s,FIONBIO_jsocket_,1
)

httpsend=: ] [ [: sdcheck ,&(13 10{a.)@[ sdsend ] , 0:

httprecvall=: 3 : 0
  60000 httprecvall y
  :
  z=. ''
  while. 1 do.
    if. -.y e. >{.sdcheck sdselect y;'';'';x do. 0 return. end.
    if.0=#n=. >{. sdcheck sdrecv y,10240,0 do. break. end.
    z=. z,n
  end.
)



On Thu, Feb 13, 2014 at 11:00 AM, Pascal Jasmin <godspiral2...@yahoo.ca>wrote:

> In terms of program design, imagine if getting a web page involved first
> connecting to the web server, waiting for the GUI to regain focus, and then
> requesting the web page in a second user action.
>
> I guess the workaround is to set the send code to trigger on the onOpen
> event.
>
> Though not having any way to yield to the message handlers makes it
> impossible to have a "main loop" as part of the same program.  That would
> seem to make it impossible to have file polling, or use standard sockets,
> in the same application.  The workaround of separating out programs that
> use files or sockets, and setting up a websocket connection to the
> websocket application at load time with a start and stop interface and
> manual start after launch probably still doesn't work:  The "backend"
> application will never process websocket messages if it has a loop.  The
> problems I've been describing is primarily that no events are processed,
> rather than just the specific send failure.
>
> However, if the J console has a way of allowing for/deferring to the
> processing of the handler events, perhaps there is a way to do it within J
> code too?  I thought 6!:3 might do that.  As a guess, perhaps 6!:3 ] 0
> could be made to.
>
>
>
>
>
>
> ----- Original Message -----
> From: bill lam <bbill....@gmail.com>
> To: programm...@jsoftware.com
> Cc:
> Sent: Thursday, February 13, 2014 9:23:35 AM
> Subject: Re: [Jprogramming] Qt websockets and doevents
>
> connection of websocket involves some hand-shaking between
> client and server, there is no guarantee that it will finish
> within 3 second or 3 minute.  For production work, it should
> never send data without knowing the socket is connected to
> remote side first.  Frankly speaking, I think your program is
> faulty in its design principle.
>
> The jwiki documentation on query is incorrect for client mode,
> some of those socket may be not yet connected to ther remote
> server.
>
> Чт, 13 фев 2014, Pascal Jasmin писал(а):
> > The problem is that it appears to be impossible to wait for the onOpen
> event while running code.  Inserting a delay does not work anyway.
> >
> > ( pD =: 1!:2&2 )
> >
> >
> > wd 'ws send ' , s , ' get index' [  6!:3 (1)[ pD s=. wd 'ws connect
> ws://localhost 3000'
> >
> >
> > a secondary but still big problem is that send returns that it is
> successful.  The above code probably needs to be possible?  -- connect and
> interact with a server with a single call?
> >
> > Another secondary issue is that inserting 'ws query 1' shows the socket
> as connected.
> >
> >    wd 'ws send ' , s , ' f123' [ pD wd 'ws query 1' [ 6!:3 (3)[ pD s=.
> wd 'ws connect ws://localhost 3000'
> > 77364096
> > 77369696
> > 77364096
> >
> > 4
> > disconnected 77364096
> >
> >
> > trying to call handler explicitly, doesn't seem to work either :
> >
> >    wd 'ws send ' , s , ' f123' [ wscln_handler jws_onOpen , 0 ". pD s=.
> wd 'ws connect ws://localhost 3000'
> > 77365216
> > connected 77365216
> > 4
> > disconnected 77365216
> >
> >
> >
> > ----- Original Message -----
> > From: bill lam <bbill....@gmail.com>
> > To: Programming forum <programm...@jsoftware.com>
> > Cc:
> > Sent: Thursday, February 13, 2014 4:08:14 AM
> > Subject: Re: [Jprogramming] Qt websockets and doevents
> >
> > I doubted the line (as one sentence)
> >
> > wd 'ws send ' , s , ' f123'  [ s=. wd 'ws connect ws://localhost 3000'
> >
> > will actually work when typed on terminal. please read the notes under
> > the documentation for the cmd connect in jwiki, recaped here:
> >
> > This command will return as soon as after sending request to server
> > without waiting for the reply. The connection is not guaranteed to be
> > successful.
> >
> > Therefore you need to wait for the onOpen event before sending any data.
> >
> > On Thu, Feb 13, 2014 at 1:05 PM, Pascal Jasmin <godspiral2...@yahoo.ca>
> wrote:
> > > Something like that might help, though I'm not sure any of those are
> the specific windows calls I need, and it perhaps involves a qt call.
> > >
> > > To better highlight the problem, and actually highlight a bigger
> problem than trying to connect to our own process, loading the websocket
> client and server demos in separate (or the same instance of J8), the line:
> > >
> > >      wd 'ws send ' , s , ' f123'  [ s=. wd 'ws connect ws://localhost
> 3000'            NB has following output
> > > 4
> > > disconnected 503025...
> > >
> > > the above line connects and creates a socket, and then sends the
> message 'f123' to the server.  The output 4 signals that it was a success.
> "disconnected is a message that probably results from the server
> autodisconnecting the client because its too fast, and is printed from the
> handler loop.  There would be no way for the code to know if the message
> was delivered (it probably was not), because it received "success" in one
> code path, and the failure is from an unrelated event/path.
> > >
> > > The individual code lines (in terminal)
> > > [ s=. wd 'ws connect ws://localhost 3000'
> > >
> > >  wd 'ws send ' , s , ' f123'
> > >
> > >
> > > work fine. (but they would fail in a script)
> > >
> > >
> > > ----- Original Message -----
> > > From: Raul Miller <rauldmil...@gmail.com>
> > > To: Programming forum <programm...@jsoftware.com>
> > > Cc:
> > > Sent: Wednesday, February 12, 2014 10:43:23 PM
> > > Subject: Re: [Jprogramming] Qt websockets and doevents
> > >
> > > Are you looking for
> http://www.jsoftware.com/jwiki/Scripts/WindowsTimer?
> > >
> > > Thanks,
> > >
> > > --
> > > Raul
> > >
> > >
> > >
> > >
> > > On Wed, Feb 12, 2014 at 10:38 PM, Pascal Jasmin <
> godspiral2...@yahoo.ca>wrote:
> > >
> > >> The code with no nouns in z.  The server and client handlers do
> nothing
> > >> with messages other than print to console, and so there should be no
> > >> concern about running it.  The code is there to exercise opening and
> > >> closing sockets.
> > >>
> > >> There is both a client and server loop handler, but as mentioned,
> nothing
> > >> is done onMessage in each.
> > >>
> > >> There are only 2 lines of code that are run:
> > >>
> > >>    a: new_wsconnection_ 'localhost 3000'
> > >>
> > >>
> > >> creates a new client, that will also create a new server.  1 socket
> and
> > >> locale numbers are placed in array for each.
> > >>
> > >>    'close 1' inl  '''client'' -: conntype' (] #~ inl)
> wsconnections_ws_
> > >>
> > >>
> > >> That line has been commented out, but it does: For connections of
> conntype
> > >> 'client' that are in the connectionslist, close them.
> > >>
> > >>
> > >> I've narrowed down the issue to 6!:3 does not allow the server
> handler to
> > >> process messages.
> > >> 6!:3 also happens to not be necessary to get client handler to
> process.
> > >>  These happen in order after connect.
> > >> You can confirm this by noticing the order of "Serv connect" prints in
> > >> console.  These occur after the query 1 and query 0 regardless of the
> > >> length of delay in 6!:3 line.
> > >> The server messages process after code stops.
> > >>
> > >>
> > >> cocurrent 'ws'
> > >> wssockets =: i.0 NB.
> > >> wsconnections =: i.0
> > >>
> > >> wscln_handler_z_ =: wscln_handler =: 3 : 0
> > >> 'evt sk'=. y
> > >> if. evt = jws_onMessage do.
> > >>   smoutput 'client: ' wss0_jrx_
> > >> elseif. evt = jws_onOpen do.
> > >>   smoutput 'connected ', ": sk
> > >>  'onOpen 1' inl wsconnections_ws_ {~ wssockets_ws_ i. sk
> > >> elseif. evt = jws_onClose do.
> > >>   smoutput 'disconnected ' , ": sk
> > >>  'onClose 1' inl wsconnections_ws_ {~ wssockets_ws_ i. sk
> > >> elseif. evt = jws_onError do.
> > >>   smoutput wsc0_jrx_
> > >> end.
> > >> EMPTY
> > >> )
> > >>
> > >> wssvr_handler_z_ =: wssvr_handler =: 3 : 0
> > >> 'evt sk'=. y
> > >> if. evt = jws_onMessage do.
> > >> smoutput 'server: ' wss0_jrx_
> > >> NB.  assert. _1 ~: r
> > >> elseif. evt = jws_onOpen do.
> > >>   smoutput 'Serv connected ', ": sk
> > >>  NB. pD datatype sk
> > >>  'onOpen 1' inl ((sk);'server') conew 'wsconnection'
> > >>  NB. 'onOpen 1' inl wsconnections {~ wssockets i. sk
> > >> elseif. evt = jws_onClose do.
> > >>   smoutput 'Serv disconnected ' , ": sk
> > >>  'onClose 1' inl wsconnections_ws_ {~ wssockets_ws_ i. sk
> > >> elseif. evt = jws_onError do.
> > >>   smoutput 'error ', wss0_jrx_
> > >> end.
> > >> EMPTY
> > >> )
> > >>
> > >> addsockconn =: 4 : 0
> > >> pD 'adds'
> > >> pD wssockets_ws_ =: wssockets_ws_ , x
> > >> pD wsconnections_ws_ =: wsconnections_ws_ , y
> > >> )
> > >> delsock=: 3 : 0
> > >> if. _ > i =. y iorinf~ wssockets do.
> > >> wssockets_ws_ =: i deleteitem wssockets_ws_
> > >> wsconnections_ws_ =: i deleteitem wsconnections_ws_
> > >> end.
> > >> )
> > >> delconn=: 3 : 0
> > >> if. _ > i =. y iorinf~ wsconnections_ws_ do.
> > >> wssockets_ws_ =: i deleteitem wssockets_ws_
> > >> wsconnections_ws_ =: i deleteitem wsconnections_ws_
> > >> end.
> > >>
> > >> )
> > >> coclass 'wsconnection'
> > >> connected =: 0
> > >> create =: 3 : 0
> > >> 'socket conntype commands auth' =: y defaults fixlenx
> > >> a:;'client';'testcommands';'authserver'
> > >> pD 18!:5 ''
> > >> socket (addsockconn_ws_ ]]) 18!:5 ''
> > >> )
> > >> createServer =: 3 : 0
> > >>
> > >> )
> > >> onOpen =: 3 : 'connected =: 1'
> > >> onClose =: 3 : 0
> > >> connected =: 0
> > >> delconn_ws_ 18!:5 ''
> > >> )
> > >> close =: 3 : 'wd ''ws close '', ": socket'
> > >>
> > >> NB. ( [conntype = 'client'];[commandslocale];[authlocale])
> > >> new_wsconnection_ 'localhost 3000' ('addr port') > wsconnectionObj
> > >> new =: 4 : 0 NB. called for client connection
> > >> s =. 0 ". wd 'ws connect ws://', y
> > >> (s ; x) conew >18!:5 ''
> > >> )
> > >>
> > >> NB. =========================================================
> > >> wd 'ws listen 3000'
> > >> cocurrent 'base'
> > >> testws =: 3 : 0
> > >> a: new_wsconnection_ 'localhost 3000'
> > >> a: new_wsconnection_ 'localhost 3000'
> > >> 6!:3 (0.2)
> > >> NB. 'close 1' inl  '''client'' -: conntype' (] #~ inl)
> wsconnections_ws_
> > >> NB. closes all clients (cascades cleanup)
> > >> NB.6!:3 (0.2)
> > >> pD wsconnections_ws_ ; wssockets_ws_
> > >> pD  'q0';wd 'ws query 0'
> > >> pD  'q1';wd 'ws query 1'
> > >> )
> > >>
> > >> cocurrent 'z'
> > >> deleteitem_z_ =:  {. , >:@[ }. ]
> > >> defaults1 =: ([`]@.(0=#@>@[))
> > >> defaults =: defaults1"0 0 f.
> > >> fixlenx =: 1 : (':';'((#y) {. x) u y')
> > >> iorinf =: (#@[ _:^:= i.)
> > >> inl_z_ =: (cocurrent@] ".@] [)"1 0
> > >> pD_z_ =:  1!:2&2
> > >>
> > >>
> > >>
> > >> ----- Original Message -----
> > >> From: bill lam <bbill....@gmail.com>
> > >> To: "programm...@jsoftware.com" <programm...@jsoftware.com>
> > >> Cc:
> > >> Sent: Wednesday, February 12, 2014 8:51:46 PM
> > >> Subject: Re: [Jprogramming] Qt websockets and doevents
> > >>
> > >> I agree with Raul, and uncomfortable to try your script. If your
> handler
> > >> is non-trivial you should define it inside a locale/class and export
> it to
> > >> z-locale.
> > >>
> > >> result of any wd command is always a string, ever since wd was first
> > >> introduced some decades ago.
> > >>
> > >> 13.02.2014, в 9:08, Pascal Jasmin <godspiral2...@yahoo.ca>
> написал(а):
> > >>
> > >> > the z locale is apparently necessary for the websockets handlers
> (which
> > >> is how J communicates with websockets).
> > >> >
> > >> > The documentation is here:
> > >> http://www.jsoftware.com/jwiki/Guides/JqtWebsocket, and there are
> also
> > >> demos with j8.
> > >> >
> > >> > If the handlers have to be in z, I might as well put the tracking
> list
> > >> for sockets and connections there, as the handlers need to access the
> > >> tracking lists in order to dispatch to the right code, and there can
> only
> > >> be one handler in program.
> > >> >
> > >> >
> > >> > I rely on some favorite utility verbs, that I keep in z.  Nothing
> else
> > >> is in z though.
> > >> >
> > >> > " you can call it yourself if you wish to do so (and you
> couldmaintain
> > >> your own queue of commands to feed it, if you want that"
> > >> >
> > >> > I'm surprised to hear this.  I assume J/QT would also "double call"
> it,
> > >> if I did.  Would probably cause its own problems.  Its possible that
> you
> > >> are describing a technique I don't know of, in maintaining my "own
> queue of
> > >> commands"
> > >> >
> > >> >
> > >> >
> > >> >
> > >> > ----- Original Message -----
> > >> > From: Raul Miller <rauldmil...@gmail.com>
> > >> > To: Programming forum <programm...@jsoftware.com>
> > >> > Cc:
> > >> > Sent: Wednesday, February 12, 2014 7:52:43 PM
> > >> > Subject: Re: [Jprogramming] Qt websockets and doevents
> > >> >
> > >> > I am a little uncomfortable, reading ad-hoc code in the 'z' locale.
> Why
> > >> not
> > >> > use some other locale?
> > >> >
> > >> > Also, I am not clear what you are asking for, with the event
> handler, but
> > >> > clearly you can call it yourself if you wish to do so (and you could
> > >> > maintain your own queue of commands to feed it, if you want that).
> > >> >
> > >> > Thanks,
> > >> >
> > >> > --
> > >> > Raul
> > >> >
> > >> >
> > >> >
> > >> > On Wed, Feb 12, 2014 at 7:23 PM, Pascal Jasmin <
> godspiral2...@yahoo.ca
> > >> >wrote:
> > >> >
> > >> >> A minor wierdness with websockets is that connect returns a string
> > >> socket,
> > >> >> whereas the event handlers have integer sockets.
> > >> >>
> > >> >> I was hoping that 6!:2 allowed for event handlers to process
> messages,
> > >> but
> > >> >> it doesn't appear to.  Does such a command exist?  A bit like the
> old vb
> > >> >> windows 3.1 doevents()/yield()
> > >> >>
> > >> >> Anyways, if you load the included code listing, and run
> > >> >>
> > >> >> testws a:
> > >> >>
> > >> >> you will note that it fails to unload/close client sockets (line
> wd 'ws
> > >> >> query 1' returns open clients)
> > >> >>
> > >> >> if you run the lines inside testws individually in repl, it works.
> > >> (closes
> > >> >> everything)
> > >> >>
> > >> >>
> > >> >>
> > >> ----------------------------------------------------------------------
> > >> For information about J forums see
> http://www.jsoftware.com/forums.htm
> > >>
> > > ----------------------------------------------------------------------
> > > For information about J forums see http://www.jsoftware.com/forums.htm
> >
> > > ----------------------------------------------------------------------
> > > For information about J forums see http://www.jsoftware.com/forums.htm
> > ----------------------------------------------------------------------
> > For information about J forums see http://www.jsoftware.com/forums.htm
> > ----------------------------------------------------------------------
> > For information about J forums see http://www.jsoftware.com/forums.htm
>
> --
> regards,
> ====================================================
> GPG key 1024D/4434BAB3 2008-08-24
> gpg --keyserver subkeys.pgp.net --recv-keys 4434BAB3
> gpg --keyserver subkeys.pgp.net --armor --export 4434BAB3
>
> ----------------------------------------------------------------------
> For information about J forums see http://www.jsoftware.com/forums.htm
> ----------------------------------------------------------------------
> For information about J forums see http://www.jsoftware.com/forums.htm
>
----------------------------------------------------------------------
For information about J forums see http://www.jsoftware.com/forums.htm 
----------------------------------------------------------------------
For information about J forums see http://www.jsoftware.com/forums.htm

Reply via email to