Storing another control value in a field of DetailsView Insert Interface - asp.net

I have an asp.net program.
Here I want to keep Insert Facility of the Details view. But in the interface I want to keep the 'UserName' attribute of the new Record as fixed and same as the UserName of the Logged in user. I also want to check it on Server side whether it corresponds to the logged in user's username.
How can I achieve this functionality.
I have made the BoundField ReadOnly. But I can't find anything else suitable for this functionality.

In your .aspx do the following:
<asp:SqlDataSource ID="SqlDataSource1" runat="server" OnInserting="SqlDataSource1_Inserting">
<InsertParameters>
<asp:Parameter Type="String" Name="Username" />
//Place other parameters here
</InsertParameters>
</asp:SqlDataSource>
In your code behind:
protected void SqlDataSource1_Inserting(object sender, SqlDataSourceCommandEventArgs e)
{
SqlDataSource1.InsertParameters["Username"].DefaultValue = Context.User.Identity.Name;
}

Related

How to properly use Session Parameters in asp.net

I am not even sure how SessionParameters are meant to be used as opposed to a normal Parameters. What I am trying to do is Update or Insert records into my database based on a value from a Session variable "StaffID", which I know exists (based on debugging the PageLoad event). As it turns out my "StaffID" session is actually NULL (found after exhaustive debugging) and I get exceptions about trying to update a table with null values.
My SqlDataSource is thus ...
<asp:SqlDataSource ID="SqlDataProgmDetails" runat="server" ConnectionString="<%$ ConnectionStrings:ATCNTV1ConnectionString %>"
UpdateCommand="UPDATE tblStudentProgramReg SET StaffModified = #StaffModified, DateModified = GETDATE() WHERE (ProgramEnrolmentID = #ProgramEnrolmentID)">
<UpdateParameters>
<asp:Parameter Name="EnrolmentDate" Type="DateTime" />
<asp:Parameter Name="StudentProgramNotes" Type="String" />
<asp:Parameter Name="TerminationDate" Type="DateTime" />
<asp:Parameter Name="StudProgEnrolStatusID" />
<asp:Parameter Name="QualificationCode" />
<asp:ControlParameter ControlID="gvPrograms" Name="ProgramEnrolmentID" Type="Int32" PropertyName="SelectedValue" />
<asp:SessionParameter Name="StaffModified" SessionField="StaffID" />
</UpdateParameters>
rs>
</asp:SqlDataSource>
When I UPDATE my DetailsView I get the dreaded "String or binary data would be truncated.
The statement has been terminated." error.
I know this is happening because the "StaffID" session variable that I am sure existed at one point is NULL in the UPDATE phase of the above SqlDataSource.
The only way around it I found was to force load the value in CodeBehind ...
protected void SqlDataProgmDetails_Updating(object sender, SqlDataSourceCommandEventArgs e)
{
if (Session["StaffID"] != null)
{
e.Command.Parameters[5].Value = Session["StaffID"].ToString().Trim();
}
}
protected void SqlDataProgmDetails_Inserting1(object sender, SqlDataSourceCommandEventArgs e)
{
if (Session["StaffID"] != null)
{
e.Command.Parameters[8].Value = Session["StaffID"].ToString().Trim();
}
}
But why should I have to do this?
I would have thought the StaffID should have loaded automatically as per the SessionParameter request in my ASP page.
Like I said, I am not sure how SessionParameters (or Session variables work) in general, so if someone could please explain why I have to use codebehind to get this to work, that would be appreciated?
Thank you
The Session object is in fact an IDictionary<string, object>, which is persisted for you. It is persisted per-session. When a new session begins, the client receives a cookie from the server with a unique session identifier.
On each subsequent request the client sends the cookie to the server and in the global.asax the Session dictionary is repopulated. So let's say that in a code-behind you do Session[UserId] when the user authenticates, on each subsequent request you could do var UserId = Session[UserId] and as long as the session is "alive", you will receive the value you stored.
Restoring values from session as you have done is very logical. Since HTTP is state-less, Session is one of the mechanisms for simulating statefulness.

SqlDataSource won't retrieve logged in user's data from database?

I tried retrieving the user's data based on the logged in UserId, but no progress. Any suggestions?
protected void SqlDataSource1_Selecting(object sender, SqlDataSourceSelectingEventArgs e)
{
// Get a reference to the currently logged on user
MembershipUser currentUser = Membership.GetUser();
// Determine the currently logged on user's UserId value
Guid currentUserId = (Guid)currentUser.ProviderUserKey;
// Assign the currently logged on user's UserId to the #UserId parameter
e.Command.Parameters["#UserId"].Value = currentUserId;
}
And this is the SqlDataSource
<asp:SqlDataSource ID="SqlDataSource1" runat="server"
ConnectionString='<%$ ConnectionStrings:NaviConnectionString %>'
SelectCommand="SELECT [UserId], [FirstName], [LastName] FROM [UserProfiles] WHERE ([UserId] = #UserId)">
<SelectParameters>
<asp:Parameter Name="UserId" Type="String"></asp:Parameter>
</SelectParameters>
</asp:SqlDataSource>
And this is the GridView
<asp:GridView ID="GridView1" runat="server" AutoGenerateColumns="False"
DataKFFeyNames="UserId" DataSourceID="SqlDataSource1"
EmptyDataText="There are no data records to display."
DataKeyNames="UserId">
<Columns>
<asp:BoundField DataField="UserId" HeaderText="UserId" SortExpression="UserId" />
<asp:BoundField DataField="FirstName" HeaderText="FirstName" SortExpression="FirstName" />
<asp:BoundField DataField="LastName" HeaderText="LastName" SortExpression="LastName" />
</Columns>
</asp:GridView>
There are no data records to display.
However, when I execute the code in query builder, it works.
So I need to get the UserId manually from the database.
Then go to the query builder then execute then paste the userid in to the value of UserID.
Then it displays the correct data based on the UserId:
I also tried changing it to this:
<SelectParameters>
<asp:Parameter Name="UserId" Type="Empty" DbType="Guid"></asp:Parameter>
</SelectParameters>
You should set a break point and see if currentUserId is populated. I believe that it is. If so, then retrieving the UserId is not the problem, but instead the problem is setting the parameter value or selecting the data.
I think you need to change the type of your parameter from string to Guid
<SelectParameters>
<asp:Parameter Name="UserId" Type="Guid"></asp:Parameter>
</SelectParameters>
Just Change This:
protected void SqlDataSource1_Selecting(object sender, SqlDataSourceSelectingEventArgs e)
{
// Get a reference to the currently logged on user
MembershipUser currentUser = Membership.GetUser();
// Determine the currently logged on user's UserId value
Guid currentUserId = (Guid)currentUser.ProviderUserKey;
// Assign the currently logged on user's UserId to the #UserId parameter
e.Command.Parameters["#UserId"].Value = currentUserId.ToString();
}
in parameter types there is no guid option. (Also in above codes sql data source has not been set SqlDataSource1_Selecting.) How could it be answer? Just declare parameter name and its ok.
<asp:Parameter Name="UserId"></asp:Parameter>

Passing C# variable into aspx Source Sql Query

I'm trying to do a messaging system where the inbox is a gridview of all the messages associated with a user's ID. I have a global get method in C# to get the user currently signed in. I'm wondering how to tie this back so that the database only shows the data I want it to.
In my .aspx.cs file, I have something like:
protected void Page_Load(object sender, EventArgs e)
{
int userInSess = getLoggedInUser();
Session["user"] = user;
}
In the source file, I have something like:
<asp:SqlDataSource ID="ProjectDB" runat="server"
ConnectionString="<%$ ConnectionStrings:ProjectConnectionString %>"
SelectCommand="SELECT [SentByUserName], [Subject], [CreateDate] FROM [Messages] WHERE (ReceivedByUserID = #user) ORDER BY [CreateDate] DESC">
<SelectParameters>
<asp:SessionParameter Name = "user" />
</SelectParameters>
</asp:SqlDataSource>
I know this is wrong but I can't seem to find clear answer on how to exactly do this. Any help would be greatly appreciated.
Thanks
You need to reference the value stored in the session with:
<asp:SessionParameter Name="User" SessionField="user" />
Note the addition of SessionField attribute.
SqlDataSource control only uses Name="User" of the Parameter object to match a #user placeholder in SQL query

GridView and DropDownlist

I have a gridview that when enter to edit mode one of the column change to dropdownlist:
<EditItemTemplate>
<asp:DropDownList ID="DropDownList2" runat="server"
DataSourceID="SqlDataSource1" DataTextField="name" DataValueField="name">
</asp:DropDownList>
</EditItemTemplate>
Now i have a SqlDataSource with update method that define in this aspx file:
<UpdateParameters>
<asp:Parameter Name="name" Type="String" />
<asp:ControlParameter ControlID="DropDownList2" Type="string"
PropertyName="SelectedValue" Name="genre" />
</UpdateParameters>
now i want to get the selected value and insert it but when i press the Update button in the row in the gridview i get this error:
Could not find control 'DropDownList2' in ControlParameter 'genre'
any idea why it happen?
Yes. ControlParameters only work when the DOM can find the control you're referring to that's within the same branch of the GridView. The problem is that Gridviews are a poor way of handling DOM controls because as soon as you go into a "mode" of the GridView like the EDIT mode, the entire DOM structure changes. The DOM by the way, is the Document Object Model. Because it's changed, therefore ASP cannot find the control you're referring to.
I've overcome this by doing one of two things.
First see if it works by simply tailing the control name with the '$' character.
<UpdateParameters>
<asp:Parameter Name="name" Type="String" />
<asp:ControlParameter ControlID="MyGridView$DropDownList2" Type="string"
PropertyName="SelectedValue" Name="genre" />
</UpdateParameters>
This sometimes works if you're lucky.
If not, then you'll need to find the control, get its value and pass it into the SQL parameter programmatically in code behind.
Try something like this (I use C#) ...
protected void MyGridView_RowUpdating(object sender, GridViewUpdateEventArgs e)
{
...
GridViewRow gvRow = (GridViewRow)sender;
DropDownList myDDL = (DropDownList)gvRow.FindControl("DropDownList2");
if (myDDL != null)
{
//assuming your datasource is outside the gridview, you have to find it!
SqlDataSource sds1 = (SqlDataSource)page.FindControl("myDataSource");
if (sds1 != null)
{
sds1.UpdateParameter["genre"].DefaultValue = myDDL.SelectedValue;
... and do your databinding etc
sds1.Update();
}
}
}
I always rely on the client-side code (ASPX) to do most of the work for me, like Bind(), Eval(), etc, but over time you'll realise that to really control your program, you'll have to rely on JavaScript or code behind to do the finer bits. ASP is not always "clever" in doing what you expect it to do.

Pass a this.property to ObjectDataSource

A user control contains a ListView, ObjectDataSource and a CustomerID property, is there a way to pass CustomerID to ObjectDataSource.
it seems ControlParameter does not fix the problem.
Regards
ControlParameter must be used for to get a parameter from a Control. To get a parameter from a property you have to get it from code behind:
<asp:ObjectDataSource OnSelecting="OdsOnSelecting" .... >
<SelectParameters>
<asp:Parameter Name="CustomerID" />
</SelectParameters>
</asp:objectDataSource>
protected void OdsOnSelecting(object sender, ObjectDataSourceMethodEventArgs e) {
e.InputParameters["CustomerID"] = CustemerID;
}
Respond to this event:
http://msdn.microsoft.com/en-us/library/system.web.ui.webcontrols.objectdatasource.objectcreating.aspx
Try creating an attribute/property for the usercontrol in question, THEN do what is mentioned in the two post before this one...

Resources