第一次分享代码,不足或不对之处请指正。。

需求:微信端传递不同的参数调用WebAPI进行分页查询菜谱计划点评结果

思路:基于视图来查询,根据传递的不同参数拼接分页查询Sql来查询。

分页的sql如下

select * from 视图 where 排序字段 in( select top 每页数量 排序字段 from ( select top 每页数量 排序字段 from 视图  where条件  order by 排序字段 asc ) t )

首先建立参数模型类BasePageQueryInfo

/// <summary>
/// 分页查询信息-基类
/// </summary>
public class BasePageQueryInfo
{
/// <summary>
/// 查询语句
/// </summary>
protected string _querySql; /// <summary>
/// 查询语句
/// </summary>
public string QuerySql
{
get
{
return _querySql;
}
} /// <summary>
/// 查询视图名称
/// </summary>
protected string _view; /// <summary>
/// 查询视图名称
/// </summary>
public string View
{
get
{
return _view;
}
} /// <summary>
/// 每页记录数
/// </summary>
public int PageSize { get; set; } /// <summary>
/// 当前页
/// </summary>
public int Page { get; set; } /// <summary>
/// 排序字段
/// </summary>
public string OrderByField { get; set; } /// <summary>
/// 排序/降序
/// </summary>
public string OrderBy { get; set; } /// <summary>
/// where查询条件
/// </summary>
protected string _whereCondition; /// <summary>
/// where查询条件
/// </summary>
public string WhereCondition
{
get
{
return _whereCondition;
}
} /// <summary>
/// where入参
/// </summary>
protected List<SqlInParameter> _listSqlInParameter; /// <summary>
/// where入参
/// </summary>
public List<SqlInParameter> ListSqlInParameter
{
get
{
return _listSqlInParameter;
}
} /// <summary>
/// 总条目数Sql
/// </summary>
protected string _totalCountSql; /// <summary>
/// 总条目数Sql
/// </summary>
public string TotalCountSql
{
get
{
return _totalCountSql;
}
} /// <summary>
/// 分页查询Sql
/// </summary>
protected string _pageSql; /// <summary>
/// 分页查询Sql
/// </summary>
public string PageSql
{
get
{
return _pageSql;
}
} /// <summary>
/// 初始化分页查询属性
/// </summary>
/// <returns></returns>
public bool InitPageQueryProperty()
{
try
{
//Where条件语句和入参
StringBuilder sbWhereSql = new StringBuilder();
Type t = this.GetType();
PropertyInfo[] properties = t.GetProperties().Where(x => !IsNullValue(x.GetValue(this))).ToArray();
_listSqlInParameter = new List<SqlInParameter>();
bool isFirst = true;
for (int i = ; i < properties.Length; i++)
{
PropertyInfo property = properties[i];
object propertyValueObj = property.GetValue(this);
SqlConditionAttribute conditionAttr = property.GetCustomAttribute<SqlConditionAttribute>();
if (conditionAttr == null) continue;
if (isFirst)
{
sbWhereSql.AppendFormat(" {0} {1} @{2} ",
conditionAttr.SqlField, conditionAttr.CompareSymbol, conditionAttr.SqlField);
isFirst = false;
}
else
{
sbWhereSql.AppendFormat(" And {0} {1} @{2} ",
conditionAttr.SqlField, conditionAttr.CompareSymbol, conditionAttr.SqlField);
}
SqlInParameter inParam = new SqlInParameter();
inParam.DataType = conditionAttr.DataType;
inParam.ParameterName = conditionAttr.SqlField;
inParam.ParameterValue = propertyValueObj;
inParam.IsVague = conditionAttr.CompareSymbol == CompareSymbol.LIKE;
_listSqlInParameter.Add(inParam);
}
if (_listSqlInParameter.Count > )
{
sbWhereSql.Insert(, " Where ");
}
_whereCondition = sbWhereSql.ToString(); //分页Sql
StringBuilder sbPageSql = new StringBuilder();
sbPageSql.AppendFormat("select * from {0} where ", this.View);
sbPageSql.Append(this.OrderByField);
sbPageSql.Append(" in( select top ");
sbPageSql.Append(this.PageSize);
sbPageSql.Append(" ");
sbPageSql.Append(this.OrderByField);
sbPageSql.Append(" from ( select top (");
sbPageSql.Append(this.PageSize * this.Page);
sbPageSql.Append(") ");
sbPageSql.Append(this.OrderByField);
sbPageSql.AppendFormat(" from {0} ", this.View);
sbPageSql.Append(_whereCondition);
sbPageSql.Append(" order by ");
sbPageSql.Append(this.OrderByField);
sbPageSql.Append(" ");
sbPageSql.Append(this.OrderBy);
sbPageSql.Append(" ) t )");
_pageSql = sbPageSql.ToString(); //总个数sql
StringBuilder sbTotalSql = new StringBuilder();
sbTotalSql.AppendFormat("Select Count(1) From {0} ", this.View);
sbTotalSql.Append(WhereCondition);
_totalCountSql = sbTotalSql.ToString(); return true;
}
catch (Exception ex)
{
return false;
}
} private bool IsNullValue(object obj)
{
if (obj == null) return true; Type type = obj.GetType();
if (type.FullName == "System.Int32")
{
int d = -;
try
{
int.Parse(obj.ToString());
}
catch { d = -; }
if (d == -) return true;
}
else if (type.FullName == "System.String")
{
return string.IsNullOrWhiteSpace(obj.ToString());
}
//其他待补充
return false;
} /// <summary>
/// 自检
/// </summary>
/// <returns></returns>
public bool SelfValidate()
{
string[] orderbys = new string[] { "asc","desc" };
if (this.Page < || this.PageSize <=
|| string.IsNullOrWhiteSpace(this.OrderBy)
|| !orderbys.Contains(this.OrderBy.ToLower())
|| string.IsNullOrWhiteSpace(this.OrderByField))
{
return false;
} return true;
} }

