Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/javascript/376.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Javascript 在触发操作时执行函数_Javascript_Reactjs_Rxjs_Rxjs5_Redux Observable - Fatal编程技术网

Javascript 在触发操作时执行函数

Javascript 在触发操作时执行函数,javascript,reactjs,rxjs,rxjs5,redux-observable,Javascript,Reactjs,Rxjs,Rxjs5,Redux Observable,我想在触发takeUntil操作符时执行一个函数(在ajaxObservable之外)。立即被激发,因为我调用了observer.complete(),但如果我不调用它,就会出现内存泄漏,对吗? 实现这一目标的好方法是什么 export const ajaxObservable = (url, method, data, params) => { let cancelToken = axios.CancelToke.source() return Observable

我想在触发takeUntil操作符时执行一个函数(在ajaxObservable之外)。立即被激发,因为我调用了observer.complete(),但如果我不调用它,就会出现内存泄漏,对吗?
实现这一目标的好方法是什么

export const ajaxObservable = (url, method, data, params) => {
    let cancelToken = axios.CancelToke.source()
    return Observable
        .fromPromise(axios({/* axios params */}))
        .map(r => r.data)
        .catch(err => Observable.throw(err))
        .merge(
            new Observable(observer => {
                observer.complete()
                return () => cancelToke.cancel()
            })
        )
 }

这种方法的一个问题是调用
ajaxObservable()
不会返回惰性的可观察的。相反,ajax请求是由axios立即生成的,即使没有人订阅返回的Observable

虽然也有例外,但通常最好的做法是让像这样的自定义观察对象变得懒惰,因此对用户也有同样的期望

要做到这一点,您需要返回一个新的匿名可观察对象,非常类似于您可能通过承诺实现的方式。在我们的定制可观察订阅处理程序中,不需要使用
fromPromise
或任何rxjs,因为我们只需要调用axios和
then

作为奖励,当我们这样做时,原始问题的解决方案变得更加明显:如果有人退订,我们可以调用
cancelToken.cancel()


顺便说一句,catch(err=>Observable.throw(err))实际上是一个noop,再次抛出相同的错误


您可能有兴趣知道rxjs附带了AjaxObservable,这使得类似axios的东西变得不必要。不幸的是,rxjs v5文档中没有正确显示它的文档,但是可以在内联中找到它:它有一个非常标准的API,与大多数ajax实用程序类似

/**
 * Creates an observable for an Ajax request with either a request object with
 * url, headers, etc or a string for a URL.
 *
 * @example
 * source = Rx.Observable.ajax('/products');
 * source = Rx.Observable.ajax({ url: 'products', method: 'GET' });
 *
 * @param {string|Object} request Can be one of the following:
 *   A string of the URL to make the Ajax call.
 *   An object with the following properties
 *   - url: URL of the request
 *   - body: The body of the request
 *   - method: Method of the request, such as GET, POST, PUT, PATCH, DELETE
 *   - async: Whether the request is async
 *   - headers: Optional headers
 *   - crossDomain: true if a cross domain request, else false
 *   - createXHR: a function to override if you need to use an alternate
 *   XMLHttpRequest implementation.
 *   - resultSelector: a function to use to alter the output value type of
 *   the Observable. Gets {@link AjaxResponse} as an argument.
 */

它还有类似于ajax.getJSON等的缩写。

对不起。我很难听懂你说的话。你能偶然地展示一些看起来像什么的代码例子吗?也可以考虑把代码的图片移到你的问题中的实际代码中。编辑器在顶部有代码按钮-看起来像“{}”在你的例子中你想做什么?我想在我执行ajaxObservable(..)时启动我作为unsubscribe(()=>cancelToken.cancel())返回的函数。takeUntil({type:'cancel')是的。catch(…)绝对是一个noop,我只是复制粘贴删除了一些代码。我真的很喜欢你的方法,学习rxjs真的不平凡。观察事情是如何实现的可能会在将来有所帮助。非常感谢你
/**
 * Creates an observable for an Ajax request with either a request object with
 * url, headers, etc or a string for a URL.
 *
 * @example
 * source = Rx.Observable.ajax('/products');
 * source = Rx.Observable.ajax({ url: 'products', method: 'GET' });
 *
 * @param {string|Object} request Can be one of the following:
 *   A string of the URL to make the Ajax call.
 *   An object with the following properties
 *   - url: URL of the request
 *   - body: The body of the request
 *   - method: Method of the request, such as GET, POST, PUT, PATCH, DELETE
 *   - async: Whether the request is async
 *   - headers: Optional headers
 *   - crossDomain: true if a cross domain request, else false
 *   - createXHR: a function to override if you need to use an alternate
 *   XMLHttpRequest implementation.
 *   - resultSelector: a function to use to alter the output value type of
 *   the Observable. Gets {@link AjaxResponse} as an argument.
 */