Convertire CSV in JSON con Python — Guida json.dumps()

·Backend Developer·Revisionato daPriya Sharma·Pubblicato

Usa il Da CSV a JSON gratuito direttamente nel tuo browser — nessuna installazione.

Prova Da CSV a JSON online →

I file CSV sono ovunque — report esportati, dump di database, estratti di log — e prima o poi è necessario convertire quel CSV in JSON con Python. La libreria standard gestisce questo con due moduli: csv.DictReader trasforma ogni riga in un dict Python, e json.dumps() serializza quei dict in una stringa JSON. Per una conversione rapida senza codice, il convertitore CSV in JSON lo fa istantaneamente nel browser. Questa guida copre il percorso programmatico completo: json.dump() vs json.dumps(), scrittura di JSON su file, serializzazione di dataclass, coercizione dei tipi per i valori CSV, gestione di datetime e Decimal, e alternative ad alte prestazioni come orjson. Tutti gli esempi sono per Python 3.10+.

  • csv.DictReader produce una lista di dict — serializza la lista completa con json.dump(rows, f, indent=2) per scrivere un file JSON.
  • json.dump() scrive direttamente su un oggetto file. json.dumps() restituisce una stringa. Scegliere quello giusto evita una copia inutile.
  • I valori CSV sono sempre stringhe. Converti esplicitamente le colonne numeriche (int(), float()) prima di serializzare in JSON.
  • Passa ensure_ascii=False a json.dumps() per preservare i caratteri Unicode — nomi accentati, testo CJK — nell'output.
  • Per datetime, UUID o Decimal provenienti da CSV, usa il parametro default= con una funzione di fallback personalizzata.
Before · json
After · json
order_id,product,quantity,price
ORD-7291,Wireless Keyboard,2,49.99
ORD-7292,USB-C Hub,1,34.50
[
  {
    "order_id": "ORD-7291",
    "product": "Wireless Keyboard",
    "quantity": "2",
    "price": "49.99"
  },
  {
    "order_id": "ORD-7292",
    "product": "USB-C Hub",
    "quantity": "1",
    "price": "34.50"
  }
]
Nota:Nota che quantity e price appaiono come stringhe JSON ("2", "49.99") nell'output grezzo. CSV non ha un sistema di tipi — ogni valore è una stringa. La correzione è trattata nella sezione sulla coercizione dei tipi più avanti.

json.dumps() — Serializzare un Dict Python in una Stringa JSON

Il modulo json è incluso in ogni installazione Python — nessun pip install necessario. json.dumps(obj) prende un oggetto Python (dict, list, stringa, numero, bool o None) e restituisce una str contenente JSON valido. Un dizionario Python sembra simile a un oggetto JSON, ma sono fondamentalmente diversi: un dict è una struttura dati Python in memoria, mentre una stringa JSON è testo serializzato. Chiamare json.dumps() colma questa differenza.

Esempio minimale — Singola riga CSV in JSON

Python 3.10+
import json

# Una singola riga CSV rappresentata come dict Python
server_entry = {
    "hostname": "web-prod-03",
    "ip_address": "10.0.12.47",
    "port": 8080,
    "region": "eu-west-1"
}

# Converti il dict in stringa JSON
json_string = json.dumps(server_entry)
print(json_string)
# {"hostname": "web-prod-03", "ip_address": "10.0.12.47", "port": 8080, "region": "eu-west-1"}
print(type(json_string))
# <class 'str'>

Questo produce JSON compatto su una riga — ottimo per payload e storage, pessimo per la leggibilità. Aggiungi indent=2 per un output leggibile dall'uomo:

Python 3.10+ — output formattato
import json

server_entry = {
    "hostname": "web-prod-03",
    "ip_address": "10.0.12.47",
    "port": 8080,
    "region": "eu-west-1"
}

pretty_json = json.dumps(server_entry, indent=2)
print(pretty_json)
# {
#   "hostname": "web-prod-03",
#   "ip_address": "10.0.12.47",
#   "port": 8080,
#   "region": "eu-west-1"
# }

Altri due parametri che uso in quasi ogni chiamata: sort_keys=True ordina alfabeticamente le chiavi del dizionario (ottimo per il diff di file JSON tra versioni), e ensure_ascii=False preserva i caratteri non-ASCII invece di fare l'escape in sequenze \uXXXX.

Python 3.10+ — sort_keys e ensure_ascii
import json

warehouse_record = {
    "sku": "WH-9031",
    "location": "Magazzino Milano 3",
    "quantity": 240,
    "last_audit": "2026-03-10"
}

output = json.dumps(warehouse_record, indent=2, sort_keys=True, ensure_ascii=False)
print(output)
# {
#   "last_audit": "2026-03-10",
#   "location": "Magazzino Milano 3",
#   "quantity": 240,
#   "sku": "WH-9031"
# }

Una nota rapida sul parametro separators: il default è (", ", ": ") che aggiunge spazi dopo le virgole e i due punti. Per l'output più compatto possibile (utile quando si incorpora JSON nei parametri URL o si vuole ridurre i byte nelle risposte API), passa separators=(",", ":").

Nota:Un dict Python e un oggetto JSON sembrano quasi identici quando vengono stampati. La differenza: json.dumps() converte True di Python in true JSON, None in null, e racchiude le stringhe tra virgolette doppie (Python accetta virgolette singole, JSON no). Usa sempre json.dumps() per produrre JSON valido — non affidarti a str() o repr().

Da csv.DictReader a File JSON — La Pipeline Completa

Il compito più comune nel mondo reale è leggere un intero file CSV e salvarlo come JSON. Ecco lo script end-to-end in meno di 10 righe. csv.DictReader produce un iteratore di oggetti dict — uno per riga, usando la prima riga come chiavi. Racchiuderlo in list() raccoglie tutte le righe in una lista Python, che si serializza in un array JSON.

Python 3.10+ — conversione completa da CSV a JSON
import csv
import json

# Passo 1: leggi le righe CSV in una lista di dict
with open("inventory.csv", "r", encoding="utf-8") as csv_file:
    rows = list(csv.DictReader(csv_file))

# Passo 2: scrivi la lista come file JSON
with open("inventory.json", "w", encoding="utf-8") as json_file:
    json.dump(rows, json_file, indent=2, ensure_ascii=False)

print(f"Convertite {len(rows)} righe in inventory.json")

Due chiamate open(): una per leggere il CSV, una per scrivere il JSON. Questo è tutto il pattern. Nota che usa json.dump() (senza la s) — scrive direttamente sull'handle del file. Usare json.dumps() restituirebbe una stringa che poi andrebbero a scrivere separatamente con f.write(). json.dump() è più efficiente in termini di memoria perché trasmette l'output in streaming invece di costruire l'intera stringa in memoria prima.

Quando hai bisogno del JSON come stringa invece che come file — per incorporarlo in un payload API, stamparlo su stdout, o inserirlo in una colonna di database — passa a json.dumps():

Python 3.10+ — righe CSV come stringa JSON
import csv
import json

with open("sensors.csv", "r", encoding="utf-8") as f:
    rows = list(csv.DictReader(f))

# Ottieni il JSON come stringa invece di scrivere su file
json_payload = json.dumps(rows, indent=2)
print(json_payload)
# [
#   {
#     "sensor_id": "TMP-4401",
#     "location": "Edificio 7 - Piano 2",
#     "reading": "22.4",
#     "unit": "celsius"
#   },
#   ...
# ]

Riga singola vs. dataset completo: chiamando json.dumps(single_dict) si ottiene un oggetto JSON ({...}). Chiamando json.dumps(list_of_dicts) si ottiene un array JSON ([{...}, {...}]). La forma del contenitore esterno dipende da cosa si passa. La maggior parte dei consumer a valle si aspetta un array per i dati tabulari.

Gestione dei Valori non Stringa — Coercizione dei Tipi da CSV

Ecco l'insidia che coglie tutti la prima volta: csv.DictReader restituisce ogni valore come stringa. Il numero 42 nel CSV diventa la stringa "42" nel dict. Se lo serializzi direttamente con json.dumps(), il JSON avrà "quantity": "42" invece di "quantity": 42. Le API che validano i tipi lo rifiuteranno. È necessario convertire i valori esplicitamente.

