title: How to return a mapped string from a Service that fetches values from an API with rjxs?
body: <p>I have a service called <code>MappingService</code> in Angular 7. This service fetches a list of names from an API:</p>
  
  <pre><code>{
    'guid1': 'Item 1',
    'guid2': 'Item 2',
    'guide': 'Item 3',
  }
  </code></pre>
  
  <p>These values should later be mapped by their ids. Of course I could subscribe to <code>items$</code> in a componentn and then do something like:</p>
  
  <pre><code>{{ mapping[id] }}
  </code></pre>
  
  <p>But I thought it would be nice, If I don't have to subscribe to that service or its list so I don't have to pass it around all the time, because the mapping is fixed once loaded and is needed by multiple components.</p>
  
  <p>So I thought I add a method <code>map</code> to the service that does this:</p>
  
  <ul>
  <li>gets an id</li>
  <li>returns the corresponding string</li>
  </ul>
  
  <p>Like:</p>
  
  <pre><code>{{ mappingSrervice.map(id) }}
  </code></pre>
  
  <p>But this is where I'm stuck:</p>
  
  <pre><code>import { Injectable } from '@angular/core';
  import { HttpClient } from '@angular/common/http';
  import { BehaviorSubject, Observable, of } from 'rxjs';
  import { mergeMap, tap, catchError } from 'rxjs/operators';
  
  @Injectable({
    providedIn: 'root'
  })
  
  export class MappingService {
    items$ = new BehaviorSubject&lt;any&gt;(null);
  
    constructor(private http: HttpClient) { }
  
    getAll(): Observable&lt;any&gt; {
      return this.items$.pipe(mergeMap(items =&gt; {
        if (items) {
          return of(items);
        } else {
          return this.http.get&lt;any&gt;(
            'http://api'
          ).pipe(
            tap((response: any) =&gt; response),
            catchError(error =&gt; {
              return of([]);
            })
          );
        }
      }));
    }
  
    map(id: number): string {
      return this.items$[id] || null;
    }
  }
  </code></pre>
  
  <p>How do I correctly implement <code>map()</code>? Should I run <code>getAll()</code> in the constructor? The problem is still of course that <code>items$</code> will not be filled before <code>getAll()</code> is finished.</p>
  
  <p>Can I get it to work like I thought? Is <code>string</code> the correct return type? </p>
  
  <p>I wonder whether this approach is possible? Or do I need to return promises instead? But this would generate a new level of abstraction, making it not that much simpler instead of the naive approach (just subscribing to <code>items$</code>.</p>