Azure SQL Database with Access Frontend - Active Directory Authentication - ms-access

I have a MS Access database serving as the frontend for an Azure SQL Server backend. I need to use both an ADO and an ODBC connection string for different functions (perform backend tasks, link frontend tables). I'm using Azure Active Directory Interactive authentication. The first time each of these connection strings is used in the frontend, it prompts the user to enter their Microsoft password (so the user is always entering the password twice - once for ADO, and again for ODBC). I've looked around for an answer but couldn't seem to find one - I just want to allow the user to authenticate a single time for each session.
There are other questions on SO about how to use Azure AD to connect Access to a SQL Server DB, but they don't answer this specific problem since I'm already connecting successfully.
I use a ConnectionString function to pass in "ADO" or "ODBC" depending on what I need. Here are the connection strings (both of them work).
Select Case connectionType
Case "ADO":
ConnectionString = "Provider=MSOLEDBSQL19;" & _
"Data Source=" & serverName & ";" & _
"Initial Catalog=" & databaseName & ";" & _
"Authentication=ActiveDirectoryInteractive;" & _
"User ID=" & userEmail & ";" & _
"Use Encryption for Data=true;"
Case "ODBC":
ConnectionString = "ODBC;" & _
"DRIVER=ODBC Driver 17 for SQL Server;" & _
"SERVER=" & serverName & ";" & _
"DATABASE=" & databaseName & ";" & _
"UID=" & userEmail & ";" & _
"Authentication=ActiveDirectoryInteractive;" & _
"Encrypt=yes;"
End Select
I've tried changing the ODBC connection string to Authentication=ActiveDirectoryIntegrated (no password entry), but it doesn't work. In this scenario the users will NOT be able to just use their Windows credentials because of the way their company security is set up. I also can't use a hardcoded username/password in this case.
Any suggestions would be appreciated as this is functional but definitely a headache for users!

Thank you #June7 - you put me on track to come up with this solution. I used "ActiveDirectoryPassword" as the auth type but it kept throwing errors related to invalid credentials. I played around with some options and ultimately this solves the problem: use Interactive authentication for the first (ADO) connection, then use Integrated for the second (ODBC) connection. Since the user is authenticated after the first connection, the second one doesn't ask for any inputs.
Select Case connectionType
Case "ADO":
ConnectionString = "Provider=MSOLEDBSQL19;" & _
"Data Source=" & serverName & ";" & _
"Initial Catalog=" & databaseName & ";" & _
"Authentication=ActiveDirectoryInteractive;" & _
"User ID=" & userEmail & ";" & _
"Use Encryption for Data=true;"
Case "ODBC":
ConnectionString = "ODBC;" & _
"DRIVER=ODBC Driver 17 for SQL Server;" & _
"SERVER=" & serverName & ";" & _
"DATABASE=" & databaseName & ";" & _
"UID=" & userEmail & ";" & _
"Authentication=ActiveDirectoryIntegrated;" & _
"Encrypt=yes;"
End Select

Related

Pulling information to unbound fields

I am trying to pull data from an unlinked table to a form with unbound fields. I already have a form where you enter the data and send it to the table but this is to be able to pull it back and update.
This is what I have
DoCmd.RunSQL "SELECT * " & _
" FROM [" & Address & "].[BusinessAccountOpening]" & _
" WHERE [ID]= " & Me![txtID] & ""
Forms!frm_ViewUpdateRecords!Sub_Details.Form.subaddthedata
But getting the error. An RunSQL action requires an argument consisting of an sql statement.
Please help
DoCmd.RunSQL and CurrentDb.Execute are for action queries (delete, update, append) while you present a select query.
So call DoCmd.OpenQuery ... or assign the records to a recordset.

Re Share File on Network

I currently use the VB6 CompactDatabase method to compact a .mdb (Access DB) file and have searched high and low for a way to reapply the Share Permissions on Original DB using VB6.
The CompactDatabase code:
Set jro = CreateObject("jro.JetEngine")
If IsObject(jro) Then
jro.CompactDatabase _
"Provider=Microsoft.Jet.OLEDB.4.0;Data Source=" & sourcePath & _
";Jet OLEDB:Database Password=" & DBPassword, _
"Provider=Microsoft.Jet.OLEDB.4.0;Data Source=" & tmpPath & _
";Jet OLEDB:Database Password=" & DBPassword & _
";Jet OLEDB:Encrypt Database=True;Jet OLEDB:Engine Type=5;"
Else
compactDB = "Compact Failed: MDAC not installed correctly - missing JRO.JETENGINE"
End If
This compacts to new DB and sequence is to Delete the original and rename new to old.
Problem with this is that new file does not have original Share Permissions, Currently set to 'Everyone' with 'Full Control'. I have found code on how to set permissions on folders but not directly to files.
Any help would be appreciated.
For anyone who is interested I have found the resolution.
In original code; by using a temp path "C:\temp" to create the new '.mdb' and then copying it over to my Program Files directory; I actually inherited the Permissions of "temp" folder.
I changed the Temp file name to be in same directory as current DB and when process is complete new .mdb has full permissions as with Old.mdb.
Cheers

