473,385 Members | 1,813 Online
Bytes | Software Development & Data Engineering Community
Post Job

Home Posts Topics Members FAQ

Join Bytes to post your question to a community of 473,385 software developers and data experts.

How to pass Parameter Value in Query via VBA

124 100+
I have a saved query (q_StdDegReqAll) that has one parameter (WHERE StdDegReq.StdDegReqId = lngStdDegReqId). I want to pass a value into this parameter in vba. I have the following code:

Expand|Select|Wrap|Line Numbers
  1. Dim lngStdDegReqId As Long
  2. Dim qd1 As DAO.QueryDef
  3.  
  4. Set qd1 = CurrentDb.QueryDefs("q_StdDegReqAll")
  5. qd1.Parameters(lngStdDegReqId) = lngStdDegReqId
  6.  
  7. DoCmd.OpenQuery "q_StdDegReqAll", , "acReadOnly"
  8.  
When I execute the code I get the error: "Item not found in this collection". It's referring to my 4th line. I do not know what I am doing wrong.
May 6 '10 #1

✓ answered by Jim Doherty

@bullfrog83
Sorry....... have been absent and very busy last couple of days.....

OK you are using the DoCmd.OpenQuery statement. The arguments for that action do not include a capability ie an 'argument' in itself to pass parameters (as would appear logical, given parameters do tend to go hand in hand with queries) I agree with Neopa in that, it is somewhat lacking in that area. It is not like the OpenForm method for instance where you can pass an sql string as a WHERE clause or a filter or openargs for a form.

The DoCmd.OpenQuery command is designed to open a saved query but as you know many queries have parameters attached to them. The general rule of thumb if you want to open a query using the parameters AS IS is to open a recordset in code by reference to the QUERYDEFS collection. You then manipulate any dataset using recordset code. An example of this would be as follows:

Expand|Select|Wrap|Line Numbers
  1. Dim MyDb as DAO.Database
  2. Dim Myqdf as DAO.QueryDef
  3. Dim rst as DAO.Recordset
  4. Dim MyQueryName As String
  5. Dim strSurname as String
  6.  
  7. MyQueryName = "qryPeople"
  8. strSurname="Lennon"
  9.  
  10. set MyDb =CurrentDb()
  11. Set Myqdf = MyDb.QueryDefs(MyQueryName)
  12. qdf.parameters("Surname")=strSurname
  13. 'Open a recordset on this query
  14. set rst=Myqdf.OpenRecordset()
  15. Do While Not rst.EOF
  16.  
  17. 'your code sequence goes here
  18. Loop
  19.  
  20. rst.Close
  21. Myqdf.Close
  22. MyDB.Close
  23. rst=Nothing
  24. Myqdf=Nothing
  25. Mydb=Nothing
The other method is to build your SQL on the fly in your form code assigning elements for any WHERE clause and then use this to set the recordsource of a form.

If you merely want to use and open the the query itself you might want to consider using a function to pass back values to your parameter query. Your form code could set the criteria and pass this to a global variable. A Function could pick up on that global variable and pass the value to the query. The below function can be pasted into a new module


Expand|Select|Wrap|Line Numbers
  1. Global MY_INTEGER As Integer
  2. Global MY_LONG As Long
  3. Global MY_STRING As String
  4. Global MY_BOOLEAN As Boolean
  5.  
  6. Function GetMyInteger() As Integer
  7. GetMyInteger = MY_INTEGER
  8. End Function
  9. Function GetMyString() As Integer
  10. GetMyString = MY_STRING
  11. End Function
  12. Function GetMyBoolean() As Integer
  13. GetMyBoolean = MY_BOOLEAN
  14. End Function
To implement the above functions you would merely replace your 'square bracketed' parameters in your query in the query grid and instead use a function call ie:

GetMyLongInteger()

(Remember you are explicitly setting the value of your global variable from your form code) so in your particular specific example case, your current DoCmd.Openquery command program flow could still be used


Expand|Select|Wrap|Line Numbers
  1. MY_LONG=7
  2. DoCmd.OpenQuery "q_StdDegReqAll", , "acReadOnly"

So your current query amended SQL would look like this...

