jsonp(P4907)

サービスを使わない

app.module.ts

import { NgModule }      from '@angular/core';
import { FormsModule }   from '@angular/forms';
import { JsonpModule }  from "@angular/http";
import { BrowserModule } from '@angular/platform-browser';

import { AppComponent }  from './app.component';

@NgModule({
  imports:      [ BrowserModule, FormsModule, JsonpModule ],
  declarations: [ AppComponent ],
  bootstrap:    [ AppComponent ]
})
export class AppModule { }

app.component.ts

import { Component } from '@angular/core';
import { Jsonp, URLSearchParams }  from '@angular/http';

@Component({
  selector: 'app-root',
  template: `
  <form>
    <label for="url">URL:</label>
    <input id="url" name="url" type="url" size="50" [(ngModel)]="url" />
    <input type="button" (click)="onclick()" value="検索" />
  </form>
  <div>{{count}}件</div>
  <ul>
    <li *ngFor="let comment of comments">{{comment}}</li>
  </ul>
  `,
})
export class AppComponent {
  url = 'http://gihyo.jp/';
  count = 0;
  comments: string[] = [];

  constructor(private jsonp:Jsonp) {}

  onclick() {
    let params = new URLSearchParams();
    params.set('url', this.url);
    params.set('callback', 'JSONP_CALLBACK');

    this.jsonp.get('http://b.hatena.ne.jp/entry/jsonlite/', { search: params })
      .subscribe(
        response => {
          let data = response.json() || {};
          this.count = data.count;

          let result: string[] = [];
          data.bookmarks.forEach(function(value: any) {
            if (value.comment !== '') {
              result.push(value.comment)
            }
          });
          this.comments = result;
        },
        error => {
          this.count = 0;
          this.comments = [];
          console.log('はてなサービスのアクセスに失敗しました。');
        }
      );
  }
}

サービスに切り出す

app.module.ts

特に切り出す際に修正の必要なし

import { NgModule }      from '@angular/core';
import { FormsModule }   from '@angular/forms';
import { JsonpModule }  from "@angular/http";
import { BrowserModule } from '@angular/platform-browser';

import { AppComponent }  from './app.component';

@NgModule({
  imports:      [ BrowserModule, FormsModule, JsonpModule ],
  declarations: [ AppComponent ],
  bootstrap:    [ AppComponent ]
})
export class AppModule { }

app.component.ts

import { Component } from '@angular/core';
import { Jsonp, URLSearchParams }  from '@angular/http';
import { HatenaService } from './hatena.service'; // サービス読み込み

@Component({
  selector: 'my-app',
  providers: [ HatenaService ], // プロバイダ登録
  template: `
  <form>
    <label for="url">URL:</label>
    <input id="url" name="url" type="url" size="50" [(ngModel)]="url" />
    <button (click)="onclick()">検索</button>
  </form>
  <div>{{count}}件</div>
  <ul>
    <li *ngFor="let comment of comments">{{comment}}</li>
  </ul>
  `,
})
export class AppComponent {
  url = 'http://gihyo.jp/';
  count = 0;
  comments: string[] = [];

  constructor(private hatena:HatenaService) {} // サービスを注入

  onclick() {
    this.hatena.requestGet(this.url)
      .subscribe(
        data => {
          let result: string[] = [];
          data.bookmarks.forEach(function(value: any) {
            if (value.comment !== '') {
              result.push(value.comment)
            }
          });
          this.comments = result;
          this.count = data.count;
        },
        error => {
          this.count = 0;
          this.comments = [];
          console.log('はてなサービスのアクセスに失敗しました。');
        }
      );
  }
}

hatena.service.ts

import { Injectable } from '@angular/core';
import { Jsonp, URLSearchParams } from '@angular/http';
import { Observable } from 'rxjs/Observable';

import 'rxjs/add/observable/throw';
import 'rxjs/add/operator/map';
import 'rxjs/add/operator/catch';

@Injectable()
export class HatenaService {

  constructor(private jsonp: Jsonp) { }

  requestGet(url: string): Observable<any> {
    let params = new URLSearchParams();
    params.set('url', url);
    params.set('callback', 'JSONP_CALLBACK');

    return this.jsonp.get('http://b.hatena.ne.jp/entry/jsonlite/', { search: params })
      .map(
        response => {
          return response.json() || {};
        }
      )
      .catch(
        error => {
          return Observable.throw(error.statusText);
        }
      );
  }
}