入参SqlInParameter

/// <summary>
/// Sql入参信息
/// </summary>
public class SqlInParameter
{
/// <summary>
/// 参数名称
/// </summary>
public string ParameterName { get; set; } /// <summary>
/// 数据类型
/// </summary>
public DbType DataType { get; set; } /// <summary>
/// 参数值
/// </summary>
public object ParameterValue { get; set; } /// <summary>
/// 是否模糊参数查询
/// </summary>
public bool IsVague { get; set; }
}

参数模型属性SqlConditionAttribute,主要用来反射得到对应的查询字段,比较符号,生成SqlInParameter。

  /// <summary>
/// Sql条件属性
/// </summary>
public class SqlConditionAttribute : Attribute
{ /// <summary>
/// 对应Sql查询字段
/// </summary>
public string SqlField { get; set; } /// <summary>
/// 数据类型
/// </summary>
public System.Data.DbType DataType { get; set; } /// <summary>
/// 比较符号
/// </summary>
public string CompareSymbol { get; set; }
}

比较符号常量CompareSymbol

/// <summary>
/// 比较符号
/// </summary>
public class CompareSymbol
{
/// <summary>
/// 等于
/// </summary>
public const string EQUALS = "="; /// <summary>
/// 不等于
/// </summary>
public const string NOTEQUALS = "!="; /// <summary>
/// Like
/// </summary>
public const string LIKE = "Like"; /// <summary>
/// 大于
/// </summary>
public const string GREATER = ">"; /// <summary>
/// 大于等于
/// </summary>
public const string GREATEREQUALS = ">="; /// <summary>
/// 小于
/// </summary>
public const string SMALLER = "<"; /// <summary>
/// 小于等于
/// </summary>
public const string SMALLEREQUALS = "<="; }

分页查询结果类

/// <summary>
/// 分页结果数据
/// </summary>
/// <typeparam name="T"></typeparam>
public class PageResult<T> where T : class
{
/// <summary>
/// 总记录数
/// </summary>
public int Count { get; set; } /// <summary>
/// 总页数
/// </summary>
public int TotalPage { get; set; } /// <summary>
/// 当前页
/// </summary>
public int CurPage { get; set; } /// <summary>
/// 当前页数据
/// </summary>
public List<T> PageData { get; set; }
}

分页查询器PageQuerier

/// <summary>
/// 分页查询器
/// </summary>
public class PageQuerier
{
/// <summary>
/// 查询分页信息
/// </summary>
/// <typeparam name="T"></typeparam>
/// <param name="dbSession"></param>
/// <param name="pageQueryInfo"></param>
/// <returns></returns>
public static PageResult<T> Query<T>(DbSession dbSession,BasePageQueryInfo pageQueryInfo) where T : class
{
//总记录数
SqlSection countSqlSection = dbSession.FromSql(pageQueryInfo.TotalCountSql);
AddInParameterToSqlSection(countSqlSection, pageQueryInfo.ListSqlInParameter);
int totalCount = countSqlSection.ToFirst<int>(); //总页数
int totalPage = totalCount / pageQueryInfo.PageSize + (totalCount % pageQueryInfo.PageSize > ? : ); //当前页数据
SqlSection pageSqlSection = dbSession.FromSql(pageQueryInfo.PageSql);
AddInParameterToSqlSection(pageSqlSection, pageQueryInfo.ListSqlInParameter);
List<T> lstData = pageSqlSection.ToList<T>(); PageResult<T> pageResult = new PageResult<T>()
{
Count = totalCount,
TotalPage = totalPage,
CurPage = totalPage > pageQueryInfo.Page ? pageQueryInfo.Page : totalPage,
PageData = lstData
}; return pageResult;
} /// <summary>
/// 向SqlSection追加参数
/// </summary>
/// <param name="sqlSection"></param>
/// <param name="pageQueryInfo"></param>
private static void AddInParameterToSqlSection(SqlSection sqlSection,IEnumerable<SqlInParameter> sqlInParameters)
{
foreach (SqlInParameter inParam in sqlInParameters)
{
sqlSection.AddInParameter(inParam.ParameterName, inParam.DataType,
inParam.IsVague ? "%" + inParam.ParameterValue + "%" : inParam.ParameterValue);
}
}
}

