User details stored in separate table ASP.NET Identity - asp.net

I am a complete beginner at ASP.net(and this forum) i am using Visual studio 2013 and have created created another table in the created database using the package manager console.
How do i go about placing the information into this new table? (I am looking to store firstname and last name in a separate table)
The create account button is below:
Protected Sub CreateUser_Click(sender As Object, e As EventArgs)
Dim userName As String = UserNameCtrl.Text
Dim Firstnane As String = firstnamectrl.Text
Dim manager = New UserManager
Dim User = New ApplicationUser() With {.UserName = userName}
Dim result = manager.Create(User, Password.Text)
If result.Succeeded Then
IdentityHelper.SignIn(manager, User, isPersistent:=False)
IdentityHelper.RedirectToReturnUrl(Request.QueryString("ReturnUrl"), Response)
Else
ErrorMessage.Text = result.Errors.FirstOrDefault()
End If
End Sub
Any pointers in the right direction, hints or suggested reading would be very helpful.

If I understand correctly, this link may be of some help:
http://www.codeguru.com/vb/gen/vb_database/adonet/article.php/c15033/A-Basic-VBNET-ADONET-Tutorial-Adding-Deleting-and-Updating.htm
It is for a windows form application, but it should translate pretty well if you're using web forms. Basically, you just want to make a connection to the database during the button click event (the simplest way I know of to make this connection is using ADO.NET), and pass the values of the first and last name in a SQL query to the sql server.
You would be building the sql query as a string, and concatenating your vb variables into that string. Something like; "Insert into table xxx(firstname, LastName) values " & Firstname & ", " & Lastname...

Related

Evaluating whether a page is the result of a referral from a particular page

I have an Edit Profile page which allows users to change their information - currently it only allows users who have a record in the table 'userprofiles' to edit their information. I want newly registered users to be able to edit their profiles as well.
At the minute, I am using the ASP.NET membership system with the appropriate asp.net_ tables in an Access database to store user credentials. The 'userprofiles' table is a separate table which has more personal information in it. There is no link between the two tables
Here is my code behind:
Protected Sub Page_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load
If IsCrossPagePostBack Then
SeparateNewUserFunction()
Return
End If
If Not IsPostBack Then
DisplayData()
SaveConfirmation.Visible = False
End If
End Sub
And here is my DisplayData() function just if anyone was interested as to what it does:
Protected Sub DisplayData()
Dim conn As OleDbConnection = New OleDbConnection(ConfigurationManager.ConnectionStrings("BookMeetConnString").ConnectionString)
Dim sql = "SELECT * FROM userprofiles WHERE TravellerName=#f1"
Dim cmd = New OleDbCommand(sql, conn)
cmd.Parameters.AddWithValue("#f1", User.Identity.Name)
conn.Open()
Dim profileDr = cmd.ExecuteReader()
profileDr.Read()
Dim newEmailAddress = ""
Dim newDescription = ""
If Not IsDBNull(profileDr("EmailAddress")) Then newEmailAddress = profileDr.Item("EmailAddress")
If Not IsDBNull(profileDr("Description")) Then newDescription = profileDr.Item("Description")
If Not IsDBNull(profileDr("AvatarURL")) Then ProfilePic.ImageUrl = profileDr.Item("AvatarURL")
description.Text = newDescription
email.Text = newEmailAddress
conn.Close()
End Sub
Rather than checking if a record exists in the 'userprofiles' table that matches the User.Identity.Name of the current user, I thought it would be easier just to evaluate whether or not the user had just been redirected from the Register.aspx page. (If this evaluation is true, then as you can see above, a separate "New User" function will be called).
That is my logic, but I have no clue if VB.NET has a "referrer" or "isReferred" expression? (at the minute as you can see I thought isCrossPagePostback might be the right thing but no luck!)
Any ideas?
You need to check whether or not a record exists and base your logic on that. That is the only right way to do it. As in:
What if you introduce a new page to handle registrations? This logic breaks.
What if you one day you retire and the next guy decides to rename the Register.aspx page? This logic breaks.
What if user hits back button and clicks the Register button again? This logic may break.
You should also consider a foreign key and unique constraint on that table, as well as using UserId instead of TravellerName. TravellerName can change, UserId will not.
... and yes you can the referring page by using HttpRequest.ServerVariables, which gets you a list of IIS Server Variables.