Expand|Select|Wrap|Line Numbers
  1. SELECT StdDegReq.StdDegReqId, Cl.StdDegReqDiscId AS DiscId, D.SortOrder AS DiscSortOrder, D.CreditMin AS DiscCreditMin, D.CourseMin AS DiscCourseMin, Cr.StdDegReqClassId AS ClassId, Cl.SortOrder AS ClassSortOrder, Cl.CreditMin AS ClassCreditMin, Cl.CourseMin AS ClassCourseMin, Cr.StdDegReqCourseId AS CourseId, Cr.Course, Cr.SortOrder AS CourseSortOrder, T.Event_Id AS TakenCourse, T.Credit_Grade 
  2. FROM (((StdDegReq INNER JOIN StdDegReqDisc AS D ON StdDegReq.StdDegReqId=D.StdDegReqId) INNER JOIN StdDegReqClass AS Cl ON D.StdDegReqDiscId=Cl.StdDegReqDiscId) INNER JOIN StdDegReqCourse AS Cr ON Cl.StdDegReqClassId=Cr.StdDegReqClassId) LEFT JOIN t_TranscriptDetail AS T ON Cr.TakenCourseId=T.TranscriptDetailId 
  3. WHERE StdDegReq.StdDegReqId=GetMyLongInteger()
  4. ORDER BY D.SortOrder, Cl.SortOrder, Cr.SortOrder; 
Hope this helps you a little and yes I know this is workaround material :)

13 62233
Jim Doherty
897 Expert 512MB
@bullfrog83
Yes.

qd1.Parameters(lngStdDegReqId) = lngStdDegReqId

Passing lngStdDegReqId unto itself? where is lngStdDegReqId defined value
May 6 '10 #2
bullfrog83
124 100+
Sorry. It's defined at the beginning of the routine where a value is passed into it:

Public Sub procEvaluateDegReq(lngStdDegReqId As Long)
May 6 '10 #3
NeoPa
32,556 Expert Mod 16PB
This is a tricky area. Parameters in a Recordset are transitory. They do not get saved with any QueryDef you may be accessing in your Recordset.

Your line #5 (I assume to be the one that fails) would only set the parameter for use by qd1. The subsequent call to open the QueryDef would not have any reference to the parameter in qd1. Does that make sense?
May 6 '10 #4
NeoPa
32,556 Expert Mod 16PB
Sorry. It's defined at the beginning of the routine where a value is passed into it:

Public Sub procEvaluateDegReq(lngStdDegReqId As Long)
I believe Jim was referring to the name of the QueryDef's parameter.

Do you have the SQL for that to view?
May 6 '10 #5
bullfrog83
124 100+
@NeoPa
I'm assuming you mean the SQL to the query? If so, here it is:

Expand|Select|Wrap|Line Numbers
  1. SELECT StdDegReq.StdDegReqId, Cl.StdDegReqDiscId AS DiscId, D.SortOrder AS DiscSortOrder, D.CreditMin AS DiscCreditMin, D.CourseMin AS DiscCourseMin, Cr.StdDegReqClassId AS ClassId, Cl.SortOrder AS ClassSortOrder, Cl.CreditMin AS ClassCreditMin, Cl.CourseMin AS ClassCourseMin, Cr.StdDegReqCourseId AS CourseId, Cr.Course, Cr.SortOrder AS CourseSortOrder, T.Event_Id AS TakenCourse, T.Credit_Grade
  2. FROM (((StdDegReq INNER JOIN StdDegReqDisc AS D ON StdDegReq.StdDegReqId=D.StdDegReqId) INNER JOIN StdDegReqClass AS Cl ON D.StdDegReqDiscId=Cl.StdDegReqDiscId) INNER JOIN StdDegReqCourse AS Cr ON Cl.StdDegReqClassId=Cr.StdDegReqClassId) LEFT JOIN t_TranscriptDetail AS T ON Cr.TakenCourseId=T.TranscriptDetailId
  3. WHERE StdDegReq.StdDegReqId=lngStdDegReqId
  4. ORDER BY D.SortOrder, Cl.SortOrder, Cr.SortOrder;
May 6 '10 #6
bullfrog83
124 100+
@NeoPa
I think so. So, is there not a way to pass a parameter value into a query via vba?
May 6 '10 #7
NeoPa
32,556 Expert Mod 16PB
I see no parameters in your query at all. This would certainly explain the error message.
May 6 '10 #8
NeoPa
32,556 Expert Mod 16PB
I think so. So, is there not a way to pass a parameter value into a query via vba?
If I read you aright (Query here referring to a QueryDef opened in data view on the screen as opposed to into a recordset in your code), then no. i don't believe there is. Something I always thought was a strange omission if I'm honest.
May 6 '10 #9
bullfrog83
124 100+
@NeoPa
The parameter is lngStdDegReqId in the WHERE clause. When I execute the query it prompts me to enter a value for it.
May 6 '10 #10
NeoPa
32,556 Expert Mod 16PB
You need to use the PARAMETERS declaration. You can find details in the help system under Microsoft Jet SQL Reference.
Expand|Select|Wrap|Line Numbers
  1. PARAMETERS name datatype [, name datatype [, ...]]
