VBScript how to set the connection string - sql-server-2005

I am not sure whether it has been disscussed before or not but I have the following code (I changed from example for an Access database.)
I don't know what to put inside the 'Provider' and the 'Data Source'. I'm using MS SQL Server 2005 and how to find this information in my machine? Please, even I try to follow from here http://www.connectionstrings.com/, yet I still don't know how to do it.
Dim conn, sql
sql = "SELECT * FROM tblOutbox"
Set conn = CreateObject("ADODB.Connection")
With conn
.Provider = "myProvider"
.Mode = adModeReadWrite
.ConnectionString = "Data Source=mysource;" & _
"database=myDbase.mdf; "
.Open
End With
If conn.State = adStateOpen Then
WScript.Echo "Connection was established."
End If
conn.Close
Set conn = Nothing
here is using access database:
Dim conn
Dim sql
sql = "SELECT * FROM tblOutbox"
Set conn = CreateObject("ADODB.Connection")
With conn
.Provider = "Microsoft.Jet.OLEDB.4.0"
.Mode = adModeReadWrite
.ConnectionString = "Data Source= f:/Status.mdb"
.Open
End With
WScript.Echo "Connection was opened."
conn.Close
Set conn = Nothing
WScript.Echo "Connection was closed."

Try setting the provider in the connection string
conn.ConnectionString = "Provider=SQLOLEDB.1;Data Source=XXX;Initial Catalog=XXX;User ID=<XXX>;Password=<XXX>;"
Note: I haven't tested it but it should work

For all your connection string needs: http://www.connectionstrings.com/

I finally found the solution thanks to your help.
Under the Administrative Tools, Data Source (ODBS), driver tabs, I use provider: SQLNCLI, my Server: Data Source, and I add Recordset rs to the code. It seems that, without this one, the connection is not established. I don't know what happened.
Dim conn , rs, sql, ConnString
sql = "SELECT * FROM tblOutbox"
Set rs = CreateObject("ADODB.Recordset")
Set conn = CreateObject("ADODB.Connection")
With conn
.Provider = "SQLNCLI"
.Mode = adModeReadWrite
.ConnectionString = "SERVER=.\SQLExpress;AttachDbFilename=F:\Test2.mdf;Database=Test2.mdf; Trusted_Connection=Yes;"
.Open
WScript.Echo "Connection was established."
End With
rs.Open sql,conn
If conn.State = adStateOpen Then
WScript.Echo "Connection was established."
Else
WScript.Echo "No Connection ."
End If
rs.Close
Set rs = Nothing
conn.Close
Set conn = Nothing

With SQL Server you don't connect directly to the file. Access, being a file-based RDBMS is a little different.
Following your example, it would look something like this:
Dim conn, sql
sql = "SELECT * FROM tblOutbox"
Set conn = CreateObject("ADODB.Connection")
With conn
.Mode = adModeReadWrite
.ConnectionString = "Provider=SQLOLEDB;server=[servername];database=[databasename]uid=[insertuser];pwd=[insertpassword];"
.Open
End With
If conn.State = adStateOpen Then
WScript.Echo "Connection was established."
End If
conn.Close
Set conn = Nothing
There's usually a more compact way of doing this, but without the context its hard to give a better example

Related

VBA Runtime Error when connection to SQL Database

I'm trying to connect to a SQL Server from multiple PCs in the same domain.
When using the following code:
Dim conn As ADODB.Connection
Set conn = New ADODB.Connection 'Neue Verbindung initialisieren
'Verbindung einrichten'
conn.ConnectionString = "PERSIST SECURITY INFO=True;Provider=SQLOLEDB.1;Server=WWDDB;Database=01Projekt;User ID=XXX;Password=XXX;Trusted_Connection=True;Integrated Security=SSPI;"
conn.Open
conn.Open returns the error:
Error on login for the user 'XXXX'
The issue is because you are using a named user with Integrated Security. These two modes are incompatible.
Try removing Integrated Security=SSPI:
conn.ConnectionString = "PERSIST SECURITY INFO=True;Provider=SQLOLEDB.1;Server=WWDDB;Database=01Projekt;User ID=XXX;Password=XXX;Trusted_Connection=True;" conn.Open
Or the named user:
conn.ConnectionString = "PERSIST SECURITY INFO=True;Provider=SQLOLEDB.1;Server=WWDDB;Database=01Projekt;Trusted_Connection=True;Integrated Security=SSPI;" conn.Open
this is my snippet, try it :
Set cnConn = New ADODB.Connection
With cnConn
.Provider = "SQLOLEDB.1"
.CursorLocation = adUseClient
.ConnectionTimeout = 0
.Properties("Data Source").Value = ' serverName
.Properties("Password").Value = ' pswd
.Properties("User ID").Value = ' userName
.Properties("Initial Catalog").Value = ' init DB
.Open
End With

