您的位置:澳门402永利com > 前端技术 > 连不上网

连不上网

发布时间:2019-11-12 08:13编辑:前端技术浏览(162)

    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.  … …

    正文以能源缓存为例,说美赞臣下service worker是哪些做事的。

    连不上网?英帝国卫报的天性离线页面是这样做的

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

    本文由 伯乐在线 - Erucy 翻译,weavewillg 校稿。未经许可,防止转发!
    立陶宛共和国(Republic of Lithuania卡塔尔语出处:Oliver Ash。迎接出席翻译组。

    我们是什么运用 service worker 来为 theguardian.com 构建三个自定义的离线页面。

    图片 1

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

    你正在朝着公司途中的大巴里,在三弟大上开采了 Guardian 应用。大巴被隧道包围着,然则这一个利用能够健康运维,即便未有互连网连接,你也能得到完全的效果,除了出示的剧情也可以有一点点旧。倘使你尝试在网站上也如此干,缺憾它完全没办法加载:

    图片 2

    安卓版 Chrome 的离线页面

    Chrome 中的这几个彩蛋,超级多少人都不领悟》

    Chrome 在离线页面上有个藏匿的玩耍(桌面版上按空格键,手机版上点击那只恐龙卡塔 尔(英语:State of Qatar),那有个别能减轻一点您的超慢。可是大家可以做得更好。

    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 异常快将在援救了(在每一日更新的本子中豆蔻梢头度支撑了卡塔 尔(英语:State of Qatar),除此之外 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(UQashqaiL).then(function(response) { // 通过promise 对象获得对应内容,而且将响应内容依照json格式转成对象,json()方法调用之后回来的依旧是promise对象 // 也足以把内容转形成arraybuffer、blob对象 return response.json(); }).then(function(json) { // 渲染页面 insertPhotos(json); }); } fetch德姆o();

    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. 假设网络央浼抛出了老大(举例因为客户掉线了卡塔 尔(英语:State of Qatar),大家捕获那些可怜,然后接纳缓存的离线 HTML 页面作为响应内容。
    2. 要不,当大家检验到诉求的不是 HTML 的话,大家会从缓存中寻找响应的乞请内容。
      1. 万后生可畏找到了缓存内容,大家得以向来回到缓存的源委。
      2. 再不,大家会尝试把这些央浼通过互连网发送给服务器。

    在代码中,我们采取了 新的缓存 API(它是 Service 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对象,世襲自ExtendableEvent,在那之中的waitUntil()方法接纳三个promise对象,直到这么些promise对象成功resolve之后,才会持续运维service-worker.js。
    caches是二个CacheStorage对象,使用open()方法张开一个缓存,缓存通过名称进行区分。
    收获cache实例之后,调用addAll()方法缓存文件。

    如此那般就将文件增添到caches缓存中了,想让浏览器接受缓存,还索要拦截fetch事件

    JavaScript

    // 缓存图片 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; }); }) ) });

    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的名头卡塔 尔(英语:State of Qatar),今后的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

    本文由澳门402永利com发布于前端技术,转载请注明出处:连不上网

    关键词:

上一篇:前端本地文件操作与上传,web前端学习

下一篇:没有了