May 7 '10 #11
Jim Doherty
897 Expert 512MB
@bullfrog83
Sorry....... have been absent and very busy last couple of days.....

OK you are using the DoCmd.OpenQuery statement. The arguments for that action do not include a capability ie an 'argument' in itself to pass parameters (as would appear logical, given parameters do tend to go hand in hand with queries) I agree with Neopa in that, it is somewhat lacking in that area. It is not like the OpenForm method for instance where you can pass an sql string as a WHERE clause or a filter or openargs for a form.

The DoCmd.OpenQuery command is designed to open a saved query but as you know many queries have parameters attached to them. The general rule of thumb if you want to open a query using the parameters AS IS is to open a recordset in code by reference to the QUERYDEFS collection. You then manipulate any dataset using recordset code. An example of this would be as follows:

Expand|Select|Wrap|Line Numbers
  1. Dim MyDb as DAO.Database
  2. Dim Myqdf as DAO.QueryDef
  3. Dim rst as DAO.Recordset
  4. Dim MyQueryName As String
  5. Dim strSurname as String
  6.  
  7. MyQueryName = "qryPeople"
  8. strSurname="Lennon"
  9.  
  10. set MyDb =CurrentDb()
  11. Set Myqdf = MyDb.QueryDefs(MyQueryName)
  12. qdf.parameters("Surname")=strSurname
  13. 'Open a recordset on this query
  14. set rst=Myqdf.OpenRecordset()
  15. Do While Not rst.EOF
  16.  
  17. 'your code sequence goes here
  18. Loop
  19.  
  20. rst.Close
  21. Myqdf.Close
  22. MyDB.Close
  23. rst=Nothing
  24. Myqdf=Nothing
  25. Mydb=Nothing
The other method is to build your SQL on the fly in your form code assigning elements for any WHERE clause and then use this to set the recordsource of a form.

If you merely want to use and open the the query itself you might want to consider using a function to pass back values to your parameter query. Your form code could set the criteria and pass this to a global variable. A Function could pick up on that global variable and pass the value to the query. The below function can be pasted into a new module


Expand|Select|Wrap|Line Numbers
  1. Global MY_INTEGER As Integer
  2. Global MY_LONG As Long
  3. Global MY_STRING As String
  4. Global MY_BOOLEAN As Boolean
  5.  
  6. Function GetMyInteger() As Integer
  7. GetMyInteger = MY_INTEGER
  8. End Function
  9. Function GetMyString() As Integer
  10. GetMyString = MY_STRING
  11. End Function
  12. Function GetMyBoolean() As Integer
  13. GetMyBoolean = MY_BOOLEAN
  14. End Function
To implement the above functions you would merely replace your 'square bracketed' parameters in your query in the query grid and instead use a function call ie:

GetMyLongInteger()

(Remember you are explicitly setting the value of your global variable from your form code) so in your particular specific example case, your current DoCmd.Openquery command program flow could still be used


Expand|Select|Wrap|Line Numbers
  1. MY_LONG=7
  2. DoCmd.OpenQuery "q_StdDegReqAll", , "acReadOnly"

So your current query amended SQL would look like this...

Expand|Select|Wrap|Line Numbers
  1. SELECT StdDegReq.StdDegReqId, Cl.StdDegReqDiscId AS DiscId, D.SortOrder AS DiscSortOrder, D.CreditMin AS DiscCreditMin, D.CourseMin AS DiscCourseMin, Cr.StdDegReqClassId AS ClassId, Cl.SortOrder AS ClassSortOrder, Cl.CreditMin AS ClassCreditMin, Cl.CourseMin AS ClassCourseMin, Cr.StdDegReqCourseId AS CourseId, Cr.Course, Cr.SortOrder AS CourseSortOrder, T.Event_Id AS TakenCourse, T.Credit_Grade 
  2. FROM (((StdDegReq INNER JOIN StdDegReqDisc AS D ON StdDegReq.StdDegReqId=D.StdDegReqId) INNER JOIN StdDegReqClass AS Cl ON D.StdDegReqDiscId=Cl.StdDegReqDiscId) INNER JOIN StdDegReqCourse AS Cr ON Cl.StdDegReqClassId=Cr.StdDegReqClassId) LEFT JOIN t_TranscriptDetail AS T ON Cr.TakenCourseId=T.TranscriptDetailId 
  3. WHERE StdDegReq.StdDegReqId=GetMyLongInteger()
  4. ORDER BY D.SortOrder, Cl.SortOrder, Cr.SortOrder; 
