ASP.NET and SQL getting values to label - asp.net

I created a table in sql database which has list of prices and Items Name....
I wrote a small coding to get the values of item names into my dropdownlist....
Now,
If i select an item in the dropdownlist, I need the price to displayed in the textbox or label... How can I do this? help me out!

There are several different ways of doing that.
You could
- load price/product as JS name value collection and do it client side - most efficient way
- populate dropdown with productId (value) and description and handle itemindexchanged event and do everything server side - not recommended for a public facing, busy web apps.
- send ajax call to web service to get price (client side) - that when you have a bit more complicated model.
It's up to you to decide.
Hope that helps.

Set the AutoPostback property of the DropDownBox to True
Then use something like this:
protected void DropDownList1_SelectedIndexChanged(object sender, EventArgs e)
{
Label1.Text = DropDownList1.SelectedItem.Value;
}

Related

Should i make a call to DB or save value in viewstate

On asp.net page, I am using tabs and one of the tab has got user control on it.
On the first tab, data is being displayed from table A and the second tab (which has user control on it) is getting data from table B.
On the user control (second Tab), I need to show the column value of table A. It is just one string value.
I am wondering if there is any best way of displaying the value of a table A column without making a call to database?
The way code has been designed, I can’t access the user control’s textbox from the first tab.
I can only think of using view state or session but don’t know if I should use them instead of making call to DB.
I want value to live for the current page's lifecycle.
If you can save it in viewstate then go for it. But there are plenty of storage options in addition to just viewstate:
querystring (good for Ids, not great for strings)
cookie (pretty straight forward)
local storage (HTML 5 only)
cache (you could still appear to make the call but just have the results cached. you then have to deal with cache expiration as well)
session (as you mentioned, this is basically a per-person cache usage, but is not a bad option)
hidden field (basically what viewstate is)
Even with all of those options, the viewstate is going to be a pretty good one, but it just requires that you post back the viewstate every time you need that value.
How about using js to copy the data contents from tab1? Are you loading the usercontrols in tabs using ajax?
If you have a complex form and need to split into smaller chunks I would use a multiview control with as many views as you need to complete your task. If you design each view with its own controls, validation groups and logics .net will do the rest, you won't have to manually deal with states or saving middle steps
<asp:MultiView ID="MultiView1" runat="server">
<asp:View ID="View1" runat="server">
<asp:TextBox ID="txt1" runat="server" />
<asp:Button ID="Button1" runat="server" Text="Next" OnClick="NextStep_Click" />
</asp:View>
<asp:View ID="View2" runat="server">
<asp:TextBox ID="txt2" runat="server" />
<asp:Button ID="Button2" runat="server" Text="End" OnClick="EndProcess_Click" />
</asp:View>  
</asp:MultiView>
<asp:TextBox ID="txt3" runat="server" />
In code behind
protected void NextStep_Click(object sender, EventArgs e)
{
MultiView1.SetActiveView(View2);
txt2.Text = txt1.Text;
}
protected void EndProcess_Click(object sender, EventArgs e)
{
txt3.Text = txt1.Text + " " + txt2.Text;
}
you can go back and forth the times you want and won't have to worry with the values the users entered. Obviously, you have to put buttons to go back and just set the active view you want.

Concurrency exception with Devexpress ASPXGridView and EntityFramework 4.3.1