笔者使用的是Dos.ORM来查询数据,该ORM中直接执行Sql示例如下

var list = DB.Context.FromSql("SELECT * FROM table WHERE name=@name AND id=@id")
.AddInParameter("@name", DbType.String, "ITdos")
.AddInParameter("@id", DbType.Int32, "")
.ToList<table>();
//也可以先拼接好参数,再一次性传入
var params = new DbParameter[];
params[] = DbSession.Default.Db.DbProviderFactory.CreateParameter();
params[].DbType = DbType.String;
params[].ParameterName = "@name";
params[].Value = "ITdos";
params[] = DB.Context.Db.DbProviderFactory.CreateParameter();
params[].DbType = DbType.Int32;
params[].ParameterName = "@id";
params[].Value = ;
DB.Context.FromSql("SELECT * FROM table WHERE name=@name AND id=@id")
.AddParameter(params)
.ToDataTable();

接下来是具体的分页查询模型

/// <summary>
/// 菜谱计划点评分页查询参数
/// </summary>
public class FoodPlanCommentPageQueryInfo : BasePageQueryInfo
{
/// <summary>
/// 菜谱计划点评分页查询参数
/// </summary>
public FoodPlanCommentPageQueryInfo()
{
this._view = "V_FoodPlanComment";
this.OrderBy = "asc";
this.OrderByField = "CommentTime";
} /// <summary>
/// MemberId
/// </summary>
[SqlCondition(SqlField = "MemberGuid", DataType = DbType.Guid, CompareSymbol = CompareSymbol.EQUALS)]
public string MemberGuid { get; set; } /// <summary>
/// OpenId
/// </summary>
[SqlCondition(SqlField = "OpenId", DataType = DbType.String, CompareSymbol = CompareSymbol.EQUALS)]
public string OpenId { get; set; } /// <summary>
/// 菜谱计划Id
/// </summary>
[SqlCondition(SqlField = "FoodPlanGuid", DataType = DbType.Guid, CompareSymbol = CompareSymbol.EQUALS)]
public string FoodPlanGuid { get; set; }
}

WebAPI实现

  public class FoodPlanCommentController : BaseApiController
{
/// <summary>
/// 获取菜谱计划点评信息
/// </summary>
/// <param name="param"></param>
/// <returns></returns>
public ResponseResult<PageResult<FoodPlanComment>> Get(FoodPlanCommentPageQueryInfo param)
{
if (!param.SelfValidate())
{
return ResponseResult<PageResult<FoodPlanComment>>.Custome(APICode.InValidParams);
}
if (string.IsNullOrWhiteSpace(param.FoodPlanGuid)
&& string.IsNullOrWhiteSpace(param.MemberGuid)
&& string.IsNullOrWhiteSpace(param.OpenId))
{
return ResponseResult<PageResult<FoodPlanComment>>.Custome(APICode.InValidParams,
"FoodPlanGuid,MemberGuid,OpenId必须存在一个查询参数");
}
if (!param.InitPageQueryProperty())
{
return ResponseResult<PageResult<FoodPlanComment>>.Custome(APICode.InternalError, "分页查询模型绑定失败");
}
try
{
PageResult<FoodPlanComment> pageResult = PageQuerier.Query<FoodPlanComment>(DBContext.Instance, param);
return ResponseResult<PageResult<FoodPlanComment>>.Success(pageResult);
}
catch (Exception ex)
{
this.Error(ex);
return ResponseResult<PageResult<FoodPlanComment>>.Custome(APICode.InternalError);
}
}
}

测试结果:

传递一个参数

传递两个参数时

