發(fā)文章
發(fā)文工具
撰寫
網(wǎng)文摘手
文檔
視頻
思維導(dǎo)圖
隨筆
相冊(cè)
原創(chuàng)同步助手
其他工具
圖片轉(zhuǎn)文字
文件清理
AI助手
留言交流
題目有些大,但文中談到的問題很??;看似表揚(yáng)C#,實(shí)際不是。
這個(gè)小問題來自這樣的應(yīng)用場景——以HTTP POST的方式調(diào)用第三方API,第三方API不支持JSON傳參,只能通過URL query string方式傳參(a=1&b=2)。
假設(shè)API的地址是http://www.cnblogs.com/api/say,需要傳遞的參數(shù)是username與words,只支持HTTP POST調(diào)用。
jQuery中的調(diào)用示例代碼
var postData = { username: 'test', words: 'hello world' }; $.ajax({ url: 'http://www.cnblogs.com/api/say', data: postData, type: 'post', });
在上面的Javascript代碼執(zhí)行時(shí),jQuery會(huì)自動(dòng)將js對(duì)象postData轉(zhuǎn)換為Url query string的形式(username=test&words=hello+world),并自動(dòng)進(jìn)行Url encode。
PHP中的調(diào)用示例代碼
$url = 'http://www.cnblogs.com/api/say'; $data = array('username' => 'test', 'words' => 'hello world'); $data = http_build_query($data); $ch = curl_init(); curl_setopt($ch, CURLOPT_URL, $url); curl_setopt($ch, CURLOPT_POST, 1); curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1); curl_setopt($ch, CURLOPT_POSTFIELDS, $data); $response = curl_exec($ch); curl_close($ch);
PHP內(nèi)置的http_build_query()函數(shù)能自動(dòng)將數(shù)組轉(zhuǎn)換為Url query string的形式(username=test&words=hello+world),并自動(dòng)進(jìn)行Url encode。
C#中的調(diào)用示例代碼
1、在.NET Framework 4.0中的實(shí)現(xiàn)(HttpWebRequest+匿名類型+反射+LINQ)
參數(shù)通過匿名類型(Anonymous Type)進(jìn)行定義:
var postData = new { username = "test", words = "hello world" };
.NET Framework 4.0的類庫中沒有提供直接將“匿名類型實(shí)例”轉(zhuǎn)換為“Url查詢參數(shù)”的API,只能借助“反射+LINQ”自己實(shí)現(xiàn)。實(shí)現(xiàn)代碼如下:
static void Main(string[] args) { var url = "http://www.cnblogs.com/api/say"; var postData = new { username = "test", words = "hello world" }; var webRequest = WebRequest.Create(url) as HttpWebRequest; webRequest.Method = "post"; webRequest.ContentType = "application/x-www-form-urlencoded"; var queryString = string.Join("&", from p in postData.GetType().GetProperties() select p.Name + "=" + HttpUtility.UrlEncode(p.GetValue(postData, null).ToString())); using (var sw = new StreamWriter(webRequest.GetRequestStream())) { sw.Write(queryString); } using (var response = webRequest.GetResponse()) { using (var sr = new StreamReader(response.GetResponseStream())) { Console.WriteLine(sr.ReadToEnd()); } } }
2、在.NET Framework 4.5中的實(shí)現(xiàn)(HttpClient+FormUrlEncodedContent)
.NET Framework 4.5考慮到了這個(gè)應(yīng)用場景,提供了FormUrlEncodedContent,但它不支持匿名類型(Anonymous Type),只支持字典(Dictionary)。參數(shù)需要這樣定義:
var postData = new Dictionary<string, string> { { "username", "test" }, { "words", "hello world" } };
完整實(shí)現(xiàn)代碼如下(需要引用System.Net.Http):
static void Main(string[] args) { var url = "http://www.cnblogs.com/api/say"; var postData = new Dictionary<string, string> { { "username", "test" }, { "words", "hello world" } }; var urlEncodedContent = new FormUrlEncodedContent(postData); var httpClient = new HttpClient(); var result = httpClient.PostAsync(url, urlEncodedContent).Result.Content.ReadAsStringAsync().Result; Console.WriteLine(result); }
.NET Framework 4.5中的實(shí)現(xiàn)還算簡單,但是FormUrlEncodedContent只支持Dictionary,考慮還是不周到。
感想
.NET因互聯(lián)網(wǎng)而生,而通過URL query string傳參的需求在互聯(lián)網(wǎng)應(yīng)用中普通存在,但.NET從4.5才開始考慮這個(gè)應(yīng)用場景,實(shí)在有點(diǎn)說不過去。
多數(shù)開發(fā)互聯(lián)網(wǎng)應(yīng)用多年的.NET開發(fā)者都有多年拼接字符串的經(jīng)歷,但是.NET也沒考慮到這個(gè)場景,比如雙引號(hào)問題(字符串不支持單引號(hào)內(nèi)直接包含雙引號(hào))。即使拼接字符串,也沒有Javascript與PHP中操作方便。
.NET功能強(qiáng)大、設(shè)計(jì)領(lǐng)先,但是對(duì)互聯(lián)網(wǎng)應(yīng)用場景缺少細(xì)致入微的考慮,在用.NET開發(fā)互聯(lián)網(wǎng)應(yīng)用時(shí)經(jīng)常有殺雞用牛刀的感覺。幸虧牛刀上有非常舒服的刀柄(Visual Studio),才吸引了如些多的開發(fā)者。如果互聯(lián)網(wǎng)應(yīng)用是未來,即使刀柄再舒服,用牛刀殺雞的感覺畢竟不好,牛刀自身的改變才是解決之道。
來自: 昵稱10504424 > 《C#》
0條評(píng)論
發(fā)表
請(qǐng)遵守用戶 評(píng)論公約
深入理解HTTP協(xié)議之POST方法——ajax實(shí)例
2. 如果在Linux下面運(yùn)行 wget --post-data="xxxxxxxx" url的命令來發(fā)送post請(qǐng)求 ,或者是post curl推送,都是把數(shù)據(jù)“xxxxxxxx...
C# : 模擬請(qǐng)求初步應(yīng)用,制作網(wǎng)頁游戲輔助程序(開心網(wǎng)爭車位、咬人、買房子、虛擬朋友、禮物)
/login/login.php,就是登陸的請(qǐng)求地址,全部連接應(yīng)該是:http://www.kaixin001.com/login/login.php。/// <summary> /// ...
用Socket實(shí)現(xiàn)HTTP協(xié)議的文件上傳
//要發(fā)送文件的URL var $formData; //發(fā)送的表單數(shù)據(jù) var $fileData; //文件數(shù)據(jù) var $boundary; //數(shù)據(jù)分隔標(biāo)識(shí) var $response; //保存服務(wù)器返回的信息 var $username; //需要身份驗(yàn)證時(shí)的用戶名 var...
php curl登錄cookie值存取示例
php curl登錄cookie值存取示例php curl登錄cookie值存取示例www.111cn.net 編輯:phper 來源:轉(zhuǎn)載很多同學(xué)都在問為什么時(shí)候curl登錄之后cookie取不了或存儲(chǔ)不了怎么辦,下面我來給大家演示兩個(gè)php curl ...
一個(gè)jquery-ajax post例子ajax 登陸
jquery ajax的例子
jquery ajax的例子jquery ajax的例子。$.get( ''ajax_json.php'', { username:$("#input1").val(), age:$("#input2").val(), sex...
使用jquery ajax代替iframe
使用jquery ajax代替iframe.稍微介紹下jquery ajax,首先我們來比較下傳統(tǒng)和jquery的ajax的不同。<div id="content" style="border: 1px solid red;width: 210px"></div&...
前端實(shí)用插件大全
1.操作cookie的插件jquery.cookie.js。$(''#username'').val( $.cookie(COOKIE_NAME) );$.cookie(COOKIE_NAME, $('...
php+jquery+ajax+json的一個(gè)最簡單實(shí)例
php+jquery+ajax+json的一個(gè)最簡單實(shí)例php+jquery+ajax+json的一個(gè)最簡單實(shí)例html頁面:<html><head><meta http-equiv="content-type" content="text/html;charset=utf-...
微信掃碼,在手機(jī)上查看選中內(nèi)容