Python 3.10+ — coercizione dei tipi per le righe CSV
import csv
import json

def coerce_types(row: dict) -> dict:
    """Converti i valori stringa nei tipi Python appropriati."""
    return {
        "sensor_id": row["sensor_id"],
        "location": row["location"],
        "temperature": float(row["temperature"]),
        "humidity": float(row["humidity"]),
        "battery_pct": int(row["battery_pct"]),
        "active": row["active"].lower() == "true",
    }

with open("sensor_readings.csv", "r", encoding="utf-8") as f:
    rows = [coerce_types(row) for row in csv.DictReader(f)]

print(json.dumps(rows[0], indent=2))
# {
#   "sensor_id": "TMP-4401",
#   "location": "Edificio 7 - Piano 2",
#   "temperature": 22.4,
#   "humidity": 58.3,
#   "battery_pct": 87,
#   "active": true
# }

Ora temperature è un float, battery_pct è un intero, e active è un booleano nell'output JSON. La funzione di coercizione è specifica per lo schema del CSV — non esiste un modo generico per indovinare i tipi dai dati CSV, quindi si scrive una funzione per ogni formato CSV.

Serializzazione di Oggetti Personalizzati e Tipi Non Standard

Il modulo json di Python non riesce a serializzare datetime, UUID, Decimal, o classi personalizzate direttamente. Chiamare json.dumps() su uno di questi solleva un TypeError. Due approcci risolvono questo problema.

Approccio 1: Il Parametro default=

Passa una funzione a default= che converte i tipi sconosciuti in qualcosa di serializzabile. Questa funzione viene chiamata solo per gli oggetti che il codificatore JSON non sa come gestire.

Python 3.10+ — default= per datetime, UUID, Decimal
import json
from datetime import datetime
from decimal import Decimal
from uuid import UUID

def json_serial(obj):
    """Serializzatore di fallback per tipi non standard."""
    if isinstance(obj, datetime):
        return obj.isoformat()
    if isinstance(obj, UUID):
        return str(obj)
    if isinstance(obj, Decimal):
        return float(obj)
    raise TypeError(f"Type {type(obj).__name__} is not JSON serializable")

transaction = {
    "txn_id": UUID("a1b2c3d4-e5f6-7890-abcd-ef1234567890"),
    "amount": Decimal("149.99"),
    "currency": "EUR",
    "processed_at": datetime(2026, 3, 15, 14, 30, 0),
    "gateway": "stripe",
}

print(json.dumps(transaction, indent=2, default=json_serial))
# {
#   "txn_id": "a1b2c3d4-e5f6-7890-abcd-ef1234567890",
#   "amount": 149.99,
#   "currency": "EUR",
#   "processed_at": "2026-03-15T14:30:00",
#   "gateway": "stripe"
# }
Attenzione:Solleva sempre TypeError alla fine della funzione default= per i tipi non riconosciuti. Se restituisci None o li salti silenziosamente, ottieni null nell'output senza alcuna indicazione che i dati sono stati persi.

Approccio 2: Dataclass con asdict()

Le dataclass Python danno alle righe CSV una definizione di tipo appropriata. Usa dataclasses.asdict() per convertire un'istanza di dataclass in un dict semplice, poi passalo a json.dumps().

Python 3.10+ — serializzazione di dataclass
import json
from dataclasses import dataclass, asdict
from datetime import datetime

@dataclass
class ShipmentRecord:
    tracking_id: str
    origin: str
    destination: str
    weight_kg: float
    shipped_at: datetime

def json_serial(obj):
    if isinstance(obj, datetime):
        return obj.isoformat()
    raise TypeError(f"Not serializable: {type(obj).__name__}")

shipment = ShipmentRecord(
    tracking_id="SHP-9827",
    origin="Genova",
    destination="Roma",
    weight_kg=1240.5,
    shipped_at=datetime(2026, 3, 12, 8, 0, 0),
)

print(json.dumps(asdict(shipment), indent=2, default=json_serial))
# {
#   "tracking_id": "SHP-9827",
#   "origin": "Genova",
#   "destination": "Roma",
#   "weight_kg": 1240.5,
#   "shipped_at": "2026-03-12T08:00:00"
# }
Nota:asdict() converte ricorsivamente le dataclass annidate in dict. Se la dataclass contiene una lista di altre dataclass, l'intero albero viene convertito — senza codice aggiuntivo.