If i create a disconnected ADO recordset from scratch in VBA how do i set the base table information for UpdateBatch?

I have been using disconnected recordsets for a few weeks now, typically retrieving data from SQL Server, disconnecting the rs and filtering/formatting in VBA. Now i'm trying to do the reverse and create a new ADO recordset from scratch, and then connect it to my database and use UpdateBatch to insert the recordset into the database without using a loop. I have a fully populated recordset at this point, hooked it back up to my connection string, and try UpdateBatch. Understandably, it has no information at this point about what table I'm trying to update (only Data Source and Initial Catalog via the connection string). Is there a recordset property that I use to provide the table in question? Additionally, the table I'm trying to import into has a GUID field (first field) that I have left blank on purpose in my disconnected recordset assuming that upon import, SQL Server would assign this GUID/primary key automatically.
The specific error I'm getting after "rs.UpdateBatch" is
Run-time error '-2147467259 (80004005)'"
Insufficient base table information for updating or refreshing.
I know I could use a loop and a SQL command "INSERT INTO ...". I'd like to use a recordset object though since those provide much more functionality as a container for data. One thing I haven't tried is to first retrieve a recordset from the table in question, then clear it and re-populate it with the new data so that the recordset itself retains all of the original database and table properties. If that's the only/best approach I can try that route too. I just wanted to see if it was possible to create an ADO recordset, populate it, and then insert it into a matching table of my choice.
dim rs as ADODB.Recordset
set rs = New ADODB.Recordset
With rs.Fields
.append "alias", adVarChar, 255
.append "textA", adVarChar, 255
.append ......
End With
rs.Open
rs.AddNew Array(0, 1, 2, ..., n), Array(val0, val1, val2, ..., valn)
rs.Update
call importRS(rs)
rs.close
set rs = nothing
After rs.update above some recordsets may need to go to a database, other recordset objects are just used to expedite filtering and sorting so I just use them as a convenient container and they'd never go to importRS()
However, IF I need to send the disconnected recordset to a database, i'd like to just pass the recordset object to another function that serves the purpose of opening the connection, sending the update, and closing the connection. The code below would serve that purpose which is why i'd like to wait to establish a connection until this point, right at the end after my rs is populated.
sub importRS(byref rs as ADODB.Recordset)
dim cn as ADODB.Connection
set cn = New ADODB.Connection
cn.ConnectionString = strConnection 'my connection string variable'
cn.Open
rs.ActiveConnection = cn
rs.UpdateBatch '-------error message appears on this line
cn.close
set cn = nothing
You can get the data, (wherever it may be) into an array and add to the recordset using a loop. Then then when the loop is finished, you do rs.updatebatch as follows:
Private Sub SaveToSQLSever()
Dim lngLastRow As Long
Dim arrySheet As Variant
Dim rs As ADODB.Recordset
Dim cn As ADODB.Connection
Dim strCn As String
Set cn = New ADODB.Connection
Set rs = New ADODB.Recordset
strCn= "Provider=VersionOfSQL;User ID=*********;Password=*********;"
& _ "Data Source=ServerName;Initial Catalog=DataBaseName"
cn.Open strCn
On Error Goto exiting
'*********************************************************
'If the data is coming from a sheet
'Set to your Range
With Sheets("SheetName")
lngLastRow = .Range("A2").CurrentRegion.Rows _
(.Range("A2").CurrentRegion.Rows.Count).Row
arrySheet = .Range("A1:G" & lngLastRow).Value2
End With
'Else populate the array and pass it to this Sub
'*************************************************************
'Note the property parameters
'.Source = Table That you want to populate
With rs
.ActiveConnection = cn
.Source = "Select * from TableName"
.CursorType = adOpenDynamic
.CursorLocation = adUseClient
.LockType = adLockBatchOptimistic
.Open
End With
For i = LBound(arrySheet,1) To UBound(arrySheet,1)
rs.AddNew
For j = LBound(arrySheet,2) To UBound(arrySheet,2)
rs.Fields(j).Value = arrySheet(i,j)
Next j
rs.MoveNext
Next i
rs.UpdateBatch 'Updates the table with additions from the array
i = 0
'******************************************************************
'Note that you can also refer to the Field Names Explicitly Like So:
For i = LBound(arryData,1) To UBound(arryData,1)
With rs
.AddNew
.Fields("FieldName1").Value = arryData(i,1)
.Fields("FieldName2").Value = arryData(i,2)
.Fields("FieldName3").Value = arryData(i,3)
.Fields("FieldName4").Value = arryData(i,4)
.Fields("FieldName5").Value = arryData(i,5)
.Fields("FieldName6").Value = arryData(i,6)
.Fields("FieldName7").Value = arryData(i,7)
End With
Next i
rs.UpdateBatch
'******************************************************************
MsgBox "The data has successfully been saved to the SQL Server", _
vbInformation + vbOKOnly,"Alert: Upload Successful"
exiting:
If cn.State > 0 Then cn.Close
If rs.State > 0 Then rs.Close
Set cn = Nothing
Set rs = Nothing
End Sub
Edit: As per OP's request to pass an existing recordset to a SQL table, below should do so:
Private Sub SendRcrdsetToSQL(ByRef rsIn As ADODB.Recordset)
Dim arrySheet As Variant
Dim rsSQL As ADODB.Recordset
Dim cn As ADODB.Connection
Dim strCn As String
Set cn = New ADODB.Connection
strCn= "Provider=VersionOfSQL;User ID=*********;Password=*********;"
& _ "Data Source=ServerName;Initial Catalog=DataBaseName"
cn.Open strCn
On Error Goto exiting
Set rsSQL = New ADODB.Recordset
With rsSQL
.ActiveConnection = cn
.Source = "Select * from TableName"
.CursorType = adOpenDynamic
.CursorLocation = adUseClient
.LockType = adLockBatchOptimistic
.Open
End With
'disconnect the recordset and close the connection
Set rsSQL.ActiveConnection = Nothing
cn.Close
Set cn = Nothing
rsIn.MoveFirst
rsSQL.MoveLast
'Add the records from the passed recordset to the SQL recordset
Do While Not rsIn.EOF
With rsSQL
.AddNew
.Fields("FieldName1").Value = rsIn.Fields("FieldName1").Value
.Fields("FieldName2").Value = rsIn.Fields("FieldName2").Value
.Fields("FieldName3").Value = rsIn.Fields("FieldName3").Value
.Fields("FieldName4").Value = rsIn.Fields("FieldName4").Value
.Fields("FieldName5").Value = rsIn.Fields("FieldName5").Value
.Fields("FieldName6").Value = rsIn.Fields("FieldName6").Value
.Fields("FieldName7").Value = rsIn.Fields("FieldName7").Value
End With
rsIn.MoveNext
Loop
rsSQL.UpdateBatch
MsgBox "The data has successfully been saved to the SQL Server", _
vbInformation + vbOKOnly,"Alert: Upload Successful"
exiting:
If cn.State > 0 Then cn.Close
If rsIn.State > 0 Then rsIn.Close
If rsSQL.State > 0 Then rsSQL.Close
Set cn = Nothing
Set rsIn = Nothing
Set rsSQL = Nothing
End Sub
The only way I was able to get this to work was by running a query to build the structure of my Recordset. So your code becomes something like this:
Private Sub Command1_Click()
Dim cn As ADODB.Connection
Set cn = New ADODB.Connection
cn.ConnectionString = "<your connection string>"
cn.CursorLocation = adUseClient
cn.Open
Dim rs As ADODB.Recordset
Set rs = New ADODB.Recordset
Set rs.ActiveConnection = cn
rs.Open "select * from states where 1<>1", , adOpenStatic, adLockBatchOptimistic
rs.AddNew Array("Abbrev", "Name", "Region", "SchoolDataDirect"), Array("TN", "TestName", "MyRegion", 1)
Set rs.ActiveConnection = Nothing
cn.Close
ImportRS rs
End Sub
Private Sub ImportRS(ByRef rs As ADODB.Recordset)
Dim cn As ADODB.Connection
Set cn = New ADODB.Connection
cn.ConnectionString = "<your connection string>"
cn.CursorLocation = adUseClient
cn.Open
Set rs.ActiveConnection = cn
rs.UpdateBatch
Set rs.ActiveConnection = Nothing
cn.Close
End Sub

