У меня есть список параметров и по каждому параметру на сервер отправляется запрос. Количество параметров может варьироваться, поэтому запросы отправляются циклично. Вопрос в том, как мне отправить запросы по всем параметрам, дождаться ответа от всех запросов и продолжить выполнение программы. Для этого вам нужно использовать RxJS.
private getValuesForEditTariff(parameter: Parameter) {
if (parameter.dependParams != null && parameter.dependParams.length > 0) {
let pars: Parameter[] = new Array<Parameter>();
this.actionEditTariff.groups.forEach(group => {
pars = pars.concat(group.parameters);
});
let locator = (p: Parameter, id: number) => p.id == id;
let service = this.actionService;
let action = this.actionEditTariff;
parameter.dependParams.forEach(parameter => {
let par = pars.find(p => locator(p, parameter));
if (par) {
par.loading = true;
service.getValues(parameter, pars,action.action, action.actionScheme).subscribe({
next: (data) => {
par.values = data;
par.loading = false;
console.info("Значения получены");
},
error: (error)=> {
this.message = error.error.message || error.statusText;
par.loading = false;
this.showError();
}
})
}
})
}
}
Я пытался использовать concatMap, но не понимаю, как он работает.



![Безумие обратных вызовов в javascript [JS]](https://i.imgur.com/WsjO6zJb.png)


Вы можете использовать forkJoin, чтобы дождаться всех подобных ответов.
private getValuesForEditTariff(parameter: Parameter) {
if (parameter.dependParams != null && parameter.dependParams.length > 0) {
let pars: Parameter[] = new Array<Parameter>();
this.actionEditTariff.groups.forEach(group => {
pars = pars.concat(group.parameters);
});
const locator = (p: Parameter, id: number) => p.id == id;
const service = this.actionService;
const action = this.actionEditTariff;
const parameters$ = parameter.dependParams.reduce((parameters, parameter) => {
const par = pars.find(p => locator(p, parameter));
if (par) {
par.loading = true;
parameters.push(
service.getValues(parameter, pars, action.action, action.actionScheme).pipe(
tap(() => {
par.values = data;
par.loading = false;
console.info('Значения получены');
}),
catchError(() => {
this.message = error.error.message || error.statusText;
par.loading = false;
this.showError();
return of(null);
}),
),
);
}
return parameters;
}, []);
forkJoin(parameters$).subscribe();
}
}
@denikotin это первый параметр, передаваемый в обратный вызов метода уменьшения массива, вы можете проверить его здесь Developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/…
Хорошо, не могли бы вы объяснить, почему вы используете здесь сокращение, пожалуйста. И как вы делаете параметры.push(), если параметры — это числовой тип
@denikotin Цель состоит в том, чтобы получить массив наблюдаемых для передачи в forkJoin, поэтому я использовал reduce, потому что вы фильтруете по условию if (par) перед отправкой запроса, поэтому вы можете использовать .reduce() или .filter().map(), чтобы получить желаемый массив, поэтому reduce подойдет 1 цикл по массиву вместо 2, и parameters — это не число, это массив, в который будут отправлены запросы.
Я получил ошибку, что параметры не являются массивом и не могут выполнить push(). Но в любом случае огромное спасибо, для меня это очень полезно, ценю это.
@denikotin, пожалуйста, повтори попытку, я обновил свой ответ
Спасибо большое, а что такое переменные «параметры»? Это массив? Не могу найти декларацию об этом