HN Theater @HNTheaterMonth

The best talks and videos of Hacker News.

Hacker News Comments on
Om Next - David Nolen

ClojureTV · Youtube · 276 HN points · 7 HN comments
HN Theater has aggregated all Hacker News stories and comments that mention ClojureTV's video "Om Next - David Nolen".
Youtube Summary
Over the past year and a half the ClojureScript community has collectively become the industry's leading experts on building effective and compelling user experiences over immutable data. However, while immutability and functional programming dramatically reduce the complexity of client side code there is more work left to do, especially at the boundary between clients and servers. There are a growing set of technologies and ideas that can complete the story that deserve assessment. We'll examine Relay (Facebook), JSONGraph (Netflix), and Datomic (Cognitect) and see how these technologies are guiding the design of the next version of Om, a popular React binding for ClojureScript.
HN Theater Rankings

Hacker News Stories and Comments

All the comments and stories posted to Hacker News that reference this video.
They haven't copied om next (fulcro makes it easier) https://www.youtube.com/watch?v=ByNs9TG30E8 #graphs-not-trees
I have nothing to say on Lein vs Boot, but I'm a long-term emacers with > 10 years and I can't endorse Cursive strongly enough. I've got easily at least 1k hours in my .emacs.d. Suffice it to say, it takes a lot to take away from Emacs/SLIME. Never bought into the Textmate hype during the Ruby days, or the SublimeText hype subsequently because Emacs already had all that functionality if not out of the box, there certainly was someone with an .el I could borrow. It takes a lot for me to leave Emacs, especially for a LISP.

Here's my 2 cents - Cursive is worth it. (Hey Ideogram folks, if you want an endorsement, feel free to use that paragraph in exchange for a lifetime license ;)). For one-off-scripts, for back-end solutions, and what tipped me over the edge, it's CLJS script integration goes beyond acceptable -- it's actually fun to work in-- Cursive is my go-to. Om and Figwheel (optionally with Prismatic Schema if you like type guarantees) makes web development's feedback loop a lot tighter.

Rich Hickey assembled a team of just insanely talented and charismatic(1) developers who not only are a) remarkably intelligent but b) know when to steal ideas and integrate them [none of that too-proud-NIH-syndrome there], and c) know how to interact in a way to that is community-feedback-positive(2) so people contribute. Watch this talk by David Nolen https://www.youtube.com/watch?v=ByNs9TG30E8 (CLJS lead). [Sidebar - He even mentions how that whole immutable, one way data flow, datomic-ish single state idea existed in other languages, but read (2) on that].

Anyways, Cursive + Lein + ClojureScript + Om is the holy grail for me right now. On the other hand, that nREPL/cider/boot setup is what I'd be using as a long-time emacs'er were I to give up Cursive.

(1) Having someone like Hickey or Nolen to shepherd ideas is actually really important in garnering traction. Developers go to conferences and when everyones talking about that 4PM Thursday talk that someone gave, it really resonates within the community for quite a while. I like Perl 6's ideas but if you've ever seen Larry Wall talk, well, yeah. (2) Some communities cough Haskell have great ideas, Lenses, FRP, applying (pun not intended) monoids -> functors -> applicative functors -> monads was genius. But for some reason the barrier to entry is so high (even for me with a fairly advanced math background) that concepts remain isolated within the community. LINQ is a monad (though few know it) and it took Brian Beckman (or Anders, or Bart de Smet, or whomever) to take it into C# to make the concept widely used by the Joe-the-programmer (again, pun not intended).

eric-hu
I've been a vim user for a number of years and have fiddled with building in Clojure support at different times with repl support, syntax highlighting and other basics. My success was varying and incomplete. Tooling has been a barrier for me learning Clojure. Half the time I want to learn or practice Clojure, I remember gaps in my tooling. Subsequently, I spend a few hours yak-shaving to improve it.