Issue with connecting MySQL to VB.NET when multiple users

I'm doing a computing project in VB.NET which requires a user to login before the application runs. I also need to use databases throughout so my weapon of choice was MySQL.
This is the code I am using for when the user presses the login button which connects and opens the database.
Private Sub btnLogin_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles btnLogin.Click
MySqlConn.ConnectionString = "server=localhost;" _
& "user id=" & txtUsername.Text & ";" _
& "password=" & txtPassword.Text & ";" _
& "database=main"
Try
MySqlConn.Open()
MessageBox.Show("Connection successful!")
Catch ex As Exception
MessageBox.Show("Cannot connect to the database: " & ex.Message)
End Try
End Sub
This is all well and fine but when I want to execute querys later (and in different forms) etc I will have to pretty much write the same code again. I thought of putting it in a seperate class and calling it when I needed but I couldn't see how it could grab the details form the text box for the connnection string. And I cant use static parameters as their could be use multiple users.
Thanks in advance,
Robin
You can create MySqlConn as a global, that way it can be seen from anywhere in your application.
http://msdn.microsoft.com/en-us/library/ms973875.aspx
Once you've connected (using the user name and password) you shouldn't need to reference the text boxes again.

How to use MS Access SaveAsText with Queries (specifically Stored Procedures)

I have read every question on this site having to do with SaveAsText (and other version-control-with-Access related questions).
The most helpful one so far was this one. I am using a slightly modified version of the VBScript code posted in Oliver's answer to save my objects as text files. My application is an .adp, and the database (which obviously includes the Stored Procedures) is SQL Server 2005.
I have attempted to add this code to my VBScript, but I consistently get an error that says "You have cancelled the previous operation" when the SaveAsText line is hit.
For Each myObj In oApplication.CurrentData.AllStoredProcedures
WScript.Echo " " & myObj.fullname
oApplication.SaveAsText acQuery, _
myObj.fullname, _
sExportpath & "\" & myObj.fullname & ".sql"
dctDelete.Add "RE" & myObj.fullname, acQuery
Next
Based on the response in this question, I made sure to add
Const acQuery = 1
to the top of the file.
Also, this code
For i = 0 To oApplication.CurrentDatabase.QueryDefs.Count - 1
oApplication.SaveAsText acQuery, _
oApplication.CurrentDatabase.QueryDefs(i).Name, _
sExportpath & "\" & db.QueryDefs(i).Name & ".sql"
Next i
did not work, but I believe that was intended for a .mdb anyway, not an .adp. Is there any solution for exporting StoredProcedures (and Views or Table definitions, while we're at it) to text files?
It probably doesn't have anything to do with mdb vs adp. When I try the following in an mdb, I get the same error message.
MsgBox Application.CurrentData.AllStoredProcedures.Count
I suspect that it is doing that because MS Access doesn't know the underlying structure of the SQL database is. And really, why should it care, and why would the DB tell your app what it looks like under the covers? The stored procedures run entirely on the DB side and knows nothing about the MS Access app, and the views are just that a view (or presentation of) the data. As far as I know, you can't manipulate either from within MS Access.
What I think you are trying to do is automate an export of the sql scripts necessary to recreate your database, and store them in some sort of version control system. The folks on Serverfault might have a convenient solution for that.
As for SaveAsText, unfortunately it is an undocumented method. I've used the following for exporting Queries
''...
Dim db As Database
Set db = CurrentDb()
Dim Qry As QueryDef
For Each Qry In db.QueryDefs
strObjectName = Qry.Name
If Not (strObjectName Like "~sq_*") Then
Debug.Print " - " & strObjectName
Application.SaveAsText acQuery, strObjectName, _
MY_PATH & "queries_" & strObjectName & ".txt"
End If
Next
''...
TableDef's were a little different (couldn't get SaveAsText/LoadAsText to work properly)
For Each Tbl In db.TableDefs
If Tbl.Attributes = 0 Then 'Ignores System Tables
strObjectName = Tbl.Name
Debug.Print " - " & strObjectName
Application.ExportXML acExportTable, strObjectName, , _
MY_PATH & "tables_" & strObjectName & ".xsd"
End If
Next

mysql datareader

I am using MySql 5.0. I using Mupliple datareader in same connection i get error message. Is possible to use multiple Datareader in same connection?
I using Mysql Connection is
MySqlConn.ConnectionString = "SERVER=" & gServerName & ";DATABASE=" & DBname & ";user=" & gUserName & ";password=" & gPassword & ";MultipleActiveResultSets=True"
MySqlConn.Open()
Please Help Me
The DataReader usually (excluding SQL Server 2005+) requires a connection all to itself while it is Executing. Until the DataReader's Close method is called, the connection cannot be used by anything else including another DataReader.
However, you can use the DataReader's NextResult method to let it process multiple sets of records one after another.