sql >> Database teknologi >  >> RDS >> Sqlserver

Sådan importeres en JSON-fil til en SQL Server-tabel

Hvis du har et JSON-dokument, er der flere måder, du kan gå for at få det ind i SQL Server.

Hvis det er et lille dokument, kan du kopiere og indsætte dets indhold. Hvis det er et større dokument (eller endda et lille), vil du måske importere hele filen.

Denne artikel præsenterer et eksempel på import af en JSON-fil til en SQL Server-database.

Valg af indholdet af JSON-filen

T-SQL inkluderer OPENROWSET() funktion, der kan læse data fra enhver fil på det lokale drev eller netværk og returnere det som et rækkesæt. For at gøre det skal du udføre denne funktion med BULK mulighed.

Selvom denne artikel er skrevet specifikt til at importere JSON-filen til en tabel, kan du også bruge OPENROWSET() at læse fra en datafil uden nødvendigvis at indlæse den i en tabel.

Dette giver dig mulighed for at tjekke dataene først, før de indlæses i tabellen.

Her er et eksempel på valg af indholdet af en JSON-fil.

SELECT BulkColumn FROM OPENROWSET (
    BULK '/var/opt/mssql/bak/pets.json', 
    SINGLE_CLOB
    ) AS [Json]; 

Resultat:

+--------------+| BulkColumn ||--------------|| { "pets" :{ "cats" :[ { "id" :1, "name" :"Fluffy", "sex" :"Kvinde" }, { "id" :2, "name" :"Long Tail" , "sex" :"Kvinde" }, { "id" :3, "name" :"Scratch", "sex" :"Han" } ], "hunde" :[ { "id" :1, "name" :"Fetch", "sex" :"Mand" }, { "id" :2, "name" :"Fluffy", "sex" :"Mand" }, { "id" :3, "name" :" Wag", "sex" :"Kvinde" } ] }} |+--------+

I dette tilfælde er filsystemet Linux, og derfor bruges Linux-stikonventionerne, når man angiver, hvilken fil der skal uploades.

Hvis du er på Windows, ser din filsti måske mere ud som denne:

SELECT BulkColumn FROM OPENROWSET (
    BULK 'D:\data\pets.json', 
    SINGLE_CLOB
    ) AS [Json]; 

Under alle omstændigheder kan vi se indholdet af JSON-filen ovenfor. Lad os nu indlæse det i en tabel.

Indlæs det i en tabel

Vi kan ændre den tidligere sætning, så filens indhold importeres direkte ind i en tabel.

-- Import it directly into the table
SELECT BulkColumn INTO ImportedJson FROM OPENROWSET (
    BULK '/var/opt/mssql/bak/pets.json', 
    SINGLE_CLOB
    ) AS [Json];

-- Select the contents of the table
SELECT * FROM ImportedJson; 

Resultat:

+--------------+| BulkColumn ||--------------|| { "pets" :{ "cats" :[ { "id" :1, "name" :"Fluffy", "sex" :"Kvinde" }, { "id" :2, "name" :"Long Tail" , "sex" :"Kvinde" }, { "id" :3, "name" :"Scratch", "sex" :"Han" } ], "hunde" :[ { "id" :1, "name" :"Fetch", "sex" :"Mand" }, { "id" :2, "name" :"Fluffy", "sex" :"Mand" }, { "id" :3, "name" :" Wag", "sex" :"Kvinde" } ] }} |+--------+

Hvis du gør det, oprettes tabellen og indsætter JSON.

Bemærk, at når du bruger OPENROWSET() med BULK mulighed, skal du også angive et korrelationsnavn (også kendt som en intervalvariabel eller alias) i FROM klausul.

Hvis du ikke angiver et korrelationsnavn, får du en fejl.

I mit eksempel brugte jeg Json som korrelationsnavnet, men vælg gerne dit eget.

Parser JSON i rækker og kolonner

Det er her, tingene bliver spændende. Ikke alene kan vi uploade indholdet af en fil og importere den til en tabelkolonne, vi kan også adskille dens indhold på tværs af flere rækker og kolonner.

OPENJSON() er en funktion med tabelværdi, der konverterer JSON-dokumenter til et tabelformat.

Derfor kan vi bruge OPENJSON() at konvertere indholdet af vores JSON-fil til tabelformat, og indsætte det i en tabel eller flere tabeller, hvis det er målet.

Men igen, vi kan tjekke vores data, før vi indsætter dem i nogen tabeller.

-- Select the cats
SELECT Cats.* FROM OPENROWSET (
    BULK '/var/opt/mssql/bak/pets.json', 
    SINGLE_CLOB) AS [Json]
    CROSS APPLY OPENJSON ( BulkColumn, '$.pets.cats' )
    WITH  (
            CatId     int             '$.id',  
            CatName   varchar(60)     '$.name', 
            Sex       varchar(6)      '$.sex'  
        ) AS [Cats]

-- Select the dogs
SELECT Dogs.* FROM OPENROWSET (
    BULK '/var/opt/mssql/bak/pets.json', 
    SINGLE_CLOB) AS [Json]    
    CROSS APPLY OPENJSON ( BulkColumn, '$.pets.dogs' )
    WITH  (
            DogId     int             '$.id',  
            DogName   varchar(60)     '$.name', 
            Sex       varchar(6)      '$.sex'  
        ) AS [Dogs] 

Resultat:

+--------+-----------+--------+| CatId | Kattenavn | Køn ||--------+-----------+--------|| 1 | Fluffy | Kvinde || 2 | Lang hale | Kvinde || 3 | Ridse | Mand |+--------+------------+--------+(3 rækker påvirket)+--------+ ----------+--------+| DogId | Hundenavn | Køn ||--------+-----------+--------|| 1 | Hent | Mand || 2 | Fluffy | Mand || 3 | Wag | Kvinde |+--------+-----------+--------+(3 rækker påvirket)

Sådan vil det se ud, når det først er indsat i to tabeller.

For at indsætte det i tabellerne er det eneste, vi skal gøre, at tilføje INTO TableName mellem SELECT del og FROM (hvor TableName er navnet på den tabel, vi vil oprette).

-- Insert cats into a table SELECT Cats.* INTO ImportedCats FROM OPENROWSET ( BULK '/var/opt/mssql/bak/pets.json', SINGLE_CLOB) AS [Json] CROSS APPLY OPENJSON ( BulkColumn, '$.pets.cats' ) WITH ( CatId int '$.id', CatName varchar(60) '$.name', Sex varchar(6) '$.sex' ) AS [Cats] -- Insert dogs into a table SELECT Dogs.* INTO ImportedDogs FROM OPENROWSET ( BULK '/var/opt/mssql/bak/pets.json', SINGLE_CLOB) AS [Json] CROSS APPLY OPENJSON ( BulkColumn, '$.pets.dogs' ) WITH ( DogId int '$.id', DogName varchar(60) '$.name', Sex varchar(6) '$.sex' ) AS [Dogs] -- Select the results from both tables SELECT * FROM ImportedCats SELECT * FROM ImportedDogs

Resultat:

+--------+-----------+--------+| CatId | Kattenavn | Køn ||--------+-----------+--------|| 1 | Fluffy | Kvinde || 2 | Lang hale | Kvinde || 3 | Ridse | Mand |+--------+------------+--------+(3 rækker påvirket)+--------+ ----------+--------+| DogId | Hundenavn | Køn ||--------+-----------+--------|| 1 | Hent | Mand || 2 | Fluffy | Mand || 3 | Wag | Kvinde |+--------+-----------+--------+(3 rækker påvirket)

Disse tabeller blev oprettet ved hjælp af de kolonnedefinitioner, vi leverede i WITH klausul.

Hver JSON-nøgle er knyttet til et kolonnenavn efter vores valg.

Du kan også basere dine kolonnenavne ud fra nøglenavnene i JSON-filen. Hvis du gør det, behøver du ikke at kortlægge dem med en sti, som OPENJSON() vil automatisk matche dem med JSON-nøglenavnene.

For eksempel i stedet for at bruge følgende WITH-sætning:

