angular 4 odata删除/发布不工作

时间:2017-06-29 16:09:06

标签: angular odata angular-services

我创建了一个简单的测试类,用于向OData API发出我的http请求(两者都在我的本地机器上运行,并启用了COR)。我的OData服务看起来像这样:

import { Injectable } from '@angular/core';

import { Http, Response, RequestOptionsArgs, Headers } from '@angular/http';

import { Observable } from 'rxjs';
import 'rxjs/add/operator/map';

import { IUrlOptions } from './odata.model';
import { RequestTypes } from './odata.model';

@Injectable()
export class ODataService {

    constructor(
        private host: string,
        private http: Http
    ) {  }


    private constructUrl(urlOptions: IUrlOptions): string {
        return this.host + urlOptions.restOfUrl;
    }



    //T specifies a generic output of function
    public Request<T>(requestType: RequestTypes, urlOptions: IUrlOptions, body?: any, options?: RequestOptionsArgs) : Observable<T> {
        let response: Observable<Response>;

        if(requestType == RequestTypes.delete){
            response = this.http.delete(this.constructUrl(urlOptions), options);
        } else if(requestType == RequestTypes.get){

            response = this.http.get(this.constructUrl(urlOptions), options);
        } else if (requestType == RequestTypes.post){
            response = this.http.post(this.constructUrl(urlOptions), body, options)
        }

        return response.map((res) => <T>res.json());
    }
}

现在我有一个组件来测试这项服务:

import { Component, OnInit } from '@angular/core';

import { ODataService } from './odata.service';
import { RequestTypes } from './odata.model';
import { IUrlOptions } from './odata.model';

import  { Template } from '../../models/template.model' 

@Component({
    selector: 'odata',
    templateUrl: 'odata.component.html'
})
export class ODataComponent implements OnInit {


    public requestResult: any;

    constructor(
        private odata: ODataService
    ) { }

    ngOnInit() { }

    testGet() {
        let urlOptions: IUrlOptions = <IUrlOptions>{};
        urlOptions.restOfUrl = "Template";
        this.odata.Request(RequestTypes.get, urlOptions).subscribe(
            data => this.requestResult = data,
            error => alert(error)
        );
    }

    testPost() {
        let urlOptions: IUrlOptions = <IUrlOptions>{};
        urlOptions.restOfUrl = "Template";
        let body = new Template();
        body.Name = "Test3";
        body.Private = false;
        body.User = "chp";

        let jsonBody = JSON.stringify(body);

        this.odata.Request(RequestTypes.post, urlOptions, jsonBody).subscribe(
            data => this.requestResult = data,
            error => alert(error)
        );
    }

    testPut() {
        let urlOptions: IUrlOptions = <IUrlOptions>{};
        this.odata.Request(RequestTypes.put, urlOptions).subscribe(
            data => this.requestResult = data,
            error => alert(error)
        );
    }

    testPatch() {
        let urlOptions: IUrlOptions = <IUrlOptions>{};
        this.odata.Request(RequestTypes.patch, urlOptions).subscribe(
            data => this.requestResult = data,
            error => alert(error)
        );
    }

    testDelete() {
        let urlOptions: IUrlOptions = <IUrlOptions>{};
        urlOptions.restOfUrl = "Template(6)"
        this.requestResult = this.odata.Request(RequestTypes.delete, urlOptions);
    }

}

忽略Put和Patch,因为它们尚未实现,唯一可行的服务是GET。 POST和DELETE似乎根本不起作用;调用DELETE http://localhost:53219/Template(6)应删除ID为6的模板,该模板在使用SOAP UI完成时有效,但不使用第一个代码片段中定义的this.http.delete(...)函数。

此外,查看Chrome上的网络录音,看起来不像删除请求,我错过了调用该功能的内容吗?

我的SOAP UI请求如下:

DELETE http://localhost:53219/Template(6) HTTP/1.1
Accept-Encoding: gzip,deflate
Content-Type: application/json
Content-Length: 83
Host: localhost:53219
Connection: Keep-Alive
User-Agent: Apache-HttpClient/4.1.1 (java 1.5)

任何帮助将不胜感激

1 个答案:

答案 0 :(得分:0)

这最终成为了一个Header / CORs问题。 我做了以下步骤来修复它:

  1. 在我的请求中添加了以下标题:
  2. let headers = new Headers();
    headers.append("OData-Version","4.0");
    headers.append("Content-Type","application/json;odata.metadata=minimal");
    headers.append("Accept","application/json");
    return headers;
    
    1. 然后我还必须在我的OData API服务器上公开标题,因为Chrome和其他较新的浏览器会执行一些发送OPTIONS请求的“飞行前”内容(了解更多here)。为此,我在 WebApiConfi.cs
    2. 中添加了以下内容
       var cors = new EnableCorsAttribute(origins: "*", headers: "*", methods: "*", exposedHeaders: "*");
                  config.EnableCors(cors);
      

      这会在所有控制器上启用CORS,您可以在上面的链接中提到的各个控制器或方法上指定它。