【问题标题】:Host Aurelia CLI app and WebApi service on same http server在同一 http 服务器上托管 Aurelia CLI 应用程序和 WebApi 服务
【发布时间】:2016-08-09 10:38:30
【问题描述】:

您如何进行配置,以便au run 在同一个 http 服务器中启动和托管 Aurelia 应用程序和 Web API 服务?

Contact Manager 很棒,我完全理解为什么它会模拟 Web 服务,但您无法构建这样的真实应用。

是否有设置 Web 服务的演练?如果它只是从文件中读取一些 JSON 并传递它,那么真正的问题是如何设置在同一个 http 服务器中运行的 Web 服务来处理 XSS 问题。

如果没有完整的演练,请提供一些关于创建 http 服务器实例的节点代码位置的指导。 au 和 CLI 很棒,但它们隐藏了很多重要信息。

【问题讨论】:

  • 你弄明白了吗?
  • 这是一个很难回答的问题。得到一个微软服务器。设置 iis 以将虚拟目录指向您的 aurelia 应用程序,并将应用程序指向您的 Web api 应用程序。其中的 aurelia 和 web api 部分是完全解耦的,并且有很多关于如何独立完成这两项任务的资源。
  • @MatthewJamesDavis - 我尝试了这个选项,虽然我可以让它工作,但我更喜欢使用 au run --watch 来获得 BrowserSync 的好处,因此有必要根据我的回答解决 CORS 问题。
  • @Larsi - 是也不是。有一个我认为令人满意的解决方案,如下面的回答中所述。

标签: asp.net-web-api cors aurelia


【解决方案1】:

简短的回答是你不这样做。

虽然理论上可行,但这比仅仅解决 CORS 问题和为 Web API 使用单独的服务器要求更高,但用处更少。仅当您知道如何在客户端和服务器上处理 CORS 并且您知道不会想到问这个问题时,这一点才很明显。

为了帮助这条路标昏暗的道路上迷路的人,这里是如何使用 9000 上的 Aurelia 客户端处理 IIS7 MVC/WepApi2 的 CORS。

服务器

将其作为 <system.webServer> 部分的子项放入 Web API 项目根目录下的 web.config 文件中。

<httpProtocol>
  <customHeaders>
    <add name="Access-Control-Allow-Origin" value="*" />
  </customHeaders>
</httpProtocol>

对于这个例子,http://testserver/DAL3/api/Form 有一个 Web API 服务,其方法绑定到 post。

这是一个支持类

  public class JsonRequest
  {
    public int UID { get; set; }
    public string Command { get; set; }
    public string Raw { get; set; }
  }

这就是 Web 服务的样子。有一个支持它的 LINQ2SQL 模型,为简洁起见,我将其省略。

using Newtonsoft.Json;
using System.Linq;
using System.Reflection;
using System.Web.Http;

namespace DAL3.Controllers
{
  public class FormController : ApiController
  {

    // POST: api/Form
    public object Post([FromBody]JsonRequest jsr)
    {
      var T = GetType();
      var M = T.GetMethod(jsr.Command, BindingFlags.NonPublic | BindingFlags.Instance);
      var parms = new object[] { jsr.UID, jsr.Raw };
      if (M == null) return string.Format("M is null (\"{0}\")",jsr.Command);
      if (parms == null) return "parms is null";

      return M.Invoke(this, parms);
    }

    object Get(int UID, string Raw)
    {
      var dc = new Models.FormsDataContext();
      if (string.IsNullOrEmpty(Raw))
      {
        return dc.Forms.Where(x => x.FormEngine == true);
      }
      else
      {
        var id = JsonConvert.DeserializeObject<GetParams>(Raw).Id;
        return dc.Forms.Where(x => x.FormID == id);
      }
    }
  }
  //this class describes how to parse the parameters for Get
  class GetParams
  {
    public int Id { get; set; }
  }
  //if you defined some other method Quux that takes parameters 
  //create a QuuxParams class that matches what JS sends
}

所有这些反射业务都允许您在Command 中指定一个方法名称,并在Raw 中传递您喜欢的任何内容。 UID 是用户标识符。

这样做可以让您将 CORS 合规性与您的请求分开,并自动对您在 Raw 中输入的任何内容进行编码。可能应该命名为Parameters,但无论如何。现在您知道如何将它们组合在一起了。

客户

使用 bash 并将 pwd 设置为应用的根目录:

npm i aurelia-http-client --save

然后将其添加到 aurelia.json 中的供应商捆绑包依赖项中。您不需要对象,只需要双引号中的名称和尾随逗号,以适用于有效的 JSON 语法。

在您的代码中,您需要导入它。

import {HttpClient} from 'aurelia-http-client';

这是一个发布到名为 Form 的 Web API 服务的示例,该服务位于名为 testserver 的盒子上名为 DAL3 的网络应用程序中。

let foo = {
  UID: 18974,
  Command: "Get",
  Raw: null
}

let content = "UID=" + foo.UID + "&Command=" + foo.Command + "&Raw=" + JSON.stringify(foo.Raw)

let client = new HttpClient();

let req = client.createRequest("http://testserver/DAL3/api/Form")
 .asPost()
 .withHeader("Content-Type","application/x-www-form-urlencoded")
 .withContent(content)
 .send()
 .then(res => {
   console.log("Hurrah we have a response!");
 });

注意事项

以下任何一项都将导致使用动词 OPTIONS 的“预检”请求,这将导致失败。

  • 添加非标准标题
  • 使用除text/plainapplication/x-www-form-urlencoded 以外的内容类型
  • 使用 GET 或 POST 以外的动词

编码内容

对象foo 根的三个属性是URL 编码的,并用& 符号分隔,如上面的示例代码所示。 Raw 可以包含一个对象,甚至是一个对象的有向无环图。 JSON.stringify 正确处理两者。 Null 将解析为一个空字符串,但 URL 编码的解码将产生一个 null,所以这很好;重要的是 Raw 参数应该存在以满足另一端的 Web API 签名匹配。

【讨论】:

    猜你喜欢
    • 2020-12-06
    • 2020-08-10
    • 1970-01-01
    • 2018-11-18
    • 1970-01-01
    • 2016-11-17
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多