Hope this helps you a little and yes I know this is workaround material :)
May 7 '10 #12
When assigning parameters, you need to refer to the parameter name

I think your your line:
Expand|Select|Wrap|Line Numbers
  1. qd1.Parameters(lngStdDegReqId) = lngStdDegReqId
should be
Expand|Select|Wrap|Line Numbers
  1. qd1.Parameters("StdDegReqId") = lngStdDegReqId
Here's a good resource for queries including VBA code for parameters:
http://www.fmsinc.com/tpapers/querie...ningParameters
May 9 '10 #13
bullfrog83
124 100+
@Jim Doherty
Thanks for the workarounds! I decided to just type my sql in code. Hopefully, Microsoft will improve on the .OpenQuery command in a future release and allow an argument to pass parameters. Definitely a serious omission.
May 10 '10 #14

Sign in to post your reply or Sign up for a free account.

Similar topics

0
by: Reggie | last post by:
Hi and TIA, I Have a query that uses a function for setting the Criteria. When I view the return value of the finction it appears to be exactly what I want for my criteria. The problem is if I...
7
by: Annelies | last post by:
I need to pass a parameter to the source query of a subform via vba. Any ideas on how to do that? (Actually I wanted to set the subform source to a query but I guess that isn't possible.. ) ...
3
by: thomas goodwin | last post by:
I have a query which asks for a parameter value to execute it. To see the results I have to: a) click on the query -- the "Enter Parameter Value" window pops up. b) enter the parameter value c)...
2
by: rg | last post by:
Hi all, I have query about passing a parameter from form to a query. My situation is as follows: I have a query that pulls up some data from a table, however there is a condition that must...
1
by: | last post by:
Hi, I've defined an ObjectDataSource and a parameterized DataSet. I would like it if I could pass the parameter value that describes the query that creates the DataSet as part of a user control...
3
by: programmer2004 | last post by:
Hi, I am trying to pass parameter value to ODBCCommand object. but it is not assigning values , the null value is gets stored. i m using following code, Private Sub cmdsave_Click(ByVal sender As...
2
by: Roger | last post by:
Anyone know how to pass a parameter to a query via a report in Access 2003?
2
by: de_ja | last post by:
Hi, If, for example an access database that concerns insurance claim investigations. The database comprises only one table containing data - investigation reference number, referral date,...
2
by: ncsthbell | last post by:
Using MS Access 2007. I built a form that has a combo box of lists of 'actions' (cmboActions). This form also has a button to click that I want to run a query and display the results in datasheet...
0
by: taylorcarr | last post by:
A Canon printer is a smart device known for being advanced, efficient, and reliable. It is designed for home, office, and hybrid workspace use and can also be used for a variety of purposes. However,...
0
by: Charles Arthur | last post by:
How do i turn on java script on a villaon, callus and itel keypad mobile phone
0
by: aa123db | last post by:
Variable and constants Use var or let for variables and const fror constants. Var foo ='bar'; Let foo ='bar';const baz ='bar'; Functions function $name$ ($parameters$) { } ...
0
by: ryjfgjl | last post by:
If we have dozens or hundreds of excel to import into the database, if we use the excel import function provided by database editors such as navicat, it will be extremely tedious and time-consuming...
0
BarryA
by: BarryA | last post by:
What are the essential steps and strategies outlined in the Data Structures and Algorithms (DSA) roadmap for aspiring data scientists? How can individuals effectively utilize this roadmap to progress...
1
by: nemocccc | last post by:
hello, everyone, I want to develop a software for my android phone for daily needs, any suggestions?
1
by: Sonnysonu | last post by:
This is the data of csv file 1 2 3 1 2 3 1 2 3 1 2 3 2 3 2 3 3 the lengths should be different i have to store the data by column-wise with in the specific length. suppose the i have to...
0
by: Hystou | last post by:
There are some requirements for setting up RAID: 1. The motherboard and BIOS support RAID configuration. 2. The motherboard has 2 or more available SATA protocol SSD/HDD slots (including MSATA, M.2...
0
Oralloy
by: Oralloy | last post by:
Hello folks, I am unable to find appropriate documentation on the type promotion of bit-fields when using the generalised comparison operator "<=>". The problem is that using the GNU compilers,...

By using Bytes.com and it's services, you agree to our Privacy Policy and Terms of Use.

To disable or enable advertisements and analytics tracking please visit the manage ads & tracking page.