Why is an action query not working in access VBA? - sql

I tested an UPDATE query in Access's query design, and it works, but when I try to use it in my module, I get the error:
Invalid SQL statement; expected... or 'UPDATE'.
My query:
strSql = "UPDATE " & rs.Fields("tableName") & _
" SET " & rs.Fields("foreignKeyName") & " = " & rsContacts.Fields("contactId") & _
" WHERE contactId = " & ContactID
rs: a table that has tableName, foriegnKeyName of the tables to update
rsContacts: a list of contactIds (currently standing on a particular one).
The actual string comes out like this:
UPDATE myTable SET ContactId = 5 WHERE contactId = 2
If the query works, and it is an action query, why am I getting this error?
This is my full code:
Public Sub updateChildTables(ByVal ContactID As Long, ByVal CompanyID As Long)
Dim strSql As String
Dim rs As Recordset
Dim rsPending As Recordset
strSql = "SELECT contactID FROM contacts _
WHERE companyId = " & CompanyID & " and contactId <> " & ContactID
Set rs = CurrentDb.OpenRecordset(strSql)
If Not (rs.BOF And rs.EOF) Then
rs.MoveFirst
strSql = "SELECT * FROM childTables"
Set rsChild = CurrentDb.OpenRecordset(strSql)
rsChild.MoveFirst
Do While Not rsChild.EOF
strSql = "UPDATE " & rsChild.Fields("tableName") & " SET " & rsChild.Fields("foreignKeyName") & " = " & rs.Fields("contactId") & " WHERE contactId = " & ContactID
DoCmd.RunSQL strSql
rs.moveNext
Loop
rsChild.Close
Set rsChild = Nothing
End If

Here is my idea for debugging and possibly even resolving this.
Create a query from within Access normally -- name it UpdateMyTable, for the sake of this example.
Then, rather than using the DoCmd, actually execute this specific query from your VBA.
Dim qry As QueryDef
strSql = "UPDATE " & rsChild.Fields("tableName") & " SET " & _
rsChild.Fields("foreignKeyName") & " = " & _
rs.Fields("contactId") & " WHERE contactId = " & ContactID
Set qry = CurrentDb.QueryDefs("UpdateMyTable")
qry.SQL = strSql
qry.Execute
The big advantage of this is that you can very easily debug this from within Access to both see the rendered SQL and manually run it / tweak it.

Related

Is there any way to get the acSysCmdInitMeter and shows it on the form?

I have the following query running in the background when the user press a button on the form.
'Insert new data
strSQL = "INSERT INTO TBL_DIRECTORS " & _
"SELECT importDirectors.* " & _
"FROM importDirectors LEFT JOIN TBL_DIRECTORS ON importDirectors.[CompanyRegNumber] = TBL_DIRECTORS.[CompanyRegNumber];"
DoCmd.RunSQL strSQL
'Update existent data
strSQL = "UPDATE TBL_DIRECTORS INNER JOIN importDirectors ON (importDirectors.[OperatorName] = " & _
"TBL_DIRECTORS.[OperatorName]) AND (importDirectors.CompanyRegNumber = TBL_DIRECTORS.CompanyRegNumber) SET "
For Each field In fields
strSQL = strSQL & strFormat("TBL_DIRECTORS.[{0}] = [importDirectors].[{1}], ", field.Name, field.Name)
Next
strSQL = Left(strSQL, InStrRev(strSQL, ",") - 1) & ";"
DoCmd.RunSQL strSQL
When the UPDATE query is running I know that we have this on the status bar:
It is a acSysCmdInitMeter.
Is there a way to get this and shows in other place, like on my form?

Error 424 object required after NULL SQL query

