|
6 | 6 | [cljs.analyzer.api :as ana]
|
7 | 7 | [cljs.closure]
|
8 | 8 | [cljs.env]
|
9 |
| - [clojure.string :as str])) |
| 9 | + [clojure.string :as str] |
| 10 | + [codox.utils :as util])) |
10 | 11 |
|
11 | 12 | (defn- cljs-filename? [filename]
|
12 | 13 | (or (.endsWith filename ".cljs")
|
|
51 | 52 | (multimethod? opts) :multimethod
|
52 | 53 | :else :var))
|
53 | 54 |
|
54 |
| -(defn- read-var [file vars var] |
55 |
| - (let [vt (var-type var)] |
| 55 | +(defn- read-var [source-path file vars var] |
| 56 | + (let [vt (var-type var) |
| 57 | + normalize (partial util/normalize-to-source-path source-path)] |
56 | 58 | (-> var
|
57 |
| - (select-keys [:name :line :arglists :doc :dynamic :added :deprecated :doc/format]) |
| 59 | + (select-keys [:name :file :line :arglists :doc :dynamic :added :deprecated :doc/format]) |
58 | 60 | (update-some :name (comp symbol name))
|
59 | 61 | (update-some :arglists remove-quote)
|
60 | 62 | (update-some :doc correct-indent)
|
61 |
| - (assoc-some :file (if (= vt :macro) (:file var) (.getPath file)) |
62 |
| - :type vt |
63 |
| - :members (map (partial read-var file vars) |
64 |
| - (protocol-methods var vars)))))) |
65 |
| - |
66 |
| -(defn- read-publics [state namespace file] |
67 |
| - (let [vars (vals (ana/ns-publics state namespace))] |
| 63 | + (update-some :file normalize) |
| 64 | + (assoc-some :type vt |
| 65 | + :members (->> (protocol-methods var vars) |
| 66 | + (map (partial read-var source-path file vars)) |
| 67 | + (map util/remove-empties) |
| 68 | + (map #(dissoc % :file :line)) |
| 69 | + (sort-by :name))) |
| 70 | + util/remove-empties))) |
| 71 | + |
| 72 | +(defn- unreferenced-protocol-fn? |
| 73 | + "Tools like potemkin import-vars can create a new function in one namespace point to an existing function within a protocol. |
| 74 | + In these cases, we want to include the new function." |
| 75 | + [source-path actual-file vars] |
| 76 | + (let [meta-file (util/normalize-to-source-path source-path (:file vars)) |
| 77 | + actual-file (util/normalize-to-source-path source-path (str actual-file))] |
| 78 | + (and (:protocol vars) (= meta-file actual-file)))) |
| 79 | + |
| 80 | +(defn- read-publics [state namespace source-path file] |
| 81 | + (let [vars (vals (ana/ns-publics state namespace)) |
| 82 | + unreferenced-protocol? (partial unreferenced-protocol-fn? source-path file)] |
68 | 83 | (->> vars
|
69 |
| - (remove :protocol) |
70 | 84 | (remove :anonymous)
|
| 85 | + (remove unreferenced-protocol?) |
71 | 86 | (remove no-doc?)
|
72 |
| - (map (partial read-var file vars)) |
| 87 | + (map (partial read-var source-path file vars)) |
73 | 88 | (sort-by (comp str/lower-case :name)))))
|
74 | 89 |
|
75 | 90 | (defn- analyze-file [file]
|
|
80 | 95 | (ana/analyze-file state file opts))
|
81 | 96 | state))
|
82 | 97 |
|
83 |
| -(defn- read-file [path file exception-handler] |
| 98 | +(defn- read-file [source-path file exception-handler] |
84 | 99 | (try
|
85 |
| - (let [source (io/file path file) |
| 100 | + |
| 101 | + (let [source (io/file source-path file) |
86 | 102 | ns-name (:ns (ana/parse-ns source))
|
87 | 103 | state (analyze-file source)]
|
88 | 104 | {ns-name
|
89 | 105 | (-> (ana/find-ns state ns-name)
|
90 | 106 | (select-keys [:name :doc])
|
91 | 107 | (update-some :doc correct-indent)
|
92 | 108 | (merge (-> ns-name meta (select-keys [:no-doc])))
|
93 |
| - (assoc :publics (read-publics state ns-name file)))}) |
| 109 | + (util/remove-empties) |
| 110 | + (assoc :publics (read-publics state ns-name source-path file)))}) |
94 | 111 | (catch Exception e
|
95 | 112 | (exception-handler e file))))
|
96 | 113 |
|
|
129 | 146 | ([paths {:keys [exception-handler]
|
130 | 147 | :or {exception-handler default-exception-handler}}]
|
131 | 148 | (mapcat (fn [path]
|
132 |
| - (let [path (io/file path) |
| 149 | + (let [path (io/file (util/canonical-path path)) |
133 | 150 | file-reader #(read-file path % exception-handler)]
|
134 | 151 | (->> (find-files path)
|
135 | 152 | (map file-reader)
|
|
0 commit comments