Riferimento Parametri di json.dumps()

Elenco completo degli argomenti keyword accettati da json.dumps() e json.dump(). Entrambe le funzioni accettano parametri identici — json.dump() prende un argomento posizionale aggiuntivo per l'oggetto file.

Parametro
Tipo
Default
Descrizione
obj
Any
(obbligatorio)
L'oggetto Python da serializzare — dict, list, str, int, float, bool, None
indent
int | str | None
None
Numero di spazi (o una stringa) per livello di indentazione. None = output compatto su una riga
sort_keys
bool
False
Ordina alfabeticamente le chiavi del dizionario nell'output
ensure_ascii
bool
True
Fa l'escape di tutti i caratteri non-ASCII come \\uXXXX. Impostare False per emettere UTF-8 direttamente
default
Callable | None
None
Funzione chiamata per oggetti non serializzabili di default — restituisce un valore serializzabile o solleva TypeError
separators
tuple[str, str] | None
None
Sovrascrive (separatore_elementi, separatore_chiavi). Usare (",", ":") per output compatto senza spazi
skipkeys
bool
False
Salta le chiavi del dict che non sono str, int, float, bool o None invece di sollevare TypeError
allow_nan
bool
True
Permette float("nan"), float("inf"), float("-inf"). Impostare False per sollevare ValueError su questi valori
cls
Type[JSONEncoder] | None
None
Sottoclasse JSONEncoder personalizzata da usare al posto di quella di default

csv.DictReader — Lettura di CSV in Dict Python

csv.DictReader è l'altra metà della pipeline CSV-to-JSON. Racchiude un oggetto file e produce un dict per riga, usando la prima riga come nomi dei campi. Rispetto a csv.reader (che produce liste semplici), DictReader offre accesso nominato alle colonne — niente indici magici come row[3].

Python 3.10+ — DictReader con delimitatore personalizzato
import csv
import json

# File separato da tabulazioni da un export di database
with open("user_sessions.tsv", "r", encoding="utf-8") as f:
    reader = csv.DictReader(f, delimiter="\t")
    sessions = list(reader)

print(json.dumps(sessions[:2], indent=2))
# [
#   {
#     "session_id": "sess_8f2a91bc",
#     "user_id": "usr_4421",
#     "started_at": "2026-03-15T09:12:00Z",
#     "duration_sec": "342",
#     "pages_viewed": "7"
#   },
#   {
#     "session_id": "sess_3c7d44ef",
#     "user_id": "usr_1187",
#     "started_at": "2026-03-15T09:14:22Z",
#     "duration_sec": "128",
#     "pages_viewed": "3"
#   }
# ]
Attenzione:csv.DictReader legge l'intero file in modo lazy — produce le righe una alla volta. Chiamare list(reader) carica tutte le righe in memoria. Per file con milioni di righe, elabora le righe in modalità streaming invece di raccoglierle tutte.

Convertire CSV da File e Risposta API

Due scenari di produzione: leggere un file CSV dal disco e convertirlo, e recuperare dati CSV da un endpoint API (molti servizi di reportistica restituiscono CSV). Entrambi richiedono una gestione appropriata degli errori.

Leggi File CSV → Converti → Scrivi JSON

Python 3.10+ — conversione file con gestione degli errori
import csv
import json
import sys

def csv_to_json_file(csv_path: str, json_path: str) -> int:
    """Converti un file CSV in JSON. Restituisce il numero di righe scritte."""
    try:
        with open(csv_path, "r", encoding="utf-8") as f:
            rows = list(csv.DictReader(f))
    except FileNotFoundError:
        print(f"Error: {csv_path} not found", file=sys.stderr)
        sys.exit(1)
    except csv.Error as e:
        print(f"CSV parse error in {csv_path}: {e}", file=sys.stderr)
        sys.exit(1)

    with open(json_path, "w", encoding="utf-8") as f:
        json.dump(rows, f, indent=2, ensure_ascii=False)

    return len(rows)