I am running some EXCEL VBA code to update the contents of an ACCESS database table along the lines suggested here:
IF ##Rowcount = 0 -- SQL Syntax Error in Access
. When I execute the SELECT query, EXCEL VBA gives this error message:
Run-time error 424: Object required
I extracted the SQL string from the VBA Watch window and ran it as a Query in ACCESS. The first time I did this, there were no records becasue the table was empty, so I ran the INSERT query in ACCESS and then tried running the VBA code but got the same error message.
The code is here:
Public db As DAO.Database
' Open database
Public Sub OpenMdtDatabase()
Set db = DBEngine(0).OpenDatabase("SL_MDT_data_v1.accdb")
End Sub
' Update DB table
Sub UpdateDb()
' Initialise
Dim rs As DAO.Recordset
Set xlSht = Sheets("plot_data")
' Open database
Call OpenMdtDatabase
' Get the data to store
sname = xlSht.Cells(6, "R").Value
xfill = xlSht.Cells(6, "S").Value
xedge = xlSht.Cells(6, "T").Value
xstyl = xlSht.Cells(6, "U").Value
xsize = xlSht.Cells(6, "V").Value
' SQL stuff
sqlTxtSelect = "SELECT SeriesName FROM SeriesProperties WHERE SeriesName ='" & sname & "';"
sqlTxtUpdate = "UPDATE SeriesProperties " & _
sqlTxtUpdate = "SET SeriesFill = " & xfill & ", " & _
sqlTxtUpdate = "SeriesEdge = " & xedge & ", " & _
sqlTxtUpdate = "SeriesStyle = " & xstyl & ", " & _
sqlTxtUpdate = "SeriesSize = " & xsize & " " & _
sqlTxtUpdate = "WHERE SeriesName = '" & sname & "';"
sqlTxtInsert = "INSERT INTO SeriesProperties('" & sname & "') " & _
sqlTxtInsert = "VALUES(" & xfill & ", " & xedge & ", " & xstyl & ", " & xsize & ");"
Set rs = db.OpenRecordset(sqlTxtSelect)
If rs.RecordCount = 0 Then
DoCmd.RunSQL (sqlTxtInsert)
Else
DoCmd.RunSQL (sqlTxtUpdate)
End If
End Sub
I am guessing that there is something wrong with the SQL SELECT string. I tried setting this directly using
SELECT SeriesName FROM SeriesProperties WHERE SeriesName ='14/10-2:F2F_SLMC'
but still get the same error message. I have also tried removing the colon ...
The problem lies with the statement
DoCmd.RunSQL (sqlTxtInsert)
If I change this to
db.Execute (sqlTxtInsert)
then everything is fine. Should have scrolled to the end of the answer at the original link ....

Update SQL MS Access 2010

