Пример #1
0
def main(args):
    # process all files so the user can use wildcards like *.wav
    for input_file in args.files:

        output_file_w = input_file + "_w.png"
        output_file_s = input_file + "_s.jpg"

        this_args = (input_file, output_file_w, output_file_s, args.width,
                     args.height, args.fft_size, progress_callback,
                     args.color_scheme)

        print("processing file %s:\n\t" % input_file, end="")

        if not args.profile:
            try:
                create_wave_images(*this_args)
            except AudioProcessingException as e:
                print("Error running wav2png: %s" % e)
        else:
            from hotshot import stats
            import hotshot

            prof = hotshot.Profile("stats")
            prof.runcall(create_wave_images, *this_args)
            prof.close()

            print("\n---------- profiling information ----------\n")
            s = stats.load("stats")
            s.strip_dirs()
            s.sort_stats("time")
            s.print_stats(30)
        print("")
Пример #2
0
            failure("unhandled exception", e)
            cleanup(to_cleanup)
            return False
        success("created ogg: " + ogg_path)

    # create waveform images M
    waveform_path_m = sound.locations("display.wave.M.path")
    spectral_path_m = sound.locations("display.spectral.M.path")

    try:
        os.makedirs(os.path.dirname(waveform_path_m))
    except OSError:
        pass

    try:
        audioprocessing.create_wave_images(tmp_wavefile2, waveform_path_m, spectral_path_m, 120, 71, 2048)
    except AudioProcessingException, e:
        cleanup(to_cleanup)
        failure("creation of images (M) has failed", e)
        return False
    except Exception, e:
        failure("unhandled exception", e)
        cleanup(to_cleanup)
        return False
    success("created previews, medium")

    # create waveform images L
    waveform_path_l = sound.locations("display.wave.L.path")
    spectral_path_l = sound.locations("display.spectral.L.path")
    try:
        audioprocessing.create_wave_images(tmp_wavefile2, waveform_path_l, spectral_path_l, 900, 201, 2048)