I've contemplated learning Emacs because of the general praise for its workflow in the Clojure community. I even know some basic emacs from bash scripting. Switching just seemed like it would add another learning block to an already long list of tools to learn. Cursive, on the other hand, is based on IntelliJ, which is familiar to me through RubyMine.

Thanks for taking the time to write up about Cursive. You just convinced me to finally install it and give it a shot.

freshhawk
As a fellow vim user and full time clojure dev, I should point out that spacemacs is pretty great for getting the best of vim and emacs in one editor.

But to get up and running and try things out? Use Cursive until you are comfortable, don't get distracted by tooling problems (which there will be).

lemming
Hey Ideogram folks, if you want an endorsement, feel free to use that paragraph in exchange for a lifetime license ;)

Well, I'd hate to be accused of buying positive reviews :-). But thanks, I really appreciate it and I'm glad it's working well for you.

One of my main goals for 2016 is to focus heavily on CLJS support to bring it fully up to par with Clojure support. Better REPLs, a much easier getting started story, testing support, a debugger, and as much support as seems to be required for React Native. I'm increasingly convinced that CLJS may turn out to be more important than Clojure, and certainly has the potential to bring a lot more devs to the CLJ(S) world if it manages to take off properly.

One of my main aspirations with Cursive is that it can help make both languages more accessible. I think Clojure support in Cursive is further along that path and I'm hoping to do the same for ClojureScript this year.

> ...but right now we're focusing on building stuff instead of playing with languages

Which is exactly what's so compelling with regard to ClojureScript and say Om or any one of the React wrappers out there: you guys already use Clojure and ClojureScript and its libraries are incredibly pragmatic and designed for "real work". CoffeeScript would seem more like language play than ClojureScript, but of course I'm speaking as an outsider. :)

Also if you haven't already, take a look at David Nolen's recent talk on Om Next[1]. Personally if I were using Clojure on the backend, I'd be pushing hard for it on the frontend too.

[1] https://www.youtube.com/watch?v=ByNs9TG30E8

vcarl
Personally, I'm not a big fan of CoffeeScript and it's something I brought up when I started, but at the end of the day you can write good and bad code in any language. I've watched that talk and found it really compelling, but I'd sooner get rid of Backbone than change languages. I've been following Dan Abramov's stuff pretty closely, the refinements in Redux seem to take the best parts of Om and Flux.
Aug 12, 2015 · lewisl9029 on Relay Technical Preview
Any idea why they decided to use string-based queries for GraphQL?

I feel something that can be composed programmatically without having to deal with string concatenation like Falcor's queries or the Datomic Pull syntax proposed in Om Next [1] could be more flexible and robust. I may be missing something.

[1] https://www.youtube.com/watch?v=ByNs9TG30E8

tracker1
You can always use JS/ES6 string templates (using Babel or Traceur).
Sorry if it wasn't apparent but I agree / advocate strongly for what you mention, and we use that model at my company. If you look at how Om evolved though, it started out with that simple model of passing the state object down to child components. Then cursors were implemented to make it easier to pass around parts of your global state without having components needing to know everything.

GraphQL doesn't mean moving to stateful components, it's just a nicer way to have a singleton data store because instead of chunking and passing a map around, components can declare which data they need. In that system components are still read only, and dispatch to external pure functions.

David Nolen does a great job talking about the trade offs and the evolution of everything in this talk https://www.youtube.com/watch?v=ByNs9TG30E8& I highly recommend it!

Link to said video (cljs-in-cljs) - https://youtu.be/ByNs9TG30E8?t=31m43s (link starts at cljs-specific stuff)

Discussion on HN - https://news.ycombinator.com/item?id=9848602

Jul 07, 2015 · 259 points, 48 comments · submitted by ivank
Spendar89
Swannodette never disappoints. If you're interested in this approach, you should check out re-frame: https://github.com/Day8/re-frame. The README is a great resource, regardless of whether or not you intend to use the framework.
ds300
That README changed my life.
Spendar89
And for anyone who'd like to jump right in:

https://github.com/Day8/re-frame-template

Includes Figwheel, and (optionally) Secretary.