This is wrecking my brains for 4 hours now,
I have a Table named BreakSked,
and I this button to update the table with the break end time with this sql:
strSQL1 = "UPDATE [BreakSked] SET [BreakSked].[EndTime] = " & _
Me.Text412.Value & " WHERE [BreakSked].AgentName = " & Me.List423.Value _
& " AND [BreakSked].ShiftStatus = '1'"
CurrentDB.Execute strSQL1
Text412 holds the current system time and List423 contains the name of the person.
I'm always getting this
"Run-time error 3075: Syntax Error (missing operator) in query
expression '03:00:00 am'
Any help please?
EDIT: Thanks, now my records are updating. But now its adding another record instead of updating the record at hand. I feel so silly since my program only has two buttons and I can't figure out why this is happening.
Private Sub Form_Load()
DoCmd.GoToRecord , , acNewRec
End Sub
Private Sub Command536_Click()
strSQL1 = "UPDATE BreakSked SET BreakSked.EndTime = '" & Me.Text412.Value & "',BreakSked.Duration = '" & durationz & "' " & vbCrLf & _
"WHERE (([BreakSked].[AgentID]='" & Me.List423.Value & "'));"
CurrentDb.Execute strSQL1
CurrentDb.Close
MsgBox "OK", vbOKOnly, "Added"
End Sub
Private Sub Command520_Click()
strSql = "INSERT INTO BreakSked (ShiftDate,AgentID,StartTime,Status) VALUES ('" & Me.Text373.Value & "', '" & Me.List423.Value & "', '" & Me.Text373.Value & "','" & Me.Page657.Caption & "')"
CurrentDb.Execute strSql
CurrentDb.Close
MsgBox "OK", vbOKOnly, "Added"
End Sub
You wouldn't need to delimit Date/Time and text values if you use a parameter query.
Dim strUpdate As String
Dim db As DAO.Database
Dim qdf As DAO.QueryDef
strUpdate = "PARAMETERS pEndTime DateTime, pAgentName Text ( 255 );" & vbCrLf & _
"UPDATE BreakSked AS b SET b.EndTime = [pEndTime]" & vbCrLf & _
"WHERE b.AgentName = [pAgentName] AND b.ShiftStatus = '1';"
Debug.Print strUpdate ' <- inspect this in Immediate window ...
' Ctrl+g will take you there
Set db = CurrentDb
Set qdf = db.CreateQueryDef("", strUpdate)
qdf.Parameters("pEndTime").Value = Me.Text412.Value
qdf.Parameters("pAgentName").Value = Me.List423.Value
qdf.Execute dbFailOnError
And if you always want to put the current system time into EndTime, you can use the Time() function instead of pulling it from a text box.
'qdf.Parameters("pEndTime").Value = Me.Text412.Value
qdf.Parameters("pEndTime").Value = Time() ' or Now() if you want date and time
However, if that is the case, you could just hard-code the function name into the SQL and dispense with one parameter.
"UPDATE BreakSked AS b SET b.EndTime = Time()" & vbCrLf & _
As I said in my comment you need to wrap date fields in "#" and string fields in escaped double quotes
strSQL1 = "UPDATE [BreakSked] SET [BreakSked].[EndTime] = #" & _
Me.Text412.Value & "# WHERE [BreakSked].AgentName = """ & Me.List423.Value & _
""" AND [BreakSked].ShiftStatus = '1'"

a temp table for updating the values, getting error message saying 'temp table0' already exists, how to navigate this?

I am using a VBA query in Access database for creating a temp table for updating the values, however I am getting error message saying 'temp table0' already exists, how to navigate this?
I am getting error message in 'CurrentProject.Connection.Execute strSql'
rs2.Close 'Close the recordset
Set rs2 = Nothing 'Clean up
'Create temporary tables
Dim tableFlag As String
tableFlag = "Treaty"
For x = 1 To 2
If (rs1![Prems/Claims] = "Premium") Then
If (tableFlag = "Treaty") Then
strSql = "SELECT [Premiums " & tableFlag & "].ID, [Premiums " & tableFlag & "].[Pricing Segment]"
For i = 0 To columnsCount - 1 ' loop through all boolean atributes
strSql = strSql & ", [Premiums " & tableFlag & "].[" & boolAtrName(i) & "]"
Next
strSql = strSql & " INTO [tempTable " & tablesCount & "] FROM [Premiums " & tableFlag & "] WHERE [GDS Version] = " & rs1!ID & ";"
'Execute temporary table string
CurrentProject.Connection.Execute strSql
'Add column percentage to table
CurrentDb.Execute "ALTER TABLE [tempTable " & tablesCount & "] ADD COLUMN Percentage double, Identifier Text"
'Update values in column percentage
Set rs2 = CurrentDb.OpenRecordset("SELECT * FROM [tempTable " & tablesCount & "];")

VB.net - Check SQL Field to see if Bit is Set

There is a bit field in my SQL table that I need to update to 1 if it's set at 0. I have the code written to set the field for every entry, but I need to check to see if it's at 0 already first so I can log what is changed.
Here's what I have already:
Public Function Update_User_to_TR(ByVal strUserName As String) As String
Dim myUserName As String = strUserName.Trim
Dim myReturn As String
Try
Dim sql As New SQL
Dim strQuery As String
strQuery = "Update dbo.USERS set user_field_Department_TR = 1 where USER_NAME = '" & myUserName & "'"
myReturn = sql.SQLUpdateWT(strQuery)
Catch ex As Exception
myReturn = ex.ToString
MsgBox(myReturn)
End Try
Return myReturn
End Function
You should upgrade to a stored procedure or a function, in this case, but here is a sample query.
"Declare #WillUpdate bit;Set #WillUpdate = 0;" & _
"If Exists(Select user_name from dbo.Users where user_name ='" & myUserName & _
"' and user_field_department_tr = 0 " & _
" Begin " & _
" Update dbo.USERS set user_field_Department_TR = 1 where USER_NAME = '" & myUserName & "';" & _
" Insert Into MyLog(field1, field2) " & _
" Values('sampledata', 'field was updated from 0 to 1');" & _
" End"
But please read the other comments and learn about sql injection and how it's bad, then learn how to use parameterized queries such as with ADO.NET.