MOD Le fichier film.rb et divisé en film.rb et films.rb pour une meilleure lecture
[pompage.git] / src / films.rb
diff --git a/src/films.rb b/src/films.rb
new file mode 100644 (file)
index 0000000..a934dbb
--- /dev/null
@@ -0,0 +1,230 @@
+# Représente un ensemble de films\r
+\r
+require 'rexml/document'\r
+require 'thwait'\r
+\r
+require 'film.rb'\r
+require 'pays.rb'\r
+require 'genre.rb'\r
+require 'personne.rb'\r
+require 'constantes.rb'\r
+\r
+class Films\r
+   def initialize(xmlFile)\r
+      @xmlFile = xmlFile\r
+      \r
+      # repertoire de base, par exemple C:/Divx/\r
+      @repBase = ''   \r
+         \r
+      # Les films indexés par leur titre\r
+      @films = {}\r
+      \r
+      # Les films indexés par leur nom de fichier, deux fichiers différents peuvent pointer sur le même film\r
+      @filmsFichier = {}\r
+      \r
+      # Les films qui ont plusieurs réponses lors de la recherche, traités à la fin\r
+      @filmsPlusieursReponses = []\r
+\r
+      @threadsWait = ThreadsWait::new\r
+      @nbConn = 0 # le nombre de connexion\r
+      \r
+      # le prochain id disponible\r
+      @idDisponible = 1\r
+      \r
+      chargerFilms\r
+   end\r
+\r
+   # Lit un repertoire de manière recursive et va chercher les informations concernant le film sur le net\r
+   def pomper(r)\r
+      @repBase = r\r
+      repPrecedant = Dir::getwd\r
+      Dir::chdir(r)\r
+      \r
+      pomperR('.')\r
+      \r
+      # on attends que les threads se terminent\r
+      @threadsWait.all_waits\r
+      \r
+      # traite les films qui avaient plusieurs réponses lors de la recherche\r
+      # l'utilisateur doit faire un choix\r
+      i = 1\r
+      @filmsPlusieursReponses.each{|f|\r
+         puts\r
+         puts "Plop, ya un conflit #{i} / #{@filmsPlusieursReponses.length} :"\r
+         if f.reglerConflitPlusieursReponses\r
+            ajouterFilm(f)\r
+         end\r
+         i += 1\r
+      }\r
+      \r
+      Dir::chdir(repPrecedant)      \r
+   end\r
+   \r
+   # Sauve les films dans un fichier XML\r
+   def sauverFilms\r
+      # le document\r
+      docXml = REXML::Document::new\r
+      docXml.xml_decl().encoding = "UTF-8"  # normalement UTF-8\r
+      docXml.xml_decl().dowrite\r
+            \r
+      # la racine du document\r
+      racine = REXML::Element::new('filmographie')\r
+      docXml.add(racine)\r
+      pi = REXML::Instruction.new("xml-stylesheet", "type=\"text/xsl\" href=\"../xsl/yopyop.xsl\"")\r
+      racine.previous_sibling = pi\r
+      \r
+      # on ajoute chaque film à la racine\r
+      @films.each{|nom, f|\r
+         racine.add(f.getXml)\r
+      } \r
+      \r
+      # sauve le document\r
+      docXml.write(File::new(@xmlFile, 'w'), 0)\r
+   end   \r
+   \r
+   private\r
+      \r
+   # Charge les films depuis le fichier XML\r
+   def chargerFilms\r
+      # si le fichier n'existe pas il n'y a rien à charger\r
+      if !File.exists?(@xmlFile)\r
+         return\r
+      end\r
+      \r
+      racine = REXML::Document::new(File::new(@xmlFile)).root\r
+      racine.each_element{|e|       \r
+         id = e.attribute('id').to_s.to_i\r
+       \r
+         if id > @idDisponible\r
+            @idDisponible = id + 1   \r
+         end\r
+         \r
+         titre = e.get_elements('titre')[0].get_text\r
+         \r
+         fichiers = e.get_elements('fichiers')[0].get_elements('fichier')\r
+         annee = e.get_elements('annee')[0].get_text\r
+         duree = e.get_elements('duree')[0].get_text\r
+         critiquePresse = e.get_elements('critiquePresse')[0].get_text\r
+         critiqueSpectateur = e.get_elements('critiqueSpectateur')[0].get_text\r
+         synopsis = e.get_elements('synopsis')[0].get_elements('p')\r
+         budget = e.get_elements('budget')[0].get_text  \r
+         realisateurs = e.get_elements('realisateurs')[0].get_elements('realisateur')\r
+         acteurs = e.get_elements('acteurs')[0].get_elements('acteur')\r
+         pays = e.get_elements('lespays')[0].get_elements('pays')\r
+         genres = e.get_elements('genres')[0].get_elements('genre')\r
+         \r
+         film = Film::new(fichiers[0].get_text.value)\r
+         \r
+         film.titre = titre.value unless titre.nil?\r
+         film.id = id\r
+         fichiers.each{|e|\r
+            film.addFichier(e.get_text.value)\r
+            @filmsFichier[e.get_text.value] = film\r
+         }\r
+         film.annee = annee.value unless annee.nil?\r
+         acteurs.each{|e|\r
+            film.acteurs << Personne::ajouter(e.get_text.value)\r
+         }\r
+         pays.each{|e|\r
+            film.pays << Pays::ajouter(e.get_text.value)\r
+         }\r
+         film.duree = duree.value unless duree.nil?\r
+         film.critiquePresse = critiquePresse.value unless critiquePresse.nil?\r
+         film.critiqueSpectateur = critiqueSpectateur.value unless critiqueSpectateur.nil?\r
+         genres.each{|e|\r
+            film.genres << Genre::ajouter(e.get_text.value) if e.get_text != nil\r
+         }\r
+         debut = true\r
+         film.synopsis = ""\r
+         synopsis.each{|e|\r
+            film.synopsis += "\n" unless debut\r
+            film.synopsis += e.get_text.value if e.get_text != nil\r
+            debut = false\r
+         }\r
+         film.budget = budget.value unless budget.nil?\r
+         @films[film.titre] = film\r
+      }\r
+   end\r
+   \r
+   # Retourne un nouvel id, utilisé lors de la création d'un nouveau film\r
+   def getNewId\r
+      id = @idDisponible\r
+      @idDisponible += 1\r
+      return id\r
+   end   \r
+   \r
+   # Ajoute un film\r
+   def ajouterFilm(film)\r
+      if film.plusieursReponses?\r
+         @filmsPlusieursReponses << film\r
+         return\r
+      end\r
+      \r
+      # le film existe déjà\r
+      if @films.has_key?(film.titre)\r
+         # le fichier n'est pas connu -> nième partie d'un film\r
+         if !@filmsFichier.has_key?(film.fichiers[0])\r
+            puts "[i] movie #{film.titre} has a another file part : #{film.fichiers[0]}"\r
+            @films[film.titre].addFichier(film.fichiers[0])\r
+            @filmsFichier[film.fichiers[0]] = @films[film.titre]                     \r
+         else\r
+            puts "[!] Duplicate movie : #{film.titre} (#{film.fichiers[0]})"\r
+         end\r
+      else\r
+         puts "[i] movie added : #{film.titre} (#{film.fichiers[0]})"\r
+         @films[film.titre] = film\r
+         @filmsFichier[film.fichiers[0]] = film\r
+      end\r
+   end\r
+   \r
+   # Appelé par 'pomper'. Cette méthode est récursive.\r
+   def pomperR(r)\r
+      Dir::foreach(r){|f|\r
+         next if f[0,1] == '.'\r
+         fichier = (r == '.' ? '' : r + "/") + f\r
+         if File::directory?(fichier)\r
+            litRepertoireR(fichier) \r
+         else\r
+            \r
+            # vérification de l'extension\r
+            /^.*?\.(.{3,4})$/ =~ fichier\r
+            if !FILMS_EXTENSIONS.include?($1)\r
+               next\r
+            end\r
+            \r
+            fichier = CGI::escapeHTML(fichier.unpack("C*").pack("U*"))\r
+            \r
+            # on skip si le film est déjàa dans la BD\r
+            if film = @filmsFichier[fichier]\r
+               puts "[i] Already exists in DB : #{film.titre} (#{fichier})"\r
+               next\r
+            end\r
+            \r
+            film = nil\r
+             \r
+            # pour limiter le nombre de connexion simultanée\r
+            if @nbConn >= NB_CONN_MAX\r
+               @threadsWait.next_wait\r
+            end\r
+             \r
+            @nbConn += 1    \r
+            @threadsWait.join_nowait(\r
+               Thread::new{\r
+                  begin                  \r
+                     film = Film::new(fichier).loadData\r
+                     film.id = getNewId # on lui donne un nouvel ID\r
+                     \r
+                     unless film.nil? # le film a été correctement construit\r
+                        ajouterFilm(film)\r
+                     end\r
+                  rescue Exception => e\r
+                     puts e.message\r
+                     puts e.backtrace\r
+                  end      \r
+                  @nbConn -= 1\r
+               }\r
+            )\r
+         end\r
+      }\r
+   end\r
+end
\ No newline at end of file