Checking if there is an exception coming from the server

I have an ASP.NET web application written in vb.net. I have uploaded the application on a web server in the wwroot folder and once I type in the URL with a QueryString, on page_Load it should request that QueryString and store it in the database once in Table1 and another in Table2. Well it is inserting the QueryString to Table 1 but not to Table2. The insertion code is within a Try Catch block but the problem is that I have no idea how to display a server MsgBox with the exception on the client-side.
I have also tried writing a txtFile containing any ex.message on the WebServer itself, but with no luck, even without an exception firing, the txtFile is not created I guess its a path issue. Whether to write the physical path or virtual path both tested without luck.
I am really desperate to know in anyway possible why its inserting the QueryString to Table1 and not Table2.
I am using a class.vb to insert the Querystring. On the main page, I request the QueryString which is a variable (changing) table name (Table2), pass it to a function defined in class.vb and then apply an Insert statement for a predefined un-changing table (Table1) and also using the retrieved QueryString (Table2) name to insert a date and time to both tables.
On MainPage.aspx:
Dim classOBJ AS new Projet.class1
classOBJ.Fun(Request.QueryString("Table"))
In Class1.vb:
Public Sub Fun(ByVal value As String)
Dim date_T As Date = Date.Today
Try
Using myconn As New SqlConnection(ConnString)
myconn.Open()
Dim cmd1 = New SqlCommand("INSERT INTO Table1 (Date_T,Time_T) values (#paramdate, #paramtime)", myconn)
cmd1.Parameters.AddWithValue("#paramdate", date_T)
cmd1.Parameters.AddWithValue("#paramtime", Now().ToString("HH:mm:ss"))
cmd1.ExecuteNonQuery()
cmd1.Dispose()
Dim cmd2 = New SqlCommand("Insert into [" & value & "] (Date_T, Time_T) values (#paramdate, #paramtime)", myconn)
cmd2.Parameters.AddWithValue("#paramdate", date_T)
cmd2.Parameters.AddWithValue("#paramtime", Now().ToString("HH:mm:ss"))
cmd2.ExecuteNonQuery()
cmd2.Dispose()
myconn.Close()
End Using
I am using this notation [ ] because Table's 2 name is a number.

Get Logged/Signed in Username from DefaultConnection Database VB.net 2012 ASP.NET Web Forms Application

