Chromium 中JavaScript Fetch API接口c++代码实现(一)-CSDN博客
接着上一篇继续介绍调用,上函数堆栈。
1、打开http://192.168.8.1/chfs/shared/test/test02.html
此标签进程ID12484,
2、打开vs附加上此进程ID12484
3、点击页面测试按钮 调转到c++代码
F:\code\google\src\third_party\blink\renderer\core\fetch\fetch_manager.cc
ScriptPromise FetchManager::Fetch(ScriptState* script_state,
FetchRequestData* request,
AbortSignal* signal,
ExceptionState& exception_state) {
DCHECK(signal);
if (signal->aborted()) {
exception_state.RethrowV8Exception(signal->reason(script_state).V8Value());
return ScriptPromise();
}
request->SetDestination(network::mojom::RequestDestination::kEmpty);
auto* resolver = MakeGarbageCollected<ScriptPromiseResolver>(
script_state, exception_state.GetContext());
ScriptPromise promise = resolver->Promise();
auto* loader = MakeGarbageCollected<Loader>(
GetExecutionContext(), this, resolver, request, script_state, signal);
loaders_.insert(loader);
// TODO(ricea): Reject the Response body with AbortError, not TypeError.
loader->Start(exception_state);
return promise;
}
可以看到已经进入fetch函数
4、response响应堆栈:
third_party\blink\renderer\platform\loader\fetch\url_loader\background_url_loader.cc
5、third_party\blink\renderer\platform\loader\fetch\resource_loader.h 资源加载响应
\third_party\blink\renderer\platform\loader\fetch\resource_loader.cc
//通知body 响应response.json()函数
// FrameType never changes during the lifetime of a request.
if (auto* observer = fetcher_->GetResourceLoadObserver()) {
ResourceRequest request_for_obserber(initial_request);
// TODO(yoichio): Have DidReceiveResponse take a ResourceResponseHead, not
// ResourceRequest.
observer->DidReceiveResponse(
resource_->InspectorId(), request_for_obserber, response, resource_,
ResourceLoadObserver::ResponseSource::kNotFromMemoryCache);
}
6、src\out\Debug\gen\third_party\blink\renderer\bindings\core\v8\v8_response.cc
void JsonOperationCallback(const v8::FunctionCallbackInfo<v8::Value>& info) {
RUNTIME_CALL_TIMER_SCOPE_DISABLED_BY_DEFAULT(info.GetIsolate(), "Blink_Response_json");
BLINK_BINDINGS_TRACE_EVENT("Response.json");
// Promise returning function: Convert a TypeError to a reject promise.
v8::Isolate* isolate = info.GetIsolate();
v8::Local<v8::Object> v8_receiver = info.This();
const ExceptionContextType exception_context_type = ExceptionContextType::kOperationInvoke;
const char* const class_like_name = "Response";
const char* const property_name = "json";
ExceptionState exception_state(isolate, exception_context_type, class_like_name, property_name);
ExceptionToRejectPromiseScope reject_promise_scope(info, exception_state);
if (!V8Response::HasInstance(isolate, v8_receiver)) {
exception_state.ThrowTypeError("Illegal invocation");
return;
}
Response* blink_receiver = V8Response::ToWrappableUnsafe(isolate, v8_receiver);
v8::Local<v8::Context> receiver_context = v8_receiver->GetCreationContextChecked();
ScriptState* receiver_script_state = ScriptState::From(receiver_context);
ScriptState* script_state = receiver_script_state;
auto&& return_value = blink_receiver->json(script_state, exception_state);
if (UNLIKELY(exception_state.HadException())) {
return;
}
bindings::V8SetReturnValue(info, return_value);
}
7、src\third_party\blink\renderer\core\fetch\body.cc
Response.json 响应
ScriptPromise Body::json(ScriptState* script_state,
ExceptionState& exception_state) {
auto on_no_body = [script_state](ScriptPromiseResolver* resolver) {
resolver->Reject(V8ThrowException::CreateSyntaxError(
script_state->GetIsolate(), "Unexpected end of input"));
};
return LoadAndConvertBody<BodyJsonConsumer>(
script_state, &CreateLoaderAsStringWithUTF8Decode, on_no_body,
exception_state);
}
8、最后返回前端 效果如下:
至于其他细节,自行查看代码吧,用户还可以通过此处源码自行修改前端的一些请求数据。