96c52b7e31c1f50c4e572756441320ad0c2c610c.svn-base 16 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401
  1. using System;
  2. using System.IO;
  3. using System.Xml;
  4. using System.Data;
  5. using System.Text;
  6. using System.Collections;
  7. using System.Reflection;
  8. using System.Configuration;
  9. using Core.Mes.Common;
  10. using Core.Mes.IBaseInterface;
  11. namespace Core.Mes.ServerFrameWork
  12. {
  13. public class Dispatcher : MarshalByRefObject, ICommon
  14. {
  15. private ArrayList _objects = null;
  16. private ServerConfigure _servConf = null;
  17. public ServerConfigure ServConfig
  18. {
  19. get { return _servConf; }
  20. }
  21. #region " Construct "
  22. public Dispatcher() { }
  23. public Dispatcher(IServerPool pool, ServerConfigure _conf, ArrayList _objs)
  24. {
  25. Pool = pool;
  26. _servConf = _conf;
  27. _objects = _objs;
  28. }
  29. private IServerPool _pool = null;
  30. public IServerPool Pool
  31. {
  32. get { return _pool; }
  33. set
  34. {
  35. _pool = value;
  36. if (_pool.OwnObjects == null && _objects != null) _pool.OwnObjects = _objects;
  37. }
  38. }
  39. #endregion
  40. #region " Variable "
  41. //== 子服务集合
  42. public static Hashtable _htServers = new Hashtable();
  43. //== 数据链接集合
  44. public static Hashtable htDBManager = new Hashtable();
  45. public event GetStatusInfoHandler getStatusInfo;
  46. public delegate void GetStatusInfoHandler(string info);
  47. protected virtual void SetStatusMessage(string info)
  48. {
  49. if (getStatusInfo != null)
  50. {
  51. getStatusInfo(info);
  52. }
  53. }
  54. #endregion
  55. #region 内存释放
  56. public void MemoryDispose()
  57. {
  58. long memorysize = System.Diagnostics.Process.GetCurrentProcess().WorkingSet64;
  59. int PagedMemorySize = (int)memorysize / (1024 * 1024);
  60. if (PagedMemorySize > _servConf.MemoryMaxSize)//进程占用内存>100M 做GC.
  61. {
  62. try
  63. {
  64. GC.Collect(GC.MaxGeneration, GCCollectionMode.Forced);
  65. }
  66. catch
  67. {
  68. }
  69. System.Diagnostics.Process.GetCurrentProcess().Dispose();
  70. }
  71. }
  72. #endregion
  73. #region MethodTimeLog
  74. private static object lockObj = new object();
  75. public void MethodTimeLog(TimeSpan tspan, object[] objs, object[] args)
  76. {
  77. string path = string.Format(@"./log/Method/MethodTimeLog_{0}.txt", System.DateTime.Now.ToString("yyyy_MM_dd"));
  78. lock (lockObj)
  79. {
  80. using (StreamWriter sw = new StreamWriter(path, true, Encoding.UTF8))
  81. {
  82. StringBuilder sbtxt = new StringBuilder();
  83. sbtxt.AppendLine("==============================================");
  84. sbtxt.AppendLine(string.Format("LogWriteTime:{0}", DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss")));
  85. sbtxt.AppendLine(string.Format("Time:{0}", tspan.TotalMilliseconds));
  86. sbtxt.AppendLine(string.Format("ClassName:{0}", objs[0].ToString()));
  87. sbtxt.AppendLine(string.Format("MethodName:{0}", objs[1].ToString()));
  88. if (args != null)
  89. {
  90. foreach (object obj in args)
  91. {
  92. if (obj != null)
  93. {
  94. sbtxt.AppendLine(string.Format("Parameters:{0}", obj.ToString()));
  95. }
  96. }
  97. }
  98. sbtxt.AppendLine("==============================================");
  99. sw.WriteLine(sbtxt.ToString());
  100. }
  101. }
  102. }
  103. public void MethodErrLog(Exception ex, object[] objs, object[] args)
  104. {
  105. string path = string.Format(@"./log/Method/MethodErrLog_{0}.txt", System.DateTime.Now.ToString("yyyy_MM_dd"));
  106. lock (lockObj)
  107. {
  108. using (StreamWriter sw = new StreamWriter(path, true, Encoding.UTF8))
  109. {
  110. StringBuilder sbtxt = new StringBuilder();
  111. sbtxt.AppendLine("==============================================");
  112. sbtxt.AppendLine(string.Format("LogWriteTime:{0}", DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss")));
  113. sbtxt.AppendLine(string.Format("ClassName:{0}", objs[0].ToString()));
  114. sbtxt.AppendLine(string.Format("MethodName:{0}", objs[1].ToString()));
  115. if (args != null)
  116. {
  117. foreach (object obj in args)
  118. {
  119. if (obj != null)
  120. {
  121. sbtxt.AppendLine(string.Format("Parameters:{0}", obj.ToString()));
  122. }
  123. }
  124. }
  125. sbtxt.AppendLine(ex.Message);
  126. sbtxt.AppendLine(ex.StackTrace);
  127. sbtxt.AppendLine("==============================================");
  128. sw.WriteLine(sbtxt.ToString());
  129. }
  130. }
  131. }
  132. public void DebugLog(object[] objs, object[] args)
  133. {
  134. string path = string.Format(@"./log/Method/DebugLog_{0}.txt", System.DateTime.Now.ToString("yyyy_MM_dd"));
  135. lock (lockObj)
  136. {
  137. if (File.Exists(Path.GetFullPath(path)))
  138. {
  139. FileInfo fileInfo = new FileInfo(Path.GetFullPath(path));
  140. if (fileInfo.Length / (1024 * 1024) > 6)
  141. {
  142. File.Delete(path);
  143. }
  144. }
  145. using (StreamWriter sw = new StreamWriter(path, true, Encoding.UTF8))
  146. {
  147. StringBuilder sbtxt = new StringBuilder();
  148. sbtxt.AppendLine("==============================================");
  149. sbtxt.AppendLine(string.Format("LogWriteTime:{0}", DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss")));
  150. sbtxt.AppendLine(string.Format("ClassName:{0}", objs[0].ToString()));
  151. sbtxt.AppendLine(string.Format("MethodName:{0}", objs[1].ToString()));
  152. if (args != null)
  153. {
  154. foreach (object obj in args)
  155. {
  156. if (obj != null)
  157. {
  158. sbtxt.AppendLine(string.Format("Parameters:{0}", obj.ToString()));
  159. }
  160. }
  161. }
  162. sbtxt.AppendLine("==============================================");
  163. sw.WriteLine(sbtxt.ToString());
  164. }
  165. }
  166. }
  167. #endregion
  168. #region " 调用服务 "
  169. /// <summary>
  170. /// 服务端公开给客户端的调用后台服务的方法
  171. /// </summary>
  172. /// <param name="message"></param>
  173. /// <returns></returns>
  174. public ReturnObject MethodHandler(CallingMessage message, ValidateInfo validateInfo)
  175. {
  176. CallingMessageEx messageEx = new CallingMessageEx();
  177. messageEx.FromCallingMessage(message);
  178. messageEx.RedirectLimit = 0;
  179. messageEx.InnerServerRedirect = true;
  180. ReturnObjectEx rtnObjEx = Execute(messageEx, validateInfo);
  181. ReturnObject rtnObj = new ReturnObject();
  182. rtnObj.ErrCode = rtnObjEx.ErrCode;
  183. rtnObj.ErrMessage = rtnObjEx.ErrMessage;
  184. rtnObj.RealDataSet = rtnObjEx.RealDataSet;
  185. rtnObj.RealObject = rtnObjEx.RealObject;
  186. return rtnObj;
  187. }
  188. public ReturnObjectEx MethodHandlerEx(CallingMessageEx message, ValidateInfo validateInfo)
  189. {
  190. return Execute(message, validateInfo);
  191. }
  192. private ReturnObjectEx Execute(CallingMessageEx messageEx, ValidateInfo validateInfo)
  193. {
  194. //step1:
  195. MemoryDispose();
  196. //step2:
  197. string serverName = messageEx.ServerName;
  198. string assemblyName = messageEx.AssemblyName;
  199. string className = messageEx.ClassName;
  200. string methodName = messageEx.MethodName;
  201. object[] args = messageEx.args;
  202. ReturnObjectEx rtnObjEx = new ReturnObjectEx();
  203. MethodInfo myMethod = null;
  204. try
  205. {
  206. if (Pool.HtComponent.Contains(className))
  207. {
  208. try
  209. {
  210. if (serverName.ToUpper() != "SERVERCOMMON" && messageEx.RedirectLimit > 0)
  211. {
  212. string RedirURL = "";
  213. double sum_factor = 0;
  214. ArrayList serviceProvider = new ArrayList();
  215. ArrayList pfactors = new ArrayList();
  216. serviceProvider.Add("THIS");
  217. sum_factor += this.ServConfig.PriorityFactor;
  218. pfactors.Add(sum_factor);
  219. foreach (string server in Pool.HtExtServer.Keys)
  220. {
  221. RemotingServer rs = (RemotingServer)Pool.HtExtServer[server];
  222. if (rs.Valid != RemoteServerStatus.Normal || rs.Enable == false) continue;
  223. rs.FindRemoteServer(serverName);
  224. if (!rs.HTServices.ContainsKey(serverName)) continue;
  225. ServiceObject so = ((ServiceObject)(rs.HTServices[serverName]));
  226. if (so.Valid != ServiceObjectStatus.Normal || so.Enable == false) continue;
  227. RedirURL = so.URL;
  228. sum_factor += rs.PriorityFactor;
  229. serviceProvider.Add(server);
  230. pfactors.Add(sum_factor);
  231. }
  232. Random rand = new Random();
  233. double rand_selector = rand.NextDouble() * sum_factor;
  234. int selector = 0;
  235. for (int idx = 0; idx < pfactors.Count; idx++)
  236. {
  237. if (rand_selector <= (double)pfactors[idx])
  238. {
  239. selector = idx;
  240. break;
  241. }
  242. }
  243. if (selector != 0)
  244. {
  245. SimpleReturnObject _out = new SimpleReturnObject();
  246. if (messageEx.InnerServerRedirect)
  247. {
  248. RemotingServer rs = (RemotingServer)Pool.HtExtServer[serviceProvider[selector]];
  249. rtnObjEx = (ReturnObjectEx)rs.ExecuteMethod(messageEx, out _out);
  250. return rtnObjEx;
  251. }
  252. else
  253. {
  254. rtnObjEx.ReDirectURL = RedirURL;
  255. return rtnObjEx;
  256. }
  257. }
  258. }
  259. //使用本地服务
  260. myMethod = Pool.GetType().GetMethod("HandleMethodEx"); ;
  261. DateTime startTime = DateTime.Now;
  262. if (_servConf.Debug == "true")
  263. {
  264. DebugLog(new object[] { className, methodName }, args);
  265. }
  266. ReturnObject rtnObj = (ReturnObject)myMethod.Invoke(Pool, new object[] { className, methodName, args, _objects });
  267. rtnObjEx.ReDirectURL = "";
  268. rtnObjEx.ErrCode = rtnObj.ErrCode;
  269. rtnObjEx.ErrMessage = rtnObj.ErrMessage;
  270. rtnObjEx.RealDataSet = rtnObj.RealDataSet;
  271. rtnObjEx.RealObject = rtnObj.RealObject;
  272. DateTime endTime = DateTime.Now;
  273. TimeSpan tspan = endTime - startTime;
  274. if (tspan.TotalMilliseconds > (_servConf.MethodTime * 1000))
  275. {
  276. MethodTimeLog(tspan, new object[] { className, methodName }, args);
  277. }
  278. if (rtnObjEx.RealObject != null)
  279. {
  280. if (rtnObjEx.RealObject.GetType() == typeof(DataSet))
  281. {
  282. DataSet _ds = (DataSet)rtnObjEx.RealObject;
  283. bool largeData = false;
  284. int row_cnt = 0;
  285. foreach (DataTable _dt in _ds.Tables)
  286. {
  287. row_cnt += _dt.Rows.Count;
  288. if (_dt.Rows.Count > _servConf.CompressThreshold || row_cnt > _servConf.CompressThreshold)
  289. {
  290. largeData = true;
  291. break;
  292. }
  293. }
  294. if (largeData)
  295. {
  296. byte[] _rtn = Utility.SerializeDataSet(_ds);
  297. byte[] _rtn_comp = Utility.CompressBytes(_rtn);
  298. DataTable dt_rus = new DataTable("RETURN_RESULT");
  299. dt_rus.Columns.AddRange(new DataColumn[]{
  300. new DataColumn("IsCompressed", System.Type.GetType("System.Int32") ),
  301. new DataColumn("UnCompress_size", System.Type.GetType("System.Int32")),
  302. new DataColumn("Compress_size", System.Type.GetType("System.Int32"))}
  303. );
  304. dt_rus.AcceptChanges();
  305. dt_rus.Rows.Add(new object[] { 1, _rtn.Length, _rtn_comp.Length });
  306. dt_rus.AcceptChanges();
  307. if (rtnObjEx.RealDataSet == null)
  308. {
  309. rtnObjEx.RealDataSet = new DataSet();
  310. }
  311. rtnObjEx.RealDataSet.Tables.Add(dt_rus);
  312. rtnObjEx.RealObject = _rtn_comp;
  313. }
  314. }
  315. }
  316. return rtnObjEx;
  317. }
  318. catch (Exception ex)
  319. {
  320. MethodErrLog(ex, new object[] { className, methodName }, args);
  321. return new ReturnObjectEx(null, ex.Message);
  322. }
  323. finally
  324. {
  325. try
  326. {
  327. if (rtnObjEx.RealObject != null)
  328. {
  329. rtnObjEx.RealObject = null;
  330. }
  331. if (rtnObjEx.RealDataSet != null)
  332. {
  333. rtnObjEx.RealDataSet = null;
  334. }
  335. }
  336. catch { }
  337. }
  338. }
  339. else
  340. {
  341. return new ReturnObjectEx(null, "未找到请求的服务![2]");
  342. }
  343. }
  344. catch (Exception ex)
  345. {
  346. return new ReturnObjectEx(null, "服务调用发生异常! \n" + ex.Message);
  347. }
  348. }
  349. #endregion
  350. #region " Common Handler "
  351. //=======================================================
  352. // 用来确保当创建 Singleton 时, 第一个实例永远不会过期
  353. //=======================================================
  354. public override object InitializeLifetimeService()
  355. {
  356. return null;
  357. }
  358. #endregion
  359. }
  360. }