sql >> Databasteknik >  >> RDS >> Mysql

Spara filer som blob i databasen ajax php pdo

Enligt PHP/PDO/MySQL :infogning i MEDIUMBLOB lagrar dålig data , försök att använda följande rad för att konstruera ditt PDO-objekt:

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

Förklaring

Jag tror att det finns, som Ben M noterar i den länkade frågan, två dåliga designbeslut som fungerar här.

Det finns detta koncept med en anslutningsteckenuppsättning. Tanken är att SQL-texten kan finnas i vilken teckenuppsättning som helst och sedan konverteras vid hämtning av SQL-servern.

Detta fungerar inte så bra med binär data eftersom det inte är text och därför inte får per definition finnas i någon teckenuppsättning, men överförs fortfarande med strängliterals .

Det här problemet kan lösas genom att citera BLOB-data under överföringen (antingen med BASE64_*-funktionerna eller genom hexadecimalt escape ) och det är faktiskt vad många människor gör.

Det andra designbeslutet är i PDO/PHP:PDO gör ingen teckenuppsättningskonvertering (det kan inte, eftersom strängar i PHP är i sig teckenuppsättnings-agnostiska) så PHP är det enda (eller ett av de få språken) där valet av SQL-överföringsteckenuppsättningen är faktiskt viktig eftersom den måste matcha kodningen som inmatningssträngarna faktiskt är i.

På andra språk behöver överföringsteckenuppsättningen bara vara tillräckligt uttrycksfull för att omfatta alla tecken som kan användas i strängar. I dagens värld av emojis garanteras detta troligen bara av unicode-teckenuppsättningar (utf-8 och liknande). Men ingen av dessa är binärsäker (eftersom inte alla möjliga kombinationer av byte ger en giltig sträng) så även om vi skulle kunna komma runt PHP-problemet skulle vi fortfarande sitta kvar med problem #1.

I en ideal värld skulle SQL-kommandon alltid finnas i ASCII-teckenuppsättningen under överföringen och varje strängvärde skulle ha ett teckenuppsättningsargument, av vilket "binärt" skulle kunna vara ett möjligt värde, levererat med det. MySQL har faktiskt en sådan konstruktion för strängar, som den kallar en "introducer". "_binary" verkar dock inte vara ett giltigt värde.

Denna teckenuppsättningsinformation skulle sedan användas av den andra änden för att konvertera strängvärdet till dess ursprungliga teckenuppsättning (antingen kolumnen för klient-till-server-överföringar eller programmeringsspråkets sträng-teckenuppsättning för server-till-klient-överföringar).

På så sätt skulle det enda som skulle behöva escapes i BLOB-värden vara strängavgränsaren (" eller ' ).



  1. Gruppera mysql-fråga med 15 minuters intervall

  2. Bättre förståelse - Class.forName(com.mysql.jdbc.Driver).newInstance ();

  3. Hur tar man bort en unik begränsning i SQL?

  4. Hur man läser sql-fråga till pandas dataframe / python / django