Access Query Loop Update - sql

I have a table with purchase orders, and all POs could have several entries with different items associated.
PO
PN
Status
1
A
Open
1
B
progress
1
C
Delivered
2
A
Open
3
A
Delivered
3
A
Delivered
From this master data Table, I would like to create a overview table, with just one entry per PO and only one Status information, according certain criteria.
Criteria example:
if one item is in PROGRESS or DELIVERED set PO status as PROGRESS
if one item is in OPEN (But don't exist PROGRESS) set PO Status as OPEN.
if all item is in PROGRESS or DELIVERED or OPEN set PO Status as PROGRESS or DELIVERED or OPEN accordingly.
OVERVIEW TABLE Example:
PO
Status
1
PROGRESS
2
OPEN
3
Delivered

I will offer one approach to consider. Assuming there are only 3 status categories:
Query1:
SELECT OrderDetails.PO,
Count(OrderDetails.PN) AS CntPN,
Sum(IIf([Status]="Progress",1,0)) AS CntP,
Sum(IIf([Status]="Open",1,0)) AS CntO,
Sum(IIf([Status]="Delivered",1,0)) AS CntD
FROM OrderDetails
GROUP BY OrderDetails.PO;
Query2:
SELECT Query1.PO, Switch([CntP]=[CntPN],"Progress", [CntO]=[CntPN],"Open", [CntD]=[CntPN],"Delivered", CntO>0 AND CntP=0,"Open", CntP>0 Or CntD>0,"Progress", True,Null) AS S
FROM Query1;
Query1 could be a CROSSTAB instead of using IIf() expressions to emulate. CROSSTAB will return Null instead of 0 so would have to deal with that. Then adjust Query2 structure for different field names.
Anything else will probably need a VBA custom function.

Related

SQL-Script to Automatically build pallets

I have code that I am using to call out how many pallets an item would be able to build. The issue I am having is I cannot figure out how to then automatically build pallets based on this number.
For example, if I have an item that can build 3.50 pallets, then I would want that to go into a new table that will then call out Pallet #1 and then a unique name, Pallet #2 then a unique name, Pallet #3 then a unique name. There will then be left over of .50.
I would want to then look in the category and find a ITEM that could fit with the .50 pallet item and try to make a whole pallet. In the table below, the remaining .50 of ITEM '1111' would be paired with ITEM '3333' which is .350 to then make Pallet #4, this process would then loop and find all the other combos based on the category to make the closest full pallet.
Ideally I would like the first pallets to be made on anything greater then 1, by giveng them a unique name, then using the leftovers to combine with other leftovers(items <1) to make other potentially full pallets, with a threshold of between 1 and .85:
ITEM CUBIC_INCHES PALLETS CATEGORY RANKING
1111 100,000 3.50 HIGH_TOP 1
2222 50,000 1.75 LOW_TOP 1
3333 10,000 .350 HIGH_TOP 2
4444 5,000 .175 LOW_TOP 2
My code that I am using to make this table is:
SELECT
ITEM
,CUBIC_INCHES
,CAST(CASE WHEN CUBIC_INCHES=0 THEN 0
ELSE (CUBIC_INCHES)/28,571.42 END AS DEC(38,4)) AS PALLETS
,CATEGORY
,RANK() OVER (PARTITION BY CATEGORY ORDER BY CUBIC_INCHES) AS RANKING
FROM TABLE_1

Should I denormalize to a join with an added bit, or what?

I have many documents in my system such as order invoices, requisitions etc. In order to track their approval workflow I have one common table in which I have the following columns.
WFID ActionDate DocInstancetype DocinstanceID iscurrent status
1 2017-04-04 PO 58 0 Submitted
2 2017-04-05 PO 58 1 Approved
3 2017-04-04 PR 74 1 Submitted
In my reports I usually need to consider only approved documents. Is it a good idea to add an IsApproved bit in the Documents Master table (in PR and PO tables) and sync it using a trigger so that I can avoid a join with workflow table every time I need to get approved documents only?
Any other better suggestion would also be appreciated.
Document table should contain the status (not is_approved) because you might need to filter document on basis of document status in future though today your need are limited to status="approved". Status change history should be maintain in another table which is workflow in your case but I would suggest `document_status_tracking' or just 'document_tracking' would be a better name for the table.

Challenging Excel VBA/Macro for inventory management

I work for an eCommerce company and we use Microsoft Excel for our inventory database. We currently just keep adding items to this database as we purchase them, without ever removing them. What I would like to do is start removing items as they sell. I am not sure how to attach the file, so if you e-mail me at drenollet#supplykick.com I can send it to you. Below are the following steps:
The Sales tab includes the sales data for the items. I would like to take this data and be able to copy and paste it in a sheet in our Inventory Managment file in excel (a separate file, but I included a sample in the "Database" sheet).
I then need to just use a VLOOKUP formula and the Catalog data to get the Product ID instead of the SKU. (I can do this.)
Then use the copied data in the Sales Tab that is in the Inventory Management file and move the corresponding rows out of the Database file/sheet to the Sold Items sheet.
A few thoughts on specifics:
I want to make sure all the quantities are right. (e.g.1 if we purchased two of an item and only one sold - reducing the quantity in the Database sheet from two down to one.) (e.g.2 If we purchased an item two different times at two different prices and both were purchased in one sale, I would want to make sure both of the rows are moved out of the database).
If you have any thoughts on making sure the quantities are right, let me know. Maybe we need to set all the purchase quantities to one and copy the purchase of a multiple quantity of items X number of times for each one that was purchased.
Would love your input on how to cross this bridge! Let me know if you would like to see the sample file and I can directly e-mail it to you!
Best Regards,
Don Renollet
The best way to do this is to have a sheet called Movements
then you have just rows of entries like
A B C D
----------------------------------------
prodID Movement type Qty Date
123 Purchase 5 08/01/15
789 Sale 2 07/01/15
123 Return 1 06/01/15
456 Sale 1 05/01/15
789 Purchase 10 04/01/15
456 Purchase 5 03/01/15
123 Sale 2 03/01/15
123 Return 1 02/01/15
123 Sale 1 02/01/15
123 Purchase 10 01/01/15
Then at anytime excel can calculate whats in stock using sumifs or similar
=SUMIFS(C:C,A:A,"123",B:B,"Purchase") - Sumif(C:C,A:A,"123",B:B,"Sale")) + Sumif(C:C,A:A,"123",B:B,"Return"))
You should never remove rows from a database like this, you can always do a stock take every so often and restart the database with 1 entry for each item, but aways store the old data elsewhere.
Try not to mix price with quantity if possible, if you need to manage price , consider using a moving average price (MAP)

MS Access SQL updating in sequence

I have a table that provides a point-in-time snapshot with the following headings:
| Cust# | Last Trans. | Charge | Quantity |
Every month, I will receive a file from a third party with transactions that will add new cust# or change existing customer information. I am having problems when there are multiple updates to the same Cust# in one month.
For example:
processing the following transaction file:
should yield the following snapshot table:
It may not be the best method, but now I have 3 separate queries to handle NEW, CHANGE and CANCEL. There are no problems with NEW and CANCEL.
Here's how my CHANGE query is set up:
UPDATE snp
INNER JOIN tr
ON snp.[Cust#] = tr.[Cust#]
SET
snp.[Last Trans] = tr.Transaction,
snp.Charge = snp.Charge + tr.Charge,
snp.Quantity = tr.Quantity
WHERE tr.Trans='CHANGE'
Note that Charge is incremental and Quantity is not. Updating Charge is working as expected, but Quantity is not. I do not necessarily get the latest quantity.
How do I ensure that if there are any changes to one customer, that the last Quantity field taken is from the latest CHANGE row (ie. max ID of that cust#)?
SELECT * FROM snp
WHERE ID IN (SELECT MAX(ID)
FROM tr
GROUP BY CUST#)
The inner query would give you all customers' max ID. You can filter the cust# based on your change criteria. The outer query would give you all the details of that row. You can then use those values in your queries.

Multi-Row Per Record SQL Statement

I'm not sure this is possible but my manager wants me to do it...
Using the below picture as a reference, is it possible to retrieve a group of records, where each record has 2 rows of columns?
So columns: Number, Incident Number, Vendor Number, Customer Name, Customer Location, Status, Opened and Updated would be part of the first row and column: Work Notes would be a new row that spans the width of the report. Each record would have two rows. Is this possible with a GROUP BY statement?
Record 1
Row 1 = Number, Incident Number, Vendor Number, Customer Name, Customer Location, Status, Opened and Updated
Row 2 = Work Notes
Record 2
Row 1 = Number, Incident Number, Vendor Number, Customer Name, Customer Location, Status, Opened and Updated
Row 2 = Work Notes
Record n
...
I don't think that possible with the built in report engine. You'll need to export the data and format it using something else.
You could have something similar to what you want on short description (list report, group by short description), but you can't group by work notes so that's out.
One thing to note is that the work_notes field is not actually a field on the table, the work_notes field is of type journal_input, which means it's really just a gateway to the actual underlying data model. "Modifying" work_notes actually just inserts into sys_journal_field.
sys_journal_field is the table which stores the work notes you're looking for. Given a sys_id of an incident record, this URL will give you all journal field entries for that particular record:
/sys_journal_field_list.do?sysparm_query=name=task^element_id=<YOUR_SYS_ID>
You will notice this includes ALL journal fields (comments + work_notes + anything else), so if you just wanted work notes, you could simply add a query against element thusly:
/sys_journal_field_list.do?sysparm_query=name=task^element=work_notes^element_id=<YOUR_SYS_ID>
What this means for you!
While you can't separate a physical row into multiple logical rows in the UI, in the case of journal fields you can join your target table against the sys_journal_field table using a Database View. This deviates from your goal in that you wouldn't get a single row for all work notes, but rather an additional row for each matched work note.
Given an incident INC123 with 3 work notes, your report against the Database View would look kind of like this:
Row 1: INT123 | markmilly | This is a test incident |
Row 2: INT123 | | | Work note #1
Row 3: INT123 | | | Work note #2
Row 4: INT123 | | | Work note #3