768 lines
53 KiB
HTML
768 lines
53 KiB
HTML
<html>
|
|
<head>
|
|
<meta http-equiv="Content-Type" content="text/html; charset=utf-8">
|
|
<link rel="stylesheet" href="../../../coverage.css"/> <title> dog_and_duck/quack/picky/utils.clj </title>
|
|
</head>
|
|
<body>
|
|
<span class="covered" title="1 out of 1 forms covered">
|
|
001 (ns dog-and-duck.quack.picky.utils
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
002 "Utility functions supporting the picky validator"
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
003 (:require [clojure.set :refer [intersection]]
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
004 [dog-and-duck.quack.picky.constants :refer [activitystreams-context-uri
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
005 actor-types
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
006 context-key severity-filters
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
007 validation-fault-context-uri
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
008 activity-types]]
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
009 [dog-and-duck.utils.process :refer [get-hostname get-pid]]
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
010 [scot.weft.i18n.core :refer [get-message]]
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
011 [taoensso.timbre :as log :refer [warn]])
|
|
</span><br/>
|
|
<span class="blank" title="0 out of 0 forms covered">
|
|
012
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
013 (:import [java.net URI URISyntaxException]))
|
|
</span><br/>
|
|
<span class="blank" title="0 out of 0 forms covered">
|
|
014
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
015 ;;; Copyright (C) Simon Brooke, 2022
|
|
</span><br/>
|
|
<span class="blank" title="0 out of 0 forms covered">
|
|
016
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
017 ;;; This program is free software; you can redistribute it and/or
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
018 ;;; modify it under the terms of the GNU General Public License
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
019 ;;; as published by the Free Software Foundation; either version 2
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
020 ;;; of the License, or (at your option) any later version.
|
|
</span><br/>
|
|
<span class="blank" title="0 out of 0 forms covered">
|
|
021
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
022 ;;; This program is distributed in the hope that it will be useful,
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
023 ;;; but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
024 ;;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
025 ;;; GNU General Public License for more details.
|
|
</span><br/>
|
|
<span class="blank" title="0 out of 0 forms covered">
|
|
026
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
027 ;;; You should have received a copy of the GNU General Public License
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
028 ;;; along with this program; if not, write to the Free Software
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
029 ;;; Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
|
</span><br/>
|
|
<span class="blank" title="0 out of 0 forms covered">
|
|
030
|
|
</span><br/>
|
|
<span class="blank" title="0 out of 0 forms covered">
|
|
031
|
|
</span><br/>
|
|
<span class="covered" title="1 out of 1 forms covered">
|
|
032 (defn actor-type?
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
033 "Return `true` if the `x` is a recognised actor type, else `false`."
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
034 [^String x]
|
|
</span><br/>
|
|
<span class="covered" title="6 out of 6 forms covered">
|
|
035 (if (actor-types x) true false))
|
|
</span><br/>
|
|
<span class="blank" title="0 out of 0 forms covered">
|
|
036
|
|
</span><br/>
|
|
<span class="covered" title="1 out of 1 forms covered">
|
|
037 (defn truthy?
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
038 "Return `true` if `x` is truthy, else `false`. There must be some more
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
039 idiomatic way to do this?"
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
040 [x]
|
|
</span><br/>
|
|
<span class="covered" title="4 out of 4 forms covered">
|
|
041 (if x true false))
|
|
</span><br/>
|
|
<span class="blank" title="0 out of 0 forms covered">
|
|
042
|
|
</span><br/>
|
|
<span class="covered" title="1 out of 1 forms covered">
|
|
043 (defn xsd-non-negative-integer?
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
044 "Return `true` if `value` matches the pattern for an
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
045 [xsd:nonNegativeInteger](https://www.w3.org/TR/xmlschema11-2/#nonNegativeInteger), else `false`"
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
046 [x]
|
|
</span><br/>
|
|
<span class="partial" title="9 out of 10 forms covered">
|
|
047 (and (integer? x)(>= x 0)))
|
|
</span><br/>
|
|
<span class="blank" title="0 out of 0 forms covered">
|
|
048
|
|
</span><br/>
|
|
<span class="covered" title="1 out of 1 forms covered">
|
|
049 (defn has-type?
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
050 "Return `true` if object `x` has a type in `acceptable`, else `false`.
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
051
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
052 The values of `:type` fields of ActivityStreams objects may be lists; they
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
053 are considered to have a type if a member of the list is in `acceptable`.
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
054
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
055 `acceptable` may be passed as a string, in which case there is only one
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
056 acceptable value, or as a set of strings, in which case any member of the
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
057 set is acceptable."
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
058 [x acceptable]
|
|
</span><br/>
|
|
<span class="partial" title="5 out of 25 forms covered">
|
|
059 (assert (map? x) (or (string? acceptable) (set? acceptable)))
|
|
</span><br/>
|
|
<span class="covered" title="4 out of 4 forms covered">
|
|
060 (let [tv (:type x)]
|
|
</span><br/>
|
|
<span class="covered" title="2 out of 2 forms covered">
|
|
061 (truthy?
|
|
</span><br/>
|
|
<span class="partial" title="4 out of 5 forms covered">
|
|
062 (cond
|
|
</span><br/>
|
|
<span class="partial" title="10 out of 19 forms covered">
|
|
063 (and (string? acceptable) (coll? tv)) (not-empty (filter #(= % acceptable) tv))
|
|
</span><br/>
|
|
<span class="partial" title="10 out of 19 forms covered">
|
|
064 (and (set? acceptable) (coll? tv)) (not-empty (filter #(acceptable %) tv))
|
|
</span><br/>
|
|
<span class="covered" title="6 out of 6 forms covered">
|
|
065 (string? acceptable) (= tv acceptable)
|
|
</span><br/>
|
|
<span class="covered" title="6 out of 6 forms covered">
|
|
066 (set? acceptable) (acceptable tv)))))
|
|
</span><br/>
|
|
<span class="blank" title="0 out of 0 forms covered">
|
|
067
|
|
</span><br/>
|
|
<span class="covered" title="1 out of 1 forms covered">
|
|
068 (defn object-or-uri?
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
069 "Very basic check that `x` is either an object or a URI."
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
070 ([x]
|
|
</span><br/>
|
|
<span class="partial" title="1 out of 3 forms covered">
|
|
071 (try
|
|
</span><br/>
|
|
<span class="covered" title="12 out of 12 forms covered">
|
|
072 (cond (string? x) (uri? (URI. x))
|
|
</span><br/>
|
|
<span class="covered" title="3 out of 3 forms covered">
|
|
073 (map? x) true
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
074 :else false)
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
075 (catch URISyntaxException _ false)
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
076 (catch NullPointerException _ false)))
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
077 ([x type]
|
|
</span><br/>
|
|
<span class="covered" title="5 out of 5 forms covered">
|
|
078 (if (object-or-uri? x)
|
|
</span><br/>
|
|
<span class="covered" title="5 out of 5 forms covered">
|
|
079 (if (map? x)
|
|
</span><br/>
|
|
<span class="covered" title="4 out of 4 forms covered">
|
|
080 (has-type? x type)
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
081 true)
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
082 false)))
|
|
</span><br/>
|
|
<span class="blank" title="0 out of 0 forms covered">
|
|
083
|
|
</span><br/>
|
|
<span class="partial" title="5 out of 46 forms covered">
|
|
084 (defmacro link-or-uri?
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
085 "Very basic check that `x` is either a link object or a URI."
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
086 [x]
|
|
</span><br/>
|
|
<span class="not-covered" title="0 out of 2 forms covered">
|
|
087 `(if (object-or-uri? ~x) (has-type? ~x "Link") false))
|
|
</span><br/>
|
|
<span class="blank" title="0 out of 0 forms covered">
|
|
088
|
|
</span><br/>
|
|
<span class="blank" title="0 out of 0 forms covered">
|
|
089
|
|
</span><br/>
|
|
<span class="covered" title="1 out of 1 forms covered">
|
|
090 (defn activity-type?
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
091 "`true` if `x`, a string, represents a recognised ActivityStreams activity
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
092 type."
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
093 [^String x]
|
|
</span><br/>
|
|
<span class="covered" title="6 out of 6 forms covered">
|
|
094 (if (activity-types x) true false))
|
|
</span><br/>
|
|
<span class="blank" title="0 out of 0 forms covered">
|
|
095
|
|
</span><br/>
|
|
<span class="covered" title="1 out of 1 forms covered">
|
|
096 (defn has-activity-type?
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
097 "Return `true` if the object `x` has a type which is an activity type, else
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
098 `false`."
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
099 [x]
|
|
</span><br/>
|
|
<span class="covered" title="4 out of 4 forms covered">
|
|
100 (let [tv (:type x)]
|
|
</span><br/>
|
|
<span class="covered" title="2 out of 2 forms covered">
|
|
101 (cond
|
|
</span><br/>
|
|
<span class="partial" title="3 out of 11 forms covered">
|
|
102 (coll? tv) (truthy? (not-empty (filter activity-type? tv)))
|
|
</span><br/>
|
|
<span class="covered" title="3 out of 3 forms covered">
|
|
103 :else (activity-type? tv))))
|
|
</span><br/>
|
|
<span class="blank" title="0 out of 0 forms covered">
|
|
104
|
|
</span><br/>
|
|
<span class="covered" title="1 out of 1 forms covered">
|
|
105 (defn has-actor-type?
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
106 "Return `true` if the object `x` has a type which is an actor type, else
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
107 `false`."
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
108 [x]
|
|
</span><br/>
|
|
<span class="covered" title="4 out of 4 forms covered">
|
|
109 (let [tv (:type x)]
|
|
</span><br/>
|
|
<span class="covered" title="2 out of 2 forms covered">
|
|
110 (cond
|
|
</span><br/>
|
|
<span class="partial" title="3 out of 11 forms covered">
|
|
111 (coll? tv) (truthy? (not-empty (filter actor-type? tv)))
|
|
</span><br/>
|
|
<span class="covered" title="3 out of 3 forms covered">
|
|
112 :else (actor-type? tv))))
|
|
</span><br/>
|
|
<span class="blank" title="0 out of 0 forms covered">
|
|
113
|
|
</span><br/>
|
|
<span class="covered" title="1 out of 1 forms covered">
|
|
114 (defn filter-severity
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
115 "Return a list of reports taken from these `reports` where the severity
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
116 of the report is greater than this or equal to this `severity`."
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
117 [reports severity]
|
|
</span><br/>
|
|
<span class="partial" title="9 out of 11 forms covered">
|
|
118 (cond (nil? (severity-filters severity)) (throw
|
|
</span><br/>
|
|
<span class="not-covered" title="0 out of 3 forms covered">
|
|
119 (ex-info
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
120 "Argument `severity` was not a valid severity key"
|
|
</span><br/>
|
|
<span class="not-covered" title="0 out of 6 forms covered">
|
|
121 {:arguments {:reports reports
|
|
</span><br/>
|
|
<span class="not-covered" title="0 out of 1 forms covered">
|
|
122 :severity severity}}))
|
|
</span><br/>
|
|
<span class="covered" title="3 out of 3 forms covered">
|
|
123 (empty? reports) nil
|
|
</span><br/>
|
|
<span class="partial" title="8 out of 10 forms covered">
|
|
124 (and
|
|
</span><br/>
|
|
<span class="covered" title="3 out of 3 forms covered">
|
|
125 (coll? reports)
|
|
</span><br/>
|
|
<span class="covered" title="4 out of 4 forms covered">
|
|
126 (every? map? reports)
|
|
</span><br/>
|
|
<span class="covered" title="5 out of 5 forms covered">
|
|
127 (every? :severity reports))(remove
|
|
</span><br/>
|
|
<span class="partial" title="4 out of 5 forms covered">
|
|
128 #(if (:severity %)
|
|
</span><br/>
|
|
<span class="covered" title="7 out of 7 forms covered">
|
|
129 ((severity-filters severity) (:severity %))
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
130 false)
|
|
</span><br/>
|
|
<span class="covered" title="1 out of 1 forms covered">
|
|
131 reports)
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
132 :else
|
|
</span><br/>
|
|
<span class="not-covered" title="0 out of 1 forms covered">
|
|
133 (throw
|
|
</span><br/>
|
|
<span class="not-covered" title="0 out of 3 forms covered">
|
|
134 (ex-info
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
135 "Argument `reports` was not a collection of fault reports"
|
|
</span><br/>
|
|
<span class="not-covered" title="0 out of 6 forms covered">
|
|
136 {:arguments {:reports reports
|
|
</span><br/>
|
|
<span class="not-covered" title="0 out of 1 forms covered">
|
|
137 :severity severity}}))))
|
|
</span><br/>
|
|
<span class="blank" title="0 out of 0 forms covered">
|
|
138
|
|
</span><br/>
|
|
<span class="covered" title="1 out of 1 forms covered">
|
|
139 (defn context?
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
140 "Returns `true` iff `x` quacks like an ActivityStreams context, else false.
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
141
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
142 A context is either
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
143 1. the URI (actually an IRI) `activitystreams-context-uri`, or
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
144 2. a collection comprising that URI and a map."
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
145 [x]
|
|
</span><br/>
|
|
<span class="partial" title="4 out of 6 forms covered">
|
|
146 (cond
|
|
</span><br/>
|
|
<span class="covered" title="3 out of 3 forms covered">
|
|
147 (nil? x) false
|
|
</span><br/>
|
|
<span class="covered" title="11 out of 11 forms covered">
|
|
148 (string? x) (and (= x activitystreams-context-uri) true)
|
|
</span><br/>
|
|
<span class="partial" title="19 out of 20 forms covered">
|
|
149 (coll? x) (and (context? (first (remove map? x)))
|
|
</span><br/>
|
|
<span class="covered" title="4 out of 4 forms covered">
|
|
150 (= (count x) 2)
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
151 true)
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
152 :else false))
|
|
</span><br/>
|
|
<span class="blank" title="0 out of 0 forms covered">
|
|
153
|
|
</span><br/>
|
|
<span class="covered" title="27 out of 27 forms covered">
|
|
154 (defmacro has-context?
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
155 "True if `x` is an ActivityStreams object with a valid context, else `false`."
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
156 [x]
|
|
</span><br/>
|
|
<span class="covered" title="1 out of 1 forms covered">
|
|
157 `(context? (context-key ~x)))
|
|
</span><br/>
|
|
<span class="blank" title="0 out of 0 forms covered">
|
|
158
|
|
</span><br/>
|
|
<span class="covered" title="1 out of 1 forms covered">
|
|
159 (defn make-fault-object
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
160 "Return a fault object with these `severity`, `fault` and `narrative` values.
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
161
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
162 An ActivityPub object MUST have a globally unique ID. Whether this is
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
163 meaningful depends on whether we persist fault report objects and serve
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
164 them, which at present I have no plans to do."
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
165 ;; TODO: should not pass in the narrative; instead should use the :fault value
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
166 ;; to look up the narrative in a resource file.
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
167 [severity fault]
|
|
</span><br/>
|
|
<span class="covered" title="9 out of 9 forms covered">
|
|
168 (assoc {}
|
|
</span><br/>
|
|
<span class="covered" title="2 out of 2 forms covered">
|
|
169 context-key validation-fault-context-uri
|
|
</span><br/>
|
|
<span class="covered" title="5 out of 5 forms covered">
|
|
170 :id (str "https://"
|
|
</span><br/>
|
|
<span class="covered" title="2 out of 2 forms covered">
|
|
171 (get-hostname)
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
172 "/fault/"
|
|
</span><br/>
|
|
<span class="covered" title="2 out of 2 forms covered">
|
|
173 (get-pid)
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
174 ":"
|
|
</span><br/>
|
|
<span class="covered" title="3 out of 3 forms covered">
|
|
175 (inst-ms (java.util.Date.)))
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
176 :type "Fault"
|
|
</span><br/>
|
|
<span class="covered" title="1 out of 1 forms covered">
|
|
177 :severity severity
|
|
</span><br/>
|
|
<span class="covered" title="1 out of 1 forms covered">
|
|
178 :fault fault
|
|
</span><br/>
|
|
<span class="partial" title="7 out of 8 forms covered">
|
|
179 :narrative (or (get-message fault)
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
180 (do
|
|
</span><br/>
|
|
<span class="not-covered" title="0 out of 17 forms covered">
|
|
181 (warn "No narrative provided for fault token " fault)
|
|
</span><br/>
|
|
<span class="not-covered" title="0 out of 3 forms covered">
|
|
182 (str fault)))))
|
|
</span><br/>
|
|
<span class="blank" title="0 out of 0 forms covered">
|
|
183
|
|
</span><br/>
|
|
<span class="covered" title="58 out of 58 forms covered">
|
|
184 (defmacro nil-if-empty
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
185 "if `x` is an empty collection, return `nil`; else return `x`."
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
186 [x]
|
|
</span><br/>
|
|
<span class="covered" title="2 out of 2 forms covered">
|
|
187 `(if (and (coll? ~x) (empty? ~x)) nil
|
|
</span><br/>
|
|
<span class="covered" title="1 out of 1 forms covered">
|
|
188 ~x))
|
|
</span><br/>
|
|
<span class="blank" title="0 out of 0 forms covered">
|
|
189
|
|
</span><br/>
|
|
<span class="covered" title="1 out of 1 forms covered">
|
|
190 (defn concat-non-empty
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
191 "Quick function to replace the pattern (nil-if-empty (remove nil? (concat ...)))
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
192 which I'm using a lot!"
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
193 [& lists]
|
|
</span><br/>
|
|
<span class="partial" title="28 out of 29 forms covered">
|
|
194 (nil-if-empty (remove nil? (apply concat lists))))
|
|
</span><br/>
|
|
<span class="blank" title="0 out of 0 forms covered">
|
|
195
|
|
</span><br/>
|
|
<span class="covered" title="1 out of 1 forms covered">
|
|
196 (defn has-type-or-fault
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
197 "If object `x` has a `:type` value which is `acceptable`, return `nil`;
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
198 else return a fault object with this `severity` and `token`.
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
199
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
200 `acceptable` may be passed as either nil, a string, or a set of strings.
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
201 If `acceptable` is `nil`, no type specific tests will be performed."
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
202 [x acceptable severity token]
|
|
</span><br/>
|
|
<span class="covered" title="3 out of 3 forms covered">
|
|
203 (when acceptable
|
|
</span><br/>
|
|
<span class="covered" title="4 out of 4 forms covered">
|
|
204 (let [tv (:type x)]
|
|
</span><br/>
|
|
<span class="covered" title="3 out of 3 forms covered">
|
|
205 (when-not
|
|
</span><br/>
|
|
<span class="partial" title="1 out of 6 forms covered">
|
|
206 (cond
|
|
</span><br/>
|
|
<span class="partial" title="12 out of 13 forms covered">
|
|
207 (and (string? tv) (string? acceptable)) (= tv acceptable)
|
|
</span><br/>
|
|
<span class="not-covered" title="0 out of 13 forms covered">
|
|
208 (and (string? tv) (set? acceptable)) (acceptable tv)
|
|
</span><br/>
|
|
<span class="not-covered" title="0 out of 15 forms covered">
|
|
209 (and (coll? tv) (string? acceptable)) ((set tv) acceptable)
|
|
</span><br/>
|
|
<span class="not-covered" title="0 out of 12 forms covered">
|
|
210 (and (coll? tv) (set? acceptable)) (not-empty
|
|
</span><br/>
|
|
<span class="not-covered" title="0 out of 6 forms covered">
|
|
211 (intersection (set tv) acceptable))
|
|
</span><br/>
|
|
<span class="not-covered" title="0 out of 2 forms covered">
|
|
212 (not
|
|
</span><br/>
|
|
<span class="not-covered" title="0 out of 8 forms covered">
|
|
213 (or (string? acceptable)
|
|
</span><br/>
|
|
<span class="not-covered" title="0 out of 3 forms covered">
|
|
214 (set? acceptable))) (throw
|
|
</span><br/>
|
|
<span class="not-covered" title="0 out of 3 forms covered">
|
|
215 (ex-info
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
216 "`acceptable` argument not as expected."
|
|
</span><br/>
|
|
<span class="not-covered" title="0 out of 8 forms covered">
|
|
217 {:arguments {:x x
|
|
</span><br/>
|
|
<span class="not-covered" title="0 out of 1 forms covered">
|
|
218 :acceptable acceptable
|
|
</span><br/>
|
|
<span class="not-covered" title="0 out of 1 forms covered">
|
|
219 :severity severity
|
|
</span><br/>
|
|
<span class="not-covered" title="0 out of 1 forms covered">
|
|
220 :token token}})))
|
|
</span><br/>
|
|
<span class="covered" title="4 out of 4 forms covered">
|
|
221 (make-fault-object severity token)))))
|
|
</span><br/>
|
|
<span class="blank" title="0 out of 0 forms covered">
|
|
222
|
|
</span><br/>
|
|
<span class="covered" title="1 out of 1 forms covered">
|
|
223 (defn any-or-faults
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
224 "Return `nil` if validating one of these options returns `nil`; otherwise
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
225 return a list comprising a fault report object with this `severity-if-none`
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
226 and this token followed by all the fault reports from validating each
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
227 option.
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
228
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
229 There are several places - but especially in validating collections - where
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
230 there are several different valid configurations, but few or no properties
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
231 are always required."
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
232 [options severity-if-none token]
|
|
</span><br/>
|
|
<span class="covered" title="5 out of 5 forms covered">
|
|
233 (let [faults (filter empty? options)]
|
|
</span><br/>
|
|
<span class="covered" title="5 out of 5 forms covered">
|
|
234 (when (empty? faults)
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
235 ;; i.e. there was at least one option that returned no faults...
|
|
</span><br/>
|
|
<span class="covered" title="7 out of 7 forms covered">
|
|
236 (cons (make-fault-object severity-if-none token) faults))))
|
|
</span><br/>
|
|
<span class="blank" title="0 out of 0 forms covered">
|
|
237
|
|
</span><br/>
|
|
<span class="covered" title="1 out of 1 forms covered">
|
|
238 (defn cond-make-fault-object
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
239 "If `v` is `false` or `nil`, return a fault object with this `severity` and `token`,
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
240 else return nil."
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
241 [v severity token]
|
|
</span><br/>
|
|
<span class="covered" title="8 out of 8 forms covered">
|
|
242 (when-not v (make-fault-object severity token)))
|
|
</span><br/>
|
|
<span class="blank" title="0 out of 0 forms covered">
|
|
243
|
|
</span><br/>
|
|
<span class="covered" title="1 out of 1 forms covered">
|
|
244 (defn string-or-fault
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
245 "If this `value` is not a string, return a fault object with this `severity`
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
246 and `token`, else `nil`. If `pattern` is also passed, it is expected to be
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
247 a Regex, and the fault object will be returned unless `value` matches the
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
248 `pattern`."
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
249 ([value severity token]
|
|
</span><br/>
|
|
<span class="not-covered" title="0 out of 10 forms covered">
|
|
250 (when-not (string? value) (make-fault-object severity token)))
|
|
</span><br/>
|
|
<span class="not-tracked" title="0 out of 0 forms covered">
|
|
251 ([value severity token pattern]
|
|
</span><br/>
|
|
<span class="not-covered" title="0 out of 14 forms covered">
|
|
252 (when not (and (string? value) (re-matches pattern value))
|
|
</span><br/>
|
|
<span class="not-covered" title="0 out of 4 forms covered">
|
|
253 (make-fault-object severity token))))
|
|
</span><br/>
|
|
</body>
|
|
</html>
|