Bacon.js «разделение» события, содержащего массив, на несколько событий для каждого элемента

#javascript #functional-programming #reactive-programming #bacon.js

#javascript #функциональное программирование #реактивное программирование #bacon.js

Вопрос:

Недавно я обнаружил Bacon.js и я возился, но боролся с проблемой.

У меня есть поток событий results для недавних пользователей GitHub, возвращенный из запроса AJAX. Каждое результирующее событие представляет собой массив пользовательских объектов, например, [{ id: 1, login: 'somlor' }, { id: 2, login: 'raimohanska' }, ...]

ВОПРОС: Я бы хотел создать новый users поток событий, который поступает из результирующих событий и возвращает фактические пользовательские объекты в виде отдельных событий. Возможно ли это?

Вот мой код для потока результатов, он работает так, как ожидалось:

 // get some recent github users
var ajaxStream = function() {
  var randomOffset = Math.floor(Math.random() * 500);
  var url = 'https://api.github.com/users?since='   randomOffset;
  return Bacon.fromPromise($.ajax(url));
}

// refresh click stream, start as true to trigger initial ajax call
var refresh = $('a.refresh').asEventStream('click')
                            .map(true)
                            .startWith(true);

// latest results stream. each event is an array of user objects.
var results = refresh.flatMapLatest(ajaxStream);
  

Это не работает. Это создает единый поток событий для каждого results массива. Я хочу, чтобы он «разделял» каждый results массив на новое событие для каждого пользовательского объекта в этом массиве.

 // stream of individual users created from each result event array
var users = results.map(function(e) { return new Bacon.fromArray(e); });
  

Есть идеи?

Спасибо,
Шон

Обновить:
Это то, что я искал:

 var users = results.flatMap(Bacon.fromArray);
  

Ответ №1:

Если я правильно понимаю вопрос, вам нужно использовать .flatMap для создания потока.

 results.flatMap(Bacon.fromArray).onValue(function(v){ console.log(v) });
  

Комментарии:

1. Это здорово, спасибо @jjuutila. Я думаю, что тогда, чтобы преобразовать это в новый поток, я мог бы сделать var users = new Bacon.Bus(); тогда results.flatMap(Bacon.fromArray).onValue(function(v) { users.push(v); });

2. Я думаю, вам не нужна эта дополнительная шина, потому что flatMap создает новый поток.