Execute stored procedure in Entity Framework, return List<DataTable> or DataSet - entity-framework

How do I modify the below method to return a List< DataTable> or a DataSet? I want to make it generic so it can return multiple resultsets from the database.
public static DataTable ExecuteStoredProcedure(ObjectContext db, string storedProcedureName, IEnumerable<SqlParameter> parameters)
{
var entityConnection = (EntityConnection) db.Connection;
var conn = entityConnection.StoreConnection;
var initialState = conn.State;
var dt = new DataTable();
try
{
if (initialState != ConnectionState.Open)
conn.Open();
using (var cmd = conn.CreateCommand())
{
cmd.CommandText = storedProcedureName;
cmd.CommandType = CommandType.StoredProcedure;
foreach (var parameter in parameters)
{
cmd.Parameters.Add(parameter);
}
using (var reader = cmd.ExecuteReader())
{
dt.Load(reader);
reader.Close();
}
}
}
catch (Exception ex)
{
throw ex;
}
finally
{
if (initialState != ConnectionState.Open)
conn.Close();
}
return dt;
}

I ended up doing it like this -
public static DataSet ExecuteStoredProcedure(ObjectContext db, string storedProcedureName, IEnumerable<SqlParameter> parameters)
{
var connectionString = ((EntityConnection)db.Connection).StoreConnection.ConnectionString;
var ds = new DataSet();
using (var conn = new SqlConnection(connectionString))
{
using (var cmd = conn.CreateCommand())
{
cmd.CommandText = storedProcedureName;
cmd.CommandType = CommandType.StoredProcedure;
foreach (var parameter in parameters)
{
cmd.Parameters.Add(parameter);
}
using (var adapter = new SqlDataAdapter(cmd))
{
adapter.Fill(ds);
}
}
}
return ds;
}

reader.NextResult() should technically work. Here is the modified version:
public static DataSet ExecuteStoredProcedure(ObjectContext db, string storedProcedureName, IEnumerable<SqlParameter> parameters)
{
var entityConnection = (EntityConnection) db.Connection;
var conn = entityConnection.StoreConnection;
var initialState = conn.State;
DataSet dataSet = new DataSet();
try
{
if (initialState != ConnectionState.Open)
conn.Open();
using (var cmd = conn.CreateCommand())
{
cmd.CommandText = storedProcedureName;
cmd.CommandType = CommandType.StoredProcedure;
foreach (var parameter in parameters)
{
cmd.Parameters.Add(parameter);
}
using (var reader = cmd.ExecuteReader())
{
do
{
DataTable dt = new DataTable();
dt.Load(reader);
dataSet.Tables.Add(dt);
}
while (reader.NextResult());
}
}
}
catch (Exception ex)
{
throw ex;
}
finally
{
if (initialState != ConnectionState.Open)
conn.Close();
}
return dataSet;
}

Related

How to Repeat Previous Actions in Exception in EF 6

I am having a problem with repeating previous operations when there is an error in the SaveChanges method of Entity Framework.
Below is the code block
public static int SaveChangesTask(this DbContext db)
{
int result = -1;int countLoop = 0;
bool continueLoop = true;
var modifiedOrAddedEntities = db.ChangeTracker.Entries().Where(a => a.State != EntityState.Detached
&& a.State != EntityState.Unchanged).ToList();
while (continueLoop && countLoop<3)
{
try
{
result= db.SaveChanges();
continueLoop = false;
}
catch(Exception ex)
{
string error = ex.ToSystemException();
if(error.ToLowerInvariant().Contains("ORA-00060".ToLowerInvariant()) || error.ToLowerInvariant().Contains("deadlock"))
{
foreach (var item in modifiedOrAddedEntities)
{
db.Entry(item).State = item.State;
}
countLoop++;
Random rnd = new Random();
System.Threading.Thread.Sleep(rnd.Next(1, 5)* 1000);
}
else
{
throw ex;
}
}
}
return result;
}
But when I want to add old tracking objects to context, Entity Framework Throws Exception like that
"The entity type DbEntityEntry is not part of the model for the current context"

how to store dbcontext.emps.ToList() data in a data table

