Home | History | Annotate | Download | only in service_worker
      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 #ifndef CONTENT_BROWSER_SERVICE_WORKER_EMBEDDED_WORKER_INSTANCE_H_
      6 #define CONTENT_BROWSER_SERVICE_WORKER_EMBEDDED_WORKER_INSTANCE_H_
      7 
      8 #include <map>
      9 #include <vector>
     10 
     11 #include "base/basictypes.h"
     12 #include "base/callback_forward.h"
     13 #include "base/gtest_prod_util.h"
     14 #include "base/logging.h"
     15 #include "base/memory/ref_counted.h"
     16 #include "base/memory/weak_ptr.h"
     17 #include "base/observer_list.h"
     18 #include "base/strings/string16.h"
     19 #include "content/common/content_export.h"
     20 #include "content/common/service_worker/service_worker_status_code.h"
     21 #include "url/gurl.h"
     22 
     23 struct EmbeddedWorkerMsg_StartWorker_Params;
     24 
     25 namespace IPC {
     26 class Message;
     27 }
     28 
     29 namespace content {
     30 
     31 class EmbeddedWorkerRegistry;
     32 class ServiceWorkerContextCore;
     33 struct ServiceWorkerFetchRequest;
     34 
     35 // This gives an interface to control one EmbeddedWorker instance, which
     36 // may be 'in-waiting' or running in one of the child processes added by
     37 // AddProcessReference().
     38 class CONTENT_EXPORT EmbeddedWorkerInstance {
     39  public:
     40   typedef base::Callback<void(ServiceWorkerStatusCode)> StatusCallback;
     41   enum Status {
     42     STOPPED,
     43     STARTING,
     44     RUNNING,
     45     STOPPING,
     46   };
     47 
     48   class Listener {
     49    public:
     50     virtual ~Listener() {}
     51     virtual void OnStarted() {}
     52     virtual void OnStopped() {}
     53     virtual void OnPausedAfterDownload() {}
     54     virtual void OnReportException(const base::string16& error_message,
     55                                    int line_number,
     56                                    int column_number,
     57                                    const GURL& source_url) {}
     58     virtual void OnReportConsoleMessage(int source_identifier,
     59                                         int message_level,
     60                                         const base::string16& message,
     61                                         int line_number,
     62                                         const GURL& source_url) {}
     63     // These should return false if the message is not handled by this
     64     // listener. (TODO(kinuko): consider using IPC::Listener interface)
     65     // TODO(kinuko): Deprecate OnReplyReceived.
     66     virtual bool OnMessageReceived(const IPC::Message& message) = 0;
     67   };
     68 
     69   ~EmbeddedWorkerInstance();
     70 
     71   // Starts the worker. It is invalid to call this when the worker is not in
     72   // STOPPED status. |callback| is invoked when the worker's process is created
     73   // if necessary and the IPC to evaluate the worker's script is sent.
     74   // Observer::OnStarted() is run when the worker is actually started.
     75   void Start(int64 service_worker_version_id,
     76              const GURL& scope,
     77              const GURL& script_url,
     78              bool pause_after_download,
     79              const StatusCallback& callback);
     80 
     81   // Stops the worker. It is invalid to call this when the worker is
     82   // not in STARTING or RUNNING status.
     83   // This returns false if stopping a worker fails immediately, e.g. when
     84   // IPC couldn't be sent to the worker.
     85   ServiceWorkerStatusCode Stop();
     86 
     87   // Sends |message| to the embedded worker running in the child process.
     88   // It is invalid to call this while the worker is not in RUNNING status.
     89   ServiceWorkerStatusCode SendMessage(const IPC::Message& message);
     90 
     91   void ResumeAfterDownload();
     92 
     93   int embedded_worker_id() const { return embedded_worker_id_; }
     94   Status status() const { return status_; }
     95   int process_id() const { return process_id_; }
     96   int thread_id() const { return thread_id_; }
     97   int worker_devtools_agent_route_id() const {
     98     return worker_devtools_agent_route_id_;
     99   }
    100 
    101   void AddListener(Listener* listener);
    102   void RemoveListener(Listener* listener);
    103 
    104  private:
    105   typedef ObserverList<Listener> ListenerList;
    106 
    107   friend class EmbeddedWorkerRegistry;
    108   FRIEND_TEST_ALL_PREFIXES(EmbeddedWorkerInstanceTest, StartAndStop);
    109 
    110   // Constructor is called via EmbeddedWorkerRegistry::CreateWorker().
    111   // This instance holds a ref of |registry|.
    112   EmbeddedWorkerInstance(base::WeakPtr<ServiceWorkerContextCore> context,
    113                          int embedded_worker_id);
    114 
    115   // Called back from ServiceWorkerProcessManager after Start() passes control
    116   // to the UI thread to acquire a reference to the process.
    117   static void RunProcessAllocated(
    118       base::WeakPtr<EmbeddedWorkerInstance> instance,
    119       base::WeakPtr<ServiceWorkerContextCore> context,
    120       scoped_ptr<EmbeddedWorkerMsg_StartWorker_Params> params,
    121       const EmbeddedWorkerInstance::StatusCallback& callback,
    122       ServiceWorkerStatusCode status,
    123       int process_id);
    124   void ProcessAllocated(scoped_ptr<EmbeddedWorkerMsg_StartWorker_Params> params,
    125                         const StatusCallback& callback,
    126                         int process_id,
    127                         ServiceWorkerStatusCode status);
    128   // Called back after ProcessAllocated() passes control to the UI thread to
    129   // register to WorkerDevToolsManager.
    130   void SendStartWorker(scoped_ptr<EmbeddedWorkerMsg_StartWorker_Params> params,
    131                        const StatusCallback& callback,
    132                        int worker_devtools_agent_route_id,
    133                        bool wait_for_debugger);
    134 
    135   // Called back from Registry when the worker instance has ack'ed that
    136   // it is ready for inspection.
    137   void OnReadyForInspection();
    138 
    139   // Called back from Registry when the worker instance has ack'ed that
    140   // it finished loading the script and has started a worker thread.
    141   void OnScriptLoaded(int thread_id);
    142 
    143   // Called back from Registry when the worker instance has ack'ed that
    144   // it failed to load the script.
    145   void OnScriptLoadFailed();
    146 
    147   // Called back from Registry when the worker instance has ack'ed that
    148   // its WorkerGlobalScope is actually started and parsed.
    149   // This will change the internal status from STARTING to RUNNING.
    150   void OnStarted();
    151 
    152   void OnPausedAfterDownload();
    153 
    154   // Called back from Registry when the worker instance has ack'ed that
    155   // its WorkerGlobalScope is actually stopped in the child process.
    156   // This will change the internal status from STARTING or RUNNING to
    157   // STOPPED.
    158   void OnStopped();
    159 
    160   // Called back from Registry when the worker instance sends message
    161   // to the browser (i.e. EmbeddedWorker observers).
    162   // Returns false if the message is not handled.
    163   bool OnMessageReceived(const IPC::Message& message);
    164 
    165   // Called back from Registry when the worker instance reports the exception.
    166   void OnReportException(const base::string16& error_message,
    167                          int line_number,
    168                          int column_number,
    169                          const GURL& source_url);
    170 
    171   // Called back from Registry when the worker instance reports to the console.
    172   void OnReportConsoleMessage(int source_identifier,
    173                               int message_level,
    174                               const base::string16& message,
    175                               int line_number,
    176                               const GURL& source_url);
    177 
    178   base::WeakPtr<ServiceWorkerContextCore> context_;
    179   scoped_refptr<EmbeddedWorkerRegistry> registry_;
    180   const int embedded_worker_id_;
    181   Status status_;
    182 
    183   // Current running information. -1 indicates the worker is not running.
    184   int process_id_;
    185   int thread_id_;
    186   int worker_devtools_agent_route_id_;
    187 
    188   ListenerList listener_list_;
    189 
    190   base::WeakPtrFactory<EmbeddedWorkerInstance> weak_factory_;
    191 
    192   DISALLOW_COPY_AND_ASSIGN(EmbeddedWorkerInstance);
    193 };
    194 
    195 }  // namespace content
    196 
    197 #endif  // CONTENT_BROWSER_SERVICE_WORKER_EMBEDDED_WORKER_INSTANCE_H_
    198