My Issue
I have a simple WebForms project for testing concurrency.
I am using:
1. Entity Framework 4.3.1 code first approach.
2. DevExpress ASP.net controls to visualize my data. Specifically an ASPXGridView control.
3. MySQL as database backend.
Now I am having an issue with the concurrency check.
Even if I am the only user editing the data, if I edit the same record twice using the DevExpress ASPXGridView I get a concurrency exception!
The exception I get is :
System.Data.OptimisticConcurrencyException
My Setup
** Simplified here for brevity
My code first entity is defined something like this:
public class Country
{
//Some constructors here
[Required, ConcurrencyCheck]
public virtual string LastUpdate { get; set; }
[Required, Key, DatabaseGenerated(DatabaseGeneratedOption.None)]
public virtual int CountryID { get; set; }
//Various other data fields here
}
You can see I have added a single field called LastUpdate which the concurrecny check is being tested against due to setting the [ConcurrencyCheck] attribute.
On my web page with the DevExpress ASPXGridView I am using an EntityDataSource to make the binding between the grid view and the entity framework. The grid view is using a popup editor. I have the following events hooked:
protected void Page_Load(object sender, EventArgs e)
{
//Hook entity datasource to grid view
dbgCountries.DataSource = CountriesEntityDataSource;
dbgCountries.DataBind();
}
protected void CountriesEntityDataSource_ContextCreating(object sender, EntityDataSourceContextCreatingEventArgs e)
{
//Create and hook my DBContext class to the entity
//datasources ObjectContext property.
var context = new MyDBContextClass();
e.Context = ((IObjectContextAdapter)context ).ObjectContext;
}
protected void dbgCountries_InitNewRow(object sender, DevExpress.Web.Data.ASPxDataInitNewRowEventArgs e)
{
//I create a new MyDBContextClass here and use it
//to get the next free id for the new record
}
protected void dbgCountries_CustomErrorText(object sender, DevExpress.Web.ASPxGridView.ASPxGridViewCustomErrorTextEventArgs e)
{
//My code to catch the System.Data.OptimisticConcurrencyException
//excpetion is in here.
//I try to rtefresh the entity here to get the latest data from
//database but I get an exception saying the entity is not being
//tracked
}
protected void dbgCountries_RowValidating(object sender, DevExpress.Web.Data.ASPxDataValidationEventArgs e)
{
//Basic validation of record update in here
}
protected void dbgCountries_RowUpdating(object sender, DevExpress.Web.Data.ASPxDataUpdatingEventArgs e)
{
//I set the LastUpdate field (my concurrency field)
//to the current time here
}
I also have some button events hooked to test a direct concurrecny test.
eg
- Get Entity
- Update Entity
- Update DB directly with sql
- Save Entity
- Get concurrency exception as expected
eg
- Get Entity
- Update Entity
- Save Entity
- No issue.
- Get Entity again.
- Update Entity again.
- Save Entity again.
- No issue.
These buttons work as expected. Only ther grid updates seem to have an issue.
Maybe it is because the grid needs to use ObjectContect and my entity framework classes are using DBContext?
My Attempted Fixes
I have scoured the internet trying to find a solution. Checked DevExpress forums, checked other posts here on StackOverflow, various posts on the internet, Microsoft MSDN articles on concurrency and I just can not work this out.
None of the posts were as 'simple' as mine. They all had other data involved. eg a master/detail
relashionship. custom editors. etc. I am using all inbuild DevExpress controls and just display a
single grid view on my db table / entity.
Some posts suggest refreshing the entities. I tried this but get an exception saying the entity is
not being tracked in the object state manager.
I tried refreshing the entity framework by destroying and recreating my object context / db
context but somehow I still get the concurrency issue.
I tried refreshing using the DBContexct and also the ObjectContext. Neither worked.
(objContext.Refresh(RefreshMode.StoreWins, entity). I either get an exception as stated]
earlier sayign the entity is not being tracked, or if I tell it to refresh only non modifed
entities then nothing happens at all (no refresh, no excpetion)
I tried making my DBContext global but this is no good as WebForms appears to want to recreate its
entire state and rehook its grids data context etc after every web refresh. (page loads, user
clicks edit, user clicks ok to update)
Now all of these solutions seem to takle what to do AFTER the concurrency exception. Seeing that I should not even be getting the exception in the first place I guess they would not help.
Suggestions
Do any of you have suggestions on how to make this work?
Do I have to maybe force the entity framework to refresh manually after posting data from the grid?
(I only just thought of this one now)
It seems a pretty simple setup I have. Maybe I am missing something very obvious. I have not worked with WebForms or EntityFramework much yet so there could be simple (and perhaps obvious) solutions I am missing?
Any help appreciated.
Thanks
Peter Mayes
I have managed to solve my issue.
It may not be the most correct solution but it is working and any progress at this point is much appreciated.
Approach
I tried refreshing Entity Framework after posting data in the ASPXGridView.
Many attempts. None worked.
I tried using a TimeStamp attribute on my Country entity but this did
not seem to map very well to MySQL. (However I might try this again now
I have solved the issue)
I then thought maybe my DevArt MySQL dot connector and MySQL was at fault.
So I switched over to MSSQL and its standard connector. This showed the same
issue am having with MySQL & co.
Finally I was mucking around with various attempts and noticed that if I go to a different
page on my web site, then back again the issue does not occur.
E.g.:
Edit Country and Save. No Issues.
Switch to other site page.
Switch back to Countries.
Edit Country and Save. No Issues.
The difference being, if I do not switch pages the second edit creates a concurrency exception.
With some more testing with co-workers I got a hunch that maybe the viewstate for the
entity datasource was not being refreshed after a post/update on the ASPGridView.
So what I did was:
> Set EntityDataSource.StoreOriginalValuesInViewState = FALSE
This stopped all concurrency working as no old/pre edit values were being stored and so
were not available for the concurrecny check.
I then thought I would force the oldvalues to be what was in the editor before I edited.
I was using ASPXGridView.RowUpdating to do this.
I thought thats ok, I can just use the OldValues passed to ASPXGridView.RowUpdating to
ensure entity framework is good to go.
Doing this I found some very odd behaviour...
If I:
- open edit form in browser A
- open edit form in browser B
- save changes in browser B (DB updates with new values here)
- save changes in browser A (DB updated here too. but should have been a
concurrency exception!)
The reason post from A was succeeding was that OldValues on A had been magically updated
to the new values B had posted!
Remember the edit form on A was open the whole time so it should not have updated its OldValues underneath. I have no idea why this occurs. Very odd.
Maybe OldValues are not retrieved by the DevExpress ASPXGridView until the
edit form is closing?
Anyway, then I thought. Fine, I will just work around that oddity. So to do so I created
a static member on the web page to store a copy of my Country entity.
When the user goes to open the editor I get the current values and store them.
Then when ASPXGridView.RowUpdating fires I push the stored old values back into the
OldValues data. (I also update my timstamp/concurrency field here too in the NewValues
data)
With this approach my concurrency now works. Hurah!.
I can edit locally as much as I want and get no conflicts. If I edit in two browsers at once the second one to post raises concurrency exception.
I can also switch between MySQL and MSSQL and both work correctly now.
Solution Summary
Set EntityDataSource.StoreOriginalValuesInViewState = FALSE. (I did this in the designer.)
Create private member to hold pre-edit country values
private static Country editCountry = null;
Hook StartRowEditing on ASPXGridView. In here I get the current country values and store them as 'pre edit' values. Note that CopyFrom is just a helper method on my entity.
protected void dbgCountries_StartRowEditing(object sender, DevExpress.Web.Data.ASPxStartRowEditingEventArgs e)
{
if (editCountry == null)
{
editCountry = new Country();
}
var context = new MyDBContext();
var currCountry = context.Countries.Where(c => c.CountryID == (int)(e.EditingKeyValue)).Single();
editCountry.CopyFrom(currCountry);
}
Hook RowUpdating on ASPXGridView. Here is where I make sure old values are correct before update goes ahead. This ensures concurrency will work as expected.
protected void dbgCountries_RowUpdating(object sender, DevExpress.Web.Data.ASPxDataUpdatingEventArgs e)
{
//Ensure old values are populated
e.OldValues["RowVersion"] = editCountry.RowVersion;
//No need to set other old values as I am only testing against
//the one field for concurrency.
//On row updating ensure RowVersion is set.
//This is the field being used for the concurrency check.
DateTime date = DateTime.Now;
var s = date.ToString("yyyy-MM-dd HH:mm:ss");
e.NewValues["RowVersion"] = s;
}

