Home | History | Annotate | Download | only in common
      1 // Copyright 2013 The Chromium Authors. All rights reserved.
      2 // Use of this source code is governed by a BSD-style license that can be
      3 // found in the LICENSE file.
      4 
      5 #include "chrome/browser/ui/app_list/search/common/json_response_fetcher.h"
      6 
      7 #include "base/bind.h"
      8 #include "base/values.h"
      9 #include "chrome/browser/safe_json_parser.h"
     10 #include "net/base/load_flags.h"
     11 #include "net/url_request/url_fetcher.h"
     12 #include "net/url_request/url_request_status.h"
     13 #include "url/gurl.h"
     14 
     15 namespace app_list {
     16 
     17 const char kBadResponse[] = "Bad Web Service search response";
     18 
     19 JSONResponseFetcher::JSONResponseFetcher(
     20     const Callback& callback,
     21     net::URLRequestContextGetter* context_getter)
     22     : callback_(callback),
     23       context_getter_(context_getter),
     24       weak_factory_(this) {
     25   DCHECK(!callback_.is_null());
     26 }
     27 
     28 JSONResponseFetcher::~JSONResponseFetcher() {}
     29 
     30 void JSONResponseFetcher::Start(const GURL& query_url) {
     31   Stop();
     32 
     33   fetcher_.reset(net::URLFetcher::Create(
     34       query_url,
     35       net::URLFetcher::GET,
     36       this));
     37   fetcher_->SetRequestContext(context_getter_);
     38   fetcher_->SetLoadFlags(net::LOAD_DO_NOT_SAVE_COOKIES |
     39                          net::LOAD_DISABLE_CACHE);
     40   fetcher_->Start();
     41 }
     42 
     43 void JSONResponseFetcher::Stop() {
     44   fetcher_.reset();
     45   weak_factory_.InvalidateWeakPtrs();
     46 }
     47 
     48 void JSONResponseFetcher::OnJsonParseSuccess(
     49     scoped_ptr<base::Value> parsed_json) {
     50   if (!parsed_json->IsType(base::Value::TYPE_DICTIONARY)) {
     51     OnJsonParseError(kBadResponse);
     52     return;
     53   }
     54 
     55   callback_.Run(make_scoped_ptr(
     56       static_cast<base::DictionaryValue*>(parsed_json.release())));
     57 }
     58 
     59 void JSONResponseFetcher::OnJsonParseError(const std::string& error) {
     60   callback_.Run(scoped_ptr<base::DictionaryValue>());
     61 }
     62 
     63 void JSONResponseFetcher::OnURLFetchComplete(
     64     const net::URLFetcher* source) {
     65   CHECK_EQ(fetcher_.get(), source);
     66 
     67   scoped_ptr<net::URLFetcher> fetcher(fetcher_.Pass());
     68 
     69   if (!fetcher->GetStatus().is_success() ||
     70       fetcher->GetResponseCode() != 200) {
     71     OnJsonParseError(kBadResponse);
     72     return;
     73   }
     74 
     75   std::string json_data;
     76   fetcher->GetResponseAsString(&json_data);
     77 
     78   scoped_refptr<SafeJsonParser> parser =
     79       new SafeJsonParser(json_data,
     80                          base::Bind(
     81                              &JSONResponseFetcher::OnJsonParseSuccess,
     82                              weak_factory_.GetWeakPtr()),
     83                          base::Bind(
     84                              &JSONResponseFetcher::OnJsonParseError,
     85                              weak_factory_.GetWeakPtr()));
     86   // The parser will call us back via one of the callbacks.
     87   parser->Start();
     88 }
     89 
     90 }  // namespace app_list
     91