winstonewert
He mentions getting rid of cursors, but I'm not clear how he would replace the modification side of cursors. i.e. I can see how a system like he describes supports nicely querying data, how do it help a component that needs to trigger modifying data?
hojberg
A group of us talked to him after the talk, and if I understood it correctly, you'd still use the om transact function to trigger modifications.
2bit
Exactly my question, this is a big missing piece and something that cursors solve nicely.
Spendar89
I imagine you would trigger something like a datomic transaction, which returns a new version of the database.
elwell
> 41:15

Pretty sure Apple won't approve of being able to update iOS apps outside of their regular release cycle. If they don't care, I should be doing that now with my HTML5 app.

reilly3000
I believe trigger.io has done this for a couple of years now
wging
You can definitely do that now.
elwell
Actually it may be fine, if it falls under this exception:

  3.3.2 An Application may not download or install executable code. Interpreted code may only be used in an Application if all scripts, code and interpreters are packaged in the Application and not downloaded. The only exception to the foregoing is scripts and code downloaded and run by Apple's built-in WebKit framework, provided that such scripts and code do not change the primary purpose of the Application by providing features or functionality that are inconsistent with the intended and advertised purpose of the Application as submitted to the App Store.
andrewchambers
Clojurescript in Clojurescript is demoed in the last 5-6 minutes of the video. I think this is an awesome way to ship a repl with applications.
akilism
Yeah, that was a great talk.

I really want to try out Om Next. I've been building a bunch of stuff in Om lately and the Falcor/Relay/GraphQL/Om Next stuff is really going to be great to have at my disposal.

The clojurescript compiling clojurescript stuff looks great too.

bsaul
Why does the idea of having frontend guys directly query the db without any kind of interface scares me ?

Seems like going the nosql to sql route once again( nosql is great until you realize query language and schema constraints are actually a good thing).

Having some kind of pipe structure and interface between your db and your GUI that can be used as a contract,or as an intermediate level to do data rearranging, and can be documented, without having to know all the db schema internals really seems like a sound approach. Now of course some people tackling very special problems may reach the limits of such an approach, yet i hope it won't become mainstream too soon.

spion
This presentation doesn't go into detail of how thats going to work between Om and Clojure, but if its going to be similar to GraphQL, then there is no problem.

Every field request in GraphQL [1] maps really well to a method invocation on an object (GraphQL even supports arguments). Its not necessary that those objects in turn map directly to actual database entities... and you can of course do many things with methods, like authentication / authorization, or perhaps even (with async servers) delaying get() requests in order to aggregate them into a single IN query

[1]: https://www.youtube.com/watch?v=WQLzZf34FJ8&feature=youtu.be...

bsaul
Thanks for the link. Very interesting talk.

At then end though, you understand why they had to build such a system : dozens of apps, with weekly releases, and mutliple version support.

Now of course, building an API supporting each of those apps needs is almost equivalent to supporting any kind of query. You might as well create a generic implemention, like GraphQL, which they did.

But for the 99.99% of us, i don't think bypassing the API design phase is a really good idea.

spion
I don't think it qualifies as bypassing the API design phase. You still need to design the classes that map to GraphQL object, the methods they support, the authentication / authorization that those methods require and so on.

All in all its pretty much the same thing as with a classic API. The only difference is you can send multiple (as well as nested) calls in one go, and decide which fields you want to include With this scheme you can even include/exclude fields based on user authorization! For example:

  class UserService {
    email() {
      if (this.context.user.id == this._id) 
        return this._email
      else
        throw new CodedError(403, "Cannot request another users email")
    }
  }
What is necessary now I think is an example open source app implemented with it to demonstrate how the stuff we do with regular APIs would work in GraphQL...
lewisl9029
> Why does the idea of having frontend guys directly query the db without any kind of interface scares me ?

I don't think giving frontend a direct path to the db is what the talk is advocating.

