您的位置:澳门新葡8455最新网站 > Web前端 > 连不上网

连不上网

发布时间:2019-10-11 09:45编辑:Web前端浏览(116)

    Service Worker初体验

    2016/01/06 · JavaScript · Service Worker

    原来的书文出处: AlloyTeam   

    在二零一五年,W3C公布了service worker的草案,service worker提供了不菲新的工夫,使得web app具有与native app同样的离线体验、音讯推送体验。
    service worker是一段脚本,与web worker同样,也是在后台运维。作为三个独立的线程,运维情状与常见脚本分歧,所以不能够直接参加web交互行为。native app能够变成离线使用、音信推送、后台自动更新,service worker的产出是幸好为了使得web app也可以具备类似的力量。

     

    service worker可以:

    1. 后台音信传递
    2. 互连网代理,转载呼吁,伪造响应
    3. 离线缓存
    4. 音信推送
    5.  … …

    正文以财富缓存为例,说澳优(Ausnutria Hyproca)下service worker是何等工作的。

    连不上网?United Kingdom卫报的特性离线页面是这么做的

    2015/11/20 · HTML5 · Service Worker, 离线页面

    本文由 伯乐在线 - Erucy 翻译,weavewillg 校稿。未经许可,防止转载!
    塞尔维亚(Република Србија)语出处:Oliver Ash。欢迎到场翻译组。

    小编们是何许行使 service worker 来为 theguardian.com 创设一个自定义的离线页面。

    图片 1

    theguardian.com 的离线页面。插图:奥利弗 Ash

    你正在朝着公司途中的地铁里,在手提式有线电话机上张开了 Guardian 应用。大巴被隧道包围着,然则那一个动用能够符合规律运维,即使未有互联网连接,你也能博得完全的效应,除了显示的剧情或然有一点旧。假设你品尝在网址上也那样干,缺憾它完全没法加载:

    图片 2

    安卓版 Chrome 的离线页面

    Chrome 中的那么些彩蛋,相当多少人都不领悟》

    Chrome 在离线页面上有个暗藏的游戏(桌面版上按空格键,手机版上点击那只恐龙),那有一点能缓慢化解一点你的烦心。可是我们能够做得越来越好。

    Service workers 允许网址小编拦截自身站点的有所互连网央求,那也就代表大家能够提供完善的离线体验,就如原生应用一样。在 Guardian 网址,大家多年来上线了七个自定义的离线体验效果。当客商离线的时候,他们会看到多个包涵Guardian 标志的页面,上边带有二个轻松易行的离线提醒,还会有三个填字游戏,他们得以在等候网络连接的时候玩玩这些找点乐子。那篇博客解释了我们是怎么营造它的,不过在起来此前,你能够先自个儿探寻看。

    生命周期

    先来看一下一个service worker的运营周期

    图片 3
    上航海用体育场合是service worker生命周期,出处

    图中得以见到,三个service worker要经历以下进度:

    1.  安装

    2.  激活,激活成功今后,打开chrome://inspect/#service-workers能够查看见近期运转的service worker

    图片 4

    1. 监听fetch和message事件,上边三种事件会实行轻巧描述

    2. 销毁,是还是不是销毁由浏览器决定,倘诺二个service worker长时间不行使或然机器内部存款和储蓄器有数,则或许会销毁那个worker

    试试看

    您要求二个支持 Service Worker 和 fetch API 的浏览器。甘休到本文编写时唯有Chrome(手提式有线电话机版和桌面版)同不常间援救那三种 API(译者注:Opera 如今也补助那五头),可是 Firefox 非常的慢就要支持了(在每一日更新的版本中一度援救了),除开 Safari 之外的全部浏览器也都在探索。另外,service worker 只可以登记在行使了 HTTPS 的网址上,theguardian.com 已经起来慢慢搬迁到 HTTPS,所以我们只可以在网址的 HTTPS 部分提供离线体验。就现阶段以来,我们选用了 开拓者博客 作为我们用来测量检验的地点。所以倘若您是在我们网址的 开荒者博客 部分阅读这篇文章的话,很幸运。

    当您使用支持的浏览器访问我们的 开荒者博客 中的页面包车型大巴时候,一切就计划稳当了。断开你的网络连接,然后刷新一下页面。假如您自身没条件尝试的话,能够看一下这段 演示摄像(译者注:需梯子)。

    fetch事件

    在页面发起http央求时,service worker能够透过fetch事件拦截央浼,并且付诸本人的响应。
    w3c提供了二个新的fetch api,用于代替XMLHttpRequest,与XMLHttpRequest最大不一样有两点:

    1. fetch()方法再次来到的是Promise对象,通过then方法进行连接调用,裁减嵌套。ES6的Promise在改为正式之后,会更加的便利开荒人士。

    2. 提供了Request、Response对象,假诺做过后端开采,对Request、Response应该比较纯熟。前端要倡导呼吁能够透过url发起,也足以选取Request对象发起,并且Request能够复用。不过Response用在哪个地方呢?在service worker出现在此以前,前端确实不会友善给和煦发新闻,不过有了service worker,就足以在阻碍乞求之后听他们讲须要发回自个儿的响应,对页面来讲,那个日常的伏乞结果并从未分别,那是Response的一处采用。

    上面是在中,小编利用fetch api通过fliker的公然api获取图片的例子,注释中详细表明了每一步的效应:

    JavaScript

    /* 由于是get必要,直接把参数作为query string传递了 */ var URL = ''; function fetch德姆o() { // fetch(url, option)援救三个参数,option中得以设置header、body、method信息fetch(U索罗德L).then(function(response) { // 通过promise 对象获得对应内容,并且将响应内容根据json格式转成对象,json()方法调用之后回到的照样是promise对象 // 也能够把内容转化成arraybuffer、blob对象 return response.json(); }).then(function(json) { // 渲染页面 insertPhotos(json); }); } fetchDemo();

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    /* 由于是get请求,直接把参数作为query string传递了 */
    var URL = 'https://api.flickr.com/services/rest/?method=flickr.photos.search&api_key=your_api_key&format=json&nojsoncallback=1&tags=penguins';
     
    function fetchDemo() {
      // fetch(url, option)支持两个参数,option中可以设置header、body、method信息
      fetch(URL).then(function(response) {
        // 通过promise 对象获得相应内容,并且将响应内容按照json格式转成对象,json()方法调用之后返回的依然是promise对象
        // 也可以把内容转化成arraybuffer、blob对象
        return response.json();
      }).then(function(json) {
        // 渲染页面
        insertPhotos(json);
      });
    }
     
    fetchDemo();

    fetch api与XMLHttpRequest相比较,特别从简,并且提供的功用更全面,能源获得格局比ajax越来越高贵。包容性方面:chrome 42始发扶持,对于旧浏览器,可以经过合法维护的polyfill援助。

    做事原理

    通过一段简单的 JavaScript,大家得以提示浏览器在顾客访谈页面包车型地铁时候立刻登记大家相濡以沫的 service worker。这几天支撑 service worker 的浏览器少之甚少,所感到了防止不当,大家供给接纳性子检验。

    JavaScript

    if (navigator.serviceWorker) { navigator.serviceWorker.register('/service-worker.js'); }

    1
    2
    3
    if (navigator.serviceWorker) {
        navigator.serviceWorker.register('/service-worker.js');
    }

    Service worker 安装事件的一局部,大家得以动用 新的缓存 API 来缓存大家网址中的种种内容,举例 HTML、CSS 和 JavaScript:

    JavaScript

    var staticCacheName = 'static'; var version = 1; function updateCache() { return caches.open(staticCacheName + version) .then(function (cache) { return cache.addAll([ '/offline-page.html', '/assets/css/main.css', '/assets/js/main.js' ]); }); }; self.addEventListener('install', function (event) { event.waitUntil(updateCache()); });

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    var staticCacheName = 'static';
    var version = 1;
     
    function updateCache() {
        return caches.open(staticCacheName + version)
            .then(function (cache) {
                return cache.addAll([
                    '/offline-page.html',
                    '/assets/css/main.css',
                    '/assets/js/main.js'
                ]);
            });
    };
     
    self.addEventListener('install', function (event) {
        event.waitUntil(updateCache());
    });

    当安装到位后,service worker 能够监听和决定 fetch 事件,让大家得以完全调整之后网址中发生的有所网络央求。

    JavaScript

    self.addEventListener('fetch', function (event) { event.respondWith(fetch(event.request)); });

    1
    2
    3
    self.addEventListener('fetch', function (event) {
        event.respondWith(fetch(event.request));
    });

    在这里地我们有很灵巧的长空能够表达,比如下边这些节骨眼,能够经过代码来生成大家和好的供给响应:

    JavaScript

    self.addEventListener('fetch', function (event) { var response = new Response('<h1>Hello, World!</h1>', { headers: { 'Content-Type': 'text/html' } }); event.respondWith(response); });

    1
    2
    3
    4
    5
    self.addEventListener('fetch', function (event) {
        var response = new Response('&lt;h1&gt;Hello, World!&lt;/h1&gt;',
            { headers: { 'Content-Type': 'text/html' } });
        event.respondWith(response);
    });

    还可能有那几个,就算在缓存中找到了乞请相应的缓存,大家能够直接从缓存中回到它,假使没找到的话,再经过互联网获得响应内容:

    JavaScript

    self.addEventListener('fetch', function (event) { event.respondWith( caches.match(event.request) .then(function (response) { return response || fetch(event.request); }) ); });

    1
    2
    3
    4
    5
    6
    7
    8
    self.addEventListener('fetch', function (event) {
        event.respondWith(
            caches.match(event.request)
                .then(function (response) {
                    return response || fetch(event.request);
                })
        );
    });

    那么大家怎么利用那个职能来提供离线体验呢?

    率先,在 service worker 安装进程中,我们须要把离线页面须要的 HTML 和财富文件通过 service worker 缓存下来。在缓存中,大家加载了谐和支付的 填字游戏 的 React应用 页面。之后,大家会阻碍全体访问theguardian.com 网络央求,富含网页、以至页面中的财富文件。管理那一个央求的逻辑大概如下:

    1. 当我们检验到传播诉求是指向大家的 HTML 页面时,咱们连年会想要提供新型的剧情,所以我们会尝试把这么些诉求通过网络发送给服务器。
      1. 当大家从服务器获得了响应,就足以直接再次回到那一个响应。
      2. 假定网络央求抛出了要命(比方因为客商掉线了),我们捕获那么些那几个,然后使用缓存的离线 HTML 页面作为响应内容。
    2. 要不,当大家检查测量试验到乞求的不是 HTML 的话,大家会从缓存中检索响应的伸手内容。
      1. 假使找到了缓存内容,我们能够一向回到缓存的剧情。
      2. 要不然,大家会尝试把这么些央浼通过互联网发送给服务器。

    在代码中,大家应用了 新的缓存 API(它是 瑟维斯 Worker API 的一局地)以至 fetch 功效(用于转移网络央浼),如下所示:

    JavaScript

    var doesRequestAcceptHtml = function (request) { return request.headers.get('Accept') .split(',') .some(function (type) { return type === 'text/html'; }); }; self.addEventListener('fetch', function (event) { var request = event.request; if (doesRequestAcceptHtml(request)) { // HTML pages fallback to offline page event.respondWith( fetch(request) .catch(function () { return caches.match('/offline-page.html'); }) ); } else { // Default fetch behaviour // Cache first for all other requests event.respondWith( caches.match(request) .then(function (response) { return response || fetch(request); }) ); } });

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    var doesRequestAcceptHtml = function (request) {
        return request.headers.get('Accept')
            .split(',')
            .some(function (type) { return type === 'text/html'; });
    };
     
    self.addEventListener('fetch', function (event) {
        var request = event.request;
        if (doesRequestAcceptHtml(request)) {
            // HTML pages fallback to offline page
            event.respondWith(
                fetch(request)
                    .catch(function () {
                        return caches.match('/offline-page.html');
                    })
            );
        } else {
            // Default fetch behaviour
            // Cache first for all other requests
            event.respondWith(
                caches.match(request)
                    .then(function (response) {
                        return response || fetch(request);
                    })
            );
        }
    });

    就只要求如此多!theguardian.com 上的 有着代码都以在 GitHub 上开源 的,所以你能够去那儿查看大家的 service worker 的完好版本,大概直接从生产意况上访谈 。

    小编们有足够的理由为这几个新的浏览器技能欢呼喝彩,因为它能够用来令你的网址像前日的原生应用一样,具有完美的离线体验。以往当 theguardian.com 完全迁移到 HTTPS 之后,离线页面包车型客车重大性会鲜明扩展,大家能够提供越发周全的离线体验。虚构一下您在上下班途中互连网比较不佳的时候访问theguardian.com,你会见到特意为您订制的个性化内容,它们是在您从前访谈网址时由浏览器缓存下来的。它在安装进程中也不会产生此外劳顿,你所急需的只是访问那几个网址而已,不像原生应用,还需求客商有贰个选用商城的账号才能安装。Serviceworker 一样可以扶助大家进步网址的加载速度,因为网址的框架能够被保险地缓存下来,就如原生应用一样。

    比如您对 service worker 很感兴趣,想要领会更加多内容的话,开垦者 马特Gaunt(Chrome的忠诚补助者)写了一篇特别详细地 介绍 Service Worker的文章。

    打赏帮忙作者翻译越来越多好小说,多谢!

    打赏译者

    message事件

    页面和serviceWorker之间能够透过posetMessage()方法发送消息,发送的音讯能够通过message事件接收到。

    那是四个双向的进度,页面可以发音讯给service worker,service worker也得以发送消息给页面,由于那些特点,能够将service worker作为中间纽带,使得八个域名依然子域名下的八个页面能够随性所欲通讯。

    此地是一个小的页面之间通信demo

    打赏帮忙本身翻译越来越多好小说,感谢!

    图片 5

    1 赞 收藏 评论

    行使service workder缓存文件

    上边介绍八个应用service worker缓存离线文件的例子
    策动index.js,用于注册service-worker

    JavaScript

    if (navigator.serviceWorker) { navigator.serviceWorker.register('service-worker.js').then(function(registration) { console.log('service worker 注册成功'); }).catch(function (err) { console.log('servcie worker 注册失利') }); }

    1
    2
    3
    4
    5
    6
    7
    if (navigator.serviceWorker) {
        navigator.serviceWorker.register('service-worker.js').then(function(registration) {
            console.log('service worker 注册成功');
        }).catch(function (err) {
            console.log('servcie worker 注册失败')
        });
    }

    在上述代码中,注册了service-worker.js作为当下路线下的service worker。由于service worker的权力极高,全体的代码都亟待是安全可相信的,所以独有https站点才可以使用service worker,当然localhost是三个特例。
    登记截至,未来启幕写service-worker.js代码。
    依据前边的生命周期图,在四个新的service worker被注册之后,首先会触发install事件,在service-workder.js中,能够透过监听install事件开展部分伊始化学工业作,或然哪些也不做。
    因为大家是要缓存离线文件,所以能够在install事件中初步缓存,可是只是将文件加到caches缓存中,真正想让浏览器采取缓存文件须要在fetch事件中阻止

    JavaScript

    var cacheFiles = [ 'about.js', 'blog.js' ]; self.addEventListener('install', function (evt) { evt.waitUntil( caches.open('my-test-cahce-v1').then(function (cache) { return cache.addAll(cacheFiles); }) ); });

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    var cacheFiles = [
        'about.js',
        'blog.js'
    ];
    self.addEventListener('install', function (evt) {
        evt.waitUntil(
            caches.open('my-test-cahce-v1').then(function (cache) {
                return cache.addAll(cacheFiles);
            })
        );
    });

    第一定义了供给缓存的公文数组cacheFile,然后在install事件中,缓存那个文件。
    evt是五个Install伊夫nt对象,承袭自Extendable伊夫nt,在那之中的waitUntil()方法接收二个promise对象,直到这几个promise对象成功resolve之后,才会一而再运营service-worker.js。
    caches是一个CacheStorage对象,使用open()方法展开一个缓存,缓存通过名称举行区分。
    赢得cache实例之后,调用addAll()方法缓存文件。

    这么就将文件增加到caches缓存中了,想让浏览器选用缓存,还亟需拦截fetch事件

    JavaScript

    // 缓存图片 self.add伊夫ntListener('fetch', function (evt) { evt.respondWith( caches.match(evt.request).then(function(response) { if (response) { return response; } var request = evt.request.clone(); return fetch(request).then(function (response) { if (!response && response.status !== 200 && !response.headers.get('Content-type').match(/image/)) { return response; } var responseClone = response.clone(); caches.open('my-test-cache-v1').then(function (cache) { cache.put(evt.request, responseClone); }); return response; }); }) ) });

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    // 缓存图片
    self.addEventListener('fetch', function (evt) {
        evt.respondWith(
            caches.match(evt.request).then(function(response) {
                if (response) {
                    return response;
                }
                var request = evt.request.clone();
                return fetch(request).then(function (response) {
                    if (!response && response.status !== 200 && !response.headers.get('Content-type').match(/image/)) {
                        return response;
                    }
                    var responseClone = response.clone();
                    caches.open('my-test-cache-v1').then(function (cache) {
                        cache.put(evt.request, responseClone);
                    });
                    return response;
                });
            })
        )
    });

    通过监听fetch事件,service worker能够回来本人的响应。

    率先检缓存中是或不是曾经缓存了那几个央求,纵然有,就径直回到响应,就收缩了叁次互联网央求。不然由service workder发起伏乞,那时的service workder起到了二个中路代理的功能。

    service worker恳求的经过通过fetch api达成,获得response对象今后举办过滤,查看是不是是图片文件,假如不是,就径直再次来到央求,不会缓存。

    一旦是图表,要先复制一份response,原因是request或然response对象属于stream,只可以利用三遍,之后一份存入缓存,另一份发送给页面。
    那正是service worker的有力之处:拦截诉求,伪造响应。fetch api在此边也起到了很大的坚守。

     

    service worker的更新很简单,只要service-worker.js的文书内容有更新,就可以动用新的本子。不过有几许要专注:旧缓存文件的化解、新文件的缓存要在activate事件中开展,因为只怕旧的页面还在利用在此以前的缓存文件,清除之后会失去作用。

     

    在第一使用service worker的经过中,也越过了有的标题,下边是其中多少个

    有关作者:Erucy

    图片 6

    现已的SharePoint喵星程序猿(临时还挂着微软MVP的名头),以往的Azure/.Net/MongoDB/Cordova/前端技术员,有的时候写小说 个人主页 · 小编的篇章 · 46 ·   

    图片 7

    难点1. 运维时刻

    service worker并非直接在后台运转的。在页面关闭后,浏览器可以接二连三保险service worker运维,也足以关闭service worker,那取决与浏览器本人的表现。所以并不是定义一些全局变量,举个例子下边包车型大巴代码(来自):

    JavaScript

    var hitCounter = 0; this.addEventListener('fetch', function(event) { hitCounter++; event.respondWith( new Response('Hit number ' + hitCounter) ); });

    1
    2
    3
    4
    5
    6
    7
    8
    var hitCounter = 0;
     
    this.addEventListener('fetch', function(event) {
      hitCounter++;
      event.respondWith(
        new Response('Hit number ' + hitCounter)
      );
    });

    回去的结果可能是未曾规律的:1,2,1,2,1,1,2….,原因是hitCounter并从未平素留存,假设浏览器关闭了它,下次起步的时候hitCounter就赋值为0了
    那般的政工导致调节和测试代码困难,当你更新贰个service worker现在,唯有在开拓新页面以往才恐怕应用新的service worker,在调试进程中不常等上一两分钟才会选择新的,比较抓狂。

    主题素材2. 权力太大

    当service worker监听fetch事件今后,对应的呼吁都会经过service worker。通过chrome的network工具,能够看看此类央浼会标注:from service worker。假如service worker中冒出了难点,会导致全部需要战败,包涵普通的html文件。所以service worker的代码品质、容错性绝对要很好技巧确定保障web app不荒谬运作。

     

    参照文章:

    1. 

    2. 

    3. 

    4. 

    5. 

    1 赞 3 收藏 评论

    图片 8

    本文由澳门新葡8455最新网站发布于Web前端,转载请注明出处:连不上网

    关键词: