যে ফাংশনটির ভিতরে পর্যবেক্ষণযোগ্য সাবস্ক্রিপশন রয়েছে তার থেকে কীভাবে মূল্য ফেরানো যায়?


98

আমি জানি না কীভাবে পর্যবেক্ষণযোগ্য থেকে উপস্থিত ফাংশনটিতে ফেরত পেতে পর্যবেক্ষণযোগ্য থেকে মান বের করতে হয়। এটি থেকে ফিরে আসার জন্য আমার কেবল একটি মান দরকার else

বর্তমান সংস্করণ যা কাজ করে

function getValueFromObservable() {
    this.store.subscribe(
        (data:any) => {
            console.log(data)
        }
    )
}
getValueFromObservable()

আমার এটি কাজ করতে হবে, মূল্য ফেরত দেওয়ার জন্য ফাংশন করতে হবে এবং তারপরে:

function getValueFromObservable() {
    this.store.subscribe(
        (data:any) => {
            return data
        }
    )
}
console.log(getValueFromObservable())

আমি এখানে কি ভুল করছি?


4
আপনার পর্যবেক্ষণযোগ্য সমাধান হয়ে গেলে আপনার কোনও পর্যবেক্ষণযোগ্য / প্রতিশ্রুতি ফেরানো উচিত এবং তার মাধ্যমে ডেটা পাস করা উচিত
জুলভ

4
আপনি কি এর জন্য কিছু সাধারণ কোড রাখতে পারেন?
টেডি

6
আপনি যা অর্জন করতে চাইছেন তা একটি অ্যান্টি-প্যাটার্ন: আপনি একটি অ্যাসিঙ্ক কার্যটি "সিঙ্ক্রোনাইজ" করার চেষ্টা করছেন। পর্যবেক্ষকরা যেভাবে কাজ করবেন বলে মনে করা হয় তা নয়। সংক্ষেপে, বেশিরভাগ ক্ষেত্রে, ইনপুট হিসাবে পর্যবেক্ষণযোগ্য কোনও ক্রিয়াকলাপটি একটি পর্যবেক্ষণযোগ্যকে ফিরিয়ে দেয় - বা কিছুই ফিরিয়ে দেয় না। এবং যখন আপনাকে আউটপুট দিয়ে কিছু করার দরকার হবে তখন এটিতে সাবস্ক্রাইব করুন। এই ক্ষেত্রে আপনি ডাটা console.log করতে চান তাহলে, শুধু ভিতরে এটা করতেsubscribe
ক্যান গুয়েন

4
আপনারা যা বলেছেন তা আমি বুঝতে পেরেছি। আমি কেবল ডেমো হিসাবে কনসোল লগটি ব্যবহার করছি, আমি সেই ডেটাটি আরও ব্যবহার করব, তবে পর্যবেক্ষণের বাইরে লগ কনসোল করার জন্য আমার এটি কেন প্রয়োজন ts বিন্দুটি হ'ল ফাংশনটি যা আপনি যখন পর্যবেক্ষণযোগ্য সাবস্ক্রাইব করতে পারেন, ডেটা পেতে পারেন, সাবস্ক্রাইব করতে পারেন এবং সেই ফাংশনে ডেটা ফেরত দিতে পারেন যাতে আমি সেই তথ্যটি আরও ব্যবহার করতে পারি। আমি জানি এটি নিদর্শন বিরোধী, তবে এটি কাজ করা আমার দরকার I কোন সাহায্য প্রশংসা করা হয়। আমার সমাধানটি বর্তমান কাজ করে তবে আমি এ সম্পর্কে খুব বেশি আত্মবিশ্বাসী নই।
টেডি

4
দৃষ্টি আকর্ষন করা! 'সলিউশন' বিভাগের কোডটি একেবারেই ভুল। এটি ব্যবহার করবেন না! এটি কেবল তখনই কাজ করবে যদি বিভাগটি.স্টোর.সউসস্ক্রাইব ((ডেটা: কোনও) => {আউটপুট = ডেটা}) unউন্সস্ক্রাইব () ফেরত হওয়া পর্যন্ত শেষ হবে। অন্যথায় এটি অপরিবর্তিত ফিরে আসবে।
রডিয়ন গোলভুশকিন

উত্তর:


58

সম্পাদনা: আরএক্সজেএসের আরও সাম্প্রতিক সংস্করণগুলিতে পাইপগুলি যেভাবে কাজ করে তাতে পরিবর্তনগুলি প্রতিফলিত করার জন্য আপডেট করা কোড। সমস্ত অপারেটর (আমার উদাহরণটি ধরুন) এখন পাইপ () অপারেটরে আবৃত।

আমি বুঝতে পেরেছি যে এই প্রশ্নটি বেশ আগে হয়েছিল এবং আপনার অবশ্যই এখনই সঠিক সমাধান হবে তবে যে কেউ এটি খুঁজছেন আমি এ্যাসিঙ্ক প্যাটার্নটি রাখার প্রতিশ্রুতি দিয়ে সমাধান করার পরামর্শ দেব suggest

আরও ভার্বোজ সংস্করণ একটি নতুন প্রতিশ্রুতি তৈরি করবে:

function getValueFromObservable() {
    return new Promise(resolve=>{
        this.store.pipe(
           take(1) //useful if you need the data once and don't want to manually cancel the subscription again
         )
         .subscribe(
            (data:any) => {
                console.log(data);
                resolve(data);
         })
    })
}

প্রাপ্তির শেষে আপনার এইরকম কিছু দিয়ে সমাধানের প্রতিশ্রুতির জন্য "অপেক্ষা" করতে হবে:

getValueFromObservable()
   .then((data:any)=>{
   //... continue with anything depending on "data" after the Promise has resolved
})

একটি পাতলা সমাধান পরিবর্তে RxJS '.toPromise () ব্যবহার করা হবে:

function getValueFromObservable() {
    return this.store.pipe(take(1))
       .toPromise()   
}

গ্রহণকারী পক্ষ অবশ্যই অবশ্যই উপরে হিসাবে একই থাকে।


আপনার getValueFromObservableফাংশনের রিটার্নের ধরন কী ?
হার্ডওয়াইং

স্টোর ডেটা যাই হউক না কেন তার প্রতিশ্রুতি থাকা উচিত। যেমন প্রতিশ্রুতি <স্টোরটাইপ>
jparg

4
আপনি এখনও এমন প্রতিশ্রুতি ফিরিয়ে দিচ্ছেন যা সমাধান করা দরকার এবং সরাসরি কোনও মান ফেরত দিচ্ছে না।
রোজ

4
সম্পত্তি 'নিতে' টাইপ 'পর্যবেক্ষণযোগ্য <>' টাইপ নেই
মেমো

4
@Memmo .pipe চেষ্টা করুন (নেওয়া (1)) পরিবর্তে
Thibault

20

এটি ব্যবহারের সঠিক ধারণা নয় Observable

উপাদানটিতে আপনাকে শ্রেণীর সদস্য ঘোষণা করতে হবে যা একটি অবজেক্টকে ধারণ করবে (এমন কিছু যা আপনি নিজের উপাদানটিতে ব্যবহার করতে যাচ্ছেন)

export class MyComponent {
  name: string = "";
}

তারপরে একজন Serviceআপনাকে ফেরত দেবে Observable:

getValueFromObservable():Observable<string> {
    return this.store.map(res => res.json());
}

Component এটি থেকে কোনও মান পুনরুদ্ধার করতে সক্ষম হওয়ার জন্য নিজেকে প্রস্তুত করা উচিত:

OnInit(){
  this.yourServiceName.getValueFromObservable()
    .subscribe(res => this.name = res.name)
}

আপনাকে Observableভেরিয়েবলের জন্য একটি মান নির্ধারণ করতে হবে:

এবং আপনার টেম্পলেটটি ভেরিয়েবল গ্রাস করবে name:

<div> {{ name }} </div>

ব্যবহারের আরেকটি উপায় Observableহ'ল asyncপাইপ http://briantroncone.com/?p=623 মাধ্যমে

দ্রষ্টব্য : আপনি যা জিজ্ঞাসা করছেন এটি যদি তা না হয় তবে দয়া করে আপনার প্রশ্নটি আরও বিশদ সহ আপডেট করুন


বেশ ভাল না। সমস্যাটি হ'ল পর্যবেক্ষণের অভ্যন্তরে ডেটা ক্যাপচার করা হয় এবং আমি এটি লগইয়ে কনসোল করতে পারি। আমি সেই মানটি এবং কনসোল.লগ বা বিভিন্ন ফাইল থেকে যে কোনও ফাংশন যেখানে এটিতে রয়েছে তাকে কল করে ফিরে আসতে চাই।
টেডি

আন্ড্রে nameকলব্যাকের বাইরে কীভাবে উপাদানটির nameভেরিয়েবলটি অর্পণ করবেন তা নির্দেশ করে । nameআপনার ক্ষেত্রে সুসংগতভাবে ফিরে আসা সম্ভব নয় ।
ম্যাট

@ ম্যাট: আমি এটির Oninitমতো এটি ব্যবহার করতে পারি না , যদি আমার স্পষ্টভাবে ফিরে আসতে হয় তবে আমার কলিং কোডটি দেখতে দেখতে this.actions$.ofType(SearchActions.SEARCH_MULTIPLE_NEW_QUERY).map(toPayload).fnWithMultipleAsyncReturns()
এমনটি হয়

@ ইসহান্দুত্ত2007 হেই আছে। আপনি আপনার ইস্যুটি সম্পর্কে আরও ভাল নতুন প্রশ্ন তৈরি করুন।
ম্যাট

@Matt: সৃষ্টি যদি আপনি দেখে নিতে চান ( stackoverflow.com/questions/43381922/... )
ishandutta2007

7

আপনি যদি একই পর্যবেক্ষণযোগ্য যা ফিরে আসবে তার পূর্ব সাবস্ক্রাইব করতে চান, তবে কেবল ব্যবহার করুন

.do ():

function getValueFromObservable() {
    return this.store.do(
        (data:any) => {
            console.log("Line 1: " +data);
        }
    );
}

getValueFromObservable().subscribe(
        (data:any) => {
            console.log("Line 2: " +data)
        }
    );

4
আপনি অন্যান্য অপারেটরগুলিও .map(data => data)একই জিনিসটি ব্যবহার করতে পারেন এবং ফলাফলটি যেখানেই প্রত্যাশা করেন সেখানে তা সাবস্ক্রাইব করতে পারেন
ashok_khman

আমি আশোক_খুমানের সাথে একমত এখানে গাইড Angular.io/guide/pines
আরমান্ডো

এটি একটি ভাল উত্তর হতে পারে, তবে বাস্তবে আপনি এটি সম্পর্কে কোনও ব্যাখ্যা দেননি, এটি একটি খারাপ উত্তরে পরিণত করে। "প্রাক সাবস্ক্রাইব" এর অর্থ কী? এবং এটি থ্রেড ওপেনার থেকে প্রশ্নটি সমাধান করা উচিত?
ফ্লোরিয়ান লেটজেব

নোট করুন যে আরএক্সজেএস 6 doএ এখন বলা হয়েছে tapএবং আপনাকে অবশ্যই এটি একটি পাইপে ব্যবহার করতে হবে। এছাড়াও নোট করুন যে tapবিভিন্ন হ্যান্ডলার যেমন next, completeএবং এর জন্য একাধিক পরামিতি নেয় error
সাইমন_উইভার

7

সমস্যাটি হ'ল পর্যবেক্ষনের অভ্যন্তরে ডেটা ক্যাপচার করা হয় এবং আমি এটি লগইয়ে কনসোল করতে পারি। আমি সেই মানটি এবং কনসোল.লগ বা বিভিন্ন ফাইল থেকে যে কোনও ফাংশন যেখানে এটিতে রয়েছে তাকে কল করে ফিরে আসতে চাই।

দেখে মনে হচ্ছে আপনি কোনও পর্যবেক্ষনের অভ্যন্তরে কোনও "বর্তমান মান" পাওয়ার সন্ধান করছেন, যখন এটি নির্গত হয় এবং নির্গমন হওয়ার পরে।

Subjectএবং এ Observableজাতীয় জিনিস নেই। যখন কোনও মান নির্গত হয় তখন এটি তার গ্রাহকদের হাতে দেওয়া হয় এবং এটি Observableদিয়ে এটি করা হয়।

আপনি BehaviorSubjectসর্বশেষ নিঃসৃত মানটি সংরক্ষণ করে এবং এটি নতুন গ্রাহকদের কাছে অবিলম্বে নির্গত করতে পারেন।

getValue()বর্তমান মান পাওয়ার জন্য এটিরও একটি পদ্ধতি রয়েছে ;

আরও পড়া:

আরএক্সজেএস আচরণমূলক বিষয়

কীভাবে আরএক্সজেএস সাবজেক্ট বা পর্যবেক্ষনের বর্তমান মূল্য পাবেন?


2

পর্যবেক্ষণযোগ্য মানগুলি যে কোনও অবস্থান থেকে পুনরুদ্ধার করা যেতে পারে। উত্স ক্রমটি প্রথমে একটি বিশেষ পর্যবেক্ষকের দিকে ঠেলে দেওয়া হয় যা অন্য কোথাও নির্গত করতে সক্ষম। প্রতিক্রিয়াশীল এক্সটেনশনগুলি (আরএক্সজেএস) থেকে সাবজেক্ট ক্লাস দিয়ে এটি অর্জন করা হয়েছে ।

var subject = new Rx.AsyncSubject();  // store-last-value method

পর্যবেক্ষকের উপরে স্টোরের মান ।

subject.next(value); // store value
subject.complete(); // publish only when sequence is completed

অন্য কোথাও থেকে মানটি পুনরুদ্ধার করতে, পর্যবেক্ষকের মতো সাবস্ক্রাইব করুন:

subject.subscribe({
  next: (response) => {
      //do stuff. The property name "response" references the value
  }
});

বিষয়গুলি পর্যবেক্ষণযোগ্য এবং পর্যবেক্ষক উভয়ই। অন্যান্য হয় সাপেক্ষে ধরনের অন্যান্য ব্যবহার পরিস্থিতিতে এমন BehaviourSubject এবং ReplaySubject হিসাবে।

আরএক্সজেএস আমদানি করতে ভুলবেন না।

var Rx = require('rxjs');

1

পূর্ববর্তী উত্তরগুলি কোনও ফ্যাশনে কাজ করতে পারে এমন সময়, আমি মনে করি যে আপনি যদি পর্যবেক্ষণযোগ্য ব্যবহার চালিয়ে যেতে চান তবে বিহেভিয়ারসুবজেক্ট ব্যবহার করা সঠিক উপায়।

উদাহরণ:

    this.store.subscribe(
        (data:any) => {
            myService.myBehaviorSubject.next(data)
        }
    )

সেবায়:

let myBehaviorSubject = new BehaviorSubjet(value);

উপাদানগুলিতে।

this.myService.myBehaviorSubject.subscribe(data => this.myData = data)

আশা করি এটা কাজে লাগবে!


0

উদাহরণস্বরূপ এটি আমার এইচটিএমএল টেমপ্লেট:

<select class="custom-select d-block w-100" id="genre" name="genre"
                  [(ngModel)]="film.genre"
                  #genreInput="ngModel"
                  required>
            <option value="">Choose...</option>
            <option *ngFor="let genre of genres;" [value]="genre.value">{{genre.name}}</option>
          </select>

এটি আমার ক্ষেত্রের টেমপ্লেটের সাথে আবদ্ধ ক্ষেত্র:

  // Genres of films like action or drama that will populate dropdown list.
  genres: Genre[];

আমি গতিশীল সার্ভার থেকে ছায়াছবির জেনার এনেছি। যাতে আমি তৈরি করা সার্ভারের সাথে যোগাযোগ করিFilmService

এটি সার্ভার যোগাযোগ করার পদ্ধতি:

 fetchGenres(): Observable<Genre[]> {
    return this.client.get(WebUtils.RESOURCE_HOST_API + 'film' + '/genre') as Observable<Genre[]>;
  }

এই পদ্ধতিটি কেন Observable<Genre[]>এমন কিছু দেয় না Genre[]?

জাভাস্ক্রিপ্টটি asyncএবং কোনও ব্যয়বহুল প্রক্রিয়া পরে কোনও পদ্ধতির মান ফেরানোর জন্য এটি অপেক্ষা করে না। ব্যয়বহুল সহ আমি এমন একটি প্রক্রিয়া বোঝাই যা মান ফেরত দিতে সময় নেয়। সার্ভার থেকে ডেটা আনার মতো। সুতরাং আপনি আছে পর্যবেক্ষণযোগ্য এর রেফারেন্স ফিরে যান এবং এটা সাবস্ক্রাইব করুন।

উদাহরণস্বরূপ আমার কম্পোনেন্টে:

ngOnInit() {
    this.filmService.fetchGenres().subscribe(
      val => this.genres = val
    );
  }

0
function getValueFromObservable() {
    this.store.subscribe(
        (data:any) => {
            return data
        }
    )
}
console.log(getValueFromObservable())

উপরের ক্ষেত্রে কনসোল.লগ প্রতিশ্রুতি সমাধানের আগে চলে তাই কোনও মান প্রদর্শিত হয় না, এটি নিম্নলিখিতটিতে পরিবর্তন করুন

function getValueFromObservable() {
    return this.store
}