Select Statement for Excel Datasource

I am connected to Excel sheet, which is acting as database. I need to select some records with where condition but I am getting error:
No value given for one or more required parameters
by using below code:
Dim conn As Object
Dim rs As ADODB.Recordset
Set rs = New ADODB.Recordset
Set conn = CreateObject("ADODB.Connection")
XLName = "C:\Users\X\Desktop\rawdata.xlsx"
connString = "Provider=Microsoft.ACE.OLEDB.12.0;Data Source='" &
XLName & "';Extended Properties='Excel 12.0;HDR=NO;IMEX=1';"
conn.Open connString
rs.Open ("SELECT * FROM [data$] where industry='Government'"), conn,
adOpenDynamic, adLockReadOnly
Sheet1.Range("A2").CopyFromRecordset rs
rs.Close
conn.Close
When you set HDR=NO the column titles from the excel table will be ignored and it will be used internal names. See older answer: c#, oledb connection string issue

VBA. Cant get data from .mdb file. Operation is not allowed when object is closed

Here is my problem: I need to get data from .mdb file that is on the network hard drive. I am using ADODB to connect to it, but when i try to return field value from RecordSet that i created it returns error:
Operation is not allowed when the object is closed
Here is my code:
Dim rs As New ADODB.Recordset
Dim cmd As New ADODB.Command
cmd.ActiveConnection = "Provider=Microsoft.Jet.OLEDB.4.0;Data Source=" & dbPath & ".mdb"
cmd.CommandText = SQLRequst
cmd.CommandType = adCmdText
cmd.CommandTimeout = 900
rs.CursorLocation = adUseClient
rs.Open cmd, , adOpenForwardOnly, adLockReadOnly
Debug.Print rs.Fields(0)
Set cmd.ActiveConnection = Nothing
Set cmd = Nothing
Set rs.ActiveConnection = Nothing
At the moment i tried many different types of connection. The main thing thats makes me confused is that it connects to .mdb file and also creates RecordSet but most values are set to "Operation is not allowed when object is closed"
I think the problem is with the way i am connecting and getting records sets because I use same method to connect to sql database and it works just fine.
Any help will be appreciated
*Edited : SQLRequest = "SELECT * FROM tblStack WHERE StackID=XXXXX"
Changed code to this:
Dim rs As New ADODB.Recordset
Dim conn As New ADODB.Connection
conn.Open "Provider=Microsoft.Jet.OLEDB.4.0;Data Source=" & dbPath & ".mdb"
rs.Open SQLRequst, conn, adOpenForwardOnly, adLockReadOnly
Debug.Print rs.Fields(0)
Set cmd.ActiveConnection = Nothing
Set cmd = Nothing
Set rs.ActiveConnection = Nothing
Still debug doesn't print anything and in Locals window shows that Fields(0).Value Operation is not allowed when the object is closed
Problem was in SQLRequst string :
SQLRequest = "SELECT * FROM tblStack WHERE StackID='XXXXX'"
It needed ''.

