除了默认的JSON和XML序列化器外,如果想使用其它格式的(比如二进制)序列化器,也是可以的。比如著名的Protobuf和Msgpack,它们都是二进制的序列化器,特点是速度快,体积小。使用方法如下。

1.定义MediaTypeFormatter,这里以定义MsgPack的formatter为例,主要代码如下。

2.WebApiConfig中注册,代码如下。

3.客户端调用(请求头中指定Accept),在.net端调用使用HttpClient,代码如下图。

附:MessagePackMediaTypeFormatter源代码。

using MsgPack;
using MsgPack.Serialization;
using System;
using System.Collections;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Net;
using System.Net.Http;
using System.Net.Http.Formatting;
using System.Net.Http.Headers;
using System.Threading.Tasks;
using System.Web; namespace HWA.OData.Site.Formatter
{
/// <summary>
/// MsgPack序列化器formatter
/// </summary>
public class MessagePackMediaTypeFormatter : MediaTypeFormatter
{
private readonly string _mime = "application/x-msgpack";
Func<Type, bool> IsAllowedType = (t) =>
{
if (!t.IsAbstract && !t.IsInterface && t != null && !t.IsNotPublic)
return true;
if (typeof(IEnumerable).IsAssignableFrom(t))
return true;
return false;
};
public MessagePackMediaTypeFormatter()
{
SupportedMediaTypes.Add(new MediaTypeHeaderValue(_mime));
}
public override bool CanWriteType(Type type)
{
if (type == null)
throw new ArgumentNullException("Type is null");
return IsAllowedType(type);
}
public override Task WriteToStreamAsync(Type type, object value, System.IO.Stream stream, HttpContent content, TransportContext transportContext)
{
if (type == null)
throw new ArgumentNullException("type is null");
if (stream == null)
throw new ArgumentNullException("Write stream is null");
var tcs = new TaskCompletionSource<object>();
if (type != typeof(string) && typeof(IEnumerable).IsAssignableFrom(type))
{
value = (value as IEnumerable<object>).ToList();
}
var serializer = MessagePackSerializer.Create<dynamic>();
serializer.Pack(stream, value);
tcs.SetResult(null);
return tcs.Task;
}
public override Task<object> ReadFromStreamAsync(Type type, Stream stream, HttpContent content, IFormatterLogger formatterLogger)
{
var tcs = new TaskCompletionSource<object>();
if (content.Headers != null && content.Headers.ContentLength == 0)
return null;
try
{
var serializer = MessagePackSerializer.Create(type);
object result;
using (var mpUnpacker = Unpacker.Create(stream))
{
mpUnpacker.Read();
result = serializer.UnpackFrom(mpUnpacker);
}
tcs.SetResult(result);
}
catch (Exception e)
{
if (formatterLogger == null) throw;
formatterLogger.LogError(String.Empty, e.Message);
tcs.SetResult(GetDefaultValueForType(type));
}
return tcs.Task;
}
public override bool CanReadType(Type type)
{
if (type == null)
throw new ArgumentNullException("type is null");
return IsAllowedType(type);
}
}
}

