How to Save a menu items (text) into dynamic Session states - c#

Okay , below is the code for populating menu items dynamically from a database table.
now what i want to do is to save the "PageHeader" from the database into sessions states so that i can use those session values to check the authorization of a user on Page-load of different content pages.
now since every user have different no. of authorized pages so the no. of sessions will vary from user to user. the values of those sessions will be matched with a PageHeader variable on the Page-Load of content pages.
can someone help me how to go about it.
also i want to change the style of the menu-bar which is otherwise
default and very simple.
private void GetMenu()
{
DataTable dt = new DataTable();
dt = bll.master_Menu_Bar(en);
DataRow[] drow = dt.Select();
foreach (DataRow dr in drow)
{
MenuBar.Items.Add(new MenuItem(dr["PageHeader"].ToString(), dr["PageId"].ToString(), "", dr["PageUrl"].ToString()));
}
business logic layer method used in above code is:
public DataTable master_Menu_Bar(EntityLayer.Entity en)
{
return dll.ReturnSingleTable("Select PageHeader,PageUrl from authorized_view where Emp_Mobile="+ en.cal_EmpMobile);
}

you can make a list of string and put your menu items in there, then put that string list in session
later retrieve from the session only.
foreach (DataRow dr in drow)
{
//add items to list here
}
//make menu from that list
//put that in session or view state
Updated
How to make it store Page Id, Page Url, and Page headers
First we declare a class
public Class MenuHelper
{
public String PageId {get; set;}
public String PageHeader {get; set;}
public String PageUrl {get; set;}
}
The how we do it
List menulist = new List();
DataTable dt = new DataTable();
dt = bll.master_Menu_Bar(en);
DataRow[] drow = dt.Select();
foreach (DataRow dr in drow)
{
MenuHelper helperItem = new MenuHelper();
helperItem.PageId = dr["PageId"].ToString();
helperItem.PageHeader = dr["PageHeader"].ToString();
helperItem.PageUrl = dr["PageUrl"].ToString();
//can add menu here or not
MenuBar.Items.Add(new MenuItem(dr["PageHeader"].ToString(), dr["PageId"].ToString(), "", dr["PageUrl"].ToString()));
//Add items to list
menulist.Add(helperItem);
}
//Add list to session or view state
Session["MenuItems"] = menulist;
//When retrieving list do like this
List<MenuHelper> menulist = (List<MenuHelper>)Session["MenuItems"];

here is my simple code which does the thing ..
private void GetMenu()
{
//fetches data from business logic layer
DataTable dt1 = new DataTable();
dt1 = bll.Master_Menu_Bar(en);
//session so that the masterpage doesnt interact with database on everypostback
Session["dataTable"] = dt1;
DataTable dt=new DataTable();
dt=(DataTable)Session["dataTable"];
//session for page id's of the menuitems which will be checked for authorization at page loads of every page.
int i = 0;
while (i < dt.Rows.Count)
{
int[] PageId = new int[dt.Rows.Count];
PageId[i] = Convert.ToInt32(dt.Rows[i][2]);
Session["PageId" + i] = PageId[i];
i++;
}
//A session to keep count of the no. of menu items , this session is also used at page loads of pages as condition of if statement
Session["count"] = dt.Rows.Count;
DataRow[] drow = dt.Select();
foreach (DataRow dr in drow)
{
MenuBar.Items.Add(new MenuItem(dr["PageHeader"].ToString(), dr["PageId"].ToString(), "", dr["PageUrl"].ToString()));
}

Related

I have two datagridview, one on the staff calls, I want to make the other contain the number of staff did the call

The following images show my two datagrid views
From what I understand from your question, you can use the following method
public DataTable numOfCalls(DataTable table)
{
//Initialize Result Table
DataTable numOfCallsTable = new DataTable();
numOfCallsTable.Columns.Add("agentName", typeof(string));
numOfCallsTable.Columns.Add("numOfCall", typeof(int));
// Get the unique agents
DataView view = new DataView(table);
DataTable distinctValues = view.ToTable(true, "agentName");
// Check if there are agents
if (distinctValues.Rows.Count > 0)
{
// Loop thru the agents
for (int i = 0; i < distinctValues.Rows.Count; i++)
{
string agentName = distinctValues.Rows[i]["agentName"].ToString();
// Get all the rows that this agent has
DataRow[] agentRows = table.Select($"agentName='{agentName}'");
// And then fill the second table
DataRow newRow = numOfCallsTable.NewRow();
newRow["agentName"] = agentName;
newRow["numOfCall"] = agentRows.Length;
numOfCallsTable.Rows.Add(newRow);
}
}
return numOfCallsTable;
}
You can call this method every time you add or delete a line to the first table.
update for the button that you asked
private void Button1_Click(object sender, EventArgs e)
{
DataTable dt = new DataTable();
dt = (DataTable)dataGridView1.DataSource;
dataGridView2.DataSource = numOfCalls(dt);
}

How to dynamically delete rows in DataList c# asp

Looking for a way to dynamically delete rows from a datalist, providing a user a way to 'clean up' their input interface. The asp datalist gets loaded from SQL, then the user gets to manipulate the table before sending it on to another database.
I have a functioning 'addRows' by using a datatable session variable, adding rows to it then re-binding to the datalist, however I can't seem to get the same function with deleting rows.
Current logic is to use datalist 'delRows' command, get current typed-in or modified data from the asp datalist, assign it to a datatable, loop thru datatable and delete rows where certain fields are empty, then re-bind datatable to asp datalist.
Current code workup, but cannot get dt filled, error "dt = null" :
if (e.CommandName == "delRows")
{
DataList DataList1 = (DataList)FindControl("DataList1"); //find datalist in current state
Session["dataList1"] = DataList1; //assign datalist to session variable
DataTable dt = Session["dataList1"] as DataTable; //populate datatable with datalist session
for (int i = dt.Rows.Count - 1; i >= 0; i--)
{
DataRow dr = dt.Rows[i];
string check = dr["item_no"].ToString();
if (check == String.Empty)
{
dr.Delete();
}
}
DataList1.DataSource = dt;
DataList1.DataBind();
}
Hopefully there is a better way to accomplish this! Not to mention working....
For any future info seekers: Had to loop thru table to get most current textbox text into dt, then modify dt datatable in code behind, then rebind dt to datalist.
protected void doDataTable(string command, int e)
{
DataTable dt = new DataTable();
dt.Columns.Add("no", typeof(string));
dt.Columns.Add("desc", typeof(string));
dt.Columns.Add("code", typeof(string));
dt.Columns.Add("measure", typeof(string));
dt.Columns.Add("qty", typeof(int));
dt.Columns.Add("price", typeof(double));
foreach (DataListItem item in DataList4.Items)
{
string no = ((TextBox)item.FindControl("no")).Text;
string desc = ((TextBox)item.FindControl("desc")).Text;
string code = ((TextBox)item.FindControl("code")).Text;
string measure = ((TextBox)item.FindControl("measure")).Text;
int qty = Convert.ToInt16(((TextBox)item.FindControl("qty")).Text);
double price = Convert.ToDouble(((TextBox)item.FindControl("price")).Text.TrimStart('$'));
dt.Rows.Add(no, desc, code, measure, qty, price);
}
if (command == "add")
{
DataRow dr = dt.NewRow();
dt.Rows.Add(dr);
DataList4.DataSource = dt;
DataList4.DataBind();
}
else if (command == "del")
{
dt.Rows[e].Delete();
DataList4.DataSource = dt;
DataList4.DataBind();
}
}
Called with:
protected void DataList1_ItemCommand(object source, DataListCommandEventArgs e)
{
if (e.CommandName == "addRow")
{
doDataTable("add", e.Item.ItemIndex);
}
if (e.CommandName == "delRows")
{
doDataTable("del", e.Item.ItemIndex);
}
}

Deleting a row from a datatable in C#

I am searching a PDF file for a keyword and returning the pages on which that keyword was found. If the keyword IS FOUND, I'm returning a list of pages and the fileName. However, if the keyword was NOT FOUND in the PDF file, I want to deleted the row in the datatable.
public DataTable dtPubSearchResultsFromFiles(string sqlQuery, string safeKeyword)
{
// Returns a datatable of publication search results based on PDF files.
SqlConnection con = new SqlConnection(getConnectionString());
SqlCommand cmd = new SqlCommand(sqlQuery, con);
SqlDataAdapter da = new SqlDataAdapter(cmd);
DataTable dt = new DataTable();
dt.Columns.Add("Pages", typeof(string));
da.Fill(dt);
dt.PrimaryKey = new DataColumn[] { dt.Columns["publicationID"] };
foreach (DataRow row in dt.Rows)
{
//call search function to look for keyword
List<int> myPages = new List<int>();
string fileName = row["linkToPublicationPDF"].ToString();
myPages = ReadPdfFile(fileName, safeKeyword);
if (myPages.Count > 0)
{
string pagelist = "";
foreach (int page in myPages)
{
pagelist = pagelist + page + " ";
}
row["Pages"] = pagelist;
}
else
{
//remove/delete the row from the datatable if "myPages.Count" is 0
dt.Rows.Remove(row);
}
}
return dt;
}
When I add this ("dt.Rows.Remove(row)"), I get this error when the page is called "System.InvalidOperationException: Collection was modified; enumeration operation might not execute."
Suggestions? Comments? Fixes? All are welcome...
Bob
Your code is getting some data from the database such that your program can work with it.
The exception you're getting is because your you're modifying (by removing an element) the collection you're iterating on and that's not possible.
You can solve this by creating a temporary List where you store the rows you want to delete. Once you're done with the iteration you can iterate on the temporary list and remove what you decided you don't want anymore.
var toRemove = new List<DataRow>();
foreach (DataRow row in dt.Rows)
{
//call search function to look for keyword
List<int> myPages = new List<int>();
string fileName = row["linkToPublicationPDF"].ToString();
myPages = ReadPdfFile(fileName, safeKeyword);
if (myPages.Count > 0)
{
string pagelist = "";
foreach (int page in myPages)
{
pagelist = pagelist + page + " ";
}
row["Pages"] = pagelist;
}
else
{
//remove/delete the row from the datatable if "myPages.Count" is 0
toRemove.Add(row);
}
}
}
foreach (DataRow row toRemove.Add)
{
dt.Rows.Remove(row);
}
try a simple Delete
row.Delete();
then after the loop
dt.AcceptChanges();
but it will probably fail
see answer from mario
it may work if it is really only marking the row for deletion

Duplicate user are not allowing in gridview in ASP.NET C#

I have many checkbox lists for searching, but when I will search by any of the checkbox list search if any record will be two times in table means will not fill into gridview.
This line of code is not allowed duplicate values, if duplicate means allow single record.
if (newdt.TableName == dt.TableName) {
// see if filter is already present in the dataset
tableMatchFound = true;
// when the current filter is already present in the dataset
foreach (DataRow dr in dt.Rows)
ds.Tables[newdt.TableName].ImportRow(dr);
}
// importrow() adds distinct new subfilters to the existing filter, duplicate items are not added
if (!tableMatchFound)
ds.Tables.Add(dt);
Below is my full .cs code.
private DataTable list(String dbObject, String filterName, String filterValue,string PositonId,string Status) {
NameValuePairList objNameValuePairList = new NameValuePairList();
objNameValuePairList.Add(new NameValuePair("#FilterValue", filterValue, PositonId, Status));
objNameValuePairList.Add(new NameValuePair("#Action", "FilterBy" + filterName, PositonId, Status));
DataTable dt = dl.Search_RegisterationInfo(dbObject, objNameValuePairList, PositonId, Status);
return dt;
}
public DataTable list(String dbOject, FilterList myFilterList,string PositonId,string Status) {
// gets a collection(dataset) of all unique filters(datatables) and also group all subfilters(rows) under each filter
DataTable dt;
DataSet ds = new DataSet();
// a filter may be a Nationality or a Qualification
foreach (Filter item in myFilterList)
// a subfilter may be Indian or Expatriate under the filter Nationality
{
// another subfilter may be Bachelor degree or Master Degree under the filter Qualification
dt = list(dbOject, item.getFilterName, item.getFilterValue, PositonId,Status);
dt.TableName = item.getFilterName;
// datatables are named based on the filters
if (ds.Tables.Count == 0)
// so we get a collection of unique filters (datatables) in the dataset
ds.Tables.Add(dt);
// add new filter without checking, since for the first time, no conflicts are possible
else
{
bool tableMatchFound = false;
foreach (DataTable newdt in ds.Tables)
if (newdt.TableName == dt.TableName)
{
// see if filter is already present in the dataset
tableMatchFound = true;
// when the current filter is already present in the dataset
foreach (DataRow dr in dt.Rows)
ds.Tables[newdt.TableName].ImportRow(dr);
}
// importrow() adds distinct new subfilters to the existing filter, duplicate items are not added
if (!tableMatchFound)
ds.Tables.Add(dt);
}
// if the filter does not exist, add the new filter to the collection
}
// the entire collection of filters will contain duplicate items
// distinct items from the entire collection is filtered out in the next section
dt = ds.Tables[0].Clone();
// get the structure of the first filter as they all apply to the same table object
if (ds.Tables.Count == 1)
dt = ds.Tables[0];
// if there is only one filter, no filtering is required
else
// if there are more than one, compare each subfilter of every other filter with the subfilters of the first filter
foreach (DataRow dr in ds.Tables[0].Rows)
{
// each subfilter from the first filter is used as a pivot
int rowMatchFound = 1;
for (int i = 1; i < ds.Tables.Count; i++)
// search all filters except the first one
foreach (DataRow newdr in ds.Tables[i].Rows)
// select each subfilter from all the filter
if ((int)dr["RegistrationId"] == (int)newdr["RegistrationId"])
rowMatchFound++;
if (rowMatchFound == ds.Tables.Count)
// a match is found exactly once in all the filters
dt.ImportRow(dr);
// the final item is selected so that is is present in all the filters
}
return dt;
}
Please follow the link for more details of my question.
https://forums.asp.net/t/2078301.aspx?Duplicate+items+are+not+added+using+ASP+NET+C+

MenuControl in asp.net from database

I have a menu control in my Master page.T he name of the menu and corresponding url is coming from the database. If a menu has a sub menu it is also showing properly.
But the problem arises if a sub menu has a child menu.
My database table has 4 columns
MenuId || MenuName || ParentId || URL.
and the code is
private void getMenu()
{
DataSet ds = new DataSet();
DataTable dt = new DataTable();
ds = objSec.ShowMenu(s_UserId);
dt = ds.Tables[0];
DataRow[] drowpar = dt.Select("ParentID=" + 0);
foreach (DataRow dr in drowpar)
{
menuBar.Items.Add(new MenuItem(dr["MenuName"].ToString(), dr["MenuID"].ToString(),
"", dr["URL"].ToString()));
}
foreach (DataRow dr in dt.Select("ParentID >" + 0))
{
try
{
MenuItem mnu = new MenuItem(dr["MenuName"].ToString(), dr["MenuID"].ToString(),
"", dr["URL"].ToString());
menuBar.FindItem(dr["ParentID"].ToString()).ChildItems.Add(mnu);
}
catch (Exception ex)
{
}
}
}
The approach in your sample might lead to incorrect results if sub-items are contained in the table before their parent-item. In addition, the empty catch-block might hide any errors. Therefore, I'd recommend another approach.
Instead of looping the table, you can also use recursion to fill the control. This removes the amount of duplicated code:
private void getMenu()
{
DataSet ds = objSec.ShowMenu(s_UserId);
DataTable dt = ds.Tables[0];
AddMenuItems(dt, 0, menu.Items);
}
private void AddMenuItems(DataTable dt, int parentId, MenuItemCollection items)
{
DataRow[] rows = dt.Select("ParentID=" + parentId.ToString());
foreach(var dr in rows)
{
var id = (int) dr["MenuID"];
var menuItem = new MenuItem(dr["MenuName"].ToString(), id.ToString(),
"", dr["URL"].ToString());
items.Add(menuItem);
// Add subitems
AddMenuItems(dt, id, menuItem.ChildItems);
}
}
The sample first calls the AddMenuItems method for the top-level items (ParentID = 0). After each item is added, its children are added by calling the AddMenuItems method again (hence the term "recursive"), providing the id of the top-level item as parent. For each 2nd level child, the method is called again and so on.

Categories