如何从 service worker 对象调用 react class 的函数?

How to call a function of a react class from a service worker object?

我正在尝试使用我自己的服务工作者在反应网络中进行非侵入式更新。我想在网站有新更新时显示通知。我正在使用一个组件来处理服务工作者逻辑。问题是我不知道如何在服务工作者的事件侦听器中调用我的 class 的函数,其中 this 引用服务工作者本身。有小费吗?这是处理 service worker 的 class:

import * as React from 'react';
import { RouteComponentProps } from 'react-router';

export class ServiceWorker extends React.Component<RouteComponentProps<{}>> {
    constructor() {
        super();
    }

    registerServiceWorker() {
        if ('serviceWorker' in navigator) {
            window.addEventListener('load', () => {
                navigator.serviceWorker.register('/ServiceWorker.js').then(reg => {
                    console.log('SW registered: ', reg);
                    if (!navigator.serviceWorker.controller) {
                        return;
                    }
                    if (reg.waiting) {
                        console.log("update ready1");
                        //Can call updateAlert() here, because still using the same object
                        this.updateAlert();
                        return;
                    }

                    if (reg.installing) {
                        reg.installing.addEventListener('statechange', () => {
                            if (reg.installing.state == 'installed') {
                                console.log("update ready2");
                                //Can't call here
                                //this.updateAlert();
                            }
                        });
                        return;
                    }

                    reg.addEventListener('updatefound', function () {
                        reg.installing.addEventListener('statechange', () => {
                            if (reg.installing) {
                                if (reg.installing.state == 'installed') {
                                    console.log("update ready3");
                                    //or here
                                    //this.updateAlert();
                                }
                            }
                            if (reg.waiting) {
                                if (reg.waiting.state == 'installed') {
                                    console.log("update ready4");
                                    //or here
                                    //this.updateAlert();
                                }
                            }
                        });
                    })
                }).catch(registrationError => {
                    console.log('SW registration failed: ', registrationError);
                });
            });
        }
    }

    updateAlert() {
        console.log("success");
    }

    public render() {
        this.registerServiceWorker();
        return null;
    }
}

您或许可以尝试使用箭头函数来使用 class 的作用域:registerServiceWorker = () => { ... }

顺便说一下,如果您只想添加一次事件侦听器,那么在渲染中调用 this.registerServiceWorker(); 可能不是一个好主意,请尝试在 componentDidMount 中调用它。