I am a bit new to this web application stuff. When I create a new project in Visual Studios 2012 for ASP.NET Web Forms Application, it generates several predefined pages/functions. I actually want to use these functions since it seems to look like it might save me some time.
At this point I noticed how it has a Register.aspx and Login.aspx, which works fine. The Problem is that I have a database in Access 2007 with some tables. I want to know if it is possible to do one of the following and how:
1) keep the DefualtConnection database and query for the currently logged in username, to then use that usename to query my Access Database for the information based on that username.
2) Create my Own Register and Login using the Access Database. I wonder how do I keep track of the logged in user for this case and I also get an error when using the Create User Wizard
Please help, I need this information so that I can continue working on my final project. The Prof has no clue on how to do this, and I have been searching the web for and answer, however it seems like I may not be asking the right questions. Thanks in advance :)
*Edit
•What I mean by logged in user:
Picture https://dl.dropbox.com/u/22962879/Project_4_Registro_Est/Logged%20in%20user%20Project4.png
•DefaulConnection:
<add name="DefaultConnection" connectionString="Data Source=(LocalDb)\v11.0;Initial Catalog=aspnet-Project_4_Registro_Est-20130131171154;Integrated Security=SSPI;AttachDBFilename=|DataDirectory|\aspnet-Project_4_Registro_Est-20130131171154.mdf"
providerName="System.Data.SqlClient" />
•My Access Database
myConn = New System.Data.OleDb.OleDbConnection("Provider=Microsoft.ACE.OLEDB.12.0;Data Source=C:\Users\cast\Documents\test.accdb")
My Solution:
It turns out that i can get the logged in users name by calling User.Identity.Name.
So I did the following:
'//The following code is an example of using the Logged/signed in username to then'
'//Query other Databases based on the user name:'
Dim myConn As System.Data.OleDb.OleDbConnection
Dim cmd As New System.Data.OleDb.OleDbCommand
Dim sqlstring As String
'//Connecting to My Database:'
myConn = New System.Data.OleDb.OleDbConnection("Provider=Microsoft.ACE.OLEDB.12.0;Data Source=C:\Users\cast\Documents\test.accdb")
'//Query I wish to use to find all data based on User name:'
sqlstring = "Select FirstName, LastName, UserType FROM users WHERE Username = '" + User.Identity.Name + "'"
Try
'//Start by opening the connection'
myConn.Open()
'//I use str for now to store the results'
Dim str As String = ""
'//Set the command by adding the SQL string and Connection:'
cmd = New OleDb.OleDbCommand(sqlstring, myConn)
'//Create variable which contains results from Executed command:'
Dim oledbReader As OleDb.OleDbDataReader = cmd.ExecuteReader
'//Keep reading each row that contains the Queried Results:'
While oledbReader.Read
'//Store result to str. each item is a Column in the order I Queried'
str = str + (oledbReader.Item(0) & " " & oledbReader.Item(1) & " (" & oledbReader.Item(2)).ToString() & ")" + "\n"
End While
'//Show results on page's Label1:'
Label1.Text = str
'//Close everything'
oledbReader.Close()
cmd.Dispose()
myConn.Close()
Catch ex As Exception
'//show error message if could not connect'
MsgBox("Can not open connection! X_X")
End Try
This should be using SimpleMembership. So ask WebMatrix.WebData.WebSecurity.CurrentUserName. Also WebSecurity.IsAuthenticated would be good to look at.

Identity of recently added record and insert from gridview?

I am developing an ASP.Net VB Web Application
The application contains a GridView which displays the records of a user table from my created datable. The database is an Sql server database.
The code below inserts data into one table and through the built in function ##Identity to insert the most recently added record id (tt_id) from the trainingTbl table and inserting that record id into the userAssessmentTbl. Adding the identity to the second userAssessmentTbl table works fine.
Protected Sub Button1_Click(ByVal sender As Object, ByVal e As System.EventArgs)
Dim lblUsr2 As Control = FindControlRecursive(MultiTabs, "txtUsr")
Dim strQuery As String
Dim cmd As SqlCommand
strQuery = "Insert into trainingTbl(s_id, t_date, EditorId, wa_id, st_id) values(#s_id , #t_date, #EditorId, #wa_id, #st_id ) Insert into userAssessmentTbl(tt_id, UserId) values(##Identity, #UserId)"
cmd = New SqlCommand(strQuery)
cmd.Parameters.AddWithValue("#s_id", DDLCourse.Text)
cmd.Parameters.AddWithValue("#t_date", Convert.ToDateTime(txtDate.Text))
cmd.Parameters.AddWithValue("#EditorId", User.Identity.Name.ToString())
cmd.Parameters.AddWithValue("#st_id", myLblStation.Value().ToString)
cmd.Parameters.AddWithValue("#wa_id", myLblWatch.Value().ToString)
cmd.Parameters.AddWithValue("#UserId", lblUsr2.UniqueID.ToString)
InsertUpdateData(cmd)
End Sub
The issue I’m having seems to be centered on how I insert a uniqueidenifier from a GridView into a userAssessmentTbl database!
And how, I guess using a loop I can insert the UserId records from that Gridview (GridView1) into the userAssessmentTbl table along with the looped id from the ##Identity.
This part of the insert parameter seems to be incorrect:
cmd.Parameters.AddWithValue("#UserId", lblUsr2.UniqueID().ToString)
And the error I’m met with is: 'Conversion failed when converting from a character string to uniqueidentifier.'
I’ve also tried it like this:
cmd.Parameters.AddWithValue("#UserId", SqlDbType.UniqueIdentifier).Value().ToString()
And im met with the error: 'Operand type clash: int is incompatible with uniqueidentifier'
The qusetion has slightly changed to how do I Insert a String into SQL DB Where DataType Is Uniqueidentifier?
Any help will be really appreciated.
Well first of all:
##IDENTITY returns the most recently created identity for your current
connection, not necessarily the identity for the recently added row in
a table. Always use SCOPE_IDENTITY() to return the identity of the
recently added row.
Secondly, to asnwer your question:
The SQL type Uniqueidentifier and the CLR type Guid match up.
So instead of passing "#UserId" in as a parameter you need to create a Guid out of the string value.
Dim userID As Guid = New Guid(lblUsr2.UniqueID.ToString)

