2011-06-06 11 views
6

Jestem nowy w Postgresql i staram się zbudować funkcję pętli nad serią plików CSV i ładowania ich. Mogę sprawić, aby KOPIUJ działało dobrze z jednym plikiem, ale nie mogę uzyskać poprawnej składni FOR LOOP. Próbuję zastąpić szereg lat jako moje muchy nazwie /path/tmp.YEAR.out.csvplpgsql: łączenie zmiennej w klauzulę FROM

To co ja włamał się:

CREATE OR REPLACE FUNCTION test() RETURNS void as $$ 
BEGIN 
    FOR i IN 1982..1983 LOOP 
    COPY myTable 
    FROM '/path/tmp.' || i::VARCHAR || '.out.csv' 
    delimiters ',' 
    END LOOP; 
END; 
$$ LANGUAGE 'plpgsql'; 

to zgłasza błąd u pierwszy ||. Podejrzewam, że nieprawidłowo zarządzam zmienną zmiennej i. Jakieś wskazówki?

+0

Czy możemy dodać znacznik "r" i rozwiązać go w ten sposób? –

+0

Oczywiście myślałem o tym ... ale potrzebowałem szybkiego załadowania polecenia COPY POGESQL ... Mam kilka tuzinów plików ~ 500MB. –

+0

@dirk, jeśli mam przetasować ciąg zapytania w R, czy mogę go przesłać jako zapytanie? Myślałem, że mogę to zrobić tylko za pomocą zwykłego sql, a nie plpgsql, więc nawet nie spróbowałem. –

Odpowiedz

6
CREATE OR REPLACE FUNCTION test() RETURNS void as $$ 
BEGIN 
FOR i IN 1982..1983 LOOP 
    EXECUTE 'COPY myTable FROM ''/path/tmp.' || i::text 
              || '.out.csv'' DELIMITERS '',''; '; 
END LOOP; 
END; 
$$ language plpgsql; 
+0

Dzięki Seth. Byłem pewien, że miało to związek z przetwarzaniem i porządkowaniem w odpowiedniej kolejności. Na pewno nie zdekodowałbym tego bez pomocy. –

5

Nie sądzę, bym użył plpgsql do tego. Skrypt powłoki może być znacznie bardziej ogólnie przydatne:

#!/bin/sh 

DBHOST=mydbhost 
DBNAME=mydbname 

files=$1 
target=$2 

for file in ${files}; do 
    psql -h ${DBHOST} ${DBNAME} -c "\copy ${target} FROM '${file}' delimiters ','" 
done 

przykład użycia:

csv2psql "$(ls *.out.csv)" someschema.tablename 

Uwaga: W ten sposób można również ominąć problem odczytu plików z egzemplarzem wymaga od użytkownika serwera PostgreSQL do przeczytałeś uprawnienia do pliku.

+1

używając komendy psql \ copy mógłbym to owinąć w dowolnym języku. Sprytne podejście. Dzięki! –

Powiązane problemy