Python语言技术文档

微信小程序技术文档

php语言技术文档

jsp语言技术文档

asp语言技术文档

C#/.NET语言技术文档

html5/css技术文档

javascript

点击排行

您现在的位置:首页 > 技术文档 > MVC/.NET框架

利用ASP.NET_MVC+EasyUI+SqlServer搭建企业开发框架

来源:中文源码网    浏览:324 次    日期:2024-04-27 18:53:00
【下载文档:  利用ASP.NET_MVC+EasyUI+SqlServer搭建企业开发框架.txt 】


利用ASP.NET MVC+EasyUI+SqlServer搭建企业开发框架
我们要搭建的框架是企业级开发框架,适用用企业管理信息系统的开发,如:OA、HR等
1、框架名称:sampleFrame。
2、搭建原则:最少知识原则。
3、先定义一个简单的编码规范:除类名和接口名外,其余首字母小写。
4、准备开发环境:vs2010及以上(mvc4)、sqlserver、jquery2.0和easyui1.4.5
首先来看一下列表页面的效果图:
我们期望简洁带前台代码,如下:










customerId

companyName

phone

address




data-options="onClickButton:function(){loadList(loadListSettings);}" />

详细查询





为了这样简洁的前台,我们需要准备:
1、通用的布局模板_Layout.cshtml。base.css、base.js、defaultSettings.js、tool.js和private.js见后面

















@RenderSection("scripts", required: false)


@RenderBody()


