before `:where`. You can call `clause-order` to see what the
current ordering of clauses is.
> Note: if you call `register-clause!` more than once for the same clause, the last call "wins". This allows you to correct an incorrect clause order insertion by simply calling `register-clause!` again with a different third argument.
Having registered a new clause, you might also want a helper function
for it, just as the built-in clauses have helpers in `honey.sql.helpers`.
Two functions exist in that namespace to make it easier for you to
define your own helpers:
*`generic-helper-variadic` -- most clauses accept an arbitrary number of items in a sequence and multiple calls in a DSL expression will merge so this is the helper you will use for most clauses,
*`generic-helper-unary` -- a handful of clauses only accept a single item and cannot be merged (they behave as "last one wins"), so this helper supports that semantic.
Each of these helper support functions should be called with the keyword that
identifies your new clause and the sequence of arguments passed to it. See
A number of PostgreSQL operators contain `@` which is not legal in a Clojure keyword or symbol (as literal syntax). The recommendation is to `def` your own name for these
operators, using `at` in place of `@`, with an explicit call to `keyword` (or `symbol`), and then use that `def`'d name when registering new operators and when writing
your DSL expressions:
```clojure
(def <at(keyword"<@"))
(sql/register-op! <at)
;; and use it in expressions: [<at:submitted[:range:begin:end]]
*`:ansi` -- the default, that quotes identifiers with double-quotes, like `"this"`
*`:mysql` -- quotes identifiers with backticks, and changes the precedence of `SET` in `UPDATE`
*`:oracle` -- quotes identifiers like `:ansi`, and does not use `AS` in aliases
*`:sqlserver` -- quotes identifiers with brackets, like `[this]`
A dialect spec is a hash map containing at least `:quote` but also optionally `:clause-order-fn` and/or `:as`:
*`:quote` -- a unary function that takes a string and returns the quoted version of it
*`:clause-order-fn` -- a unary function that takes a sequence of clause names (keywords) and returns an updated sequence of clause names; this defines the precedence of clauses in the DSL parser
*`:as` -- a boolean that indicates whether `AS` should be present in aliases (the default, if `:as` is omitted) or not (by specifying `:as false`)
To make writing new dialects easier, the following helper functions in `honey.sql` are available:
*`add-clause-before` -- a function that accepts the sequence of clause names, the (new) clause to add, and the clause to add it before (`nil` means add at the end)
*`get-dialect` -- a function that accepts an existing dialect name (keyword) and returns its spec (hash map)
*`strop` -- a function that accepts an opening quote, a string, and a closing quote and returns the quoted string, doubling-up any closing quote characters inside the string to make it legal SQL
*`upper-case` -- a locale-insensitive version of `clojure.string/upper-case`
For example, to add a variant of the `:ansi` dialect that forces names to be upper-case as well as double-quoting them: