ipkn / crow

Crow is very fast and easy to use C++ micro web framework (inspired by Python Flask)
BSD 3-Clause "New" or "Revised" License
7.46k stars 889 forks source link

Getting static pictures #375

Closed ezamosch closed 4 years ago

ezamosch commented 4 years ago

Hello.

I am trying Crow and had a problem of transfer static pictures from server to client(browser).

My program looks like:

void sendFile(crow::response& res, std::string filename, std::string contentType) {
    std::string ROOT_DIR = "publics/";
    std::string filename_path = ROOT_DIR.append(filename);
    std::ifstream InputContent;
    InputContent.open(filename_path, std::ifstream::in);
    InputContent.exceptions(std::ifstream::failbit | std::ifstream::badbit);
    std::ostringstream stringStream;
    stringStream << InputContent.rdbuf();
    InputContent.close();
    res.add_header("Content-Type", contentType);
    res.write(stringStream.str());
    res.end();
}
void sendHtml(crow::response& res, std::string filename) {
    sendFile(res, filename.append(".html"), "text/html");
}

void sendScript(crow::response& res, std::string filename) {
    std::string path = "js/" + filename;
    sendFile(res, path, "text/script");
}

void sendImage(crow::response& res, std::string filename) {
    std::string path = "images/" + filename;
    sendFile(res, path, "image/jpeg");
}

void sendStyle(crow::response& res, std::string filename) {
    std::string path = "css/" + filename;
    sendFile(res, path, "text/css");
}
int main()
{
    crow::SimpleApp app;

    CROW_ROUTE(app, "/")([](const crow::request& req, crow::response& res) {       
        sendHtml(res, "index");
        });

    CROW_ROUTE(app, "/js/<string>")([](const crow::request& req, crow::response& res, std::string filename) {
        sendScript(res, filename);
        });

    CROW_ROUTE(app, "/css/<string>")([](const crow::request& req, crow::response& res, std::string filename) {
        sendStyle(res, filename);
        });
    CROW_ROUTE(app, "/images/<string>")([](const crow::request& req, crow::response& res, std::string filename) {
        sendImage(res, filename);
        });
    app.port(18080).multithreaded().run();
}

But on client (in browser) I got empty pictures. Can you help me with this issuee?

mrozigor commented 4 years ago

What browser's 'Inspector' shows? Maybe this will help: https://github.com/mrozigor/mrozigor.net/blob/master/src/controllers/ResourcesController.cpp

ezamosch commented 4 years ago

Solution is here:

void sendFile(crow::response& res, std::string filename, std::string contentType) {

    std::string ROOT_DIR = "publics/";
    std::string filename_path = ROOT_DIR.append(filename);

    if (contentType == "images/jpeg") { //pictures

        std::ifstream fileContent(filename_path, std::ios::binary);
        if (fileContent.is_open()) {

            res.add_header("Content-Type", contentType);
            res.write(std::string(std::istreambuf_iterator<char>(fileContent), std::istreambuf_iterator<char>()));
        }
        else {

            std::cerr << "Content not found..." << std::endl;
            res.code = 404;
            res.write("Content not found...");
        }
    }
    else { //other stuff

        std::string ROOT_DIR = "publics/";
        std::string filename_path = ROOT_DIR.append(filename);

        try {

            std::ifstream InputContent;
            InputContent.open(filename_path, std::ifstream::in);
            InputContent.exceptions(std::ifstream::failbit | std::ifstream::badbit);

            std::ostringstream stringStream;
            stringStream << InputContent.rdbuf();
            InputContent.close();

            res.add_header("Content-Type", contentType);
            res.write(stringStream.str());
        }
        catch (const std::exception& e) {

            std::cerr << e.what() << std::endl;
            res.code = 404;
            res.write("Content not found...");
        }
    }

    res.end();
}