2、平台样式表base.css
.icon-find
{
background: url('icons/find.png') no-repeat center center;
}
.datagrid-toolbar div:nth-child(1)
{
float: left;
width: 60%;
}
.datagrid-toolbar div:nth-child(2)
{
margin-left: 60%;
margin-right: 10px;
width: auto;
text-align: right;
}
3、基本方法脚本base.js
//取消自动渲染
$.parser.auto = false;
function pageInit() {
//改变控件默认值
$.fn.linkbutton.defaults.plain = true;
$.fn.datagrid.defaults.fit = true;
$.fn.datagrid.defaults.fitColumns = true;
$.fn.datagrid.defaults.pagination = true;
//显示ajax异常信息
$(document).ajaxError(function (event, xhr, options, exc) {
$.messager.alert({ title: '异步请求出错', msg: xhr.responseText, icon: "error" });
});
//地址栏传参允许中文
jQuery(document).ajaxSend(function (event, request, options) {
options.url = encodeURI(options.url);
});
$.parser.parse();
}
function loadList(settings) {
var settings = $.extend(true, {}, loadListDefaultSettings, settings);
if ($("#" + settings.gridId).length == 0)
$.messager.alert({ title: "系统异常", msg: "DataGrid:" + settings.gridId + "不存在!", icon: "error" });
var quickQueryData = [];
if ($("#" + settings.queryBoxId).length > 0) {
var val = $("#" + settings.queryBoxId).textbox("getValue");
if (settings.searchFields && val) {
var keys = settings.searchFields.split(',');
for (i = 0, len = keys.length; i < len; i++) {
quickQueryData.push({ field: keys[i], method: 'inLike', value: val });
}
}
}
var queryData = []; //详细查询预留
//加载数据
$("#" + settings.gridId).datagrid("load", { quickQueryData: JSON.stringify(quickQueryData), queryData: JSON.stringify(queryData) });
}
4、基本脚本默认值defaultSettings.js
//查询参数设置
var loadListDefaultSettings = {
url: "getList",
gridId: "dataGrid",
queryWindowId: "queryWindow",
queryBoxId: "queryBox",
searchFields: "Name",
addQueryString: true,
prompt: "请输入"
};
5、可能需要使用的工具方法tool.js
//判断是否包含地址栏参数
function hasQueryString(key, url) {
if (typeof (url) == "undefined")
url = window.location.search;
var re = new RegExp("[?&]" + key + "=([^\\&]*)", "i");
var a = re.exec(url);
if (a == null) return false;
return true;
}
//获取地址栏参数,如果参数不存在则返回空字符串
function getQueryString(key, url) {
if (typeof (url) == "undefined")
url = window.location.search;
var re = new RegExp("[?&]" + key + "=([^\\&]*)", "i");
var a = re.exec(url);
if (a == null) return "";
return a[1];
}
//将当前地址栏参数加入到url
function addUrlSearch(url) {
var newParams = [];
var paramKeys = window.location.search.replace('?', '').split('&');
for (var i = 0; i < paramKeys.length; i++) {
var key = paramKeys[i].split('=')[0];
if (key == "" || key == "_t" || key == "_winid" || key == "isTab")
continue;
if (!hasQueryString(key, url))
newParams.push(paramKeys[i]);
}
if (url.indexOf('?') >= 0)
return url + "&" + newParams.join('&');
else
return url + "?" + newParams.join('&');
}
//url增加参数
function addSearch(url, key, value) {
if (!hasQueryString(key, url)) {
if (url.indexOf('?') >= 0)
return url + "&" + key + "=" + value;
else
return url + "?" + key + "=" + value;
}
else
return url;
}
//获取数组中对象的某个值,逗号分隔
function getValues(rows, attr) {
var fieldValues = [];
for (var i = 0; i < rows.length; i++) {
if (rows[i] != null)
fieldValues.push(rows[i][attr]);
}
return fieldValues.join(',');
}
6、可能需要使用的私有方法private.js,此文件包含的方法专供base.js使用,开发web时禁止使用
//替换掉Url中的{}参数
function replaceUrl(settings, pty) {
if (!pty)
pty = "url";
if (!settings[pty])
return;
var str = settings[pty];
var guid = "";
var result = str.replace(/\{[0-9a-zA-Z_]*\}/g, function (e) {
var key = e.substring(1, e.length - 1);
if (key == "GUID") {
if (!guid) {
$.ajax({
url: "getGuid",
type: "post",
async: false,
success: function (text, textStatus) {
guid = text;
}
});
}
return guid;
}
if (hasQueryString(key)) //从地址栏返回
return getQueryString(key);
if (settings.currentRow && settings.currentRow[key])//从当前行返回
return settings.currentRow[key];
if (settings.paramFrom) { //从指定控件返回
var ctrl = mini.get(settings.paramFrom);
if (ctrl == undefined) {
$.messager.alert({ title: 'UI出错', msg: "Id为" + settings.paramFrom + "的控件不存在!", icon: "error" });
return;
}
else if (ctrl.showCheckBox) {
return getValues(ctrl.getCheckedNodes(), key);
}
else if (ctrl.getSelecteds)
return getValues(ctrl.getSelecteds(), key);
else if (ctrl.getValue)
return ctrl.getValue();
}
return e;
});
settings[pty] = result;
return result;
}
//转化为全路径
function changeToFullUrl(settings) {
var url = settings.url;
if (url.indexOf('/') == 0 || url.indexOf("http://") == 0 || url.indexOf('?') == 0 || url == "")
return url;
currentUrlPathName = window.location.pathname;
var currentPathNameParts = currentUrlPathName.split('/');
var pathNameParts = url.split('?')[0].split('/');
if (currentPathNameParts[currentPathNameParts.length - 1] == "")
currentPathNameParts.pop(); //去掉一个反斜线
if (pathNameParts[pathNameParts.length - 1] == "")
pathNameParts.pop(); //去掉一个反斜线
var index = currentPathNameParts.length - 1;
for (var i = 0; i < pathNameParts.length; i++) {
if (pathNameParts[i] == "..") {
index = index - 1;
if (index <= 0) {
$.messager.alert({ title: "系统异常", msg: "Url错误:" + url + "!", icon: "error" });
return;
}
continue;
}
if (index < currentPathNameParts.length)
currentPathNameParts[index] = pathNameParts[i];
else
currentPathNameParts.push(pathNameParts[i]);
index = index + 1;
}
var length = currentPathNameParts.length;
for (var i = index; i < length; i++) {
currentPathNameParts.pop();
}
var result = currentPathNameParts.join('/');
if (url.indexOf('?') > 0)
result += url.substring(url.indexOf('?'));
settings.url = result;
}
我们期望简洁的后台代码,如下:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Web.Mvc;
using formula;
using System.Data;
namespace demo.Areas.basic.Controllers
{
public class customerController : BaseController
{
public JsonResult getList(QueryBuilder qb)
{
SqlHelper sqlHelper = new SqlHelper("demo");
var data = sqlHelper.ExecuteGridData("select *,id=customerId from customer", qb);
return Json(data);
}
}
}
为了这种简洁的代码我们需要:
1、Controller基类BaseController:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Web.Mvc;
using System.Data.Entity;
using System.Data.SqlClient;
using System.Data.Entity.Validation;
using System.ComponentModel;
using System.Reflection;
using System.Web.Security;
using formula;
namespace formula
{
public abstract class BaseController : Controller
{
#region 处理不存在的Action
protected override void HandleUnknownAction(string actionName)
{
if (Request.HttpMethod == "POST")
{
HttpContext.ClearError();
HttpContext.Response.Clear();
HttpContext.Response.StatusCode = 500;
HttpContext.Response.Write("没有Action:" + actionName);
HttpContext.Response.End();
}
// 搜索文件是否存在
var filePath = "";
if (RouteData.DataTokens["area"] != null)
filePath = string.Format("~/Areas/{2}/Views/{1}/{0}.cshtml", actionName, RouteData.Values["controller"], RouteData.DataTokens["area"]);
else
filePath = string.Format("~/Views/{1}/{0}.cshtml", actionName, RouteData.Values["controller"]);
if (System.IO.File.Exists(Server.MapPath(filePath)))
{
View(filePath).ExecuteResult(ControllerContext);
}
else
{
HttpContext.ClearError();
HttpContext.Response.Clear();
HttpContext.Response.StatusCode = 500;
HttpContext.Response.Write("没有Action:" + actionName);
HttpContext.Response.End();
}
}
#endregion
#region 基类Json方法重载
protected override JsonResult Json(object data, string contentType, Encoding contentEncoding, JsonRequestBehavior behavior)
{
NewtonJsonResult result = new NewtonJsonResult() { Data = data, ContentType = contentType, ContentEncoding = contentEncoding, JsonRequestBehavior = behavior };
return result;
}
protected override JsonResult Json(object data, string contentType, Encoding contentEncoding)
{
NewtonJsonResult result = new NewtonJsonResult() { Data = data, ContentType = contentType, ContentEncoding = contentEncoding };
return result;
}
#endregion
#region 异常处理
protected override void OnException(ExceptionContext filterContext)
{
Exception exp = filterContext.Exception;
if (string.IsNullOrEmpty(exp.Message))
exp = exp.GetBaseException();
if (filterContext.RequestContext.HttpContext.Request.IsAjaxRequest())
{
var response = filterContext.RequestContext.HttpContext.Response;
response.Clear();
response.Write(exp.Message);
response.StatusCode = 500;
response.End();
}
}
#endregion
}
}
2、查询构造器QueryBuilder:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Collections;
using System.Web.Mvc;
namespace formula
{
[ModelBinder(typeof(QueryBuilderBinder))]
public class QueryBuilder : SearchCondition
{
public int page { get; set; }
public int rows { get; set; }
public string sort { get; set; }
public string order { get; set; }
public int total { get; set; }
public string getOrderByString(bool hasOrderBy = true)
{
var sortFields = this.sort.Split(',');
var sortOrders = this.order.Split(',');
string str = "";
for (int i = 0; i < sortFields.Length; i++)
{
str += sortFields[i] + " " + sortOrders[i] + ",";
}
if (hasOrderBy && str != "")
str = "order by " + str;
return str.Trim(',');
}
}
public class SearchCondition
{
public string fields = "*";
private List quickItems = new List();
private List complexItems = new List();
public SearchCondition add(string field, string method, object val, bool isQuickSearch = false)
{
//处理日期型数据
if (method == "<" || method == "<=")
{
if (val.GetType() == typeof(DateTime))
{
DateTime t = (DateTime)val;
val = t.Date.AddHours(23).AddMinutes(59).AddSeconds(59);
}
}
ConditionItem item = new ConditionItem(field, method, val);
if (isQuickSearch)
quickItems.Add(item);
else
complexItems.Add(item);
return this;
}
public string getWhereString(bool hasWhere = true)
{
if (quickItems.Count == 0 && complexItems.Count == 0)
return "";
string strWhere = "";
if (quickItems.Count > 0)
strWhere += " and (" + getGourpWhereString(quickItems, true) + ")";
if (complexItems.Count > 0)
strWhere += " and (" + getGourpWhereString(complexItems, false) + ")";
if (hasWhere)
strWhere = " where " + strWhere.Substring(4);
else
strWhere = " and " + strWhere.Substring(4);
return strWhere;
}
#region 私有方法
private string getGourpWhereString(List list, bool isOrRelation = false)
{
if (list.Count == 0)
return "";
string strWhere = "";
for (int i = 0; i < list.Count(); i++)
{
var item = list[i];
string str = item.getWhereString();
if (isOrRelation)
{
strWhere += " or " + str;
}
else
{
strWhere += " and " + str;
}
}
strWhere = strWhere.Substring(4);
return strWhere;
}
#endregion
}
public class ConditionItem
{
public ConditionItem(string field, string method, object val)
{
this.field = field;
this.method = method;
this.value = val;
}
public string field { get; set; }
public string method { get; set; }
public object value { get; set; }
public string getWhereString()
{
var item = this;
switch (item.method)
{
case "=":
case "<":
case ">":
case "<=":
case ">=":
case "<>":
return string.Format("{0} {1} '{2}'", item.field, item.method, item.value);
case "in":
string v = "";
if (item.value is ICollection)
{
ICollection collection = item.value as ICollection;
v = string.Join("','", collection.ToArray());
return string.Format("{0} in('{1}')", item.field, v);
}
else
{
v = item.value.ToString().Replace(",", "','");
}
return string.Format("{0} in ('{1}')", item.field, v);
case "between":
object[] objs = item.value as object[];
return string.Format("{0} between '{1}' and '{2}'", item.field, objs[0], objs[1]);
case "inLike":
string[] arr = null;
if (item.value is ICollection)
{
ICollection collection = item.value as ICollection;
arr = collection.ToArray();
}
else
{
arr = item.value.ToString().Split(',', ',');
}
string str = "";
foreach (string s in arr)
{
str += string.Format("or {0} like '%{1}%'", item.field, s);
}
return "(" + str.Substring(3) + ")";
case "day":
DateTime dt = DateTime.Now;
if (!DateTime.TryParse(item.value.ToString(), out dt))
{
throw new BuessinessException("查询条件不能转化为日期时间");
}
string start = dt.Date.ToString("yyyy-MM-dd");
string end = dt.Date.AddDays(1).ToString("yyyy-MM-dd");
return string.Format("{0} between '{1}' and '{2}'", item.field, start, end);
case "startWith":
return string.Format("{0} like '{1}%'", item.field, item.value);
case "endWith":
return string.Format("{0} like '%{1}'", item.field, item.value);
default:
return "";
}
}
}
}
3、查询构造器QueryBuilder的创建方法QueryBuilderBinder:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Web.Mvc;
namespace formula
{
public class QueryBuilderBinder : IModelBinder
{
public object BindModel(ControllerContext controllerContext, ModelBindingContext bindingContext)
{
var qb = (QueryBuilder)(bindingContext.Model ?? new QueryBuilder());
var dict = controllerContext.HttpContext.Request.Params;
var quickQueryList = !string.IsNullOrEmpty(dict["quickQueryData"]) ? JsonHelper.ToList(dict["quickQueryData"]) : new List>();
var queryList = !string.IsNullOrEmpty(dict["queryData"]) ? JsonHelper.ToList(dict["queryData"]) : new List>();
foreach (var dic in quickQueryList)
{
var val = dic["value"].ToString();
if (val == "") continue;
qb.add(dic["field"].ToString(), dic["method"].ToString(), val, true);
}
foreach (var dic in queryList)
{
var val = dic["value"].ToString();
if (val == "") continue;
qb.add(dic["field"].ToString(), dic["method"].ToString(), val, false);
}
qb.page = !string.IsNullOrEmpty(dict["page"]) ? int.Parse(dict["page"].ToString()) : 1;
qb.rows = !string.IsNullOrEmpty(dict["rows"]) ? int.Parse(dict["rows"].ToString()) : 10;
qb.sort = !string.IsNullOrEmpty(dict["sort"]) ? dict["page"].ToString() : "id";
qb.order = !string.IsNullOrEmpty(dict["order"]) ? dict["order"].ToString() : "desc";
return qb;
}
}
}
4、数据库查询帮助类SqlHelper:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Data.SqlClient;
using System.Data;
using System.Web;
namespace formula
{
public class SqlHelper
{
#region 构造函数
public SqlHelper(string connName)
{
if (System.Configuration.ConfigurationManager.ConnectionStrings[connName] == null)
throw new BuessinessException(string.Format("配置文件中不包含数据库连接字符串:{0}", connName));
this.connName = connName;
this.connString = System.Configuration.ConfigurationManager.ConnectionStrings[connName].ConnectionString;
}
public string connName { get; private set; }
public string connString { get; private set; }
public string dbName
{
get
{
SqlConnection conn = new SqlConnection(connString);
return conn.Database;
}
}
#endregion
#region 基本方法
public object ExecuteScalar(string cmdText)
{
using (SqlConnection conn = new SqlConnection(connString))
{
conn.Open();
SqlCommand cmd = new SqlCommand(cmdText, conn);
return cmd.ExecuteScalar();
}
}
public DataTable ExecuteDataTable(string cmdText)
{
using (SqlConnection conn = new SqlConnection(connString))
{
DataTable dt = new DataTable();
SqlDataAdapter apt = new SqlDataAdapter(cmdText, conn);
apt.Fill(dt);
return dt;
}
}
public DataTable ExecuteDataTable(string cmdText, int start, int len)
{
using (SqlConnection conn = new SqlConnection(connString))
{
DataTable dt = new DataTable();
SqlDataAdapter apt = new SqlDataAdapter(cmdText, conn);
apt.Fill(start, len, dt);
return dt;
}
}
public string ExecuteNonQuery(string cmdText)
{
using (SqlConnection conn = new SqlConnection(connString))
{
conn.Open();
SqlCommand cmd = new SqlCommand(cmdText, conn);
return cmd.ExecuteNonQuery().ToString();
}
}
#endregion
#region 支持查询对象
public DataTable ExecuteDataTable(string sql, SearchCondition cnd, string orderBy)
{
string sqlWhere = " where 1=1" + GetUrlFilterSqlWhere(sql) + cnd.getWhereString(false);
sql = string.Format("select {0} from ({1}) sourceTable {2} {3}", cnd.fields, sql, sqlWhere, orderBy);
DataTable dt = this.ExecuteDataTable(sql);
return dt;
}
public Dictionary ExecuteGridData(string sql, QueryBuilder qb)
{
string sqlWhere = " where 1=1" + GetUrlFilterSqlWhere(sql) + qb.getWhereString(false);
qb.total = (int)this.ExecuteScalar(string.Format("select count(1) from ({0}) sourceTable {1}", sql, sqlWhere));
sql = string.Format("select {0} from ({1}) sourceTable {2} {3}", qb.fields, sql, sqlWhere, qb.getOrderByString());
DataTable dt = ExecuteDataTable(sql, (qb.page - 1) * qb.rows, qb.rows);
Dictionary dic = new Dictionary();
dic.Add("total", qb.total);
dic.Add("rows", dt);
return dic;
}
#endregion
#region 私有方法
private string GetUrlFilterSqlWhere(string sql)
{
sql = string.Format("select * from({0}) as dt1 where 1=2", sql);
var dtField = ExecuteDataTable(sql);
StringBuilder sb = new StringBuilder();
foreach (string key in HttpContext.Current.Request.QueryString.Keys)
{
if (string.IsNullOrEmpty(key) || key.ToLower() == "id")
continue;
if (dtField.Columns.Contains(key))
{
string value = HttpContext.Current.Server.UrlDecode(HttpContext.Current.Request[key]);
value = value.Replace(",", "','");
sb.AppendFormat(" and {0} in ('{1}')", key, value);
}
}
return sb.ToString();
}
#endregion
}
}
5、用于取代返回值JsonResult的NewtonJsonResult:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Web.Mvc;
using System.Web;
using System.Data;
namespace formula
{
public class NewtonJsonResult : JsonResult
{
public override void ExecuteResult(ControllerContext context)
{
//确认是否用于响应HTTP-Get请求
if (this.JsonRequestBehavior == JsonRequestBehavior.DenyGet &&
string.Compare(context.HttpContext.Request.HttpMethod, "GET", true) == 0)
{
throw new InvalidOperationException("禁止Get请求");
}
HttpResponseBase response = context.HttpContext.Response;
//设置媒体类型和编码方式
response.ContentType = string.IsNullOrEmpty(this.ContentType) ?
"application/json" : this.ContentType;
if (this.ContentEncoding != null)
{
response.ContentEncoding = this.ContentEncoding;
}
//序列化对象,并写入当前的HttpResponse
if (null == this.Data) return;
if (this.Data is string)
{
response.Write(Data);
}
else if (this.Data is DataRow)
{
Dictionary dic = new Dictionary();
DataRow row = this.Data as DataRow;
foreach (DataColumn col in row.Table.Columns)
{
dic.Add(col.ColumnName, row[col]);
}
response.Write(JsonHelper.ToJson(dic));
}
else
{
response.Write(JsonHelper.ToJson(this.Data));
}
}
}
}
6、Json序列化和反序列的帮助类JsonHelper:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Newtonsoft.Json.Converters;
using Newtonsoft.Json;
namespace formula
{
public static class JsonHelper
{
public static string ToJson(T obj)
{
if (obj == null || obj.ToString() == "null") return null;
if (obj != null && (obj.GetType() == typeof(String) || obj.GetType() == typeof(string)))
{
return obj.ToString();
}
IsoDateTimeConverter dt = new IsoDateTimeConverter();
dt.DateTimeFormat = "yyyy'-'MM'-'dd'T'HH':'mm':'ss";
return JsonConvert.SerializeObject(obj, dt);
}
///
/// 从一个Json串生成对象信息
///

/// JSON字符串
/// 对象类型
///
public static T ToObject(string json) where T : class
{
if (String.IsNullOrEmpty(json)) return null;
T obj = JsonConvert.DeserializeObject(json);
return obj;
}
///
/// 返回 Diction
///

///
///
public static Dictionary ToObject(string json)
{
if (String.IsNullOrEmpty(json)) return new Dictionary();
return ToObject>(json);
}
///
/// 返回 List>
///

///
///
public static List> ToList(string json)
{
if (String.IsNullOrEmpty(json)) return new List>();
return ToObject>>(json);
}
///
/// 组装对象
///

///
///
public static void PopulateObject(string json, object obj)
{
if (String.IsNullOrEmpty(json)) return;
JsonConvert.PopulateObject(json, obj);
}
}
}
7、用于区分系统异常和业务异常的BusinessException:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Runtime.Serialization;
namespace formula
{
///
/// 业务异常
///

[Serializable]
public class BuessinessException : Exception
{
///
/// 系统异常构造函数
///

public BuessinessException()
{
}
///
/// 系统异常构造函数
///

/// 异常的消息
public BuessinessException(string message)
: base(message)
{
}
///
/// 系统异常构造函数
///

/// 异常的消息
/// 内部的异常
public BuessinessException(string message, System.Exception inner)
: base(message, inner)
{
}
///
/// 系统异常构造函数
///

/// 存有有关所引发异常的序列化的对象数据
/// 包含有关源或目标的上下文信息
public BuessinessException(SerializationInfo info, StreamingContext context)
: base(info, context)
{
}
}
}
最后,上代码:http://xiazai.zwyuanma.com/201604/yuanma/ASP.NET-MVC-EasyUI-sampleFrame%28zwyuanma.com%29.rar

相关内容