EF Code Structure in WinForms - c#

I need some help with my code structure!
I have a form with some mandatory fields and some optionals.
I run some validation prior to saving the records on the database to make sure the data conforms to integrity rules. If its properly validated the data can then be saved. The problem sets with with my optional fields, comboboxes:
private async void SaveRecord()
{
if (ValidateForm())
{
int sucessReg = 0;
try
{
var memberRecord = new ClubMember()
{// Tab ID
Name = txtName.Text,
Surname = txtSurname.Text,
PassportNumber = (Int32)txtPasspt.text,
MaritalStatus = cboMarital.SelectedValue.ToString(),
Gender = cboGender.SelectedValue.ToString(),
DOB = dtpDob.Value,
DataEntrada = dtpDataEntra.Value,
Photo = ConvertImgToBinary(picBoxPhoto.Image),
Country = cboCountry.SelectedValue.ToString(),
};
ctxt.CubMember.Add(memberRecord);
sucessReg = await ctxt.SaveChangesAsync();
if (sucessReg == 1)
{
MessageBox.Show(this, "Record successfully saved.", "System Message");
}
}
catch (TargetInvocationException ex)
{
string err;
err = ex.ToString();
if (ex.InnerException != null)
{
err = ex.InnerException.Message;
}
MessageBox.Show(err);
}
}
}
Since some comboxes are optional and the selectedValue property is null at the moment of saving, the compiler throws the error "Object reference not set to an instance of an object."
The optional fields should go as is, that is, should be null on the database if the user didn't pick any item on the combo list.
So, I need a better way to structure my code in order to address this issue.
Does anybody have a brilliant idea?? :-)
Thanks in advance.

If you are using C#6 you could use ?. null conditional operator to check if ComboBox.SelectedValue is null before you use .ToString():
var memberRecord = new ClubMember()
{// Tab ID
Name = txtName.Text,
Surname = txtSurname.Text,
PassportNumber = (Int32)txtPasspt.text,
MaritalStatus = cboMarital.SelectedValue?.ToString(),
Gender = cboGender.SelectedValue?.ToString(),
DOB = dtpDob.Value,
DataEntrada = dtpDataEntra.Value,
Photo = ConvertImgToBinary(picBoxPhoto.Image),
Country = cboCountry.SelectedValue?.ToString(),
};
It is equivalent to:
var memberRecord = new ClubMember()
{// Tab ID
Name = txtName.Text,
Surname = txtSurname.Text,
PassportNumber = (Int32)txtPasspt.text,
MaritalStatus = cboMarital.SelectedValue == null ? null : cboMarital.SelectedValue.ToString(),
Gender = cboGender.SelectedValue == null ? null : cboGender.SelectedValue.ToString(),
DOB = dtpDob.Value,
DataEntrada = dtpDataEntra.Value,
Photo = ConvertImgToBinary(picBoxPhoto.Image),
Country = cboCountry.SelectedValue == null ? null : cboCountry.SelectedValue.ToString(),
};

Related

C#, .NET, Check for null in function which converts request to string

