asami

Asami, the graph database https://github.com/threatgrid/asami
2020-12-29T20:50:31.247400Z

oh, hello 👋

quoll 2020-12-29T20:50:47.247700Z

Hi Alan!

2020-12-29T20:51:19.248Z

just took a cruise through the asami query engine, very nice 👏

2020-12-29T20:51:36.248400Z

i like the subgraph discovery piece that avoids unnecessary cross joins

quoll 2020-12-29T20:51:47.248700Z

Aww, thank you.

quoll 2020-12-29T20:53:19.251Z

Do you mean the analytics namespace, or are you referring to the aggregates part? (I’m unhappy with aggregate queries right now)

2020-12-29T20:53:43.251500Z

oh, i was referring to paths i think the function was called

quoll 2020-12-29T20:53:52.251800Z

Ah!

2020-12-29T20:53:58.252100Z

finding the route thruogh the tuples for the least amount of tuple-scooping

quoll 2020-12-29T20:54:02.252400Z

That’s the planner

2020-12-29T20:54:03.252500Z

err, the rules rather

quoll 2020-12-29T20:54:17.252800Z

Yup. It helps a lot!

quoll 2020-12-29T20:54:48.253500Z

I can’t say that I did a GREAT job of it, but I did it. 😊

quoll 2020-12-29T20:55:07.254300Z

Working code beats perfect proposals

2020-12-29T20:55:16.254400Z

i like it and it's small

2020-12-29T20:55:36.254800Z

i have been on a personal quest lately to write the smallest viable tuple store/datalog in javascript

2020-12-29T20:55:46.255100Z

eschewing optimizations when possible etc

2020-12-29T20:56:14.256100Z

i got kind of lost in the literature about bottom-up vs top-down evaluation, magic sets, etc

😂 1
quoll 2020-12-29T20:56:31.256700Z

Oh... going back to Naga in late 2016 should provide a good Cljs example. Easily portable to JS, I think

quoll 2020-12-29T20:57:16.257800Z

The “paths” function wasn’t as good, but the query engine was definitely minimum viable!

quoll 2020-12-29T20:57:30.258200Z

On my phone, but let me look...

2020-12-29T20:59:11.258900Z

https://gist.github.com/alandipert/4e390808b5dcee9020b6622c0a24023e#file-tinylog-js-L54-L60 is my vision for the DSL, tho the engine on that gist is too naive/broken

quoll 2020-12-29T21:00:48.260600Z

The only supported operation is inner joins, but it works. The index namespace is tiny as well

2020-12-29T21:03:09.261100Z

cool. yeah for indexes i'll just be doing JS arrays + binary search i think

quoll 2020-12-29T21:04:08.262200Z

That version of the planner used dynamic programming, so definitely don’t touch that old planner

quoll 2020-12-29T21:04:37.263Z

Yes, that will pack in far better, and give you other benefits as well

quoll 2020-12-29T21:04:56.263400Z

Hashmaps are expensive

quoll 2020-12-29T21:05:46.265100Z

The durable storage does arrays, though they’re broken into chunks and accessed via a tree

quoll 2020-12-29T21:06:11.265700Z

But I’m familiar with using arrays 🙂

2020-12-29T21:06:27.266Z

i prefer linked lists of course, but i'll deal 😄

2020-12-29T21:07:07.266700Z

i'd be curious to hear your reaction to my general ideas around using stuff like this for UI maintenance

quoll 2020-12-29T21:07:39.267100Z

I think it’s extremely flexible

quoll 2020-12-29T21:08:22.268200Z

I was storing lots of things in this sort of format without a query engine, because of the flexibility it provides

quoll 2020-12-29T21:09:04.269200Z

And it can be used to represent shallow maps trivially. Deeper structures take more effort, but are possible

quoll 2020-12-29T21:09:40.269900Z

Do you have specific ideas in terms of UI?

2020-12-29T21:10:53.270200Z

a general feeling, punctuated with concrete ideas

2020-12-29T21:11:49.271700Z

the general UI problem is continuously/efficiently synchronizing/managing UI primitives as business data underneath them changes

2020-12-29T21:12:18.272900Z

since most business data is hierarchical, most UI toolkits and UI data models propose hierarchical definitions of equality (and thus, change)

2020-12-29T21:12:44.273900Z

but in practice state used "internally" (for composition of UI primitives) gets muddled with business data

2020-12-29T21:13:25.275200Z

anyway, i have a good feeling about little datalog databases wired up to one another, each with independent ideas of what constitutes a "change", based on which queries are installed

2020-12-29T21:14:31.277200Z

my current direction is, make minimum viable database and query, and then build "subscriptions" on that. just run subscribed queries every time a new fact goes in, and if the result is different, fire a callback with the differences

quoll 2020-12-29T21:14:45.277400Z

When the data is quickly accessible in memory, then even without a query engine, I think it offers a lot. It’s easy to build any kind of structure in there. And you can store the universe in there without messing things up. You can also link things (like business data and UI elements) arbitrarily. It’s easy to get anything out of it. And it’s efficient.

2020-12-29T21:14:56.277700Z

the difference set can be interpreted at the DOM node level to inform adding/removing/changing DOM nodes etc

quoll 2020-12-29T21:15:49.278700Z

It’s relatively easy to find out if a fact can affect a subscribed query too. Naga does this

2020-12-29T21:17:53.281500Z

ah cool, i've noodled about that. i was thinking about how you could transform a query into a function that returned whether or not a fact could possibly affect it... and then only actually run the query again if there's a chance it would

2020-12-29T21:17:59.281800Z

that line of thinking got me back into rete

quoll 2020-12-29T21:18:31.282600Z

eg. If your query has: [?e :type ?t] [?e :name ?n] Then the output isn’t affected if you insert: [:entity124 :value 13]

quoll 2020-12-29T21:18:58.283200Z

Did you ever see my 2016 talk at the Conj?

quoll 2020-12-29T21:19:11.283600Z

Because I was discussing exactly this

2020-12-29T21:19:33.283900Z

no, but a watching is imminent

quoll 2020-12-29T21:19:50.284500Z

And pointing you at that is much easier than typing on my phone :rolling_on_the_floor_laughing:

👍 1
quoll 2020-12-29T21:22:26.288Z

It takes a shortcut. It assumes that data is only added, rather than allowing modifications. This is how Description Logic systems usually work. And you can emulate modification detection by having a system with time stamped add/delete statements. Or you can just save query results and compare them. It depends on your scalability needs

quoll 2020-12-29T21:23:35.289Z

If it’s in pure JS, then comparing results (as opposed to result-counts) is probably ideal

2020-12-29T21:32:00.290200Z

that's what i'm thinking... data inherently small... and timestamp for handling deletions not required

quoll 2020-12-29T21:33:02.290700Z

Naga’s engine would be ideal, I think

quoll 2020-12-29T21:34:26.293Z

It’s in 2 phases. The first finds dependencies between rules (this is run once, but you would run it after each insert) and then the engine looks for changes via counts, though you would look for data changes instead

2020-12-29T21:34:31.293200Z

i will watch the talk, study naga, and emit JS codes. thanks much for the info and pointers!

quoll 2020-12-29T21:36:07.293800Z

The code that does what I just said is all in here: https://github.com/threatgrid/naga/blob/main/src/naga/engine.cljc

1
1