Multipart

Browsers send multipart/form-data when a form contains file inputs. Garvan parses these requests through crow::multipart::message.

Reading multipart

CROW_ROUTE(app, "/upload")
    .methods("POST"_method)
([](const crow::request &req) {
    crow::multipart::message msg(req);
    for (const auto &part : msg.parts) {
        const std::string &name = part.headers.at("Content-Disposition").params.at("name");
        CROW_LOG_INFO << name << " = " << part.body.substr(0, 64);
    }
    return crow::response(200, "received");
});

File uploads

The body of each part contains raw bytes; write it out to disk:

if (part.headers.at("Content-Disposition").params.count("filename")) {
    std::ofstream out("/tmp/" + part.headers.at("Content-Disposition").params.at("filename"),
                      std::ios::binary);
    out << part.body;
}
Warning

Never trust the client-supplied filename. Strip path separators and validate against an allow-list before writing to disk.