Home | History | Annotate | Download | only in variations
      1 // Copyright (c) 2012 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 #ifndef CHROME_BROWSER_METRICS_VARIATIONS_VARIATIONS_HTTP_HEADER_PROVIDER_H_
      6 #define CHROME_BROWSER_METRICS_VARIATIONS_VARIATIONS_HTTP_HEADER_PROVIDER_H_
      7 
      8 #include <set>
      9 #include <string>
     10 
     11 #include "base/basictypes.h"
     12 #include "base/gtest_prod_util.h"
     13 #include "base/metrics/field_trial.h"
     14 #include "base/synchronization/lock.h"
     15 #include "components/variations/variations_associated_data.h"
     16 
     17 namespace content {
     18 class ResourceContext;
     19 }
     20 
     21 namespace net {
     22 class HttpRequestHeaders;
     23 }
     24 
     25 class GURL;
     26 class Profile;
     27 class ProfileIOData;
     28 
     29 template <typename T> struct DefaultSingletonTraits;
     30 
     31 namespace chrome_variations {
     32 
     33 // A helper class for maintaining Chrome experiments and metrics state
     34 // transmitted in custom HTTP request headers.
     35 // This class is a thread-safe singleton.
     36 class VariationsHttpHeaderProvider : base::FieldTrialList::Observer {
     37  public:
     38   static VariationsHttpHeaderProvider* GetInstance();
     39 
     40   // Adds Chrome experiment and metrics state as custom headers to |headers|.
     41   // Some headers may not be set given the |incognito| mode or whether
     42   // the user has |uma_enabled|.  Also, we never transmit headers to non-Google
     43   // sites, which is checked based on the destination |url|.
     44   void AppendHeaders(const GURL& url,
     45                      bool incognito,
     46                      bool uma_enabled,
     47                      net::HttpRequestHeaders* headers);
     48 
     49   // Sets *additional* variation ids and trigger variation ids to be encoded in
     50   // the X-Client-Data request header.  This is intended for development use to
     51   // force a server side experiment id.  |variation_ids| should be a
     52   // comma-separated string of numeric experiment ids.  If an id is prefixed
     53   // with "t" it will be treated as a trigger experiment id.
     54   bool SetDefaultVariationIds(const std::string& variation_ids);
     55 
     56  private:
     57   friend struct DefaultSingletonTraits<VariationsHttpHeaderProvider>;
     58 
     59   FRIEND_TEST_ALL_PREFIXES(VariationsHttpHeaderProviderTest,
     60                            ShouldAppendHeaders);
     61   FRIEND_TEST_ALL_PREFIXES(VariationsHttpHeaderProviderTest,
     62                            SetDefaultVariationIds_Valid);
     63   FRIEND_TEST_ALL_PREFIXES(VariationsHttpHeaderProviderTest,
     64                            SetDefaultVariationIds_Invalid);
     65   FRIEND_TEST_ALL_PREFIXES(VariationsHttpHeaderProviderTest,
     66                            OnFieldTrialGroupFinalized);
     67 
     68   VariationsHttpHeaderProvider();
     69   virtual ~VariationsHttpHeaderProvider();
     70 
     71   // base::FieldTrialList::Observer implementation.
     72   // This will add the variation ID associated with |trial_name| and
     73   // |group_name| to the variation ID cache.
     74   virtual void OnFieldTrialGroupFinalized(
     75       const std::string& trial_name,
     76       const std::string& group_name) OVERRIDE;
     77 
     78   // Prepares the variation IDs cache with initial values if not already done.
     79   // This method also registers the caller with the FieldTrialList to receive
     80   // new variation IDs.
     81   void InitVariationIDsCacheIfNeeded();
     82 
     83   // Takes whatever is currently in |variation_ids_set_| and recreates
     84   // |variation_ids_header_| with it.  Assumes the the |lock_| is currently
     85   // held.
     86   void UpdateVariationIDsHeaderValue();
     87 
     88   // Checks whether variation headers should be appended to requests to the
     89   // specified |url|. Returns true for google.<TLD> and youtube.<TLD> URLs.
     90   static bool ShouldAppendHeaders(const GURL& url);
     91 
     92   // Guards |variation_ids_cache_initialized_|, |variation_ids_set_| and
     93   // |variation_ids_header_|.
     94   base::Lock lock_;
     95 
     96   // Whether or not we've initialized the cache.
     97   bool variation_ids_cache_initialized_;
     98 
     99   // Keep a cache of variation IDs that are transmitted in headers to Google.
    100   // This consists of a list of valid IDs, and the actual transmitted header.
    101   std::set<chrome_variations::VariationID> variation_ids_set_;
    102   std::set<chrome_variations::VariationID> variation_trigger_ids_set_;
    103 
    104   // Provides the google experiment ids forced from command line.
    105   std::set<chrome_variations::VariationID> default_variation_ids_set_;
    106   std::set<chrome_variations::VariationID> default_trigger_id_set_;
    107 
    108   std::string variation_ids_header_;
    109 
    110   DISALLOW_COPY_AND_ASSIGN(VariationsHttpHeaderProvider);
    111 };
    112 
    113 }  // namespace chrome_variations
    114 
    115 #endif  // CHROME_BROWSER_METRICS_VARIATIONS_VARIATIONS_HTTP_HEADER_PROVIDER_H_
    116