You still need a backend in front of the db, even in the special case of using Datomic as the db, to handle things like auth. The difference seems to be that instead of having the backend serve a messy web of REST endpoints for the clients to consume and compose individually, the backend would serve a single endpoint that can speak this new query language. The client can then declaratively request exactly the data it needs in the shape that it needs it in, eliminating an overwhelming majority of network related boilerplate on both the backend and client.

I'm personally extremely excited to see this become mainstream. So much of the front-end code I write on a day-to-day basis involves fetching data from various endpoints and shaping it into a logical structure for my components to display. It's tedious work that provides no intrinsic value. I can't wait to not have to write any more of that and focus my time on solving actual problems.

elwell
Isn't there an argument for abstracting and preparing data at the backend level, rather than facing the db nearly directly from the frontend?
emidln
This does that. There's nothing saying that individual query elements have to hit the database directly. Besides authz (which others have mentioned), you have the potential for various caching strategies as well as letting the backend make cost decisions in general about where to get things. It could be that you mostly pass through to a Datomic. It could also be that each element hits a different microservice. The point is that your client doesn't know this or care.
akilism
yes this is exactly what it is. it's definitely going to be one of those clutch things in the near future. being able to write some ui code that is acting as if the data is already available to it.
cageface
How does caching work in this scenario? Caching REST responses is fairly straightforward but caching arbitrarily complex queries to a single endpoint seems much more difficult.

Sorry if he answers this in his talk. I haven't had a chance to watch it yet.

hcarvalhoalves
The caching happens at the "DB" level, where it can happen more efficiently (e.g., Datomic caches segments on peers).
i_s
You have to implement it yourself. For some apps, you may need to do this anyway for perf reasons, because you don't want to parse the same HTTP response body more than once.
fnordsensei
One solution is to not cache queries, but cache data, as in the case with Datomic.
drcode
Of course then you're sacrificing some of the authentication, potentially.
sgrove
It's worthwhile watching Nubank's talk on how they manage these things with Datomic on the backend [0] - providing a "complete" (filtered) database to the client, http caches for queries based on tx-time, and syncing mobiles data via transactions-since. Takes care of said concerns nicely - I'm just implementing this stuff today however, so I'm not sure how well it'll work in practice.

[0] - https://www.youtube.com/watch?v=7lm3K8zVOdY

lewisl9029
I'm not familiar with the approach either, but the video mentioned that you would mainly execute these queries using a client side library. The library would be backend agnostic, and offer remote sync capabilities.

So I believe you can set the primary backend for the library to a local, in-memory data-structure to serve as the local cache, and have the library handle synchronization between the local cache and a remote backend that can also execute these queries.

drcode
So, in principle I like everything with David's new approach... the main question I have is "How well do 'recursive queries' work when the data relationships between my components is really complex?" I think I will only be able to answer that question by trying this approach myself and seeing how it performs for my needs.

(Another question is: "How am I going to use this when my server's database is a blockchain and not a conventional database [1] like datomic?" but I know that's a niche question I'll have to figure out for myself.)

[1] Just kidding (mostly)

spion
Thats indeed something that doesn't seem to be discussed much, even if you look at graphql's presentation - https://www.youtube.com/watch?v=WQLzZf34FJ8 there seems to be a lot of redundancy when "my friends including their events" is fetched.

I imagine that a scheme based on an UUID and deduplication would work - when constructing the response an object repository is kept and if an object with the same uuid appears twice its replaced with a reference to them.