count = csv_to_json_file("fleet_vehicles.csv", "fleet_vehicles.json")
print(f"Scritti {count} record in fleet_vehicles.json")

Recupera CSV da API → Analizza → JSON

Python 3.10+ — risposta API CSV in JSON
import csv
import io
import json
import urllib.request

def fetch_csv_as_json(url: str) -> str:
    """Recupera CSV da un URL e restituiscilo come stringa JSON."""
    try:
        with urllib.request.urlopen(url, timeout=10) as resp:
            raw = resp.read().decode("utf-8")
    except urllib.error.URLError as e:
        raise RuntimeError(f"Failed to fetch {url}: {e}")

    reader = csv.DictReader(io.StringIO(raw))
    rows = list(reader)

    if not rows:
        raise ValueError("CSV response was empty or had no data rows")

    return json.dumps(rows, indent=2, ensure_ascii=False)

# Esempio: endpoint di export che restituisce CSV
try:
    result = fetch_csv_as_json("https://reports.internal/api/v2/daily-metrics.csv")
    print(result)
except (RuntimeError, ValueError) as e:
    print(f"Error: {e}")

Entrambi gli esempi usano encoding="utf-8" esplicito su ogni apertura di file. Questo è importante per i file CSV con caratteri non-ASCII — nomi accentati, indirizzi con caratteri speciali, testo CJK. Senza codifica esplicita, Python usa il default di sistema, che su Windows è spesso cp1252 e corrompe silenziosamente i caratteri multibyte.

Verifica dell'Output JSON con json.loads()

Dopo aver convertito CSV in una stringa JSON, puoi verificare il risultato analizzandolo di nuovo con json.loads(). Questo round-trip intercetta problemi di codifica, sequenze di escape non valide, o concatenazioni accidentali di stringhe che produrrebbero JSON non valido. Racchiudi la chiamata in un blocco try/except.

Python 3.10+ — validazione round-trip
import json

json_string = json.dumps({"order_id": "ORD-7291", "total": 129.99})

# Verifica che sia JSON valido analizzandolo di nuovo
try:
    parsed = json.loads(json_string)
    print(f"Valid JSON with {len(parsed)} keys")
except json.JSONDecodeError as e:
    print(f"Invalid JSON: {e}")
# Valid JSON with 2 keys

Conversione CSV in JSON dalla Riga di Comando

Conversioni rapide dal terminale — nessun file script necessario. Il flag -c di Python esegue codice inline, e puoi reindirizzare il risultato attraverso python3 -m json.tool per la formattazione.

bash — one-liner CSV in JSON
python3 -c "
import csv, json, sys
rows = list(csv.DictReader(sys.stdin))
json.dump(rows, sys.stdout, indent=2)
" < inventory.csv > inventory.json
bash — pipe file CSV e formatta con json.tool
python3 -c "import csv,json,sys; print(json.dumps(list(csv.DictReader(sys.stdin))))" < data.csv | python3 -m json.tool
bash — converti e valida con jq
python3 -c "import csv,json,sys; json.dump(list(csv.DictReader(sys.stdin)),sys.stdout)" < report.csv | jq .
Nota:python3 -m json.tool è il formattatore JSON integrato. Legge JSON da stdin, lo valida e lo stampa con indentazione a 4 spazi. Utile per verificare che la conversione CSV-to-JSON abbia prodotto output valido. Se preferisci indentazione a 2 spazi o hai bisogno di filtrare, usa jq.

Alternativa ad Alte Prestazioni — orjson

Il modulo json integrato va bene per la maggior parte dei file CSV. Ma se stai elaborando dataset con decine di migliaia di righe in un ciclo, o la tua API deve serializzare dati derivati da CSV ad ogni richiesta, orjson è 5–10x più veloce. È scritto in Rust, restituisce bytes invece di str, e serializza nativamente datetime, UUID, e array numpy senza una funzione default= personalizzata.

bash — installa orjson
pip install orjson
Python 3.10+ — CSV in JSON con orjson
import csv
import orjson

with open("telemetry_events.csv", "r", encoding="utf-8") as f:
    rows = list(csv.DictReader(f))

# orjson.dumps() restituisce bytes, non str
json_bytes = orjson.dumps(rows, option=orjson.OPT_INDENT_2)

