3
Sample Function A typical database has an Invoice table and an Invoice Detail table, so one invoice can have many lines. (If this is unfamiliar, see the Order and Order Detail tables in the Northwind sample database.) In the same way, a single incoming delivery may include many products, so you need Acquisition and Acquisition Detail tables. With the Product table and Stocktake table, you have a structure like this: This function returns the quantity on hand for any product, optionally at any date. Function OnHand(vProductID As Variant, Optional vAsOfDate As Variant) As Long 'Purpose: Return the quantity-on-hand for a product. 'Arguments: vProductID = the product to report on. ' vAsOfDate = the date at which quantity is to be calculated. ' If missing, all transactions are included. 'Return: Quantity on hand. Zero on error. Dim db As DAO.Database 'CurrentDb() Dim rs As DAO.Recordset 'Various recordsets. Dim lngProduct As Long 'vProductID as a long. Dim strAsOf As String 'vAsOfDate as a string. Dim strSTDateLast As String 'Last Stock Take Date as a string. Dim strDateClause As String 'Date clause to use in SQL statement. Dim strSQL As String 'SQL statement. Dim lngQtyLast As Long 'Quantity at last stocktake. Dim lngQtyAcq As Long 'Quantity acquired since stocktake. Dim lngQtyUsed As Long 'Quantity used since stocktake. If Not IsNull(vProductID) Then 'Initialize: Validate and convert parameters. Set db = CurrentDb() lngProduct = vProductID If IsDate(vAsOfDate) Then strAsOf = "#" & Format$(vAsOfDate, "mm\/dd\/yyyy") & "#"

Sample Function

Embed Size (px)

DESCRIPTION

Excel FUnction

Citation preview

Page 1: Sample Function

Sample Function

A typical database has an Invoice table and an Invoice Detail table, so one invoice can have many lines. (If this is unfamiliar, see the Order and Order Detail tables in the Northwind sample database.) In the same way, a single incoming delivery may include many products, so you need Acquisition and Acquisition Detail tables. With the Product table and Stocktake table, you have a structure like this:

This function returns the quantity on hand for any product, optionally at any date.

Function OnHand(vProductID As Variant, Optional vAsOfDate As Variant) As Long 'Purpose: Return the quantity-on-hand for a product. 'Arguments: vProductID = the product to report on. ' vAsOfDate = the date at which quantity is to be calculated. ' If missing, all transactions are included. 'Return: Quantity on hand. Zero on error. Dim db As DAO.Database 'CurrentDb() Dim rs As DAO.Recordset 'Various recordsets. Dim lngProduct As Long 'vProductID as a long. Dim strAsOf As String 'vAsOfDate as a string. Dim strSTDateLast As String 'Last Stock Take Date as a string. Dim strDateClause As String 'Date clause to use in SQL statement. Dim strSQL As String 'SQL statement. Dim lngQtyLast As Long 'Quantity at last stocktake. Dim lngQtyAcq As Long 'Quantity acquired since stocktake. Dim lngQtyUsed As Long 'Quantity used since stocktake.

If Not IsNull(vProductID) Then 'Initialize: Validate and convert parameters. Set db = CurrentDb() lngProduct = vProductID If IsDate(vAsOfDate) Then strAsOf = "#" & Format$(vAsOfDate, "mm\/dd\/yyyy") & "#" End If

'Get the last stocktake date and quantity for this product. If Len(strAsOf) > 0 Then strDateClause = " AND (StockTakeDate <= " & strAsOf & ")" End If strSQL = "SELECT TOP 1 StockTakeDate, Quantity FROM tblStockTake " & _ "WHERE ((ProductID = " & lngProduct & ")" & strDateClause & _ ") ORDER BY StockTakeDate DESC;"

Page 2: Sample Function

Set rs = db.OpenRecordset(strSQL) With rs If .RecordCount > 0 Then strSTDateLast = "#" & Format$(!StockTakeDate, "mm\/dd\/yyyy") & "#" lngQtyLast = Nz(!Quantity, 0) End If End With rs.Close

'Build the Date clause If Len(strSTDateLast) > 0 Then If Len(strAsOf) > 0 Then strDateClause = " Between " & strSTDateLast & " And " & strAsOf Else strDateClause = " >= " & strSTDateLast End If Else If Len(strAsOf) > 0 Then strDateClause = " <= " & strAsOf Else strDateClause = vbNullString End If End If

'Get the quantity acquired since then. strSQL = "SELECT Sum(tblAcqDetail.Quantity) AS QuantityAcq " & _ "FROM tblAcq INNER JOIN tblAcqDetail ON tblAcq.AcqID = tblAcqDetail.AcqID " & _ "WHERE ((tblAcqDetail.ProductID = " & lngProduct & ")" If Len(strDateClause) = 0 Then strSQL = strSQL & ");" Else strSQL = strSQL & " AND (tblAcq.AcqDate " & strDateClause & "));" End If

Set rs = db.OpenRecordset(strSQL) If rs.RecordCount > 0 Then lngQtyAcq = Nz(rs!QuantityAcq, 0) End If rs.Close

'Get the quantity used since then. strSQL = "SELECT Sum(tblInvoiceDetail.Quantity) AS QuantityUsed " & _ "FROM tblInvoice INNER JOIN tblInvoiceDetail ON " & _ "tblInvoice.InvoiceID = tblInvoiceDetail.InvoiceID " & _ "WHERE ((tblInvoiceDetail.ProductID = " & lngProduct & ")" If Len(strDateClause) = 0 Then strSQL = strSQL & ");" Else strSQL = strSQL & " AND (tblInvoice.InvoiceDate " & strDateClause & "));" End If

Set rs = db.OpenRecordset(strSQL) If rs.RecordCount > 0 Then lngQtyUsed = Nz(rs!QuantityUsed, 0) End If

Page 3: Sample Function

rs.Close

'Assign the return value OnHand = lngQtyLast + lngQtyAcq - lngQtyUsed End If

Set rs = Nothing Set db = Nothing Exit FunctionEnd Function