Hi Atamert, воскресенье, 17 мая 2015 г., 19:35:57 UTC+6 пользователь Atamert Ölçgen написал: > > I’m new to Clojure async operations (while have a good understanding of >> other things) and want to get a bit of advice. Atoms & agents still confuse >> me. >> >> What I’m implementing is a small REST webservice with custom in-memory >> database. Database is indexed by unique key, basically it’s a map (I’ll >> denote it as MAP). There are two basic operations: >> >> *PUT /api/…/<KEY>.* Initiate an update for given KEY. The HTTP response >> should be returned immediately, and the processing should be done >> asynchronously. The processing consists of downloading a data file from web >> and doing some data crunching, the result should go into MAP. >> >> *GET /api/…/<KEY>.* Use (get MAP KEY) and request params to generate >> response synchronously. >> >> The tricky part (well, for me :) is that parallel PUT requests should be >> possible. The downloading and processing can and should go in parallel, >> independently, whereas updating the MAP should come synchronized, >> one-after-the-other. >> >> How would you implement this? >> > > While this can be done with atoms & agents, perhaps you should check out > core.async or Lamina first. > > Neither atoms nor agents can be updated in a parallel manner. Only one > update runs on a single atom/agent at a given time. If you really need > parallelism and the updates affect small parts of MAP, perhaps you can > model it using refs, but then it's not one big map anymore. (Still you > can't update a single ref in more than one thread at the same time.) > > You probably also want to control how the files are downloaded and > processed, so that there's not duplication of effort. So an event driven > solution seems to fit this problem. >
In fact, I don't use the MAP as a whole, each read/update operation is scoped by KEY. So a map of refs sounds good. Speaking of event driven solution and core.async. I came up with the following scheme: [PUT request handler] ----> processing queue channel ====> Download/process ====> update queue channel ----> [updating the MAP]. *[updating the MAP]* is basically a (go ...) block which does synchronous updates. -- You received this message because you are subscribed to the Google Groups "Clojure" group. To post to this group, send email to clojure@googlegroups.com Note that posts from new members are moderated - please be patient with your first post. To unsubscribe from this group, send email to clojure+unsubscr...@googlegroups.com For more options, visit this group at http://groups.google.com/group/clojure?hl=en --- You received this message because you are subscribed to the Google Groups "Clojure" group. To unsubscribe from this group and stop receiving emails from it, send an email to clojure+unsubscr...@googlegroups.com. For more options, visit https://groups.google.com/d/optout.