VBA in Access 2010 - Run-time Error 430

I’m getting a Run-time error '430': Class does not support Automation or does not support expected interface" on this line of code Set Me.lstResults.Recordset = rs or this Set Me![frmM_SearchForDocumentsSubForm].Form.Recordset = rs. I am trying to get the ADO Recordset based on a SQL stored procedure to appear in an unbound Listbox or Subform of an Access form. I’m on Win 7 Machine using Access 2010 connecting to SQL Server 2008:
On_Click event:
Private Sub cmdRun_Click()
'On Error Resume Next
Dim strSQL As String
'Stored procedure + parameters called from form
strSQL = "Exec sqlsp_searchalltables " & Me.txtTables & _
", " & "'%" & Me.txtSearchTerm & "%'"
OpenMyRecordset rs, strSQL
'debug - view procedure
Me.lblQuery.Caption = strSQL
Me.Repaint
Set Me.lstResults.Recordset = rs
'or this
'Set Me![frmM_SearchForDocumentsSubForm].Form.Recordset = rs
End Sub
I found some solutions for this error on the web and tried all of them to no avail. Most suggested checking the references which I did and verified.
I am able to successfully connect to the SQL server and have the results display in both a Listbox and Subform when I use DAO Querydef and a passthrough query or if I use this .listbox method:
With Me.lstResults
Do
strItem = rs.Fields("CLIENT_ID").Value
.AddItem strItem
rs.MoveNext
Loop Until rs.EOF
End With
I would prefer not to use the DAO method because I found I need the coding flexibility of ADO especially with connecting to multiple Recordsets in SQL. Thoughts?
FYI: My OpenMyRecordset public function in Module:
Option Compare Database
Option Explicit
Global con As New ADODB.Connection
Global rs As ADODB.Recordset
Global NoRecords As Boolean
Public Enum rrCursorType
rrOpenDynamic = adOpenDynamic
rrOpenForwardOnly = adOpenForwardOnly
rrOpenKeyset = adOpenKeyset
rrOpenStatic = adOpenStatic
End Enum
Public Enum rrLockType
rrLockOptimistic = adLockOptimistic
rrLockReadOnly = adLockReadOnly
End Enum
Public Function OpenMyRecordset(rs As ADODB.Recordset, strSQL As String, Optional rrCursor As rrCursorType, _
Optional rrLock As rrLockType, Optional bolClientSide As Boolean) As ADODB.Recordset
If con.STATE = adStateClosed Then
con.ConnectionString = "ODBC;Driver={SQL Server};Server=mysqlsvr;DSN=RecordsMgmt_SQLDB;UID=XXX;Trusted_Connection=Yes;DATABASE=RecordsManagementDB;"
con.Open
End If
Set rs = New ADODB.Recordset
With rs
.ActiveConnection = con
.CursorLocation = adUseClient
.CursorType = IIf((rrCursor = 0), adOpenDynamic, rrCursor)
.LockType = IIf((rrLock = 0), adLockOptimistic, rrLock)
.Open strSQL
If .EOF And .BOF Then
NoRecords = True
Exit Function
End If
End With
End Function
You definitely do not have to do the looping method to just to populate the listbox. I'm not familiar with the OpenMyRecordset command you used, but I suspect that something in its functionality is what is causing this error (i.e., it's not opening the recordset in a manner compatible with the listbox). This is how I connected to a local instance of SQL Server Express and was able to populate a listbox.
Dim cn As ADODB.Connection
Dim rs As ADODB.Recordset
Set cn = New ADODB.Connection
With cn
.ConnectionString = _
"Provider=SQLOLEDB;Data Source=localhost\SQLEXPRESS;" & _
"Initial Catalog=Northwind;Trusted_Connection=yes"
.Open
End With
Set rs = New ADODB.Recordset
With rs
Set .ActiveConnection = cn
.Source = "SELECT FirstName, LastName FROM Employees"
.LockType = adLockOptimistic
.CursorType = adOpenKeyset
.Open
End With
Set Me.lstTest.Recordset = rs
Set rs = Nothing
Set cn = Nothing
You will have to make sure that you have the Microsoft ActiveX Data Objects Library reference enabled in your project.