with open("telemetry_events.json", "wb") as f:  # nota: "wb" per bytes
    f.write(json_bytes)

print(f"Scritti {len(rows)} eventi ({len(json_bytes)} byte)")

L'API è leggermente diversa: orjson.dumps() restituisce bytes e usa flag option= invece di argomenti keyword. Apri i file in modalità scrittura binaria ("wb") quando scrivi l'output di orjson. Se hai bisogno di una stringa, chiama .decode("utf-8") sul risultato.

Output nel Terminale con Evidenziazione della Sintassi — rich

Il debug delle conversioni CSV-to-JSON nel terminale diventa più semplice con output colorato. La libreria rich renderizza JSON con evidenziazione della sintassi — chiavi, stringhe, numeri e booleani hanno ciascuno il proprio colore.

bash — installa rich
pip install rich
Python 3.10+ — output JSON con rich
import csv
import json
from rich.console import Console
from rich.syntax import Syntax

console = Console()

with open("deployment_log.csv", "r", encoding="utf-8") as f:
    rows = list(csv.DictReader(f))

json_output = json.dumps(rows[:3], indent=2, ensure_ascii=False)
syntax = Syntax(json_output, "json", theme="monokai", line_numbers=True)
console.print(syntax)
Attenzione:rich aggiunge codici di escape ANSI all'output. Non scrivere output formattato con rich su un file o una risposta API — conterrà caratteri di controllo invisibili. Usa rich solo per la visualizzazione nel terminale.

Lavoro con File CSV di Grandi Dimensioni

Caricare un file CSV da 500 MB con list(csv.DictReader(f)) alloca l'intero dataset in memoria, poi json.dump() costruisce la stringa JSON completa sopra. Per file più grandi di 50–100 MB, passa a un approccio streaming o scrivi NDJSON (JSON newline-delimited) — un oggetto JSON per riga.

NDJSON — Un Oggetto JSON Per Riga

Python 3.10+ — streaming CSV in NDJSON
import csv
import json

def csv_to_ndjson(csv_path: str, ndjson_path: str) -> int:
    """Converti CSV in NDJSON, elaborando una riga alla volta."""
    count = 0
    with open(csv_path, "r", encoding="utf-8") as infile, \
         open(ndjson_path, "w", encoding="utf-8") as outfile:
        for row in csv.DictReader(infile):
            outfile.write(json.dumps(row, ensure_ascii=False) + "\n")
            count += 1
    return count

rows_written = csv_to_ndjson("access_log.csv", "access_log.ndjson")
print(f"Scritte {rows_written} righe in access_log.ndjson")
# Ogni riga è un oggetto JSON autonomo:
# {"timestamp":"2026-03-15T09:12:00Z","method":"GET","path":"/api/v2/orders","status":"200"}
# {"timestamp":"2026-03-15T09:12:01Z","method":"POST","path":"/api/v2/payments","status":"201"}

Streaming con ijson per Input JSON di Grandi Dimensioni

Python 3.10+ — ijson per lettura di JSON di grandi dimensioni
import ijson  # pip install ijson

def count_high_value_orders(json_path: str, threshold: float) -> int:
    """Conta gli ordini sopra una soglia senza caricare l'intero file."""
    count = 0
    with open(json_path, "rb") as f:
        for item in ijson.items(f, "item"):
            if float(item.get("total", 0)) > threshold:
                count += 1
    return count

# Elabora un file JSON da 2 GB con utilizzo costante della memoria
high_value = count_high_value_orders("all_orders.json", 500.0)
print(f"Trovati {high_value} ordini sopra 500€")
Nota:Passa a NDJSON o allo streaming quando il CSV supera 50–100 MB. ijson serve per leggere file JSON di grandi dimensioni — per la scrittura, il pattern NDJSON sopra mantiene l'utilizzo della memoria costante indipendentemente dalle dimensioni del file.

Errori Comuni

Usare json.dumps() e poi scrivere su file separatamente

Problema: json.dumps() restituisce una stringa. Scriverla con f.write() funziona ma crea una stringa intermedia inutile in memoria — uno spreco per grandi dataset.

