Deployd - 通过AngularJS CORS检索的数据

时间:2014-04-28 16:55:20

标签: javascript angularjs cors deployd

我目前正在阅读Adam Freeman撰写的“Pro AngularJS”。通过这些示例,他让读者使用Angular(当然)和Deployd服务器资源创建了一个体育商店应用程序。 Deployd资源设置为返回要填充到模型中的JSON数据。我正在使用NodeJS来运行我的服务器。它目前在端口5000(http://localhost:5000/sportsstore/app.html)上设置。 Deployd资源在端口5500(http://localhost:5500/products)上运行。点击Deployd时,响应如下:

[
    { "name": "Kayak", "description": "A boat for one person", "category": "Watersports", "price": 275, "id": "a1c999fc248b2959" },
    { "name": "Lifejacket", "description": "Protective and fashionable", "category": "Watersports", "price": 48.95, "id": "61303717cfad182e" },
    { "name": "Soccer Ball", "description": "FIFA-approved size and weight", "category": "Soccer", "price": 19.5, "id": "0fb5f67bdcbd992f" },
    { "name": "Corner Flags", "description": "Give your playing field a professional touch", "category": "Soccer", "price": 34.95, "id": "24385d315dd388b4" },
    { "name": "Stadium", "description": "Flat-packed 35,000-seat stadium", "category": "Soccer", "price": 79500, "id": "500fb6805905a856" },
    { "name": "Thinking Cap", "description": "Improve your brain efficiency by 75%", "category": "Chess", "price": 16, "id": "637d8a1f42e6fa1c" },
    { "name": "Unsteady Chair", "description": "Secretly give your opponent a disadvantage", "category": "Chess", "price": 29.95, "id": "73393312ec7dfab7" },
    { "name": "Human Chess Board", "description": "A fun game for the family", "category": "Chess", "price": 75, "id": "7871d02a662b0915" },
    { "name": "Bling-Bling King", "description": "Gold plated, diamon-studded King", "category": "Chess", "price": 1200, "id": "b59a3389a0e248bd" }
]

我正在尝试使用$http.get

检索此数据
$http.get("http://localhost:5500/products")
    .success(function (data) { ... })
    .error(function (error) { ... });

但是,这会导致返回错误:

XMLHttpRequest cannot load http://localhost:5500/products. No 'Access-Control-Allow-Origin' header is present on the requested resource. Origin 'http://localhost:5000' is therefore not allowed access. 

研究表明,Angular和CORS存在一些问题,并且标头必须配置为运行跨域请求。结果,我在app.config中添加了以下内容:

$http.defaults.useXDomain = true;
delete $http.defaults.headers.common['X-Requested-With']; // this isn't needed anymore, but was put here as a just-in-case

尽管添加了这些设置,但我仍然收到错误消息。 Deployd文档说它是为CORS(Cross-Origin Requests)自动配置的,只要请求不包含无效的自定义标头,它就会发送相应的标头信息。我很确定我的请求不包含无效的自定义标头:

Accept: application/json, text/plain, */*
Cache-Control: max-age=0
Origin: http://localhost:5000
Referer: http://localhost:5000/sportsstore/app.html
User-Agent: Mozilla/5.0 (Windows NT 6.3; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/34.0.1847.131 Safari/537.36

我的问题:为了让Deployd配置为允许CORS请求处理,我是否需要实施其他配置?本书未指定任何特殊的Angular标头设置或其他任何内容。

7 个答案:

答案 0 :(得分:11)

Bic,将您的deployd版本升级到版本0.6.10。这对我有用。我现在能够处理get请求。看起来AngularJS代码和Adam Freeman的书都不是错误。

在书中,他确实提到他在http://www.apress.com/9781430264484上包含了deployd程序和源代码下载。这个版本是0.6.9。我确定它能正常使用它。它比试图找到0.6.10版本更容易..这就是我所做的。如果你想要那个版本,请点击这里:

https://www.versioneye.com/nodejs/deployd/0.6.10

它不是安装程序,因此您必须将其粘贴到deployd目录中,替换node_modules

答案 1 :(得分:4)

只需运行" npm update"在您的deployd安装文件夹中,它将确保您已更新到最新版本0.6.10。在阅读了javaauthority的答案之后,这解决了我的问题(谢谢你:))。

答案 2 :(得分:1)

您可以将文件(app.html,sportStore.js,...)放在deployd项目的公共文件夹下,并使用以下URL http://localhost:5500/app.html

答案 3 :(得分:1)

我要解决的问题是使用“--disable-web-security”标志启动Chrome。但首先转到任务管理器并关闭您在那里的每个chrome进程。

答案 4 :(得分:1)

虽然我提供了正确的答案而其他人已经对其进行了改进,但如果您不使用本书中提到的Deployd Web服务器,该怎么办?我使用Wildfly(JBOSS 8.X),我不得不让CORS问题适用于它。我创建了一个名为CorsFilter的简单Java类。如果你正在运行Wildfly,那么进口应该很容易找到。

希望这有助于其他与不同网络服务器有类似问题的人。

请注意:responseContext.getHeaders()。add(" Access-Control-Allow-Origin"," *");

注意上面一行中的*?这将允许任何请求成功。这通常适用于本地开发工作,但应为生产/暂存环境实施更严格的安全控制。例如,您只能接受来自某个IP地址的请求。

import org.jboss.resteasy.annotations.interception.HeaderDecoratorPrecedence;
import org.jboss.resteasy.annotations.interception.ServerInterceptor;

import javax.servlet.FilterChain;
import javax.servlet.ServletException;
import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;
import javax.servlet.annotation.WebFilter;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.ws.rs.container.ContainerRequestContext;
import javax.ws.rs.container.ContainerResponseContext;
import javax.ws.rs.container.ContainerResponseFilter;
import javax.ws.rs.ext.Provider;
import java.io.IOException;

/**
 * Class to .
 * User: Java Authority
 * Date: 12/6/2014
 * Time: 12:38 PM
 */
@Provider
@ServerInterceptor
@HeaderDecoratorPrecedence
@WebFilter
public class CorsFilter implements ContainerResponseFilter {

    public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException {
        HttpServletRequest r = (HttpServletRequest)request;
        HttpServletResponse s = (HttpServletResponse)response;
        chain.doFilter(request, response);
    }


    @Override
    public void filter(ContainerRequestContext requestContext, ContainerResponseContext responseContext) throws IOException {
        responseContext.getHeaders().add("Access-Control-Allow-Origin", "*");
        responseContext.getHeaders().add("Access-Control-Allow-Headers", "Origin, X-Requested-With, Content-Type, Accept");
    }
}

答案 5 :(得分:0)

我用fiddler修改了deployd的响应。此链接将显示如何向fiddler添加自定义规则,以便为所有响应添加Access-Control-Allow-Origin: *标头。它很棒。

http://www.leggetter.co.uk/2010/03/19/using-fiddler-to-help-develop-cross-domain-capable-javascript-web-applications.html

答案 6 :(得分:0)

Angular还会发送DPD拒绝的自定义标头,将其放入您的代码中以便dev删除这些标头并且DPD可以正常工作:

delete $http.defaults.headers.common['X-Requested-With'];