Skip to content

Commit 08c6ce5

Browse files
committed
add URLRequestNWAppJob to provide response code
Fix nwjs#1314 Conflicts: src/net/app_protocol_handler.cc
1 parent 76261c1 commit 08c6ce5

File tree

1 file changed

+140
-1
lines changed

1 file changed

+140
-1
lines changed

src/net/app_protocol_handler.cc

Lines changed: 140 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,16 +4,155 @@
44

55
#include "content/nw/src/net/app_protocol_handler.h"
66

7+
#include "base/base64.h"
8+
#include "base/file_util.h"
9+
#include "base/files/file_path.h"
10+
#include "base/format_macros.h"
711
#include "base/logging.h"
12+
#include "base/sha1.h"
13+
#include "base/strings/stringprintf.h"
14+
#include "base/threading/sequenced_worker_pool.h"
15+
#include "content/public/browser/browser_thread.h"
16+
#include "net/base/mime_util.h"
817
#include "net/base/net_errors.h"
918
#include "net/base/net_util.h"
19+
#include "net/http/http_request_headers.h"
20+
#include "net/http/http_response_headers.h"
21+
#include "net/http/http_response_info.h"
1022
#include "net/url_request/url_request.h"
1123
#include "net/url_request/url_request_error_job.h"
1224
#include "net/url_request/url_request_file_dir_job.h"
1325
#include "net/url_request/url_request_file_job.h"
1426

1527
namespace net {
1628

29+
namespace {
30+
31+
net::HttpResponseHeaders* BuildHttpHeaders(
32+
const std::string& content_security_policy, bool send_cors_header,
33+
const base::Time& last_modified_time) {
34+
std::string raw_headers;
35+
raw_headers.append("HTTP/1.1 200 OK");
36+
if (!content_security_policy.empty()) {
37+
raw_headers.append(1, '\0');
38+
raw_headers.append("Content-Security-Policy: ");
39+
raw_headers.append(content_security_policy);
40+
}
41+
42+
if (send_cors_header) {
43+
raw_headers.append(1, '\0');
44+
raw_headers.append("Access-Control-Allow-Origin: *");
45+
}
46+
47+
if (!last_modified_time.is_null()) {
48+
// Hash the time and make an etag to avoid exposing the exact
49+
// user installation time of the extension.
50+
std::string hash = base::StringPrintf("%" PRId64,
51+
last_modified_time.ToInternalValue());
52+
hash = base::SHA1HashString(hash);
53+
std::string etag;
54+
if (base::Base64Encode(hash, &etag)) {
55+
raw_headers.append(1, '\0');
56+
raw_headers.append("ETag: \"");
57+
raw_headers.append(etag);
58+
raw_headers.append("\"");
59+
// Also force revalidation.
60+
raw_headers.append(1, '\0');
61+
raw_headers.append("cache-control: no-cache");
62+
}
63+
}
64+
65+
raw_headers.append(2, '\0');
66+
return new net::HttpResponseHeaders(raw_headers);
67+
}
68+
69+
void ReadMimeTypeFromFile(const base::FilePath& filename,
70+
std::string* mime_type,
71+
bool* result) {
72+
*result = net::GetMimeTypeFromFile(filename, mime_type);
73+
}
74+
75+
base::Time GetFileLastModifiedTime(const base::FilePath& filename) {
76+
if (base::PathExists(filename)) {
77+
base::PlatformFileInfo info;
78+
if (file_util::GetFileInfo(filename, &info))
79+
return info.last_modified;
80+
}
81+
return base::Time();
82+
}
83+
84+
base::Time GetFileCreationTime(const base::FilePath& filename) {
85+
if (base::PathExists(filename)) {
86+
base::PlatformFileInfo info;
87+
if (file_util::GetFileInfo(filename, &info))
88+
return info.creation_time;
89+
}
90+
return base::Time();
91+
}
92+
93+
void ReadResourceFilePathAndLastModifiedTime(
94+
const base::FilePath& file_path,
95+
base::Time* last_modified_time) {
96+
*last_modified_time = GetFileLastModifiedTime(file_path);
97+
}
98+
99+
class URLRequestNWAppJob : public net::URLRequestFileJob {
100+
public:
101+
URLRequestNWAppJob(net::URLRequest* request,
102+
net::NetworkDelegate* network_delegate,
103+
const base::FilePath& file_path,
104+
const std::string& content_security_policy,
105+
bool send_cors_header)
106+
: net::URLRequestFileJob(
107+
request, network_delegate, base::FilePath(),
108+
content::BrowserThread::GetBlockingPool()->
109+
GetTaskRunnerWithShutdownBehavior(
110+
base::SequencedWorkerPool::SKIP_ON_SHUTDOWN)),
111+
content_security_policy_(content_security_policy),
112+
send_cors_header_(send_cors_header),
113+
weak_factory_(this) {
114+
file_path_ = file_path;
115+
// response_info_.headers = BuildHttpHeaders(content_security_policy,
116+
// send_cors_header,
117+
// base::Time());
118+
}
119+
120+
virtual void GetResponseInfo(net::HttpResponseInfo* info) OVERRIDE {
121+
*info = response_info_;
122+
}
123+
124+
virtual void Start() OVERRIDE {
125+
base::Time* last_modified_time = new base::Time();
126+
bool posted = content::BrowserThread::PostBlockingPoolTaskAndReply(
127+
FROM_HERE,
128+
base::Bind(&ReadResourceFilePathAndLastModifiedTime,
129+
file_path_,
130+
base::Unretained(last_modified_time)),
131+
base::Bind(&URLRequestNWAppJob::OnFilePathAndLastModifiedTimeRead,
132+
weak_factory_.GetWeakPtr(),
133+
base::Owned(last_modified_time)));
134+
DCHECK(posted);
135+
}
136+
137+
private:
138+
virtual ~URLRequestNWAppJob() {}
139+
140+
void OnFilePathAndLastModifiedTimeRead(base::Time* last_modified_time) {
141+
response_info_.headers = BuildHttpHeaders(
142+
content_security_policy_,
143+
send_cors_header_,
144+
*last_modified_time);
145+
URLRequestFileJob::Start();
146+
}
147+
148+
net::HttpResponseInfo response_info_;
149+
std::string content_security_policy_;
150+
bool send_cors_header_;
151+
base::WeakPtrFactory<URLRequestNWAppJob> weak_factory_;
152+
};
153+
154+
} // namespace
155+
17156
AppProtocolHandler::AppProtocolHandler(const base::FilePath& root)
18157
:root_path_(root)
19158
{
@@ -51,7 +190,7 @@ URLRequestJob* AppProtocolHandler::MaybeCreateJob(
51190

52191
// Use a regular file request job for all non-directories (including invalid
53192
// file names).
54-
return new URLRequestFileJob(request, network_delegate, file_path);
193+
return new URLRequestNWAppJob(request, network_delegate, file_path, "", false);
55194
}
56195

57196
bool AppProtocolHandler::IsSafeRedirectTarget(const GURL& location) const {

0 commit comments

Comments
 (0)