我正在使用jQuery數據表與服務器端C#/ asp.net mvc3處理。它現在一切正常,但我有一個新的任務要做:jquery datatables服務器端列
我想隱藏一些列出於安全原因某些用戶。如何在服務器端c#中創建列並傳遞給視圖中的數據表?
我正在使用jQuery數據表與服務器端C#/ asp.net mvc3處理。它現在一切正常,但我有一個新的任務要做:jquery datatables服務器端列
我想隱藏一些列出於安全原因某些用戶。如何在服務器端c#中創建列並傳遞給視圖中的數據表?
控制器可能類似於:
public JsonResult NewsJSON(jQueryDataTableParamModel param)
{
var news = _newsRepository.GetNews();
string col = param.sColumns.Split(',')[param.iSortCol_0];
string orderby = col + " " + param.sSortDir_0;
if (param.sSearch != null)
news = news.Search(param.sSearch);
var qry = new PaginatedList<News>(news.OrderBy(orderby), param.iDisplayStart, param.iDisplayLength);
return Json(new
{
sEcho = param.sEcho,
iTotalRecords = qry.TotalCount,
iTotalDisplayRecords = qry.TotalCount,
aaData = (
from n in qry
select new[]
{
n.Headline,
n.DateCreated.ToString()
}).ToArray()
}, JsonRequestBehavior.AllowGet);
}
jQueryDataTableParamModel.cs
public class jQueryDataTableParamModel
{
/// <summary>
/// Request sequence number sent by DataTable,
/// same value must be returned in response
/// </summary>
public string sEcho { get; set; }
/// <summary>
/// Text used for filtering
/// </summary>
public string sSearch { get; set; }
/// <summary>
/// Number of records that should be shown in table
/// </summary>
public int iDisplayLength { get; set; }
/// <summary>
/// First record that should be shown(used for paging)
/// </summary>
public int iDisplayStart { get; set; }
/// <summary>
/// Number of columns in table
/// </summary>
public int iColumns { get; set; }
/// <summary>
/// Number of columns that are used in sorting
/// </summary>
public int iSortingCols { get; set; }
/// <summary>
/// Comma separated list of column names
/// </summary>
public string sColumns { get; set; }
/// <summary>
/// Sort column
/// </summary>
public int iSortCol_0 { get; set; }
/// <summary>
/// Asc or Desc
/// </summary>
public string sSortDir_0 { get; set; }
}
,並考慮:
<script type="text/javascript" charset="utf-8">
$(function() {
$('#news').dataTable({
"bSort" : true,
"bServerSide": true,
"sAjaxSource": "/News/NewsJSON",
"bProcessing": true,
"sPaginationType": "full_numbers",
"iDisplayLength": 25,
"aLengthMenu": [[25, 50, 100, 150, 200], [25, 50, 100, 150, 200]],
"aaSorting": [[1,'asc']],
"aoColumns": [
{ "sName": "Headline" }
,{ "sName": "DateCreated" }
]
});
});
</script>
<table id="news" class="default-table" cellpadding="0" cellspacing="0">
<thead>
<tr>
<th>
Headline
</th>
<th style="width: 114px">
Created
</th>
</tr>
</thead>
</table>
或者類似的:)不知道如果我得到了JS正確的,但。
/拉塞
UPDATE:
有點凌亂,但類似:
public class DataTableOptions
{
public string ID { get; set; }
public string Url { get; set; }
public string Cols { get; set; }
public bool Sort { get; set; }
public string ViewUrlLinkname { get; set; }
public string EditUrlLinkname { get; set; }
public string DeleteLinkname { get; set; }
public string DeleteTitle { get; set; }
public string DeleteYes { get; set; }
public string DeleteNo { get; set; }
public string DeleteMessage { get; set; }
}
public static class DataTableHelpers
{
private static string aLengthMenu = "[[25, 50, 100, 150, 200], [25, 50, 100, 150, 200]]";
public static MvcHtmlString DataTable(this HtmlHelper helper, DataTableOptions options)
{
string[] arrcols = options.Cols.Split(',');
int sortOffset = arrcols.Where(x => x == "Delete" || x == "View" || x == "Edit").Count();
StringBuilder sb = new StringBuilder();
sb.AppendLine("<script type=\"text/javascript\" charset=\"utf-8\">");
sb.AppendLine("$(function() {");
sb.AppendLine("$('#" + options.ID + "').dataTable({");
sb.AppendLine("\"bSort\" : " + options.Sort.ToString().ToLower() + ",");
sb.AppendLine("\"oLanguage\": { \"sUrl\": \"" + oLanguage + "\" },");
sb.AppendLine("\"bServerSide\": true,");
sb.AppendLine("\"sAjaxSource\": \"" + options.Url + "\",");
sb.AppendLine("\"bProcessing\": true,");
sb.AppendLine("\"sPaginationType\": \"full_numbers\",");
sb.AppendLine("\"iDisplayLength\": 25,");
sb.AppendLine("\"aLengthMenu\": " + aLengthMenu + ",");
sb.AppendLine("\"aaSorting\": [[" + sortOffset.ToString() + ",'asc']],");
sb.AppendLine("\"aoColumns\": [");
for (int i = 0; i < arrcols.Length; i++)
{
if (i > 0)
sb.Append(",");
switch (arrcols[i])
{
case "Delete":
sb.AppendLine("{");
sb.AppendLine("\"sName\": \"" + arrcols[i] + "\",");
sb.AppendLine("\"bSearchable\": false,");
sb.AppendLine("\"bSortable\": false,");
sb.AppendLine("\"fnRender\": function (oObj) {");
sb.Append("return '");
sb.Append("<a class=\"deletelink\" href=\"' + oObj.aData["+ i.ToString() + "] + '\">" + options.DeleteLinkname + "</a> ");
sb.Append("';");
sb.AppendLine("}");
sb.AppendLine("}");
break;
case "Edit":
sb.AppendLine("{");
sb.AppendLine("\"sName\": \"" + arrcols[i] + "\",");
sb.AppendLine("\"bSearchable\": false,");
sb.AppendLine("\"bSortable\": false,");
sb.AppendLine("\"fnRender\": function (oObj) {");
sb.Append("return '");
sb.Append("<a class=\"editlink\" href=\"' + oObj.aData["+ i.ToString() + "] +'\">" + options.EditUrlLinkname + "</a> ");
sb.Append("';");
sb.AppendLine("}");
sb.AppendLine("}");
break;
case "View":
sb.AppendLine("{");
sb.AppendLine("\"sName\": \"" + arrcols[i] + "\",");
sb.AppendLine("\"bSearchable\": false,");
sb.AppendLine("\"bSortable\": false,");
sb.AppendLine("\"fnRender\": function (oObj) {");
sb.Append("return '");
sb.Append("<a class=\"viewlink\" href=\"' + oObj.aData["+ i.ToString() + "] + '\">" + options.ViewUrlLinkname + "</a> ");
sb.Append("';");
sb.AppendLine("}");
sb.AppendLine("}");
break;
default:
sb.AppendLine("{ \"sName\": \"" + arrcols[i] + "\" }");
break;
}
}
sb.AppendLine("]");
sb.AppendLine("});");
sb.AppendLine("});");
sb.AppendLine("</script>");
if (options.DeleteLinkname != null)
{
sb.Append(ConfirmHelpers.RenderConfirm(options.DeleteTitle, options.DeleteYes, options.DeleteNo, options.DeleteMessage));
}
return MvcHtmlString.Create(sb.ToString());
}
,並在控制器通過鏈接,以及:
return Json(new
{
sEcho = param.sEcho,
iTotalRecords = qry.TotalCount,
iTotalDisplayRecords = qry.TotalCount,
aaData = (
from n in qry
select new[]
{
Url.Action("Detail", new { newsID = n.NewsID, headline = n.Headline.ToURLParameter() }),
Url.Action("Edit", new { newsID = n.NewsID, headline = n.Headline.ToURLParameter() }),
Url.Action("Delete", new { newsID = n.NewsID }),
n.Headline,
n.DateCreated.ToString()
}).ToArray()
}, JsonRequestBehavior.AllowGet);
然後
@Html.DataTable(Model.DataTableOptions)
<table id="news" class="default-table" cellpadding="0" cellspacing="0">
<thead>
<tr>
<th style="width: 20px">
</th>
<th style="width: 50px">
</th>
<th style="width: 40px"></th>
<th>
Headline
</th>....
對於刪除我用插件:http://tutorialzine.com/2010/12/better-confirm-box-jquery-css3/
public static string RenderConfirm(string title, string yes, string no, string deleteMessage)
{
StringBuilder sb = new StringBuilder();
sb.AppendLine("<script type=\"text/javascript\" charset=\"utf-8\">");
sb.AppendLine("$(function() {");
sb.AppendLine("$('.deletelink').live('click', function (e) {");
sb.AppendLine("e.preventDefault();");
sb.AppendLine("var elem = $(this);");
sb.AppendLine("$.confirm({");
sb.AppendLine("'title': '" + title + "',");
//sb.AppendLine("'message': $(this).attr('data-delete-message'),");
sb.AppendLine("'message': '" + deleteMessage + "',");
sb.AppendLine("'buttons': {");
sb.AppendLine("'" + yes + "': {");
sb.AppendLine("'class': 'confirm-yes',");
sb.AppendLine("'action': function() {");
sb.AppendLine("$.post($(elem).attr('href'));");
sb.AppendLine("}");
sb.AppendLine("},");
sb.AppendLine("'" + no + "': {");
sb.AppendLine("'class': 'confirm-no',");
sb.AppendLine("'action': function() { } // Nothing to do in this case. You can as well omit the action property.");
sb.AppendLine("}");
sb.AppendLine("}");
sb.AppendLine("});");
sb.AppendLine("});");
sb.AppendLine("});");
sb.AppendLine("</script>");
return sb.ToString();
}
其很好。我有這個。我想要的是在控制器中生成的aoColumns屬性,所以我只發送用戶可以看到的列的數據。有些用戶看不到Headline列和Headline列的數據,所以我不發送這些數據,但由於aColumns屬性,jquery需要兩列(不僅僅是創建列) – InfoLearner 2011-12-27 11:34:36
您可以爲此編寫一個html-helper,逗號分隔值(或類似),併爲您生成腳本。 @ Html.DataTable(...) – 2011-12-27 12:58:15
對不起,我不明白。你的意思是「aColumns」:@ Html.GetColumnsForUser(「UserRole」)?我不知道我是否清楚。我想隱藏一列。所以如果一列包含編輯超鏈接,並且用戶不是管理員,那麼我想隱藏所有行的此列。如果用戶是管理員,那麼我想隱藏編輯,當他創建的行由他 – InfoLearner 2011-12-27 13:03:43
如果這是一個安全問題,我不會推動一切,並在客戶端解析它,因爲這意味着沒有任何安全性。您不顯示某些列的事實並不意味着未經授權的用戶無法使用這些數據。開發人員可以通過任何瀏覽器(Firebug)或代理輕鬆訪問它。
您需要確保用戶只能得到他們需要的數據。如果您擁有不同權限/訪問級別的用戶,則需要實施RBAC - 基於角色的訪問控制方法。然後,根據特定用戶所屬的角色,向他提供他有資格獲得的數據&。從這裏你可以走很多路徑來達到你的目標。快速和骯髒的方法是創建一個動態的LINQ查詢來選擇只有特定用戶需要的列和角色變量上的簡單開關/案例結構來構建正確的查詢。 更復雜的需要爲每個角色創建列名稱集合,併爲通用LINQ結果過濾邏輯。它會更靈活,並且可以輕鬆添加/刪除列,而無需更改邏輯。
這些是一些高層次的建議/想法,因爲您沒有提供關於應用程序的什麼代碼或背景以及爲什麼它需要這樣工作。但是,如果您正在討論隱藏數據的安全原因,請不要將其以純文本格式發送到客戶端瀏覽器。最終有人會發現你正在發送完整的集合,並且它只能被渲染。將javascript用於安全性從來都不是好主意,因爲ist全部在客戶端,並且可以在運行時進行修改。
簡單的答案是一切分配到一個大的JSON對象,然後在客戶端解析它。該JSON理想情況下應該有至少列名和數據 – naveen 2011-12-27 02:31:29
我試過了,但沒有運氣。你的意思是我必須在c#結果JSON中添加columdef或acolum屬性,以便查看? – InfoLearner 2011-12-27 02:37:13
請顯示您嘗試過的以及您目前如何綁定的內容。 – naveen 2011-12-27 02:39:00