Les dates en paramètres des requêtes

Hello à tous !

Ça y est, je commence mon (mini-)projet perso Vapor. Pour simplifier le contexte, j’ai des enregistrements datés.

Dans mon modèle j’ai donc un champ :

@Field(key: "date")
var date: Date

Défini ainsi dans ma structure de migration :

.field("date", .datetime, .required)

Tout est parfait quand je reçois mon JSON j’ai bien mon champ formaté en ISO8601, la vie est belle, tout roule comme prévu :

"date":"2020-08-20T13:17:51Z"

C’est là que les choses se gâtent… J’aimerais pouvoir lister mes enregistrements entre deux dates données.

N’étant pas un pro mais ayant quelques notions en REST je décide en accord avec moi-même de passer ces infos en paramètres :

/count-records?start=2020-08-18T12:00:00Z&end=2020-08-20T17:00:00Z

Et c’est là que le bât blesse… D’après ce que j’ai vu de la doc de Vapor, on doit pouvoir faire ceci, à partir d’une requête req :

req.query[Date.self, at: "start"]

Pour récupérer le paramètre start de type Date. Ça doit renvoyer nil s’il n’existe pas ou s’il n’arrive pas à décoder.

Et là, c’est le drame… Il me renvoie toujours nil que le paramètre soit présent ou non. J’ai bien vérifié que ça fonctionnait en changeant le type pour récupérer la chaîne de caractère :

req.query[String.self, at: "start"]

Mais je n’ai que faire d’un String – phrase à ne pas sortir de son contexte, merci. – Alors voilà… Que fais-je mal ?

Merci de vos lumières !

PS : En attendant, j’ai créé une structure décodable qui me permet de faire le job, je partage si ça intéresse :

struct DateParameter : Decodable {
    let date : Date?
    
    init(from decoder: Decoder) throws {
        let container = try decoder.singleValueContainer()
        let string = try container.decode(String.self)
        
        date = Self.formatter.date(from: string)
    }
    
    static let formatter = ISO8601DateFormatter()
}

Ensuite, on a juste à faire ceci :

req.query[DateParameter.self, at: "start"]?.date

Ca ressemble à un bug ou une limitation dans la fonction query de Vapor, tu as essayé de demander sur leur Discord ?
Autre idée : pour tester tes requêtes, suivant le logiciel que tu utilises, vérifies que l’encodage est correct sur ton paramètre d’URL, si ça se trouve la date arrive avec des caractères mal encodés et c’est pour ça que la fonction query ne parvient pas à parser la date

1 « J'aime »

Je n’ai pas vu avec eux effectivement, par contre l’encodage n’est pas en question, les tests ont été réalisés avec Paw (encore merci pour cette découverte) en direct donc peu de risques de ce côté, et la chaîne récupérée était correctement encodée, car je récupère bien une date à partir du formateur.

Je vais essayer de créer une issue sur leur GitHub, pour voir.

Voilà, c’est fait : https://github.com/vapor/vapor/issues/2481