Question

J'ai une application Perl qui analyse les tables MediaWiki SQL et affiche les données de plusieurs pages wiki. Je dois pouvoir recréer le chemin d'image absolu pour afficher les images, par exemple: ... / f / fc / Herbs.jpg / 300px-Herbs.jpg

Du manuel MediaWiki:

  

Image_Authorisation: "le chemin [image] peut être calculé facilement à partir du nom du fichier et ...".

Comment le chemin est-il calculé?

Était-ce utile?

La solution

Une solution possible serait de calculer la signature MD5 du fichier (ou l'ID de fichier dans une base de données), puis de créer / trouver le chemin d'accès en fonction de cela.

Par exemple, supposons que nous obtenions une signature MD5 du type "1ff8a7b5dc7a7d1f0ed65aaa29c04b1e"

Le chemin peut ressembler à "/ 1f / f". ou "/ 1f / ff / 8a"

La raison en est que vous ne souhaitez pas que tous les fichiers se trouvent dans un seul dossier et que vous souhaitez avoir la possibilité de "partitionner" sur différents serveurs, sur un réseau SAN ou autre, de manière égale.

La signature MD5 est une chaîne de 16 "hex". personnages. Donc, notre exemple de "/ 1f / ff / 8a" nous donne 256 * 256 * 256 dossiers dans lesquels stocker les fichiers. Cela devrait suffire à tout le monde:)

Mise à jour, à la demande générale:

REMARQUE : je viens de me rendre compte que nous parlons spécifiquement de la manière dont MediaWiki le fait. Ce n'est pas maintenant MediaWiki le fait, mais une autre façon de le faire aurait pu être fait .

Par " Signature MD5 " Je veux dire quelque chose comme ça (exemples de code en Perl):

use Digest::MD5 'md5_hex';
my $sig = md5_hex( $file->id );

$ sig comporte maintenant 32 caractères alphanumériques: "1ff8a7b5dc7a7d1f0ed65aaa29c04b1e"

Construisez ensuite une structure de dossiers comme celle-ci:

my $path = '/usr/local/media';
map { mkdir($path, 0666); $path .= "/

Une solution possible serait de calculer la signature MD5 du fichier (ou l'ID de fichier dans une base de données), puis de créer / trouver le chemin d'accès en fonction de cela.

Par exemple, supposons que nous obtenions une signature MD5 du type "1ff8a7b5dc7a7d1f0ed65aaa29c04b1e"

Le chemin peut ressembler à "/ 1f / f". ou "/ 1f / ff / 8a"

La raison en est que vous ne souhaitez pas que tous les fichiers se trouvent dans un seul dossier et que vous souhaitez avoir la possibilité de "partitionner" sur différents serveurs, sur un réseau SAN ou autre, de manière égale.

La signature MD5 est une chaîne de 16 "hex". personnages. Donc, notre exemple de "/ 1f / ff / 8a" nous donne 256 * 256 * 256 dossiers dans lesquels stocker les fichiers. Cela devrait suffire à tout le monde:)

Mise à jour, à la demande générale:

REMARQUE : je viens de me rendre compte que nous parlons spécifiquement de la manière dont MediaWiki le fait. Ce n'est pas maintenant MediaWiki le fait, mais une autre façon de le faire aurait pu être fait .

Par " Signature MD5 " Je veux dire quelque chose comme ça (exemples de code en Perl):

use Digest::MD5 'md5_hex';
my $sig = md5_hex( $file->id );

$ sig comporte maintenant 32 caractères alphanumériques: "1ff8a7b5dc7a7d1f0ed65aaa29c04b1e"

Construisez ensuite une structure de dossiers comme celle-ci:

/
  usr/
    local/
      media/
        1f/
          f8/
            a7/
              1ff8a7b5dc7a7d1f0ed65aaa29c04b1e

La structure des dossiers ressemble à

<*>" } $sig =~ m/^(..)(..)(..)/; open my $ofh, '>', "$path/$sig" or die "Cannot open '$path/$sig' for writing: $!"; print $ofh "File contents"; close($ofh);

La structure des dossiers ressemble à

<*>

Autres conseils

La réponse acceptée est incorrecte:

  • La somme MD5 d'une chaîne est de 32 caractères hexadécimaux (128 bits) et non de 16
  • Le chemin du fichier est calculé à partir de la somme MD5 du nom de fichier, et non du contenu du fichier lui-même
  • Le premier répertoire du chemin est le premier caractère et le deuxième répertoire, les premier et deuxième caractères. Le chemin du répertoire n'est pas une combinaison des 3 ou 6 premiers caractères.

La somme MD5 de 'Herbs.jpg' est fceaa5e7250d5036ad8cede5ce7d32d6. Les 2 premiers caractères sont "fc", donnant le chemin du fichier f / fc /, comme dans l'exemple.

En PHP, vous pouvez appeler la fonction suivante pour obtenir l'URL. Vous voudrez peut-être consulter le code php pour comprendre comment ils calculent le chemin.

$url = wfFindFile(Title::makeTitle(NS_IMAGE, $fileName))->getURL();

J'ai créé un petit script Bash appelé reorder.sh , qui déplace les fichiers de l'intérieur "images". aux sous-dossiers spécifiques:

#!/bin/bash

cd /opt/mediawiki/mediawiki-cur/images

for i in `find -maxdepth 1 -type f ! -name .htaccess ! -name README ! -name reorder.sh -printf '%f\n'`; do
    path1=$(echo -n $i | md5sum | head -c1)    &&
    path2=$(echo -n $i | md5sum | head -c2)    &&
    mkdir -p $path1/$path2/                    &&
    mv $i $path1/$path2/;
done
Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top