重点关注之自定义序列化方式(Protobuf和Msgpack)的更多相关文章

  1. WeihanLi.Redis自定义序列化及压缩方式

    WeihanLi.Redis自定义序列化及压缩方式 Intro WeihanLi.Redis 是基于 StackExchange.Redis 的扩展,提供了一些常用的业务组件和对泛型的更好支持,默认使 ...

  2. java序列化和反序列化及序列化方式

    平时我们在Java内存中的对象,是无 法进行IO操作或者网络通信的,因为在进行IO操作或者网络通信的时候,人家根本不知道内存中的对象是个什么东西,因此必须将对象以某种方式表示出来,即 存储对象中的状态 ...

  3. .Net Core 自定义序列化格式

    序列化对大家来说应该都不陌生,特别是现在大量使用WEBAPI,JSON满天飞,序列化操作应该经常出现在我们的代码上. 而我们最常用的序列化工具应该就是Newtonsoft.Json,当然你用其它工具类 ...

  4. Newtonsoft.Json高级用法 1.忽略某些属性 2.默认值的处理 3.空值的处理 4.支持非公共成员 5.日期处理 6.自定义序列化的字段名称

    手机端应用讲究速度快,体验好.刚好手头上的一个项目服务端接口有性能问题,需要进行优化.在接口多次修改中,实体添加了很多字段用于中间计算或者存储,然后最终用Newtonsoft.Json进行序列化返回数 ...

  5. Java Serializable接口(序列化)理解及自定义序列化

      1 Serializable接口 (1)简单地说,就是可以将一个对象(标志对象的类型)及其状态转换为字节码,保存起来(可以保存在数据库,内存,文件等),然后可以在适当的时候再将其状态恢复(也就是反 ...

  6. Android进程通信之一:两种序列化方式

    2月下旬辞职了,去海南度假到现在,领略了一把三亚风情也算任性和 然而这样任性带来的后果就是..不行了我必须吐槽一句.. 没毕业的找工作就这么难嘛!投了57家一家面试机会都没有,好歹给个面试机会啊!!本 ...

  7. SpringBoot修改Redis序列化方式

    前言 由于Springboot默认提供了序列化方式并不是非常理想,对于高要求的情况下,序列化的速度和序列化之后大小有要求的情况下,不能满足,所以可能需要更换序列化的方式. 这里主要记录更换序列化的方式 ...

  8. 几种序列化协议(protobuf,xstream,jackjson,jdk,hessian)相关数据对比

    测试结果 序列化数据对比 bytes字节数对比 具体的数字:   protobuf jackson xstream Serializable hessian2 hessian2压缩 hessian1 ...

  9. 自定义兼容多种Protobuf协议的编解码器

    <从零开始搭建游戏服务器>自定义兼容多种Protobuf协议的编解码器 直接在protobuf序列化数据的前面,加上一个自定义的协议头,协议头里包含序列数据的长度和对应的数据类型,在数据解 ...

随机推荐

  1. IP地址匹配

    问题描述: 在路由器中,一般来说转发模块采用最大前缀匹配原则进行目的端口查找,具体如下: IP地址和子网地址匹配: IP地址和子网地址所带掩码做AND运算后,得到的值与子网地址相同,则该IP地址与该子 ...

  2. mysql概要(九)字符集和校对集

    1.mysql 字符集有细致设置: 2.mysql字符处理机制是:数据库和客户端之间存在一个字符集转换器(后文简称转换器)将客户端字符编码(必须告诉服务端的)转换成一种中间编码的数据(可自定义的但保证 ...

  3. [转载] Codis作者黄东旭细说分布式Redis架构设计和踩过的那些坑们

    原文: http://mp.weixin.qq.com/s?__biz=MzAwMDU1MTE1OQ==&mid=208733458&idx=1&sn=691bfde670fb ...

  4. 半平面交模板(O(n*n)&& O(n*log(n))

    摘自http://blog.csdn.net/accry/article/details/6070621 首先解决问题:什么是半平面? 顾名思义,半平面就是指平面的一半,我们知道,一条直线可以将平面分 ...

  5. linux install sublime_text3

    ubuntu & debian: (baidu or google) 1). download ***.deb to install inux系统下怎么安装.deb文件? deb 是 ubun ...

  6. Java编程思想学习笔记_6(并发)

    一.从任务中产生返回值,Callable接口的使用 Callable是一种具有泛型类型参数的泛型,它的类型参数表示的是从方法call返回的值,而且必须使Executor.submit来去调用它.sub ...

  7. FLAG_ACTIVITY_CLEAR_TOP和FLAG_ACTIVITY_REORDER_TO_FRONT用法

    Activity的两种启动模式: FLAG_ACTIVITY_CLEAR_TOP和FLAG_ACTIVITY_REORDER_TO_FRONT 1. 如果已经启动了四个Activity:A,B,C和D ...

  8. iOS开发之 Xcode 6 创建一个Empty Application

    参考链接http://jingyan.baidu.com/article/2a138328bd73f2074b134f6d.html Xcode 6 正式版如何创建一个Empty Applicatio ...

  9. Yii2.0 依赖注入(DI)和依赖注入容器的原理

    依赖注入和依赖注入容器 为了降低代码耦合程度,提高项目的可维护性,Yii采用多许多当下最流行又相对成熟的设计模式,包括了依赖注入(Denpdency Injection, DI)和服务定位器(Serv ...

  10. HBase之表空间

    1.介绍 在HBase中,namespace命名空间指对一组表的逻辑分组,类似RDBMS中的database,方便对表在业务上划分.Apache HBase从0.98.0, 0.95.2两个版本开始支 ...