2014-11-20 1 views
2

나는 related question을 읽었지만 사용자 kenthewala와는 달리 데이터베이스에 JSON 객체의 배열을 가져 오려고합니다.json_populate_recordset을 사용하여 단일 JSON 객체의 여러 테이블 채우기

내 JSON 파일은 다음과 같다 다음에 따라 이름

{ 
"tablename_a":[{"a_id":1,"b_id":2,"c_id":3}, 
{"a_id":2,"b_id":51,"c_id":3}], 
"tablename_b":[{"b_id":2,"name":"John Doe", "z_id":123}, 
{"b_id":51,"name":"Mary Ann", "z_id":412}], 
"tablename_c":[{"c_id":3, "OS type":"Windows 7"}], 
"tablename_z":[{"z_id":123, "Whatever":"Something"}, 
{"z_id":123, "Whatever":"Something else"}] 
} 

테이블이 이미 DB에 존재한다. 의사 코드에서

나는

for each key in JSON_FILE as tbl_name 
(
    insert into tbl_name select * from json_populate_recordset 
    (
    null::tbl_name, 'content of tbl_name' 
) 
) 

같은 것을 상상하지만, 이것을 실현하는 방법을 나는 확실하지 않다.

PostgreSQL 9.3.5 (및 PHP 5.3.3이 도움이되는 경우)를 사용하고 있습니다. (필자는 DB에서 원래 JSON을 수출로)

테이블 구조는 JSON 파일과 유사 등등

create table tablename_a (a_id integer, b_id integer, c_id integer); 
create table tablename_b (b_id integer, name text, z_id integer); 

하고 있습니다.

+0

실제 테이블 정의가 좋을 것이다. 'CREATE TABLE ... '. 그리고 항상 Postgres 버전. –

+0

당신 말이 맞아요, 힌트를 주셔서 감사합니다! 그에 따라 내 게시물을 변경했습니다. – Picl

답변

3

3 단계 : JSON 객체 느릅 나무 ->

  1. 액세스 필드.
  2. json_populate_recordset()을 사용하여 레코드의 JSON 배열에서 파생 테이블을 만듭니다.
  3. INSERT 명령의 행 유형을 분해하십시오.

data-modifying CTEs에 싸서, 모든 테이블에 대한 입력 값을 재사용 : SQL Fiddle.

WITH input AS (
    SELECT '{ 
     "tablename_a":[{"a_id":1,"b_id":2,"c_id":3}, 
     {"a_id":2,"b_id":51,"c_id":3}], 
     "tablename_b":[{"b_id":2,"name":"John Doe", "z_id":123}, 
     {"b_id":51,"name":"Mary Ann", "z_id":412}], 
     "tablename_c":[{"c_id":3, "OS type":"Windows 7"}], 
     "tablename_z":[{"z_id":123, "Whatever":"Something"}, 
     {"z_id":123, "Whatever":"Something else"}] 
     }'::json AS j 
    ) 
, a AS (
    INSERT INTO tablename_a 
    SELECT t.* 
    FROM input i 
     , json_populate_recordset(NULL::tablename_a, i.j->'tablename_a') t 
    ) 
, b AS (
    INSERT INTO tablename_b 
    SELECT t.* 
    FROM input i 
     , json_populate_recordset(NULL::tablename_b, i.j->'tablename_b') t 
    ) 
    -- ... more ... 
INSERT INTO tablename_z 
SELECT t.* 
FROM input i 
    , json_populate_recordset(NULL::tablename_z, i.j->'tablename_z') t 
; 

암시 JOIN LATERAL 사용. 관련 적어도 하나 개의 테이블에 대한

+0

감사합니다. 현재이 구문 오류가 발생하지만 올바른 방향으로 나를 안내합니다! 필자는 필자가 기대했던 것처럼 테이블 이름을 어떤 종류의 변수로 추출하는 방법이 있으므로 모든 SELECT 문을 수동으로 작성할 필요가 없음을 인정해야합니다. – Picl

+0

@Picl : 그럴 수도 있지만 동적 SQL이 필요합니다. 나는 많은 관련 답변을 올렸습니다. [검색을 시도하십시오.] (http://stackoverflow.com/questions/tagged/plpgsql+dynamic-sql) 어쨌든 주어진 구조를 가지고 있다면 추가적인 노력이 가치가 있다고 생각하지 않습니다. 구문 오류에 관해서 : 추가 된 바이올린은 내 코드가 작동 함을 증명합니다. –

+0

문제는 저에게 너무 많은 생각이 들었습니다 ^^. 코드를 축약 한 것으로 생각했습니다. 그 때문에 나는 마지막 삽입 문을 'z AS (...);로 둘러 쌌다. 전에 다른 진술과 마찬가지로, 분명히 잘못된 길이었다. 테이블이 많아서 항상 모든 테이블을 한 번에 업데이트하고 싶지는 않을 것 같습니다. 동적 인 방식으로 시도하겠습니다.도움과 제공된 링크에 감사드립니다! – Picl