使用ReportXml的帮助类

  1 using System;
  2 using System.Collections.Generic;
  3 using System.Linq;
  4 using System.Text;
  5 using System.Xml.Linq;
  6 using System.Text.RegularExpressions;
  7 using System.Data.SqlClient;
  8 using System.Data;
  9 using System.Configuration;
 10 using System.Xml;
 11 
 12 namespace Components
 13 {
 14     public static class ReportHelper
 15     {
 16         #region 获取分页数据
 17         /// <summary>
 18         /// 获取分页数据
 19         /// </summary>
 20         /// <typeparam name="T"></typeparam>
 21         /// <param name="reportName"></param>
 22         /// <param name="p_Params"></param>
 23         /// <param name="p_ReportXmlName"></param>
 24         /// <param name="totalCount"></param>
 25         /// <returns></returns>
 26         public static List<T> GetPageData<T>(string reportName, ReportParams p_Params, string p_ReportXmlName, out int totalCount)
 27         {
 28             List<T> m_List = new List<T>();
 29             DataSet m_result = getReportDataByPage(reportName, p_Params, p_ReportXmlName, out totalCount);
 30             if (!m_result.IsEmpty())
 31             {
 32                 m_List = m_result.Tables[0].ToList<T>();
 33             }
 34             return m_List;
 35         }
 36 
 37         /// <summary>
 38         /// 获取分页数据
 39         /// </summary>
 40         /// <typeparam name="T"></typeparam>
 41         /// <param name="reportName"></param>
 42         /// <param name="p_Params"></param>
 43         /// <param name="p_ReportXmlName"></param>
 44         /// <param name="totalCount"></param>
 45         /// <returns>返回DataTable</returns>
 46         public static DataTable GetDataTablePageData(string reportName, ReportParams p_Params, string p_ReportXmlName, out int totalCount)
 47         {
 48             DataSet m_result = getReportDataByPage(reportName, p_Params, p_ReportXmlName, out totalCount);
 49             if (!m_result.IsEmpty())
 50             {
 51                 return m_result.Tables[0];
 52             }
 53             return null;
 54         }
 55         /// <summary>
 56         /// 获取不分页数据
 57         /// </summary>
 58         /// <param name="reportName"></param>
 59         /// <param name="p_Params"></param>
 60         /// <param name="p_ReportXmlName"></param>
 61         /// <param name="totalCount"></param>
 62         /// <returns></returns>
 63         public static DataTable GetDataTableData(string reportName, ReportParams p_Params, string p_ReportXmlName)
 64         {
 65             return getData(reportName, p_Params, p_ReportXmlName);
 66         }
 67         /// <summary>
 68         /// 获取不分页数据
 69         /// </summary>
 70         /// <typeparam name="T"></typeparam>
 71         /// <param name="reportName"></param>
 72         /// <param name="p_Params"></param>
 73         /// <param name="p_ReportXmlName"></param>
 74         /// <returns></returns>
 75         public static List<T> GetDataListData<T>(string reportName, ReportParams p_Params, string p_ReportXmlName)
 76         {
 77             List<T> m_List = new List<T>();
 78             DataTable m_result = getData(reportName, p_Params, p_ReportXmlName);
 79             if (!m_result.IsEmpty())
 80             {
 81                 m_List = m_result.ToList<T>();
 82             }
 83             return m_List;
 84         }
 85         #endregion
 86 
 87         #region 导出报表
 88         /// <summary>
 89         /// 获取分页数据
 90         /// </summary>
 91         /// <typeparam name="T"></typeparam>
 92         /// <param name="reportName"></param>
 93         /// <param name="p_Params"></param>
 94         /// <param name="p_ReportXmlName"></param>
 95         /// <returns></returns>
 96         public static List<T> GetExportData<T>(string reportName, string p_ReportXmlName, ReportParams p_Params, out int totalCount)
 97         {
 98             totalCount = 0;
 99             List<T> m_List = new List<T>();
100             DataTable m_result = getData(reportName, p_Params, p_ReportXmlName);
101             //DataSet m_result = getReportExportData(reportName, p_ReportXmlName, p_Params.Where);
102             if (!m_result.IsEmpty())
103             {
104                 m_List = m_result.ToList<T>();
105             }
106             return m_List;
107         }
108 
109         #endregion
110 
111         #region 前台需要点击排序的时候调用
112         /// <summary>
113         /// 要获取数据的XML配置报表名称
114         /// </summary>
115         /// <param name="reportName">要获取数据的XML配置报表名称</param>
116         /// <param name="p_Params">报表参数</param>
117         /// <param name="p_ReportXmlName">报表XML文件名称</param>
118         /// <param name="totalCount">数据总数</param>
119         /// <returns></returns>
120         private static DataSet getReportDataByPage(string reportName, ReportParams p_Params, string p_ReportXmlName, out int totalCount)
121         {
122             List<KeyValue> where = p_Params.Where;
123             int pageSize = p_Params.PageSize;
124             int pageIndex = p_Params.PageIndex;
125             string order = p_Params.Order;
126             string sort = p_Params.Sort;
127             totalCount = 0;
128             if (pageIndex < 1)  //不能出现索引页小于1的情况,否则查询语句报错
129                 return null;
130             if (where == null)
131                 where = new List<KeyValue>();
132 
133             string reportPath = GetReportPath(p_ReportXmlName); //报表路径
134 
135             if (string.IsNullOrEmpty(reportPath))
136                 return null;
137 
138             string sql = GetSql(reportPath, reportName, where).Trim(); //获取要查询的SQL语句 及其 参数
139             if (string.IsNullOrEmpty(sql))
140                 return null;
141 
142             string conString = GetConnection(); //获取SQL连接串
143            
144             if (string.IsNullOrEmpty(conString))
145                 return null;
146             string rowOrder = "";
147             if (!string.IsNullOrEmpty(order))
148             {
149                 rowOrder = "order by "+sort+" " + order+ " ";
150             }
151             else
152             {
153                 rowOrder = "order by t.Id desc";
154             }
155             int start = pageSize * (pageIndex - 1) + 1;
156             int end = pageSize * pageIndex;
157 
158 
159             var match = Regex.Match(sql, @"\s+order\s+", RegexOptions.IgnoreCase); //检查语句中是否含有order by
160             string strCount = sql;
161             if (match.Success) //有order by 则舍去order by 
162             {
163                 strCount = sql.Substring(0, match.Index);
164                 if (string.IsNullOrEmpty(order))
165                 {
166                     rowOrder = sql.Substring(match.Index);
167                 }
168 
169                 sql = ForSql(strCount, rowOrder, start, end); //把order by 加入到rownumber
170             }
171             else
172             {
173                 strCount = sql;
174                 sql = @" SELECT * FROM ( SELECT Row_Number() OVER ({0}) row, * from ( select * FROM (" + sql + " )  tt) t ) item "
175                        + " WHERE item.row BETWEEN " + start + " AND " + end + " ";
176 
177                 sql = string.Format(sql, rowOrder);
178             }
179             strCount = "select count(0) from (" + strCount + ") item ";
180 
181             sql = sql + ";" + strCount;
182             SqlConnection conn = new SqlConnection(conString);
183             SqlCommand cmd = new SqlCommand(sql, conn);
184             //where 替换
185             foreach (var data in where)
186             {
187                 cmd.Parameters.Add(new SqlParameter("@" + data.Key, data.Value));
188             }
189             DataSet ds = new DataSet();
190             SqlDataAdapter adp = new SqlDataAdapter(cmd);
191             adp.Fill(ds);
192             conn.Close();
193             totalCount = Convert.ToInt32(ds.Tables[1].Rows[0][0]);
194             return ds;
195         }
196         #endregion
197 
198         #region 获取数据,不分页
199         /// <summary>
200         /// 获取数据,不分页
201         /// </summary>
202         /// <param name="reportName"></param>
203         /// <param name="where"></param>
204         /// <param name="order"></param>
205         /// <param name="reportType"></param>
206         /// <param name="totalCount"></param>
207         /// <returns></returns>
208         private static DataTable getData(string reportName, ReportParams p_Params, string p_ReportXmlName)
209         {
210 
211             var order = p_Params.Order;
212             List<KeyValue> where = p_Params.Where;
213             if (where == null)
214                 where = new List<KeyValue>();
215 
216             string reportPath = GetReportPath(p_ReportXmlName); //报表路径
217 
218             if (string.IsNullOrEmpty(reportPath))
219                 return null;
220             string sql = GetSql(reportPath, reportName, where).Trim(); //获取要查询的SQL语句 及其 参数
221             if (string.IsNullOrEmpty(sql))
222                 return null;
223             string conString = GetConnection(); //获取SQL连接串
224 
225             if (string.IsNullOrEmpty(conString))
226                 return null;
227             string rowOrder = "";
228             if (!string.IsNullOrEmpty(order))
229             {
230                 rowOrder = "order by " + order + "";
231             }
232             else
233             {
234                 rowOrder = "order by t.Id desc";
235             }
236 
237             var match = Regex.Match(sql, @"\s+order\s+", RegexOptions.IgnoreCase); //检查语句中是否含有order by
238             string strCount = sql;
239             if (match.Success) //有order by 则舍去order by 
240             {
241                 strCount = sql.Substring(0, match.Index);
242                 if (string.IsNullOrEmpty(order))
243                 {
244                     rowOrder = sql.Substring(match.Index);
245                 }
246 
247                 //sql = ForSql(strCount, rowOrder); //把order by 加入到rownumber
248             }
249             else
250             {
251                 //strCount = sql;
252                 sql = @"select * FROM (" + sql + " )";
253 
254                 sql = string.Format(sql, rowOrder);
255             }
256 
257             //strCount = "select count(0) from (" + strCount + ") item ";
258 
259             // sql = sql+";" + strCount;
260             SqlConnection conn = new SqlConnection(conString);
261 
262             SqlCommand cmd = new SqlCommand(sql, conn);
263             //where 替换
264             foreach (var data in where)
265             {
266                 cmd.Parameters.Add(new SqlParameter("@" + data.Key, data.Value));
267             }
268             DataSet ds = new DataSet();
269 
270             SqlDataAdapter adp = new SqlDataAdapter(cmd);
271 
272             adp.Fill(ds);
273             conn.Close();
274             //totalCount = Convert.ToInt32(ds.Tables[1].Rows[0][0]);
275             return ds.Tables[0];
276         }
277 
278         #endregion
279 
280         #region 导出报表
281         /// <summary>
282         /// 导出报表
283         /// </summary>
284         /// <param name="reportName">报表名称</param>
285         /// <param name="p_ReportXmlName">Xml文件名称</param>
286         /// <param name="where">条件</param>
287         /// <returns></returns>
288         private static DataSet getReportExportData(string reportName, string p_ReportXmlName, List<KeyValue> where)
289         {
290             if (where == null)
291                 where = new List<KeyValue>();
292 
293             string reportPath = GetReportPath(p_ReportXmlName); //报表路径
294             if (string.IsNullOrEmpty(reportPath))
295                 return null;
296             string reportSql = GetSql(reportPath, reportName, where); //获取要查询的SQL语句 及其 参数
297 
298             if (string.IsNullOrEmpty(reportSql))
299                 return null;
300 
301             string conString = GetConnection(); //获取SQL连接串
302 
303             if (string.IsNullOrEmpty(conString))
304                 return null;
305             string sql = reportSql;
306             SqlConnection conn = new SqlConnection(conString);
307             SqlCommand cmd = new SqlCommand(sql, conn);
308             //where 替换
309             foreach (var data in where)
310             {
311                 cmd.Parameters.Add(new SqlParameter("@" + data.Key, data.Value));
312             }
313             SqlDataAdapter adapter = new SqlDataAdapter(cmd);
314             DataSet ds = new DataSet();
315             adapter.Fill(ds);
316             conn.Close();
317             return ds;
318         }
319         #endregion
320 
321         /// <summary>
322         /// 
323         /// </summary>
324         /// <param name="sql"></param>
325         /// <param name="order"></param>
326         /// <param name="start"></param>
327         /// <param name="end"></param>
328         /// <returns></returns>
329         private static string ForSql(string sql, string order, int start, int end)
330         {
331             var match = Regex.Match(sql, @"[\s+]?SELECT\s+");
332             if (match.Success)
333             {
334                 sql = sql.Insert(match.Length, string.Format("Row_Number() OVER ({0}) rowNumber,", order));
335                 // sql = string.Format("select Row_Number() OVER ({0}) rowNumber,* from ({1}) t", order, sql);
336                 sql = @" SELECT * FROM  (" + sql + " ) item "
337                        + " WHERE item.rowNumber BETWEEN " + start + " AND " + end + " ";
338 
339             }
340             return sql;
341         }
342 
343         /// <summary>
344         /// 
345         /// </summary>
346         /// <param name="sql"></param>
347         /// <param name="order"></param>
348         /// <returns></returns>
349         private static string ForSql(string sql, string order)
350         {
351             var match = Regex.Match(sql, @"[\s+]?SELECT\s+");
352             if (match.Success)
353             {
354                 sql = sql.Insert(match.Length, string.Format("Row_Number() OVER ({0}) rowNumber,", order));
355                 // sql = string.Format("select Row_Number() OVER ({0}) rowNumber,* from ({1}) t", order, sql);
356                 /*sql = @" SELECT * FROM  (" + sql + " ) item "
357                        + " WHERE item.rowNumber BETWEEN " + start + " AND " + end + " ";*/
358             }
359             return sql;
360         }
361 
362         #region 获取连接串
363         /// <summary>
364         /// 获取连接串
365         /// </summary>
366         /// <returns></returns>
367         internal static string GetConnection()
368         {
369             return ConfigurationManager.ConnectionStrings["ConnectionString"].ConnectionString;
370         }
371         #endregion
372 
373         #region 获取报表路径
374         /// <summary>
375         /// 获取报表路径
376         /// </summary>
377         /// <param name="p_ReportXmlName"></param>
378         /// <returns></returns>
379         internal static string GetReportPath(string p_ReportXmlName)
380         {
381             string m_BasePath = AppDomain.CurrentDomain.BaseDirectory + "/bin/Resource/ReportXml/";
382             return m_BasePath + p_ReportXmlName + ".xml";
383         }
384         #endregion
385 
386         #region 获取Sql语句
387         /// <summary>
388         /// 获取Sql语句
389         /// </summary>
390         /// <param name="reportPath"></param>
391         /// <param name="reportName"></param>
392         /// <param name="where"></param>
393         /// <returns></returns>
394         internal static string GetSql(string reportPath, string reportName, List<KeyValue> where)
395         {
396             var xDoc = XDocument.Load(reportPath);  //加载XML报表参数
397 
398             //读取XML获取参数字段信息
399             var queryXml = (from q in xDoc.Descendants("report")
400                             where q.Attribute("id").Value.Trim().ToLower() == reportName.Trim().ToLower()
401                             select q).AsQueryable();
402 
403             var querySql = queryXml.Elements("sql").FirstOrDefault();  //查出SQL语句
404             //var m_SqlType = string.Empty;
405             //var querySqlObj = queryXml.Elements("type").FirstOrDefault();
406             //if (m_SqlType != null)
407             //{
408             //    m_SqlType = querySqlObj.Value;
409             //}
410 
411             #region 语句最后的查询条件
412             if (querySql == null)  //如果没配置则返回NULL
413                 return null;
414 
415             string uperSql = querySql.Value;
416 
417             #region 子查询的查询条件
418             var childAttr = queryXml.Elements("childDynamic");
419 
420             foreach (var _child in childAttr)
421             {
422                 int cIndex = 1;
423                 var child = _child.Elements("isNotEmpty");
424                 if (child == null)
425                     continue;
426                 var childEle = _child.Elements("isNotEmpty").ToList();
427 
428                 //StringBuilder para = new StringBuilder();
429                 string c_Param = HandleParam(childEle, where, cIndex);
430                 string childEnd = _child.Element("childEnd") == null ? "" : _child.Element("childEnd").Value;
431                 if (c_Param.Length == 0)
432                 {
433                     uperSql = uperSql.Replace(_child.Attribute("property").Value.ToLower(), childEnd);
434                     continue;
435                 }
436                 uperSql = uperSql.Replace(_child.Attribute("property").Value.ToLower(), c_Param.Insert(0, _child.Attribute("prepend").Value + " ") + childEnd);
437             }
438 
439             #endregion
440 
441             StringBuilder sql = new StringBuilder();
442             var attr = queryXml.Elements("dynamic");    //得到设置类型的查询参数  (获取查询条件)
443             if (attr == null || attr.Elements("isNotEmpty").Count() == 0)
444                 return uperSql;
445             sql.Append(uperSql);
446 
447             var paraEle = attr.Elements("isNotEmpty").ToList();
448             int index = 1;
449 
450             string strPara = HandleParam(paraEle, where, index); //where 参数
451 
452             #endregion
453             if (!string.IsNullOrEmpty(strPara))
454             {
455                 sql.Append(strPara.Insert(0, attr.Attributes("prepend").Select(q => q.Value).FirstOrDefault() + " "));
456             }
457             var endSql = queryXml.Elements("endSql");
458             if (endSql.FirstOrDefault() != null)
459             {
460                 sql.Append(endSql.Select(q => q.Value).FirstOrDefault() + " ");
461             }
462 
463             return sql.ToString();  //得到查询的SQL语句,去掉XML里面的多余空格 
464 
465         }
466         #endregion
467 
468         #region 处理所有参数以及Where的值
469         /// <summary>
470         /// 处理所有参数以及Where的值
471         /// </summary>
472         /// <param name="childEle"></param>
473         /// <param name="where"></param>
474         /// <param name="index"></param>
475         /// <returns></returns>
476         private static string HandleParam(List<XElement> childEle, List<KeyValue> where, int index)
477         {
478             StringBuilder para = new StringBuilder();
479             foreach (var ele in childEle)
480             {
481                 if (ele.Attribute("value") != null && ele.Attribute("value").Value.ToLower() == "fixed")
482                 {
483                     para.Append(" " + GetStr(index, ele.Value, ele.Attribute("prepend").Value));
484                     index++;
485                     continue;
486                 }
487                 var ctn = where.Where(q => q.Key.ToString().ToLower() == ele.Attribute("property").Value.ToLower()).FirstOrDefault(); //判断查询条件是否存在
488                 if (ctn == null)
489                     continue;
490 
491                 object objType = ele.Attribute("type");
492                 string type = string.Empty;
493                 if (null != objType)
494                 {
495                     type = ele.Attribute("type").Value.ToLower();
496                 }
497 
498                 //in条件特殊处理
499                 if (type == "in")
500                 {
501                     string[] inValue = ctn.Value.ToString().Split(new char[] { ',' }, StringSplitOptions.RemoveEmptyEntries).Select(n => n).ToArray();
502                     string strValue = string.Join(",", inValue);
503 
504                     List<string> p = new List<string>();
505                     for (int i = 0; i < inValue.Count(); i++)
506                     {
507                         where.Add(new KeyValue { Key = ctn.Key.ToString() + i, Value = inValue[i] });
508                         p.Add("@" + ctn.Key + i);
509                     }
510 
511                     if (index == 1)
512                     {
513                         para.Append(" " + ele.Value.ToLower().Replace("@" + ctn.Key.ToString().ToLower(), string.Join(",", p)));
514                     }
515                     else
516                     {
517                         para.Append(" " + ele.Attribute("prepend").Value);
518                         para.Append(" " + ele.Value.ToLower().Replace("@" + ctn.Key.ToString().ToLower(), string.Join(",", p)));
519                     }
520                     where.Remove(ctn);
521                     index++;
522                     continue;
523                 }
524 
525                 if (type == "like" && (ctn.Value.ToString().Contains("%") || ctn.Value.ToString().Contains("_")))
526                 {
527                     ctn.Value = ctn.Value.ToString().Replace("%", "[%]").Replace("_", "[_]");
528                     para.Append(" " + GetStr(index, ele.Value, ele.Attribute("prepend").Value));
529 
530                     index++;
531                     continue;
532                 }
533 
534                 para.Append(" " + GetStr(index, ele.Value, ele.Attribute("prepend").Value));
535                 index++;
536             }
537             return para.ToString();
538         }
539         #endregion
540 
541         #region type sql的查询条件,index,where 当1的时候紧跟where后面 strIn in的时候值带入SQL语句,XML中的语句,prepend 语句中的关键字(and ,or )
542         /// <summary>
543         /// type sql的查询条件,index,where 当1的时候紧跟where后面 strIn in的时候值带入SQL语句,XML中的语句,prepend 语句中的关键字(and ,or )
544         /// </summary>
545         /// <param name="index"></param>
546         /// <param name="eleStr"></param>
547         /// <param name="prepend"></param>
548         /// <returns></returns>
549         private static string GetStr(int index, string eleStr, string prepend)
550         {
551             string para = string.Empty;
552             if (index == 1)
553             {
554                 return eleStr;
555             }
556             else
557             {
558                 return prepend + " " + eleStr;
559             }
560         }
561         #endregion
562 
563 
564     }
565 
566     #region 报表参数
567     /// <summary>
568     /// 报表参数
569     /// </summary>
570     public class ReportParams
571     {
572         /// <summary>
573         /// 过滤条件
574         /// </summary>
575         public List<KeyValue> Where { get; set; }
576         /// <summary>
577         /// 页面大小
578         /// </summary>
579         public int PageSize { get; set; }
580         /// <summary>
581         /// 页面索引
582         /// </summary>
583         public int PageIndex { get; set; }
584         /// <summary>
585         /// 排序方式
586         /// </summary>
587         public string Order { get; set; }
588         /// <summary>
589         /// 排序字段
590         /// </summary>
591         public string Sort { get; set; }
592     }
593 
594     public class KeyValue
595     {
596         public object Key { get; set; }
597 
598         public object Value { get; set; }
599     }
600     #endregion
601 }
ReportHelper

 

posted @ 2016-04-30 14:44  不二囧青年  阅读(250)  评论(0编辑  收藏  举报