linq with Msaccess [duplicate]

I have a *.MDB database file, and I am wondering if it is possible or recommended to work against it using LINQ in C#. I am also wondering what some simple examples would look like.
I don't know a lot about LINQ, but my requirements for this task are pretty simple (I believe). The user will be passing me a file path to Microsoft Access MDB database and I would like to use LINQ to add rows to one of the tables within the database.
What you want is a LINQ to ODBC provider, or a LINQ to JET/OLEDB provider.
Out of the box, MS doesn't make one. There may be a 3rd party who does.
Actually I recently (today) discovered that you can access an Access database with LinqToSql. It must be in the 2002 or newer format, you will not be able to drag and drop the tables to your datacontext so either manually create the objects in your dbml or you can use SQL Server Migration for Access to move it to a sql server and then drag and drop all you want. When you want to actually create the context pass it an OleDbConnection. Use your standard Jet.OLEDB.4.0 connection string on the OleDbConnection and you are good to go. Not sure of the limitation this may incurr though. I just did a quick sample and did an OrderBy without issue.
I wrote a small sample program to test this out with David's answer. You'll need to make an access database and manually create the DBML for Linq-to-SQL, as you cannot drag 'n drop them.
Inserts fail, citing Missing semicolon (;) at end of SQL statement. but queries seem to work alright.
using System;
using System.Collections.Generic;
using System.Data.OleDb;
using System.IO;
using System.Linq;
using Linq2Access.Data;
namespace Linq2Access
{
class Program
{
static readonly string AppPath = Path.GetDirectoryName(System.Reflection.Assembly.GetExecutingAssembly().Location);
static readonly string DbPath = Path.Combine(AppPath, "Data", "database.accdb");
static readonly string DbConnString = #"Provider=Microsoft.ACE.OLEDB.12.0;Data Source='" + DbPath + "';Persist Security Info=False;";
static void Main(string[] args)
{
if (!File.Exists(DbPath))
throw new Exception("Database file does not exist!");
using (OleDbConnection connection = new OleDbConnection(DbConnString))
using (DataRepositoryDataContext db = new DataRepositoryDataContext(connection))
{
List<dbProject> projects = new List<dbProject>();
for (int i = 1; i <= 10; i++)
{
dbProject p = new dbProject() { Title = "Project #" + i };
for (int j = 1; j <= 10; j++)
{
dbTask t = new dbTask() { Title = "Task #" + (i * j) };
p.dbTasks.Add(t);
}
projects.Add(p);
}
try
{
//This will fail to submit
db.dbProjects.InsertAllOnSubmit(projects);
db.SubmitChanges();
Console.WriteLine("Write succeeded! {0} projects, {1} tasks inserted",
projects.Count,
projects.Sum(x => x.dbTasks.Count));
}
catch(Exception ex)
{
Console.WriteLine("Write FAILED. Details:");
Console.WriteLine(ex);
Console.WriteLine();
}
try
{
//However, if you create the items manually in Access they seem to query fine
var projectsFromDb = db.dbProjects.Where(x => x.Title.Contains("#1"))
.OrderBy(x => x.ProjectID)
.ToList();
Console.WriteLine("Query succeeded! {0} Projects, {1} Tasks",
projectsFromDb.Count,
projectsFromDb.Sum(x => x.dbTasks.Count));
}
catch (Exception ex)
{
Console.WriteLine("Query FAILED. Details:");
Console.WriteLine(ex);
Console.WriteLine();
}
Console.WriteLine();
Console.WriteLine("Press any key to continue...");
Console.ReadKey();
}
}
}
}
You can use a DataSet. There are linq extensions that will allow you to query the data with all that LINQ goodness we have become use to :)
eICATDataSet.ICSWSbuDataTable tbl = new eICATDataSet.ICSWSbuDataTable();
ICSWSbuTableAdapter ta = new ICSWSbuTableAdapter();
ta.Fill(tbl);
var res = tbl.Select(x => x.ProcedureDate.Year == 2010);
I have seen this question a lot and in several fora. I made a go at it and here is a complete answer for those who have been looking at it.
LinQ was not made for Access. However, many of the queries will work with Access, including delete procedure. So, according to me, there are only 2 crucial deficiencies when working with Access, which are:
not being able to save data.
not being able to drag and drop objects onto the dbml
Insert will fail with the error "missing semicolon (;)". This is because LinQ save procedure was made to save data and retrieve the primary key ID of the record saved in one go. We know that you cannot execute multiple SQL statements in Access, so that is the reason for that failure.
Update will fail with the error "record not found". An update procedure will of cause look for the record to be updated then update it. I cannot tell why it wouldn't find it, when normal LinQ query to find a record works fine.
Because there is so much benefit to use LinQ, I figured out how to work around the deficiency, while enjoy the other benefits throughout my application. This is how (NB: My codes are in VB.net, but you can convert if required):
Create the LinQ to SQL (.dbml) class to manage your LinQ against the access database, and a way to manager your save procedure. Below is the full procedures of what I created and I now work with LinQ to Access without any problems:
Add a DataGridView on a form. Add buttons for Add, Edit & Delete
Code to fill the grid:
Private Sub ResetForm()
Try
Using db As New AccessDataClassesDataContext(ACCCon)
Dim rows = (From row In db.AccountTypes
Where row.AccountTypeID > 1
Order By row.AccountTypeID Ascending
Select row).ToList()
Me.DataGridView1.DataSource = rows
End Using
Catch ex As Exception
MessageBox.Show("Error: " & vbCr & ex.ToString, "Data Error", MessageBoxButtons.OK)
End Try
End Sub
DetailForm
Code to set control values
Private Sub ResetForm()
Try
If _accountTypeID = 0 Then
Exit Sub
End If
Using db As New AccessDataClassesDataContext(ACCCon)
'Dim rows = (From row In db.AccountTypes
' Where row.AccountTypeID = _accountTypeID
' Order By row.AccountTypeID Ascending
' Select row.AccountTypeID, row.AccountType, row.LastUpdated).ToList()
Dim rows = (From row In db.AccountTypes
Where row.AccountTypeID = _accountTypeID
Select row).ToList()
For Each s In rows
Me.AccountTypeIDTextBox.Text = s.AccountTypeID
Me.myGuidTextBox.Text = s.myGuid
Me.AccountTypeTextBox.Text = s.AccountType
Me.AcHeadIDTextBox.Text = s.AcHeadID
Me.DescriptionTextBox.Text = s.Description
Me.LastUpdatedDateTimePicker.Value = s.LastUpdated
Next
End Using
Catch ex As Exception
End Try
End Sub
LinQToSQLClass
You will have to add the data objects to the dbml manually since you cannot drag and drop when using Access. Also note that you will have to set all the properties of the fields correctly in the properties windows. Several properties are not set when you add the fields.
Code to Save
Public Function SaveAccountType(Optional ByVal type As String =
"Close") As Boolean
Dim success As Boolean = False
Dim row As New AccountType
Using db As New AccessDataClassesDataContext(ACCCon)
If _accountTypeID > 0 Then
row = (From r In db.AccountTypes
Where r.AccountTypeID = _accountTypeID).ToList()(0)
If String.IsNullOrEmpty(row.AccountTypeID) Then
MessageBox.Show("Requested record not found", "Update Customer Error")
Return success
End If
End If
Try
With row
.myGuid = Me.myGuidTextBox.Text
.AccountType = Me.AccountTypeTextBox.Text
.Description = Me.DescriptionTextBox.Text
.AcHeadID = Me.AcHeadIDTextBox.Text
.LastUpdated = Date.Parse(Date.Now())
End With
If _accountTypeID = 0 Then db.AccountTypes.InsertOnSubmit(row)
db.SubmitChanges()
success = True
Catch ex As Exception
MessageBox.Show("Error saving to Customer: " & vbCr & ex.ToString, "Save Data Error")
End Try
End Using
Return success
End Function
Now replace these two lines:
If _accountTypeID = 0 Then db.AccountTypes.InsertOnSubmit(row)
db.SubmitChanges()
with something like this:
Dim cmd As IDbCommand
cmd = Me.Connection.CreateCommand()
cmd.Transaction = Me.Transaction
cmd.CommandText = query
If myGuid.Trim.Length < 36 Then myGuid = UCase(System.Guid.NewGuid.ToString())
cmd.Parameters.Add(New OleDbParameter("myGuid", row.myGuid))
cmd.Parameters.Add(New OleDbParameter("AccountType", row.AccountType))
cmd.Parameters.Add(New OleDbParameter("Description", row.Description))
cmd.Parameters.Add(New OleDbParameter("AcHeadID", row.AcHeadID))
cmd.Parameters.Add(New OleDbParameter("LastUpdated", Date.Now))
If AccountTypeID > 0 Then cmd.Parameters.Add(New OleDbParameter("AccountTypeID", row.AccountTypeID))
If Connection.State = ConnectionState.Closed Then Connection.Open()
result = cmd.ExecuteNonQuery()
cmd = Me.Connection.CreateCommand()
cmd.Transaction = Me.Transaction
cmd.CommandText = "SELECT ##IDENTITY"
result = Convert.ToInt32(cmd.ExecuteScalar())
The last part of the code above is what gets you the ID of the record saved. Personally, I usually make that an option, because I don't need it in most of the cases, so I don't need to add that overhead of fetching back data every time a record is saved, I am happy just to know a record was saved.
That is the overhead added to LinQ, which causes Insert to fail with Access. Is it really necessary to have it? I don't think so.
You may have noted that I normally put my Update and Insert procedures together, so that saves me time and has address both the Insert & Update procedures in one go.
Code for Delete:
Private Sub DelButton_Click(sender As Object, e As EventArgs) Handles DelButton.Click
Using db As New AccessDataClassesDataContext(ACCCon)
Dim AccountTypeID As Integer = Me.DataGridView1.CurrentRow.Cells(0).Value
Dim row = From r In db.AccountTypes Where r.AccountTypeID = AccountTypeID
For Each detail In row
db.AccountTypes.DeleteOnSubmit(detail)
Next
Try
db.SubmitChanges()
Catch ex As Exception
' Provide for exceptions.
MsgBox(ex)
End Try
End Using
End Sub
Now you can enjoy LinQ to Access! Happy coding :)
LINQ to SQL only works for SQL Server databases. What you need is the Microsoft Entity Framework. This makes object oriented access to your mdb. From this you can run LINQ queries.
http://msdn.microsoft.com/en-us/library/aa697427(vs.80).aspx

Resources