sql >> Databáze >  >> RDS >> Mysql

Ukládání souborů jako blob v databázi ajax php pdo

Podle PHP/PDO/MySQL :vložení do MEDIUMBLOB ukládá špatná data , zkuste k vytvoření objektu PDO použít následující řádek:

$dbh = new PDO($dsn, $username, $password, array(PDO::MYSQL_ATTR_INIT_COMMAND => "SET NAMES latin1 COLLATE latin1_general_ci"));

Vysvětlení

Myslím, že, jak poznamenává Ben M v související otázce, zde fungují dvě špatná rozhodnutí o designu.

Existuje tento koncept znakové sady připojení. Myšlenka je taková, že text SQL může být v jakékoli znakové sadě a je poté převeden na SQL server.

To nefunguje tak dobře s binárními daty, protože se nejedná o text, a proto podle definice nesmí být v žádné znakové sadě, ale jsou stále přenášeny pomocí řetězcových literálů .

Tento problém lze vyřešit citováním dat BLOB během přenosu (buď pomocí funkcí BASE64_* nebo pomocí hexadecimálním kódováním ) a skutečně to mnoho lidí dělá.

Druhé rozhodnutí o návrhu je v PDO/PHP:PDO neprovádí žádnou konverzi znakových sad (nemůže, protože řetězce v PHP jsou ze své podstaty charakteristické znaky znakové sady), takže PHP je jediný (nebo jeden z mála jazyků), kde je možné vybrat znaková sada přenosu SQL je ve skutečnosti důležitá, protože musí odpovídat kódování, ve kterém jsou vstupní řetězce skutečně použity.

V jiných jazycích musí být přenosová znaková sada dostatečně výrazná, aby zahrnovala všechny znaky, které mohou být použity v řetězcích. V dnešním světě emotikonů to s největší pravděpodobností zaručují pouze znakové sady unicode (utf-8 a podobně). Žádný z nich však není binárně bezpečný (v tom, že ne každá možná kombinace bajtů poskytuje platný řetězec), takže i kdybychom problém s PHP mohli obejít, stále bychom měli problém č. 1.

V ideálním světě by příkazy SQL byly během přenosu vždy ve znakové sadě ASCII a každá hodnota řetězce by měla argument znakové sady, jehož možnou hodnotou by mohl být „binární“, dodávaný s ní. MySQL má ve skutečnosti takovou konstrukci pro řetězce, kterou nazývá „uvaděč“. „_binary“ se však nezdá být platnou hodnotou.

Tyto informace o znakové sadě by pak použil druhý konec k převodu hodnoty řetězce na jeho nativní znakovou sadu (buď sloupec pro přenosy klient-server, nebo znaková sada řetězců programovacího jazyka pro přenosy server-klient).

Tímto způsobem by jediná věc, která by v hodnotách BLOB musela být escapována, byl oddělovač řetězce (" nebo ' ).



  1. Funkce UPPER() v Oracle

  2. Importujte soubor CSV přímo do MySQL

  3. Jak zálohovat nebo vytvořit novou tabulku ze Stávající tabulky SQL Serveru na SQL Serveru - SQL Server / Výukový program TSQL, část 105

  4. Kódujte své první API pomocí Node.js a Express:Připojte databázi