In de scalaire subquery die u gebruikt, kunt u alleen verwijzen naar de tabellen van de "hoofd"-query "één genest niveau naar beneden", niet verder naar beneden, zoals u hebt gezien. (Ik geloof dat deze beperking in versie 12 is opgeheven, dus misschien kun je je database gewoon upgraden?;-)
In de scalaire subquery probeert u de waarde van de INSERTDATE-kolom van de eerste rij te krijgen volgens uw bestelling. Dat kan ook als volgt worden geschreven zonder te nesten:
SELECT
O.INSERTDATE OrderCreateDate,
-- Determine delivery date
(SELECT MAX(DD.INSERTDATE) KEEP (
DENSE_RANK FIRST ORDER BY
DD.CLOSED ASC, ABS(TRUNC(CURRENT_DATE-TO_DATE(TO_CHAR(DD.INSERTDATE, 'DDMMYYYY'), 'DDMMYYYY'))) ASC
)
FROM MY_DELIVERYDATE_TABLE DD
JOIN MY_ORDERPOS_TABLE OP2 ON DD.FK_ORDERPOS=OP2.ID
LEFT OUTER JOIN MY_ORDER_TABLE O2 ON OP2.FK_ORDER=O2.ID
WHERE OP2.FK_ORDER=O.ID AND -- This will no longer give "Invalid identifier O.ID"
DD.DELFLAG IS NULL AND OP2.DELFLAG IS NULL
) DeliveryDate
FROM MY_ORDER_TABLE O
WHERE O.ID = 620; -- ID goes here!
KEEP (DENSE_RANK FIRST vertelt de MAX-functie dat deze de MAX alleen moet berekenen van die rijen die eerst rangschikken in de ORDER BY-clausule. Dus als uw ORDER BY "uniek" is, wordt MAX alleen toegepast op één rij. Als uw ORDER BY niet "uniek" is en duplicaten kan hebben, kunt u overwegen of u de MAX of de MIN wilt (of iets toevoegen aan de ORDER BY om het uniek te maken.)
(Als u Oracle versie 12 had gebruikt, zou een alternatief voor de KEEP (DENSE_RANK-truc zou zijn om de FIRST 1 ROW ONLY-clausule van de SELECT-instructie te gebruiken.)