Skip to content

Commit 0d2b6b3

Browse files
authored
Merge pull request #1030 from kiwix/cleanup_of_error_response_generation
2 parents f8aae39 + 5f27b4b commit 0d2b6b3

File tree

10 files changed

+137
-218
lines changed

10 files changed

+137
-218
lines changed

src/server/i18n.h

+6
Original file line numberDiff line numberDiff line change
@@ -111,6 +111,12 @@ struct ParameterizedMessage
111111
const Parameters params;
112112
};
113113

114+
inline ParameterizedMessage nonParameterizedMessage(const std::string& msgId)
115+
{
116+
const ParameterizedMessage::Parameters noParams;
117+
return ParameterizedMessage(msgId, noParams);
118+
}
119+
114120
struct LangPreference
115121
{
116122
const std::string lang;

src/server/internalServer.cpp

+41-73
Original file line numberDiff line numberDiff line change
@@ -190,12 +190,6 @@ ParameterizedMessage tooManyBooksMsg(size_t nbBooks, size_t limit)
190190
);
191191
}
192192

193-
ParameterizedMessage nonParameterizedMessage(const std::string& msgId)
194-
{
195-
const ParameterizedMessage::Parameters noParams;
196-
return ParameterizedMessage(msgId, noParams);
197-
}
198-
199193
struct Error : public std::runtime_error {
200194
explicit Error(const ParameterizedMessage& message)
201195
: std::runtime_error("Error while handling request"),
@@ -564,7 +558,7 @@ MHD_Result InternalServer::handlerCallback(struct MHD_Connection* connection,
564558
response->set_etag_body(getLibraryId());
565559
}
566560

567-
auto ret = response->send(request, connection);
561+
auto ret = response->send(request, m_verbose.load(), connection);
568562
auto end_time = std::chrono::steady_clock::now();
569563
auto time_span = std::chrono::duration_cast<std::chrono::duration<double>>(end_time - start_time);
570564
if (m_verbose.load()) {
@@ -593,20 +587,19 @@ std::unique_ptr<Response> InternalServer::handle_request(const RequestContext& r
593587
{
594588
try {
595589
if (! request.is_valid_url()) {
596-
return HTTP404Response(*this, request)
597-
+ urlNotFoundMsg;
590+
return UrlNotFoundResponse(request);
598591
}
599592

600593
if ( request.get_url() == "" ) {
601594
// Redirect /ROOT_LOCATION to /ROOT_LOCATION/ (note the added slash)
602595
// so that relative URLs are resolved correctly
603596
const std::string query = getSearchComponent(request);
604-
return Response::build_redirect(*this, m_root + "/" + query);
597+
return Response::build_redirect(m_root + "/" + query);
605598
}
606599

607600
const ETag etag = get_matching_if_none_match_etag(request, getLibraryId());
608601
if ( etag )
609-
return Response::build_304(*this, etag);
602+
return Response::build_304(etag);
610603

611604
const auto url = request.get_url();
612605
if ( isLocallyCustomizedResource(url) )
@@ -647,15 +640,15 @@ std::unique_ptr<Response> InternalServer::handle_request(const RequestContext& r
647640

648641
const std::string contentUrl = m_root + "/content" + urlEncode(url);
649642
const std::string query = getSearchComponent(request);
650-
return Response::build_redirect(*this, contentUrl + query);
643+
return Response::build_redirect(contentUrl + query);
651644
} catch (std::exception& e) {
652645
fprintf(stderr, "===== Unhandled error : %s\n", e.what());
653-
return HTTP500Response(*this, request)
654-
+ e.what();
646+
return HTTP500Response(request)
647+
+ ParameterizedMessage("non-translated-text", {{"MSG", e.what()}});
655648
} catch (...) {
656649
fprintf(stderr, "===== Unhandled unknown error\n");
657-
return HTTP500Response(*this, request)
658-
+ "Unknown error";
650+
return HTTP500Response(request)
651+
+ nonParameterizedMessage("unknown-error");
659652
}
660653
}
661654

@@ -668,7 +661,7 @@ MustacheData InternalServer::get_default_data() const
668661

669662
std::unique_ptr<Response> InternalServer::build_homepage(const RequestContext& request)
670663
{
671-
return ContentResponse::build(*this, m_indexTemplateString, get_default_data(), "text/html; charset=utf-8");
664+
return ContentResponse::build(m_indexTemplateString, get_default_data(), "text/html; charset=utf-8");
672665
}
673666

674667
/**
@@ -697,8 +690,7 @@ std::unique_ptr<Response> InternalServer::handle_suggest(const RequestContext& r
697690
}
698691

699692
if ( startsWith(request.get_url(), "/suggest/") ) {
700-
return HTTP404Response(*this, request)
701-
+ urlNotFoundMsg;
693+
return UrlNotFoundResponse(request);
702694
}
703695

704696
std::string bookName, bookId;
@@ -712,7 +704,7 @@ std::unique_ptr<Response> InternalServer::handle_suggest(const RequestContext& r
712704
}
713705

714706
if (archive == nullptr) {
715-
return HTTP404Response(*this, request)
707+
return HTTP404Response(request)
716708
+ noSuchBookErrorMsg(bookName);
717709
}
718710

@@ -747,7 +739,7 @@ std::unique_ptr<Response> InternalServer::handle_suggest(const RequestContext& r
747739
results.addFTSearchSuggestion(request.get_user_language(), queryString);
748740
}
749741

750-
return ContentResponse::build(*this, results.getJSON(), "application/json; charset=utf-8");
742+
return ContentResponse::build(results.getJSON(), "application/json; charset=utf-8");
751743
}
752744

753745
std::unique_ptr<Response> InternalServer::handle_viewer_settings(const RequestContext& request)
@@ -762,7 +754,7 @@ std::unique_ptr<Response> InternalServer::handle_viewer_settings(const RequestCo
762754
{"enable_library_button", m_withLibraryButton ? "true" : "false" },
763755
{"default_user_language", request.get_user_language() }
764756
};
765-
return ContentResponse::build(*this, RESOURCE::templates::viewer_settings_js, data, "application/javascript; charset=utf-8");
757+
return ContentResponse::build(RESOURCE::templates::viewer_settings_js, data, "application/javascript; charset=utf-8");
766758
}
767759

768760
std::string InternalServer::getNoJSDownloadPageHTML(const std::string& bookId, const std::string& userLang) const
@@ -817,19 +809,13 @@ std::unique_ptr<Response> InternalServer::handle_no_js(const RequestContext& req
817809
const auto bookId = mp_nameMapper->getIdForName(urlParts[2]);
818810
content = getNoJSDownloadPageHTML(bookId, userLang);
819811
} catch (const std::out_of_range&) {
820-
return HTTP404Response(*this, request)
821-
+ urlNotFoundMsg;
812+
return UrlNotFoundResponse(request);
822813
}
823814
} else {
824-
return HTTP404Response(*this, request)
825-
+ urlNotFoundMsg;
815+
return UrlNotFoundResponse(request);
826816
}
827817

828-
return ContentResponse::build(
829-
*this,
830-
content,
831-
"text/html; charset=utf-8"
832-
);
818+
return ContentResponse::build(content, "text/html; charset=utf-8");
833819
}
834820

835821
namespace
@@ -867,14 +853,12 @@ std::unique_ptr<Response> InternalServer::handle_skin(const RequestContext& requ
867853
try {
868854
const auto accessType = staticResourceAccessType(request, resourceCacheId);
869855
auto response = ContentResponse::build(
870-
*this,
871856
getResource(resourceName),
872857
getMimeTypeForFile(resourceName));
873858
response->set_kind(accessType);
874859
return std::move(response);
875860
} catch (const ResourceNotFound& e) {
876-
return HTTP404Response(*this, request)
877-
+ urlNotFoundMsg;
861+
return UrlNotFoundResponse(request);
878862
}
879863
}
880864

@@ -887,20 +871,17 @@ std::unique_ptr<Response> InternalServer::handle_search(const RequestContext& re
887871
if ( startsWith(request.get_url(), "/search/") ) {
888872
if (request.get_url() == "/search/searchdescription.xml") {
889873
return ContentResponse::build(
890-
*this,
891874
RESOURCE::ft_opensearchdescription_xml,
892875
get_default_data(),
893876
"application/opensearchdescription+xml");
894877
}
895-
return HTTP404Response(*this, request)
896-
+ urlNotFoundMsg;
878+
return UrlNotFoundResponse(request);
897879
}
898880

899881
try {
900882
return handle_search_request(request);
901883
} catch (const Error& e) {
902-
return HTTP400Response(*this, request)
903-
+ invalidUrlMsg
884+
return HTTP400Response(request)
904885
+ e.message();
905886
}
906887
}
@@ -942,7 +923,7 @@ std::unique_ptr<Response> InternalServer::handle_search_request(const RequestCon
942923
// Searcher->search will throw a runtime error if there is no valid xapian database to do the search.
943924
// (in case of zim file not containing a index)
944925
const auto cssUrl = renderUrl(m_root, RESOURCE::templates::url_of_search_results_css);
945-
HTTPErrorResponse response(*this, request, MHD_HTTP_NOT_FOUND,
926+
HTTPErrorResponse response(request, MHD_HTTP_NOT_FOUND,
946927
"fulltext-search-unavailable",
947928
"404-page-heading",
948929
cssUrl);
@@ -972,13 +953,11 @@ std::unique_ptr<Response> InternalServer::handle_search_request(const RequestCon
972953
renderer.setPageLength(pageLength);
973954
if (request.get_requested_format() == "xml") {
974955
return ContentResponse::build(
975-
*this,
976956
renderer.getXml(*mp_nameMapper, mp_library.get()),
977957
"application/rss+xml; charset=utf-8"
978958
);
979959
}
980960
auto response = ContentResponse::build(
981-
*this,
982961
renderer.getHtml(*mp_nameMapper, mp_library.get()),
983962
"text/html; charset=utf-8"
984963
);
@@ -1001,8 +980,7 @@ std::unique_ptr<Response> InternalServer::handle_random(const RequestContext& re
1001980
}
1002981

1003982
if ( startsWith(request.get_url(), "/random/") ) {
1004-
return HTTP404Response(*this, request)
1005-
+ urlNotFoundMsg;
983+
return UrlNotFoundResponse(request);
1006984
}
1007985

1008986
std::string bookName;
@@ -1016,15 +994,15 @@ std::unique_ptr<Response> InternalServer::handle_random(const RequestContext& re
1016994
}
1017995

1018996
if (archive == nullptr) {
1019-
return HTTP404Response(*this, request)
997+
return HTTP404Response(request)
1020998
+ noSuchBookErrorMsg(bookName);
1021999
}
10221000

10231001
try {
10241002
auto entry = archive->getRandomEntry();
10251003
return build_redirect(bookName, getFinalItem(*archive, entry));
10261004
} catch(zim::EntryNotFound& e) {
1027-
return HTTP404Response(*this, request)
1005+
return HTTP404Response(request)
10281006
+ nonParameterizedMessage("random-article-failure");
10291007
}
10301008
}
@@ -1037,13 +1015,12 @@ std::unique_ptr<Response> InternalServer::handle_captured_external(const Request
10371015
} catch (const std::out_of_range& e) {}
10381016

10391017
if (source.empty()) {
1040-
return HTTP404Response(*this, request)
1041-
+ urlNotFoundMsg;
1018+
return UrlNotFoundResponse(request);
10421019
}
10431020

10441021
auto data = get_default_data();
10451022
data.set("source", source);
1046-
return ContentResponse::build(*this, RESOURCE::templates::captured_external_html, data, "text/html; charset=utf-8");
1023+
return ContentResponse::build(RESOURCE::templates::captured_external_html, data, "text/html; charset=utf-8");
10471024
}
10481025

10491026
std::unique_ptr<Response> InternalServer::handle_catch(const RequestContext& request)
@@ -1056,8 +1033,7 @@ std::unique_ptr<Response> InternalServer::handle_catch(const RequestContext& req
10561033
return handle_captured_external(request);
10571034
}
10581035

1059-
return HTTP404Response(*this, request)
1060-
+ urlNotFoundMsg;
1036+
return UrlNotFoundResponse(request);
10611037
}
10621038

10631039
std::vector<std::string>
@@ -1117,7 +1093,7 @@ InternalServer::build_redirect(const std::string& bookName, const zim::Item& ite
11171093
{
11181094
const auto contentPath = "/content/" + bookName + "/" + item.getPath();
11191095
const auto url = m_root + kiwix::urlEncode(contentPath);
1120-
return Response::build_redirect(*this, url);
1096+
return Response::build_redirect(url);
11211097
}
11221098

11231099
std::unique_ptr<Response> InternalServer::handle_content(const RequestContext& request)
@@ -1141,15 +1117,14 @@ std::unique_ptr<Response> InternalServer::handle_content(const RequestContext& r
11411117

11421118
if (archive == nullptr) {
11431119
const std::string searchURL = m_root + "/search?pattern=" + kiwix::urlEncode(pattern);
1144-
return HTTP404Response(*this, request)
1145-
+ urlNotFoundMsg
1120+
return UrlNotFoundResponse(request)
11461121
+ suggestSearchMsg(searchURL, kiwix::urlDecode(pattern));
11471122
}
11481123

11491124
const std::string archiveUuid(archive->getUuid());
11501125
const ETag etag = get_matching_if_none_match_etag(request, archiveUuid);
11511126
if ( etag )
1152-
return Response::build_304(*this, etag);
1127+
return Response::build_304(etag);
11531128

11541129
auto urlStr = url.substr(prefixLength + bookName.size());
11551130
if (urlStr[0] == '/') {
@@ -1168,7 +1143,7 @@ std::unique_ptr<Response> InternalServer::handle_content(const RequestContext& r
11681143
// '-' namespaces, in which case that resource is returned instead.
11691144
return build_redirect(bookName, getFinalItem(*archive, entry));
11701145
}
1171-
auto response = ItemResponse::build(*this, request, entry.getItem());
1146+
auto response = ItemResponse::build(request, entry.getItem());
11721147
response->set_etag_body(archiveUuid);
11731148

11741149
if ( !startsWith(entry.getItem().getMimetype(), "application/pdf") ) {
@@ -1189,8 +1164,7 @@ std::unique_ptr<Response> InternalServer::handle_content(const RequestContext& r
11891164
printf("Failed to find %s\n", urlStr.c_str());
11901165

11911166
std::string searchURL = m_root + "/search?content=" + bookName + "&pattern=" + kiwix::urlEncode(pattern);
1192-
return HTTP404Response(*this, request)
1193-
+ urlNotFoundMsg
1167+
return UrlNotFoundResponse(request)
11941168
+ suggestSearchMsg(searchURL, kiwix::urlDecode(pattern));
11951169
}
11961170
}
@@ -1208,13 +1182,11 @@ std::unique_ptr<Response> InternalServer::handle_raw(const RequestContext& reque
12081182
bookName = request.get_url_part(1);
12091183
kind = request.get_url_part(2);
12101184
} catch (const std::out_of_range& e) {
1211-
return HTTP404Response(*this, request)
1212-
+ urlNotFoundMsg;
1185+
return UrlNotFoundResponse(request);
12131186
}
12141187

12151188
if (kind != "meta" && kind!= "content") {
1216-
return HTTP404Response(*this, request)
1217-
+ urlNotFoundMsg
1189+
return UrlNotFoundResponse(request)
12181190
+ invalidRawAccessMsg(kind);
12191191
}
12201192

@@ -1225,15 +1197,14 @@ std::unique_ptr<Response> InternalServer::handle_raw(const RequestContext& reque
12251197
} catch (const std::out_of_range& e) {}
12261198

12271199
if (archive == nullptr) {
1228-
return HTTP404Response(*this, request)
1229-
+ urlNotFoundMsg
1200+
return UrlNotFoundResponse(request)
12301201
+ noSuchBookErrorMsg(bookName);
12311202
}
12321203

12331204
const std::string archiveUuid(archive->getUuid());
12341205
const ETag etag = get_matching_if_none_match_etag(request, archiveUuid);
12351206
if ( etag )
1236-
return Response::build_304(*this, etag);
1207+
return Response::build_304(etag);
12371208

12381209
// Remove the beggining of the path:
12391210
// /raw/<bookName>/<kind>/foo
@@ -1244,24 +1215,23 @@ std::unique_ptr<Response> InternalServer::handle_raw(const RequestContext& reque
12441215
try {
12451216
if (kind == "meta") {
12461217
auto item = archive->getMetadataItem(itemPath);
1247-
auto response = ItemResponse::build(*this, request, item);
1218+
auto response = ItemResponse::build(request, item);
12481219
response->set_etag_body(archiveUuid);
12491220
return response;
12501221
} else {
12511222
auto entry = archive->getEntryByPath(itemPath);
12521223
if (entry.isRedirect()) {
12531224
return build_redirect(bookName, entry.getItem(true));
12541225
}
1255-
auto response = ItemResponse::build(*this, request, entry.getItem());
1226+
auto response = ItemResponse::build(request, entry.getItem());
12561227
response->set_etag_body(archiveUuid);
12571228
return response;
12581229
}
12591230
} catch (zim::EntryNotFound& e ) {
12601231
if (m_verbose.load()) {
12611232
printf("Failed to find %s\n", itemPath.c_str());
12621233
}
1263-
return HTTP404Response(*this, request)
1264-
+ urlNotFoundMsg
1234+
return UrlNotFoundResponse(request)
12651235
+ rawEntryNotFoundMsg(kind, itemPath);
12661236
}
12671237
}
@@ -1286,12 +1256,10 @@ std::unique_ptr<Response> InternalServer::handle_locally_customized_resource(con
12861256

12871257
auto byteRange = request.get_range().resolve(resourceData.size());
12881258
if (byteRange.kind() != ByteRange::RESOLVED_FULL_CONTENT) {
1289-
return Response::build_416(*this, resourceData.size());
1259+
return Response::build_416(resourceData.size());
12901260
}
12911261

1292-
return ContentResponse::build(*this,
1293-
resourceData,
1294-
crd.mimeType);
1262+
return ContentResponse::build(resourceData, crd.mimeType);
12951263
}
12961264

12971265
}

src/server/internalServer.h

-4
Original file line numberDiff line numberDiff line change
@@ -188,10 +188,6 @@ class InternalServer {
188188

189189
class CustomizedResources;
190190
std::unique_ptr<CustomizedResources> m_customizedResources;
191-
192-
friend std::unique_ptr<Response> Response::build(const InternalServer& server);
193-
friend std::unique_ptr<ContentResponse> ContentResponse::build(const InternalServer& server, const std::string& content, const std::string& mimetype);
194-
friend std::unique_ptr<Response> ItemResponse::build(const InternalServer& server, const RequestContext& request, const zim::Item& item);
195191
};
196192

197193
}

0 commit comments

Comments
 (0)