Как да имитирам обратно извикване с параметър на обещаваща функция в rxjs?

Аз съм абсолютен начинаещ в rxjs. За да започна да се уча да мисля в наблюдаеми, трябва да преведа концепции чрез примери на код. Имам чувството, че ако мога да видя кода за това, мога да започна да правя това сам с други концепции.

Аз НЕ искам да КОНВЕРТИРАМ обещание в наблюдаемо, искам да направя ново внедряване с помощта на Обсервируемо, което може да се държи като обещание. Как бих могъл да пренапиша следното с помощта на Observables?

 constructor(){
    let makeMessage2 = function(){
        return new Promise(resolve, reject){
           setTimeout(()=>{
                  var r = Math.random();
                  resolve("message two plus random value: " + r );
           }, 1000);
        }
    }
    this.logMessageAndResultOfCallback("message one!", makeMessage2);
}
private sideEffect1:string = "";
private sideEffect2:string = "";

logMessageAndResultOfCallback( message1:string, callback:Function ){
    console.log(message1);
    this.sideEffect1 = message1;

    callback().then((message2)=>{
          console.log(message2);
          this.sideEffect2 = message2;
    }
}

Предполагам, че частта, която не разбирам, е как да дефинирам функцията "обратно извикване", как да я извикам. Разбирам, че бих изчакал манипулаторите за пълно или излъчване, като makeMessage2().subscribe(message2 => console.log(message2));, но нямам представа как да дефинирам makeMessage2.

Това може да е напълно безсмислен въпрос, но прочетох около 10 различни въведения към rxjs и това не ми хареса. Просто трябва да съпоставя този сценарий с наблюдаем модел и мисля, че мога да го разбера.

По принцип искам да дефинирам наблюдаема функция myObs(), която не се "изпълнява незабавно", а се "изпълнява", когато someMethod(message:string,obs:Observable) се изпълнява. Когато myObs се изпълнява, той трябва да направи нещо асинхронно в него (като получаване на резултата от HTTP заявка), след това да зададе следващата стойност, след което да задейства complete(), така че моят наблюдател, дефиниран в someMethod, да може да обработи пълното и да направи нещо с резултата .

Редактиране: Не се занимавам с таймера или естествените еквиваленти в rxjs, това е само за симулиране на всяко асинхронно действие, като получаване на данни от сървъра.


person FlavorScape    schedule 30.03.2017    source източник
comment
Observable.create приема функция за абонат -- която се изпълнява за всеки, който се абонира. Това не работи ли за вас? Въпросът ви наистина не е ясен. На сайта на rxjs docs има добър съветник за това как да започнете да се наблюдава от различни неща   -  person aarosil    schedule 31.03.2017
comment
моделът за обратно извикване на обещание също е много объркващ.. обикновено това са 2 различни подхода за асинхронен код   -  person aarosil    schedule 31.03.2017
comment
И така, в крайна сметка направих моя собствен опит. Това правилно ли изглежда?   -  person FlavorScape    schedule 31.03.2017
comment
Точно така, това са потенциално две асинхронни поведения. В моя случай на употреба той отхвърля елемент от потребителския интерфейс, след като обратното извикване приключи изчислението, но не извиква обратното извикване до действие от страна на потребителя.   -  person FlavorScape    schedule 31.03.2017
comment
Да, това имах предвид. Само за информация, но за този пример, въпреки че изобщо не се нуждаете от setTimeout, има вграден rx оператор delayTime   -  person aarosil    schedule 31.03.2017
comment
това е просто за симулиране на някакво асинхронно действие, като получаване на нещо от сървъра или т.н. Всъщност не се занимавам с таймери.   -  person FlavorScape    schedule 31.03.2017


Отговори (2)


Кодът, който сте написали и искате да „преведете“ в наблюдаеми, вероятно няма да работи. callback е обещание, а не функция, така че не можете да напишете callback().

Опитахте ли и това въведение? Проработи при много хора.

За да отговорите на въпроса си, можете да пишете

Rx.Observable.of(""message one!", "message two!")
  .map(console.log.bind(console)) // would be better to use `do` operator actually, for semantic reasons, but that works the same here
  .subscribe(noop, noop, noop)

or

Rx.Observable.of(""message one!", "message two!")
  .subscribe(console.log.bind(console), noop, noop)

където noop е функция, която не прави нищо, т.е. function noop(){}

Накратко, вашият поток излъчва данни, тези данни преминават през поредица от оператори и потокът от данни се стартира от .subscribe. Във вашия случай нямате нищо интересно за правене при абонамент, защото всичко, което правите, е да регистрирате.

Rxjs потоците всъщност са базирани на обратно извикване под капака. Искате да проверите този отговор да го разберем.

person user3743222    schedule 30.03.2017
comment
Ами сега, имах за цел да направя функция, която връща обещание. Редактиран код. Не мисля, че това е, което търся. Предвиденият случай на употреба е функция, която има някакъв първоначален страничен ефект (регистрира съобщение1) и изисква обратно извикване да бъде извикано с асинхронна резолюция. Резолюцията на това обратно извикване трябва да извика поведения/странични ефекти, които са агностични за вътрешните функции на обратното извикване. Не просто се опитвам да отпечатам две съобщения. - person FlavorScape; 31.03.2017
comment
Не, имам нужда от странични ефекти. вашият пример не може да направи това. Току-що направих примера ми да има конкретни странични ефекти за илюстрация. - person FlavorScape; 31.03.2017
comment
Добавих моя опит. изглежда ли това съответства на модела, който предлагам? - person FlavorScape; 31.03.2017

Реших го с помощта на това ръководство.

import {Observable} from 'rxjs';
var makeMessage2 = Observable.create(observer => {
  // Yield a single value and complete
  setTimeout(function(){
     let r = Math.random();
     observer.next("message two plus random value: " + r );
     observer.complete();
  }, 1000);
  return () => console.log('disposed')
});
logMessageAndResultOfCallback( "some message one", makeMessage2);


logMessageAndResultOfCallback( message1:string, callback:Observeable ){
    console.log(message1);
    this.sideEffect1 = message1;

    var subscription = callback.subscribe(
       (value)=>{this.sideEffect2 = value;},
       (e) =>{ console.log('onError: %s', e)},
       () => {console.log(this.sideEffect2);});
      subscription.dispose();
}
person FlavorScape    schedule 31.03.2017