问题
So, as I've been exploring this new space I needed to do a Web API call. Theres a lot of confusion out there between the versions of everything. Anyhow, I found something that works, and I know "best practice" is a bit too subjective. However, what I don't know is if there is a more direct way to do this.
Here is the format of the response I'm seeking:
export interface AuditDetail {
updatedAt: Date;
updatedBy: string;
}
Here is the server-side model:
[DataContract]
public class PlanHistory
{
[Key]
public int Id { get; set; }
[DataMember]
[MaxLength(50)]
public string UpdatedBy { get; set; }
[DataMember]
public DateTime UpdatedAt { get; set; }
}
And here is my Angular service:
getAuditDetails(planId: number, fieldName: string, fieldValue: string): Observable<AuditDetail> {
//return of({ updatedAt: new Date(), updatedBy: "Hawchorn" }); //Tooltip displays data
interface PlanHistory //Created because couldn't figure out how to directly map from Json to an Audit Detail.
{
UpdatedAt: Date;
UpdatedBy: string;
}
this.log("Retrieving Audit Details");
return this.http
.get<PlanHistory>(this.webApiUrl +
"PlanHistories?planId=" +
planId +
"&fieldName=" +
fieldName +
"%20&fieldValue=" +
fieldValue).pipe(map((response: PlanHistory) => {
return <AuditDetail>{ updatedAt: response.UpdatedAt, updatedBy: response.UpdatedBy };
}));
}
That works. But I hate making that intermediate interface.
So how do I do the same thing, directly from JSON to AuditDetail?
回答1:
You want to have the Web API return camelCasing output, so you don't have to change the casing. See JSON and XML Serialization in ASP.NET Web API:
To write JSON property names with camel casing, without changing your data model, set the
CamelCasePropertyNamesContractResolveron the serializer:var json = GlobalConfiguration.Configuration.Formatters.JsonFormatter; json.SerializerSettings.ContractResolver = new CamelCasePropertyNamesContractResolver();
Then your code becomes:
getAuditDetails(planId: number, fieldName: string, fieldValue: string): Observable<AuditDetail> {
this.log("Retrieving Audit Details");
return this.http
.get<AuditDetail>(`${this.webApiUrl}PlanHistories?planId=${planId}&fieldName=${fieldName}%20&fieldValue=${fieldValue}`);
}
回答2:
The mapping should be inferred, only difference is your casing, could you not update to make the names match?
来源:https://stackoverflow.com/questions/52118204/rxjs-mapping-from-json-to-typescript-interface