2 Replies Latest reply on Jan 14, 2009 9:57 AM by Stuart Douglas

    entity manager question

    Derek Knapp Newbie

      I have a Asynchronous method which calls ffmpeg (to convert an uploaded video). Every 2% I would like to update the percentage that users will see when viewing the status of their uploaded videos... I don't particularly care if it is immediately writen to the database, but I do want it to be updated when the user refreshes the page...



      "select v from Video v where v.userid = :userid"




      above is my SQL query, which returns all videos for the user. with the code below it works perfect, however, if I remove the em.flush(); the percent doesn't change until the video is completly done processing. is this normal behaviour? is there a better way to do this? I always thought using em.flush() should be avoided?


      Thanks
          Derek






      package wyd.ffmpeg;
      
      import java.io.BufferedReader;
      import java.io.InputStreamReader;
      import javax.persistence.EntityManager;
      import org.jboss.seam.annotations.AutoCreate;
      import org.jboss.seam.annotations.In;
      import org.jboss.seam.annotations.Name;
      import org.jboss.seam.annotations.Transactional;
      import org.jboss.seam.annotations.async.Asynchronous;
      import wyd.entity.Video;
      
      /**
       *
       * @author Derek Knapp
       */
      @Name("convert")
      @AutoCreate
      public class ffmpegService
      {
          @In
          EntityManager em;
      
          public String[] getONE(String[] a1, String[] a2)
          {
              String[] result = new String[a1.length + a2.length];
              System.arraycopy(a1, 0, result, 0, a1.length);
              System.arraycopy(a2, 0, result, a1.length, a2.length);
              return result;
          }
      
          @Asynchronous
          @Transactional
          public void run(Video video)
          {
              try
              {
                  String in = "/ffmpeg/in/" + video.getUuid();
                  String out = "/ffmpeg/out/" + video.getUuid() + ".mp4";
      
                  String[] common = {
                      "/ffmpeg/ffmpeg",
                      "-y",
                      "-i", in,
                      "-vcodec", "libx264",
                      "-b", "256k",
                    //"-b", "512k",
                      "-bf", "3",
                      "-subq", "6",
                      "-cmp", "256",
                      "-refs", "5",
                      "-qmin", "10",
                      "-qmax", "51",
                      "-qdiff", "4",
                      "-coder", "1",
                      "-loop", "1",
                      "-me_method", "hex",
                      "-me_range", "16",
                      "-trellis", "1",
                      "-flags", "+mv4",
                      "-flags2", "+bpyramid+wpred+mixed_refs+dct8x8",
                      "-partitions", "parti4x4+parti8x8+partp4x4+partp8x8+partb8x8",
                      "-g", "250",
                      "-keyint_min", "25",
                      "-sc_threshold", "40",
                      "-i_qfactor", "0.71",
                      "-vhook", "/ffmpeg/watermark.so -f /ffmpeg/wm.gif"
                  };
      
                  String[][] pass = {
                      {
                          "-an",
                          "-pass", "1",
                          "-threads", "2",
                          out
                      },
                      {
                          "-acodec", "libfaac",
                          "-ar", "22050",
                          "-ab", "64k",
                          "-pass", "2",
                          "-threads", "2",
                          out
                      }
                  };
      
      
                  for (int i = 0; i < pass.length; i++)
                  {
                      Process p = Runtime.getRuntime().exec(getONE(common, pass[i]));
      
                      BufferedReader stderr = new BufferedReader(new InputStreamReader(p.getErrorStream()));
                      String line;
      
                      while ((line = stderr.readLine()) != null)
                      {
                          if (line.contains("time="))
                          {
                              int pos = line.indexOf("time=");
                              line = line.substring(pos + 5, line.indexOf(" ", pos));
      
                              Double percent = Double.valueOf(line.trim()) / video.getDuration() * 100 / pass.length + 100 / pass.length * i;
      
                              if (Math.abs(video.getPercent() - percent) > 2)
                              {
                                  System.out.println("percent = " + percent.intValue());
                                  System.out.println("em = " + em);
                                  video.setPercent(percent.intValue());
                                  em.merge(video);
                                  em.flush();
                              }
                          }
                      }
                  }
      
                  video.setPercent(100);
                  em.merge(video);
                  em.flush();
              }
              catch (Exception e)
              {
                  e.printStackTrace();
              }
          }
      }