I use an asp:SqlDataSource Element to fetch Data and then display it in an asp:ListView.
For the sake of simplicity, let's assume the Database consists of the rows and id, author (it's actually more, but that doesn't matter).
This is the code I use:
<asp:SqlDataSource ID="NewsDataSource" runat="server"
ConnectionString="<%$ connectionStrings:RemoteSqlConnection %>"
ProviderName="System.Data.SqlClient"
SelectCommand="SELECT * FROM [news]"
UpdateCommand="UPDATE [news] SET author=#author WHERE id=#id"
DeleteCommand="DELETE FROM [news] WHERE id=#id"
InsertCommand="INSERT INTO [news] (author) VALUES (#author)">
<UpdateParameters>
<asp:Parameter Name="id" Type="Int32" />
</UpdateParameters>
<DeleteParameters>
<asp:Parameter Name="id" Type="Int32" />
</DeleteParameters>
</asp:SqlDataSource>
My problem is, that the parameter id which I define for UpdateParameters and DeleteParameters is always null.
It doesn't seem to be associated with the database field id.
One hack which allowed me to fix the problem (but only for the update case) was to insert an invisible asp:Label to which I binded the id (Just like I binded the Author field to a Textbox).
I don't think that the ListView code should be relevant, but I'll try to include some lines which are relevant here:
<asp:ListView runat="server" DataSourceID="NewsDataSource">
<LayoutTemplate>
<div id="itemPlaceholder" runat="server"></div>
</LayoutTemplate>
<ItemTemplate>
<%# Eval("author")%>
</ItemTemplate>
<EditItemTemplate>
<!-- This line is only the workaround solution --><asp:Label ID="idLabel" runat="server" Text='<%# Bind("id")%>'></asp:Label>
<asp:TextBox ID="authorTextbox" runat="server" Text='<%# Bind("author")%>'></asp:TextBox>
</EditItemTemplate>
</asp:ListView>
There is an attribute on the asp:ListView called DataKeyNames, adding id to this should make it store that parameter value without the need for a hidden element.
For more information on the DataKeyNames attribute see: http://msdn.microsoft.com/en-us/library/system.web.ui.webcontrols.listview.datakeynames(v=vs.110).aspx
Related
Pretty sure I know why I'm getting the error, just not sure how to go about fixing it. In a FormView ItemTemplate I've got a Label control for the Project ID# bound to the FormView's SQLDatasource. I've also got a DropDownList whose SQLDatasource I've got tied to the Label.Text as a ControlParameter. I am guessing since the Label control isn't bound yet, that's causing my DDL to kick out that error.
ASPX
<asp:FormView ID="FvChangeOrder" runat="server" DataKeyNames="ProjectChangeOrderID"
DataSourceID="FvChangeOrderSQL" OnItemCommand="FvChangeOrder_OnItemCommand"
OnDataBound="FvChangeOrder_OnDataBound">
<ItemTemplate>
<div>Project #: </div>
<div>
<asp:Label ID="LblProjectID" runat="server" Text='<%# Bind("ProjectID") %>' /></div>
<div>Shipment #: </div>
<div>
<asp:DropDownList runat="server" ID="DdlShipment" DataSourceID="DdlShipmentSQL"
SelectedValue='<%# Bind("ProjectShipmentID") %>' DataValueField="ProjectShipmentID"
DataTextField="ShipmentNo" Enabled="False" />
</div>
...
</ItemTemplate>
</asp:FormView>
<asp:SqlDataSource ID="FvChangeOrderSQL" runat="server"
ConnectionString="<%$ ConnectionStrings:ProjectLogicTestConnectionString %>"
SelectCommand="SELECT [ProjectID], [ProjectChangeOrderID], [ProjectShipmentID], [SeqNo],
[Date], [EnteredBy_UserID], [Source], [Initiator], [Reason], [ReasonNotes],
[ApprovalCode], [Description], [NumPanels], [Amount], [IsCommissionable], [DateDue],
[DateRecd], [Status]
FROM [tblProjectChangeOrder] WHERE ([ProjectChangeOrderID] = #PCOID)">
<SelectParameters>
<asp:QueryStringParameter Name="PCOID" QueryStringField="PCOID" Type="Int32"/>
</SelectParameters>
</asp:SqlDataSource>
<asp:SqlDataSource ID="DdlShipmentSQL" runat="server"
ConnectionString="<%$ ConnectionStrings:ProjectLogicTestConnectionString %>"
SelectCommand="SELECT pco.ProjectShipmentID, ps.ShipmentNo FROM tblProjectChangeOrder pco
LEFT JOIN tblProjectShipment ps ON pco.ProjectShipmentID = ps.ProjectShipmentID
WHERE pco.ProjectID = #ProjectID">
<SelectParameters>
<asp:ControlParameter ControlID="FvChangeOrder$LblProjectID"
Name="ProjectID" PropertyName="Text"/>
</SelectParameters>
</asp:SqlDataSource>
Would I be better off leaving out the WHERE and ControlParameter on the DDL SQLDatasource and changing the DDL's SQL Source in codebehind on the OnDataBound method of the FormView?
Think I got it worked out. I changed the ControlParameter to just Parameter Type="String" and on Form_Load set a Label to FvChangeOrder.FindControl("LblProjectID"), assigned LblProject.Text to a string, then passed that as the DefaultValue for the Select Parameter.
On an semi-related problem I had to remove the SelectedValue on the markup side and handle SQLCommand in the Form_Load for the DDL SelectedValue. Probably a bad dataset but I kept getting an error that the value in the field wasn't in the List or something like that. There are multiple Change Orders for a given project that have NULL values for the ShippingID.
Anywho, all is working on the ItemTemplate side. Now to see if I can keep everything working on the EditItemTemplate. :P
I have a formview that is populated with an ObjectDataSource and it works great. Nested in that is a gridview also populated with a nested ODS that works perfect 99% of the time. Also nested in the formview is another ODS populated from the same control that populates the other nested datasource that works perfect all of the time. Code below to make that make sense.
The problem is if you change pages it all works fine most of the time. There are 2 search features built into the page. That is where the error occurs. If you use either of them without changing pages it works great. If you use one of them and then change pages and try to use either one of them the page crashes with an error that says something like Control Parameter 'X' is not found in 'Y'. The problem is that it is not a true error because there is a button that displays the bootstrap model which displays its gridview with no issues and the ODS is based on exactly the same control so it is obviously there. I imagine that it is related to the events, but they step through just fine. I am not sure what could be causing it.
Here is a little test project that is basically the same setup only paging is setup in the formview and the ODS1 in the real project and it works perfectly.
<asp:FormView ID="FormView1" runat="server" DataSourceID="ObjectDataSource1">
<ItemTemplate>
ImportantID:
<asp:Label Text='<%# Bind("ImportantID") %>' runat="server" ID="ImportantIDLabel" Visible="false" /><br />
Name:
<asp:Label Text='<%# Bind("Name") %>' runat="server" ID="NameLabel" /><br />
<div id="nestedContent">
<asp:ObjectDataSource ID="ObjectDataSource2" runat="server" SelectMethod="listNested" TypeName="TestProject.DataSourceClass">
<SelectParameters>
<asp:ControlParameter ControlID="ImportantIDLabel" PropertyName="Text" DefaultValue="-1" Name="ImportantIDFromOnject1ForNestedObject" Type="Int32"></asp:ControlParameter>
</SelectParameters>
</asp:ObjectDataSource>
<asp:GridView ID="GridView1" runat="server" DataSourceID="ObjectDataSource2" AutoGenerateColumns="False">
<Columns>
<asp:BoundField DataField="YetAnotherProperty" HeaderText="YetAnotherProperty" SortExpression="YetAnotherProperty"></asp:BoundField>
<asp:BoundField DataField="OtherPropertiesGoInThisClass" HeaderText="OtherPropertiesGoInThisClass" SortExpression="OtherPropertiesGoInThisClass"></asp:BoundField>
</Columns>
</asp:GridView>
</div>
SomeProperty:
<asp:Label Text='<%# Bind("SomeProperty") %>' runat="server" ID="SomePropertyLabel" /><br />
SomeOtherProperty:
<asp:Label Text='<%# Bind("SomeOtherProperty") %>' runat="server" ID="SomeOtherPropertyLabel" /><br />
<asp:ObjectDataSource ID="ObjectDataSource3" runat="server" SelectMethod="GetDataObject2" TypeName="TestProject.DataSourceClass">
<SelectParameters>
<asp:ControlParameter ControlID="ImportantIDLabel" PropertyName="Text" DefaultValue="-1" Name="ImportantID" Type="Int32"></asp:ControlParameter>
</SelectParameters>
</asp:ObjectDataSource>
<div id="BootStrapModalPopup">
This displays the data with no problems
</div>
</ItemTemplate>
</asp:FormView>
<asp:ObjectDataSource ID="ObjectDataSource1" runat="server" SelectMethod="GetDataObject1" TypeName="TestProject.DataSourceClass">
<SelectParameters>
<asp:Parameter DefaultValue="-1" Name="ImportantID" Type="Int32"></asp:Parameter>
<asp:Parameter DefaultValue="" Name="Name" Type="String"></asp:Parameter>
<asp:Parameter Name="SomeProperty" Type="String"></asp:Parameter>
</SelectParameters>
</asp:ObjectDataSource>
I would appreciate any ideas of where to look next. By the way I have used a textbox, hiddencontrol and Session variable for the ID field and nothing makes a difference for it. If I disable the ODS2 it goes back to working perfectly also but I need that data.
Thanks
Jimmy
I actually lucked into the answer for this. It was not my nesting it was my paging. I will leave the question for anyone that has a similar problem since I don't see any successful errors to this. The issue I faced was I needed to reset my pageindex on search. It worked great searching from page one, but searching from any other page is an empty return due to the indexing so the controls did not exist. Hopefully it will help someone to search that if you run into this issue. Just set pageindex on the formview back to 0.
I am new to .net/c# and visual studio. I have been looking all over the internet for an answer but couldn't find it. Thanks for your help.
I'm populating a drop down list from a database table, I want to pass a dynamic parameter to the asp server control (the logged in persons username). The 2 areas I want to put this dynamic string I added PUT_LOGGED_IN_USERNAME_HERE".
<asp:DropDownList ID="DropDownList1" runat="server"
DataSourceID="SqlDataSource1" DataTextField="Name" DataValueField="PK_Task" AppendDataBoundItems="true">
<asp:ListItem Selected="True">Supportive</asp:ListItem>
</asp:DropDownList>
<asp:SqlDataSource ID="SqlDataSource1" runat="server"
ConnectionString="<%$ ConnectionStrings:ApplicationServices %>"
SelectCommand="SELECT [PK_Task], [Name] FROM [Task] WHERE ([PointPerson] LIKE '%' + #PointPerson + '%') AND [Status] LIKE 'Done'">
<SelectParameters>
<asp:QueryStringParameter DefaultValue="PUT_LOGGED_IN_USERNAME_HERE" Name="PointPerson"
QueryStringField="PUT_LOGGED_IN_USERNAME_HERE"" Type="String" />
</SelectParameters>
</asp:SqlDataSource>
How do I accomplish this?
I found the code to display username:
<%= Page.User.Identity.Name %>
However it is not working when I use it as shown:
<asp:QueryStringParameter DefaultValue="<%= Page.User.Identity.Name %>" Name="PointPerson"
QueryStringField="<%= Page.User.Identity.Name %>"" Type="String" />
You can access properties of SqlDataSource, including Parameters in code behind, like so:
SqlDataSource1.SelectParameters["PointPerson"].DefaultValue = "User";
I have a sqldatasource, in select command i have #status parameter. The parameter take the value from the textbox at runtime.
<asp:SqlDataSource ID="SqlDataSource1" runat="server"
ConnectionString="<%$ ConnectionStrings:ConnectionString %>"
SelectCommand="SELECT * FROM [project_details] WHERE ([status] = #status)"
FilterExpression="title='{4}'"
ProviderName="<%$ ConnectionStrings:ConnectionString.ProviderName %>"
EnableCaching="True">
<SelectParameters>
<asp:ControlParameter ControlID="TextBox1" Name="status" PropertyName="Text" ConvertEmptyStringToNull="false"
Type="String" />
</SelectParameters>
</asp:SqlDataSource>
my problem is that when i run the page without entring the parameter in text box sqldatasource is not returing any row.
Looking at the documentation on MSDN, you have to alter how you have setup the SqlDataSource.
Try this:
<asp:SqlDataSource ID="SqlDataSource1" runat="server"
ConnectionString="<%$ ConnectionStrings:ConnectionString %>"
SelectCommand="SELECT * FROM [project_details]"
FilterExpression="title='{0}'"
ProviderName="<%$ ConnectionStrings:ConnectionString.ProviderName %>"
EnableCaching="True">
<FilterParameters>
<asp:ControlParameter ControlID="TextBox1" Name="status" PropertyName="Text" ConvertEmptyStringToNull="false" Type="String" />
</FilterParameters>
</asp:SqlDataSource>
I have removed the Where clause from the query as this will be applied by the filter expression. Also, I have changed the filter expression from title='{4}' to title='{0}'. The documentation states that the number is a placeholder to an item in the FilterParameters collection.
Updated
I have also changed the SelectParameters to FilterParameters
Update 2
I have created a working example to finish of this answer. This will filter the Title column using the text from the text box. If this text box is empty it will return all the rows from the table (a scary thought but OK for this example). It is querying the AdventureWorks database for which I set a connection string called AWorks.
<asp:SqlDataSource ID="SqlDataSource1"
ConnectionString="<%$ ConnectionStrings:AWorks %>"
SelectCommand="SELECT ContactId, Title, FirstName, LastName FROM Person.Contact"
FilterExpression="Title='{0}'"
runat="server">
<FilterParameters>
<asp:ControlParameter Name="Title" ControlID="txtTitle" PropertyName="Text" />
</FilterParameters>
</asp:SqlDataSource>
<asp:TextBox runat="server" Id="txtTitle"></asp:TextBox>
<asp:Button runat="server" UseSubmitBehavior="true" Text="Submit" />
<asp:GridView
DataSourceID="SqlDataSource1"
AutoGenerateColumns="false"
runat="server">
<Columns>
<asp:BoundField Visible="false" DataField="ContactId"></asp:BoundField>
<asp:BoundField Visible="true" DataField="Title"></asp:BoundField>
<asp:BoundField Visible="true" DataField="FirstName"></asp:BoundField>
<asp:BoundField Visible="true" DataField="LastName"></asp:BoundField>
</Columns>
</asp:GridView>
try a condition like this:
(#Status is null or #Status ='' Or Status = #Status)
set ConvertEmptyStringToNull="true" and then try....
Add CancelSelectOnNullParameter="false" to your SqlDataSource.
I have an asp.net intranet site hosted on IIS on my computer.
On one page you can enter two user id's and get a side by side comparison of their roles in our (custom app) system.
I often use it to add roles when I'm setting up new users. After running the query, if i change a role and run the query again it will not show updated results. It's being cached somehow. I have to go to another page and come back and them run the query to get updated results.
How can avoid having to navigate away to get the updated query results displayed.n
here's the code
<asp:Label ID="Label1" runat="server" Text="Username"></asp:Label>
<asp:TextBox ID="TextBox1" runat="server"></asp:TextBox>
<br />
<asp:Label ID="Label2" runat="server" Text="Username"></asp:Label>
<asp:TextBox ID="TextBox2" runat="server"></asp:TextBox>
<asp:Button ID="Button1" runat="server"
Text="Compare Permissions" />
<br /><br />
<asp:GridView ID="GridView1" runat="server" CssClass="mGrid" DataSourceID="SqlDataSource1">
</asp:GridView>
<asp:SqlDataSource ID="SqlDataSource1" runat="server"
ConnectionString="<%$ ConnectionStrings:ConnectionString %>"
ProviderName="<%$ ConnectionStrings:ConnectionString.ProviderName %>" SelectCommand="WITH
firstPerson AS
(
select username, security_role from user_role
where username=upper(:Username1)
),
secondPerson as
(
select username, security_role from user_role
where username=upper(:UserName2)
)
select firstPerson.username , firstPerson.security_role,secondPerson.username,secondPerson.security_role from firstPerson FULL JOIN secondPerson
on firstPerson.security_role=secondPerson.security_role order by firstPerson.security_role, secondPerson.Security_role">
<SelectParameters>
<asp:ControlParameter ControlID="TextBox1" Name="Username1"
PropertyName="Text" />
<asp:ControlParameter ControlID="TextBox2" Name="UserName2"
PropertyName="Text" />
</SelectParameters>
</asp:SqlDataSource>
I think the problem is simply that after you add these new values, you are not refreshing your gridview. There aren't any controls that can "automagically realize" the data has changed. Instead, you need to do it manually, by rebinding your data view control to it's (new) data with DataBind().
Check where you are getting your data.
If you have it in an if statement like
if(!IsPostBack)
That means you will only get the data when you first run. When you are navigate away and then back you are loading the page again for the first time.