概述
Windows8和Windows Phone8提供了用于通过HTTP协议发送和接受网络数据的类。在Windows8中为HttpClient类,Windows Phone中为WebClient和HttpWebRequest类。
Android系统包含两种HTTP Client:HttpURLConnection和Apache HTTP Client。蓝牙技术支持HTTPS协议,流方式上传和下载,请求超时配置,IPv6和连接池。
IOS SDK的NSURLRequest及其子类提供通过http协议发送和接受网络数据的功能。
Windows Phone 8 Web服务
Web 服务允许以编程方式访问 Internet 上的各种数据。数据服务是基于 HTTP 的 Web 服务,这种 Web 服务实现开放数据协议 (OData) 以将数据公开为资源,这些资源通过数据模型进行定义并通过统一资源标识符 (URI) 进行寻址。
Web 和数据服务都使用一种基于 XML 的开放式语言来描述其基于 Web 的 API。使用 Web 服务描述语言 (WSDL) 描述 Web 服务提供的服务。概念性架构定义语言 (CSDL) 描述数据服务提供的数据模型。有关更多信息,请参见 Web 服务描述语言 (WSDL) 和概念性架构定义文件格式。
Web 服务
因为在 Internet 上发布的绝大多数 Web 服务都基于 HTTP,因此您可以使用 HttpWebRequest 和 WebClient类从 Windows Phone 应用访问 Web 服务。为了帮助减轻生成 Web 服务通常所需的其他代码的任务,可以使用服务模型代理生成工具 (SLsvcUtil.exe) 或 Visual Studio 的“添加服务引用”功能生成代理类。有关如何使用WebClient 类访问 RSS 源的示例,请参见 如何为 Windows Phone 创建基本的 RSS 读取器。
根据 Web 服务 WSDL 文件,Web 服务代理类为 Web 服务实现序列化、请求和响应代码。您可以在 Windows Phone 应用中使用生成的代理类与相应的 Web 服务进行通信。
数据服务 (OData)
数据服务是基于 HTTP 的 Web 服务,该 Web 服务实现开放数据协议 (OData) 以将数据公开为资源,这些资源通过数据模型进行定义并通过 URI 进行寻址。这使您能够使用具象状态传输 (REST) 的语义(尤其是 GET、PUT、POST 和 DELETE 等标准 HTTP 谓词)访问和更改数据。
由于数据服务是基于 HTTP 的,因此您可以使用 HttpWebRequest 和 WebClient 类从 Windows Phone 应用访问数据服务。为了帮助减轻生成数据服务所需其他代码的任务,您可以使用 WCF 数据服务客户端实用工具 DataSvcUtil.exe 或 Visual Studio 的“添加服务引用”功能生成一个基于数据服务 CSDL 文件的代理类。您可以在 Windows Phone 应用中使用生成的代理类与相应的数据服务进行通信。
在WindowsPhone应用中可以使用 HttpWebRequest 和 WebClient 类访问 Web 服务。
WebClient类
提供用于将数据发送到由 URI 标识的资源及从这样的资源接收数据的常用方法。WebClient 类提供向 URI 标识的任何本地、Intranet 或 Internet 资源发送数据以及从这些资源接收数据的。WebClient 类使用 WebRequest 类提供对资源的访问。 WebClient 实例可以通过任何已向 WebRequest.RegisterPrefix 方法注册的 WebRequest 子代访问数据。
l 属性
AllowReadStreamBuffering | 获取或设置一个值,该值指示是否对从某一 WebClient 实例的 Internet 资源读取的数据进行缓冲处理 |
AllowWriteStreamBuffering | 获取或设置一个值,该值指示是否对写入到 WebClient 实例的 Internet 资源的数据进行缓冲处理 |
BaseAddress | 获取或设置 WebClient 发出请求的基 URI |
Credentials | 获取或设置发送到主机并用于对请求进行身份验证的网络凭据 |
Encoding | 获取和设置用于上载和下载字符串的 Encoding |
Headers | 获取或设置与请求关联的标头名称/值对集合 |
IsBusy | 获取一个值,该值指示某一 Web 请求是否处于进行中 |
ResponseHeaders | 获取与响应关联的标头名称/值对集合 |
UseDefaultCredentials | 获取或设置一个 Boolean 值,该值控制默认凭据是否随请求一起发送 |
l 方法
CancelAsync | 取消一个挂起的异步操作 |
DownloadStringAsync | 以字符串形式下载位于指定 Uri 的资源 |
GetWebRequest | 为指定资源返回一个 WebRequest 对象 |
GetWebResponse | 使用指定的 IAsyncResult 返回指定 WebRequest 的 WebResponse |
OpenReadAsync | 打开流向指定资源的可读流 |
OpenWriteAsync | 打开一个流以将数据写入指定的资源。 |
UploadStringAsync | 将指定的字符串上载到指定的资源 |
l 事件
DownloadProgressChanged | 在异步下载操作成功传输部分或全部数据后发生 |
DownloadStringCompleted | 在异步资源下载操作完成时发生 |
OpenReadCompleted | 在异步资源读取操作完成时发生 |
OpenWriteCompleted | 在打开流以将数据写入资源的异步操作完成时发生 |
UploadProgressChanged | 在异步上载操作成功传输部分或全部数据后发生 |
UploadStringCompleted | 在异步字符串上载操作完成时发生 |
WriteStreamClosed | 在异步写入流操作完成时发生 |
使用WebClient类
发送请求
创建实例
1 | WebClient webClient = new WebClient(); |
设置回调
1 | webClient.DownloadStringCompleted += new DownloadStringCompletedEventHandler(webClient_DownloadStringCompleted); |
下载数据
HttpWebRequest类
此类为Windows Phone使用HTTP协议获取网络数据的另外一个选择,提供 WebRequest 类的 HTTP 特定的实现。
l 属性
Accept | 获取或设置 Accept HTTP 标头的值 |
AllowAutoRedirect | 获取或设置一个值,该值指示请求是否应跟随重定向响应 |
AllowReadStreamBuffering | 如果已在子类中重写,则获取或设置一个值,该值指示是否对从 Internet 资源读取的数据进行缓冲处理 |
AllowWriteStreamBuffering | 获取或设置一个值,该值指示是否对发送到 Internet 资源的数据进行缓冲处理 |
ContentLength | 为设置客户端发送的内容长度(以字节计)而获取 |
ContentType | 获取或设置 Content-type HTTP 标头的值 |
CookieContainer | 指定与 HTTP 请求相关联的 CookieCollection 对象的集合 |
CreatorInstance | 当在子类中重写时,获取从 IWebRequestCreate 类派生的工厂对象,该类用于创建为生成对指定 URI 的请求而实例化的 WebRequest |
Credentials | 获取或设置请求的身份验证信息 |
HaveResponse | 获取一个值,该值指示是否已收到来自 Internet 资源的响应 |
Headers | 指定一个组成 HTTP 标头的名称/值对集合 |
Method | 获取或设置请求的方法 |
RequestUri | 获取请求的原始统一资源标识符 |
SupportsCookieContainer | 获取一个值,该值指示 CookieContainer 属性是否由 HttpWebRequest 实例支持 |
UseDefaultCredentials | 当在子代类中重写时,获取或设置一个 Boolean 值,该值控制默认凭据是否随请求一起发送。 |
UserAgent | 获取或设置 User-agent HTTP 标头的值 |
l 方法
Abort | 取消对 Internet 资源的请求 |
BeginGetRequestStream | 开始对用来写入数据的 Stream 对象的异步请求 |
BeginGetResponse | 开始对 Internet 资源的异步请求 |
EndGetRequestStream | 结束对用于写入数据的 Stream 对象的异步请求 |
EndGetResponse | 结束对 Internet 资源的异步请求 |
l 扩展方法
GetCurrentNetworkInterface | 获取有关与 Web 请求相对应的网络接口的所有可用信息 |
SetNetworkPreference | 设置 Web 请求的首选项,以使用蜂窝或非蜂窝技术 |
SetNetworkRequirement | 设置 Web 请求的要求,以使用蜂窝或非蜂窝技术 |
使用HttpWebRequest类发送GET和POST请求
1. 创建实例
使用WebRequest的Create方法创建实例。
1 | var forecastRequest =WebRequest.Create(Uri) |
2.设置请求类型
当请求类型为GET时 forecastRequest.Method = "GET"
当请求类型为POST时 forecastRequest.Method = "POST"
3. 添加RequestHeader
可以使用HttpWebRequest的Headers设置请求的消息头,如:
1 | forecastRequest.Headers[ "Encoding-Type" ] = "gzip" ; |
4. 添加RequestEntity
若请求为POST时,需要向请求中添加消息体。使用BeginGetRequestStream()方法可以以流的方式添加消息体。
5. 发送请求并获取数据
使用BeginGetResponse()方法可以获得请求的响应消息。如:
1 | forecastRequest.BeginGetResponse( new AsyncCallback(HandleForecastResponse),forecastState); |
更多内容请参考:WebClient 和 HttpWebRequest
Window8 Web服务
HttpClient
HttpClient 类用于通过 HTTP 发送和接收基本要求。它提供了一个用于从 URI 所标识的资源发送 HTTP 请求和接收 HTTP 响应的基类。该类可用来向 Web 服务发送 GET、PUT、POST、DELETE 以及其他请求。上述每种请求都作为异步操作进行发送。
HttpResponseMessage 类用于声明从 HTTP 请求接收到的 HTTP 响应消息。
HttpContent 类是用于声明 HTTP 实体正文和内容标题的基类。 在这种情况下,HttpContent 用于声明 HTTP 响应。
l HttpClient类属性
BaseAddress | 获取或设置发送请求时使用的 Internet 资源的统一资源标识符 (URI) 的基地址 |
DefaultRequestHeaders | 获取与每个请求一起发送的标题 |
MaxResponseContentBufferSize | 获取或设置读取响应内容时要缓冲的最大字节数 |
Timeout | 获取或设置请求超时前等待的毫秒数 |
l HttpClient主要方法
CancelPendingRequests | 取消该实例所有挂起的请求 |
DeleteAsync | 以异步操作发送 DELETE 请求 |
GetAsync | 以异步操作发送 GET 请求 |
GetByteArrayAsync | 发送 GET 请求并在异步操作中以字节数组的形式返回响应正文 |
GetStreamAsync | 发送 GET 请求并在异步操作中以流的形式返回响应正文 |
GetStringAsync | 发送 GET 请求并在异步操作中以字符串的形式返回响应正文 |
PostAsync | 以异步操作发送 POST 请求 |
PutAsync | 以异步操作发送 PUT 请求 |
SendAsync | 以异步操作发送 HTTP 请求 |
使用HttpClient类发送GET请求
1 | HttpClient client = new HttpClient(); |
设置Web 服务的响应接受的数据量,如:
1 | httpClient.MaxResponseContentBufferSize = 256000; |
设置请求消息头,如:
1 | httpClient.DefaultRequestHeaders.Add( "user-agent" , "Mozilla/5.0 (compatible; MSIE 10.0; Windows NT 6.2; WOW64; Trident/6.0)" ); |
设置超时时间,如:
1 | httpClient.Timeout = new TimeSpan(10000); |
使用HttpClient类和HttpRequestMessage 类发送POST请求
HttpRequestMessage可以设置请求的类型,如POST、GET等,请求的地址以及请求的消息头消息体。
HttpClient类发送POST请求可以使用HttpClient.SendAsync(HttpRequestMessage)方法。如:
1 | Stream stream = GenerateSampleStream(1000); |
2 | StreamContent streamContent = new StreamContent(stream); |
3 | string resourceAddress = AddressField.Text.Trim(); |
4 | HttpRequestMessage request = new HttpRequestMessage(HttpMethod.Post, resourceAddress); |
5 | request.Content = streamContent; |
6 | request.Headers.TransferEncodingChunked = true ; |
7 | HttpResponseMessage response = await httpClient.SendAsync(request); |
获得请求返回数据
HttpResponseMessage中有请求返回的数据,可以通过ReadAsStringAsync()以string方式异步读取消息体,也可以使用ReadAsStreamAsync()以流的方式异步读取消息体。
如:
1 | HttpResponseMessage response = await httpClient.SendAsync(request); |
2 | String responseBodyAsText = await response.Content.ReadAsStringAsync(); |
3 | Stream responseStream = await response.Content.ReadAsStreamAsync() |
更多内容请参考:快速入门:使用 HttpClient 进行连接
AndroidWeb服务
以下以DefaultHttpClient介绍Andriod中通过http协议发送和接受网络数据的方法
发送GET请求
下面代码展示了Android使用DefaultHttpClient发送GET请求:
02 | HttpGet request = new HttpGet(httpUrl); |
03 | HttpClient httpClient = new DefaultHttpClient(); |
05 | HttpResponse response = httpClient.execute(request); |
06 | if (response.getStatusLine().getStatusCode()==HttpStatus.SC_OK){ |
07 | String str = EntityUtils.toString(response.getEntity()); |
10 | tv_rp.setText( "请求错误" ); |
12 | } catch (ClientProtocolException e) { |
15 | } catch (IOException e) { |
发送POST请求
下面代码展示了使用DefaultHttpClient发送POST请求:
02 | HttpPost request = new HttpPost(httpUrl); |
03 | Listparams = new ArrayList(); |
04 | params.add( new BasicNameValuePair( "par" , "request-post" )); |
06 | HttpEntity entity = new UrlEncodedFormEntity(params, "UTF-8" ); |
07 | request.setEntity(entity); |
08 | HttpClient client = new DefaultHttpClient(); |
09 | HttpResponse response = client.execute(request); |
10 | if (response.getStatusLine().getStatusCode()==HttpStatus.SC_OK){ |
11 | String str = EntityUtils.toString(response.getEntity()); |
14 | tv_rp.setText( "请求错误" ); |
16 | } catch (UnsupportedEncodingException e) { |
19 | } catch (ClientProtocolException e) { |
22 | } catch (IOException e) { |
IOS web服务
以下以NSMutableURLRequest(NSURLRequest的子类)为例,介绍IOS中通过http发送和接受网络数据的方法。
发送Get请求:
01 | NSURL *url = [NSURL URLWithString:URLString]; |
02 | NSMutableURLRequest *request = [[[NSMutableURLRequest alloc] init] autorelease]; |
04 | [request setHTTPMethod:@ "GET" ]; |
05 | NSURLConnection *conn = [[[NSURLConnection alloc] initWithRequest:request delegate:nil] autorelease]; |
07 | NSURL *url = [NSURL URLWithString:URLString]; |
08 | NSMutableURLRequest *request = [[[NSMutableURLRequest alloc] init] autorelease]; |
10 | [request setHTTPMethod:@ "GET" ]; |
11 | NSURLConnection *conn = [[[NSURLConnection alloc] initWithRequest:request delegate:nil] autorelease]; |
发送Post请求:
01 | NSURL *url = [NSURL URLWithString:URLString]; |
02 | NSData* data = xxxxxxxxxxx; |
03 | NSMutableURLRequest *request = [[[NSMutableURLRequest alloc] init] autorelease]; |
05 | [request setHTTPMethod:@ "POST" ]; |
06 | [request setHTTPBody:data]; |
07 | [request setValue:@ "application/json" forHTTPHeaderField:@ "Accept" ]; |
08 | [request setValue:@ "application/json" forHTTPHeaderField:@ "Content-Type" ]; |
09 | [request setValue:[NSString stringWithFormat:@ "%d" , [data length]] forHTTPHeaderField:@ "Content-Length" ]; |
10 | NSURLConnection *conn = [[[NSURLConnection alloc] initWithRequest:request delegate:nil] autorelease]; |
序列化和反序列化
在Http请求中,请求和响应的实体通常为XML或Json格式。
XML
Windows phone和Windows
System.Xml.Serialization命名空间下提供XmlSerializer类,将对象序列化到 XML 文档中和从 XML 文档中反序列化对象。如下代码展示了如何使用XmlSerializer类
序列化
2 | var type = obj.GetType(); |
3 | var xmlSerializer = new XmlSerializer(type); |
4 | var sb = new StringBuilder(); |
5 | xmlSerializer.Serialize(XmlWriter.Create(sb), obj); |
7 | var xmlSerializer = new XmlSerializer(typeof(T)); |
8 | var stringReader = new StringReader(xml); |
9 | obj = (T)xmlSerializer.Deserialize(stringReader); |
Android
在Android平台上可以使用Simple API for XML(SAX) 、 Document Object Model(DOM)和Android附带的pull解析器解析XML文件。SAX解析器的优点是解析速度快,占用内存少。非常适合在Android移动设备中使用。由于DOM在内存中以树形结构存放,因此检索和更新效率会更高。但是对于特别大的文档,解析和加载整个文档将会很耗资源。PULL解析器小巧轻便,解析速度快,简单易用,非常适合在Android移动设备中使用,Android系统内部在解析各种XML时也是用PULL解析器
Ios
iOS SDK提供了NSXMLParser和libxml2两个类库
● NSXMLParser,NSXMLParser Class Reference ,这是一个SAX方式解析XML的类库,默认包含在iOS SDK中,使用也比较简单。
● libxml2,http://xmlsoft.org/,是一套默认包含在iOS SDK中的开源类库,它是基于C语言的API,所以使用起来可能不如NSXML方便。这套类库同时支持DOM和SAX解析,libxml2的SAX解析方式还是非常酷的,因为它可以边读取边解析,尤其是在从网上下载一个很大的XML文件,就可以一边下载一边对已经下载好的内容进行解析,极大的提高解析效率
Json
Windows phone和Windows
System.Runtime.Serialization.Json提供DataContractJsonSerializer类对Json进行序列化和反序列化为对象。如下代码展示如何使用DataContractJsonSerializer
对象转化为JSON字符串使用WriteObject方法:
01 | var config = new Config(){ |
03 | plugins = new string[]{ "python" , "C++" , "C#" }, |
04 | indent = new Indent(){ length = 4, use_space = false } |
06 | var serializer = new DataContractJsonSerializer(typeof(Config)); |
07 | var stream = new MemoryStream(); |
08 | serializer.WriteObject(stream, config); |
09 | byte[] dataBytes = new byte[stream.Length]; |
11 | stream.Read(dataBytes, 0, ( int )stream.Length); |
12 | string dataString = Encoding.UTF8.GetString(dataBytes); |
JSON字符串转对象使用ReadObject方法:
1 | var mStream = new MemoryStream(Encoding.Default.GetBytes(dataString)); |
2 | Config readConfig = (Config)serializer.ReadObject(mStream); |
Android
android的json解析部分都在包org.json下,主要有以下几个类:
JSONObject可以看作是一个json对象,这是系统中有关JSON定义的基本单元,其包含一对儿(Key/Value)数值
JSONStringer构建json文本
JSONArray、它代表一组有序的数值。将其转换为String输出(toString)所表现的形式是用方括号包裹,数值以逗号”,”分隔
JSONTokener按照RFC4627规范将json文本解析为相应的对象。
JSONException 处理json解析异常
IOS
在ios5中,苹果引入了NSJSONSerialization用来序列化和反序列化json数据,
通过NSJSONSerialization这个类的JSONObjectWithData:options:error:方法来实现反序列化。
通过NSJSONSerialization这个类的dataWithJSONObject:options:error:方法来实现序列化