Soluzione: Usa json.dump(data, f) per scrivere direttamente sull'oggetto file. Trasmette l'output senza costruire prima la stringa completa.

Before · Python
After · Python
json_string = json.dumps(rows, indent=2)
with open("output.json", "w") as f:
    f.write(json_string)  # stringa intermedia inutile
with open("output.json", "w", encoding="utf-8") as f:
    json.dump(rows, f, indent=2, ensure_ascii=False)  # scrittura diretta
Dimenticare di convertire i valori stringa CSV in numeri

Problema: csv.DictReader restituisce tutti i valori come stringhe. L'output JSON contiene "quantity": "5" invece di "quantity": 5, il che rompe i consumer API tipizzati.

Soluzione: Converti esplicitamente le colonne numeriche con int() o float() prima di serializzare.

Before · Python
After · Python
rows = list(csv.DictReader(f))
json.dumps(rows)
# [{"port": "8080", "workers": "4"}]  ← stringhe, non numeri
rows = list(csv.DictReader(f))
for row in rows:
    row["port"] = int(row["port"])
    row["workers"] = int(row["workers"])
json.dumps(rows)
# [{"port": 8080, "workers": 4}]  ← interi corretti
Omettere encoding='utf-8' nell'apertura del file

Problema: Su Windows, la codifica predefinita è cp1252. I caratteri non-ASCII (nomi accentati, testo CJK) vengono silenziosamente corrotti o sollevano UnicodeDecodeError.

Soluzione: Passa sempre encoding='utf-8' a open() sia per la lettura del CSV sia per la scrittura del JSON.

Before · Python
After · Python
with open("locations.csv", "r") as f:  # usa la codifica di sistema predefinita
    rows = list(csv.DictReader(f))
with open("locations.csv", "r", encoding="utf-8") as f:
    rows = list(csv.DictReader(f))
Usare str() o repr() invece di json.dumps()

Problema: str(my_dict) produce sintassi Python (virgolette singole, True, None) che non è JSON valido. Le API e i parser JSON lo rifiutano.

Soluzione: Usa sempre json.dumps() per produrre JSON valido. Converte True in true, None in null, e usa le virgolette doppie.

Before · Python
After · Python
output = str({"active": True, "note": None})
# "{'active': True, 'note': None}"  ← NON è JSON valido
output = json.dumps({"active": True, "note": None})
# '{"active": true, "note": null}'  ← JSON valido

json.dumps() vs Alternative — Confronto Rapido

Metodo
Output
JSON valido
Tipi personalizzati
Velocità
Installazione richiesta
json.dumps()
str
tramite parametro default=
Base
No (stdlib)
json.dump()
scrive su file
tramite parametro default=
Base
No (stdlib)
csv.DictReader + json
str o file
tramite parametro default=
Base
No (stdlib)
pandas to_json()
str o file
✓ datetime nativo
~2x più veloce per grandi dataset
pip install pandas
orjson.dumps()
bytes
✓ datetime/UUID nativi
5–10x più veloce
pip install orjson
dataclasses.asdict() + json
str
tramite parametro default=
Base
No (stdlib)
polars write_json()
str o file
✓ datetime nativo
~3x più veloce per grandi dataset
pip install polars

Per la maggior parte delle conversioni CSV-to-JSON, la combinazione csv + json della libreria standard è la scelta giusta: nessuna dipendenza, inclusa in Python, funziona ovunque. Ricorri a orjson quando il profiling mostra che la serializzazione è un collo di bottiglia — la differenza di velocità è reale su larga scala. Usa pandas quando hai anche bisogno di pulizia, filtraggio o aggregazione dei dati prima di convertirli in JSON. Se hai solo bisogno di una conversione rapida senza scrivere codice, il convertitore CSV in JSON online lo gestisce istantaneamente.

Domande Frequenti

Qual è la differenza tra json.dump() e json.dumps() in Python?

json.dump(obj, file) scrive l'output JSON direttamente su un oggetto file (qualsiasi cosa abbia un metodo .write()). json.dumps(obj) restituisce una stringa formattata in JSON. Usa json.dump() quando scrivi su file, json.dumps() quando hai bisogno del JSON come stringa Python per il logging, per incorporarlo in un payload o per inviarlo attraverso un socket. Entrambi accettano gli stessi argomenti keyword (indent, sort_keys, ensure_ascii, default).

