SimpleHttpServer.cs 12 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300
  1. using System;
  2. using System.Collections.Generic;
  3. using System.Diagnostics;
  4. using System.Drawing;
  5. using System.Drawing.Imaging;
  6. using System.IO;
  7. using System.Text;
  8. using LJLib.Net.SPI.Com;
  9. using LJLib.Net.SPI.Server;
  10. using LJLib.Text.Parser;
  11. using LJLib.Tools.Helper;
  12. using LJLib.Tools.Utils;
  13. using JLHHJSvr.LJLib.HttpServer;
  14. using System.Web;
  15. using System.Linq;
  16. namespace LJLib.HttpServer
  17. {
  18. public class SimpleHttpServer : LJHttpServer
  19. {
  20. private ILJServer server;
  21. private IFileDBModel fileModel;
  22. private static LJParser parser = new LJParser();
  23. private static Dictionary<string, byte[]> files = new Dictionary<string, byte[]>();
  24. public SimpleHttpServer(int port, ILJServer server, IFileDBModel fileModel)
  25. : base(port)
  26. {
  27. this.server = server;
  28. this.fileModel = fileModel;
  29. }
  30. public override void HandleGetRequest(LJHttpProcessor p)
  31. {
  32. //转到POST统一处理
  33. HandlePostRequest(p, null);
  34. }
  35. public override void HandlePostRequest(LJHttpProcessor p, StreamReader inputData)
  36. {
  37. string bufferedBody = string.Empty;
  38. if (inputData != null)
  39. {
  40. bufferedBody = inputData.ReadToEnd();
  41. }
  42. if (p.http_method.Equals("POST"))
  43. {
  44. if (p.http_url.StartsWith("/api.ashx"))
  45. {
  46. if (server == null)
  47. {
  48. throw new Exception("未定义server成员");
  49. }
  50. var postParamDic = p.POSTqueryParams(inputData);
  51. if (!postParamDic.ContainsKey("method"))
  52. {
  53. p.WriteError("无效的请求接口");
  54. return;
  55. }
  56. string method = postParamDic["method"];//接口名称apiName
  57. string requestbody = string.Empty;//请求类JSON字符串
  58. if (postParamDic.ContainsKey("requestbody"))
  59. {
  60. requestbody = postParamDic["requestbody"];
  61. }
  62. // 处理请求
  63. handleAPI(p, method, requestbody);
  64. return;
  65. }
  66. else if (p.http_url.StartsWith("/api/common/"))
  67. {
  68. var apiName = p.http_url.Substring(12);
  69. var requestbody = bufferedBody;
  70. handleAPI(p, apiName, requestbody);
  71. return;
  72. }
  73. }
  74. else if (p.http_method.Equals("GET"))
  75. {
  76. // 图片/文件获取接口
  77. if (p.http_url.StartsWith("/img.ashx"))
  78. {
  79. var parms = p.GETqueryParams();
  80. string filemd5 = string.Empty;
  81. if (!parms.ContainsKey("filename"))
  82. {
  83. Trace.Write("请求img.ashx不包含filename参数");
  84. }
  85. else
  86. {
  87. filemd5 = parms["filename"];
  88. }
  89. byte[] body = null;
  90. if (files.ContainsKey(filemd5))
  91. {
  92. body = files[filemd5];
  93. }
  94. else
  95. {
  96. body = fileModel.GetBytes(filemd5);
  97. }
  98. var ext = MIMEHelper.GetExType(body);
  99. var contentType = MIMEHelper.ContentType("." + ext);
  100. if (!string.IsNullOrEmpty(ext) && parms.ContainsKey("w") && parms.ContainsKey("h"))
  101. {
  102. int width;
  103. int height;
  104. if (int.TryParse(parms["w"], out width) && int.TryParse(parms["h"], out height))
  105. {
  106. using (var ms = new MemoryStream(body))
  107. using (var img = Image.FromStream(ms))
  108. using (var oImg = ImgHelper.NewBMPFrom(img, width, height))
  109. using (var oms = new MemoryStream())
  110. {
  111. oImg.Save(oms, ImageFormat.Png);
  112. body = oms.ToArray();
  113. contentType = MIMEHelper.ContentType(".png");
  114. }
  115. }
  116. }
  117. p.WriteResponse(body, contentType);
  118. return;
  119. }
  120. else if (p.http_url.StartsWith("/dist") || p.http_url.StartsWith("/html") ||
  121. p.http_url.StartsWith("/App_Files"))
  122. {
  123. string basePath = AppDomain.CurrentDomain.BaseDirectory;
  124. string requestPath;
  125. requestPath = p.http_url.Substring(1);
  126. string filePath = basePath + "/" + requestPath;
  127. if (!File.Exists(filePath))
  128. {
  129. p.WriteError("未找到文件");
  130. return;
  131. }
  132. string fileName = p.http_url.Substring(p.http_url.LastIndexOf('.')).ToLower();
  133. string fileType = MIMEHelper.ContentType(fileName);
  134. byte[] body;
  135. using (var ms = new MemoryStream())
  136. using (var fs = File.OpenRead(filePath))
  137. {
  138. StreamHelper.StreamCopy(ms, fs);
  139. body = ms.ToArray();
  140. }
  141. if (fileType.StartsWith("text/html"))
  142. {
  143. fileType += "; charset=utf-8";
  144. }
  145. p.WriteResponse(Encoding.UTF8.GetString(body), fileType);
  146. return;
  147. }
  148. else
  149. {
  150. string basePath = AppDomain.CurrentDomain.BaseDirectory;
  151. string filePath = basePath + "/App_Files/";
  152. var sourceDir = new DirectoryInfo(filePath);
  153. var enabledSubWeb = sourceDir.GetDirectories().Select(x => x.Name);
  154. var subUrl = p.http_url;
  155. var subDirs = subUrl.Split('/').Where(x => !string.IsNullOrEmpty(x)).ToList();
  156. var subDir = "Web";
  157. if (subDirs.Any())
  158. {
  159. if (enabledSubWeb.Contains(subDirs.First()))
  160. {
  161. subDir = subDirs.First();
  162. var firstblock = $"/{subDir}/";
  163. var removeidx = subUrl.IndexOf(firstblock);
  164. subUrl = subUrl.Substring(removeidx + firstblock.Length - 1);
  165. }
  166. }
  167. filePath += subDir;
  168. if (subUrl.IndexOf(".") > 0)
  169. {
  170. if (File.Exists(filePath + subUrl))
  171. {
  172. filePath += subUrl;
  173. }
  174. else
  175. {
  176. filePath += "/index.html";
  177. }
  178. }
  179. else
  180. {
  181. filePath += "/index.html";
  182. }
  183. if (!File.Exists(filePath))
  184. {
  185. p.WriteResponse(
  186. new[]
  187. {
  188. "HTTP/1.0 404 Not Found",
  189. "Content-Type: text/plain",
  190. "Connection: close"
  191. }, "The resource you requested ('" + p.http_url + "') could not be found.");
  192. }
  193. else
  194. {
  195. byte[] body;
  196. string fileType = null;
  197. string ext = null;
  198. if (filePath.Contains("."))
  199. {
  200. ext = filePath.Substring(filePath.LastIndexOf("."));
  201. fileType = MIMEHelper.ContentType(ext);
  202. }
  203. using (var ms = new MemoryStream())
  204. using (var fs = File.OpenRead(filePath))
  205. {
  206. StreamHelper.StreamCopy(ms, fs);
  207. body = ms.ToArray();
  208. if (string.IsNullOrEmpty(fileType))
  209. {
  210. ext = MIMEHelper.GetExType(body);
  211. fileType = MIMEHelper.ContentType("." + ext);
  212. }
  213. }
  214. if (fileType.StartsWith("text/html"))
  215. {
  216. fileType += "; charset=utf-8";
  217. p.WriteResponse(new[]
  218. {
  219. "HTTP/1.0 200 OK",
  220. "Content-Type: " + fileType,
  221. "Connection: close"
  222. }, Encoding.UTF8.GetString(body));
  223. }
  224. else
  225. {
  226. p.WriteResponse(new[]
  227. {
  228. "HTTP/1.0 200 OK",
  229. "Content-Type: " + fileType,
  230. "Content-Length: " + body.Length,
  231. "Connection: close"
  232. }, body);
  233. }
  234. }
  235. return;
  236. }
  237. }
  238. p.WriteFailure();
  239. }
  240. private void handleAPI(LJHttpProcessor p, string method, string requestbody)
  241. {
  242. LJResponse responselist = null;
  243. string str = string.Empty;
  244. try
  245. {
  246. if (!requestbody.StartsWith("{"))
  247. {
  248. requestbody = HttpUtility.UrlDecode(requestbody);
  249. if (!requestbody.StartsWith("{"))
  250. {
  251. Trace.Write("请求格式错误" + requestbody);
  252. throw new Exception("请求格式错误");
  253. }
  254. }
  255. ILJRequest requestlist = null;
  256. string apiName = method;
  257. Type requestType = server.GetRequestType(apiName);
  258. string body = requestbody;
  259. requestlist = parser.JsonParse(requestType, body) as ILJRequest;
  260. responselist = server.DoExcute(requestlist, null);
  261. if (!string.IsNullOrEmpty(responselist.ErrMsg))
  262. {
  263. Trace.Write(requestlist.GetApiName() + ":" + responselist.ErrMsg);
  264. }
  265. Dictionary<string, byte[]> fil = new Dictionary<string, byte[]>();
  266. str = parser.ToJson(responselist, fil, "/img.ashx?filename=");
  267. }
  268. catch (Exception ex)
  269. {
  270. Trace.Write(ex.ToString());
  271. responselist = new ErrResponse(ex.ToString());
  272. str = parser.ToJson(responselist);
  273. }
  274. p.WriteResponse(
  275. new[]{
  276. "HTTP/1.0 200 OK",
  277. "Content-Type: text/plain; charset=utf-8",
  278. "Connection: close"
  279. },
  280. str);
  281. }
  282. }
  283. }