C# WebAPI分页实现分享的更多相关文章

  1. bootstrap table 服务器端分页例子分享

    这篇文章主要介绍了bootstrap table 服务器端分页例子分享,需要的朋友可以参考下 1,前台引入所需的js 可以从官网上下载 复制代码代码如下: function getTab(){var ...

  2. H5+.Net Webapi集成微信分享前后端代码 微信JS-SDK wx.onMenuShareTimeline wx.onMenuShareAppMessage

    说明: 1/因为赚麻烦这里没有使用数据库或服务器缓存来存储access_token和jsapi_ticket,为了方便这里使用了本地的xml进行持久化这两个值以及这两个值的创建时间和有限期限. 2/每 ...

  3. PHP分页类分享

    /** * 获取分页的HTML内容 * @param integer $page 当前页 * @param integer $pages 总页数 * @param string $url 跳转url地 ...

  4. webapi+entityframework分享

    1. webapi允许跨域的增删改查要在web.config中加入以下文字 <system.webServer> <validation validateIntegratedMode ...

  5. phpcmsv9多表联合查询分页功能实现

    phpcms v9里面自带的listinfo分页函数蛮好用的,可惜啊.不支持多表查询并分页. 看了一下前台模板层支持get标签,支持多表查询,支持分页.刚好可以把这个功能搬到后台来使用. 我们现在对g ...

  6. 经验分享:10个简单实用的 jQuery 代码片段

    尽管各种 JavaScirpt 框架和库层出不穷,jQuery 仍然是 Web 前端开发中最常用的工具库.今天,向大家分享我觉得在网站开发中10个简单实用的 jQuery 代码片段. 您可能感兴趣的相 ...

  7. 基于OWIN WebAPI 使用OAuth授权服务【客户端验证授权(Resource Owner Password Credentials Grant)】

    适用范围 前面介绍了Client Credentials Grant ,只适合客户端的模式来使用,不涉及用户相关.而Resource Owner Password Credentials Grant模 ...

  8. 使用DataList 分页方法

    什么是DataList我想应该不需要解释了,接下来分享本人在项目里使用到的通过DataList进行分页展示方法. 首先在ASPX页面添加一个DataList(后面都简称DL)控件,示例代码如下: &l ...

  9. ThinkPHP分页实例

    ThinkPHP分页实例 (2014-09-20 15:34:36)   很多人初学thinkphp时,不太熟悉thinkphp的分页使用方法,现在将自己整理的分页方法分享下,有需要的朋友可以看看. ...

随机推荐

  1. Java内存模型探秘

    1.Java内存模型概述 Java内存模型是一种抽象概念,不是真实存在的.主要定义了程序中各个变量的访问规则,即在虚拟机中将变量存储到内存和从内存取出变量这样的底层细节.注意:这里的变量仅包括实例字段 ...

  2. Kotlin 扩展

    Kotlin 可以对一个类的属性和方法进行扩展,且不需要继承或使用 Decorator 模式. 扩展是一种静态行为,对被扩展的类代码本身不会造成任何影响. 扩展函数 扩展函数可以在已有类中添加新的方法 ...

  3. HTTP响应 状态码描述

  4. allure--下的各装饰器的翻译及自己的总结

    翻译图-快捷键 红色字体感觉用的会比较多,起码现在感觉应该是比其他的多一点 lable应该没有什么特殊的用法,只是对下面方法的一个汇总(或者可以这么说,下面的方法是lable更具体的实现) sever ...

  5. es6 Promise简单介绍

    promise的基本用法 promise执行多步操作非常好用,那我们就来模仿一个多步操作的过程,那就以吃饭为例吧.要想在家吃顿饭,是要经过三个步骤的. 洗菜做饭. 坐下来吃饭. 收拾桌子洗碗. 这个过 ...

  6. English trip EM2-MP4 Teacher:Taylor voiceless consonant 清辅音 & voiced consonant 浊辅音

    课上内容(Lesson) # 区分 voiceless consonant 清辅音 & voiced consonant 浊辅音 清辅音    short   # 轻快 浊辅音    long ...

  7. idea 配置git

    1.注册https://github.com 2. 3.填入信息完成

  8. vue单位文本控件与vue加密文本控件

    vue单位文本控件: 使用方式: npm install dami-text-input --save 使用: <text-input v-model="test" :uni ...

  9. 《剑指offer》总结三 之二叉树(2)

    目录 23.二叉搜索树的后序遍历序列 26.二叉搜索树与双向链表(31ms,5756k) 23.二叉搜索树的后序遍历序列 题目描述: 输入一个整数数组,判断该数组是不是某二叉搜索树的后序遍历的结果.如 ...

  10. 项目部署Vue+Django(luffy)

    部署路飞学城 部署整体框架图: 1 熟悉linux操作 2 上传路飞学城项目到linux服务器 xftp上传到服务器 lrzsz工具 3 完成python3解释器的安装 在linux命令行模式下, 输 ...