2017-03-02 84 views
1

例如,我有一個類:當屬性不​​匹配時,如何將JSON對象轉換爲打字稿類?

export class SomeClass { 
id: number; 
name: string; 
} 

我收到JSON從服務器比看起來像這樣

[{"Id":1,"Name":"typicalname"},{"Id":2,"Name":"somename"},{"Id":3,"Name":"blablabla"},{"Id":4,"Name":"lol"},{"Id":5,"Name":"lil"},{"Id":6,"Name":"lal"}] 

如何蒙上了JSON對象的打字稿類時性能不匹配? 這就是我現在這樣做的,而且它不工作。

getSomeClass() { 
    return this.http.get(this.someClassUrl) 
    .map(response => <SomeClass[]>response.json()) 
    .catch(this.handleError); 
} 
+0

潛在的重複[http://stackoverflow.com/q/22875636/1160236](http://stackoverflow.com/q/22875636/1160236) – HirenParekh

+0

可能的重複[如何將JSON對象轉換爲打字稿類](http://stackoverflow.com/questions/22875636/how-do-i-cast-a-json-object-to-a-typescript-class) – HirenParekh

+1

@HirenParekh我看到了這個問題,但我沒」當屬性不匹配時,找到該做什麼。 – Gelo

回答

1

試試這個:

getSomeClass() { 
    return this.http.get(this.someClassUrl) 
    .map(response => { 
     let json = response.json(); 
     return json.map(m => { 
      return { 
       id: json.Id, 
       name: json.Name 
      } 
     } 
    }) 
    .catch(this.handleError); 
} 
+0

這不會做什麼要求。它不驗證反序列化的對象。 –

+2

@AluanHaddad實際上,OP明確提到「屬性不匹配」;所以問題不在於驗證。 – Henry

+0

這不是我如何解釋它,但無論如何,函數應該修改操作系統,不要返回聲明爲類的東西,因爲在給定實現的情況下這是誤導。 –

1

當你有一個類型T和值x和你寫<T>x你是不是在執行運行時意義上的演員。你正在執行一個類型斷言。這意味着你告訴TypeScript,x的類型是T

在這個特定的情況下,如果response.json()返回類型爲any的值,這也不是沒有道理用於反串行化操作,則<T>response.json()將由打字稿編譯器爲任何T被接受。這是因爲any類型與(技術上可分配的)所有內容兼容。

然而,在這種情況下,你要驗證的響應的形狀和編譯器不能爲你做這個。你需要編寫一個合適的驗證算法。

什麼是合適的,將取決於你的應用的領域,並且可以是不平凡的,但這裏有一個例子。不幸的是,因爲你的問題意味着Angular 2和RxJS,即使是一個簡單的適用答案也包含相當複雜的相當數量。

import {Http} from '@angular/http'; 
import {Observable} from 'rxjs/Observable'; 
import 'rxjs/add/operator/mergeMap'; 
import 'rxjs/add/operator/catch'; 
import 'rxjs/add/observable/of'; 

function injected(_) {} // emit decorator metadata with flag (not pertinent) 

@injected export class SomeService { 

    constructor(readonly http: Http) {} 

    getSomeValue(): Observable<Expected> { 
    return this.http.get(this.someResourceUrl) 
     .catch(handleError) 
     .mergeMap(response => { 
     const deserialized = response.json(); 
     if (isExpected(deserialized)) { 
      // note the type of derserialized is Expected in this block 
      return Observable.of(deserialized); 
     } 
     return Observable.throw('response data did not have the expected shape'); 
     }); 
    } 
} 

export interface Expected { 
    id: number; 
    name: string; 
} 

function isExpected(deserialized : any): deserialized is Expected { 
    return typeof deserialized.id === 'number' && typeof deserialized.name === 'string'; 
} 

function handleError(error) { // this is not really necessary, but was in the question 
    console.error(error); // log 
    return Observable.throw(error); // rethrow. 
} 

這裏最重要的是isExpected函數。

它採用任何類型的值,根據我們的標準對其進行驗證,並聲明如果它返回true,那麼給定的值確實是預期類型Expected

是什麼意思是預期的類型?

那麼我們的isExpected函數確定並通過返回類型向TypeScript語言提供此信息,該返回類型表示如果該函數返回true,則傳遞給它的值的類型爲Expected

這就是所謂的一個用戶定義類型保護功能,你可以在https://www.typescriptlang.org/docs/handbook/advanced-types.html閱讀更多關於它。

相關問題