{"id":15313352,"url":"https://github.com/Vincit/venia","last_synced_at":"2025-10-08T22:32:11.348Z","repository":{"id":20426524,"uuid":"89579704","full_name":"Vincit/venia","owner":"Vincit","description":"Clojure(Script) graphql query generation","archived":false,"fork":false,"pushed_at":"2022-04-07T08:16:29.000Z","size":76,"stargazers_count":197,"open_issues_count":23,"forks_count":20,"subscribers_count":12,"default_branch":"master","last_synced_at":"2025-01-26T13:05:55.866Z","etag":null,"topics":["clojure","clojurescript","graphql"],"latest_commit_sha":null,"homepage":"","language":"Clojure","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"epl-1.0","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/Vincit.png","metadata":{"files":{"readme":"README.md","changelog":"CHANGELOG.md","contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null}},"created_at":"2017-04-27T09:21:04.000Z","updated_at":"2024-05-31T07:43:10.000Z","dependencies_parsed_at":"2022-07-26T06:47:07.550Z","dependency_job_id":null,"html_url":"https://github.com/Vincit/venia","commit_stats":null,"previous_names":[],"tags_count":7,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Vincit%2Fvenia","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Vincit%2Fvenia/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Vincit%2Fvenia/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Vincit%2Fvenia/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/Vincit","download_url":"https://codeload.github.com/Vincit/venia/tar.gz/refs/heads/master","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":235706363,"owners_count":19032607,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["clojure","clojurescript","graphql"],"created_at":"2024-10-01T08:41:26.509Z","updated_at":"2025-10-08T22:32:06.007Z","avatar_url":"https://github.com/Vincit.png","language":"Clojure","funding_links":[],"categories":["Libraries","Clojure"],"sub_categories":["ClojureScript Libraries"],"readme":"# venia\n\n\n[![Clojars Project](https://img.shields.io/clojars/v/vincit/venia.svg)](https://clojars.org/vincit/venia)\n\n\n[![Build Status](https://travis-ci.org/Vincit/venia.svg?branch=master)](https://travis-ci.org/Vincit/venia)\n\nA Clojure(Script) qraphql query client library. Generate valid graphql queries with Clojure data structures.\n\n## Usage\n\nVenia is originally supposed to be used in Clojurescript apps, but can be used as well in Clojure, as the core \nis written in CLJC. The sole purpose of this library is graphql query string generation from Clojure data, \nso that strings concatenations and manipulations could be avoided when using grapqhl.\nIt is up to developers to hook it up to frontend apps. However, at least some sort of re-frame-graphql-fx library \nis on a roadmap. \n\n\n### Simple query\n\nThe easiest way to start with venia, is simple's query generation. \n\n```clj\n(ns my.project\n  (:require [venia.core :as v]))\n\n(v/graphql-query {:venia/queries [[:employee {:id 1 :active true} [:name :address [:friends [:name :email]]]]]})\n\n=\u003e \"{employee(id:1,active:true){name,address,friends{name,email}}}\"\n```\n\nObviously, If we would like to fetch employees and projects within the same simple query, we would do it this way:\n\n```clj\n(v/graphql-query {:venia/queries [[:employee {:id 1 :active true} [:name :address [:friends [:name :email]]]]\n                                  [:projects {:active true} [:customer :price]]]})\n\n=\u003e \"{employee(active:true){name,address},project(active:true){customer,price}}\"\n```\n\n### Field arguments\n\nIn the example above, `:employee` and `:projects` fields have arguments `{:id 1 :active true}` and `{:id 1 :active true}` \nrespectively.\n\nWe can add arguments to other fields easily by wrapping field name and its arguments to vector `[:customer {:id 2}]`:\n\n```clj\n(v/graphql-query {:venia/queries [[:projects {:active true} [[:customer {:id 2}] :price]]]})\n\n=\u003e \"{project(active:true){customer(id:2),price}}\"\n```\n\n### Query with alias\n\nNow, if we need to have an alias for query, it can be easily achieved by using venia's query-with-data map\n\n```clj\n(v/graphql-query {:venia/queries [{:query/data [:employee {:id 1 :active true} [:name :address [:friends [:name :email]]]]\n                                   :query/alias :workhorse}\n                                  {:query/data  [:employee {:id 2 :active true} [:name :address [:friends [:name :email]]]]\n                                   :query/alias :boss}]})\n     \n=\u003e prettified:\n{\n  workhorse: employee(id: 1, active: true) {\n    name\n    address\n  },\n  boss: employee(id: 2, active: true) {\n    name\n    address\n  }\n}\n```\n\nIn the query above, we use `:query/data` key for query definition and `:query/alias` for query's alias definition.\n\n### Query with fragments\n\nWhat about fragments? Just add `:venia/fragments` vector with fragments definitions\n\n```clj\n(v/graphql-query {:venia/queries   [{:query/data  [:employee {:id 1 :active true} :fragment/comparisonFields]\n                                     :query/alias :workhorse}\n                                    {:query/data  [:employee {:id 2 :active true} :fragment/comparisonFields]\n                                     :query/alias :boss}]\n                  :venia/fragments [{:fragment/name   \"comparisonFields\"\n                                     :fragment/type   :Worker\n                                     :fragment/fields [:name :address]}]})\n\n=\u003e prettified:\n{\n  workhorse: employee(id: 1, active: true) {\n    ...comparisonFields\n  }\n  boss: employee(id: 2, active: true) {\n    ...comparisonFields\n  }\n}\n\nfragment comparisonFields on Worker {\n  name\n  address\n}\n```\n\n### Query with variables\n\nNow you can generate really complex queries with variables as well. In order to define variables, we need to define \nan operation type and name.\n\n\n```clj\n(v/graphql-query {:venia/operation {:operation/type :query\n                                    :operation/name \"employeeQuery\"}\n                  :venia/variables [{:variable/name    \"id\"\n                                     :variable/type    :Int\n                                     :variable/default 1}\n                                    {:variable/name \"name\"\n                                     :variable/type :String}]\n                  :venia/queries   [{:query/data  [:employee {:id     :$id\n                                                              :active true\n                                                              :name   :$name}\n                                                   :fragment/comparisonFields]\n                                     :query/alias :workhorse}\n                                    {:query/data  [:employee {:id     :$id\n                                                              :active false}\n                                                   :fragment/comparisonFields]\n                                     :query/alias :boss}]\n                  :venia/fragments [{:fragment/name   \"comparisonFields\"\n                                     :fragment/type   :Worker\n                                     :fragment/fields [:name :address [:friends [:name :email]]]}]})\n\n=\u003e prettified:\nquery employeeQuery($id: Int = 1, $name: String) {\n  workhorse: employee(id: $id, active: true, name: $name) {\n    ...comparisonFields\n  }\n  boss: employee(id: $id, active: false) {\n    ...comparisonFields\n  }\n}\n\nfragment comparisonFields on Worker {\n  name\n  address\n  friends {\n    name\n    email\n  }\n}\n\n```\n\n### Mutation\n\nMutations are also supported, just use `:mutation` operation type:\n\n```clj\n\n(v/graphql-query {:venia/operation {:operation/type :mutation\n                                    :operation/name \"AddProjectToEmployee\"}\n                  :venia/variables [{:variable/name \"id\"\n                                     :variable/type :Int!}\n                                    {:variable/name \"project\"\n                                     :variable/type :ProjectNameInput!}]\n                  :venia/queries   [[:addProject {:employeeId :$id\n                                                  :project    :$project}\n                                     [:allocation :name]]]})\n                                     \n=\u003e prettified:\nmutation AddProjectToEmployee($id:Int!,$project:ProjectNameInput!) {\n  addProject(employeeId:$id, project:$project) {\n    allocation,\n    name\n  }\n}\n```\n\n### Validation\n\nVenia will verify that you don't use undefined variables or fragments. \n\nFor example, the following `v/graphql-query` calls will throw exceptions:\n\n```clj\n\n(v/graphql-query {:venia/queries [[:employee {:id 1 :active true} :fragment/undefined]]}\n\n(v/graphql-query {:venia/queries [[:employee {:id 1 :active :$undefined} [:name]]]}))\n```\n\nbecause fragment and variable are never defined.\n\n### Meta fields\n\nYou can use graphql's `__typename` meta field anywhere inside of your query.\nFor example:\n\n```clj\n(v/graphql-query {:venia/queries [[:employee [:meta/typename :name :address]]}\n\n=\u003e prettified:\n\n{\n  employee {\n    __typename,\n    name,\n    address\n  }\n}\n\n```\n\n\n## License\n\nCopyright © 2017 Vincit\n\nDistributed under the Eclipse Public License, the same as Clojure.\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2FVincit%2Fvenia","html_url":"https://awesome.ecosyste.ms/projects/github.com%2FVincit%2Fvenia","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2FVincit%2Fvenia/lists"}