Skip to content

Error in Swagger UI when the path Parameter is not String #1227

@darixsamani

Description

@darixsamani

Describe the bug
In this issue, I want to report an issue when I execute the request in Swagger UI when the path parameter is not a string

To Reproduce
Here is a small part of my code to reproduce the error:

routes/posts.rs file

use salvo::prelude::*;
use salvo_oapi::{endpoint, extract::PathParam};


#[endpoint(tags("Posts"), summary = "get all posts", description = "the objective of this endpoint is to retreive all posts")]
fn get_all_posts(res: &mut Response){
    res.render("get all posts")
}

#[endpoint(tags("Posts"), summary = "create posts", description = " the objective of this endpoint is to create a post")]
fn create_posts(res: &mut Response){
    res.render("create posts")
}

#[endpoint(tags("Posts"), summary = "update posts", description = "update a specific post by id")]
fn update_posts(id: PathParam<i32>, res: &mut Response, _req: &mut Request){
    println!("update posts");
    res.render(format!("update posts with id {}", id.into_inner()));
}

#[endpoint(tags("Posts"), summary = "delete posts", description = "delete a specific post by id")]
fn  delete_posts(id: PathParam<i32>, res: &mut Response, _req: &mut Request){
    println!("delete posts");
    res.render(format!("delete posts with id {}", id.into_inner()));
}

#[endpoint(tags("Posts"), summary = "get posts information", description = "get a specific post by id")]
fn get_posts_information(id: PathParam<i32>, res: &mut Response, _req: &mut Request){
    println!("get information posts");
    res.render(format!("get posts with id {}", id.into_inner()));
}

pub fn get_posts_router() -> Router {

    let posts_router = Router::with_path("/posts")
        .get(get_all_posts)
        .post(create_posts)
        .push(
            Router::with_path("{id:num}")
            .get(get_posts_information)
            .put(update_posts)
            .delete(delete_posts)
        );
    posts_router
}

routes/users.rs file

use salvo::prelude::*;
use salvo_oapi::endpoint;


#[endpoint(tags("Users"), summary = "get all users", description = "the objective of this endpoint is to retreive all the users in database")]
fn get_all_users(res: &mut Response){
    res.render("get all users")
}

#[endpoint(tags("Users"), summary = "create users", description = "the objective of this endpoint is to create the new users")]
fn create_users(res: &mut Response){
    res.render("create users")

}



pub fn get_users_router() -> Router {
    let users_router = Router::with_path("users")
        .get(get_all_users)
        .post(create_users);
    users_router    
}

main.rs file

use salvo::prelude::*;
use salvo_oapi::OpenApi;
use salvo_oapi::extract::QueryParam;
use salvo_oapi::endpoint;
use crate::routes::users::get_users_router;
use crate::routes::posts::get_posts_router;


pub mod database;
pub mod models;
pub mod schemas;
pub mod routes;



#[endpoint(tags("main"), summary = "hello", description = "description  of the  main endpoint")]
async fn hello(name: QueryParam<String, false>, res: &mut Response){
    println!("{:?}", name);
    res.render(format!("Hello, {}!", name.clone().unwrap()))
}

#[endpoint(tags("Hello"), summary="Just Print hello world", description= "description of the handle/endpoint to print hello world")]
async fn hello_world() -> Result<&'static str, salvo::Error>{
    Ok("Hello world")
}

#[tokio::main]
async fn main() {
    

    tracing_subscriber::fmt().init();

    let router = Router::new().get(hello_world)
        .push(Router::with_path("hello").get(hello))
        .push(get_users_router())
        .push(get_posts_router());

    let doc = OpenApi::new("Salvo Postgresql Boilerplate", "0.0.1").merge_router(&router);

    let router = router
        .unshift(doc.into_router("/api-doc/openapi.json"))
        .unshift(SwaggerUi::new("/api-doc/openapi.json").into_router("/docs"));

    let acceptor = TcpListener::new("0.0.0.0:5800").bind().await;
    
    Server::new(acceptor).serve(router).await;
}

When I request with this path: http://0.0.0.0:5800/posts/{id: num} in the post in Swagger for example http://0.0.0.0:5800/posts/12 in post i got this error

404 Undocumented Error: Not Found

<!DOCTYPE html>
<html>
<head>
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width">
    <title>404: Not Found</title>
    <style>
    :root {
        --bg-color: #fff;
        --text-color: #222;
    }
    body {
        background: var(--bg-color);
        color: var(--text-color);
        text-align: center;
    }
    pre { text-align: left; padding: 0 1rem; }
    footer{text-align:center;}
    @media (prefers-color-scheme: dark) {
        :root {
            --bg-color: #222;
            --text-color: #ddd;
        }
        a:link { color: red; }
        a:visited { color: #a8aeff; }
        a:hover {color: #a8aeff;}
        a:active {color: #a8aeff;}
    }
    </style>
</head>
<body>
    <div><h1>404: Not Found</h1><h3>The requested resource could not be found.</h3><hr><footer><a href="https://salvo.rs" target="_blank">salvo</a></footer></div>
</body>
</html>

Expected behavior
The code works well outside the Swagger UI, for example, in Postman, but I got the error in the Swagger UI when the path parameter is not a String

Screenshots
Here is the image of the error in Swagger UI

Image Image

Desktop (please complete the following information):

  • OS: [linus(debians)]
  • Browser [chrome]
  • Version [12]

Additional context
I repeat again, all endpoints work well outside the Swagger UI The issue is that in Swagger UI, I got the error when the path parameter is not a string, for example, when the path parameter is num or with a regex /d+

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions