一、跨域CORS是什么
当一个资源从与该资源本身所在的服务器的域或端口不同的域或不同的端口请求一个资源时,浏览器会发起一个跨域 HTTP 请求。出于安全考虑,浏览器会限制从脚本内发起的跨域HTTP请求或者拦截了服务器返回内容。例如,XMLHttpRequest 和 Fetch 遵循同源策略。因此,使用 XMLHttpRequest或 Fetch 的Web应用程序只能将HTTP请求发送到其自己的域;这种安全机制是为避免出现类似CSRF 跨站攻击等问题。
 
二、实现CORS
根据CORS的定义和W3C相关规范,明白了跨域的关键问题是在于服务端是否允许;而服务端是通过W3C所规定的相关CORS heades来实现的;相关headers如下:
Access-Control-Allow-Origin:*
该字段是必须的。它的值要么是请求时Origin字段的值,要么是一个*,表示接受任意域名的请求。
 
Access-Control-Allow-Methods: POST, GET, OPTIONS
该字段可选。表明服务器允许客户端使用 POST, GET 和 OPTIONS
 
Access-Control-Allow-Headers: X-PINGOTHER, Content-Type
该字段可选。表明服务器允许请求中携带字段 X-PINGOTHER 与 Content-Type。
 
Access-Control-Max-Age: 86400
表明该响应的有效时间为 86400 秒,也就是 24 小时。在有效时间内,浏览器无须为同一请求再次发起预检请求。
 
Access-Control-Allow-Credentials: true
该字段可选。它的值是一个布尔值,表示是否允许发送Cookie。
 
 
三、WCF restful实现CORS
1.

  /// <summary>
/// js跨域过滤器
/// </summary>
[AttributeUsage(AttributeTargets.Class, AllowMultiple = true)]
public class CORSAttribute : Attribute, IServiceBehavior
{
public void AddBindingParameters(ServiceDescription serviceDescription, ServiceHostBase serviceHostBase, Collection<ServiceEndpoint> endpoints, BindingParameterCollection bindingParameters)
{
}
/// <summary>
/// 扩展拦截
/// </summary>
/// <param name="serviceDescription"></param>
/// <param name="serviceHostBase"></param>
public void ApplyDispatchBehavior(ServiceDescription serviceDescription, ServiceHostBase serviceHostBase)
{
foreach (ChannelDispatcher channelDispatch in serviceHostBase.ChannelDispatchers)
{
foreach (EndpointDispatcher endpointDispatch in channelDispatch.Endpoints)
{
endpointDispatch.DispatchRuntime.MessageInspectors.Add(new CrossDomain());
}
}
} public void Validate(ServiceDescription serviceDescription, ServiceHostBase serviceHostBase)
{
}
}

2.

 /// <summary>
