Fork me on GitHub
#datomic
<
2016-12-07
>
csm02:12:02

how do you connect the peer server to the dev storage? datomic: fails because ‘foo’ isn’t in the catalog, but leaving off the db name causes it to not match predicate “database-uri?"

marshall02:12:57

@csm you'll need to create the database with a peer first. You can use the bin/repl script included with the Datomic distribution to start a repl with datomic in the classpath

marshall02:12:38

Then (require '[datomic.api :as d])

marshall02:12:51

(d/create-database "datomic:)

marshall02:12:19

(Assuming you're running a dev transactor locally on 4334)

marshall02:12:04

After that you can serve the foo database using peerserver

ovan08:12:32

I'm a little surprised about this. For some reason I just assumed idents would be returned as keywords in pull requests. I can see how it's a hassle to convert it every time you want to push those on wire as keywords/strings. I wonder what the use case here. Can't you just use the ident anywhere you could use entity id?

robert-stuttaford08:12:41

it comes back as a map in pull because you may want to put other metadata on those entities

ovan08:12:43

Ok, didn't think about that.

robert-stuttaford08:12:41

it is a bit fussy to use full entities for enums, but it’s really not that much extra code to deal with, and the benefits are worth it

robert-stuttaford08:12:49

210,437 entities in our database are active

ovan08:12:31

Is any of that information coming from metadata on enum entity?

robert-stuttaford08:12:57

the only context this code has is the query string

robert-stuttaford08:12:31

it queries to find the dates and datom count, and the text at the bottom will display the :db/doc value once i have one

robert-stuttaford08:12:59

having it as an entity allows you to e.g. mark it deprecated later, with a deprecated boolean schema attr you make for yourself

robert-stuttaford08:12:31

it boils down to this, for me: enum values have semantic meaning to which we can attach behaviour and metadata

robert-stuttaford08:12:47

making it a keyword forces you to keep that meaning / metadata outside of your database

ovan08:12:16

Makes sense. Thanks for clearing that up. This idea about metadata on enums would perhaps be useful to have in datomic docs too.

karol.adamiec09:12:11

@robert-stuttaford thx for enum stuff. one question. How do i write query that returns something constant to clients? i have db on each environment, ids are different. Need to translate them to constants so clients dont have to. Is there any way to do that other than extra query and merge?

karol.adamiec09:12:54

and on a related note when should one use keyword then?

robert-stuttaford09:12:15

for the case where i want to flatten idents into parent maps:

robert-stuttaford09:12:17

clojure
(defn flatten-idents [m]
  (walk/postwalk 
   (fn [item]
     (if (and (map? item) (:db/ident item) (check-its-not-an-attr-here))
       (:db/ident item)
       item))
   m))

robert-stuttaford09:12:54

other than that, i haven’t really had to deal with it differently

robert-stuttaford09:12:04

i haven’t ever used :db.type/keyword; in all cases i prefered an ident

robert-stuttaford09:12:15

i realise this is a personal preference thing 🙂

jarppe11:12:48

The d/entity works differently when using "real" db vs. in-memory db? On real db it returns nil if entity does not exist. with memory db it always returns a datomic.query.EntityMap. Is this a bug or feature?

jarppe11:12:15

oh, sorry, my mistake, it always returns EntityMap

jarppe11:12:13

But what is an idiomatic way to test that entity exists?

robert-stuttaford11:12:49

(seq (d/datoms db :eavt id-or-lookup-ref)) is my goto, @jarppe

karol.adamiec11:12:58

@robert-stuttaford nice bit of clojure. damn i do need to switch away from the REST endpoint 🤓

robert-stuttaford11:12:26

lol you’re on your own buddy

karol.adamiec11:12:36

yeah, good news is that having datomic as db i can spread clojure inside out 🙂

mgrbyte11:12:11

My "goto" is always: (d/entity db [:my/attr id]) or (d/entity db id)

jarppe12:12:14

@robert-stuttaford thanks, I'll go with that. Although it would be great to be able to check that entity exists and get the entity in one step.

jarppe12:12:57

@mgrbyte d/entity would be great, but afaik you cant use that to test that entity esists

jarppe12:12:43

(d/entity (d/db conn) 42) returns {:db/id 42}

rauh12:12:14

Why not use entid?

mgrbyte12:12:03

@jarppe Yeh, it seems that if you use a lookup ref you can (d/entity will return nil if it can't find) - but using a plain long id just gives you a lazy entity

mgrbyte12:12:04

@rauh entid returns the id associated with a keyword, or if an id was passed instead of an ident keyword, it just returns the id

jarppe12:12:20

@mgrbyte that explains it, I was so sure that d/entity returned nil, but I was using lookup ref at that time. Now I have actual id and must use the d/datoms as @robert-stuttaford suggested.

mgrbyte13:12:35

@jarppe yep. (-> (d/datoms db :eavt id) first nil?) would be the way to go in the id case. I'd use this instead of seq, since you wouldn't want to realise all the datoms for a given id if they did exist (i.e you're just asking if an entity exists for a given id as opposed to all datoms related to that that entity id.

leov14:12:35

hello. quick question: can I combine two entities under one pull inside d/q query?

leov14:12:50

(can't say I fully understand pull syntax)

leov14:12:30

nevermind. I think I just did it, however output is ungrouped

danielstockton14:12:47

@leov in a query the pull expression takes an ?entity-var like ?e which can be bound to several entities

leov14:12:52

so parent entity goes with one child entity, then goes next parent entity

leov14:12:46

ummm. several entities in the sense that they are of the same umm type?

danielstockton14:12:24

several entities in the sense that ?e will be bound to different values in your resultset

leov14:12:57

(d/q '[:find  (pull ?app [:heroku.app.name :heroku.app.id])        
              (pull ?config-key [:heroku.app.config.key :heroku.app.config.value :heroku.app.config.app-id])
            :where [?app :heroku.app.id     ?app-id]
                   [?config-key :heroku.app.config.app-id ?app-id]] @db/main)

leov14:12:52

well. I have parent-children relation and trying to get {...parent entity fields... :children [{...} {..}]} if possible in one query

danielstockton14:12:37

you might want to look at 'map specifications' from http://docs.datomic.com/pull.html

misha14:12:25

Why does everyone pull inside query lately?

danielstockton14:12:26

I suppose its a toss up between re-usability and terseness?

danielstockton14:12:05

Haven't used datomic enough to know much about the practical benefits of either approach.

potetm14:12:12

Well one obvious answer is you want a named map instead of a set of tuples 🙂

potetm14:12:27

I usually do it if I want something like limit, which afaik you can't get outside of pull.

danielstockton14:12:49

You can't use limit expressions with both pull and in pull expressions within a query?

danielstockton15:12:20

The other way would be using the datoms API i suppose, since this gives you a lazy sequence to iterate over?

potetm15:12:37

Yeah I meant you have to use the pull api in some capacity.

potetm15:12:56

Yeah, datoms would work if that's what you're into.

leov15:12:21

@misha, well, I understood it that pull has magic powers

tjtolton17:12:19

Having some issues getting datomic running per the tutorial... I downloaded the zip, brew installed maven, ran bin/maven-install however, still hitting this:

tjtolton17:12:26

Suggestions?

tjtolton17:12:35

@mgrbyte Moved per your suggestion

marshall17:12:45

the bin/maven-install script will install the peer library in your local maven

tjtolton17:12:11

doesn't lein automatically look in my local maven?

marshall17:12:41

if you want to use the client library you should follow this: http://docs.datomic.com/project-setup.html

marshall17:12:58

and add [com.datomic/clj-client “0.8.606”] to your dependencies

tjtolton17:12:02

hah! oh man

tjtolton17:12:15

Thanks. Boy did I overlook the obvious problem

tjtolton17:12:55

there it goes. successful require

timgilbert20:12:21

Following up on the entity thing a bit belatedly, I can definitely see the utility of having a distinct entity for enums that you can attach stuff to. For our application it didn't seem to outweigh the hassle of needing to do something like @robert-stuttaford's walk/postwalk code every time we needed to return some code to the client

timgilbert20:12:35

We generally have clients sending us pull syntax, so it can be a little hard to determine when we would need to execute that kind of post-processing, and doing it every time seemed possibly wasteful (plus wind up driving our client and server code farther apart. potentially)

timgilbert20:12:45

It seemed easier just to use keywords, which can then be just pulled in like any other attribute value in the pull syntax. If (d/pull) and friends auto-resolved idents in the output we would probably have gone with them.