how to store the dbcontext.emp.tolist(); data in datatable to perform sorting using entity frame database first approach and linq .
here i am uploading my code.
please help.
how to perform soting operation for grid using entity frame work and linq.
using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Web.UI;
using System.Web.UI.WebControls;
using System.Data;
namespace sortingby_crud
{
public partial class WebForm2 : System.Web.UI.Page
{
protected void Page_Load(object sender, EventArgs e)
{
if (!this.IsPostBack)
{
//this.BindGrid();
GridView1.DataSource = BindGrid();
GridView1.DataBind();
}
}
private DataTable BindGrid()
{
using (dbEntities db = new dbEntities())
{
//GridView1.DataSource = db.emps.ToList();
//GridView1.DataBind();
DataTable dt = new DataTable();
dt= db.emps.ToList();
return dt;
}
}
public SortDirection dir
{
get
{
if (ViewState["dirState"] == null)
{
ViewState["dirState"] = SortDirection.Ascending;
}
return (SortDirection)ViewState["dirState"];
}
set
{
ViewState["dirState"] = value;
}
}
protected void GridView1_Sorting(object sender, GridViewSortEventArgs e)
{
string sortingDirection = string.Empty;
if (dir == SortDirection.Ascending)
{
dir = SortDirection.Descending;
sortingDirection = "Desc";
}
else
{
dir = SortDirection.Ascending;
sortingDirection = "Asc";
}
DataView sortedView = new DataView(BindGrid());
sortedView.Sort = e.SortExpression + " " + sortingDirection;
GridView1.DataSource = sortedView;
GridView1.DataBind();
}
}
}
public DataTable data() // or keep return type is also
as void .
/convert db.context in data table.
{
DataTable table = new DataTable();
var list = db.SupplierAssignmentones.ToList();
//Defining the header for the datatable.
table.Columns.Add("VendorId", typeof(int));
table.Columns.Add("VendorName", typeof(string));
table.Columns.Add("VendorDescription", typeof(string));
table.Columns.Add("SupHie1_CD", typeof(string));
table.Columns.Add("SupHie2_CD", typeof(string));
table.Columns.Add("SupHie3_CD", typeof(string));
table.Columns.Add("Is_Active", typeof(string));
//assigning the data for data table rows.
foreach (var data in list)
{
table.Rows.Add(data.VendorId, data.VendorName, data.VendorDescription, data.SupHie1_CD, data.SupHie2_CD, data.SupHie3_CD, data.Is_Active);
}
return table;
}

SharePoint Backup Tool for Custom Lists

I have a SharePoint 2013 document library with three custom lists.
Once a day I would like to backup the custom lists as excel documents.
Is there an inbuilt functionality in SharePoint 2013 which can be configured as a recurring task?
Or should one use PowerShell or CSOM to write script or an application which is then run by a Windows Task?
you dont have any OOB features to do this, i had the same req and i wrote an Utility - PFB the code - this will give you an o/p in .csv file
class Program
{
private static DataTable dataTable;
private static SPList list;
static void Main(string[] args)
{
try
{
Console.WriteLine("Site Url: ");
string _siteUrl = Console.ReadLine();
if (!string.IsNullOrEmpty(_siteUrl))
{
SPSecurity.RunWithElevatedPrivileges(delegate()
{
using (SPSite site = new SPSite(_siteUrl))
{
if (site != null)
{
SPWeb web = site.RootWeb;
if (web != null)
{
// Export List code segment
Console.WriteLine("List Name:");
string _listName = Console.ReadLine();
if (!string.IsNullOrEmpty(_listName))
{
list = web.Lists[_listName];
if (list != null)
{
dataTable = new DataTable();
//Adds Columns to SpreadSheet
InitializeExcel(list, dataTable);
string _schemaXML = list.DefaultView.ViewFields.SchemaXml;
if (list.Items != null && list.ItemCount > 0)
{
foreach (SPListItem _item in list.Items)
{
DataRow dr = dataTable.NewRow();
foreach (DataColumn _column in dataTable.Columns)
{
if (dataTable.Columns[_column.ColumnName] != null && _item[_column.ColumnName] != null)
{
dr[_column.ColumnName] = _item[_column.ColumnName].ToString();
}
}
dataTable.Rows.Add(dr);
}
}
}
}
System.Web.UI.WebControls.DataGrid grid = new System.Web.UI.WebControls.DataGrid();
grid.HeaderStyle.Font.Bold = true;
grid.DataSource = dataTable;
grid.DataBind();
using (StreamWriter streamWriter = new StreamWriter("C:\\" + list.Title + ".xls", false, Encoding.UTF8))
{
using (HtmlTextWriter htmlTextWriter = new HtmlTextWriter(streamWriter))
{
grid.RenderControl(htmlTextWriter);
}
}
Console.WriteLine("File Created");
#endregion
}
}
}
});
}
}
catch (Exception ex)
{
Console.WriteLine("Error: " + ex.Message);
}
Console.ReadLine();
}
// Create excel funution
public static void InitializeExcel(SPList list, DataTable _datatable)
{
if (list != null)
{
string _schemaXML = list.DefaultView.ViewFields.SchemaXml;
if (list.Items != null && list.ItemCount > 0)
{
foreach (SPListItem _item in list.Items)
{
foreach (SPField _itemField in _item.Fields)
{
if (_schemaXML.Contains(_itemField.InternalName))
{
if (_item[_itemField.InternalName] != null)
{
if (!_datatable.Columns.Contains(_itemField.InternalName))
{
_datatable.Columns.Add(new DataColumn(_itemField.StaticName, Type.GetType("System.String")));
}
}
}
}
}
}
}
}
}

