Joi 数组验证

Joi Array Validation

考虑这个代码片段。我想通过 1 种或多种颜色查询 'Markers'...

module.exports = [
    {
        method: 'GET',
        path: '/search/markers',
        options: {
            auth,
            description: 'Get Markers',
            notes: 'Returns all marker info',
            tags: ['api', 'markers'],
            validate: {
                query: {
                    color: Joi.array().items(Joi.string().valid('Red', 'Blue')).single().allow(''),
                }
            },
            response: {
                schema: MarkersValidation.getSearchMarkers
            }
        },
        handler: SearchController.searchMarkers
    }
];

exports.searchMarkers = async (request, h) => {
    try {
        const Markers = h.models().Markers;
        const queryMarkers = Markers.query()
            .select(h.knex().raw([
                'markers.color'
            ]))
            if (request.query.color) {
                queryMarkers.andWhere(h.knex().raw(`color && '{${request.query.color}}'::text[]`));
            }
        }
    }
    catch (e) {
        //error handler
    }
}

但是,当我尝试将颜色查询参数与 Red, Blue 一起应用时,我从 Postman 那里得到了以下错误。当我应用单一颜色参数时,例如:Red,它工作正常。

错误

child "color" fails because [single value of "color" fails because ["color" must be one of [Red, Blue]]]

URL

{{url}}/search/markers?color=Red, Blue

备注

我尝试删除 .single(),但是当我这样做时,出现了这个错误:

child "color" fails because ["color" must be an array]

问题

我该如何解决这个问题?

假设我想要一个可用颜色列表来查询:'Green'、'Purple'、'Yellow'、'Red'、'Blue'.

如何向查询添加 1 个或所有选项?

例子

{{url}}/search/markers?color=Red,

{{url}}/search/markers?color=Red, Blue, Yellow

这是我当前的代码,但显然行不通,有什么想法吗?

const myColors = ['Green', 'Purple', 'Yellow', 'Red', 'Blue'];

validate: {
 query: {
  color: Joi.array().items(Joi.string().valid(myColors)).single().allow(''),
 }
}

更新 - 简化

在此图中,我有一个带有“.valid()”的数组,但验证失败。

在此图中,我有一个没有“.valid()”的数组并且验证通过。

我的问题

如何向我的 Joi.array 添加“.valid()”或类似的东西,以便只有我设置的值对此查询有效?

您必须在 URL 中将颜色查询参数作为数组传递。

{{url}}/search/markers?color[]=Red&color[]=Blue

用于验证颜色数组的 joi 模式:

const myColors = ['Green', 'Purple', 'Yellow', 'Red', 'Blue'];

joi.object().keys({
  color: joi.array().items(myColors.map(col => col)),
});

const myColors = require('../data/colors');

const validateColors = (colors) => {
    if (!colors) {
        return true;
    }
    const colorsArray = colors.split(',');
    const colorsSchema = Joi.array().items(Joi.string().valid(myColors)).allow('')
    return Joi.validate(colorsArray, colorsSchema);
}

query: {colors: Joi.string().allow('')}