how do u use a group by when using fields from different tables - group-by

Ive tried running the following query on my database but when I do it shows the wrong information
I am trying to show every product that has been bought and who bought it and instead It shows that every product has been bought by every customer.
SELECT Cust_Name, prod_type, purchases.purch_id
FROM CUSTomers, product, purchases, orders
Where Purchases.purch_id = orders.PURCH_ID
AND orders.prod_id=product.prod_id;
when I have asked my lecturer how i should change the query I was told I should be look into group by clause but when I add one I get the error message "ORA-00979: not a GROUP BY expression"
This is the structure of the relevant tables

Related

Postgres SELECT id LAG(id) OVER (ORDER BY id) FROM invoice WHERE id = 2

I've looked all over the internet and I fail to get this query running as expected.
I've got a table of invoices and some invoices are related to one another because they belong to the same project.
My ticket says I've got to get the PREVIOUS invoice based on a provided invoice.
Say Project A has 10 invoices, and I'm looking at invoice #4, I've got to write a query which will return the ID of the previous Invoice. Bear in mind, the invoice table is home to all sorts of projects, and each project could have many invoices on their own, so I want to avoid getting many IDs back and then iterating over them.
To illustrate the issue, I've written this fiddle.
It works somewhat acceptably when I don't filter for steps.id, but that means returning hundreds of IDs to sift through.
I've tried and tried but I can't seem to get the column previousStep to be kind of bound to the ID column.
Simply find the invoice with the next largest id for the same project:
SELECT inv2.id
FROM invoice AS inv1
JOIN invoice AS inv2
ON inv1.project = inv2.project AND inv1.id > inv2.id
WHERE inv1.id = 1057638
ORDER BY inv2.id DESC
LIMIT 1;

How to avoid customer's order history being changed in MongoDB?

