Angular 2 Service - Observable, который использует функцию с функцией обратного вызова в качестве аргумента

У меня есть служба Angular 2, которая использует веб-службу SOAP. Для этого я использую клиент SOAP Javascript с функцией обратного вызова. Я знаю, что результатом служебного метода может бытьObservableили aPromise, но я не знаю, как перейти от функции обратного вызова обратно к службе.

Вот мой текущий код:

import { Injectable } from '@angular/core';
declare var SOAPClient: any;//<-- The library I'm using, it doesn't have types

@Injectable()
export class SoapService {
  connection_url: Map<string,string>;
  constructor() {
   this.connection_url = new Map<string, string>();
   this.connection_url.set('Example', 'http://localhost:8080/MYAPP_EJB/ExampleSvc');
  }

  consume(service_name: string, method: string, parameters?: Map<string,any>){
   var that = this;
   return new Promise<any>(function(resolve){
      var params = new SOAPClientParameters();
      if(parameters !== null){
        for (let parameter of parameters.keys()){
          params.add(parameter,parameters.get(parameter));
        }
      }
      //Below is the line where I use the function with the callback function argument (function(j)), where j represents the response from the Web Service
      SOAPClient.invoke(that.connection_url.get(service_name), method,params,true,
      function(j){
              return new Promise<any>(function(resolve){
                console.log('Web Service Answer: ' + j.answer.entry.value);
                return j;
              });    
      }); //End of SOAPClient.invoke()
    }); //End of promise of consume()
  }//End of consume()
}//End of class

Что я могу сделать, чтобы функция consumer () предоставила компоненту ответ веб-службы? Потребуется ли мне внести некоторые изменения в SOAPClient?

Спасибо.

Изменить: решение

Я использовал ответ Робина и работал сbindCallback (та же идея, что иfromCallback, см. bindCallback для справки), используя SOAPClient.invoke в качестве аргумента для этой функции. Результирующая функция такая же, как и исходная, но без функции обратного вызова, вместо этого возвращая aObservable, на который я могу подписаться, а затем выполнить обещание ofconsume().

Новый код:

import { Injectable } from '@angular/core';
import * as Rx from "rxjs";
declare var SOAPClient: any;//<-- The library I'm using, it doesn't have types

@Injectable()
export class SoapService {
  connection_url: Map<string,string>;
  invokeSoapClient: any;
  constructor() {
   this.connection_url = new Map<string, string>();
   this.connection_url.set('Example', 'http://localhost:8080/MYAPP_EJB/ExampleSvc');
   this.invokeSoapClient = <any> Rx.Observable.bindCallback(SOAPClient.invoke);
  }

  consume(service_name: string, method: string, parameters?: Map<string,any>){
   var that = this;
   return new Promise<any>(function(resolve){
      var params = new SOAPClientParameters();
      if(parameters !== null){
        for (let parameter of parameters.keys()){
          params.add(parameter,parameters.get(parameter));
        }
      }
      var invokeObs = that.invokeSoapClient(that.conexion_url.get(service_name), method, params, true);
      invokeObs.subscribe(r => {resolve(r[0])}); //r is the answer from SOAPClient invoke, I just needed the response part.
    }); //End of promise of consume()
  }//End of consume()
}//End of class

person aerojas    schedule 10.05.2017    source источник


Ответы (1)


Лучшим способом было бы создать наблюдаемое из вашего обратного вызова. Вы можете легко создать наблюдаемое из обратного вызова. проверьте это

person Robin Dijkhof    schedule 10.05.2017
comment
Ваш ответ сработал, мне пришлось использоватьbindCallback вместоfromcallback, я думаю, что это та же функция, только с измененным именем. Спасибо @ robin-dijkhof! - person aerojas; 10.05.2017