前言
前面寫了《各大招聘網站資訊實時查詢瀏覽》,關注的朋友還真不少。各種意見的提,我也覺得意見挺好的,也就一一採納了。
有朋友說,希望能在手機端訪問。好,採納。有朋友說,選擇區域太少了。好,我加上。有朋友說,希望能在本頁面檢視詳情。ok,我同意。
額,差不多就這些改動了。
效果圖
使用webapi提供資料
為什麼要用webapi提供資料?
- 資料部分和顯示部分分離
- 可以各終端呼叫資料展示
因為我這裡請求的時候,是實時訪問的招聘網站,所以請求過程要耗費一定的時間。但是,資訊的更新並不頻繁。我們可以在webapi中使用快取。
在guget命令列執行 Install-Package Strathweb.CacheOutput.WebApi2OutputCache 。
示例程式碼:
[CacheOutput(ClientTimeSpan = 60, ServerTimeSpan = 60)] public IEnumerable<string> Get() { return new string[] { "str1", "str2" }; }
WebAPI 測試連結:http://hi.haojima.net/SwaggerUI/
響應式
什麼是響應式? 請戳。
在做響應式佈局的時候,還是遇到了點小問題的。
如:
pc端的搜尋條件所在的div 顯示效果:
在移動端的顯示效果:
要求:pc端一行顯示,移動端兩行顯示。且左右居中顯示。
問題就出在左右居中。首先,pc端的顯示。兩個div一行顯示,我們一般都是用樣式 float: left; 。可是,我發現float了以後不好居中了啊。考慮這用個東西包起來,再居中。具有包裹性的:無非就是: float: left; display:table; position:absolute 。float排除,然後table的顯示方式好使。就像我們平時讓table居中那樣。 margin:0 auto;
測試程式碼:
<style type="text/css"> .clearfix { overflow: auto; _height: 1%; } </style> <div class="clearfix" style="display:table;margin:0 auto; border: 1px dashed #ff0000"> <div style="float: left; border: 1px solid #ff0000">div1</div> <div style="float: left; border: 1px solid #ff0000; ">div2</div> </div>
注意:clearfix 用來防止使用了 float 而引起的”坍塌“效果。
pc端搞定了,那移動端直接去掉 float 再顯示就ok了。
(前端的東西,我也是知其然不知其所以然。什麼居中、”坍塌“、clearfix等 也不知道為什麼要這麼用。所以博文記錄下,方便下次自己翻閱。)
詳細資訊顯示
雖然列表中超連結到詳情頁面。但是,如果我們可以直接在本頁面檢視到詳情豈不是更加的方便。我們做的本來就是為了更加方便的瀏覽招聘資訊。
說做就做。首先,我們的列表已經有了超連結。我們在點選行的時候,傳送請求到後臺。取得詳細資訊,然後在頁面顯示。就這麼簡單。
後臺獲取詳細資訊:
#region 根據url請求,返回詳細資訊 /// <summary> /// 根據url請求,返回詳細資訊 /// </summary> /// <param name="url"></param> /// <param name="type"></param> /// <returns></returns> public string GetUrlInfo(string url, DataType type) { var ulS = string.Empty; switch (type) { case DataType.智聯招聘: #region 問題:“gzip”不是受支援的編碼名 的處理方法 http://www.cnblogs.com/soundcode/p/3785152.html HtmlAgilityPack.HtmlWeb.PreRequestHandler handler = delegate(HttpWebRequest request) { request.Headers[HttpRequestHeader.AcceptEncoding] = "gzip, deflate"; request.AutomaticDecompression = DecompressionMethods.Deflate | DecompressionMethods.GZip; request.CookieContainer = new System.Net.CookieContainer(); return true; }; htmlWeb.PreRequest += handler; #endregion htmlWeb.OverrideEncoding = Encoding.GetEncoding("UTF-8"); HtmlAgilityPack.HtmlDocument response = htmlWeb.Load(url); var fuli = response.DocumentNode.SelectNodes("/html/body/div[3]/div[1]/div[1]/div"); var jiben = response.DocumentNode.SelectNodes("/html/body/div[4]/div[1]/ul"); var miaoshu = response.DocumentNode.SelectNodes("/html/body/div[4]/div[1]/div[1]/div/div[1]"); if (fuli != null && fuli.Count >= 1 && !string.IsNullOrEmpty(fuli[0].InnerText.Trim())) ulS += "<h3>福利誘惑:</h3>" + fuli[0].InnerText; if (jiben != null && jiben.Count >= 1 && !string.IsNullOrEmpty(jiben[0].InnerText.Trim())) ulS += "<h3>基本資訊:</h3>" + jiben[0].InnerText; if (miaoshu != null && miaoshu.Count >= 1 && !string.IsNullOrEmpty(miaoshu[0].InnerText.Trim())) ulS += "<h3>職位描述:</h3>" + miaoshu[0].InnerText; break; case DataType.獵聘網: htmlWeb.OverrideEncoding = Encoding.GetEncoding("UTF-8"); response = htmlWeb.Load(url); //--基本資訊 var jbinfo = response.DocumentNode.SelectNodes("//*[@id='job-view-enterprise']/div[1]/div[1]/div[1]/div[3]/div") ?? response.DocumentNode.SelectNodes("//*[@id='job-hunter']/div[1]/div[1]/div[1]/div[3]/div"); //職位描述 var selectNodes = response.DocumentNode.SelectNodes("//*[@id='job-hunter']/div[1]/div[1]/div[1]/div[4]") ?? response.DocumentNode.SelectNodes("//*[@id='job-view-enterprise']/div[1]/div[1]/div[1]/div[4]"); //崗位要求 var ganwei = response.DocumentNode.SelectNodes("//*[@id='job-hunter']/div[1]/div[1]/div[1]/div[5]/div") ?? response.DocumentNode.SelectNodes("//*[@id='job-view-enterprise']/div[1]/div[1]/div[1]/div[5]/div"); ulS = "<h3>基本資訊:</h3>" + jbinfo[0].InnerText + "<h3>職位描述:</h3>" + selectNodes[0].InnerText + "<h3>崗位要求:</h3>" + ganwei[0].InnerText; break; case DataType.前程無憂: htmlWeb.OverrideEncoding = Encoding.GetEncoding("GBK"); response = htmlWeb.Load(url); //-- ulS = "<h3>基本資訊:</h3>" + response.DocumentNode.SelectNodes("/html/body/div[3]/div/div[2]/table[1]/tr[3]/td[1]")[0].InnerText + "<h3>職位描述:</h3>" + response.DocumentNode.SelectNodes("/html/body/div[3]/div/div[2]/div[1]/div[2]/div/table")[0].InnerText; break; case DataType.拉勾網: htmlWeb.OverrideEncoding = Encoding.GetEncoding("UTF-8"); response = htmlWeb.Load(url); ulS = "<h3>基本資訊:</h3>" + response.DocumentNode.SelectNodes("//*[@id='container']/div[1]/div[1]/dl/dd[1]")[0].InnerText + "<h3>職位描述:</h3>" + response.DocumentNode.SelectNodes("//*[@id='container']/div[1]/div[1]/dl/dd[2]")[0].InnerText; break; } return ulS.ToJson(); } #endregion
前臺資訊載入:
if ($(obj).next().hasClass("dataInfo")) $(obj).next().toggle();//如果已有詳細資訊,則只做顯示隱藏的切換 else $(obj).after("<div class='dataInfo'>正在載入...</div>");//否則提示“正在載入” $.ajax({//發起請求 url: apiHref + "/api/HiJob?url=" + url, data: null, beforeSend: function (XHR) { }, success: function (data) { $(obj).next(".dataInfo").html(eval(data.data));//用內容替換提示資訊 }, dateType: "json" });
新增拉勾網的資料
我後期又加了“拉勾”網的招聘資訊。其他的網站都是直接連結,取資訊。而偏偏拉勾就是不同。它是,請求->頁面載入->ajax非同步請求詳情->追加到頁面。然而,就因為這個非同步,好幾個同學就搞不定了。問我,拉勾的資料為什麼取不到。在這裡就統一分析下吧。
請求如:http://www.lagou.com/jobs/list_.net?city=上海 在瀏覽器F12監控。
我們可以看到資訊列表資料是從http://www.lagou.com/jobs/positionAjax.json?city=上海地址,通過ajax的post請求取得的。
所以,我們後臺模擬一個post請求就完事了。
StringContent fromurlcontent = new StringContent("first=true&pn=" + pn + "&kd=" + kd); fromurlcontent.Headers.ContentType = new MediaTypeHeaderValue("application/x-www-form-urlencoded"); fromurlcontent.Headers.Add("X-Requested-With", "XMLHttpRequest"); HttpClient httpclient = new HttpClient(); HttpResponseMessage responseMsg = httpclient.PostAsync(new Uri(url), fromurlcontent).Result;//發起post請求 var result = responseMsg.Content.ReadAsStringAsync().Result; JavaScriptSerializer _jsSerializer = new JavaScriptSerializer(); LagouInfo JPostData = _jsSerializer.Deserialize<LagouInfo>(result);
注意了,我們得到資料之後。還進行的反序列化。因為資料是json格式的。但,不是所有資料都是我們想要的。所以進行序列化,然後只取我們想要的資料。(當然,序列化類,是我對著json資料一個個摳出來,寫的類屬性)
序列化類:
public class LagouInfo { public string code; public Ccontent content; public string msg; public string requestId; public string resubmitToken; public string success; } public class Ccontent { public string currentPageNo; public string hasNextPage; public string hasPreviousPage; public string pageNo; public string pageSize; public List<Cresult> result; public string start; public string totalCount; public string totalPageCount; } public class Cresult { public string adWord; public string adjustScore; public string city; public string companyId; public List<string> companyLabelList; public string companyLogo; public string companyName; public string companyShortName; public string companySize; public string countAdjusted; public string createTime; public string createTimeSort; public string education; public string financeStage; public string formatCreateTime; public string haveDeliver; public string industryField; public string jobNature; public string leaderName; public string orderBy; public string positionAdvantage; public string positionFirstType; public string positionId; public string positionName; public string positionType; public string positonTypesMap; public string randomScore; public string relScore; public string salary; public string score; public string searchScore; public string showOrder; public string totalCount; public string workYear; }
然後,接著組裝自己想要的資料。
if (JPostData == null || JPostData.content == null || JPostData.content.result == null) return; for (int i = 0; i < JPostData.content.result.Count; i++) { var item = JPostData.content.result[i]; string titleName, infourl, company, city, date, salary, salary_em, source; titleName = item.positionName; infourl = "http://www.lagou.com/jobs/" + item.positionId + ".html"; company = item.companyShortName; city = item.city; date = DateTime.Parse(item.createTime).ToString("yyyy-MM-dd"); salary = "月薪"; //item.SelectSingleNode(xpath + "/td[@class='gsmc']/a").InnerText; salary_em = item.salary; source = "拉勾網"; listJobInfo.Add( new JobInfo(){ city = city, company = company, date = date, info_url = infourl, salary = salary, salary_em = salary_em, titleName = titleName, source = source }); }
增加選擇區域
剛開始的時候,只新增了幾個熱門的城市(也是因為偷懶)。然後,很多同學就開始不依了,為什麼沒有“**”。大哥,能不能加上“**”。
既然大家有興趣,那我一次性都加上吧。
點選更多:
說實在的,這個增加選擇區域沒有任何技術含量。純粹的一個體力活。
因為每個網站的地區對於的地區編碼都是不一樣的。所以,我就需要到各個網站一個個的摳。
如:
摳完後:(string[0]:智聯/拉勾 string[1]:前程 string[2]:獵聘)
dic_hi.Add("北京", new string[] { "北京", "010000", "010" }); dic_hi.Add("上海", new string[] { "上海", "020000", "020" }); dic_hi.Add("深圳", new string[] { "深圳", "040000", "050090" }); dic_hi.Add("廣州", new string[] { "廣州", "030200", "050020" }); dic_hi.Add("杭州", new string[] { "杭州", "080200", "070020" }); dic_hi.Add("成都", new string[] { "成都", "090200", "280020" }); dic_hi.Add("南京", new string[] { "南京", "070200", "060020" }); dic_hi.Add("武漢", new string[] { "武漢", "180200", "170020" }); dic_hi.Add("西安", new string[] { "西安", "200200", "270020" }); dic_hi.Add("廈門", new string[] { "廈門", "110300", "090040" }); dic_hi.Add("長沙", new string[] { "長沙", "190200", "180020" }); dic_hi.Add("蘇州", new string[] { "蘇州", "070300", "060080" }); dic_hi.Add("天津", new string[] { "天津", "050000", "030" }); dic_hi.Add("重慶", new string[] { "重慶", "060000", "040" }); dic_hi.Add("鄭州", new string[] { "鄭州", "170200", "150020" }); dic_hi.Add("青島", new string[] { "青島", "120300", "250070" }); dic_hi.Add("合肥", new string[] { "合肥", "150200", "080020" }); dic_hi.Add("福州", new string[] { "福州", "110200", "090020" }); dic_hi.Add("濟南", new string[] { "濟南", "120200", "250020" }); dic_hi.Add("大連", new string[] { "大連", "230300", "210040" }); dic_hi.Add("珠海", new string[] { "珠海", "030500", "050140" }); dic_hi.Add("無錫", new string[] { "無錫", "070400", "060100" }); dic_hi.Add("佛山", new string[] { "佛山", "030600", "050050" }); dic_hi.Add("東莞", new string[] { "東莞", "030800", "050040" }); dic_hi.Add("寧波", new string[] { "寧波", "080300", "070030" }); dic_hi.Add("常州", new string[] { "常州", "070500", "060040" }); dic_hi.Add("瀋陽", new string[] { "瀋陽", "230200", "210020" }); dic_hi.Add("石家莊", new string[] { "石家莊", "160200", "140020" }); dic_hi.Add("昆明", new string[] { "昆明", "250200", "310020" }); dic_hi.Add("南昌", new string[] { "南昌", "130200", "200020" }); dic_hi.Add("南寧", new string[] { "南寧", "140200", "110020" }); dic_hi.Add("哈爾濱", new string[] { "哈爾濱", "220200", "160020" }); dic_hi.Add("海口", new string[] { "海口", "100200", "130020" }); dic_hi.Add("中山", new string[] { "中山", "030700", "050130" }); dic_hi.Add("惠州", new string[] { "惠州", "030300", "050060" }); dic_hi.Add("貴陽", new string[] { "貴陽", "260200", "120020" }); dic_hi.Add("長春", new string[] { "長春", "240200", "190020" }); dic_hi.Add("太原", new string[] { "太原", "210200", "260020" }); dic_hi.Add("嘉興", new string[] { "嘉興", "080700", "070090" }); dic_hi.Add("泰安", new string[] { "泰安", "121100", "250090" }); dic_hi.Add("崑山", new string[] { "崑山", "070600", "060050" }); dic_hi.Add("煙臺", new string[] { "煙臺", "120400", "250120" }); dic_hi.Add("蘭州", new string[] { "蘭州", "270200", "100020" }); dic_hi.Add("泉州", new string[] { "泉州", "110400", "090030" });
總結
和之前那個版本顯示效果區別不大(頁面還是一樣的醜,程式碼也還是一樣的醜),不過實現方式完全不一樣了。這陣子學習了MVC和WebAPI的點皮毛知識,也就再次折騰下。
演示地址 原始碼下載 ,如果您覺得有用,那就留給腳印吧。演示地址後期可能會變,這篇博文會維護最新連結。
轉眼一年又悄悄的過去了,我猜想大家又開始蠢蠢欲動起來了。不過年後跳得應該比較多。不過,個人覺得年後的競爭壓力大得多。
如果您有更好的處理方式,希望不要吝嗇賜教。