 (defn indexes-of [v xs]
   (set (keep-indexed (fn [i x] (when (= x v) i)) xs)))
 
-(defn filled-measurements [measurements]
+(defn measurements->columns [ms]
+  (map (fn [[{:keys [timestamp value]} & more]] (apply vector timestamp value (map :value more))) ms))
+
+(defn filled-measurements [measurements out]
   (let [sentinel         (Object.)
         is-sentinel?     #(identical? % sentinel)
         next-or-sentinel #(if-let [n (next %)] n [sentinel])

                                                       (hash-map :timestamp row-timestamp :value nil))) row)
                fns            (map-indexed (fn [i _] (if (has-data? i) next-or-sentinel identity)) row)
                step           (fn [xs] (map (fn [f v] (f v)) fns xs))]
            (recur (step ms) (concat data [out-row]))))))))

(defn measurements->columns [ms]
  (map (fn [[x & more]] (apply vector (:timestamp x) (:value x) (map :value more))) ms))

(defn generate-file [store item]
  (let [{:keys [header data]} item

    (try
      (with-open [out (io/writer tmpfile)]
        (csv/write-csv out header)
        (filled-measurements data out))
      (s3/store-file (:s3 store) (-> item
                                     (assoc :dir      (.getParent tmpfile)
                                            :filename (.getName tmpfile))
