Først kan du oprette en VIEW
for at give denne funktionalitet:
CREATE VIEW orders AS
SELECT '1'::int AS source -- or any other tag to identify source
,"OrderNumber"::text AS order_nr
,"InvoiceNumber" AS tansaction_id -- no cast .. is int already
,"OrderDate" AT TIME ZONE 'UTC' AS purchase_date -- !! see explanation
FROM tbl_newegg
UNION ALL -- not UNION!
SELECT 2
"amazonOrderId"
,"merchant-order-id"
,"purchase-date"
FROM tbl_amazon;
Du kan forespørge på denne visning som enhver anden tabel:
SELECT * FROM orders WHERE order_nr = 123 AND source = 2;
-
sourceer nødvendig, hvisorder_nrer ikke enestående. Hvordan ville du ellers garantere unikke ordrenumre over forskellige kilder? -
Et
timestamp without time zoneer en tvetydig i en global sammenhæng. Det er kun godt i forbindelse med sin tidszone. Hvis du blandertimestampogtimestamptz, skal du placeretimestampi en bestemt tidszone medAT TIME ZONEkonstruere for at få dette til at fungere. For mere forklaring læs dette relaterede svar .Jeg bruger UTC som tidszone, du vil måske angive en anden. En simpel cast
"OrderDate"::timestamptzville antage din nuværende tidszone.AT TIME ZONEanvendt på ettimestampresulterer itimestamptz. Det er derfor, jeg ikke tilføjede endnu en rollebesætning. -
Mens du kan , Jeg anbefaler ikke at bruge kamel-case-id'er i PostgreSQL nogensinde . Undgår mange former for mulig forvirring. Bemærk de små bogstaver (uden de nu unødvendige dobbelte anførselstegn), jeg har leveret.
-
Brug ikke
varchar(25)som type fororder_nr. Brug baretextuden vilkårlig længdemodifikator, hvis det skal være en streng. Hvis alle ordrenumre udelukkende består af cifre,integerellerbigintville være hurtigere.
Ydeevne
En måde at gøre dette hurtigt på ville være at materialisere udsigten. Dvs. skriv resultatet ind i en (midlertidig) tabel:
CREATE TEMP TABLE tmp_orders AS
SELECT * FROM orders;
ANALYZE tmp_orders; -- temp tables are not auto-analyzed!
ALTER TABLE tmp_orders
ADD constraint orders_pk PRIMARY KEY (order_nr, source);
Du bruger et indeks. I mit eksempel giver den primære nøglebegrænsning indekset automatisk.
Hvis dine borde er store, skal du sørge for at have nok midlertidige buffere at håndtere dette i RAM før du opretter temp-tabellen. Ellers vil det faktisk bremse dig.
SET temp_buffers = 1000MB;
Skal være det første opkald til midlertidige objekter i din session. Sæt det ikke højt globalt, kun for din session. En midlertidig tabel droppes alligevel automatisk i slutningen af din session.
For at få et skøn over, hvor meget RAM du har brug for, skal du oprette tabellen én gang og måle:
SELECT pg_size_pretty(pg_total_relation_size('tmp_orders'));
Mere om objektstørrelser under dette relaterede spørgsmål på dba.SE .
Al overhead betaler sig kun, hvis du skal behandle et antal forespørgsler inden for en session. Til andre brugssager er der andre løsninger. Hvis du kender kildetabellen på tidspunktet for forespørgslen, ville det være meget hurtigere at dirigere din forespørgsel til kildetabellen i stedet for. Hvis du ikke gør det, vil jeg stille spørgsmålstegn ved det unikke ved din order_nr en gang til. Hvis det faktisk er garanteret at være unikt, kan du droppe kolonnen source Jeg introducerede.
For kun én eller nogle få forespørgsler kan det være hurtigere at bruge visningen i stedet for den materialiserede visning.
Jeg ville også overveje en plpgsql-funktion der forespørger den ene tabel efter den anden, indtil posten er fundet. Kan være billigere for et par forespørgsler i betragtning af overhead. Indekser for alle nødvendige bord selvfølgelig.
Også, hvis du holder dig til text eller varchar for din order_nr , overvej COLLATE "C"
for det.