I have a function which takes a request and converts it to a string:
private string CreateEmailData(Models.V2.RequestPaymentModel data)
{
var emailRequest = new ApiRequest<RequestPaymentEmailModel>
{
Id = id,
DateUtc = DateTime.UtcNow,
Data = new Utils.EmailRequest.RequestPaymentEmailModel
{
LanguageCode = data.LanguageCode,
DeviceID = data.DeviceId,
CoreSystem = data.CoreSystem,
Transaction = new Utils.EmailRequest.TransactionEmail()
{
Country = data.CountryCode,
TransactionType = data.Transaction.Type,
Amount = data.Transaction.Amount,
Currency = data.Transaction.Currency,
Authorization = "",
Type = data.Transaction.Type,
Description = data.Transaction.Description,
PaymentNetwork = data.PaymentNetwork,
ReferenceId = data.Transaction.ReferenceID,
CartValue = data.Transaction.CartValue,
PaymentFrequency = data.Transaction.PaymentFrequency,
InvoiceNumber = data.Transaction.InvoiceNumber,
GoodsType = data.Transaction.GoodsType,
ProductID = data.Transaction.ProductId
},
CreditCard = new Utils.EmailRequest.EmailCreditCard()
{
Number = data.DataPaymentMethod.CreditCard.Number,
Month = data.DataPaymentMethod.CreditCard.Month,
Year = data.DataPaymentMethod.CreditCard.Year,
FirstName = data.DataPaymentMethod.CreditCard.FirstName,
LastName = data.DataPaymentMethod.CreditCard.LastName
},
PaymentMethod = data.PaymentMethod,
DataSecurity = data.DataSecurity,
ExtraParameter = data.DataPaymentMethod.ExtraParameter,
Buyer = data.DataPaymentMethod.Buyer,
Payer = data.DataPaymentMethod.Payer,
}
}.ToJson();
return emailRequest;
}
But sometimes some values in a request like Payer can be null.
How can I check values for null in this function?
Right now if value null it crashes the app and returns:
$exception {"Object reference not set to an instance of an
object."} System.NullReferenceException
You'll need to include null checks. Your problem isn't that it can't be converted into a string. It's that you're referencing null objects. What you need to do is replace your code where lines that look like this
Payer = data.DataPaymentMethod.Payer
are re-written to look like this
Payer = data?.DataPaymentMethod?.Payer
This way if "data" is null then then Payer is null. If data.DataPaymentMethod is null then Payer is null. Finally if data.DataPaymentMethod.Payer is null then Payer is null. If your version of C# supports this syntax then this is what I would go with. Else you'll either need to write an ugly turnary or create a method that will handle the null checks.
You can use convert a null value to a string
This example means that if Transaction is null, then use empty string instead
TransactionType = data.Transaction?.Type ?? ""
This example means that if CountryCode is null, then use empty string instead
Country = data.CountryCode ?? ""
The syntax itself is basically an inline if statement, there's more to it at https://learn.microsoft.com/en-us/dotnet/csharp/language-reference/operators/conditional-operator

Xamarin forms stacklayout returning null

I tried to get the item on stacklayout into an SQLite Database, but it just won't carry any data with.
private void MainCategory_ItemSelected(object sender, SelectedItemChangedEventArgs e)
{
var carier = e.SelectedItem as Item;
var cart_Itemsx = new List<cart_Items>();
cart_Itemsx.Add(new Models.cart_Items { cartid = 1, Id = carier.itid, image = carier.image, name = carier.title, price = carier.price1, quantity = "1", type = "Wash and Iron" });
cart_Itemsx.Add(new Models.cart_Items { cartid = 2, Id = carier.itid, image = carier.image, name = carier.title, price = carier.price2, quantity = "1", type = "Iron Only" });
SubCategory.ItemsSource = cart_Itemsx.ToList();
}
private void SubCategory_ItemSelected(object sender, SelectedItemChangedEventArgs e)
{
var dbcontet = e.SelectedItem as cart_Items;
_dbPath = Path.Combine(System.Environment.GetFolderPath(System.Environment.SpecialFolder.LocalApplicationData), "WashPro.db3");
var db = new SQLiteConnection(_dbPath);
db.CreateTable<cart_Items>();
var MaximumPrimaryKey = db.Table<cart_Items>().OrderByDescending(zt => zt.cartid).FirstOrDefault();
var waltani = new cart_Items()
{
cartid = (MaximumPrimaryKey == null ? 1 : MaximumPrimaryKey.cartid + 1),
Id = dbcontet.Id,
image = dbcontet.image,
name = dbcontet.name,
price = dbcontet.price,
quantity = dbcontet.quantity,
type = dbcontet.quantity
};
if (MaximumPrimaryKey == null)
{
db.Insert(waltani);
}
else if (MaximumPrimaryKey != null)
{
var MaximumQuantityKey = db.Table<cart_Items>().Where(m => m.cartid.Equals(dbcontet.cartid) && m.type.Equals(dbcontet.type)).FirstOrDefault();
if (MaximumQuantityKey != null)
{
waltani.price = dbcontet.price = 1;
db.Update(waltani);
}
}
SubCategory.SelectedItem = null;
}
image of the null error I got
I cannot even begin to understand the problem. The way I found around the problem will make my already dirty code way dirtier.
I have the damaging method I tried was using the selected context of the main stack panel to influence the second stack pannel.
I have even made the primary key of the cart_item model null.
Your selected element is null or database table does not contain any elements you are looking for in query, which is more likely because you are trying to initialize your database on SubCategory_ItemSelected. This is wrong approach.
Try to check if database item exist first.
var exist = db.Table<cart_Items>().OrderByDescending(zt => zt.cartid).Any();
if (exist)
{
var MaximumPrimaryKey = db.Table<cart_Items>().OrderByDescending(zt => zt.cartid).FirstOrDefault();
var waltani = new cart_Items()
{
cartid = (MaximumPrimaryKey == null ? 1 : MaximumPrimaryKey.cartid + 1),
Id = dbcontet.Id,
image = dbcontet.image,
name = dbcontet.name,
price = dbcontet.price,
quantity = dbcontet.quantity,
type = dbcontet.quantity
};
}
The problem lies at the last line of code.
SubListview.SelectedItem = null;
This somehow makes the casting not see the e.selected items.

EF6 CurrentValues.SetValues changes current values to null

I am using EF6 with C# in Asp.net 4.5. I want to update existing entry with new entry. For example:
Customer customer = new Customer()
{
Address = txtAddress.Text,
Name = txtName.Text,
UserName = txtUserName.Text
};
if(Id==0)
{
//INSERT
customer.Password = MyHelper.md5(txtPassword.Text);
customer.CreatedDate = DateTime.Now;
db.Customers.Add(customer);
}
else
{
//UPDATE
Customer currentCustomer = db.Customers.FirstOrDefault(x => x.Id == Id);
customer.Id = Id;
if (!String.IsNullOrEmpty(txtPassword.Text))
customer.Password = MyHelper.md5(txtPassword.Text);
db.Entry(currentCustomer).CurrentValues.SetValues(customer);
}
It inserts new entry and updates Address, Name, UserName properties successfully. But in update event, it changes CreatedDate and Password fields to NULL. Because I didn't specified Password and CreatedDate fields again. I want EF to skip these fields in update. But as I understand, it assumes these fields as null.
Is it a bug, or a feature of Entity Framework. So, what should I do if I want to update an entry with another entry? Do I have to specify all values again?
This is an issue with your process. customer is an in-memory representation of a new Customer. You define .Password and .CreatedDate only when Id==0 therefore it isn't available during your update routine. And then your .SetValues(customer) declaration sets the existing currentCustomer.Password and currentCustomer.CreatedDate to null
Update your code to only update properties from customer that you wish to be updated in currentCustomer. Like so:
//UPDATE
Customer currentCustomer = db.Customers.FirstOrDefault(x => x.Id == Id);
currentCustomer.Address = customer.Address;
db.Customers.Update(currentCustomer);
For an even cleaner approach, you could revise entirely to:
Customer c;
if(Id == 0) {
c = new Customer(){
Password = MyHelper.md5(txtPassword.Text),
CreatedDate = DateTime.Now
};
}
else
c = db.Customers.FirstOrDefault(x => x.Id == Id);
if (c != null) {
c = c{
Address = txtAddress.Text,
Name = txtName.Text,
UserName = txtUserName.Text
};
if(Id != 0)
db.Customers.Update(c);
else
db.Customers.Insert(c);
db.SaveChanges();
}

Can't save edited data into database, returns NULL, how do i fix it?

Button2 is the edit button, now i'm supposed to edit data that show in textboxes and press edit to change the values and save the into the database and show them in gridview aswell. But for some reason it says that newEmployee.FirstName was null, what do i do?
private void button2_Click(object sender, EventArgs e)
{
Employee Emp = SetValues(textBox1.Text, textBox2.Text, textBox3.Text);
bool result = UpdateEmployee(Emp);
ClearAll();
Display();
}
public bool UpdateEmployee (Employee Emp)
{
bool result = false;
using (var entity = new NorthwindEntities())
{
Employee newEmployee = entity.Employee.Where(x => x.EmployeeID == Emp.EmployeeID).Select(x => x).FirstOrDefault();
newEmployee.FirstName = Emp.FirstName;
newEmployee.LastName = Emp.LastName;
newEmployee.BirthDate = Emp.BirthDate;
entity.SaveChanges();
result = true;
}
return result;
}
private Employee SetValues(string FirstName, string LastName, string BirthDate)
{
Employee Emp = new Employee();
Emp.FirstName = FirstName;
Emp.LastName = LastName;
Emp.BirthDate = BirthDate;
return Emp;
}
Simple answer would be
newEmployee.FirstName = Emp.FirstName ?? string.Empty;
That said I cannot tell why Emp.FirstName is null to start with. In your code the following makes no sense either
Employee newEmployee = entity.Employee.Where(x => x.EmployeeID == Emp.EmployeeID).Select(x => x).FirstOrDefault();
since newEmployee cannot have a EmployeeID if it's new
Please check that you are getting employee or not by doing null check like as below
Employee newEmployee = entity.Employee.Where(x => x.EmployeeID ==
Emp.EmployeeID).Select(x => x).FirstOrDefault();
if(newEmployee!=null)
{
newEmployee.FirstName = Emp.FirstName;
newEmployee.LastName = Emp.LastName;
newEmployee.BirthDate = Emp.BirthDate;
entity.SaveChanges();
result = true;
}
I think you are getting error because FirstOrDefault returning null value , which is you are not checking
Instead of FirstOrDefault you must make use of SingleOrDefault as only one employee going to map with one ID, because Id i think in most of the cases it primary value . and you are not going to get more than one record i.e. you will receive single record only.
you forgot to set status of entity to modified state :EntityState.Modified
using (var context = new BloggingContext())
{
//set stus to modified
context.Entry(existingBlog).State = EntityState.Modified;
// Do some more work...
context.SaveChanges();
}

redirect to specific page based on db value

I have a form which is like the login form ,,, the idea is the user enter his first name and last name and I need to check if the gender is male it will redirect to a male.aspx and if the gender is female it will redirect to female.aspx, and if firstname and lastname are wrong or not match or not exist he will go back to the same form again.
I did the main code but I don’t know how to check gender to redirect to the page
Also I want to show the full name (First & last name) in the next page.
Here is my code. Hope I get help.
protected void log_Click(object sender, EventArgs e)
{
SqlDataSource sds = new SqlDataSource();
sds.ConnectionString = ConfigurationManager.ConnectionStrings["myDbConnectionString1"].ToString();
sds.SelectParameters.Add("firstname", TypeCode.String, this.firstname.Text);
sds.SelectParameters.Add("lastname", TypeCode.String, this.lastname.Text);
sds.SelectCommand = "SELECT * FROM [myTb] WHERE [firstname] = #firstname AND [lastname] = #lastname";
DataView dv = (DataView)sds.Select(DataSourceSelectArguments.Empty);
if (dv.Count == 0)
{
this.lblmsg.Text = "Invalid firstname and lastname!";
return;
}
else
{
Response.Redirect("home.aspx");
}
}
try it
After storing the data in the dataview access the gender column as
string gender = dv.Table.Rows[0]["gender"].ToString();
if (gender == "male")
{
Response.Redirect("malepage.aspx");
}
else if( gender == "female" )
{
Response.Redirect("femalepage.aspx");
}
In order to get First and last name use this
string fname= dv.Table.Rows[0]["firstname"].ToString();
string lname= dv.Table.Rows[0]["lastname"].ToString();
You can pass these to the second page by using querystring or Session.
Response.Redirect("yourpage.aspx?fname="+fname+"lname="+lname);
// on second page get them as
string fname = Request.QueryString["fname"];
string lname = Request.QueryString["lname"];
// or by using session pass these values as
Session["fname"] = fname;
Session["fname"] = lname;
// and on the second page get them as
string firstname = Session["fname"].ToString();
string lasttname = Session["lname"].ToString();
if (System.Convert.ToString(dv.Table.Rows[0]["colName"]) == "Male")
{
Response.Redirect("~/Male.aspx");
}
else
{
Response.Redirect("~/female.aspx");
}
You can do like this
if(dview.Table.Rows[0]["Gender"].ToString() =="Gender")
{
Response.Redirect("Page.aspx?fname="+dview.Table.Rows[0]["fname"].ToString()"&LastName=" + dview.Table.Rows[0]["lname"].ToString());
}
else
{
Response.Redirect("Page2.aspx?fname="+dview.Table.Rows[0]["fname"].ToString()");
}
Send First Name and Last Name in a querystring and join them in the destination page by Request.Querystring

Categories

Resources