Load json from local file with http.get() in angular 2

前端 未结 7 1002
情歌与酒
情歌与酒 2020-11-29 00:38

I\'m trying to load a local json with http.get() in angular 2. I tried something, that I found here on stack. It looks like this:

this is my app.m

相关标签:
7条回答
  • 2020-11-29 01:14

    I found that the simplest way to achieve this is by adding the file.json under folder: assets.

    No need to edit: .angular-cli.json

    Service

    @Injectable()
    export class DataService {
      getJsonData(): Promise<any[]>{
        return this.http.get<any[]>('http://localhost:4200/assets/data.json').toPromise();
      }
    }
    

    Component

    private data: any[];
    
    constructor(private dataService: DataService) {}
    
    ngOnInit() {
        data = [];
        this.dataService.getJsonData()
          .then( result => {
            console.log('ALL Data: ', result);
            data = result;
          })
          .catch( error => {
            console.log('Error Getting Data: ', error);
          });
      }
    

    Extra:

    Ideally, you only want to have this in a dev environment so to be bulletproof. create a variable on your environment.ts

    export const environment = {
      production: false,
      baseAPIUrl: 'http://localhost:4200/assets/data.json'
    };
    

    Then replace the URL on the http.get for ${environment.baseAPIUrl}

    And the environment.prod.ts can have the production API URL.

    Hope this helps!

    0 讨论(0)
  • 2020-11-29 01:18

    MY OWN SOLUTION

    I created a new component called test in this folder:

    I also created a mock called test.json in the assests folder created by angular cli (important):

    This mock looks like this:

    [
            {
                "id": 1,
                "name": "Item 1"
            },
            {
                "id": 2,
                "name": "Item 2"
            },
            {
                "id": 3,
                "name": "Item 3"
            }
    ]
    

    In the controller of my component test import follow rxjs like this

    import 'rxjs/add/operator/map'
    

    This is important, because you have to map your response from the http get call, so you get a json and can loop it in your ngFor. Here is my code how I load the mock data. I used http get and called my path to the mock with this path this.http.get("/assets/mock/test/test.json"). After this i map the response and subscribe it. Then I assign it to my variable items and loop it with ngFor in my template. I also export the type. Here is my whole controller code:

    import { Component, OnInit } from "@angular/core";
    import { Http, Response } from "@angular/http";
    import 'rxjs/add/operator/map'
    
    export type Item = { id: number, name: string };
    
    @Component({
      selector: "test",
      templateUrl: "./test.component.html",
      styleUrls: ["./test.component.scss"]
    })
    export class TestComponent implements OnInit {
      items: Array<Item>;
    
      constructor(private http: Http) {}
    
      ngOnInit() {
        this.http
          .get("/assets/mock/test/test.json")
          .map(data => data.json() as Array<Item>)
          .subscribe(data => {
            this.items = data;
            console.log(data);
          });
      }
    }
    

    And my loop in it's template:

    <div *ngFor="let item of items">
      {{item.name}}
    </div>
    

    It works as expected! I can now add more mock files in the assests folder and just change the path to get it as json. Notice that you have also to import the HTTP and Response in your controller. The same in you app.module.ts (main) like this:

    import { BrowserModule } from '@angular/platform-browser';
    import { NgModule } from '@angular/core';
    import { HttpModule, JsonpModule } from '@angular/http';
    
    
    import { AppComponent } from './app.component';
    import { TestComponent } from './components/molecules/test/test.component';
    
    
    @NgModule({
      declarations: [
        AppComponent,
        TestComponent
      ],
      imports: [
        BrowserModule,
        HttpModule,
        JsonpModule
      ],
      providers: [],
      bootstrap: [AppComponent]
    })
    export class AppModule { }
    
    0 讨论(0)
  • 2020-11-29 01:24

    You have to change

    loadNavItems() {
            this.navItems = this.http.get("../data/navItems.json");
            console.log(this.navItems);
        }
    

    for

    loadNavItems() {
            this.navItems = this.http.get("../data/navItems.json")
                            .map(res => res.json())
                            .do(data => console.log(data));
                            //This is optional, you can remove the last line 
                            // if you don't want to log loaded json in 
                            // console.
        }
    

    Because this.http.get returns an Observable<Response> and you don't want the response, you want its content.

    The console.log shows you an observable, which is correct because navItems contains an Observable<Response>.

    In order to get data properly in your template, you should use async pipe.

    <app-nav-item-comp *ngFor="let item of navItems | async" [item]="item"></app-nav-item-comp>
    

    This should work well, for more informations, please refer to HTTP Client documentation

    0 讨论(0)
  • 2020-11-29 01:25

    If you are using Angular CLI: 7.3.3 What I did is, On my assets folder I put my fake json data then on my services I just did this.

    const API_URL = './assets/data/db.json';

    getAllPassengers(): Observable<PassengersInt[]> {
        return this.http.get<PassengersInt[]>(API_URL);
      }
    

    0 讨论(0)
  • 2020-11-29 01:28

    For Angular 5+ only preform steps 1 and 4


    In order to access your file locally in Angular 2+ you should do the following (4 steps):

    [1] Inside your assets folder create a .json file, example: data.json

    [2] Go to your angular.cli.json (angular.json in Angular 6+) inside your project and inside the assets array put another object (after the package.json object) like this:

    { "glob": "data.json", "input": "./", "output": "./assets/" }

    full example from angular.cli.json

    "apps": [
        {
          "root": "src",
          "outDir": "dist",
          "assets": [
            "assets",
            "favicon.ico",
            { "glob": "package.json", "input": "../", "output": "./assets/" },
            { "glob": "data.json", "input": "./", "output": "./assets/" }
          ],
    

    Remember, data.json is just the example file we've previously added in the assets folder (you can name your file whatever you want to)

    [3] Try to access your file via localhost. It should be visible within this address, http://localhost:your_port/assets/data.json

    If it's not visible then you've done something incorrectly. Make sure you can access it by typing it in the URL field in your browser before proceeding to step #4.

    [4] Now preform a GET request to retrieve your .json file (you've got your full path .json URL and it should be simple)

     constructor(private http: HttpClient) {}
            // Make the HTTP request:
            this.http.get('http://localhost:port/assets/data.json')
                     .subscribe(data => console.log(data));
    
    0 讨论(0)
  • 2020-11-29 01:33

    I you want to put the response of the request in the navItems. Because http.get() return an observable you will have to subscribe to it.

    Look at this example:

    // version without map
    this.http.get("../data/navItems.json")
        .subscribe((success) => {
          this.navItems = success.json();          
        });
    
    // with map
    import 'rxjs/add/operator/map'
    this.http.get("../data/navItems.json")
        .map((data) => {
          return data.json();
        })
        .subscribe((success) => {
          this.navItems = success;          
        });

    0 讨论(0)
提交回复
热议问题