XtraReports Not working in V11.2.8 Version

Currently i am using Devexpress XtraReports V11.2.8. My problem is i am able to populate report in V11.1.6 but i am unable to populate report in V11.2.8 it showing only scroll bar in the reportviewer when i debug it is properly mapping and binding the data. FYI: I need to bind/Initialize reportviewer in button click only. Devexpress people said that i need to initialize reportviewer with the report in page_load it self but we can't do that because we have large amount of data exist and we need to populate report with particular input criteria matched result only. Please advice.
FYI: refer this link for devexpress response on the above issue http://www.devexpress.com/Support/Center/Issues/ViewIssue.aspx?issueid=Q362696
I can't find any solution about version problem without additional information.
but, the 2nd problem you told, i can give a possible solution to that. You can take necessary input you need for the report and then click on the button to preview the report regarding on inputs. It is better to create a stored procedure in your database for this report.
Suppose, you need to show a report for specific 'Cust_Id'. In the 'Form1' put a text field for 'Cust_Id' and a 'button'. On button click event put the following code,
private void simpleButton1_Click(object sender, EventArgs e)
{
Portfolio_XtraReport port = new Portfolio_XtraReport();
string custID = textEdit1.Text.ToString();
port.Portfolio(custID);
port.ShowPreview();
}
now in the 'Portfolio_XtraReport.cs' put the following code,
public Portfolio_XtraReport()
{
Portfolio("N");
}
public void Portfolio(string custId)
{
if (custId != "N")
{
InitializeComponent();
sP_PORTFOLIOTableAdapter.GetData(custId);
}
}
Here, sP_PORTFOLIOTableAdapter is the table adapter for the dataset, I used a stored procedure which takes 'Cust_Id' as input.

How to save connection request to database in this scenario

I am new to asp.net and know little bit about its working and as I am moving forward I am getting new and more newer doubts.
Here at this point I was working with two RadioLists that are being binded at page load.
Now when a user changes the index of radio button in list 1. Second needs to get updated accordingly depending what value is currently set for selected radio button.
Since the page will be posted back hence I either need to fire a query again to get new data from DataBase for currently selected index or can store 2-3 tables in session in form of Dataset.
What should I do in such scenario. Should I fire an sql query again or retrieve DataSet from Session.
What is the most optimal approach for this. And WHY ?
The data for radio button list 1 (rbl1) should not be retrieved again from the database. It should already be populate from the ViewState. This is an invisible object on your page that keeps track of the contents of your controls between loading them into the browser and returning the form back to the server. If you rebind rbl1 to the data on a postback, you will lose the current selection.
There should be nothing wrong with retrieving the data for the send radiobuttonlist from the database if the results are going to change depending on the selection of the first.
However, if the size of the data is small you might want to cache the results to the application cache, if all users see the same set of data, or the session cache if it is user-dependent.
Then you can use Linq to query the data based on the selection from the first radiobuttonlist.
<asp:RadioButtonList ID="rbl1" runat="server" AutoPostBack = "true"
OnSelectedIndexChanged="rbl1_SelectedIndexChanged">
protected void Page_Load(object sender, EventArgs e)
{
if(!IsPostBack)
{
//bind your rbl1 here
}
}
protected void rbl1_SelectedIndexChanged(object sender, EventArgs e)
{
//load your second radio button list depending on the selection of the first
}

asp:DropDownList Error: 'DropDownList1' has a SelectedValue which is invalid because it does not exist in the list of items

I have a asp.net 2.0 web site with numerous asp:DropDownList controls.
The DropDownList control contains the standard info city, state, county etc... info.
In addition to the standard codes the site also has custom codes that the users can configure themselves.
For example a animal dropdown may contain the values Dog, Cat, Fish, ect...
I am popluating the DropDownList from a SQL 2005 table that I created e.g. tblCodes
Everything works great and users are able to add orders using the numerous DropDownList controls to choose items from the list.
The problem occurrs if a user wants to change one of their custom dropdowns. For example a user would like to change the verbage
on a animal type control from Dog to K9. This is where the problem starts.
For all new orders the drop down works fine. When the user retrieved an old order
I get the following error in the C# codebehind
"'DropDownList1' has a SelectedValue which is invalid because it does not exist in the list of items."
What's happening is the old order has a database field value of Dog and the DropDownList no longer has Dog in its list since the user changed it to K9.
Any ideas on a workaround?
Is there a way to make the asp:DropDownList accept items not seeded in its list?
Is there another control I could use?
I solved this exact same problem just two days ago. First, I moved the code that set the SelectedValue to a PreRender handler for the DropDownList. Then, I add logic to first check to see if the value is in the drop down list. If not, I add it.
Here's my code. ddSpecialty is my drop-down list, populated with "specialties" from the database. registration.Specialty is the specialty that the user chose, which may or may not be in the drop down, since that particular specialty may have been deleted since they last chose it.
protected void ddSpecialty_PreRender(object sender, EventArgs e)
{
if (!ddSpecialty.Items.Contains(new ListItem(registration.Specialty)))
ddSpecialty.Items.Add(registration.Specialty);
ddSpecialty.SelectedValue = registration.Specialty;
}
I've become very fond of the following little snippet for setting DropDownList values:
For non-DataBound (eg Items added manually):
ddl.SelectedIndex = ddl.Items.IndexOf(ddl.Items.FindByValue(value));
For DataBound:
ddl.DataBound += (o,e) => ddl.SelectedIndex = ddl.Items.IndexOf(ddl.Items.FindByValue(value));
I sure do wish though that ListControls in general didn't throw errors when you try to set values to somthing that isn't there. At least in Release mode anyways it would have been nice for this to just quietly die.
Your SelectedValue should be a unique id of some sort, that doesn't change. The Text value that gets displayed to the user is something seperate, and can change if necessary without affecting your application, because you associate the id with your Order, not the displayed string value.
I'm not sure it's the same issue, but I had a similar sounding issue with trying to bind a DropDownList that I wanted to contain in a GridView. When I looked around I found a lot of people asking similar questions, but no robust solutions. I did read conflicting reports about whether you could intercept databinding, etc events. I tried most of them but I couldn'f find a way of intercepting or pre-empting the error.
I ended up creating a subclass of the ddl, intercepting the error from there hacking a fix.
Not tidy but it worked for my needs. I put the code up on my blog in case it's of help. link text
Check this:
http://www.codeproject.com/Tips/179184/ASP-dropdownlist-missing-value-error.aspx
Ran into this myself. Oddly, ddl.ClearSelection(); didn't work. Had to use ddl.SelectedValue = null
Also noticed, that this must come AFTER I clear the items from the list ddl.Items.Clear(); which also seems weird. Setting the SelectedValue to null, then clearing the items still threw the error.
Once this is done, re-bind the list and re-select with new value.
Try this:
if (ddl.Items.Contains(new ListItem(selectedFacility)))
ddl.SelectedValue = selectedFacility;
I have made a workaround after having this problem very often. Unfortunate that MS still did not recovered this issue.
Anyway, my workaround is as follows.
1) I bind the data to the ToolTip property of the DropDownList
<asp:DropDownList ID="edtDepartureIDKey" runat="server" CssClass="textbox"
ToolTip='<%# Eval("DepartureIDKey") %>' DataSource="<%# DLL1DataSource() %>" DataTextField="DisplayField" DataValueField="IDKey"
onprerender="edtDepartureIDKey_PreRender">
2) On the prerender event i check the availibilty of the data, and if it is not in the list I simply add it, then set the selectedindex to the data valuei which I saved in ToolTip property
protected void edtDepartureIDKey_PreRender(object sender, EventArgs e)
{
DropDownList ddl = (sender as DropDownList);
if (ddl.Items.FindByValue(ddl.ToolTip) == null)
{
//I am pulling Departure Data through the ID which is saved in ToolTip, and insert it into the 1st row of the DropDownList
TODepartureData v = new TODepartureData(DBSERVER.ConnStrName);
TODeparture d = v.Select(Convert.ToInt32(ddl.ToolTip));
ddl.Items.Insert(0, new ListItem(d.DeptCode, ddl.ToolTip));
}
ddl.Items.FindByValue(ddl.ToolTip).Selected = true;
}

Resources