static void testWebContextSecurityFileXHR(WebViewTest* test, gconstpointer) { GUniquePtr<char> fileURL(g_strdup_printf("file://%s/simple.html", Test::getResourcesDir(Test::WebKit2Resources).data())); test->loadURI(fileURL.get()); test->waitUntilLoadFinished(); GUniquePtr<char> jsonURL(g_strdup_printf("file://%s/simple.json", Test::getResourcesDir().data())); GUniquePtr<char> xhr(g_strdup_printf("var xhr = new XMLHttpRequest; xhr.open(\"GET\", \"%s\"); xhr.send();", jsonURL.get())); // By default file access is not allowed, this will fail with a cross-origin error. GUniqueOutPtr<GError> error; WebKitJavascriptResult* javascriptResult = test->runJavaScriptAndWaitUntilFinished(xhr.get(), &error.outPtr()); g_assert(!javascriptResult); g_assert_error(error.get(), WEBKIT_JAVASCRIPT_ERROR, WEBKIT_JAVASCRIPT_ERROR_SCRIPT_FAILED); // Allow file access from file URLs. webkit_settings_set_allow_file_access_from_file_urls(webkit_web_view_get_settings(test->m_webView), TRUE); test->loadURI(fileURL.get()); test->waitUntilLoadFinished(); javascriptResult = test->runJavaScriptAndWaitUntilFinished(xhr.get(), &error.outPtr()); g_assert(javascriptResult); g_assert(!error); // It isn't still possible to load file from an HTTP URL. test->loadURI(kServer->getURIForPath("/").data()); test->waitUntilLoadFinished(); javascriptResult = test->runJavaScriptAndWaitUntilFinished(xhr.get(), &error.outPtr()); g_assert(!javascriptResult); g_assert_error(error.get(), WEBKIT_JAVASCRIPT_ERROR, WEBKIT_JAVASCRIPT_ERROR_SCRIPT_FAILED); webkit_settings_set_allow_file_access_from_file_urls(webkit_web_view_get_settings(test->m_webView), FALSE); }
void SpriteStore::setURL(const std::string& url) { if (url.empty()) { // Treat a non-existent sprite as a successfully loaded empty sprite. loaded = true; return; } std::string spriteURL(url + (pixelRatio > 1 ? "@2x" : "") + ".png"); std::string jsonURL(url + (pixelRatio > 1 ? "@2x" : "") + ".json"); loader = std::make_unique<Loader>(); FileSource* fs = util::ThreadContext::getFileSource(); loader->jsonRequest = fs->request({ Resource::Kind::SpriteJSON, jsonURL }, util::RunLoop::getLoop(), [this, jsonURL](const Response& res) { if (res.stale) { // Only handle fresh responses. return; } loader->jsonRequest = nullptr; if (res.error) { std::stringstream message; message << "Failed to load [" << jsonURL << "]: " << res.error->message; emitSpriteLoadingFailed(message.str()); return; } else { loader->json = res.data; } emitSpriteLoadedIfComplete(); }); loader->spriteRequest = fs->request({ Resource::Kind::SpriteImage, spriteURL }, util::RunLoop::getLoop(), [this, spriteURL](const Response& res) { if (res.stale) { // Only handle fresh responses. return; } loader->spriteRequest = nullptr; if (res.error) { std::stringstream message; message << "Failed to load [" << spriteURL << "]: " << res.error->message; emitSpriteLoadingFailed(message.str()); return; } else { loader->image = res.data; } emitSpriteLoadedIfComplete(); }); }
void SpriteStore::setURL(const std::string& url) { if (url.empty()) { // Treat a non-existent sprite as a successfully loaded empty sprite. loaded = true; return; } std::string spriteURL(url + (pixelRatio > 1 ? "@2x" : "") + ".png"); std::string jsonURL(url + (pixelRatio > 1 ? "@2x" : "") + ".json"); loader = std::make_unique<Loader>(); FileSource* fs = util::ThreadContext::getFileSource(); loader->jsonRequest = fs->request({ Resource::Kind::SpriteJSON, jsonURL }, [this, jsonURL](Response res) { if (res.stale) { // Only handle fresh responses. return; } loader->jsonRequest = nullptr; if (res.error) { observer->onSpriteError(std::make_exception_ptr(std::runtime_error(res.error->message))); } else { loader->json = res.data; emitSpriteLoadedIfComplete(); } }); loader->spriteRequest = fs->request({ Resource::Kind::SpriteImage, spriteURL }, [this, spriteURL](Response res) { if (res.stale) { // Only handle fresh responses. return; } loader->spriteRequest = nullptr; if (res.error) { observer->onSpriteError(std::make_exception_ptr(std::runtime_error(res.error->message))); } else { loader->image = res.data; emitSpriteLoadedIfComplete(); } }); }
Sprite::Sprite(const std::string& baseUrl, float pixelRatio_) : pixelRatio(pixelRatio_ > 1 ? 2 : 1) { if (baseUrl.empty()) { // Treat a non-existent sprite as a successfully loaded empty sprite. loaded = true; return; } std::string spriteURL(baseUrl + (pixelRatio_ > 1 ? "@2x" : "") + ".png"); std::string jsonURL(baseUrl + (pixelRatio_ > 1 ? "@2x" : "") + ".json"); loader = std::make_unique<Loader>(); FileSource* fs = util::ThreadContext::getFileSource(); loader->jsonRequest = fs->request({ Resource::Kind::JSON, jsonURL }, util::RunLoop::getLoop(), [this, jsonURL](const Response& res) { loader->jsonRequest = nullptr; if (res.status == Response::Successful) { loader->data->json = res.data; loader->loadedJSON = true; } else { std::stringstream message; message << "Failed to load [" << jsonURL << "]: " << res.message; emitSpriteLoadingFailed(message.str()); return; } emitSpriteLoadedIfComplete(); }); loader->spriteRequest = fs->request({ Resource::Kind::Image, spriteURL }, util::RunLoop::getLoop(), [this, spriteURL](const Response& res) { loader->spriteRequest = nullptr; if (res.status == Response::Successful) { loader->data->image = res.data; loader->loadedImage = true; } else { std::stringstream message; message << "Failed to load [" << spriteURL << "]: " << res.message; emitSpriteLoadingFailed(message.str()); return; } emitSpriteLoadedIfComplete(); }); }
static void testWebContextSecurityFileXHR(WebViewTest* test, gconstpointer) { GUniquePtr<char> fileURL(g_strdup_printf("file://%s/simple.html", Test::getResourcesDir(Test::WebKit2Resources).data())); test->loadURI(fileURL.get()); test->waitUntilLoadFinished(); GUniquePtr<char> jsonURL(g_strdup_printf("file://%s/simple.json", Test::getResourcesDir().data())); GUniquePtr<char> xhr(g_strdup_printf("var xhr = new XMLHttpRequest; xhr.open(\"GET\", \"%s\"); xhr.send();", jsonURL.get())); WebKitJavascriptResult* consoleMessage = nullptr; webkit_user_content_manager_register_script_message_handler(test->m_userContentManager.get(), "console"); g_signal_connect(test->m_userContentManager.get(), "script-message-received::console", G_CALLBACK(consoleMessageReceivedCallback), &consoleMessage); // By default file access is not allowed, this will show a console message with a cross-origin error. GUniqueOutPtr<GError> error; WebKitJavascriptResult* javascriptResult = test->runJavaScriptAndWaitUntilFinished(xhr.get(), &error.outPtr()); g_assert(javascriptResult); g_assert(!error); g_assert(consoleMessage); GUniquePtr<char> messageString(WebViewTest::javascriptResultToCString(consoleMessage)); GRefPtr<GVariant> variant = g_variant_parse(G_VARIANT_TYPE("(uusus)"), messageString.get(), nullptr, nullptr, nullptr); g_assert(variant.get()); unsigned level; const char* messageText; g_variant_get(variant.get(), "(uu&su&s)", nullptr, &level, &messageText, nullptr, nullptr); g_assert_cmpuint(level, ==, 3); // Console error message. GUniquePtr<char> expectedErrorMessage(g_strdup_printf("XMLHttpRequest cannot load %s. Cross origin requests are only supported for HTTP.", jsonURL.get())); g_assert_cmpstr(messageText, ==, expectedErrorMessage.get()); webkit_javascript_result_unref(consoleMessage); consoleMessage = nullptr; level = 0; messageText = nullptr; variant = nullptr; // Allow file access from file URLs. webkit_settings_set_allow_file_access_from_file_urls(webkit_web_view_get_settings(test->m_webView), TRUE); test->loadURI(fileURL.get()); test->waitUntilLoadFinished(); javascriptResult = test->runJavaScriptAndWaitUntilFinished(xhr.get(), &error.outPtr()); g_assert(javascriptResult); g_assert(!error); // It isn't still possible to load file from an HTTP URL. test->loadURI(kServer->getURIForPath("/").data()); test->waitUntilLoadFinished(); javascriptResult = test->runJavaScriptAndWaitUntilFinished(xhr.get(), &error.outPtr()); g_assert(javascriptResult); g_assert(!error); g_assert(consoleMessage); variant = g_variant_parse(G_VARIANT_TYPE("(uusus)"), messageString.get(), nullptr, nullptr, nullptr); g_assert(variant.get()); g_variant_get(variant.get(), "(uu&su&s)", nullptr, &level, &messageText, nullptr, nullptr); g_assert_cmpuint(level, ==, 3); // Console error message. g_assert_cmpstr(messageText, ==, expectedErrorMessage.get()); webkit_javascript_result_unref(consoleMessage); g_signal_handlers_disconnect_matched(test->m_userContentManager.get(), G_SIGNAL_MATCH_DATA, 0, 0, nullptr, nullptr, &consoleMessage); webkit_user_content_manager_unregister_script_message_handler(test->m_userContentManager.get(), "console"); webkit_settings_set_allow_file_access_from_file_urls(webkit_web_view_get_settings(test->m_webView), FALSE); }