/// js跨域过滤器
/// </summary>
public class CrossDomain : IDispatchMessageInspector
{
#region IDispatchMessageInspector
/// <summary>
/// token验证
/// </summary>
/// <param name="request"></param>
/// <param name="channel"></param>
/// <param name="instanceContext"></param>
/// <returns></returns>
public object AfterReceiveRequest(ref Message request, IClientChannel channel, InstanceContext instanceContext)
{
if (CrossDomain.DealOptions(ref request))
{
return "";
}
return string.Empty;
} /// <summary>
/// 回复内容
/// </summary>
/// <param name="reply"></param>
/// <param name="correlationState"></param>
public void BeforeSendReply(ref Message reply, object correlationState)
{
if ((string)correlationState == "")
reply = MessageTempleHelper.GetDefault(JsonResultCode.SUCESS.ToString(), "OPTIONS");
else
CrossDomain.DealtMessage(ref reply);
}
#endregion /// <summary>
/// 对已处理的消息进行cross加工
/// </summary>
/// <param name="msg"></param>
public static void DealtMessage(ref Message msg)
{
try
{
var ct = ((HttpResponseMessageProperty)msg.Properties["httpResponse"]).Headers["Content-Type"]; if (MimeTypes.Contains(ct))
{
if (ct == MimeTypes[])
{
if (!msg.Properties.ContainsKey("WebBodyFormatMessageProperty"))
{
msg.Properties.Add("WebBodyFormatMessageProperty", new WebBodyFormatMessageProperty(WebContentFormat.Json));
}
else if (msg.Properties["WebBodyFormatMessageProperty"] == new WebBodyFormatMessageProperty(WebContentFormat.Xml)) //强制将xml返回值改为json
{
msg.Properties.Remove("WebBodyFormatMessageProperty");
msg.Properties.Add("WebBodyFormatMessageProperty", new WebBodyFormatMessageProperty(WebContentFormat.Json));
}
}
var property = new HttpResponseMessageProperty();
property.StatusCode = HttpStatusCode.OK;
property.Headers.Add("Content-Type", ct);
property.Headers.Add("Access-Control-Allow-Methods", "GET, POST, PUT, DELETE, OPTIONS");
property.Headers.Add("Access-Control-Allow-Origin", "*");
property.Headers.Add("Access-Control-Allow-Headers", "Content-Type,X-Requested-With,Accept,imUserID,accessToken,appkey,userID,token");
property.Headers.Add("Access-Control-Request-Methods", "GET, POST, PUT, DELETE, OPTIONS");
property.SuppressEntityBody = false;
property.SuppressPreamble = false;
if (msg.Properties.ContainsKey("httpResponse"))
msg.Properties.Remove("httpResponse");
msg.Properties.Add("httpResponse", property);
}
}
catch (Exception ex)
{
Log4NetUtil.WriteErrLog("CrossDomain.DealtMessage", ex);
}
} /// <summary>
/// 处理新的消息
/// </summary>
/// <param name="msg"></param>
public static void DealNewMessage(ref Message msg)
{
try
{
msg.Properties.Add("WebBodyFormatMessageProperty", new WebBodyFormatMessageProperty(WebContentFormat.Json));
var property = new HttpResponseMessageProperty();
property.StatusCode = HttpStatusCode.OK;
property.Headers.Add("Content-Type", MimeTypes[]);
property.Headers.Add("Access-Control-Allow-Methods", "GET, POST, PUT, DELETE, OPTIONS");
property.Headers.Add("Access-Control-Allow-Origin", "*");
property.Headers.Add("Access-Control-Allow-Headers", "Content-Type,X-Requested-With,Accept,imUserID,accessToken,appkey,userID,token");
property.Headers.Add("Access-Control-Request-Methods", "GET, POST, PUT, DELETE, OPTIONS");
property.SuppressEntityBody = false;
property.SuppressPreamble = false;
if (msg.Properties.ContainsKey("httpResponse"))
msg.Properties.Remove("httpResponse");
msg.Properties.Add("httpResponse", property);
}
catch { } } /// <summary>
/// 对当前请求是OPTIONS进行处理
/// </summary>
/// <param name="request"></param>
/// <returns>已处理为true,未处理为false</returns>
public static bool DealOptions(ref Message request)
{
try
{
if (((System.ServiceModel.Channels.HttpRequestMessageProperty)request.Properties["httpRequest"]).Method == "OPTIONS")
{
WebOperationContext.Current.OutgoingResponse.Headers.Add("Access-Control-Allow-Methods", "GET, POST, PUT, DELETE, OPTIONS");
WebOperationContext.Current.OutgoingResponse.Headers.Add("Access-Control-Allow-Origin", "*");
WebOperationContext.Current.OutgoingResponse.Headers.Add("Access-Control-Allow-Headers", "Content-Type,X-Requested-With,Accept,imUserID,accessToken,appkey,userID,token");
WebOperationContext.Current.OutgoingResponse.Headers.Add("Access-Control-Request-Methods", "GET, POST, PUT, DELETE, OPTIONS");
WebOperationContext.Current.OutgoingResponse.StatusCode = HttpStatusCode.Accepted;
request.Close();
return true;
}
}
catch { }
return false;
} private static string[] _mimeTypes = null; /// <summary>
/// html格式
/// </summary>
public static string[] MimeTypes
{
get
{
if (_mimeTypes == null)
{
_mimeTypes = new string[] {
"application/json; charset=utf-8",
"image/png"
};
}
return _mimeTypes;
}
}
}
3.在所要公开的服务类上面[CORS],例如:

四、js测试

    <script type="text/javascript">
$(function () {
$("button").click(function () { var postData = JSON.stringify({ name: "ASDF.txt", md5Code: "F006096956B5062F8EFB72AF4DF59BC2"}); console.log(postData); $.ajax({
url: "http://127.0.0.1:16060/FileService/GetInfo",
headers: {
imUserID: "e82287ac45c14040ba8ef34b9c2dac29",
accessToken: "U6wJgLoAdxVXUpx5R6AdZnFW/ytU+kgnVzaejZZoSdR31lNoRmDsQz42viOP7Jtm3iz8L2COA16r9rl5YUvZPhpHAAWxLNJBWWjHGKibHYejUuerO9qoxEkb6Yi+apPf60MzfmZ+SIgwhs6UBYOx2AbTkMdywYPCgKh8Q/mlVImUz0BU6WG4QCqgdqIefGi3"
},
contentType: "application/json; charset=utf-8",
type: "post",
dataType: "json",
data: postData,
success: function (data) {
$("#s").html(JSON.stringify(data));
console.log(data);
},
error: function (e) {
$("#e").html(e);
console.log(e);
}
});
}); });
</script>

测试结果:

跨域CORS的更多相关文章

  1. netCore2.0 Api 跨域(Cors)

    1.在使用netCore2.0 使用WebApi的过程中涉及到了跨域处理. 在Microsoft.AspNetCore.All包中包含跨域Cors的处理,不必单独添加. 2.打开Startup.cs文 ...

  2. python 全栈开发,Day100(restful 接口,DRF组件,DRF跨域(cors组件))

    昨日内容回顾 1. 为什么要做前后端分离? - 前后端交给不同的人来编写,职责划分明确.方便快速开发 - 针对pc,手机,ipad,微信,支付宝... 使用同一个接口 2. 简述http协议? - 基 ...

  3. IIS Manager 配置文件修该,允许跨域CORS访问

    IIS Manager 配置文件修该,允许跨域CORS访问 IIS Manager 的api访问会出现跨域问题,需要 IIS Manager的配置文件中修改. 配置文件的路径:C:\Program F ...

  4. zuul+security跨域Cors问题解决

    zuul+security跨域Cors问题解决 简介 场景 在服务后台都会出现跨域cors问题,不过一般spring解决起来比较方便,在框架+框架的基础上,问题就显得特别明显了,各种冲突,不了解源码的 ...

  5. 解决dotnet-Angular的跨域(cors)问题

    解决dotnet-Angular的跨域(cors)问题 前言 之前学了点 Angular ,打算用 dotnet core 做后端,之前没接触过这方面的东西,理所当然的遇到了跨域问题,之后也解决了,所 ...

  6. MVC跨域CORS扩展

    一般的基于浏览器跨域的主要解决方法有这么几种:1.JSONP       2.IFrame方式    3.通过flash实现  4.CORS跨域资源共享  ,这里我们主要关注的是在MVC里面的CORS ...

  7. Js 跨域CORS报错 Response for preflight has invalid HTTP status code 405

    问题 公司项目H5调用接口遇到Response for preflight has invalid HTTP status code 405这样的错误,是使用PUT方式提交请求接口.Content-T ...

  8. 浏览器和服务器实现跨域(CORS)判定的原理

    前端对Cross-Origin Resource Sharing 问题(CORS,中文又称'跨域')应该很熟悉了.众所周知出于安全的考虑,浏览器有个同源策略,对于不同源的站点之间的相互请求会做限制(跨 ...

  9. Web高级 Ajax和跨域CORS

    Asynchronous JavaScript and XML 1. XMLHttpRequest 前端开发都知道,不多说. var xhr = new XMLHttpRequest(); xhr.o ...

随机推荐

  1. 蓝桥杯-n级台阶-java

    /* (程序头部注释开始) * 程序的版权和版本声明部分 * Copyright (c) 2016, 广州科技贸易职业学院信息工程系学生 * All rights reserved. * 文件名称: ...

  2. 蓝桥杯-凑算式-java

    /* (程序头部注释开始) * 程序的版权和版本声明部分 * Copyright (c) 2016, 广州科技贸易职业学院信息工程系学生 * All rights reserved. * 文件名称: ...

  3. zoj1610线段树区间覆盖

    链接https://vjudge.net/contest/66989#problem/F 坑爹的线段树,一直用区间更新做,做了半天一点眉目都没有,只好搜题解,感觉好堕落,经常不会做就搜题解,以后一定要 ...

  4. Vue项目的部署

    通过vue-cli创建的工程,默认已经打好了基础,包含vue-loader webpack. 通常我们开发中,使用npm run dev进行开发,webpack会Hot reload,不用我们手动刷新 ...

  5. Dockerfile 构建镜像 - 每天5分钟玩转容器技术(13)

    Dockerfile 是一个文本文件,记录了镜像构建的所有步骤. 第一个 Dockerfile 用 Dockerfile 创建上节的 ubuntu-with-vi,其内容则为: 下面我们运行 dock ...

  6. 用户交互式命令:read

    read命令从键盘读取变量的值,通常用在shell脚本中与用户进行交互的场合.该命令可以一次读取多个变量的值,变量和输入的值都需要使用空格隔开. 语法 read [option]... [name . ...

  7. SSH小结

    工作有一段时间了,经常用SSH登录远程机器,但对原理一直不是很了解,所以查阅了一些资料,写个小结. 一. SSH是什么? SSH的全称是Secure Shell, 是一种"用来在不安全的网络 ...

  8. nginx+gridfs+mongodb 配置访问png图片显示无法加载问题

    上传文件后,浏览器中请求:http://<nginx server ip>:<port>/gfs/<my file> 浏览器出现"无法打开页面" ...

  9. 升讯威微信营销系统开发实践:(5) Github 源码:微信接口的 .NET 封装。

    微信开发系列教程,将以一个实际的微信平台项目为案例,深入浅出的讲解微信开发.应用各环节的实现方案和技术细节. 本系列教程的最终目标是完成一个功能完善并达到高可用性能指标的微信管理软件,所以除了与微信本 ...

  10. VR全景是市场价值及前景

    消费者视角痛点:比如酒店消费行业,很多消费者在预订酒店过程中,都遇到过这样的场景:网上照片里酒店房间看着宽敞明亮,格调不凡,感觉非常喜欢,等真正推开房门插上房卡一看,却大失所望.在酒店行业,网上照片和 ...