<div dir="ltr"><div>TL;DR: A data-bound autocomplete widget will finally make it really practical to use Ur/Web as stated on its website: </div><div><br></div><div>"Ur/Web supports construction of dynamic web applications backed by SQL databases."</div><div><br></div><div><div>It would be great if someone good at front-end programming using Ur/Web FRP could contribute this kind of autocomplete widget. </div></div><div><br></div><div>And the example of the existing Mithril+RxJS autocomplete widget might be able to provide some help.</div><div><br></div><div>===</div><div><br></div><div>(I) Live demo:</div><div><br></div><div>Here is a live demo of an autocomplete widget written using RxJS + Mithril + 6to5 aka Babel + HTML5 <datalist> [1]:</div><div><br></div><div><a href="http://codepen.io/ericponto/pen/mJEyPL">http://codepen.io/ericponto/pen/mJEyPL</a></div><div><br></div><div>The code can be downloaded by clicking on "Share" and then clicking on "Export .zip" - and then it can be run in any browser, with no need for a server. </div><div><br></div><div>It's tiny - just three files: </div><div><br></div><div>- index.html</div><div><br></div><div>- ../babel/index.babel - (written in babel aka 6to5) which compiles to =></div><div><br></div><div>- ../js/index.js. </div><div><br></div><div><br></div><div>(II) Tutorial:</div><div><br></div><div>There is also a nice, "literate-programming-style" tutorial for the live demo:</div><div><br></div><div><a href="http://www.ericponto.com/blog/2015/05/31/rxjs-and-mithril/">http://www.ericponto.com/blog/2015/05/31/rxjs-and-mithril/</a></div><div><br></div><div>So here we have a short, simple implementation of a basic autocomplete widget written in the minimal, functional, FRP-friendly JavaScript framework Mithril.</div><div><br></div><div>Specifically, this autocomplete widget is using:</div><div><br></div><div>(1) Mithril: the tiny-footprint (12k gzipped), high-performance, FRP-friendly React-like JavaScript framework </div><div><br></div><div><a href="http://lhorie.github.io/mithril/">http://lhorie.github.io/mithril/</a></div><div><br></div><div>(2) RxJS: reactive extensions for JavaScript</div><div><br></div><div><a href="https://github.com/Reactive-Extensions/RxJS">https://github.com/Reactive-Extensions/RxJS</a></div><div><br></div><div>(3) 6to5 or Babel: the compiler providing a layer of "functional" syntactic sugar of JavaScript and allowing programmers to use the new, functional ECMAscript 6 before its release</div><div><br></div><div><a href="https://babeljs.io/">https://babeljs.io/</a> </div><div><br></div><div>(Warning: The babel homepage sometimes doesn't open in Chrome.)</div><div><br></div><div><br></div><div>(III) Questions:</div><div><br></div><div>(1) Could this simple RxJS+Mithril+Babel autocomplete widget example provide a short path towards implementing a simple autocomplete widget "natively" in Ur/Web (using FRP)?</div><div><br></div><div>(2) Could Mithril be a good "fit" with Ur/Web somehow?</div><div><br></div><div>(3) If so, what would be the best way to leverage Mithril in Ur/Web?</div><div><br></div><div>(a) "wrap" Mithril using Ur/Web's JavaScript FFI?</div><div><br></div><div>(b) use Mithril's implementation as a reference and emulate / re-implement some or all of it from scratch using Ur/Web FRP?</div><div><br></div><div>(c) or maybe Ur/Web's FRP already does what Mithril does, but better, so Mithril has *nothing* to offer Ur/Web?</div><div><br></div><div><br></div><div>(IV) Conjectures:</div><div><br></div><div>Even if (3)(c) above is true, it seems that this might provide additional support for the question asked in the subject of this message, ie:</div><div><br></div><div>Can the autocomplete widget implemented in RxJS + Mithril + 6to5 serve as an inspiration or template for implementing a similar widget natively using Ur/Web's FRP?</div><div><br></div><div>Intuitively, it seems that the "shape" of this RxJS + Mithril + 6to5 implementation of an autocomplete widget might somehow be "similar" to the "shape" of some code which would implement the same widget in Ur/Web. </div><div><br></div><div><br></div><div>(V) Possibly related recent work in functional and functional-reactive JavaScript libraries:</div><div><br></div><div>There has been a flurry of activity over the past couple years involving functional programming and functional-reactive programming with JavaScript libraries. </div><div><br></div><div>A short opinionated list (from a programmer who likes functional, strongly typed languages) can be seen here. </div><div><br></div><div><a href="http://doshitan.com/js-overview-early-2015/#mithril">http://doshitan.com/js-overview-early-2015/#mithril</a></div><div>(Ignore item 1 talking about Angular! - I think that's just what he has to use at his job!)</div><div><br></div><div>It is also fascinating the read the ReadMe (really a bit of a manifesto) of the Re-Frame project on GitHub (which uses React, a ClojureScript "wrapper" over Facebook React):</div><div><br></div><div><a href="https://github.com/Day8/re-frame">https://github.com/Day8/re-frame</a></div><div><br></div><div>I would imagine it can be interesting for Ur/Web programmers to be aware of these functional and functional-reactive tendencies in JavaScript libraries, because:</div><div><br></div><div>(1) They may be somewhat related to Ur/Web FRP front-end programming, eg, they may suggest useful algorithms or techniques; or </div><div><br></div><div>(2) It may be worth "wrapping" some of these functional and functional-reactive JavaScript libraries by:</div><div><br></div><div>(a) "wrapping" them via Ur/Web's FFI; or </div><div><br></div><div>(b) "emulating" them by writing portions of either:</div><div><br></div><div>(i) their implementations; or</div><div><br></div><div>(ii) implementations of *examples written in them*</div><div><br></div><div>... "natively" from scratch using Ur/Web's FRP.</div><div><br></div><div><br></div><div>(VI) MithrilJS:</div><div><br></div><div>Mithril is an interesting JavaScript library because it's tiny and functional-reactive and fast.</div><div><br></div><div><a href="https://lhorie.github.io/mithril/benchmarks.html">https://lhorie.github.io/mithril/benchmarks.html</a></div><div><br></div><div>It's also compact and expressive:</div><div><br></div><div><a href="http://lhorie.github.io/mithril-blog/a-spreadsheet-in-60-lines-of-javascript.html">http://lhorie.github.io/mithril-blog/a-spreadsheet-in-60-lines-of-javascript.html</a></div><div><br></div><div>Its implementation is short enough that you can actually read and understand the whole thing in a day:</div><div><br></div><div><a href="https://github.com/lhorie/mithril">https://github.com/lhorie/mithril</a></div><div><br></div><div>Perhaps the most convincing stuff to read on Mithril is posts on <a href="http://news.ycombinator.com">news.ycombinator.com</a> from other programmers:</div><div><br></div><div><a href="https://news.ycombinator.com/item?id=8973867">https://news.ycombinator.com/item?id=8973867</a></div><div><br></div><div><a href="https://www.google.com/?gws_rd=ssl#q=site:news.ycombinator.com+mithril">https://www.google.com/?gws_rd=ssl#q=site:news.ycombinator.com+mithril</a></div><div><br></div><div>Finally, the tutorial for the autocomplete live demo using RxJS + Mithril + 6to5 even explains what to do "when pairing Mithril with a FRP library":</div><div><br></div><div><a href="http://www.ericponto.com/blog/2015/05/31/rxjs-and-mithril/">http://www.ericponto.com/blog/2015/05/31/rxjs-and-mithril/</a></div><div><br></div><div>So this suggests that Mithril may in some way be a good "fit" to use with Ur/Web.</div><div><br></div><div><br></div><div>(VI) Mithril: Can it contribute to Ur/Web?</div><div><br></div><div>I am curious about how Mithril might be able to fit with or contribute to Ur/Web.</div><div><br></div><div>Specifically I wonder if the Mitril + RxJS implementation of an autocomplete widget can help towards implementing a similar widget natively in Ur/Web using FRP.</div><div><br></div><div>Of course, I'm *not* saying that Mithril should somehow *replace* Ur/Web's native front-end facilities. </div><div><br></div><div>But I *am* wondering if there could be some sort of cross-pollination here, in some form.</div><div><br></div><div>For example, given ...</div><div><br></div><div>- the current lack of examples and demos of Ur/Web FRP programming*</div><div><br></div><div>- Mithril's functional approach, and FRP-friendliness</div><div><br></div><div>... I wonder if Mithril could serve as some kind of inspiration, in particular for a back-end database programmer trying to learn how to do FRP in Ur/Web.</div><div><br></div><div>---</div><div><br></div><div>* By the way, I would like to mention that the chat examples in this PDF are amazing:</div><div><br></div><div><a href="http://adam.chlipala.net/papers/UrWebPOPL15/UrWebPOPL15.pdf">http://adam.chlipala.net/papers/UrWebPOPL15/UrWebPOPL15.pdf</a></div><div><br></div><div>This is some of the most inspiring web programming code I've ever seen. Amazingly compact and expressive and helpful. </div><div><br></div><div>If there were examples of nice Ur/Web FRP idioms available, it would be immensely helpful for programmers learning Ur/Web.</div><div><br></div><div><br></div><div>(VIII) Why a (native or FFI) autocomplete widget (in particular) could be very important for Ur/Web:</div><div><br></div><div>Having a community-contributed autocomplete widget for Ur/Web, implemented either:</div><div><br></div><div>- "natively" using Ur/Web FRP, or</div><div><br></div><div>- as an FFI "wrapper" around an existing full-featured library such as Select2 or twitter typeahead.js</div><div><br></div><div>... would finally make it really practical for Ur/Web to be used by more application developers as a web database framework (particular those who are good at back-end programming and not-so-good at front-end programming).</div><div><br></div><div>This is because an autocomplete widget is essential for providing a friendly UI where users editing a "child" record can use a convenient menu to select the value of a foreign-key field to link it to the appropriate "parent" record - rather than having to manually find, memorize and enter the parent record's autoincrement/surrogate integer primary key.</div><div><br></div><div>Developers who are good at data-modeling and SQL on the back-end (but might not be so good at functional-reactive programming on the front end) would benefit greatly if some Ur/Web programmer(s) who are good at front-end programming could provide a "native" implementation of an autocomplete  using Ur/Web's FRP - perhaps inspired by the Mithril+RxJS+Babel autocomplete example described in this post.</div><div><br></div><div>===</div><div><br></div><div>Source code or the RxJS + Mithril + 6to5 + Html5 DataList autocomplete widget example:</div><div><br></div><div>Below are just for the 2 human-written files index.html and index.babel.</div><div><br></div><div>File index.babel is quite similar to third file (not shown): index.js - which is output by the compiler. However, index.babel uses a more "functional" syntax.</div><div><br></div><div>I hope that if the brief code below implementing an autocomplete widget is read by some some Ur/Web programmers (who are also good at front-end development) you will think: "This looks a lot like something I could implement 'natively' in Ur/Web".</div><div><br></div><div>It would probably only take a page of code (for an Ur/Web programmer who is good at front-end development) to implement a simple data-bound autocomplete widget using Ur/Web's FRP.</div><div><br></div><div>===</div><div><br></div><div>###  this file: </div><div>###  index.html</div><div><br></div><div><!DOCTYPE html></div><div><html></div><div>  <head></div><div>    <meta charset="UTF-8"></div><div>    <title>RxJS and Mithril Autocomplete Example</title></div><div>  </head></div><div>  <body></div><div><br></div><div>    <div id="autocomplete"></div></div><div><br></div><div>    <script src='<a href="https://cdnjs.cloudflare.com/ajax/libs/rxjs/2.5.2/rx.all.min.js">https://cdnjs.cloudflare.com/ajax/libs/rxjs/2.5.2/rx.all.min.js</a>'></script></div><div>    <script src='<a href="https://cdnjs.cloudflare.com/ajax/libs/mithril/0.2.0/mithril.min.js">https://cdnjs.cloudflare.com/ajax/libs/mithril/0.2.0/mithril.min.js</a>'></script></div><div><br></div><div>    <script src="js/index.js"></script></div><div><br></div><div>  </body></div><div></html></div><div><br></div><div>===</div><div><br></div><div>###  this file:  </div><div>### ../babel/index.babel </div><div><br></div><div>###  compiles to:</div><div>###  ../js/index.js</div><div><br></div><div>var pluck = Rx.helpers.pluck;</div><div><br></div><div>var searchGithub = function(term) {</div><div>return m.request({</div><div>    method: "GET",</div><div>    url: `<a href="https://api.github.com/search/repositories?q=${term}`">https://api.github.com/search/repositories?q=${term}`</a></div><div>  });</div><div>};</div><div><br></div><div>var el = document.querySelector("#autocomplete");</div><div><br></div><div>var AutoComplete = {</div><div>  controller() {</div><div>    this.data = m.prop({});</div><div>    </div><div>    Rx.Observable.fromEvent(el, "keyup")</div><div>     .map(pluck("target")) /* get element */</div><div>     .filter(el => el.matches("input")) /* make sure it is the input */</div><div>     .map(pluck("value")) /* get element's value */</div><div>     .filter(val => val.length > 2) /* at least 3 chars */</div><div>     .debounce(250) /* debounce it */</div><div>     .distinctUntilChanged() /* ignore non character keyups */</div><div>     .flatMapLatest(searchGithub) /* fire request */</div><div>     .subscribe(this.data); /* set data prop with results */</div><div>  },</div><div>  view(ctrl) {</div><div>    var data = ctrl.data();</div><div>    </div><div>    return m(".autocomplete", [</div><div>      m("label[for=search]", ["Search for Github repo: "]),</div><div>      m("input#search[list=results]"),</div><div>      m("datalist#results", [</div><div>        data.items && data.items.map(item => m("option[value=" + <a href="http://item.name">item.name</a> + "]"))</div><div>      ])</div><div>    ]);</div><div>}</div><div>};</div><div><br></div><div>m.mount(el, AutoComplete);</div><div><br></div><div>===</div><div><br></div><div>Again, the complete source for the above demo can be downloaded from the link below, and can be run locally without a webserver (ie by simply opening the index.html file directly in a browser):</div><div><br></div><div><a href="http://codepen.io/ericponto/pen/mJEyPL">http://codepen.io/ericponto/pen/mJEyPL</a></div><div><br></div><div>The source can be downloaded by clicking on "Share" > "Export .zip"</div><div><br></div><div>===</div><div><br></div><div>[1] Caveat: This RxJS + Mithril + 6to5 aka Babel + HTML5 DataList autocomplete relies on the HTML5 DataList element - which has a couple of limitations:</div><div><br></div><div>- only usable in newer browsers</div><div><br></div><div>- also some limitation about the DOM, can't do but I can't remember (?) -</div><div><br></div><div>These limitations suggest that it may also be necessary to provide additional implementations of an autocomplete widget in Ur/Web which do not rely on on HTML5 <datalist>.</div><div><br></div><div>###</div><div><br></div></div>