I have two collections
Customers
Products
I have a field called "orders" in each of my customer document and what this "orders" field does is that it stores a reference to the product Id which was ordered by a customer, now my question is since I'm referencing product Id and if I update the "title" of that product then it will also update in the customer's order history since I can't embed each order information since a customer may order thousands of products and it can hit 16mb mark in no time so what's the fix for this. Thanks.
Create an Orders Collection
Store ID of the user who made the order
Store ID of the product bought
I understand you are looking up the value of the product from the customer entity. You will always get the latest price if you are not storing the order/price historical transactions. Because your data model is designed this way to retrieve the latest price information.
My suggestion.
Orders place with product and price always need to be stored in history entity or like order lines and not allow any process to change it so that when you look up products that customers brought you can always get the historical price and price change of the product should not affect the previous order. Two options.
Store the order history in the current collection customers (or top say 50 order lines if you don't need all of history(write additional logic to handle this)
if "option1" is not feasible due to large no. of orders think of creating an order lines transaction table and refer order line for the product brought via DBref or lookup command.
Note: it would have helped if you have given no. of transactions in each collection currently and its expected rate of growth of documents in the collection QoQ.
You have orders and products. Orders are referencing products. Your problem is that the products get updated and now your orders reference the new product. The easiest way to combat this issue is to store full data in each order. Store all the key product-related information.
The advantage is that this kind of solution is extremely easy to visualize and implement. The disadvantage is that you have a lot of repetitive data since most of your products probably don't get updated.
If you store a product update history based on timestamps, then you could solve your problem. Products are identified now by 3 fields. The product ID, active start date and active end date. Or you could configure products in this way: product ID = product ID + "Version X" and store this version against each order.
If you use dates, then you will query for the product and find the product version that was active during the time period that the order occurred. If you use versions against the product, then you will simply query the database for the particular version of the product itself. I haven't used mongoDb so I'm not sure how you would achieve this in mongoDb exactly. Naively however, you can modify the product ID to include the version as well using # as a delimiter possibly.
The advantage of this solution is that you don't store too much of extra data. Considering that products won't be updated too often, I feel like this is the ideal solution to your problem

is it possible with optimistic concurrency ensure this case?

I have a table that has a long column that is a GroupCode. I can have groups of products, so to get all the product of a group I just get all the products which GroupCode is the same.
I can change a product from one group to another, and if I change a product from a group, I want that all the products of the group change to the new group.
If I use optimistic concurrency, it could happen this:
One user wants to change a product from a group, so he gets all the products with the same groupCode. Set the new new groupCode to all this products.
A second user add a new product to the group. But the first user doesn't have this product because he got all the products before the second user add the new product.
So at the end, a new product has a wrong GroupCode, because the code is not correct because all the products of the group was change to the new group. So I would have a group with only one product, and it wouldn't be correct.
With pessimistic concurrency, the first use get all the products of the group, block all the products.
The second user try to add a new product to the group, to do that, first try to get one of the products of the group as reference product, but how it is blocked by the first user, the second user has to wait.
The first user changes all the products to the new group and unblock all the products.
The second user get the reference product, that has the new groupCode, so the new product is added to the correct group.
In summary, I want that when I change a product from one group to another, I want to change all the products of the group, and avoid that a new product belongs to the old group.
Is it possible to solve this case with optimistic concurrency? Or I have to use pessimistic concurrency?
I honestly don't see the issue here. If you want to implement it as OCC, you should just follow the OCC phases.
User A gets all records which belong to group ABC
User B gets a reference to Record1, which belongs to ABC at the moment
User A moves Record1 to group XYZ
User B wants to add a new record to the group to which Record1 belongs. So just before inserting the record, get the group of Record, which is now XYZ
This is assuming that you go with the 'referential record' approach. If your screen (or whatever) just lists the currently available groups, and meanwhile one of those groups becomes empty (because you have moved all records to another group), there is no way of telling if that's a concurrency issue or it is working as expected. In such case, you should normalize your database and split the categories into a separate table, so that at least the user gets an error that the group no longer exists.

Filemaker - Can I use a portal like a drop-down value list?

I am trying to work around a limitation that Filemaker 12 seems to have. In a value list that links to an ODBC attached SQL Server database, it doesn't display every piece of data. If there are 2 people with the same last name for example, it only displays the first person with that last name in the list. This is verified by the following in the Filemaker documentation (which I found after a lot of digging)
If the value list is defined to display information from two fields, items will not be duplicated for the field on which the value list is sorted. For example, if the value list displays information from the Company field and the Name field, and if the values are sorted by the Company field, only one person from each company will appear in the value list.
Portals on the other hand will find all the related data, I just don't understand how do something with the data once I get it in the portal. I essentially thus wish to use a portal AS my drop-down value list, and then to use it as I would have a value list (which is then to act as the key to do the rest of the lookups on the page to fill out the invoice.
The major issue here (other than this maddening choice Filemaker seems to make) is that the external file I am pulling the data from is an ODBC mounted SQL Server file, so I can't do something easy like a calculated field which would give me last name & " " & first which would make almost every person unique. Filemaker won't let me do that because it says I can't do that with a field that is not indexed. Any help would be greatly appreciated!
Assuming that we're starting with table MyTable and we're trying to get a ID from the People table for the selected person, which we'll call ID so that we can put it into MyTable::PersonID
Start by creating a new Table Occurrence of your People table and call it PeopleWhoCanBeSelected. If you want every person in the People table you can connect it to MyTable with the X relationship. If you want to show just a subset of the people you can build a different relationship.
Now, on a layout displaying records from MyTable you will make a portal showing records from the PeopleWhoCanBeSelected table.
In the portal put a button. When that button is pressed use the Set Field script step:
Set Field MyTable::PersonID to:
PeopleWhoCanBeSelected::ID
That should do it. You can make the button an invisible overlay on the entire portal record if you like, so that the user clicks on "the name" instead of "the button next to the name".
Now, if you want to pull additional data through to the MyTable record, you'll need to create a second Table Occurrence, called People with the relationship MyTable::PersonID = People::ID. Then you can get information on the specifically chosen person through that relationship.

products and configurable_products in postgresql

I have a Product table and a ConfigurableProduct table.
If there are several variations of the same product like a shirt in different colors I create a ConfigurableProduct.
When a user is looking at the catalog he should see a list of products unless there is a ConfigurableProduct, then he should see it with a select box for each variations.
How do I structure the tables for Product and ConfigurableProduct and how do I query the db so I can page through the results?
Thanks
I am going to answer this as if you do not have tables created. I am not sure if that is true though.
The following is a simple example, but I assume you have more data.
products
id
name
configurable_products
id
variation
product_id REFERENCES products(id)
You can just make the configurable products a reference to products.
If you want a listing of products with their configurations then you can do:
select p.name, c.variation
from products p left outer join configurable_products c
on (p.id = c.product_id);
Of course you can just search for all the configurable_products based on the product id too when needed.
As for the paging part of your question you will have to clarify what you mean. You can use limit to limit results if you don't want to get everything at once.