15821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Copyright (c) 2012 The Chromium Authors. All rights reserved.
25821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Use of this source code is governed by a BSD-style license that can be
35821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// found in the LICENSE file.
45821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
51320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci#ifndef EXTENSIONS_BROWSER_API_DECLARATIVE_RULES_REGISTRY_H__
61320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci#define EXTENSIONS_BROWSER_API_DECLARATIVE_RULES_REGISTRY_H__
75821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
80f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)#include <map>
90f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)#include <set>
105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include <string>
115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include <vector>
125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
130f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)#include "base/callback_forward.h"
140f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)#include "base/compiler_specific.h"
150f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)#include "base/gtest_prod_util.h"
160f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)#include "base/memory/scoped_ptr.h"
170f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)#include "base/memory/weak_ptr.h"
185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "content/public/browser/browser_thread.h"
190f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)#include "content/public/browser/notification_observer.h"
200f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)#include "content/public/browser/notification_registrar.h"
211320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci#include "extensions/common/api/events.h"
220f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)#include "extensions/common/one_shot_event.h"
230f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)
241320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tuccinamespace content {
251320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucciclass BrowserContext;
261320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci}
275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)namespace base {
290f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)class Value;
300f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)}  // namespace base
315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)namespace extensions {
335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
340f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)class RulesCacheDelegate;
355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
360f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)// A base class for RulesRegistries that takes care of storing the
370f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)// RulesRegistry::Rule objects. It contains all the methods that need to run on
380f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)// the registry thread; methods that need to run on the UI thread are separated
390f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)// in the RulesCacheDelegate object.
402a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)class RulesRegistry : public base::RefCountedThreadSafe<RulesRegistry> {
415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) public:
421320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci  typedef extensions::core_api::events::Rule Rule;
43f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)  struct WebViewKey {
44f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)    int embedder_process_id;
45f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)    int webview_instance_id;
46f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)    WebViewKey(int embedder_process_id, int webview_instance_id)
47f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)        : embedder_process_id(embedder_process_id),
48f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)          webview_instance_id(webview_instance_id) {}
49f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)    bool operator<(const WebViewKey& other) const {
50f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)      return embedder_process_id < other.embedder_process_id ||
51f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)          ((embedder_process_id == other.embedder_process_id) &&
52f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)           (webview_instance_id < other.webview_instance_id));
53f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)    }
54f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)  };
555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
560f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  enum Defaults { DEFAULT_PRIORITY = 100 };
570f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  // After the RulesCacheDelegate object (the part of the registry which runs on
580f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  // the UI thread) is created, a pointer to it is passed to |*ui_part|.
591320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci  // In tests, |browser_context| and |ui_part| can be NULL (at the same time).
601320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci  // In that case the storage functionality disabled (no RulesCacheDelegate
611320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci  // object created).
621320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci  RulesRegistry(content::BrowserContext* browser_context,
630f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)                const std::string& event_name,
640f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)                content::BrowserThread::ID owner_thread,
65f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)                RulesCacheDelegate* cache_delegate,
66f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)                const WebViewKey& webview_key);
670f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)
680f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  const OneShotEvent& ready() const {
690f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)    return ready_;
700f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  }
710f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)
720f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  // RulesRegistry implementation:
732a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Registers |rules|, owned by |extension_id| to this RulesRegistry.
755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // If a concrete RuleRegistry does not support some of the rules,
765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // it may ignore them.
775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  //
785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // |rules| is a list of Rule instances following the definition of the
795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // declarative extension APIs. It is guaranteed that each rule in |rules| has
805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // a unique name within the scope of |extension_id| that has not been
815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // registered before, unless it has been removed again.
825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // The ownership of rules remains with the caller.
835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  //
845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Returns an empty string if the function is successful or an error
855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // message otherwise.
865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  //
875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // IMPORTANT: This function is atomic. Either all rules that are deemed
885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // relevant are added or none.
890f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  std::string AddRules(
905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      const std::string& extension_id,
910f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)      const std::vector<linked_ptr<RulesRegistry::Rule> >& rules);
925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Unregisters all rules listed in |rule_identifiers| and owned by
945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // |extension_id| from this RulesRegistry.
955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Some or all IDs in |rule_identifiers| may not be stored in this
965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // RulesRegistry and are ignored.
975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  //
985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Returns an empty string if the function is successful or an error
995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // message otherwise.
1005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  //
1015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // IMPORTANT: This function is atomic. Either all rules that are deemed
1025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // relevant are removed or none.
1030f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  std::string RemoveRules(
1045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      const std::string& extension_id,
1050f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)      const std::vector<std::string>& rule_identifiers);
1065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Same as RemoveAllRules but acts on all rules owned by |extension_id|.
1080f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  std::string RemoveAllRules(const std::string& extension_id);
1095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Returns all rules listed in |rule_identifiers| and owned by |extension_id|
1115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // registered in this RuleRegistry. Entries in |rule_identifiers| that
1125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // are unknown are ignored.
1135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  //
1145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // The returned rules are stored in |out|. Ownership is passed to the caller.
115f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)  void GetRules(const std::string& extension_id,
116f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)                const std::vector<std::string>& rule_identifiers,
117f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)                std::vector<linked_ptr<RulesRegistry::Rule> >* out);
1185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Same as GetRules but returns all rules owned by |extension_id|.
120f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)  void GetAllRules(const std::string& extension_id,
121f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)                   std::vector<linked_ptr<RulesRegistry::Rule> >* out);
1225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
123f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)  // Called to notify the RulesRegistry that the extension availability has
124f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)  // changed, so that the registry can update which rules are active.
1250f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  void OnExtensionUnloaded(const std::string& extension_id);
126f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)  void OnExtensionUninstalled(const std::string& extension_id);
127f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)  void OnExtensionLoaded(const std::string& extension_id);
1280f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)
1290f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  // Returns the number of entries in used_rule_identifiers_ for leak detection.
1300f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  // Every ExtensionId counts as one entry, even if it contains no rules.
1310f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  size_t GetNumberOfUsedRuleIdentifiersForTesting() const;
1320f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)
133f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)  // Returns the RulesCacheDelegate. This is used for testing.
134f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)  RulesCacheDelegate* rules_cache_delegate_for_testing() const {
135f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)    return cache_delegate_.get();
136f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)  }
137f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)
1381320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci  // Returns the context where the rules registry lives.
1391320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci  content::BrowserContext* browser_context() { return browser_context_; }
1405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Returns the ID of the thread on which the rules registry lives.
142c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)  // It is safe to call this function from any thread.
143c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)  content::BrowserThread::ID owner_thread() const { return owner_thread_; }
144c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)
145c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)  // The name of the event with which rules are registered.
146c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)  const std::string& event_name() const { return event_name_; }
1475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
148f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)  // The key that identifies the webview (or tabs) in which these rules apply.
149f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)  // If the rules apply to the main browser, then this returns the tuple (0, 0).
150f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)  const WebViewKey& webview_key() const {
151f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)    return webview_key_;
152f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)  }
153f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)
1545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) protected:
1550f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  virtual ~RulesRegistry();
1560f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)
157f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)  // The precondition for calling this method is that all rules have unique IDs.
158f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)  // AddRules establishes this precondition and calls into this method.
159f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)  // Stored rules already meet this precondition and so they avoid calling
160f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)  // CheckAndFillInOptionalRules for improved performance.
161f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)  //
162f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)  // Returns an empty string if the function is successful or an error
163f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)  // message otherwise.
164f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)  std::string AddRulesNoFill(
165f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)      const std::string& extension_id,
166f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)      const std::vector<linked_ptr<RulesRegistry::Rule> >& rules);
167f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)
1680f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  // These functions need to apply the rules to the browser, while the base
1690f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  // class will handle defaulting empty fields before calling *Impl, and will
1700f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  // automatically cache the rules and re-call *Impl on browser startup.
1710f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  virtual std::string AddRulesImpl(
1720f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)      const std::string& extension_id,
1730f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)      const std::vector<linked_ptr<RulesRegistry::Rule> >& rules) = 0;
1740f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  virtual std::string RemoveRulesImpl(
1750f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)      const std::string& extension_id,
1760f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)      const std::vector<std::string>& rule_identifiers) = 0;
1770f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  virtual std::string RemoveAllRulesImpl(
1780f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)      const std::string& extension_id) = 0;
1792a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
1802a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) private:
1812a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  friend class base::RefCountedThreadSafe<RulesRegistry>;
1820f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  friend class RulesCacheDelegate;
1830f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)
1840f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  typedef std::string ExtensionId;
1850f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  typedef std::string RuleId;
1860f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  typedef std::pair<ExtensionId, RuleId> RulesDictionaryKey;
1870f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  typedef std::map<RulesDictionaryKey, linked_ptr<RulesRegistry::Rule> >
1880f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)      RulesDictionary;
1890f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  enum ProcessChangedRulesState {
1900f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)    // ProcessChangedRules can never be called, |cache_delegate_| is NULL.
1910f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)    NEVER_PROCESS,
1920f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)    // A task to call ProcessChangedRules is scheduled for future execution.
1930f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)    SCHEDULED_FOR_PROCESSING,
1940f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)    // No task to call ProcessChangedRules is scheduled yet, but it is possible
1950f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)    // to schedule one.
1960f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)    NOT_SCHEDULED_FOR_PROCESSING
1970f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  };
198a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles)  typedef std::map<ExtensionId, ProcessChangedRulesState> ProcessStateMap;
1990f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)
2000f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  base::WeakPtr<RulesRegistry> GetWeakPtr() {
201effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch    DCHECK_CURRENTLY_ON(content::BrowserThread::UI);
2020f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)    return weak_ptr_factory_.GetWeakPtr();
2030f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  }
2040f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)
2050f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  // Common processing after extension's rules have changed.
2060f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  void ProcessChangedRules(const std::string& extension_id);
2070f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)
208a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles)  // Calls ProcessChangedRules if
209a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles)  // |process_changed_rules_requested_(extension_id)| ==
2100f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  // NOT_SCHEDULED_FOR_PROCESSING.
2110f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  void MaybeProcessChangedRules(const std::string& extension_id);
2120f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)
2135d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)  // This method implements the functionality of RemoveAllRules, except for not
2145d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)  // calling MaybeProcessChangedRules. That way updating the rules store and
2155d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)  // extension prefs is avoided. This method is called when an extension is
2165d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)  // uninstalled, that way there is no clash with the preferences being wiped.
2175d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)  std::string RemoveAllRulesNoStoreUpdate(const std::string& extension_id);
2185d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)
2190f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  void MarkReady(base::Time storage_init_time);
2200f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)
2210f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  // Deserialize the rules from the given Value object and add them to the
2220f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  // RulesRegistry.
2230f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  void DeserializeAndAddRules(const std::string& extension_id,
2240f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)                              scoped_ptr<base::Value> rules);
2250f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)
2261320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci  // The context to which this rules registry belongs.
2271320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci  content::BrowserContext* browser_context_;
228c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)
229c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)  // The ID of the thread on which the rules registry lives.
230c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)  const content::BrowserThread::ID owner_thread_;
231c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)
232c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)  // The name of the event with which rules are registered.
233c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)  const std::string event_name_;
234c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)
235f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)  // The key that identifies the context in which these rules apply.
236f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)  WebViewKey webview_key_;
237f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)
2380f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  RulesDictionary rules_;
2390f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)
2400f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  // Signaled when we have finished reading from storage for all extensions that
2410f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  // are loaded on startup.
2420f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  OneShotEvent ready_;
2430f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)
2440f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  // The factory needs to be declared before |cache_delegate_|, so that it can
2450f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  // produce a pointer as a construction argument for |cache_delegate_|.
2460f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  base::WeakPtrFactory<RulesRegistry> weak_ptr_factory_;
2470f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)
2480f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  // |cache_delegate_| is owned by the registry service. If |cache_delegate_| is
2490f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  // NULL, then the storage functionality is disabled (this is used in tests).
2500f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  // This registry cannot own |cache_delegate_| because during the time after
2510f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  // rules registry service shuts down on UI thread, and the registry is
2520f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  // destroyed on its thread, the use of the |cache_delegate_| would not be
2530f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  // safe. The registry only ever associates with one RulesCacheDelegate
2540f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  // instance.
2550f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  base::WeakPtr<RulesCacheDelegate> cache_delegate_;
2560f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)
257a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles)  ProcessStateMap process_changed_rules_requested_;
2580f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)
2590f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  // Returns whether any existing rule is registered with identifier |rule_id|
2600f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  // for extension |extension_id|.
2610f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  bool IsUniqueId(const std::string& extension_id,
2620f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)                  const std::string& rule_id) const;
2630f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)
2640f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  // Creates an ID that is unique within the scope of|extension_id|.
2650f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  std::string GenerateUniqueId(const std::string& extension_id);
2660f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)
2670f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  // Verifies that all |rules| have unique IDs or initializes them with
2680f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  // unique IDs if they don't have one. In case of duplicate IDs, this function
2690f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  // returns a non-empty error message.
2700f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  std::string CheckAndFillInOptionalRules(
2710f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)    const std::string& extension_id,
2720f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)    const std::vector<linked_ptr<RulesRegistry::Rule> >& rules);
2730f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)
2740f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  // Initializes the priority fields in case they have not been set.
2750f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  void FillInOptionalPriorities(
2760f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)      const std::vector<linked_ptr<RulesRegistry::Rule> >& rules);
2770f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)
2780f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  // Removes all |identifiers| of |extension_id| from |used_rule_identifiers_|.
2790f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  void RemoveUsedRuleIdentifiers(const std::string& extension_id,
2800f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)                                 const std::vector<std::string>& identifiers);
2810f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)
2820f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  // Same as RemoveUsedRuleIdentifiers but operates on all rules of
2830f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  // |extension_id|.
2840f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  void RemoveAllUsedRuleIdentifiers(const std::string& extension_id);
2850f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)
2860f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  typedef std::string RuleIdentifier;
2870f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  typedef std::map<ExtensionId, std::set<RuleIdentifier> > RuleIdentifiersMap;
2880f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  RuleIdentifiersMap used_rule_identifiers_;
2890f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  int last_generated_rule_identifier_id_;
2900f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)
2912a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  DISALLOW_COPY_AND_ASSIGN(RulesRegistry);
2925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)};
2935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}  // namespace extensions
2955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2961320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci#endif  // EXTENSIONS_BROWSER_API_DECLARATIVE_RULES_REGISTRY_H__
297