Executing a stored procedure on pervasive server - vba

I have a stored procedure on my Pervasive Server called EGC_Expl_BOM_TT and I can execute it with "CALL EGC_Expl_BOM_TT('B-8579-K')" in my SQL query window within Excel, however it will perform the function and then through me an error forcing me to back out of the query window. I found the below VBA code which is designed to execute a stored procedure. I need help adapting it to me specific need. My stored procedure has only one variable input, which I will put in sheet 1 cell A1.
This is my connection string from my Excel query window. I need help formatting it in the VBA code:
Provider=MSDASQL.1;Persist Security Info=True;Extended Properties="DSN=global_EGC;ServerName=fah2.1583;UID=UserIDName;PWD=password;ArrayFetchOn=1;ArrayBufferSize=8;TransportHint=TCP;DBQ=GLOBALEGC;ClientVersion=11.31.017.000;CodePageConvert=1252;PvClientEncoding=CP1252;PvServerEncoding=CP1252;AutoDoubleQuote=0;"
Function Sproc()
Dim cnn As ADODB.Connection
Dim rst As ADODB.Recordset
Dim cmd As ADODB.Command
Dim ConnectionString As String
Dim StrSproc As String
Set cnn = New ADODB.Connection
cnn.ConnectionString = "Provider=MSDASQL.1;DSN=global_EGC;ServerName=fah2.1583;UID=Myusername;PWD=mypassword;ArrayFetchOn=1;ArrayBufferSize=8;TransportHint=TCP;DBQ=GLOBALEGC;ClientVersion=11.31.017.000;CodePageConvert=1252;PvClientEncoding=CP1252;PvServerEncoding=CP1252;AutoDoubleQuote=0;"
'Opens connection to the database
On Error GoTo SQL_ConnectionError
cnn.Open ConnectionString
On Error GoTo 0
'Timeout error in seconds for executing the entire query; this will run for 15 minutes before VBA timesout, but your database might timeout before this value
cnn.CommandTimeout = 900
Set rst = New ADODB.Connection
StrSproc = "set nocount on; "
StrSproc = "CALL EGC_Expl_BOM_TT" + Cells(1, 1)
rst.ActiveConnection = cnn
On Error GoTo SQL_StatementError
rst.Open StrSproc
On Error GoTo 0
If Not rst.EOF And Not rst.BOF Then
Sproc = IIf(IsNull(rst.Fields(0).Value), "(BLANK)", rst.Fields(0).Value)
End If
Exit Function
SQL_ConnectionError:
MsgBox "Error connecting to the server / database. Please check the connection string."
Exit Function
SQL_StatementError:
MsgBox "Error with the SQL syntax. Please check StrSproc."
Debug.Print StrSproc
Exit Function
SQL_ConnectionError:
Msgbox "Error connecting to the server / database. Please check the connection string."
Exit Function
SQL_StatementError:
Msgbox "Error with the SQL syntax. Please check StrSproc."
Debug.Print StrSproc
Exit Function
End Function

The connection string would be something like:
cnn.ConnectionString = "Provider=MSDASQL.1;DSN=global_EGC;ServerName=fah2.1583;UID=UserIDName;PWD=password;ArrayFetchOn=1;ArrayBufferSize=8;TransportHint=TCP;DBQ=GLOBALEGC;ClientVersion=11.31.017.000;CodePageConvert=1252;PvClientEncoding=CP1252;PvServerEncoding=CP1252;AutoDoubleQuote=0;"
Your statement would be something like:
StrSproc = "EXEC EGC_Expl_BOM_TT" + Cells(1,1)

Related

VBA SQL: Runtime Error 3704, how can I fix this?

