Smart File Type Detection med PHP

I de flesta webbapplikationer idag är det nödvändigt att låta användare ladda upp bilder, ljud och videofiler. Ibland behöver vi också begränsa vissa typer av filer från att laddas upp - en körbar fil är ett uppenbart exempel.

Säkerhet åt sidan kan man också förhindra att användare missbrukar uppladdningsanläggningen, t.ex. ladda upp upphovsrättsskyddat musikfiler olagligt och använda tjänsten för att främja piratkopiering! I den här artikeln kommer vi att titta på några sätt på vilka vi kan uppnå detta.

Filtypsdetektering med förlängnings- och MIME-typer

Jag kommer inte att prata om detta för mycket, eftersom det är det vi gör normalt när vi vill begränsa vissa filer. Vi får helt enkelt MIME-typen av filen med $ _FILES [ 'myFile'] [ 'typ'] och kontrollera om det är av en giltig typ.

Eller vi kan skanna de sista tecknen i filnamnet och avvisa filer som slutar med en viss fil. Tyvärr är dessa metoder knappast tillräckliga, eftersom man enkelt kan ändra filens förlängning för att kringgå denna begränsning. Vidare ges MIME-typinformation av webbläsaren och de flesta webbläsare, om inte alla, bestämmer mime-typen baserat på filens tillägg! Därför kan MIME-typerna vara ganska enkelt spoofed också.

Låt oss nu utforska några andra sätt som erbjuder bättre dumtäthet.

Använda Magic Bytes

Det bästa sättet att bestämma filtypen är att undersöka de första byte av en fil - kallad "magiska byte". Magiska byte är väsentligen signaturer som varierar i längd mellan 2 till 40 byte i filhuvudena eller i slutet av en fil. Det finns flera hundra typer av filer, och en hel del av dem har flera filsignaturer associerade med dem. Du kan se en lista över filsignaturer här borta.

Även om det är inkonsekvent, är detta vårt bästa sätt att upptäcka filtyper på ett tillförlitligt sätt. Denna till synes svåra uppgift har gjorts väldigt enkelt av en PECL-förlängning som heter Fileinfo. Från och med PHP 5.3 skickas Fileinfo med huvuddistributionen och är aktiverat som standard, så det här är definitivt ett robust och enkelt sätt att upptäcka och införa restriktioner för de typer av filer som laddas upp.

Låt oss nu se hur vi kan upptäcka en filtyp med Fileinfo:

Hantering av bilduppladdningar

Om du tänker tillåta endast bilduppladdningar kan du använda det inbyggda getimagesize () funktion för att säkerställa att användaren faktiskt laddar upp en giltig bildfil. Dessa funktioner returnerar false, om filen inte är en giltig bildfil.

Läsa och tolka magiska byte manuellt

Om du av någon anledning inte kan installera Fileinfo, kan du fortfarande manuellt bestämma filtypen genom att läsa de första bitarna av en fil och jämföra dem med kända magiska byte som är associerade med den specifika filtypen. Denna process har definitivt ett försök och fel, eftersom det fortfarande finns en chans att det finns några ookumenterade magiska byte i samband med legitima filformat. Som ett resultat kan giltiga filer avvisas av ditt system. Men det är inte omöjligt om några år tillbaka, jag blev ombedd att arbeta på ett manus som bara tillåter äkta mp3-filer att laddas upp, och eftersom vi inte kunde använda Fileinfo tog vi till den här manuell skanningen. Det tog mig ett tag att redogöra för några av de ofokumenterade magiska bytesna för mp3, men ganska snart fick jag ett stabilt uppladdningsskript som körde.

Innan jag slutar vill jag bara dela med ett allmänt försiktighetsvar: Var noga med att du aldrig ringer en inkludera() med en fil som laddades upp, eftersom PHP-kod mycket väl kan döljas som en del av bilden, och bilden skulle skicka dina tester för filvalidering bara bra för att orsaka kaos när den kördes av servern.