Postgres 클라이언트 복사 (\ copy) 명령에 ' 임시 테이블에 대한 액세스 권한이 없습니까?

최종적으로 psql -f를 사용하여 실행하는 일부 데이터를 내보내는 SQL 명령 목록을 생성하고 있습니다. 쿼리는 모두 동일한 데이터 하위 집합을 가져옵니다. 그래서 자격을 고려하여 자격을 갖춘 사용자 ID 목록을 임시 테이블에 넣었다고 생각했습니다.

create temporary table tmp_export_users as (select id from users where ...) 

그런 다음 내 \ copy 명령은 다음과 같습니다.

\copy (select ... from table where user_id in (select id from tmp_export_users)) TO "filename.csv" WITH CSV HEADER 

모두 한 줄에 하나씩 동일한 파일에 있으며 실행 중입니다. -f 복사 명령이 할 수있는 오류가 발생합니다. ” t 임시 테이블을 보면 클라이언트 복사 명령이 실제로 psql과 동일한 postgres 세션을 사용해서는 안된다고 생각합니다.

맞습니까? 해당 동작을 변경할 수있는 방법이 있습니까?

답변

\copy 임시 테이블을 사용할 수 있습니다 .

먼저 9.0 명령 줄에서.
그런 다음 SQL 및 psql 메타 명령 \copy를 사용하여 파일을 만들었습니다. 여러 임시 테이블. 저에게도 도움이되었습니다.

CREATE TEMP TABLE tmp as SELECT * FROM tbl; \copy (SELECT * FROM tmp JOIN tbl USING (id)) TO "/var/lib/postgres/test1.csv"; 

전화 :

psql -p5432 mydb -f test.sql 

종료 세미콜론 : 파일 의 끝에서 선택 사항 (암시 적으로 종료 됨)이지만 다른 SQL 문 다음에 필요하고 psql에서 대화식으로 실행되는 경우 마지막 문 뒤에 필요합니다.

일반적으로 , psql 메타 명령은 같은 줄에서 SQL 와 함께 사용할 수 없습니다. psql -f에 따라 실행되는 파일의 . psql 설명서 를 인용합니다.

인수 파싱이 끝에서 중지됩니다. 또는 인용되지 않은 다른 백 슬래시가 발견 될 때. 인용되지 않은 백 슬래시는 새 메타 명령의 시작으로 간주됩니다. 특수 시퀀스 \\ (두 개의 백 슬래시)는 인수의 끝을 표시하고 SQL 명령 (있는 경우)을 계속 구문 분석합니다. 이렇게하면 SQL 및 psql 명령을 한 줄에 자유롭게 혼합 할 수 있습니다. 그러나 어떠한 경우에도 메타 명령의 인수는 줄 끝을 넘어서 계속 될 수 없습니다.

다른 규칙이 이후 \copy입니다. 기본적으로 psql은 \copy 이후 자동으로 SQL 모드로 다시 전환됩니다. 참조 :

하지만 모든 명령이 별도의 행에 있다고 작성했습니다. 따라서 귀하의 경우에는 설명 할 수 없습니다.


그것만 제외하고 COPY\copy 대신 div> ( SQL 명령 ) ( psql 메타 명령 )?

물론 대상 파일은 이 경우 클라이언트가 아닌 서버에 로컬입니다. 그리고 다른 파일 권한이 적용됩니다. 설명서 :

COPY 명령은 클라이언트 응용 프로그램이 아닌 서버에서 직접 읽거나 씁니다. 따라서 클라이언트가 아닌 데이터베이스 서버 시스템에 상주하거나 액세스 할 수 있어야합니다. 클라이언트가 아닌 PostgreSQL 사용자 (서버가 실행되는 사용자 ID)가 액세스하고 읽고 쓸 수 있어야합니다.

댓글

  • copy는 postgres 사용자로 실행되고, \ copy는 복사를 랩핑하여 std에 쓰고 전송 한 파일로 리디렉션됩니다. psql을 호출하고 \ o를 사용하여 출력을 파일로 보낸 다음 stdout에 복사본을 실행하여 비슷한 효과를 얻을 수도 있습니다.
  • 내 대답에서 슈퍼 유저 (postgres)로 테스트를 실행했는지 확인하려면 ) 및 더미 사용자. 둘 다 나를 위해 일합니다. v8.4에서도 동일한 결과가 나타납니다.
  • 예, postgres 유닉스 사용자가 / tmp와 같은 항목에 액세스 할 수 있는지 여부는 SELinux가 설치되었는지 여부와 상자에서 꺼낼 수 있는지 여부에 따라 다릅니다. \ copy 또는 copy to stdout은 확실히 copy를 사용하는 더 신뢰할 수있는 두 가지 방법입니다.
  • 모두의 답변에 감사드립니다. 세미콜론으로 임시 테이블을 만든 줄을 끝내지 않은 것 같아서 ' 생성되지 않았습니다. 지금 예상대로 작동합니다.

답글 남기기

이메일 주소를 발행하지 않을 것입니다. 필수 항목은 *(으)로 표시합니다