DataTable already belongs to this DataSet Error working with dataset

i have dataset that fills data from three tables. here i just want to populate data of menu bar from database.
private DataSet GetData()
{
using (DataClassesDataContext db = new DataClassesDataContext())
{
var query = from m in db.Menus
where (m.IsActive == true)
select new
{
MenuID = m.MenuID,
MenuName = m.MenuName,
MenuLocation = m.MenuLocation
};
DataSet myDataSet = new DataSet();
DataTable dt = new DataTable();
dt.Columns.Add(new DataColumn("MenuID", typeof(int)));
dt.Columns.Add(new DataColumn("MenuName", typeof(string)));
dt.Columns.Add(new DataColumn("MenuLocation", typeof(string)));
foreach (var item in query)
{
if (item != null)
{
DataRow dr = dt.NewRow();
dr["MenuID"] = item.MenuID.ToString();
dr["MenuName"] = item.MenuName.ToString();
if (item.MenuLocation != null)
{
dr["MenuLocation"] = item.MenuLocation.ToString();
}
dt.Rows.Add(dr);
}
}
myDataSet.Tables.Add(dt);
var query1 = from c in db.CategoryMenus
where (c.IsActive == true)
select new
{
CategoryID = c.CategoryMenuID,
CategoryMenuName = c.CategoryMenuName,
CategoryMenuLocation = c.CategoryMenuLocation
};
dt.Columns.Add(new DataColumn("CategoryID", typeof(int)));
dt.Columns.Add(new DataColumn("CategoryMenuName", typeof(string)));
dt.Columns.Add(new DataColumn("CategoryMenuLocation", typeof(string)));
foreach (var item in query1)
{
if (item != null)
{
DataRow dr = dt.NewRow();
dr["CategoryID"] = item.CategoryID.ToString();
dr["CategoryMenuName"] = item.CategoryMenuName.ToString();
if (item.CategoryMenuLocation != null)
{
dr["CategoryMenuLocation"] = item.CategoryMenuLocation.ToString();
}
dt.Rows.Add(dr);
}
}
//Line 80
myDataSet.Tables.Add(dt);
var query2 = from s in db.SubCategoryMenus
where (s.IsActive == true)
select new
{
SubCategoryID = s.SubCategoryMenuId,
SubCategoryMenuName = s.SubCategoryMenuName,
SubCategoryMenuLocation = s.SubCategoryMenuLocation
};
dt.Columns.Add(new DataColumn("SubCategoryID", typeof(int)));
dt.Columns.Add(new DataColumn("SubCategoryMenuName", typeof(string)));
dt.Columns.Add(new DataColumn("SubCategoryMenuLocation", typeof(string)));
foreach (var item in query2)
{
if (item != null)
{
DataRow dr = dt.NewRow();
dr["SubCategoryID"] = item.SubCategoryID.ToString();
dr["SubCategoryMenuName"] = item.SubCategoryMenuName.ToString();
if (item.SubCategoryMenuLocation != null)
{
dr["SubCategoryMenuLocation"] = item.SubCategoryMenuLocation.ToString();
}
dt.Rows.Add(dr);
}
}
myDataSet.Tables.Add(dt);
return myDataSet;
}
}
from the second query while it iterates and add row to this tables then erro occured like:
Server Error in '/EasyWeb' Application.
DataTable already belongs to this DataSet.
Description: An unhandled exception occurred during the execution of the current web request. Please review the stack trace for more information about the error and where it originated in the code.
Exception Details: System.ArgumentException: DataTable already belongs to this DataSet.
Source Error:
Line 78: }
Line 79: }
Line 80: myDataSet.Tables.Add(dt);
Line 81: var query2 = from s in db.SubCategoryMenus
Line 82: where (s.IsActive == true)
Source File: f:\EasyWeb\MenuControl.ascx.cs Line: 80
Stack Trace:
[ArgumentException: DataTable already belongs to this DataSet.]
System.Data.DataTableCollection.BaseAdd(DataTable table) +4825888
System.Data.DataTableCollection.Add(DataTable table) +112
MenuControl.GetData() in f:\EasyWeb\MenuControl.ascx.cs:80
MenuControl.Page_Load(Object sender, EventArgs e) in f:\EasyWeb\MenuControl.ascx.cs:20
System.Web.Util.CalliHelper.EventArgFunctionCaller(IntPtr fp, Object o, Object t, EventArgs e) +14
System.Web.Util.CalliEventHandlerDelegateProxy.Callback(Object sender, EventArgs e) +35
System.Web.UI.Control.OnLoad(EventArgs e) +99
System.Web.UI.Control.LoadRecursive() +50
System.Web.UI.Control.LoadRecursive() +141
System.Web.UI.Control.LoadRecursive() +141
System.Web.UI.Page.ProcessRequestMain(Boolean includeStagesBeforeAsyncPoint, Boolean includeStagesAfterAsyncPoint) +627
You need to name the tables after getting the copy from your method and before adding it to the DataSet.
Like this
dt.TableName = "A";
myDataSet.Tables.Add(dt);
ok i found just need different tables for that.
like
Datatable dt=new Datatable("Menu");
DataTable dt1 = new DataTable("Category");
DataTable dt2 = new DataTable("SubCategory");

