2013-07-24 12 views
7

Podczas tworzenia aplikacji internetowych często mamy pliki powiązane z wpisami do bazy danych, np .: mamy tabelę user, a każda kategoria ma pole avatar, które przechowuje ścieżkę do powiązanego obrazu.Co jest lepsze dla wydajności - wiele plików w jednym katalogu lub wiele podkatalogów z jednym plikiem?

Aby upewnić się, nie ma żadnych konfliktów w nazwach możemy albo:

  • zmieniać nazwy plików w przypadku przesyłanego do ID.jpg; ścieżka będzie wtedy /user-avatars/ID.jpg
  • lub utworzyć podkatalog dla każdej jednostki i pozostawić oryginalną nazwę pliku nietkniętą; ścieżka byłaby wtedy /user-avatars/ID/original_filename.jpg

gdzie ID jest users „s unikalny numer ID

Zarówno doskonale ważny z punktu widzenia logiki aplikacji widzenia.

Ale który z nich byłby lepszy z punktu widzenia wydajności systemu plików? Musimy pamiętać, że liczba wpisów category może być bardzo wysoka (miliony).

Czy istnieje ograniczenie liczby podkatalogów, które może przechowywać katalog?

+1

To zależy od systemu plików . – nouney

+0

W przypadku niewielkich plików przeznaczonych głównie do odczytu (takich jak obrazy awatara), które nie zmieniają się często, użycie dedykowanego DB * może * mieć sens. Nawet lokalna instancja SQLite3 może być tego warta. Zobacz https://www.sqlite.org/intern-v-extern-blob.html - Ale w kontekście serwera WWW zasoby plików statycznych mają więcej sensu. –

Odpowiedz

4

Będzie to zależało od systemu plików, ale zakładam, że mówisz o czymś prostym, na przykład ext3, i nie uruchamiasz rozproszonego systemu plików (niektóre z nich są w tym dobre) . Ogólnie systemy plików działają nieprawidłowo w stosunku do pewnej liczby wpisów w jednym katalogu, niezależnie od tego, czy są to katalogi czy pliki. Niezależnie od tego, czy tworzysz jeden katalog na obraz, czy jeden obraz w katalogu głównym, napotkasz problemy ze skalowaniem. Jeśli spojrzeć na to odpowiedź:

How many files in a directory is too many (on Windows and Linux)?

Zobaczysz, że ext3 wpada na granicach około 32K wpisów w katalogu, znacznie mniej niż pan proponuje.

Z góry mojej głowy, sugeruję robienie pewnych podstawowych fragmentów w wielopoziomowym drzewie katalogów, coś jak /user-avatars/1/2/12345/original_filename.jpg. (Lub coś odpowiedniego dla twojego typu identyfikatora, ale interpretuję twoje pytanie jako identyfikatory numeryczne.) Uczynienie tego również ułatwi ci życie, kiedy zdecydujesz, że chcesz rozpowszechniać w klastrze, skoro możesz rozłożyć katalogi na około.

+0

Czytałem, że SO, ale nie wiedziałem, że ten limit dotyczy również podkatalogów. I tak, pytam o podstawowe systemy plików (windows/ntfs lub linux/ext3). – loostro

+0

Mogę również dodać, w oparciu o doświadczenia z superkomputerów, że nawet jeśli twój system plików będzie obsługiwał miliony plików w katalogu (i niektóre z nich), twoja wydajność znacznie spadnie nawet dla podstawowych operacji. Wiele jest liniowych rozmiarów reż. Coś jak ls wymaga kilku wywołań systemowych na jeden wpis (pobierz nazwę pliku, zrób plik, sprawdź zabezpieczenia xattrs) ... pomnóż to milion razy i masz poważne wąskie gardło. Powrót może potrwać kilka godzin. – aleatha

+0

Tak więc, z identyfikatorem numerycznym, jeśli korzystam z proponowanego rozwiązania i zapisz plik, np. '/ 12/34/56/my_file.jpg' (na każde 2 cyfry w identyfikatorze, nowy podkatalog), który ograniczyłby liczbę podkatalogów w każdym katalogu do maksymalnie 100 (0-99) ... czy to wystarczy, by uzyskać przyzwoitą wydajność? – loostro

3

Miliony wpisów (plików lub katalogów) w jednym katalogu macierzystym byłoby trudnym zadaniem w przypadku dowolnego systemu plików. Podczas gdy nowoczesne systemy plików używają sortowania i różnych algorytmów drzewa do szybkiego wyszukiwania potrzebnych plików, nawet nawigacja do folderu z Eksploratorem Windows lub Midnight Commanderem lub jakimkolwiek innym menedżerem plików będzie skomplikowana, ponieważ menedżer plików będzie musiał odczytać zawartość katalogu. To samo dotyczy wyszukiwania plików. Dlatego preferowane są do tego podkatalogi.

Muszę jednak zauważyć, że dostęp do konkretnego pliku byłby nieco szybszy, gdy wszystkie pliki znajdują się w jednym katalogu, niż gdy są podzielone na podkatalogi przynajmniej w systemie plików NTFS (mierzone to kilka razy przy plikach 400 KB).

1

Jeśli naprawdę chcesz korzystać z plików, może najlepiej jest podzielić pliki na kilka podkatalogów, aby nie przekroczyć limitu. Na przykład, jeśli masz identyfikator 123456, możesz umieścić go w /12/34/56.jpg.

Zalecam jednak po prostu użycie bazy danych do przechowywania tych danych, ponieważ już je używasz. Możesz przechowywać dane obrazu i identyfikator w tej samej tabeli, i nie musisz się martwić o niektóre brzydkie sprawy związane z obsługą plików, takich jak upewnienie się, że uprawnienia są ustawione prawidłowo, itp.

+1

Nie wszystkie bazy danych działają dobrze podczas przechowywania bloków binarnych o nieporównywalnym (i zmiennym) rozmiarze. Nie poleciłbym tego wprost, nie bez benchmarkingu. –

+1

@FrankH. Wskazujesz na dobry punkt. Myślę, że będzie to również zależeć od kontekstu aplikacji. – user1132959

Powiązane problemy