Come si converte un dizionario Python in una stringa JSON?

Chiama json.dumps(il_tuo_dict). Il valore restituito è una str contenente JSON valido. Aggiungi indent=2 per un output leggibile. Se il dict contiene valori non-ASCII, passa ensure_ascii=False per preservare caratteri come lettere accentate o testo CJK.

Python 3.10+
import json

server_config = {"host": "api.internal", "port": 8443, "debug": False}
json_string = json.dumps(server_config, indent=2)
print(json_string)
# {
#   "host": "api.internal",
#   "port": 8443,
#   "debug": false
# }

Come si salva una lista Python di dict come file JSON?

Apri un file in modalità scrittura con codifica UTF-8, poi chiama json.dump(la_tua_lista, f, indent=2, ensure_ascii=False). Usa sempre json.dump() (non json.dumps()) per l'output su file — scrive direttamente sull'handle del file senza creare una stringa intermedia in memoria.

Python 3.10+
import json

records = [
    {"order_id": "ORD-4821", "total": 129.99, "currency": "USD"},
    {"order_id": "ORD-4822", "total": 89.50, "currency": "EUR"},
]

with open("orders.json", "w", encoding="utf-8") as f:
    json.dump(records, f, indent=2, ensure_ascii=False)

Perché json.dumps() trasforma True in true e None in null?

I booleani Python (True, False) e None non sono token JSON validi. La specifica JSON usa true, false e null in minuscolo. json.dumps() gestisce questa conversione automaticamente — True diventa true, False diventa false, None diventa null. Non è necessario convertirli manualmente. Nell'altra direzione, json.loads() li rimappa ai tipi Python.

Come si gestiscono gli oggetti datetime durante la conversione di dati CSV in JSON?

Passa una funzione default= a json.dumps() che converte gli oggetti datetime in stringhe ISO 8601. La funzione default viene chiamata per qualsiasi oggetto che json non riesce a serializzare nativamente. Restituisce obj.isoformat() per le istanze datetime e solleva TypeError per tutto il resto.

Python 3.10+
import json
from datetime import datetime

def json_default(obj):
    if isinstance(obj, datetime):
        return obj.isoformat()
    raise TypeError(f"Not serializable: {type(obj)}")

event = {"action": "login", "timestamp": datetime(2026, 3, 15, 9, 30, 0)}
print(json.dumps(event, default=json_default))
# {"action": "login", "timestamp": "2026-03-15T09:30:00"}

È possibile convertire CSV in JSON senza pandas?

Sì. La libreria standard Python ha tutto il necessario. Usa csv.DictReader per leggere ogni riga come dizionario, raccogli le righe in una lista e serializza con json.dump() o json.dumps(). Non sono richieste librerie di terze parti. Vale la pena aggiungere pandas solo se hai anche bisogno di pulizia dei dati, inferenza dei tipi, o lo stai già usando altrove nel progetto.

Python 3.10+
import csv
import json

with open("inventory.csv", "r", encoding="utf-8") as csv_file:
    rows = list(csv.DictReader(csv_file))

with open("inventory.json", "w", encoding="utf-8") as json_file:
    json.dump(rows, json_file, indent=2, ensure_ascii=False)

Per un'alternativa con un solo click senza scrivere Python, prova il convertitore CSV in JSON — incolla i tuoi dati CSV e ottieni output JSON formattato immediatamente.

Strumenti Correlati

MS
Maria SantosBackend Developer

Maria is a backend developer specialising in Python and API integration. She has broad experience with data pipelines, serialisation formats, and building reliable server-side services. She is an active member of the Python community and enjoys writing practical, example-driven guides that help developers solve real problems without unnecessary theory.

PS
Priya SharmaRevisore tecnico

Priya is a data scientist and machine learning engineer who has worked across the full Python data stack — from raw data ingestion and cleaning to model deployment and monitoring. She is passionate about reproducible research, Jupyter-based workflows, and the practical engineering side of ML. She writes about NumPy, Pandas, data serialisation, and the Python patterns that make data pipelines reliable at scale.