ORA-06550 , wrong number or types of arguments in call to Oracle Stored Procedure

I have a stored procedure which has one in parameter and one out parameter as follows:
create or replace procedure worker_name (w_id in number, w_first out worker.first_name%type) is
Begin
select first_name into w_first
from worker
where worker_id = w_id;
end;
Code to call this stored procedure:
public DataTable <b>GetEmployeeName</b>(int _employeeID)
{
ArrayList arrEmployeeName = new ArrayList();
OracleParameter paramEmployeeId = new OracleParameter(":employeeid", _employeeID);
arrEmployeeName.Add(paramEmployeeId);
DataLayer obj = new DataLayer();
DataTable tblEmployee = obj.<b>GetData</b>("macw_conv.worker_name", arrEmployeeName, "SP");
if (tblEmployee.Rows.Count > 0)
{
return tblEmployee;
}
return null;
}
public DataTable <b>GetData</b>(string query, ArrayList parameters,string queryType)
{
//DataTable dt = new DataTable();
try
{
_con =
new OracleConnection(Oradb);
_con.Open();
_cmd = new OracleCommand(query, _con);
if (_cmd.Connection.State == ConnectionState.Open)
{
if (queryType == "SP" && parameters != null)
{
_cmd.CommandType = CommandType.StoredProcedure;
if (parameters.Count > 0)
{
foreach (OracleParameter param in parameters)
{
_cmd.Parameters.Add(param);
}
}
}
}
DataSet ds = new DataSet();
OracleDataAdapter da = new OracleDataAdapter(_cmd);
da.Fill(ds);
if (ds.Tables.Count > 0)
{
return ds.Tables[0];
}
return null;
}
I guess I'm unable to see the obvious error. It's something about the data type mismatch between the out parameter in the stored procedure and output parameter in the code. Any kind of help is appreciated.
Thanks!
I figured out the issue: it was because the datatype of the variable that is saving the out parameter was not handled properly. I changed the code as follows:
try
{
_con = new OracleConnection(Oradb);
_cmd = _con.CreateCommand();
_cmd.CommandType = CommandType.StoredProcedure;
_cmd.CommandText = "macw_conv.worker_name";
OracleParameter inobj1 = _cmd.Parameters.Add("w_id", OracleDbType.Int32,50);
inobj1.Direction = ParameterDirection.Input;
inobj1.Value = _employeeID;
OracleParameter inobj2 = _cmd.Parameters.Add("w_last", OracleDbType.Int32, 50);
inobj2.Direction = ParameterDirection.Input;
inobj2.Value = String.IsNullOrEmpty(_lastName) ? null : _lastName;
OracleParameter outobj = _cmd.Parameters.Add("w_first", OracleDbType.Varchar2, 50);
outobj.Direction = ParameterDirection.Output;
_con.Open();
_cmd.ExecuteNonQuery();
_employeeName = ((OracleString) _cmd.Parameters[1].Value).ToString();
_cmd.Dispose();
_con.Close();
}
catch (OracleException ex)
{
Console.WriteLine(ex.Message);
}
return _employeeName;
Try
public DataTable GetEmployeeName(int _employeeID)
{
ArrayList arrEmployeeName = new ArrayList();
OracleParameter paramEmployeeId = new OracleParameter("employeeid", _employeeID);
arrEmployeeName.Add(paramEmployeeId);
OracleParameter paramEmployeeFirst = new OracleParameter("first", OracleDbType.Varchar2, ParameterDirection.Output);
arrEmployeeName.Add(paramEmployeeFirst);
DataLayer obj = new DataLayer();
DataTable tblEmployee = obj.GetData("macw_conv.worker_name(:1,:2)", arrEmployeeName, "SP");
if (tblEmployee.Rows.Count > 0)
{
return tblEmployee;
}
return null;
}