WITH  (
            DogId     int             '$.id',  
            DogName   varchar(60)     '$.name', 
            Sex       varchar(6)      '$.sex'  
        ) AS [Dogs] 

Du kan bruge dette:

WITH  (
        id     int,  
        name   varchar(60), 
        sex    varchar(6)  
    ) AS [Dogs] 

Indlæs JSON i en variabel

En anden måde at gøre det på ville være at indlæse den uploadede JSON i en variabel og derefter overføre denne variabel til OPENJSON() funktion.

-- Declare variable
DECLARE @json nvarchar(max);

-- Upload JSON data into that variable
SELECT @json = BulkColumn FROM OPENROWSET (
    BULK '/var/opt/mssql/bak/pets.json', 
    SINGLE_CLOB
    ) AS [Json];

-- Select the cats from that variable
SELECT * FROM OPENJSON(@json, '$.pets.cats')
WITH  (
        CatId     int             '$.id',  
        CatName   varchar(60)     '$.name', 
        Sex       varchar(6)      '$.sex'   
    );

-- Select the dogs from that variable
SELECT * FROM OPENJSON(@json, '$.pets.dogs')
WITH  (
        DogId     int             '$.id',  
        DogName   varchar(60)     '$.name', 
        Sex       varchar(6)      '$.sex'  
    ); 

Resultat:

+--------+-----------+--------+| CatId | Kattenavn | Køn ||--------+-----------+--------|| 1 | Fluffy | Kvinde || 2 | Lang hale | Kvinde || 3 | Ridse | Mand |+--------+------------+--------+(3 rækker påvirket)+--------+ ----------+--------+| DogId | Hundenavn | Køn ||--------+-----------+--------|| 1 | Hent | Mand || 2 | Fluffy | Mand || 3 | Wag | Kvinde |+--------+-----------+--------+(3 rækker påvirket)

Igen, for at indsætte dette i en tabel, ville vi tilføje INTO TableName efter SELECT del (hvor TableName er navnet på den tabel, du vil oprette).

Indlæs et helt underobjekt i en kolonne

Hvis du ønskede, at hele underobjekter skulle ligge i deres egen kolonne, kan du bruge AS JSON mulighed for WITH klausul.

For eksempel, i stedet for at have hver kat og hund fordelt på tre kolonner, kan hele deres JSON-fragment fylde én kolonne. Hvert dyr vil stadig have deres egen række.

Her er et eksempel på, hvad jeg mener.

SELECT Cats.* FROM OPENROWSET (
    BULK '/var/opt/mssql/bak/pets.json', 
    SINGLE_CLOB) AS [Json]
    CROSS APPLY OPENJSON ( BulkColumn, '$.pets.cats' )
    WITH  (
            Cats nvarchar(max) '$' AS JSON   
        ) AS [Cats]

SELECT Dogs.* FROM OPENROWSET (
    BULK '/var/opt/mssql/bak/pets.json', 
    SINGLE_CLOB) AS [Json]    
    CROSS APPLY OPENJSON ( BulkColumn, '$.pets.dogs' )
    WITH  (
            Dogs nvarchar(max) '$' AS JSON   
        ) AS [Dogs] 

Resultat:

+---------------------------------------------- --------+| Katte ||------------------------------------------------------ -------|| { "id" :1, "name" :"Fluffy", "sex" :"Kvinde" } || { "id" :2, "name" :"Lang hale", "sex" :"Kvinde" } || { "id" :3, "name" :"Scratch", "sex" :"Mand" } |+-------------------------------- ------------------------------+(3 rækker påvirket)+-------- -----------------------------------+| Hunde ||------------------------------------------------------ --|| { "id" :1, "name" :"Hent", "sex" :"Mand" } || { "id" :2, "name" :"Fluffy", "sex" :"Mand" } || { "id" :3, "name" :"Wag", "sex" :"Kvinde" } |+-------------------------------- ------------------------+(3 rækker påvirket)


  1. SQL-masseimport fra CSV

  2. Trigger for at håndhæve M-M-forhold

  3. SQL Server Management Studio-alternativer til at gennemse/redigere tabeller og køre forespørgsler

  4. Hvad er PL/SQL-lagrede procedurer i Oracle-databasen