Going against the "don't extend JSON" best practice, that would be:

  {
    "friends": [{ 
      "name": "Name", 
      "events": [#uuid1, #uuid2]
    }, {
      "name": "Another name",
      "events": [#uuid1, #uuid2]
    }],
  }
  #{
    "uuid1": {"name": "MyEvent", "description": "..."},
    "uuid2": {"name": "OtherEvent", "description": "..."},
  }
And it can support cyclic references too, as a bonus. Ignoring best practices is so... liberating.

Ultimately this is just compression though. Its possible that gzip will be quite sufficient for most cases.

emidln
Transit [1] can do this for you.

[1] https://github.com/cognitect/transit-format

avodonosov
I am skeptical about "component knows what data it needs". For example, I have a component with two combo boxes: in the first combo box I select a country and the second combo box is filled with cities of that country.

Now I need a similar thing: in one combo box I choose car brand, and the second combo box is filled with models of that brand. Can I reuse my existing component? If the component knows what data it displays, it can not be used to display different data.

jeremiep
David talked about the IQueryParams protocol in the presentation, it basically lets you parametrize the component's data.
Skinney
If you need a generic component, then make a generic component. No one is forcing you to specify dependencies in all of your components.
avodonosov
OK :)
zubairq
I personally built my entire framework on top of Om, so always good to hear what David has to say:

https://github.com/zubairq/coils

agumonkey
I guess the Gregor Kiczales slides are here: http://www.cs.ubc.ca/~gregor/papers/kiczales-oopsla-07-for-v... (page 16)
andy_ppp
I was thinking about this the other day and the web just magically solved all my thoughts and wrapped it up into a perfect video.

Really excited about building my project in this (and learning clojure and Om Next).

drudru11
Is there a description of how react avoids event listeners? How does it observe changes in a model? I've never heard that aspect associated with react before.
mateuszf
It doesn't avoid them. You listen to events, and then you change your model. Based on new model view is rendered using the code you provide (one way rendering - model to code). Then React compares the two instances of rendered view (before the event and after) and renders the changes if there are any.
pwr
Has anyone an idea how pagination would work/look like with the presented query syntax?
spion
Quite amazing. This talk is not just about Om Next - its also about ClojureScript.next. Featuring:

  1. AMD, CommonJS, ES6 module support
  2. CLJS in CLJS (yup, that works - including the standalone nodejs based REPL)
Thise in combination are especially huge.

With core.typed being an option as well (once your system starts growing and the design solidifies) looks like the clojure ecosystem is really positioned to be one of the technically strongest available for web development.

And of course, replacing that awkward REST mess seems painfully obvious now (except for duplicated data which seems like something that might yet need solving). Hindsight is 20/20

jsprogrammer
Are you aware of any performance benchmarks? Do you pay for the clojure abstractions?
bostonOU
An old talk (2012) so I'm not sure how accurate it is now, but Nolen discusses performance of ClojureScript. At the very least, you know someone cares and is thinking about it.

http://www.infoq.com/presentations/ClojureScript-Optimizatio...

None
None
dominotw
I felt like it was all over the place. I am not sure if I really care about all the people who are using graphql like syntax for data retrieval, I am not interested datamoic, falcor ect.
lewisl9029
Does 1) mean we can make use of advanced optimizations (like dead code elimination) on libraries written in one of these formats without any additional configuration?

If so, that would resolve what I consider to be one of the biggest barriers for CLJS/JS interop.

arohner
I'm pretty sure the answer is yes. I watched the video a few hours ago, but I think I remember him saying that.

Of course, just like the current state of affairs, your library has to not thwart advanced optimizations (using eval, accessing properties by strings, etc).

jacobolus
Yes, that’s what swannodette said in the talk. Skip to 33 minutes, or see https://github.com/clojure/clojurescript/wiki/Google-Summer-... and the blog posts at https://mneise.github.io
Jul 07, 2015 · 17 points, 1 comments · submitted by hadronzoo
akilism
Yeah, that was a great talk.

I really want to try out Om Next. I've been building a bunch of stuff in Om lately and the Falcor/Relay/GraphQL stuff is really going to be great to have at my disposal.

The clojurescript compiling clojurescript stuff looks great too.

HN Theater is an independent project and is not operated by Y Combinator or any of the video hosting platforms linked to on this site.
~ yaj@
;laksdfhjdhksalkfj more things
yahnd.com ~ Privacy Policy ~
Lorem ipsum dolor sit amet, consectetur adipisicing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat nulla pariatur. Excepteur sint occaecat cupidatat non proident, sunt in culpa qui officia deserunt mollit anim id est laborum.