diff --git a/src/metabase/legacy_mbql/schema/helpers.cljc b/src/metabase/legacy_mbql/schema/helpers.cljc index 29275c60d95966dbbf4f859e4e265b9c73a6d467..cdbde80f5edcfa3d07204c34070478f02d2f768b 100644 --- a/src/metabase/legacy_mbql/schema/helpers.cljc +++ b/src/metabase/legacy_mbql/schema/helpers.cljc @@ -9,6 +9,35 @@ ;;; --------------------------------------------------- defclause ---------------------------------------------------- +(defn mbql-clause? + "True if `x` is an MBQL clause (a sequence with a keyword as its first arg)." + [x] + (and (sequential? x) + (not (map-entry? x)) + (keyword? (first x)))) + +(defn is-clause? + "If `x` is an MBQL clause, and an instance of clauses defined by keyword(s) `k-or-ks`? + + (is-clause? :count [:count 10]) ; -> true + (is-clause? #{:+ :- :* :/} [:+ 10 20]) ; -> true" + [k-or-ks x] + (and + (mbql-clause? x) + (if (coll? k-or-ks) + ((set k-or-ks) (first x)) + (= k-or-ks (first x))))) + +(defn check-clause + "Returns `x` if it's an instance of a clause defined by keyword(s) `k-or-ks` + + (check-clause :count [:count 10]) ; => [:count 10] + (check-clause? #{:+ :- :* :/} [:+ 10 20]) ; -> [:+ 10 20] + (check-clause :sum [:count 10]) ; => nil" + [k-or-ks x] + (when (is-clause? k-or-ks x) + x)) + (defn- wrap-clause-arg-schema [arg-schema] [:schema (if (qualified-keyword? arg-schema) [:ref arg-schema] @@ -24,21 +53,6 @@ :rest [:* (wrap-clause-arg-schema arg-schema)] (wrap-clause-arg-schema vector-arg-schema))))) -;; TODO - this is a copy of the one in the [[metabase.legacy-mbql.util]] namespace. We need to reorganize things a bit -;; so we can use the same fn and avoid circular refs -(defn is-clause? - "If `x` an MBQL clause, and an instance of clauses defined by keyword(s) `k-or-ks`? - - (is-clause? :count [:count 10]) ; -> true - (is-clause? #{:+ :- :* :/} [:+ 10 20]) ; -> true" - [k-or-ks x] - (and - (vector? x) - (keyword? (first x)) - (if (coll? k-or-ks) - ((set k-or-ks) (first x)) - (= k-or-ks (first x))))) - (defn clause "Impl of [[metabase.legacy-mbql.schema.macros/defclause]] macro. Creates a Malli schema." [tag & arg-schemas] diff --git a/src/metabase/legacy_mbql/util.cljc b/src/metabase/legacy_mbql/util.cljc index f7486bb3f532bf7cdfbb2757b0eb6bd15ab1c636..932a19430b2086841532e9d992ac26200fcc73c7 100644 --- a/src/metabase/legacy_mbql/util.cljc +++ b/src/metabase/legacy_mbql/util.cljc @@ -13,11 +13,18 @@ [metabase.lib.schema.common :as lib.schema.common] [metabase.lib.util.match :as lib.util.match] [metabase.shared.util.i18n :as i18n] + [metabase.shared.util.namespaces :as shared.ns] [metabase.shared.util.time :as shared.ut] [metabase.util :as u] [metabase.util.log :as log] [metabase.util.malli :as mu])) +(shared.ns/import-fns + [schema.helpers + mbql-clause? + is-clause? + check-clause]) + (mu/defn normalize-token :- :keyword "Convert a string or keyword in various cases (`lisp-case`, `snake_case`, or `SCREAMING_SNAKE_CASE`) to a lisp-cased keyword." @@ -28,36 +35,6 @@ (str/replace #"_" "-") keyword)) -(defn mbql-clause? - "True if `x` is an MBQL clause (a sequence with a keyword as its first arg). (Since this is used by the code in - `normalize` this handles pre-normalized clauses as well.)" - [x] - (and (sequential? x) - (not (map-entry? x)) - (keyword? (first x)))) - -(defn is-clause? - "If `x` is an MBQL clause, and an instance of clauses defined by keyword(s) `k-or-ks`? - - (is-clause? :count [:count 10]) ; -> true - (is-clause? #{:+ :- :* :/} [:+ 10 20]) ; -> true" - [k-or-ks x] - (and - (mbql-clause? x) - (if (coll? k-or-ks) - ((set k-or-ks) (first x)) - (= k-or-ks (first x))))) - -(defn check-clause - "Returns `x` if it's an instance of a clause defined by keyword(s) `k-or-ks` - - (check-clause :count [:count 10]) ; => [:count 10] - (check-clause? #{:+ :- :* :/} [:+ 10 20]) ; -> [:+ 10 20] - (check-clause :sum [:count 10]) ; => nil" - [k-or-ks x] - (when (is-clause? k-or-ks x) - x)) - ;;; +----------------------------------------------------------------------------------------------------------------+ ;;; | Functions for manipulating queries | ;;; +----------------------------------------------------------------------------------------------------------------+