Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/typescript/8.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 RxJS获取订阅回调的完成结果_Javascript_Typescript_Rxjs - Fatal编程技术网

Javascript RxJS获取订阅回调的完成结果

Javascript RxJS获取订阅回调的完成结果,javascript,typescript,rxjs,Javascript,Typescript,Rxjs,我是RxJS初学者,我想让我的代码更干净 这是我写的代码,我在接收完成结果时遇到问题 我想让我的代码更干净,在订阅回调中获得结果,而不使用其他主题来接收结果 以下是我的代码rxjs 7.0.1: 从“颜色/安全”导入颜色; 从'rxjs'导入{Subject}; 从“rxjs/operators”导入{throttle}; 接口IEventTask{ id:string, createdTime:编号 } 设全局_计数器:数=0; const mockHTTPRequest=async(事件:I

我是RxJS初学者,我想让我的代码更干净

这是我写的代码,我在接收完成结果时遇到问题

我想让我的代码更干净,在订阅回调中获得结果,而不使用其他主题来接收结果

以下是我的代码rxjs 7.0.1:

从“颜色/安全”导入颜色;
从'rxjs'导入{Subject};
从“rxjs/operators”导入{throttle};
接口IEventTask{
id:string,
createdTime:编号
}
设全局_计数器:数=0;
const mockHTTPRequest=async(事件:IEventTask)=>{
返回(Promise.resolve().then(async()=>{
等待新的承诺((决心)=>{
全局.setTimeout(解析,1000);
});
如果(event.id=='01'){
抛出新错误(`Error:${event.id}`);
}
const result=`result:${event.id}`;
//我不知道如何得到结果,所以我发布到另一个订阅者
下一步(结果);
返回结果;
}))
.catch((错误)=>{
控制台错误(error);
})
}
常量主题=新主题();
主题
.烟斗(
节气门(模拟HttpRequest{
前导:真,尾随:真
})
)
.订阅({
下一步:(值)=>{
log(`colors.blue(`starting`)}任务$${value.id}位于:${global_counter++}`);
},
错误:(错误)=>{
控制台错误(error);
},
完成:()=>{
//我怎样才能在这里得到结果?
console.log(`completed`);
}
});
//这不是我想要使用的代码,但我不知道如何让它变得简单。
const subscriber=新主题();
subscriber.subscribe((结果:字符串)=>{
log(${colors.green(`finished`)}${result}位于:${global_counter++}');
});
(异步()=>{
for(设i=1;i{
全局设置超时(()=>{
决心(正确);
}, 125);
});
常量值:IEventTask={
id:(i).toString().padStart(2,'0'),
createdTime:全局计数器++
};
主题。下一个(价值);
}
})();

非常感谢。

在我看来,每当
subject
(变量)获得新值时,您都希望发出HTTP请求

因此,使用
throttle
时要记住,它应该等待HTTP请求完成,并提供返回值。问题在于,
油门不提供后者。(见附件)

我建议您改用
switchMap
。它期望传递的函数返回一个可观察值,当它发出时,switchMap将转发该值。此外,每当发出一个新值时,它就完成了内部可观察性。这意味着,如果HTTP请求尚未完成,它将终止当前请求并发出新的请求。(见附件)

import { Subject, Observable, OperatorFunction, pipe, UnaryFunction } from 'rxjs';
import { filter, switchMap } from 'rxjs/operators';

const mockHTTPRequest = async (event: IEventTask) => {
  return (Promise.resolve().then(async () => {
    await new Promise((resolve) => {
      setTimeout(resolve, 2000);
    });

    if (event.id === '01') {
      throw new Error(`error: ${event.id}`);
    }

    const result = `result: ${event.id}`;
    // This was needed in order to provide the id in the subscribe section
    return {
      id: event.id,
      result
    };
  }))
    .catch((error) => {
      console.error(error);
      // This was needed for the filter function to work
      return undefined;
    })
}

// this filters nullish values: null and undefined
function filterNullish<T>(): UnaryFunction<Observable<T | null | undefined>, Observable<T>> {
  return pipe(
    filter(x => x != null) as OperatorFunction<T | null | undefined, T>
  );
}

const subject = new Subject<IEventTask>();
subject
  .pipe(
    switchMap(mockHTTPRequest),
    filterNullish()
  )
  .subscribe({
    next: (value) => {
      console.log(`starting Task#${value.id} at: ${global_counter++}`);
    },
    error: console.error,
    complete: () => {
      // How can I get Promise resolved result here?
      console.log(`completed`);
    }
  });
import colors from 'colors/safe';
import { Subject, Observable, OperatorFunction, pipe, UnaryFunction } from 'rxjs';
import { filter, mergeMap, tap } from 'rxjs/operators';

interface IEventTask {
  id: string,
  createdTime: number
}

let global_counter: number = 0;

function waitFor(time: number) {
  return new Promise((resolve) => {
    setTimeout(resolve, time);
  })
}

function filterNullish<T>(): UnaryFunction<Observable<T | null | undefined>, Observable<T>> {
  return pipe(
    filter(x => x != null) as OperatorFunction<T | null | undefined, T>
  );
}

const mockHTTPRequest = async (event: IEventTask) => {
  return (Promise.resolve().then(async () => {
    await waitFor(2000);

    if (event.id === '01') {
      throw new Error(`error: ${event.id}`);
    }

    return `result: ${event.id}`;
  }))
    .catch((error) => {
      console.error(error);
      return undefined;
    })
}

const subject = new Subject<IEventTask>();
subject
  .pipe(
    tap(value => console.log(`${colors.blue(`starting`)} Task#${value.id} at: ${global_counter++}`)),
    mergeMap(mockHTTPRequest),
    filterNullish()
  )
  .subscribe({
    next: (result) => {
      console.log(`${colors.green(`finished`)} ${result} at: ${global_counter++}`);;
    },
    error: console.error
  });


(async () => {
  for (let i = 1; i <= 10; i++) {
    await waitFor(125);

    const value: IEventTask = {
      id: (i).toString().padStart(2, '0'),
      createdTime: global_counter++
    };

    subject.next(value);
  }
})();