package pl.piotrsukiennik.whowhen.convertion.service; import it.sauronsoftware.jave.Encoder; import it.sauronsoftware.jave.EncoderException; import it.sauronsoftware.jave.MultimediaInfo; import org.apache.commons.lang.exception.ExceptionUtils; import org.apache.commons.logging.Log; import org.apache.commons.logging.LogFactory; import org.springframework.stereotype.Component; import pl.piotrsukiennik.whowhen.backend.api.inner.convertion.ConvertionRequest; import pl.piotrsukiennik.whowhen.backend.api.inner.convertion.ConvertionResponse; import pl.piotrsukiennik.whowhen.backend.api.inner.convertion.ConvertionService; import pl.piotrsukiennik.whowhen.backend.api.inner.util.AudioInfo; import pl.piotrsukiennik.whowhen.backend.api.outer.IBackendService; import pl.piotrsukiennik.whowhen.convertion.ProgressObservableEncoderProgressListener; import pl.piotrsukiennik.whowhen.convertion.configuration.EncoderBuilder; import pl.piotrsukiennik.whowhen.shared.serializer.impl.JSONDataSerializer; import pl.piotrsukiennik.whowhen.shared.serializer.util.SerializeOnChangeObserver; import pl.piotrsukiennik.whowhen.shared.util.progress.Progress; import pl.piotrsukiennik.whowhen.shared.util.progress.ProgressObservable; import pl.piotrsukiennik.whowhen.shared.util.progress.ProgressObservableCompletionListener; import javax.annotation.Resource; import java.io.File; import java.util.concurrent.ExecutorService; import java.util.concurrent.Executors; /** * @author Piotr Sukiennik */ @Component( "convertionServiceImpl" ) public class ConvertionServiceImpl implements ConvertionService { private static Log log = LogFactory.getLog( ConvertionServiceImpl.class ); private ExecutorService executorService = Executors.newFixedThreadPool( 4 ); @Resource private EncoderBuilder encoderBuilder; @Resource private Encoder encoder; @Resource private IBackendService backendService; @Override public void handle( final ConvertionRequest convertionRequest ) { try { final File convertedFile = new File( convertionRequest.getFileToConvert().getParentFile(), "converted_" + convertionRequest.getFileToConvert().getName() + ".wav" ); ProgressObservableEncoderProgressListener progressListener = new ProgressObservableEncoderProgressListener( new Progress() ); SerializeOnChangeObserver serializeOnChangeObserver = new SerializeOnChangeObserver( convertionRequest.getFileToConvert().getParentFile(), new JSONDataSerializer() ); serializeOnChangeObserver.setNamePrefix( "convertionProgress" ); progressListener.addObserver( serializeOnChangeObserver ); progressListener.addObserver( new ProgressObservableCompletionListener() { @Override protected void complete( ProgressObservable observable, Object arg ) { try { MultimediaInfo multimediaInfo = encoder.getInfo( convertedFile ); ConvertionResponse convertionResponse = new ConvertionResponse( convertionRequest.getRequestIdentifier(), map( convertedFile, multimediaInfo, encoderBuilder.isSigned(), encoderBuilder.isBigEndian() ) ); backendService.notify( convertionResponse ); } catch ( Exception e ) { if ( log.isErrorEnabled() ) { log.error( ExceptionUtils.getStackTrace( e ) ); } } } @Override protected boolean isCompleted( ProgressObservable observable, Object arg ) { return observable.getProgress() >= 100; } } ); executorService.submit( encoderBuilder.buildEncoder( convertionRequest.getFileToConvert(), convertedFile, progressListener ) ); } catch ( Exception e ) { if ( log.isErrorEnabled() ) { log.error( ExceptionUtils.getStackTrace( e ) ); } } } @Override public String[] getAcceptableFormats() { try { return encoder.getSupportedDecodingFormats(); } catch ( EncoderException e ) { return new String[] { }; } } public static AudioInfo map( File audioFile, MultimediaInfo multimediaInfo, boolean signed, boolean bigEndian ) { AudioInfo audioInfo = new AudioInfo( audioFile ); audioInfo.setChannels( multimediaInfo.getAudio().getChannels() ); audioInfo.setDuration( multimediaInfo.getDuration() ); audioInfo.setSampleRate( multimediaInfo.getAudio().getSamplingRate() ); if ( log.isErrorEnabled() ) { log.info( "multimediaInfo.getAudio().getBitRate()" + multimediaInfo.getAudio().getBitRate() ); log.info( "multimediaInfo.getAudio().getSamplingRate()" + multimediaInfo.getAudio().getSamplingRate() ); log.info( "setSampleSizeInBits(" + ( multimediaInfo.getAudio().getBitRate() * 1000 ) / multimediaInfo.getAudio().getSamplingRate() + ")" ); } audioInfo.setSampleSizeInBits( ( multimediaInfo.getAudio().getBitRate() * 1000 ) / multimediaInfo.getAudio().getSamplingRate() ); audioInfo.setSigned( signed ); audioInfo.setBigEndian( bigEndian ); return audioInfo; } }