Skip to content

Instantly share code, notes, and snippets.

@jonase
Forked from richhickey/codeq-examples.clj
Created November 20, 2012 10:20
Show Gist options
  • Save jonase/4117130 to your computer and use it in GitHub Desktop.
Save jonase/4117130 to your computer and use it in GitHub Desktop.

Revisions

  1. @richhickey richhickey created this gist Nov 20, 2012.
    131 changes: 131 additions & 0 deletions codeq-examples.clj
    Original file line number Diff line number Diff line change
    @@ -0,0 +1,131 @@
    (require '[datomic.api :as d])
    (require '[clojure.pprint :refer [pprint]])
    (def uri "datomic:free://localhost:4334/git")
    (def conn (d/connect uri))
    (def db (d/db conn))

    ;; committers
    (d/q '[:find ?email
    :where
    [_ :commit/committer ?u]
    [?u :email/address ?email]]
    db)

    ;; authors
    (d/q '[:find ?email
    :where
    [_ :commit/author ?e]
    [?u :email/address ?email]]
    db)

    ;; Initial commit date
    (d/q '[:find (min ?date)
    :where
    [_ :commit/committedAt ?date]]
    db)

    ;; How many commits in total
    (d/q '[:find (count ?c)
    :where
    [?c :git/type :commit]]
    db)

    ;; Top 3 committers
    (->> (d/q '[:find ?email (count ?commit)
    :where
    [?commit :commit/author ?author]
    [?author :email/address ?email]]
    db)
    (sort-by second)
    reverse
    (take 3))

    ;; First & latest commit date by author email
    (d/q '[:find ?email (min ?date) (max ?date)
    :in $ ?email
    :where
    [?e :commit/committedAt ?date]
    [?e :commit/author ?u]
    [?u :email/address ?email]]
    db "[email protected]")

    ;; Rules from http://blog.datomic.com/2012/10/codeq.html
    (def rules
    '[[(node-files ?n ?f)
    [?n :node/object ?f]
    [?f :git/type :blob]]
    [(node-files ?n ?f)
    [?n :node/object ?t]
    [?t :git/type :tree]
    [?t :tree/nodes ?n2]
    (node-files ?n2 ?f)]

    [(object-nodes ?o ?n)
    [?n :node/object ?o]]
    [(object-nodes ?o ?n)
    [?n2 :node/object ?o]
    [?t :tree/nodes ?n2]
    (object-nodes ?t ?n)]

    [(commit-files ?c ?f)
    [?c :commit/tree ?root]
    (node-files ?root ?f)]

    [(commit-codeqs ?c ?cq)
    (commit-files ?c ?f)
    [?cq :codeq/file ?f]]

    [(file-commits ?f ?c)
    (object-nodes ?f ?n)
    [?c :commit/tree ?n]]

    [(codeq-commits ?cq ?c)
    [?cq :codeq/file ?f]
    (file-commits ?f ?c)]])

    ;; Find authors who has had part in the evolution of a function
    (defn commit-dates [name]
    (map first
    (d/q '[:find (min ?date) ?sha
    :in $ % ?name
    :where
    [?n :code/name ?name]
    [?cq :clj/def ?n]
    [?cq :codeq/code ?c]
    [?c :code/sha ?sha]
    (codeq-commits ?cq ?commit)
    [?commit :commit/committedAt ?date]]
    db
    rules
    name)))

    (commit-dates "clojure.core/partition")

    (defn committer-by-insts [insts]
    (d/q '[:find ?email
    :in $ [?inst ...]
    :where
    [?commit :commit/committedAt ?inst]
    [?commit :commit/committer ?u]
    [?u :email/address ?email]]
    db
    insts))

    (-> "clojure.core.reducers/fold" commit-dates committer-by-insts)

    (->> (d/q '[:find ?name (count ?date)
    :in [[?name ?date ?sha]]]
    (d/q '[:find ?name (min ?date) ?sha
    :in $ %
    :where
    [?n :code/name ?name]
    [?cq :clj/def ?n]
    [?cq :codeq/code ?c]
    [?c :code/sha ?sha]
    (codeq-commits ?cq ?commit)
    [?commit :commit/committedAt ?date]]
    db
    rules))
    (sort-by second)
    reverse
    (take 5))