I want to create a pivot table in the active report to display dbf multiple
files records.
I'm trying to use the following code to create the PIVOT but it's not working, resulting in the error I've shown below.
This is the code:
Dim cn As New ADODB.Connection
Dim rs As New ADODB.Recordset
Private Sub openDB()
Set rs = New ADODB.Recordset
Set cn = New ADODB.Connection
cn.Open "Provider=VFPOLEDB.1;" & _
"Data Source=D:\Monthly\Colony;" & _
"Collating Sequence=MACHINE"
End Sub
Call openDB
rs.Open "SELECT HEDNAME,DEPCODE,DEPNAME," & _
"ISNULL(A,0) as A, ISNULL(B,0) as B, ISNULL(C,0) as C, ISNULL(G,0) as G " & _
"from(SELECT HED.HEDCODE,HED.HEDNAME,payfil01.DEPCODE,payfil01.DEPNAME,payfil12.PARSSCB," & _
"payfil12.EMPSHFT FROM payfil01 INNER JOIN payfil12 ON payfil01.DEPCODE = payfil12.DEPCODE " & _
"INNER JOIN payfil04 ON payfil01.DEPCODE = payfil04.DEPCODE AND payfil12.EMPTYPE = payfil04.EMPTYPE" & _
" AND payfil12.EMPCODE = payfil04.EMPCODE INNER JOIN payfil05 ON payfil12.DEPCODE = payfil05.DEPCODE" & _
" AND payfil12.EMPTYPE = payfil05.EMPTYPE AND payfil12.EMPCODE = payfil05.EMPCODE Inner Join" & _
"(Select DEPCODE HEDCODE,DEPNAME HEDNAME from payfil01 Where RIGHT(DEPCODE,2) = '00')" & _
" HED On HED.HEDCODE = Left(payfil01.DEPCODE,2) + '-00' where ltrim(rtrim(payfil04.empcode))<>''" & _
" and payfil12.parsscb>0)Final PIVOT ( SUM(PARSSCB) FOR EMPSHFT IN ([A],[B],[C],[G]) )pvt order by HEDCODE asc " & _
", cn, adOpenStatic, adLockReadOnly"
Set SS_Summary.DataControl1.Recordset = rs
SS_Summary.DataControl1.Recordset = rs
SS_Summary.Field35.Text = txtReportPeriod.Text
SS_Summary.Show
SS_Summary.Refresh
End Sub
Moreover it tried to use following query:
SELECT hedname,
depcode,
depname,
Sum(CASE
WHEN [empshft] = 'A' THEN parsscb
ELSE 0
END) AS A,
Sum(CASE
WHEN [empshft] = 'B' THEN parsscb
ELSE 0
END) AS B,
Sum(CASE
WHEN [empshft] = 'C' THEN parsscb
ELSE 0
END) AS C,
Sum(CASE
WHEN [empshft] = 'G' THEN parsscb
ELSE 0
END) AS G
FROM (SELECT HED.hedcode,
HED.hedname,
payfil01.depcode,
payfil01.depname,
payfil12.parsscb,
payfil12.empshft
FROM payfil01
INNER JOIN payfil12
ON payfil01.depcode = payfil12.depcode
INNER JOIN payfil04
ON payfil01.depcode = payfil04.depcode
AND payfil12.emptype = payfil04.emptype
AND payfil12.empcode = payfil04.empcode
INNER JOIN payfil05
ON payfil12.depcode = payfil05.depcode
AND payfil12.emptype = payfil05.emptype
AND payfil12.empcode = payfil05.empcode
INNER JOIN (SELECT depcode HEDCODE,
depname HEDNAME
FROM payfil01
WHERE RIGHT(depcode, 2) = '00') HED
ON HED.hedcode = LEFT(payfil01.depcode, 2) + '-00'
WHERE Ltrim(Rtrim(payfil04.empcode)) <> ''
AND payfil12.parsscb > 0) AS final
GROUP BY hedname,
depcode,
depname
ORDER BY depcode ASC
Screenshot of the error:
It looks like you included some of the Recordset.Open parameters into the SQL string:
rs.Open "SELECT HEDNAME,DEPCODE,DEPNAME," & _
"ISNULL(A,0) as A, ISNULL(B,0) as B, ISNULL(C,0) as C, ISNULL(G,0) as G " & _
"from(SELECT HED.HEDCODE,HED.HEDNAME,payfil01.DEPCODE,payfil01.DEPNAME,payfil12.PARSSCB," & _
"payfil12.EMPSHFT FROM payfil01 INNER JOIN payfil12 ON payfil01.DEPCODE = payfil12.DEPCODE " & _
"INNER JOIN payfil04 ON payfil01.DEPCODE = payfil04.DEPCODE AND payfil12.EMPTYPE = payfil04.EMPTYPE" & _
" AND payfil12.EMPCODE = payfil04.EMPCODE INNER JOIN payfil05 ON payfil12.DEPCODE = payfil05.DEPCODE" & _
" AND payfil12.EMPTYPE = payfil05.EMPTYPE AND payfil12.EMPCODE = payfil05.EMPCODE Inner Join" & _
"(Select DEPCODE HEDCODE,DEPNAME HEDNAME from payfil01 Where RIGHT(DEPCODE,2) = '00')" & _
" HED On HED.HEDCODE = Left(payfil01.DEPCODE,2) + '-00' where ltrim(rtrim(payfil04.empcode))<>''" & _
" and payfil12.parsscb>0)Final PIVOT ( SUM(PARSSCB) FOR EMPSHFT IN ([A],[B],[C],[G]) )pvt order by HEDCODE asc " & _
", cn, adOpenStatic, adLockReadOnly" '<--- THIS PART SHOULD NOT BE IN THE STRING!!!
Note that last line with args for the Open method are accidentally in the string. It should be more like this:
rs.Open "SELECT HEDNAME,DEPCODE,DEPNAME," & _
"ISNULL(A,0) as A, ISNULL(B,0) as B, ISNULL(C,0) as C, ISNULL(G,0) as G " & _
"from(SELECT HED.HEDCODE,HED.HEDNAME,payfil01.DEPCODE,payfil01.DEPNAME,payfil12.PARSSCB," & _
"payfil12.EMPSHFT FROM payfil01 INNER JOIN payfil12 ON payfil01.DEPCODE = payfil12.DEPCODE " & _
"INNER JOIN payfil04 ON payfil01.DEPCODE = payfil04.DEPCODE AND payfil12.EMPTYPE = payfil04.EMPTYPE" & _
" AND payfil12.EMPCODE = payfil04.EMPCODE INNER JOIN payfil05 ON payfil12.DEPCODE = payfil05.DEPCODE" & _
" AND payfil12.EMPTYPE = payfil05.EMPTYPE AND payfil12.EMPCODE = payfil05.EMPCODE Inner Join" & _
"(Select DEPCODE HEDCODE,DEPNAME HEDNAME from payfil01 Where RIGHT(DEPCODE,2) = '00')" & _
" HED On HED.HEDCODE = Left(payfil01.DEPCODE,2) + '-00' where ltrim(rtrim(payfil04.empcode))<>''" & _
" and payfil12.parsscb>0)Final PIVOT ( SUM(PARSSCB) FOR EMPSHFT IN ([A],[B],[C],[G]) )pvt order by HEDCODE asc " & _
, cn, adOpenStatic, adLockReadOnly
Related
When I try to execute this code in my excel VBA script, I get an error saying "invalid Procedure call or argument". Everything looks good to me, so where am I going wrong? Below is the code, thanks!
, Destination:=Range("$A$3")).QueryTable
.CommandText = Array( _
"Select C.SafetyStockQty as SftyStock, C.QtyOnHand as QOH01, G.QtyOnHand as QOHOF,D.QtyOnHand as QOHRDS,E.QtyOnHand as QOHRW ,H.QtyOnHand as QOH02 ,I.QtyOnHand as QOHP1 ,J.QtyOnHand as QOHPDS , F.GrossReqRule as GRR , F.PartCategory as Category ,F.LeadTime " & _
"From CompanyR.dbo.InvWarehouse C " _
, _
"left join CompanyR.dbo.InvWarehouse D on C.StockCode = D.StockCode and D.Warehouse = 'DS' " & _
"left join CompanyR.dbo.InvWarehouse E on C.StockCode = E.StockCode and E.Warehouse = 'RW' " _
, _
"left join CompanyR.dbo.InvWarehouse G on C.StockCode = G.StockCode and G.Warehouse = 'OF' " _
, _
"left join CompanyR.dbo.InvWarehouse H on C.StockCode = H.StockCode and H.Warehouse = '02' " _
, _
"left join CompanyP.dbo.InvWarehouse I on C.StockCode = I.StockCode and I.Warehouse = '01' " _
, _
"left join CompanyP.dbo.InvWarehouse J on C.StockCode = J.StockCode and J.Warehouse = 'DS' " _
, _
"left Join CompanyR.dbo.InvMaster F on C.StockCode = F.StockCode " & _
"where C.StockCode = '" & StckCd & "' And C.Warehouse = '01' " _
)
Public Function GetPendingChangeOrders(strJ As String) As Double
strSQL = "SELECT DISTINCT Sum(jcdetail.cost) AS SumOfcost " &
"FROM jcchangeorder INNER JOIN jcdetail ON (jcchangeorder.ordernum = jcdetail.ponum) AND (jcchangeorder.jobnum =jcdetail.jobnum) " &
"GROUP BY jcdetail.jobnum, jcdetail.type, jcchangeorder.type, IIf(DLookUp(""type"",""jcchangeorderstep"",""jobnum = '"" & [jcchangeorder].[jobnum] & ""' and ordernum = '"" & [ordernum] & ""' and Type = 20"")=20,-1,0) " & _
"HAVING (((jcdetail.jobnum)='" & strJ & "') AND ((jcdetail.type)=19) AND ((jcchangeorder.type)<>2) AND ((IIf(DLookUp(""type"",""jcchangeorderstep"",""jobnum = '"" & [jcchangeorder].[jobnum] & ""' and ordernum = '"" & [ordernum] & ""' and Type = 20"")=20,-1,0))=0));"
Set rs = dbs.OpenRecordset(strSQL, dbOpenSnapshot, dbReadOnly, dbReadOnly)
If Not rs.EOF Then
dblResult = Nz(rs.Fields(0), 0)
rs.Close
Set rs = Nothing
GetPendingChangeOrders = dblResult
Else
GetPendingChangeOrders = 0
End If
End Function
So I got tossed into some MS-Access database with VBA/SQL statements all over.
I am literally a beginner, but I have managed to figure some things out, and familiarize myself with our database that we use to print out job reports.
Some of the call functions are setup wrong, and are pulling from the wrong tables, and I basically need some help figuring out which way I should be going to tackle this.
Currently if we run the report, and it calls "GetPendingChangeOrders" it does what it is supposed to do, but when we look at what is under pending.
It shows a result even though it has a status of 21(DENIED) inside of "JCCHANGEORDERSTEP" table. I included images of it.
JCCHANGEORDER has the same as columns as JCCHANGEORDERSTEP(JOBNUM,ORDERNUM,TYPE) but the types in JCCHANGEORDER just has a type of 1 which I assume says hey I'm active.
JCCHANGEORDERSTEP contains 1 initiated (pending), 20 (approved), 21(denied). It filters out the 20's from results on report, but not 21. So I just need some help, and an explanation of why just adding 21 into the mix didn't work.
Thank you for your time.
EDIT-1 ADDED IMGS
IMGUR ACCESS PICTURES
Having looked at your images and studied your existing SQL code, I think the following SQL query may be more suitable and altogether more readable:
select sum(d.cost) as sumofcost
from
(
jcchangeorder o inner join jcdetail d
on o.ordernum = d.ponum and o.jobnum = d.jobnum
) inner join
(
select distinct s.jobnum, s.ordernum
from jcchangeorderstep s
where s.type = 1
) q
on o.jobnum = q.jobnum and o.ordernum = q.ordernum
where
o.jobnum = ?job and d.type = 19 and o.type <> 2
Here, the inclusion of jcdetail records for which the jcchangeorderstep.type = 1 is handled by the inner join between the tables, rather than a separate dlookup for every record.
You could implement this in your function in the following way:
Public Function GetPendingChangeOrders(strJ As String) As Double
Dim strS As String
strS = strS & "select sum(d.cost) "
strS = strS & "from "
strS = strS & " ( "
strS = strS & " jcchangeorder o inner join jcdetail d "
strS = strS & " on o.ordernum = d.ponum and o.jobnum = d.jobnum "
strS = strS & " ) inner join "
strS = strS & " ( "
strS = strS & " select distinct s.jobnum, s.ordernum "
strS = strS & " from jcchangeorderstep s "
strS = strS & " where s.type = 1 "
strS = strS & " ) q "
strS = strS & " on o.jobnum = q.jobnum and o.ordernum = q.ordernum "
strS = strS & "where "
strS = strS & " o.jobnum = ?job and d.type = 19 and o.type <> 2 "
Dim rst As DAO.Recordset
With CurrentDb.CreateQueryDef("", strS)
.Parameters(0) = strJ
Set rst = .OpenRecordset
If Not rst.EOF Then
rst.MoveFirst
GetPendingChangeOrders = Nz(rst.Fields(0), 0)
End If
rst.Close
End With
End Function
EDIT:
Following the subsequent comments, the following seems more aligned with your requirements:
select sum(d.cost)
from
jcchangeorder o inner join jcdetail d
on o.ordernum = d.ponum and o.jobnum = d.jobnum
where
o.jobnum = jobparam and
d.type = 19 and
o.type <> 2 and
not exists
(
select 1 from jcchangeorderstep s
where s.jobnum = o.jobnum and s.ordernum = o.ordernum and s.type <> 1
)
This may be implemented in your VBA function in the following way:
Public Function GetPendingChangeOrders(strJ As String) As Double
Dim strS As String
strS = strS & "select sum(d.cost) "
strS = strS & "from "
strS = strS & " jcchangeorder o inner join jcdetail d "
strS = strS & " on o.ordernum = d.ponum and o.jobnum = d.jobnum "
strS = strS & "where "
strS = strS & " o.jobnum = jobparam and "
strS = strS & " d.type = 19 and "
strS = strS & " o.type <> 2 and "
strS = strS & " not exists "
strS = strS & " ( "
strS = strS & " select 1 from jcchangeorderstep s "
strS = strS & " where s.jobnum = o.jobnum and s.ordernum = o.ordernum and s.type <> 1 "
strS = strS & " ) "
Dim rst As DAO.Recordset
With CurrentDb.CreateQueryDef("", strS)
.Parameters("jobparam") = strJ
Set rst = .OpenRecordset
If Not rst.EOF Then
rst.MoveFirst
GetPendingChangeOrders = Nz(rst.Fields(0), 0)
End If
rst.Close
End With
End Function
This part of the query in your HAVING and GROUP BY clauses is what's giving you problems:
IIf(DLookUp("type",
"jcchangeorderstep",
"jobnum = ' [jcchangeorder].[jobnum] ' and
ordernum = ' [ordernum] ' and
Type = 20")=20,-1,0))=0);
It's convoluted and very difficult to read. But it is saying, "If this job and order appears in JCCHANGEORDERSTEP with a type of 20, exclude it." So, that's what you need to fix.
The whole query should probably be fixed in a variety of ways. But I think this might get you where you need to go.
strSQL = "SELECT DISTINCT Sum(jcdetail.cost) AS SumOfcost " & _
"FROM jcchangeorder " & _
"INNER JOIN jcdetail " & _
"ON (jcchangeorder.ordernum = jcdetail.ponum) " & _
"AND (jcchangeorder.jobnum =jcdetail.jobnum) " & _
"GROUP BY jcdetail.jobnum, " & _
"jcdetail.type, " & _
"jcchangeorder.type, " & _
"DLookUp(""type"",""jcchangeorderstep"",""jobnum = '"" & [jcchangeorder].[jobnum] & ""' and ordernum = '"" & [ordernum] & ""' and Type = 1"") " & _
"HAVING (jcdetail.jobnum='" & strJ & "' AND " & _
"jcdetail.type=19 AND " & _
"jcchangeorder.type <> 2) AND " & _
"DLookUp(""type"",""jcchangeorderstep"",""jobnum = '"" & [jcchangeorder].[jobnum] & ""' and ordernum = '"" & [ordernum] & ""' and Type = 1"")=1;"
What I have done is changed to condition to say "If this job and order appears in JCCHANGEORDERSTEP with a type of 1, include it." Without actually seeing your data and testing the code myself, I can't promise this will work. There may be some typos, so I've explained what I'm trying to do, so you can fix them.
Also, take some time to go through the Stack Overflow tour. This community can be a great help if you work with it.
Try This:
After discussing the desired results with the OP, it appears that this would be a better solution. It gives the sum of all change orders that only have a change order step of PENDING.
strSQL = _
"SELECT SUM(JCD.cost) AS sumofcost " & _
"FROM jcchangeorder JCCO " & _
"INNER JOIN jcdetail JCD " & _
"ON JCCO.ordernum = jcd.ponum " & _
"AND JCCO.jobnum = jcd.jobnum " & _
"INNER JOIN (SELECT JCCOS.ponum, " & _
"JCCOS.jobnum " & _
"FROM jcchangeorderstep JCCOS " & _
"GROUP BY JCCOS.ponum, " & _
"JCCOS.jobnum " & _
"HAVING Count(*) = 1 " & _
"AND First(JCCOS.type) = 1) JCSELECT " & _
"ON JCCO.ordernum = JCSELECT.ponum " & _
"AND JCCO.jobnum = JCSELECT.jobnum " & _
"GROUP BY JCD.jobnum, " & _
"JCD.type, " & _
"JCCO.type "
"HAVING JCD.jobnum='" & strJ & "' AND " & _
"JCD.type=19 AND " & _
"JCCO.type <> 2;"
JCCO, JCCOS, and JCD are SQL aliases. SQL understands them. JCSELECT is an aliased subquery. JCSELECT creates a set of all job/orders that only have a step of PENDING.
I am getting an error message when I run my VBA code. I tried debugging and seems like there is something wrong with my connection string. I am getting an error message "Data source name not found and no default driver specified.
Sub Macro176()
Sheets("176Tk").Select
Dim i As Integer
i = 17
Set oConn = CreateObject("ADODB.Connection")
Set rs = CreateObject("ADODB.Recordset")
oConn.Open "Driver={MySQL ODBC 5.1 Driver};" & _
"server=myserveraddress;" & _
"database=mydatabasename; uid= myuserId; pwd=mypassword;" & _
"option=3"
SQLstr = "SELECT SUBSTRING(dbo.collection_points.name, CHARINDEX('-', dbo.collection_points.name) + 2, 3) + 'Tk' AS 'Tank', " & _
"dbo.data_values.actual_date_time AS 'Date', " & _
"dbo.data_values.value_text AS 'Drain Time', " & _
"dbo.data_points.name AS 'Description', " & _
"dbo.data_values.user_id AS 'Field Operator' " & _
"FROM " & _
"dbo.collection_points INNER JOIN " & _
"dbo.area ON dbo.collection_points.area_rec_id = dbo.area.area_rec_id INNER JOIN " & _
"dbo.data_points ON dbo.collection_points.cp_rec_id = dbo.data_points.cp_rec_id INNER JOIN " & _
"dbo.data_values ON dbo.data_points.dp_rec_id = dbo.data_values.dp_rec_id INNER JOIN " & _
"dbo.system_levels ON dbo.area.ownership_sysid = dbo.system_levels.system_id " & _
"WHERE " & _
"((dbo.system_levels.description = 'CX5 Crude Tank Farm' and dbo.area.name = 'Crd TF Draining') OR " & _
"(dbo.system_levels.description = 'CX5 Melvindale Tank Farm' and dbo.area.name = 'Mel Tank Draining') OR " & _
"(dbo.system_levels.description = 'CX5 Tank Farm (CP)' and dbo.area.name = 'CP Tank Draining') OR " & _
"(dbo.system_levels.description = 'CX5 Unifiner Tank Farm' and dbo.area.name = 'LabT.F. Draining')) AND " & _
"((dbo.data_values.value_text <> 'Yes') AND (dbo.data_values.value_text <> 'Complete') AND (dbo.data_values.value_text <> 'Incomplete') AND " & _
"(dbo.collection_points.name NOT like '%Roof%')) AND " & _
"dbo.data_values.nominal_date_time>='2017-01-01 00:00:00' and " & _
"dbo.data_values.nominal_date_time<'2018-12-31 11:59:59' " & _
"ORDER BY dbo.collection_points.name, dbo.data_values.actual_date_time"
rs.Open SQLstr, oConn, adLockOptimistic, adCmdTable
Do Until rs.EOF
Sheets("176Tk").Cells(i, 1).Value = rs.Fields("Tank")
Sheets("176Tk").Cells(i, 2).Value = rs.Fields("Date")
Sheets("176Tk").Cells(i, 3).Value = rs.Fields("Drain Time")
Sheets("176Tk").Cells(i, 4).Value = rs.Fields("Field Operator")
i = i + 1
Loop
rs.Close
oConn.Close
Set rs = Nothing
Set oConn = Nothing
End Sub
I have a search button which searches in 4 tables. So I made the Sql query with three inner, and I have CheckBoxes so if the CheckBox is checked it adds the conditions to the query. But I have a problem which is:
System.Data.OleDb.OleDbException
Syntax error in the JOIN operation
cmd = New OleDbCommand(Sql, myConnection)
Dim da As OleDbDataAdapter
Dim sql = "SELECT * from (tblDopages AS A INNER JOIN tblMatrice AS B on A.strMatrice = B.strMatrice) INNER JOIN (tblRefMatrice AS C on B.strMatrice = C.strMatrice) INNER JOIN (tblRefMatDetails AS D on C.intIDref = D.intIDRef) WHERE "
If CKBrefech.Checked = True Then
sql = sql & "strRefEch = '" & TBrefech.Text & "' AND "
End If
If CKBmethode.Checked = True Then
sql = sql & "strMethode = '" & CBmethode.Text & "' AND "
End If
If CKBpurif.Checked Then
sql = sql & "strPurif = '" & CBpurif.Text & "' AND "
End If
If CKBmatrice.Checked Then
sql = sql & "strMatrice = '" & CBmatrice.Text & "' AND "
End If
If CKBmol.Checked Then
sql = sql & "strMolecule = '" & CBmol.Text & "' AND "
End If
If CKBechprep.Checked Then
sql = sql & "datDatePrepa >= #DatPrepa AND "
cmd.Parameters.Add("#DatPrepa", OleDbType.Date).Value = DTPechprep.Value.Date
End If
If CKBechau.Checked Then
sql = sql & "datDatePrepa <= #Datau AND "
cmd.Parameters.Add("#Datau", OleDbType.Date).Value = DTPechau.Value.Date
End If
If CKBtrigprepa.Checked = True Then
sql = sql & "strTrigPrepa = '" & TBtrigprepa.Text & "' AND "
End If
If CKBtriganaly.Checked = True Then
sql = sql & "strTrigAnaly = '" & TBtrigAnaly.Text & "' AND "
End If
If CKBappar.Checked = True Then
sql = sql & "strNomTech = '" & CBappar.Text & "' AND "
End If
If CKBnumappar.Checked = True Then
sql = sql & "[strEquip(Appareil)] = '" & CBnumappar.Text & "' AND "
End If
If CKBteneurmini.Checked = True Then
sql = sql & "dblDopage >= " & TBteneurmini.Text & " AND "
End If
If CKBteneurmax.Checked = True Then
sql = sql & "dblDopage <= " & TBteneurmax.Text & " AND "
End If
If GroupBox1.Enabled Then
Try
If CKBnomref.Checked Then
sql = sql & "D.strReferentiel = '" & CBnomref.Text & "' AND "
End If
If CKBniv1.Checked Then
sql = sql & "D.strNIveau1 = '" & CBniv1.Text & "' AND "
End If
If CKBniv2.Checked Then
sql = sql & "D.strNiveau2 = '" & CBniv2.Text & "' AND "
End If
If CKBniv3.Checked Then
sql = sql & "D.strNiveau3 = '" & CBniv3.Text & "' AND "
End If
If CKBniv4.Checked Then
sql = sql & "D.strNiveau4 = '" & CBniv4.Text & "' AND "
End If
Catch ex As Exception
MessageBox.Show(ex.Message)
End Try
End If
If sql.EndsWith(" AND ") Then
sql = sql.Substring(0, sql.Length - 4)
End If
' Remove the WHERE if no textbox has been filled....'
If sql.EndsWith(" WHERE ") Then
sql = sql.Substring(0, sql.Length - 7)
End If
' cmd = New OleDbCommand(sql, myConnection)
cmd.CommandText = sql
cmd.Connection = myConnection
Dim MyDataSet As New DataSet
da = New OleDbDataAdapter(sql, myConnection)
da.SelectCommand = cmd
da.SelectCommand.Parameters.Add(New OleDbParameter("#DatPrepa", DTPechprep.Value)) 'adding date parameters to datatable
da.SelectCommand.Parameters.Add(New OleDbParameter("#datau", DTPechprep.Value)) 'adding date parameters to datatable
'da.SelectCommand.Parameters.Add(New OleDbParameter("#Matrice", matrice.ToString)) 'adding Matrice parameters to datatable
da.Fill(MyDataSet, "Matrice")
DataGridView1.DataSource = MyDataSet.Tables("Matrice")
'to focus on first row of DGV after populating it
DataGridView1.Rows(0).Selected = True
LBnumresult.Text = DataGridView1.RowCount - 1
Well you have some syntax errors. Change this:
SELECT *
FROM (tblDopages AS A
INNER JOIN tblMatrice AS B ON A.strMatrice = B.strMatrice)
INNER JOIN (tblRefMatrice AS C ON B.strMatrice = C.strMatrice)
INNER JOIN (tblRefMatDetails AS D ON C.intIDref = D.intIDRef)
WHERE strMethode = 'MarMeth1' AND strPurif = 'MarPurif2'
to this:
SELECT *
FROM ((tblDopages AS A
INNER JOIN tblMatrice AS B ON A.strMatrice = B.strMatrice)
INNER JOIN tblRefMatrice AS C ON B.strMatrice = C.strMatrice)
INNER JOIN tblRefMatDetails AS D ON C.intIDref = D.intIDRef
WHERE strMethode = 'MarMeth1' AND strPurif = 'MarPurif2'
General:
SELECT ...
FROM ((--here N-2 parentesis
table1
JOIN table2 ON ...)
JOIN table3 ON ...)
JOIN table4 ON ...)
JOIN tableN ON ...--here no parentesis
This is the answer I used which contains 2 inner join between 3 tables and left join.
I made first the inner join and finally the left join
Dim sql = "SELECT distinct A.* FROM ((tblMatrice AS B INNER JOIN tblRefMatrice AS C ON B.strMatrice = C.strMatrice) INNER JOIN tblRefMatDetails AS D ON C.intIDref = D.intIDRef) LEFT OUTER JOIN tblDopages AS A on A.strMatrice = B.strMatrice where "
I have a vehicle database and would like to show "related" vehicles when a user clicks to view a vehicle. For instance, the user views a '2013 Chevy Tahoe' that is listed by dealership 'ABC Dealers'.
I need to create a SQL statement to grab 4 vehicles that are similar to the vehicle they are viewing. Here is the order of importance for now:
1) Dealer Listings (d_id)(Show vehicles also listed by that dealer)
2) Vehicle Category (vc_id)(Vehicle category such as Car, Truck, SUV, etc.)
3) Vehicle Make (vm_id)(Vehicle make such as Ford, Chevy, Lexus, etc.)
I have created a SQL statement, but it does not seem to do what I am looking for it to do. Can anyone offer any suggestions on how to properly build a SQL statement to grab the most relevant records in the order defined above?
strSQL = "SELECT TOP 4 v.v_id, vm.vm_name, v.v_year, v.v_model, v.v_search_price, d.d_name, u.u_name " & _
"FROM tbl_Vehicles v " & _
"LEFT JOIN tbl_VehicleMake vm ON vm.vm_id = v.vm_id " & _
"LEFT JOIN tbl_Dealers d ON d.d_id = v.d_id " & _
"LEFT JOIN tbl_Users u ON u.u_id = v.u_id " & _
"WHERE v.v_processed = 1 AND v.v_active = 1 AND v.v_id <> " & v_id
If Not CheckBlank(d_id) Then
strSQL = strSQL & " OR v.d_id = " & d_id
End If
If Not CheckBlank(vm_id) Then
strSQL = strSQL & " OR v.vm_id = " & vm_id
End If
If Not CheckBlank(vc_id) Then
strSQL = strSQL & " OR v.vc_id = " & vc_id
End If
strSQL = strSQL & " ORDER BY v.d_id, v.vc_id, v.vm_id"
I have a couple of thoughts for you.
Your current query has some ANDs and some ORs. You may need brackets to indicate your preferred order of operations, for example:
strSQL = "SELECT TOP 4 v.v_id, vm.vm_name, v.v_year, v.v_model, v.v_search_price, d.d_name, u.u_name " & _
"FROM tbl_Vehicles v " & _
"LEFT JOIN tbl_VehicleMake vm ON vm.vm_id = v.vm_id " & _
"LEFT JOIN tbl_Dealers d ON d.d_id = v.d_id " & _
"LEFT JOIN tbl_Users u ON u.u_id = v.u_id " & _
"WHERE v.v_processed = 1 AND v.v_active = 1 AND v.v_id <> " & v_id
If Not CheckBlank(d_id) Or Not CheckBlank(vm_id) Or Not CheckBlank(vc_id) Then
strSQL = strSQL & "("
End If
If Not CheckBlank(d_id) Then
strSQL = strSQL & " OR v.d_id = " & d_id
End If
If Not CheckBlank(vm_id) Then
strSQL = strSQL & " OR v.vm_id = " & vm_id
End If
If Not CheckBlank(vc_id) Then
strSQL = strSQL & " OR v.vc_id = " & vc_id
End If
If Not CheckBlank(d_id) Or Not CheckBlank(vm_id) Or Not CheckBlank(vc_id) Then
strSQL = strSQL & ")"
End If
strSQL = strSQL & " ORDER BY v.d_id, v.vc_id, v.vm_id"
But based on what you wrote in your question, you may be better with a query that uses the ORDER BY clause to get the most appropriate records based on the criteria you specified.
strSQL = "SELECT TOP 4 v.v_id, vm.vm_name, v.v_year, v.v_model, v.v_search_price, d.d_name, u.u_name " & _
"FROM tbl_Vehicles v " & _
"LEFT JOIN tbl_VehicleMake vm ON vm.vm_id = v.vm_id " & _
"LEFT JOIN tbl_Dealers d ON d.d_id = v.d_id " & _
"LEFT JOIN tbl_Users u ON u.u_id = v.u_id " & _
"WHERE v.v_processed = 1 AND v.v_active = 1 AND v.v_id <> " & v_id & " ORDER BY"
If Not CheckBlank(d_id) Or Not CheckBlank(vm_id) Or Not CheckBlank(vc_id) Then
If Not CheckBlank(d_id) Then
strSQL = strSQL & " CASE WHEN v.d_id = " & d_id & " THEN 0 ELSE 1 END,"
End If
If Not CheckBlank(vm_id) Then
strSQL = strSQL & " CASE WHEN v.vm_id = " & vm_id & " THEN 0 ELSE 1 END,"
End If
If Not CheckBlank(vc_id) Then
strSQL = strSQL & " CASE WHEN v.vc_id = " & vc_id & " THEN 0 ELSE 1 END,"
End If
strSQL = Left(strSQL, Len(strSQL) - 1)
Else
strSQL = strSQL & "v.d_id, v.vc_id, v.vm_id"
End If
This query will still give you results even if there are no vehicles for that dealer, make or category, so you will always have related vehicles (assuming you have at least 5 records).
It looks like the OR clauses you're using are not going to bring you you want. Assuming I'm understanding the snippet and the unseen db correctly, you need to create a subclause of the OR statements that is "ANDED" in. Try the following, after the initial strSQL assignment:
...
dim strSubClause
strSubClause = ""
If Not CheckBlank(d_id)) Then
strSubClause = "v.d_id = " & d_id
End If
If Not CheckBlank(vm_id) Then
If len(strSubClause) > 0 then
strSubClause = strSubClause & " OR v.vm_id = " & vm_id
Else
strSubClause = "v.vm_id = " & vm_id
End If
End If
If Not CheckBlank(vc_id) Then
If len(strSubClause) > 0 then
strSubClause = strSubClause & " OR v.vc_id = " & vc_id
Else
strSubClause = "v.vc_id = " & vc_id
End if
End If
If len(strSubClause) > 0 then
strSQL = " AND (" & strSubClause & ")"
End If
strSQL = strSQL & " ORDER BY v.d_id, v.vc_id, v.vm_id"
So, assuming all of your checks came back with values, you'd have a where clause that looks like:
...WHERE v.v_processed = 1 AND v.v_active = 1 AND v.v_id <> NNN AND (v.d_id = XXX OR v.vm_id = YYY OR v.vc_id = ZZZ) ORDER BY v.d_id, v.vc_id, v.vm_id
Does that make sense and/or get you closer or all the way to where you're wanting to go?