Hacktoberfest 2026: los issues que los mantenedores marcaron para octubre, abiertos y aptos para principiantes. Explorar issues de Hacktoberfest

Spec form metadata is lost on visiting it during Swagger UI generation

Abierto
#417 1 comentario 0 reacciones 0 asignados Ver en GitHub

Nadie ha tomado este issue todavía.

Evaluación

Dificultad
4/5
Tiempo estimado
3-5 días
Aptitud para principiantes
45/100
Tipo de issue
Error
Claridad
Bastante claro
Estado de actividad
Estancado
Stack tecnológico
clojure
Área
api

Línea de trabajo

Empieza por spec-tools.visitor/visit y spec-tools.impl/extract-form; después, ejecuta la reproducción proporcionada contra la ruta de generación de Swagger UI para specs personalizadas en :return y :body. Compara los metadatos del formulario extraído con el caso funcional de s/coll-of; la tarea está terminada cuando los metadatos esperados siguen disponibles para el visitor personalizado.

Escrito por el modelo de indexación a partir del texto del issue.

Descripción

Library Version(s)

2.0.0-alpha29

Problem

I need to redefine spec-tools.visitor/visit for my custom spec to change how spec is shown in Swagger UI. E.g. I have closed-keys custom spec, but want to visit it as s/keys, so that Swagger UI generates appropriate model examples from my spec.

Now, it can be cumbersome to parse the custom spec form to implement its visiting. So I want instead to rely on the metadata attached to the spec form (such easy to use metadata can be conveniently generated by closed-keys macro). I.e.:

(defmethod st-visitor/visit-spec `closed-keys
  [spec accept options]
  (let [form (st-impl/extract-form spec)
        keys-form <generate from (meta form)>]
   (st-visitor/visit-spec keys-form accept options)))

But this currently doesn't work because (meta form) is always nil in this function.

I only managed to trace it back to spec-tools.visitor/visit function: it seems to get already crooked spec with no metadata in its form.

The issue is reproducible for custom specs used in :return and :body. I didn't test other places.

Steps:

  1. Code:
(ns app.foo.handler
  (:require [compojure.api.sweet :as c]
            [ring.util.http-response :as r]
            [clojure.spec.alpha :as s]
            [spec-tools.visitor :as st-visitor]
            [spec-tools.impl :as st-impl]))

; Helper to redefine spec form
(defn -with-form
  [spec form]
  {:pre [(s/spec? spec)]}
  (reify s/Spec
    (describe* [_] form)

    ; Do not modify other methods
    (conform* [_ x] (s/conform* spec x))
    (unform* [_ y] (s/unform* spec y))
    (explain* [_ path via in x] (s/explain* spec path via in x))
    (gen* [_ overrides path rmap] (s/gen* spec overrides path rmap))
    (with-gen* [_ gfn] (s/with-gen* spec gfn))))

; Create spec with a custom form and metadata attached to the form
(s/def ::my-spec (-> (s/spec int?)
                     (-with-form
                       (with-meta (list 'my-spec 1 2 3) {:my-spec-form-meta [1 2 3]}))))

; Custom visiting which relies on metadata from the form
(defmethod st-visitor/visit-spec 'my-spec
  [spec _accept _options]
  (let [form (st-impl/extract-form spec)]
    (prn :VISITED-FORM form :META (meta form))
    nil))

; Handler code
(c/context "/my" []
    (c/POST "/foo" []
      :return ::my-spec
      ;:body [x ::my-spec]
      (r/ok)))
  1. Run it and navigate to Swagger UI URL.
  2. Check console output.

Expected:

:VISITED-FORM (my-spec 1 2 3) :META {:my-spec-form-meta [1 2 3]}

Actual:

:VISITED-FORM (my-spec 1 2 3) :META nil

Workaround:

My current workaround is to attach metadata to the first symbol in the form instead of the whole form. Also in another case I just parse the form instead of relying on its metadata.

Interestingly, the issue is not reproducible when custom spec is "wrapped" by some other spec, specifically (s/coll-of ::my-spec) doesn't seem to have a problem.

Lenguaje dominante
Clojure
Estrellas
1.1k
Forks
145
Métricas de merge de PR
Sin PR fusionados en 30 d

Preparar el entorno

Primeros pasos

  1. Lee el issue completo y luego la guía de contribución del proyecto.
  2. Comenta en el issue que vas a ocuparte — evita que dos personas hagan lo mismo.
  3. Haz un fork del repositorio y trabaja en una rama.
  4. Abre un pull request que haga referencia al número del issue.

Más de metosin/compojure-api

Todos los issues de metosin/compojure-api

Issues similares

Más issues de Clojure

Recibe los nuevos issues en tu correo

Un resumen breve de issues de GitHub para principiantes.