getValueFromObservable()
 .subscribe((data: any) => {
    // do something here with data
    console.log(data);
});

অপারেটর ব্যবহার করে পর্যবেক্ষনীয় ফিরিয়ে ফাংশনটি সাবস্ক্রাইব করতে আপনার getValueFromObservable এর অভ্যন্তরে ডেটা প্রয়োজন হলে অন্যান্য সমাধান হয়।

 function getValueFromObservable() {
        return this.store.subscribe((data: any) => {
            // do something with data here
            console.log(data);
            //return again observable.
            return of(data);
       })
    }

    getValueFromObservable()
     .subscribe((data: any) => {
        // do something here with data
        console.log(data);
    });

0

জাভাস্ক্রিপ্টের একক-থ্রেডযুক্ত, অ্যাসিনক্রোনাস, প্রতিশ্রুতি-ভিত্তিক, প্রতিক্রিয়াশীল-প্রবণতা জগত async/awaitহ'ল আবশ্যক-শৈলীর প্রোগ্রামারের সেরা বন্ধু:

(async()=>{

    const store = of("someValue");
    function getValueFromObservable () {
        return store.toPromise();
    }
    console.log(await getValueFromObservable())

})();

এবং ক্ষেত্রে storeএকাধিক মানের ক্রম:

  const aiFrom = require('ix/asynciterable').from;
  (async function() {

     const store = from(["someValue","someOtherValue"]);
     function getValuesFromObservable () {
        return aiFrom(store);
     }
     for await (let num of getValuesFromObservable()) {
       console.log(num);
     }
  })();

ডেটা অ্যারের ক্ষেত্রে আমি কেন অ্যাসিঙ্ক্রোনসনেস ব্যবহার করব?
জানোস ভিনসেল্লার

@ জ্যানোস ভিন্সেল্লার কোডটির অন্যান্য অংশগুলিতে ফোকাস করার জন্য এটি কেবল একটি উদাহরণ। আপনি from(["someValue","someOtherValue"])আপনার পছন্দের একটি পর্যবেক্ষণযোগ্য দ্বারা প্রতিস্থাপন করতে পারেন যা একাধিক মান নির্ধারণ করে। আমার ধারণা, এটি ব্যবহার করা আরও উপযুক্ত হতে পারে interval(1000)
মেরিনোজ আন

0

শালীন উপায় হ'ল কোনও ফাংশন থেকে পর্যবেক্ষণযোগ্যকে ফিরিয়ে দেওয়া এবং যেখানে প্রয়োজন সেখানে এটিতে সাবস্ক্রাইব করা, কারণ পর্যবেক্ষকরা অলস, তারা সাবস্ক্রাইব করলেই মানগুলি নির্গমন করতে শুরু করবে।

এখানে আমার কাছে আরও একটি আকর্ষণীয় ইভেন্ট চালিত সমাধান রয়েছে, যা আমি প্রাথমিকভাবে সাথে প্রায়শই খেলতাম। নীচের উদাহরণ নোডেজগুলির " ইভেন্ট " মডিউলটি ব্যবহার করে এটি করে । আপনি অন্যান্য ফ্রেমওয়ার্কগুলির সাথে এটি ব্যবহার করতে পারেন যেখানে অনুরূপ মডিউল উপস্থিত রয়েছে ( দ্রষ্টব্য : ব্যবহৃত মডিউলের উপর ভিত্তি করে সিনট্যাক্স এবং শৈলী পরিবর্তন হতে পারে)।

var from =require("rxjs").from;
var map = require("rxjs/operators").map;
var EventEmitter = require("events");

function process(event) {
    from([1,2,3]).pipe(
        map(val => `The number is:: ${val}`)
    ).subscribe((data) => {
       event.emit("Event1", data); //emit value received in subscribe to the "Event1" listener
    });
}

function main() {
   class Emitter extends EventEmitter{};
    var event = new Emitter(); //creating an event
    event.on("Event1", (data)=>{ //listening to the event of name "Event1" and callback to log returned result
        console.log(data); //here log, print, play with the data you receive
    });
    process(event); //pass the event to the function which returns observable.
}

main(); //invoke main function

এটি এমন একটি ধারণা প্রদর্শন করার উদাহরণ যেখানে আমরা নির্গমন এবং শোনার পদ্ধতি দ্বারা বিভিন্ন স্থান থেকে ডেটা পাস করতে পারি। এটি ইভেন্ট-চালিত কোড হিসাবেও পরিচিত।

আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.