1 // Copyright (c) 2011 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.
5 #ifndef CHROME_BROWSER_SPELLCHECKER_SPELLCHECK_HOST_IMPL_H_
6 #define CHROME_BROWSER_SPELLCHECKER_SPELLCHECK_HOST_IMPL_H_
12 #include "base/compiler_specific.h"
13 #include "base/file_path.h"
14 #include "base/memory/scoped_ptr.h"
15 #include "base/memory/weak_ptr.h"
16 #include "chrome/browser/spellchecker/spellcheck_host.h"
17 #include "chrome/browser/spellchecker/spellcheck_profile_provider.h"
18 #include "content/public/common/url_fetcher_delegate.h"
19 #include "content/public/browser/notification_observer.h"
20 #include "content/public/browser/notification_registrar.h"
22 // This class implements the SpellCheckHost interface to provide the
23 // functionalities listed below:
24 // * Adding a word to the custom dictionary;
25 // * Storing the custom dictionary to the file, and read it back
26 // from the file during the initialization.
27 // * Downloading a dictionary and map it for the renderer, and;
28 // * Calling the platform spellchecker attached to the browser;
30 // To download a dictionary and initialize it without blocking the UI thread,
31 // this class also implements the URLFetcher::Delegate() interface. This
32 // initialization status is notified to the UI thread through the
33 // SpellCheckProfileProvider interface.
35 // We expect a profile creates an instance of this class through a factory
36 // method, SpellCheckHost::Create() and uses only the SpellCheckHost interface
37 // provided by this class.
38 // spell_check_host_ = SpellCheckHost::Create(...)
40 // Available languages for the checker, which we need to specify via Create(),
41 // can be listed using SpellCheckHost::GetAvailableLanguages() static method.
42 class SpellCheckHostImpl
: public SpellCheckHost
,
43 public content::URLFetcherDelegate
,
44 public content::NotificationObserver
{
46 SpellCheckHostImpl(SpellCheckProfileProvider
* profile
,
47 const std::string
& language
,
48 net::URLRequestContextGetter
* request_context_getter
,
49 SpellCheckHostMetrics
* metrics
);
51 virtual ~SpellCheckHostImpl();
55 // SpellCheckHost implementation
56 virtual void UnsetProfile() OVERRIDE
;
57 virtual void InitForRenderer(content::RenderProcessHost
* process
) OVERRIDE
;
58 virtual void AddWord(const std::string
& word
) OVERRIDE
;
59 virtual const base::PlatformFile
& GetDictionaryFile() const OVERRIDE
;
60 virtual const std::string
& GetLanguage() const OVERRIDE
;
61 virtual bool IsUsingPlatformChecker() const OVERRIDE
;
64 typedef SpellCheckProfileProvider::CustomWordList CustomWordList
;
66 // These two classes can destruct us.
67 friend class content::BrowserThread
;
68 friend class DeleteTask
<SpellCheckHostImpl
>;
70 // Figure out the location for the dictionary. This is only non-trivial for
72 // The default place whether the spellcheck dictionary can reside is
73 // chrome::DIR_APP_DICTIONARIES. However, for systemwide installations,
74 // this directory may not have permissions for download. In that case, the
75 // alternate directory for download is chrome::DIR_USER_DATA.
76 void InitializeDictionaryLocation();
77 void InitializeDictionaryLocationComplete();
79 // The reply point for PostTaskAndReply. Called when AddWord is finished
80 // adding a word in the background.
81 void AddWordComplete(const std::string
& word
);
83 // Inform |profile_| that initialization has finished.
84 // |custom_words| holds the custom word list which was
85 // loaded at the file thread.
86 void InformProfileOfInitializationWithCustomWords(
87 CustomWordList
* custom_words
);
89 // An alternative version of InformProfileOfInitializationWithCustomWords()
90 // which implies empty |custom_words|.
91 void InformProfileOfInitialization();
93 // If |dictionary_file_| is missing, we attempt to download it.
94 void DownloadDictionary();
96 // Loads a custom dictionary from disk.
97 void LoadCustomDictionary(CustomWordList
* custom_words
);
99 // Write a custom dictionary addition to disk.
100 void WriteWordToCustomDictionary(const std::string
& word
);
102 // Returns a metrics counter associated with this object,
103 // or null when metrics recording is disabled.
104 virtual SpellCheckHostMetrics
* GetMetrics() const OVERRIDE
;
106 // Returns true if the dictionary is ready to use.
107 virtual bool IsReady() const OVERRIDE
;
109 // content::URLFetcherDelegate implementation. Called when we finish
110 // downloading the spellcheck dictionary; saves the dictionary to |data_|.
111 virtual void OnURLFetchComplete(const content::URLFetcher
* source
) OVERRIDE
;
113 // NotificationProfile implementation.
114 virtual void Observe(int type
,
115 const content::NotificationSource
& source
,
116 const content::NotificationDetails
& details
) OVERRIDE
;
118 // Saves |data_| to disk. Run on the file thread.
119 void SaveDictionaryData();
120 void SaveDictionaryDataComplete();
122 // Verifies the specified BDict file exists and it is sane. This function
123 // should be called before opening the file so we can delete it and download a
124 // new dictionary if it is corrupted.
125 bool VerifyBDict(const FilePath
& path
) const;
128 SpellCheckProfileProvider
* profile_
;
130 // The desired location of the dictionary file (whether or not t exists yet).
131 FilePath bdict_file_path_
;
133 // The location of the custom words file.
134 FilePath custom_dictionary_file_
;
136 // State whether a dictionary has been partially, or fully saved. If the
137 // former, shortcut Initialize.
138 bool dictionary_saved_
;
140 // The language of the dictionary file.
141 std::string language_
;
143 // The file descriptor/handle for the dictionary file.
144 base::PlatformFile file_
;
146 // We don't want to attempt to download a missing dictionary file more than
148 bool tried_to_download_
;
150 // Whether we should use the platform spellchecker instead of Hunspell.
151 bool use_platform_spellchecker_
;
153 // Data received from the dictionary download.
156 // Used for downloading the dictionary file. We don't hold a reference, and
157 // it is only valid to use it on the UI thread.
158 net::URLRequestContextGetter
* request_context_getter_
;
160 // Used for downloading the dictionary file.
161 scoped_ptr
<content::URLFetcher
> fetcher_
;
163 content::NotificationRegistrar registrar_
;
165 // An optional metrics counter given by the constructor.
166 SpellCheckHostMetrics
* metrics_
;
168 base::WeakPtrFactory
<SpellCheckHostImpl
> weak_ptr_factory_
;
170 scoped_ptr
<CustomWordList
> custom_words_
;
172 DISALLOW_COPY_AND_ASSIGN(SpellCheckHostImpl
);
175 #endif // CHROME_BROWSER_SPELLCHECKER_SPELLCHECK_HOST_IMPL_H_