Пример #3
0
            failure("unhandled exception", e)
            cleanup(to_cleanup)
            return False
        success("created ogg: " + ogg_path)

    # create waveform images M
    waveform_path_m = sound.locations("display.wave.M.path")
    spectral_path_m = sound.locations("display.spectral.M.path")

    try:
        os.makedirs(os.path.dirname(waveform_path_m))
    except OSError:
        pass

    try:
        audioprocessing.create_wave_images(tmp_wavefile2, waveform_path_m,
                                           spectral_path_m, 120, 71, 2048)
    except AudioProcessingException, e:
        cleanup(to_cleanup)
        failure("creation of images (M) has failed", e)
        return False
    except Exception, e:
        failure("unhandled exception", e)
        cleanup(to_cleanup)
        return False
    success("created previews, medium")

    # create waveform images L
    waveform_path_l = sound.locations("display.wave.L.path")
    spectral_path_l = sound.locations("display.spectral.L.path")
    try:
        audioprocessing.create_wave_images(tmp_wavefile2, waveform_path_l,
Пример #4
0
def process(sound):
    def write_log(message):
        logger.info("[%d] %i: %s" % (os.getpid(), sound.id, message))
        sys.stdout.write(str(message) + '\n')
        sys.stdout.flush()

    def failure(message, error=None):
        sound.set_processing_ongoing_state("FI")
        sound.change_processing_state("FA", use_set_instead_of_save=True)
        logging_message = "Failed to process sound with id %s\n" % sound.id
        logging_message += "\tmessage: %s\n" % message
        if error:
            logging_message += "\terror: %s\n" % str(error)
        write_log(logging_message)

    def success(message):
        write_log(message)

    def cleanup(files):
        success("cleaning up files after processing: " + ", ".join(files))
        for filename in files:
            try:
                os.unlink(filename)
            except:
                pass

    # not saving the date of the processing attempt anymore
    sound.set_processing_ongoing_state("PR")

    new_path = sound.locations('path')
    # Is the file at its new location?
    if not os.path.exists(new_path):
        # Is the file at its old location?
        if not sound.original_path or not os.path.exists(sound.original_path):
            failure(
                "The file to be processed can't be found at its FS1 nor at its FS2 location."
            )
            return False
        else:
            success("Found the file at its FS1 location: %s" %
                    sound.original_path)
            if not sound.original_path.startswith('/mnt/freesound-data/'):
                failure(
                    "The file appears to be in a weird location and not in '/mnt/freesound-data/'!."
                )
                return False
            success("Copying file from %s to %s" %
                    (sound.original_path, new_path))
            dest_dir = os.path.dirname(new_path)
            if not os.path.exists(dest_dir):
                try:
                    os.makedirs(dest_dir)
                except:
                    failure("Could not create destination directory %s" %
                            dest_dir)
                    return False
            shutil.copy(sound.original_path, new_path)
            sound.set_original_path(new_path)
            success("Copied file from its FS1 to FS2 location.")
    else:
        success("Found the file at its FS2 location: %s" % new_path)
        if sound.original_path != new_path:
            sound.set_original_path(new_path)

    # convert to pcm
    to_cleanup = []
    try:
        tmp_wavefile = tempfile.mktemp(suffix=".wav", prefix=str(sound.id))
    except IOError as e:
        # Could not create tmp file
        failure("could not create tmp file", e)

    try:
        if not audioprocessing.convert_to_pcm(sound.original_path,
                                              tmp_wavefile):
            tmp_wavefile = sound.original_path
            success("no need to convert, this file is already pcm data")
        else:
            to_cleanup.append(tmp_wavefile)
            success("converted to pcm: " + tmp_wavefile)
    except AudioProcessingException as e:
        failure("conversion to pcm has failed, trying ffmpeg", e)
        try:
            audioprocessing.convert_using_ffmpeg(sound.original_path,
                                                 tmp_wavefile)
            to_cleanup.append(tmp_wavefile)
            success("converted to pcm: " + tmp_wavefile)
        except AudioProcessingException as e:
            failure("conversion to pcm with ffmpeg failed", e)
            return False
    except Exception as e:
        failure("unhandled exception", e)
        cleanup(to_cleanup)
        return False

    tmp_wavefile2 = tempfile.mktemp(suffix=".wav", prefix=str(sound.id))

    try:
        info = audioprocessing.stereofy_and_find_info(settings.STEREOFY_PATH,
                                                      tmp_wavefile,
                                                      tmp_wavefile2)
        to_cleanup.append(tmp_wavefile2)
    except AudioProcessingException as e:
        failure("stereofy has failed, trying ffmpeg first", e)
        try:
            audioprocessing.convert_using_ffmpeg(sound.original_path,
                                                 tmp_wavefile)
            info = audioprocessing.stereofy_and_find_info(
                settings.STEREOFY_PATH, tmp_wavefile, tmp_wavefile2)
            #if tmp_wavefile not in to_cleanup: to_cleanup.append(tmp_wavefile)
            to_cleanup.append(tmp_wavefile2)
        except AudioProcessingException as e:
            failure("ffmpeg + stereofy failed", e)
            cleanup(to_cleanup)
            return False
    except Exception as e:
        failure("unhandled exception", e)
        cleanup(to_cleanup)
        return False

    success("got sound info and stereofied: " + tmp_wavefile2)
    if sound.type in ["mp3", "ogg", "m4a"]:
        info['bitdepth'] = 0  # mp3 and ogg don't have bitdepth

    try:
        sound.set_audio_info_fields(info)
    except Exception as e:  # Could not catch a more specific exception
        failure("failed writting audio info fields to db", e)

    for mp3_path, quality in [(sound.locations("preview.LQ.mp3.path"), 70),
                              (sound.locations("preview.HQ.mp3.path"), 192)]:
        # create preview
        try:
            os.makedirs(os.path.dirname(mp3_path))
        except OSError:
            pass

        try:
            audioprocessing.convert_to_mp3(tmp_wavefile2, mp3_path, quality)
        except AudioProcessingException as e:
            cleanup(to_cleanup)
            failure("conversion to mp3 (preview) has failed", e)
            return False
        except Exception as e:
            failure("unhandled exception", e)
            cleanup(to_cleanup)
            return False
        success("created mp3: " + mp3_path)

    for ogg_path, quality in [(sound.locations("preview.LQ.ogg.path"), 1),
                              (sound.locations("preview.HQ.ogg.path"), 6)]:
        # create preview
        try:
            os.makedirs(os.path.dirname(ogg_path))
        except OSError:
            pass

        try:
            audioprocessing.convert_to_ogg(tmp_wavefile2, ogg_path, quality)
        except AudioProcessingException as e:
            cleanup(to_cleanup)
            failure("conversion to ogg (preview) has failed", e)
            return False
        except Exception as e:
            failure("unhandled exception", e)
            cleanup(to_cleanup)
            return False
        success("created ogg: " + ogg_path)

    # create waveform images M
    waveform_path_m = sound.locations("display.wave.M.path")
    spectral_path_m = sound.locations("display.spectral.M.path")

    try:
        os.makedirs(os.path.dirname(waveform_path_m))
    except OSError:
        pass

    try:
        audioprocessing.create_wave_images(tmp_wavefile2, waveform_path_m,
                                           spectral_path_m, 120, 71, 2048)
    except AudioProcessingException as e:
        cleanup(to_cleanup)
        failure("creation of images (M) has failed", e)
        return False
    except Exception as e:
        failure("unhandled exception", e)
        cleanup(to_cleanup)
        return False
    success("created previews, medium")

    # create waveform images L
    waveform_path_l = sound.locations("display.wave.L.path")
    spectral_path_l = sound.locations("display.spectral.L.path")
    try:
        audioprocessing.create_wave_images(tmp_wavefile2, waveform_path_l,
                                           spectral_path_l, 900, 201, 2048)
    except AudioProcessingException as e:
        cleanup(to_cleanup)
        failure("creation of images (L) has failed", e)
        return False
    except Exception as e:
        failure("unhandled exception", e)
        cleanup(to_cleanup)
        return False
    success("created previews, large")

    cleanup(to_cleanup)
    sound.set_processing_ongoing_state("FI")
    sound.change_processing_state("OK", use_set_instead_of_save=True)

    # Copy previews and display files to mirror locations
    copy_previews_to_mirror_locations(sound)
    copy_displays_to_mirror_locations(sound)

    return True
    def process(self, skip_previews=False, skip_displays=False):

        with TemporaryDirectory(
                prefix='processing_%s_' % self.sound.id,
                dir=settings.PROCESSING_TEMP_DIR) as tmp_directory:

            # Change ongoing processing state to "processing" in Sound model
            self.sound.set_processing_ongoing_state("PR")

            # Get the path of the original sound and convert to PCM
            try:
                sound_path = self.get_sound_path()
                tmp_wavefile = self.convert_to_pcm(sound_path, tmp_directory)
            except AudioProcessingException as e:
                self.set_failure(e)
                return False

            # Now get info about the file, stereofy it and save new stereofied PCM version in `tmp_wavefile2`
            try:
                fh, tmp_wavefile2 = tempfile.mkstemp(suffix=".wav", prefix="%i_" % self.sound.id, dir=tmp_directory)
                # Close file handler as we don't use it from Python
                os.close(fh)
                info = audioprocessing.stereofy_and_find_info(settings.STEREOFY_PATH, tmp_wavefile, tmp_wavefile2)
            except IOError as e:
                # Could not create tmp file
                self.set_failure("could not create tmp_wavefile2 file", e)
                return False
            except OSError as e:
                self.set_failure("stereofy has failed, "
                                 "make stereofy sure executable exists at %s: %s" % (settings.SOUNDS_PATH, e))
                return False
            except AudioProcessingException as e:
                if "File contains data in an unknown format" in str(e):
                    # Stereofy failed most probably because PCM file is corrupted. This can happen if "convert_to_pcm"
                    # above is skipped because the file is already PCM but it has wrong format. It can also happen in
                    # other occasions where "convert_to_pcm" generates bad PCM files. In this case we try to re-create
                    # the PCM file using ffmpeg and try re-running stereofy
                    self.log_info("stereofy failed, trying re-creating PCM file with ffmpeg and re-running stereofy")
                    try:
                        tmp_wavefile = self.convert_to_pcm(sound_path, tmp_directory, force_use_ffmpeg=True)
                        info = audioprocessing.stereofy_and_find_info(settings.STEREOFY_PATH,
                                                                      tmp_wavefile, tmp_wavefile2)
                    except AudioProcessingException as e:
                        self.set_failure("re-run of stereofy with ffmpeg conversion has failed", str(e))
                        return False
                    except Exception as e:
                        self.set_failure("unhandled exception while re-running stereofy with ffmpeg conversion", e)
                        return False
                else:
                    self.set_failure("stereofy has failed", str(e))
                    return False
            except Exception as e:
                self.set_failure("unhandled exception while getting info and running stereofy", e)
                return False

            self.log_info("got sound info and stereofied: " + tmp_wavefile2)

            # Fill audio information fields in Sound object
            try:
                if self.sound.type in ["mp3", "ogg", "m4a"]:
                    info['bitdepth'] = 0  # mp3 and ogg don't have bitdepth
                self.sound.set_audio_info_fields(**info)
            except Exception as e:  # Could not catch a more specific exception
                self.set_failure("failed writting audio info fields to db", e)
                return False

            # Generate MP3 and OGG previews
            if not skip_previews:

                # Create directory to store previews (if it does not exist)
                # Same directory is used for all MP3 and OGG previews of a given sound so we only need to run this once
                try:
                    create_directories(os.path.dirname(self.sound.locations("preview.LQ.mp3.path")))
                except OSError:
                    self.set_failure("could not create directory for previews")
                    return False

                # Generate MP3 previews
                for mp3_path, quality in [(self.sound.locations("preview.LQ.mp3.path"), 70),
                                          (self.sound.locations("preview.HQ.mp3.path"), 192)]:
                    try:
                        audioprocessing.convert_to_mp3(tmp_wavefile2, mp3_path, quality)
                    except OSError as e:
                        self.set_failure("conversion to mp3 (preview) has failed, "
                                         "make sure that lame executable exists: %s" % e)
                        return False

                    except AudioProcessingException as e:
                        self.set_failure("conversion to mp3 (preview) has failed", e)
                        return False
                    except Exception as e:
                        self.set_failure("unhandled exception generating MP3 previews", e)
                        return False
                    self.log_info("created mp3: " + mp3_path)

                # Generate OGG previews
                for ogg_path, quality in [(self.sound.locations("preview.LQ.ogg.path"), 1),
                                          (self.sound.locations("preview.HQ.ogg.path"), 6)]:
                    try:
                        audioprocessing.convert_to_ogg(tmp_wavefile2, ogg_path, quality)
                    except OSError as e:
                        self.set_failure("conversion to ogg (preview) has failed, "
                                         "make sure that oggenc executable exists: %s" % e)
                        return False
                    except AudioProcessingException as e:
                        self.set_failure("conversion to ogg (preview) has failed", e)
                        return False
                    except Exception as e:
                        self.set_failure("unhandled exception generating OGG previews", e)
                        return False
                    self.log_info("created ogg: " + ogg_path)

            # Generate display images for different sizes and colour scheme front-ends
            if not skip_displays:

                # Create directory to store display images (if it does not exist)
                # Same directory is used for all displays of a given sound so we only need to run this once
                try:
                    create_directories(os.path.dirname(self.sound.locations("display.wave.M.path")))
                except OSError:
                    self.set_failure("could not create directory for displays")
                    return False

                # Generate display images, M and L sizes for NG and BW front-ends
                for width, height, color_scheme, waveform_path, spectral_path in [
                    (120, 71, color_schemes.FREESOUND2_COLOR_SCHEME,
                     self.sound.locations("display.wave.M.path"), self.sound.locations("display.spectral.M.path")),
                    (500, 201, color_schemes.BEASTWHOOSH_COLOR_SCHEME,
                     self.sound.locations("display.wave_bw.M.path"), self.sound.locations("display.spectral_bw.M.path")),
                    (900, 201, color_schemes.FREESOUND2_COLOR_SCHEME,
                     self.sound.locations("display.wave.L.path"), self.sound.locations("display.spectral.L.path")),
                    (1500, 401, color_schemes.BEASTWHOOSH_COLOR_SCHEME,
                     self.sound.locations("display.wave_bw.L.path"), self.sound.locations("display.spectral_bw.L.path"))
                ]:
                    try:
                        fft_size = 2048
                        audioprocessing.create_wave_images(tmp_wavefile2, waveform_path, spectral_path, width, height,
                                                           fft_size, color_scheme=color_scheme)
                        self.log_info("created wave and spectrogram images: %s, %s" % (waveform_path, spectral_path))
                    except AudioProcessingException as e:
                        self.set_failure("creation of display images has failed", e)
                        return False
                    except Exception as e:
                        self.set_failure("unhandled exception while generating displays", e)
                        return False

        # Change processing state and processing ongoing state in Sound model
        self.sound.set_processing_ongoing_state("FI")
        self.sound.change_processing_state("OK", processing_log=self.work_log)

        # Copy previews and display files to mirror locations
        copy_previews_to_mirror_locations(self.sound)
        copy_displays_to_mirror_locations(self.sound)

        return True
def process(sound, skip_previews=False, skip_displays=False):
    def write_log(message):
        sys.stdout.write(str(message) + '\n')
        sys.stdout.flush()
        logger.info("[%d] %i: %s" % (os.getpid(), sound.id, message))

    def create_directory(path):
        try:
            os.makedirs(path)
        except OSError as exc:
            if exc.errno == errno.EEXIST and os.path.isdir(path):
                # Directory already exists
                pass
            else:
                # Directory could not be created, raise exception
                raise

    def cleanup(files):
        success("cleaning up processing files: " + ", ".join(files))
        for filename in files:
            try:
                os.unlink(filename)
            except:
                pass

    def failure(message, error=None):
        sound.set_processing_ongoing_state("FI")
        sound.change_processing_state("FA", use_set_instead_of_save=True)
        logging_message = "ERROR: Failed to process sound with id %s\n" % sound.id
        logging_message += "\tmessage: %s\n" % message
        if error:
            logging_message += "\terror: %s" % str(error)
        write_log(logging_message)
        cleanup(to_cleanup)

    def success(message):
        write_log('- ' + message)

    to_cleanup = [
    ]  # This will hold a list of files to cleanup after processing

    # Change ongoing processing state to "processing" in Sound model
    sound.set_processing_ongoing_state("PR")

    # Get the path of the original sound
    sound_path = sound.locations('path')
    if settings.USE_PREVIEWS_WHEN_ORIGINAL_FILES_MISSING and not os.path.exists(
            sound_path):
        sound_path = sound.locations('preview.LQ.mp3.path')
    if not os.path.exists(sound_path):
        failure("can't process sound as file does not exist")
        return False
    success("file to process found in " + sound_path)

    # Convert to PCM and save PCM version in `tmp_wavefile`
    try:
        tmp_wavefile = tempfile.mktemp(suffix=".wav", prefix=str(sound.id))
        if not audioprocessing.convert_to_pcm(sound_path, tmp_wavefile):
            tmp_wavefile = sound_path
            success("no need to convert, this file is already PCM data")
        else:
            to_cleanup.append(tmp_wavefile)
            success("converted to pcm: " + tmp_wavefile)
    except IOError as e:
        # Could not create tmp file
        failure("could not create tmp_wavefile file", e)
        return False
    except AudioProcessingException as e:
        try:
            audioprocessing.convert_using_ffmpeg(sound_path, tmp_wavefile)
            to_cleanup.append(tmp_wavefile)
            success("converted to PCM: " + tmp_wavefile)
        except AudioProcessingException as e:
            failure("conversion to PCM failed", e)
            return False
    except Exception as e:
        failure("unhandled exception while converting to PCM", e)
        return False

    # Now get info about the file, stereofy it and save new stereofied PCM version in `tmp_wavefile2`
    try:
        tmp_wavefile2 = tempfile.mktemp(suffix=".wav", prefix=str(sound.id))
        to_cleanup.append(tmp_wavefile2)
        info = audioprocessing.stereofy_and_find_info(settings.STEREOFY_PATH,
                                                      tmp_wavefile,
                                                      tmp_wavefile2)
        if sound.type in ["mp3", "ogg", "m4a"]:
            info['bitdepth'] = 0  # mp3 and ogg don't have bitdepth
        success("got sound info and stereofied: " + tmp_wavefile2)
    except IOError as e:
        # Could not create tmp file
        failure("could not create tmp_wavefile2 file", e)
        return False
    except AudioProcessingException as e:
        failure("stereofy has failed", e)
        return False
    except Exception as e:
        failure("unhandled exception while getting info and running stereofy",
                e)
        return False

    # Fill audio information fields in Sound object
    try:
        sound.set_audio_info_fields(info)
    except Exception as e:  # Could not catch a more specific exception
        failure("failed writting audio info fields to db", e)
        return False

    # Generate MP3 and OGG previews
    if not skip_previews:

        # Create directory to store previews (if it does not exist)
        # Same directory is used for all MP3 and OGG previews of a given sound so we only need to run this once
        try:
            create_directory(
                os.path.dirname(sound.locations("preview.LQ.mp3.path")))
        except OSError:
            failure("could not create directory for previews")
            return False

        # Generate MP3 previews
        for mp3_path, quality in [(sound.locations("preview.LQ.mp3.path"), 70),
                                  (sound.locations("preview.HQ.mp3.path"), 192)
                                  ]:
            try:
                audioprocessing.convert_to_mp3(tmp_wavefile2, mp3_path,
                                               quality)
            except AudioProcessingException as e:
                failure("conversion to mp3 (preview) has failed", e)
                return False
            except Exception as e:
                failure("unhandled exception generating MP3 previews", e)
                return False
            success("created mp3: " + mp3_path)

        # Generate OGG previews
        for ogg_path, quality in [(sound.locations("preview.LQ.ogg.path"), 1),
                                  (sound.locations("preview.HQ.ogg.path"), 6)]:
            try:
                audioprocessing.convert_to_ogg(tmp_wavefile2, ogg_path,
                                               quality)
            except AudioProcessingException as e:
                failure("conversion to ogg (preview) has failed", e)
                return False
            except Exception as e:
                failure("unhandled exception generating OGG previews", e)
                return False
            success("created ogg: " + ogg_path)

    # Generate display images for different sizes and colour scheme front-ends
    if not skip_displays:

        # Create directory to store display images (if it does not exist)
        # Same directory is used for all displays of a given sound so we only need to run this once
        try:
            create_directory(
                os.path.dirname(sound.locations("display.wave.M.path")))
        except OSError:
            failure("could not create directory for displays")
            return False

        # Generate display images, M and L sizes for NG and BW front-ends
        for width, height, color_scheme, waveform_path, spectral_path in [
            (120, 71, color_schemes.FREESOUND2_COLOR_SCHEME,
             sound.locations("display.wave.M.path"),
             sound.locations("display.spectral.M.path")),
            (500, 201, color_schemes.BEASTWHOOSH_COLOR_SCHEME,
             sound.locations("display.wave_bw.M.path"),
             sound.locations("display.spectral_bw.M.path")),
            (900, 201, color_schemes.FREESOUND2_COLOR_SCHEME,
             sound.locations("display.wave.L.path"),
             sound.locations("display.spectral.L.path")),
            (1500, 401, color_schemes.BEASTWHOOSH_COLOR_SCHEME,
             sound.locations("display.wave_bw.L.path"),
             sound.locations("display.spectral_bw.L.path"))
        ]:
            try:
                fft_size = 2048
                audioprocessing.create_wave_images(tmp_wavefile2,
                                                   waveform_path,
                                                   spectral_path,
                                                   width,
                                                   height,
                                                   fft_size,
                                                   color_scheme=color_scheme)
                success("created wave and spectrogram images: %s, %s" %
                        (waveform_path, spectral_path))
            except AudioProcessingException as e:
                failure("creation of display images has failed", e)
                return False
            except Exception as e:
                failure("unhandled exception while generating displays", e)
                return False

    # Clean up temp files
    cleanup(to_cleanup)

    # Change processing state and processing ongoing state in Sound model
    sound.set_processing_ongoing_state("FI")
    sound.change_processing_state("OK", use_set_instead_of_save=True)

    # Copy previews and display files to mirror locations
    copy_previews_to_mirror_locations(sound)
    copy_displays_to_mirror_locations(sound)

    return True