Git Product home page Git Product logo

service_worker's Introduction

Service Worker API for Dart

Dart-y wrappers for the ServiceWorker APIs.

Warning: the API is experimental, and subject to change.

Service Workers

A service worker is an event-driven worker registered against an origin and a path. It takes the form of a JavaScript file that can control the web page/site it is associated with, intercepting and modifying navigation and resource requests, and caching resources in a very granular fashion to give you complete control over how your app behaves in certain situations (the most obvious one being when the network is not available.)

A service worker is run in a worker context: it therefore has no DOM access, and runs on a different thread to the main JavaScript that powers your app, so it is not blocking. It is designed to be fully async; as a consequence, APIs such as synchronous XHR and localStorage can't be used inside a service worker.

Quickstart

Register the Service Worker from your application script, like in example/web/main.dart:

import 'package:service_worker/window.dart' as sw;

void main() {
  if (sw.isSupported) {
    sw.register('sw.dart.js');
  } else {
    print('ServiceWorkers are not supported.');
  }
}

Write the Service Worker in a separate script, like in example/web/sw.dart:

import 'package:service_worker/service_worker.dart';

void main(List<String> args) {
  onInstall.listen((event) {
    print('ServiceWorker installed.');
  });
}

Limitation

You need to force dart2js compilation for service worker to work during debug mode. See build.yaml in the example folder.

service_worker's People

Contributors

alextekartik avatar gmpassos avatar isoos avatar kevmoo avatar lejard-h avatar leonsenft avatar matanlurey avatar srawlins avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar

service_worker's Issues

Getting runtime errors casting List<T>

With Dart VM version: 2.0.0-dev.53.0+

promiseToFuture doesn't work with List<T> – you can't just do value as T you have to do (value as List).cast<TItemValue>()

library broken?

I could not get the example to work - "MAIN: ServiceWorkers are not supported."
My gut feeling is that this is broken upstream in the dart sdk, e.g:
dart-lang/sdk#34228

@isoos - could you confirm that there is a problem and if so indicate that in the top level readme.
This will save people time.

Remove uses of package:func.

This package is no longer needed with the new generic function syntax.

You will need an environment of >=2.0.0-dev, but that's probably OK at this point.

The internal version has been patched to remove pkg/func, so we need this to ever sync again.

Cannot read property 'new' of undefined

Hello,
I am getting errors in the example.
I just changed
import 'package:service_worker/service_worker.dart';
to
import 'package:service_worker/worker.dart';

And I am getting the following in the web console:
`
MAIN: registereddart_sdk.js:18740
MAIN: ready dart_sdk.js:18740
MAIN: Sending message: Sample message: 2019-06-18 10:52:26.908 dart_sdk.js:18740
MAIN: Message sent: Sample message: 2019-06-18 10:52:26.908 main.dart:34

Uncaught (in promise) TypeError: Cannot read property 'new' of undefined
`

Where new is used there:

var subs = await registration.pushManager .subscribe(new sw.PushSubscriptionOptions(userVisibleOnly: true));

Importing! service_worker breaks my app

Hi, I'm playing with your service_worker (Thanks for the lib) but unfortunately just importing service_worker/window.dart breaks my app. Very strange! I made a video to demonstrate the problem - see below (I had to ZIP it because GH does not accept MP4s anymore)

Here is the GH-Repo: https://github.com/MikeMitterer/dart-sunshine
Master works but the test_cast_error branch fails: https://github.com/MikeMitterer/dart-sunshine/tree/test_cast_error

If you click on "Settings" it replaces the the "Content-Area" (https://goo.gl/HIegNL) with another view. (it replaces this area in DOM) (https://goo.gl/o6S9Ww)

dart_bug-service_worker.mp4.zip

Allow Responses to be constructed with a body/headers

The platform Response type has a default constructor.

I am trying to write an interface that can cache to a File or browser cache and am a bit stuck without the ability to construct a response myself. I have a workaround in mind but it breaks the semantics of the cache being a local resource since I'll have to allow it to handle the fetching so it can instantiate a Response.

Provide getter for delegate in ServiceWorkerRegistration

Hi Istvan,
thank you very much for the great library!

I am now implementing a Firebase cloud messaging to firebase-dart and in some point of the time, I would love to have a native JavaScript object for ServiceWorkerRegistration. The reason is, that I need to call the messaging.useServiceWorker() method in my wrapper which calls the useServiceWorker() from JavaScript but I need to have the JavaScript ServiceWorkerRegistration object - which is your facade.ServiceWorkerRegistration :-)

And it would be great to have the getter for _delegate. Then I can do this:

import 'package:service_worker/window.dart' as sw;

dynamic useServiceWorker(sw.ServiceWorkerRegistration registration) =>
      jsObject.useServiceWorker(registration.deletage);

Would it be a problem to have a getter for _delegate?

Thanks!

TypeError: null: type 'JSNull' is not a subtype of type 'Object' (simple repro using stock example project)

I am getting a TypeError exception when I use postMessage.

Steps to reproduce the issue:

  1. Import the service_worker repo in VS Code
  2. Open the example project and modify the sw.dart code to look like:
...
onActivate.listen(ExtendableEvent event) {
  // add this line
  ServiceWorkerGlobalScope.self.clients.claim();
}
onFetch.listen(FetchEvent event) {
  ...
  console.log('Fetch request for ...');
  // add this line
  event.client.postMessage('test');
}
...
  1. Start a debug session (I use Chrome, Flutter 3.19.3, VS Code 1.87.2, Dart tools 3.84.0 on Windows 11)
  2. A web page will be open and display Your Dart app is running. Open your Developer console to see details
  3. Open the Chrome DevTools console
  4. Observe that the following exception occurred:
Uncaught TypeError: null: type 'JSNull' is not a subtype of type 'Object': core_patch.dart:278
at Object.wrapException (js_helper.dart:1196:37)
at Rti._asObject [as _as] (rti.dart:1463:3)
at main_closure1.call$1 (service_worker_api.dart:1110:39)
at _RootZone.runUnaryGuarded$1$2 (zone.dart:1594:9)
at _BroadcastSubscription._sendData$1 (stream_impl.dart:339:5)
at _BroadcastSubscription._add$1 (stream_impl.dart:271:7)
at _SyncBroadcastStreamController._sendData$1 (broadcast_stream_controller.dart:377:7)
at callbackToStream_closure.call$1 (broadcast_stream_controller.dart:244:5)
at Object.Primitives_applyFunction (js_helper.dart:921:11)
at _callDartFunctionFast (core_patch.dart:88:23)

The fetch event handler is indeed called (you will see Fetch request for ... in the console), but the postMessage line raises an exception, so it is not possible to communicate something from the SW back to the main page.

dart2js causes lots of warnings

[Info from Dart2JS]:
Compiling datingnode_angular|web/pwa.dart...
[Warning from Dart2JS on datingnode_angular|web/pwa.dart]:
web/packages/service_worker/src/service_worker_api.dart:613:3:
The type 'int' of getter 'timeStamp' declared in 'ExtendableEvent' is not assignable to the type 'double' of the overridden field inherited from 'Event'.
  int get timeStamp => _getProperty(_delegate, 'timeStamp');
  ^^^^^^^^^^^^^^^^^
[Info from Dart2JS on datingnode_angular|web/pwa.dart]:
web/packages/$sdk/lib/html/dart2js/html_dart2js.dart:16646:16:
This is the overridden field 'timeStamp' declared in class 'Event'.
  final double timeStamp;
               ^^^^^^^^^
[Warning from Dart2JS on datingnode_angular|web/pwa.dart]:
web/packages/service_worker/src/service_worker_api.dart:597:1:
'ExtendableEvent' doesn't implement the getter 'isTrusted' declared in 'Event'.
Try adding an implementation of 'isTrusted' or declaring 'ExtendableEvent' to be 'abstract'.
class ExtendableEvent implements Event {
^^^^^
[Info from Dart2JS on datingnode_angular|web/pwa.dart]:
web/packages/$sdk/lib/html/dart2js/html_dart2js.dart:16612:14:
The getter 'isTrusted' is implicitly declared by this field in class 'Event'.
  final bool isTrusted;
             ^^^^^^^^^
[Warning from Dart2JS on datingnode_angular|web/pwa.dart]:
web/packages/service_worker/src/service_worker_api.dart:597:1:
'ExtendableEvent' doesn't implement the getter 'scoped' declared in 'Event'.
Try adding an implementation of 'scoped' or declaring 'ExtendableEvent' to be 'abstract'.
class ExtendableEvent implements Event {
^^^^^
[Info from Dart2JS on datingnode_angular|web/pwa.dart]:
web/packages/$sdk/lib/html/dart2js/html_dart2js.dart:16632:14:
The getter 'scoped' is implicitly declared by this field in class 'Event'.
  final bool scoped;
             ^^^^^^
[Warning from Dart2JS on datingnode_angular|web/pwa.dart]:
web/packages/service_worker/src/service_worker_api.dart:597:1:
'ExtendableEvent' doesn't implement 'List<EventTarget> deepPath()' declared in 'Event'.
Try adding an implementation of 'deepPath' or declaring 'ExtendableEvent' to be 'abstract'.
class ExtendableEvent implements Event {
^^^^^
[Info from Dart2JS on datingnode_angular|web/pwa.dart]:
web/packages/$sdk/lib/html/dart2js/html_dart2js.dart:16655:3:
The method 'deepPath' is declared here in class 'Event'.
  List<EventTarget> deepPath() native;
  ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
[Warning from Dart2JS on datingnode_angular|web/pwa.dart]:
web/packages/service_worker/src/service_worker_api.dart:731:1:
'InstallEvent' doesn't implement the getter 'isTrusted' declared in 'Event'.
Try adding an implementation of 'isTrusted' or declaring 'InstallEvent' to be 'abstract'.
class InstallEvent extends ExtendableEvent {
^^^^^
[Info from Dart2JS on datingnode_angular|web/pwa.dart]:
web/packages/$sdk/lib/html/dart2js/html_dart2js.dart:16612:14:
The getter 'isTrusted' is implicitly declared by this field in class 'Event'.
  final bool isTrusted;
             ^^^^^^^^^
[Warning from Dart2JS on datingnode_angular|web/pwa.dart]:
web/packages/service_worker/src/service_worker_api.dart:731:1:
'InstallEvent' doesn't implement the getter 'scoped' declared in 'Event'.
Try adding an implementation of 'scoped' or declaring 'InstallEvent' to be 'abstract'.
class InstallEvent extends ExtendableEvent {
^^^^^
[Info from Dart2JS on datingnode_angular|web/pwa.dart]:
web/packages/$sdk/lib/html/dart2js/html_dart2js.dart:16632:14:
The getter 'scoped' is implicitly declared by this field in class 'Event'.
  final bool scoped;
             ^^^^^^
[Warning from Dart2JS on datingnode_angular|web/pwa.dart]:
web/packages/service_worker/src/service_worker_api.dart:731:1:
'InstallEvent' doesn't implement 'List<EventTarget> deepPath()' declared in 'Event'.
Try adding an implementation of 'deepPath' or declaring 'InstallEvent' to be 'abstract'.
class InstallEvent extends ExtendableEvent {
^^^^^
[Info from Dart2JS on datingnode_angular|web/pwa.dart]:
web/packages/$sdk/lib/html/dart2js/html_dart2js.dart:16655:3:
The method 'deepPath' is declared here in class 'Event'.
  List<EventTarget> deepPath() native;
  ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
[Warning from Dart2JS on datingnode_angular|web/pwa.dart]:
web/packages/service_worker/src/service_worker_api.dart:847:1:
'NotificationEvent' doesn't implement the getter 'isTrusted' declared in 'Event'.
Try adding an implementation of 'isTrusted' or declaring 'NotificationEvent' to be 'abstract'.
class NotificationEvent extends ExtendableEvent {
^^^^^
[Info from Dart2JS on datingnode_angular|web/pwa.dart]:
web/packages/$sdk/lib/html/dart2js/html_dart2js.dart:16612:14:
The getter 'isTrusted' is implicitly declared by this field in class 'Event'.
  final bool isTrusted;
             ^^^^^^^^^
[Warning from Dart2JS on datingnode_angular|web/pwa.dart]:
web/packages/service_worker/src/service_worker_api.dart:847:1:
'NotificationEvent' doesn't implement the getter 'scoped' declared in 'Event'.
Try adding an implementation of 'scoped' or declaring 'NotificationEvent' to be 'abstract'.
class NotificationEvent extends ExtendableEvent {
^^^^^
[Info from Dart2JS on datingnode_angular|web/pwa.dart]:
web/packages/$sdk/lib/html/dart2js/html_dart2js.dart:16632:14:
The getter 'scoped' is implicitly declared by this field in class 'Event'.
  final bool scoped;
             ^^^^^^
[Warning from Dart2JS on datingnode_angular|web/pwa.dart]:
web/packages/service_worker/src/service_worker_api.dart:847:1:
'NotificationEvent' doesn't implement 'List<EventTarget> deepPath()' declared in 'Event'.
Try adding an implementation of 'deepPath' or declaring 'NotificationEvent' to be 'abstract'.
class NotificationEvent extends ExtendableEvent {
^^^^^
[Info from Dart2JS on datingnode_angular|web/pwa.dart]:
web/packages/$sdk/lib/html/dart2js/html_dart2js.dart:16655:3:
The method 'deepPath' is declared here in class 'Event'.
  List<EventTarget> deepPath() native;
  ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
[Warning from Dart2JS on datingnode_angular|web/pwa.dart]:
web/packages/service_worker/src/service_worker_api.dart:866:1:
'PushEvent' doesn't implement the getter 'isTrusted' declared in 'Event'.
Try adding an implementation of 'isTrusted' or declaring 'PushEvent' to be 'abstract'.
class PushEvent extends ExtendableEvent {
^^^^^
[Info from Dart2JS on datingnode_angular|web/pwa.dart]:
web/packages/$sdk/lib/html/dart2js/html_dart2js.dart:16612:14:
The getter 'isTrusted' is implicitly declared by this field in class 'Event'.
  final bool isTrusted;
             ^^^^^^^^^
[Warning from Dart2JS on datingnode_angular|web/pwa.dart]:
web/packages/service_worker/src/service_worker_api.dart:866:1:
'PushEvent' doesn't implement the getter 'scoped' declared in 'Event'.
Try adding an implementation of 'scoped' or declaring 'PushEvent' to be 'abstract'.
class PushEvent extends ExtendableEvent {
^^^^^
[Info from Dart2JS on datingnode_angular|web/pwa.dart]:
web/packages/$sdk/lib/html/dart2js/html_dart2js.dart:16632:14:
The getter 'scoped' is implicitly declared by this field in class 'Event'.
  final bool scoped;
             ^^^^^^
[Warning from Dart2JS on datingnode_angular|web/pwa.dart]:
web/packages/service_worker/src/service_worker_api.dart:866:1:
'PushEvent' doesn't implement 'List<EventTarget> deepPath()' declared in 'Event'.
Try adding an implementation of 'deepPath' or declaring 'PushEvent' to be 'abstract'.
class PushEvent extends ExtendableEvent {
^^^^^
[Info from Dart2JS on datingnode_angular|web/pwa.dart]:
web/packages/$sdk/lib/html/dart2js/html_dart2js.dart:16655:3:
The method 'deepPath' is declared here in class 'Event'.
  List<EventTarget> deepPath() native;
  ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
[Warning from Dart2JS on datingnode_angular|web/pwa.dart]:
web/packages/service_worker/src/service_worker_api.dart:689:3:
The type 'int' of getter 'timeStamp' declared in 'FetchEvent' is not assignable to the type 'double' of the overridden field inherited from 'Event'.
  int get timeStamp => _getProperty(_delegate, 'timeStamp');
  ^^^^^^^^^^^^^^^^^
[Info from Dart2JS on datingnode_angular|web/pwa.dart]:
web/packages/$sdk/lib/html/dart2js/html_dart2js.dart:16646:16:
This is the overridden field 'timeStamp' declared in class 'Event'.
  final double timeStamp;
               ^^^^^^^^^
[Warning from Dart2JS on datingnode_angular|web/pwa.dart]:
web/packages/service_worker/src/service_worker_api.dart:656:1:
'FetchEvent' doesn't implement the getter 'isTrusted' declared in 'Event'.
Try adding an implementation of 'isTrusted' or declaring 'FetchEvent' to be 'abstract'.
class FetchEvent implements Event {
^^^^^
[Info from Dart2JS on datingnode_angular|web/pwa.dart]:
web/packages/$sdk/lib/html/dart2js/html_dart2js.dart:16612:14:
The getter 'isTrusted' is implicitly declared by this field in class 'Event'.
  final bool isTrusted;
             ^^^^^^^^^
[Warning from Dart2JS on datingnode_angular|web/pwa.dart]:
web/packages/service_worker/src/service_worker_api.dart:656:1:
'FetchEvent' doesn't implement the getter 'scoped' declared in 'Event'.
Try adding an implementation of 'scoped' or declaring 'FetchEvent' to be 'abstract'.
class FetchEvent implements Event {
^^^^^
[Info from Dart2JS on datingnode_angular|web/pwa.dart]:
web/packages/$sdk/lib/html/dart2js/html_dart2js.dart:16632:14:
The getter 'scoped' is implicitly declared by this field in class 'Event'.
  final bool scoped;
             ^^^^^^
[Warning from Dart2JS on datingnode_angular|web/pwa.dart]:
web/packages/service_worker/src/service_worker_api.dart:656:1:
'FetchEvent' doesn't implement 'List<EventTarget> deepPath()' declared in 'Event'.
Try adding an implementation of 'deepPath' or declaring 'FetchEvent' to be 'abstract'.
class FetchEvent implements Event {
^^^^^
[Info from Dart2JS on datingnode_angular|web/pwa.dart]:
web/packages/$sdk/lib/html/dart2js/html_dart2js.dart:16655:3:
The method 'deepPath' is declared here in class 'Event'.
  List<EventTarget> deepPath() native;
  ^^^^^^^^^^^^^^^^^^^^^^^^^^^^

Do you get these as well?
Did you try to get rid of them?

_delegate in PushMessageData is null , unable to get gcm message data

Hi István,

I change code in worker.dart
and the log seems show that: PushMessageData . _delegate is null
can you help with this?
Many Thanks.

onFetch.listen((FetchEvent event) {
if (worker.pushHandler != null) {
onPush.listen((PushEvent event) {
PushMessageData data = event.data;

print(data == null); --> false
print(data.text()); --> NullError: method not found: 'text' on null. js_primitives.dart:30

Future f = worker.pushHandler(new PushContext());
if (f != null) {
event.waitUntil(f.then((
) => null, onError: (_) => null));
}
});
}

print(data.text()); --> NullError: method not found: 'text' on null. js_primitives.dart:30

class PushMessageData {
// Masked type: facade.PushMessageData
final delegate;
PushMessageData.
(this._delegate);

/// Extracts the data as a plain text string.
String text() => _callMethod(_delegate, 'text', []);
}

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.