I am trying to run a SQL Query through VBA. (I'm new to VBA)
P.s I have searched so much online but no solution has helped just yet.
I have copied the code from another excel (which works flawlessly) but my SQL Query involves temp tables and the other doesn't (this used to work on previous files that had temp tables). For some reason it just fails and I get the following error on the following line:
Error: 3704 Operation is not allowed when the object is closed'
' Check we have data for OrderIDs.
If Not rsfswdata.EOF Then
My full VBA code;
Dim conn As ADODB.Connection
Dim rsfswdata As ADODB.Recordset
Dim sConnString As String
' Create the connection string.
sConnString = "Provider=SQLOLEDB;Data Source=server001;" & _
"Initial Catalog=Dev;" & _
"Integrated Security=SSPI;"
' Create the Connection and Recordset objects.
Set conn = New ADODB.Connection
Set rs = New ADODB.Recordset
'To wait till the query finishes without generating error
conn.ConnectionTimeout = 0
'To wait till the query finishes without generating error
conn.CommandTimeout = 0
' Open the connection and execute.
conn.Open sConnString
Set rsfswdata = conn.Execute(Sheets("SQL Query").Range("A1").Value)
' Check we have data for OrderIDs.
If Not rsfswdata.EOF Then
' Transfer result.
Sheets("test").Cells(3, 2).CopyFromRecordset rsfswdata
' Close the recordset
rsfswdata.Close
Else
MsgBox "Error: No records returned.", vbCritical
End If
' Clean up
If CBool(conn.State And adStateOpen) Then conn.Close
Set conn = Nothing
Set rsfswdata = Nothing
End Sub

Check the permission of user when calling `ADODB.connection.open`

I was stucked for many week on the following :
I need to delete and insert to SQL database using VBA Excel.
The code used to connect to database is :
sConnString= "string for the connexion to the database"
conn.Open sConnString, "username", "password"
Debug.Print conn.State
Here the answer is 1, which according to the Microsoft documentation, means that the connexion is opened.
Then I try to execute an SQL query, using the following code :
varSQL = "DELETE FROM mytable WHERE specificColumn = '" & specificVariable & "'"
Set Command1 = New ADODB.Command
With Command1
.ActiveConnection = conn
.CommandType = adCmdText
End With
With Command1
.CommandText = varSQL
.Execute NbRecordsAffected
End With
This returns access denied for the DELETE query
I want to know if the user with username has the permission to do the query, so I can be sure that the error comes form another thing
Thank you in advance
Consider capturing the more informative error via the ADO error collections using VBA error handling where you may receive if using an SQL Server database:
The DELETE permission was denied on the object 'mytable', database 'mydatabase' schema dbo
Sub Run_SQL()
On Error GoTo ErrorHandle
Dim conn As ADODB.Connection, Command1 AS ADODB.Command
'...your full code...
ExitHandle:
' RELEASE RESOURCES
Set Command1 = Nothing: Set conn = Nothing
Exit Sub
ErrorHandle:
' RAISE EVERY CONNECTION ERROR
Dim myError As ADODB.Error
For Each myError In conn.Errors
Msgbox myError.Number & " - " & myError.Description, "RUNTIME ERROR", vbCritical
Next myerror
Resume Exit_Handle
End Sub

VBS Script to Execute SQL statement?

To open, I have never written a vbs script. I have written many SQL scripts, views, developed databases. I have written plenty of VBA in Access applications.
For this, I am just trying to set up a SQL script as a VBS script, so the users don't have to go into SSMS to run it. They can just double-click the VBS script, specify the server and database when prompted, and the quick script will run for them.
This is what I have gotten so far, but I keep getting Microsoft VBScript compilation errors. The latest one is line 3 char 17, which is on a Dim statement. Just wanted to see if anyone can tell if I am missing something fundamental to this script, that is preventing it from compiling or processing correctly.
This is the very short script:
Dim conn
Set conn = createobject("Adodb.Connection")
Dim sConnString As String
Dim SqlStatement As String
sSourceServer = InputBox ("Enter the name of the SQL Server","Enter SQL Server Name","")
If Len(sSourceServer) = 0 Then
MsgBox "No SQL Server was specified.", , "Unable to Continue"
Exit Sub
End if
sSourceDB = InputBox ("Enter the name of the Law SQL Database","Enter Law SQL DB Name","")
If Len(sSourceDB) = 0 Then
MsgBox "No SQL DB was specified.", , "Unable to Continue"
Exit Sub
End if
' Create the connection string.
sConnString = "Provider=SQLOLEDB;Data Source=" & sSourceServer & "; Initial Catalog=" & sSourceDB & "; Integrated Security=SSPI;"
MsgBox sConnString
' Open the connection and execute.
conn.Open sConnString
conn.CommandTimeout = 900
SqlStatement = "UPDATE [tablename] " & _
"SET UUID = CASE WHEN CHARINDEX('.',[Filename]) > 1 THEN LEFT(CAST([Filename] AS VARCHAR),CHARINDEX('.',[Filename])-1) ELSE [Filename] END " & _
"WHERE [Filename] IS NOT NULL"
conn.Execute(SqlStatement)
conn.Close
Set rs = Nothing
SqlStatement = vbNullString
MsgBox "All Done! Go Check your results!"
If anyone can help, I'd greatly appreciate it.
Thank you
nevermind. I kept troubleshooting and finally got it to work. For those that this might help, unlike VBA, it's easier not to declare variables as a type. just Dim them and move on. see below:
Dim conn
Set conn = createobject("Adodb.Connection")
Dim sConnString
Dim SqlStatement
StartScript
Sub StartScript()
sSourceServer = InputBox ("Enter the name of the SQL Server","Enter SQL Server Name","")
If Len(sSourceServer) = 0 Then
MsgBox "No SQL Server was specified.", , "Unable to Continue"
Exit Sub
End if
sSourceDB = InputBox ("Enter the name of the Law SQL Database","Enter Law SQL DB Name","")
If Len(sSourceDB) = 0 Then
MsgBox "No SQL DB was specified.", , "Unable to Continue"
Exit Sub
End if
' Create the connection string.
sConnString = "Provider=SQLOLEDB;Data Source=" & sSourceServer & "; Initial Catalog=" & sSourceDB & "; Integrated Security=SSPI;"
' Open the connection and execute.
conn.Open sConnString
conn.CommandTimeout = 900
SqlStatement = "UPDATE [tablename] " & _
"SET UUID = CASE WHEN CHARINDEX('.',[Filename]) > 1 THEN LEFT(CAST([Filename] AS VARCHAR),CHARINDEX('.',[Filename])-1) ELSE [Filename] END " & _
"WHERE [Filename] IS NOT NULL"
conn.Execute(SqlStatement)
conn.Close
Set rs = Nothing
SqlStatement = vbNullString
End Sub
MsgBox "All Done! Go Check your results!"
Remember, for those looking to use this as a basis for a script - I'm not doing any checks, so if you don't know your data, this is a dangerous thing to run.
Know your data, backup your data, and if you can, add in some checks, to make sure anything that isn't a select statement, is checked and re-checked before it is run.

Else Portion of Code keeps timing out

I have a code to check the connection between access and sql server upon opening the form. If there is a connection a message box pops up and says so. If not there is supposed to be a message box indicating there is no connection. Instead I get the error:
Run Time Error '-2147467259 (80004005)':
[DBNETLIB][ConnectionOpen (Connect()).]Specified SQL Server Not Found
Which is not what I am wanting it to do, is it something in my coding or is there no way to get this to work?
Public Sub AutoExec()
Dim cnn As ADODB.Connection
Dim localrst As New ADODB.Recordset
Dim remoterst As New ADODB.Recordset
Set cnn = New ADODB.Connection
cnn.Open "Provider=SQLOLEDB; Data Source=DB; Initial Catalog=HRLearnDev;" _
& "User Id=ID; Password=PW;"
If cnn.State = adStateOpen Then
MsgBox ("You have an established connection with the L&TD SQL Server Database.")
Else
MsgBox ("Cannot connect to remote server. Data will be stored locally to CDData Table until application is opened again.")
End If
cnn.Close
End Sub
In situations like these, you typically want to use an On Error GoTo construct - then send the code to your error handler if an error occurs (you can test to make sure the error number is what you expect with Err.Num).
However, in your case it may be even easier to use On Error Resume Next. This tells the interpreter "If an error occurs, go to the next line. I will figure out what went wrong and deal with it."
You usually do this when you have a single function call that either produces an error or a sensible value. I often do something like this:
On Error Resume Next
returnValue = -1
returnValue = functionThatReturnsPositiveValue()
If returnValue < 0 Then
MsgBox "oops - the function failed!"
Else
' <<<< do whatever needs doing >>>>
End If
In your case that's almost exactly what you would do. Complete example:
Public Sub AutoExec()
Dim cnn As ADODB.Connection
Dim localrst As New ADODB.Recordset
Dim remoterst As New ADODB.Recordset
On Error Resume Next ' <<<<<< add this line so an error doesn't stop the code
Set cnn = New ADODB.Connection
cnn.State = 0 ' <<<<< not sure if you need something like this, or if the New command
already set it to some sensible value other than "adStateOpen"
cnn.Open "Provider=SQLOLEDB; Data Source=DB; Initial Catalog=HRLearnDev;" _
& "User Id=ID; Password=PW;"
If cnn.State = adStateOpen Then ' <<<<<< this will only be true if no error occurred
MsgBox ("You have an established connection with the L&TD SQL Server Database.")
Else
MsgBox ("Cannot connect to remote server. Data will be stored locally to CDData Table until application is opened again.")
End If
On Error GoTo 0 ' <<<<<<<< turn off error handling - we have passed the "tricky" spot.
' <<<<<< lots more code goes here >>>>>>
If cnn.State = adStateOpen Then cnn.Close ' <<<<<<<< only close connection if it was open!!
End Sub

Query regarding dsn string

Below is the code to fill a list box in a VBA application :
Private Sub Form_Open(Cancel As Integer)
''#Populate list box control.
Dim cnn As ADODB.Connection
Dim strSQL As String
Dim rst As ADODB.Recordset
Dim strList As String
On Error GoTo ErrHandler
''#Use DSN to Northwind.
''#Modify connection and connection string as needed.
Set cnn = New ADODB.Connection
cnn.Open "DSN=NorthwindExample"
strSQL = "SELECT * FROM Shippers"
Set rst = New ADODB.Recordset
rst.Open strSQL, cnn
strList = rst.GetString(adClipString, , ";", ",")
Debug.Print strList
Me.lstShippers.RowSource = strList
rst.Close
cnn.Close
Set rst = Nothing
Set cnn = Nothing
Exit Sub
ErrHandler:
MsgBox Err.No & ": " & Err.Description, vbOKOnly, "Error"
Set rst = Nothing
Set cnn = Nothing
End Sub
I need to know what i need to put as DSN string? Where will I get the info?
What is adClipString here in this code?
Is there any option to populate list control without using DSN connection object since I am taking the values from the same access table?
Here is a link that contains the different connection strings for Access:
http://www.connectionstrings.com/access
Something like this should work: Provider=Microsoft.Jet.OLEDB.4.0;Data Source=C:\mydatabase.mdb;User Id=admin;Password=;
Im not sure what adClipString is, it could be an undeclared variable or database column?
Matt
Here is the info on adClipString.
Basically, GetString method gets the content of the entire recordset into a string variable where columns will be separated by ";" and rows will be separated by "," (as per your code).
Regarding DSN - see Start -> Settings -> Control Panel -> Administrative Tools -> Data Sources (ODBC). One of the tab (I guess System DSN) is where ODBC based data source can be created and are listed.