If I were to try to run this on my system, it would fail because there is
no ffmpeg.exe file on my machine.

You need to make it easier for me to help you by making a truly
self-contained minimal example of the issue (see
http://www.catb.org/~esr/faqs/smart-questions.html#code for more details on
this).  Preferably the example will contain a pom.xml so it can be built
easily and maybe put in on a gist in github so it can be downloaded easily.



On Sun, Feb 5, 2017 at 3:46 PM, Edgar H <kaotix...@gmail.com> wrote:

> Sure, here's a minimal example.
>
> The following code belongs to a "MainApp" class, which is the basically the
> application which starts the .jar responsible of capturing live audio data
> from the system and sending it live to FFMPEG, which streams to an Icecast
> Server, like a continuous stream using pipes.
>
> public class MainApp {
>
>     public static void main(String[] args) {
>         initStream("Path to FFMPEG bin folder, which should include the
> .jar of the second application that you need to copy and paste.");
>     }
>
>     public static void initStream(String path) {
>         File file = new File(path);
>         for (File s : file.listFiles()) {
>             if (s.getName().equals("ffmpeg.exe")) {
>                 try {
>                     DefaultExecutor executor = new DefaultExecutor();
>                     executor.setWorkingDirectory(file);
>
>                     CommandLine commandLine = new
> CommandLine(s.getParentFile().getAbsolutePath());
>                     System.out.println("Path: " + commandLine.toString());
>
>                     String executeMe = "java -jar secondapp.jar"; //
> Execute "SecondApp" .jar to start sending sound bytes to stdout.
>                     commandLine = CommandLine.parse(executeMe);
>
>                     PipedOutputStream output = new PipedOutputStream(); //
> Fill this with bytes.
>                     PipedInputStream input = new PipedInputStream();
>                     output.connect(input); // Send audio bytes from output
> to this input stream.
>
>                     executor.setStreamHandler(new PumpStreamHandler(output,
> null)); // Stream all the bytes to the output.
>                     executor.execute(commandLine, new
> DefaultExecuteResultHandler()); // Execute APP2 (The one which captures
> the
> live audio bytes).
>
>                     String feedMe = "ffmpeg -f s16le -ar 48000 -ac 2 -i -
> -f ogg -content_type application/ogg icecast://source:hackme@localhost
> :8000/stream";
>                     commandLine = CommandLine.parse(feedMe);
>
>                     executor.setStreamHandler(new PumpStreamHandler(null,
> null, input)); // Send the bytes being received in real time to FFMPEG.
>                     executor.execute(commandLine, new
> DefaultExecuteResultHandler()); // Execute FFMPEG.
>                 } catch (IOException e) {
>                     e.printStackTrace();
>                 }
>             }
>         }
>     }
> }
>
> Now, this is the code for the executable .jar which is the class
> "SecondApp". This one just sends bytes to the Standard Output and it's
> started by "MainApp".
>
> public class SecondApp {
>
>     public static void main(String[] args) throws ClassNotFoundException,
> IOException {
>         Mixer mixer =
> AudioSystem.getMixer(AudioSystem.getMixerInfo()[
> Integer.parseInt(args[0])]);
>         AudioFormat af = new AudioFormat(Encoding.PCM_SIGNED, 48000f, 16,
> 2, 4, 48000f, false);
>
>         TargetDataLine line;
>         DataLine.Info info = new DataLine.Info(TargetDataLine.class, af);
>         if (!AudioSystem.isLineSupported(info))
>             System.out.println("Line is not supported.");
>
>         try {
>             line = (TargetDataLine) mixer.getLine(info);
>             line.open(af);
>
>             int bytesRead, CHUNK_SIZE = 4096;
>             byte[] data = new byte[line.getBufferSize() / 5];
>
>             line.start();
>
>             while (true) {
>                 bytesRead = line.read(data, 0, CHUNK_SIZE);
>                 System.out.write(data, 0, bytesRead);
>                 System.out.flush();
>             }
>
>         } catch (LineUnavailableException ex) {
>             System.out.println("Line is unavailable.");
>             ex.printStackTrace();
>         }
>     }
> }
>
> 2017-02-05 16:31 GMT+01:00 Raymond DeCampo <r...@decampo.org>:
>
> > Edgar, I didn't see anything obvious wrong with what you posted.  If you
> > can distill it down to a minimal self-contained example that reproduces
> the
> > behavior I can take a closer look.
> >
> > On Sat, Feb 4, 2017 at 1:47 PM, Edgar H <kaotix...@gmail.com> wrote:
> >
> > > I've been struggling with this problem for quite some time now as it's
> my
> > > very first time doing an application related to streaming and I just
> > can't
> > > figure out why. Here's the problem...
> > >
> > > What I'm trying to achieve is to send a command's output as an input
> for
> > > the next one, which is basically what the pipe operator does. As I knew
> > > this couldn't be executed directly with Exec library from Apache
> Commons
> > I
> > > started looking for ways to solve this. I've seen quite a few examples
> of
> > > similar things to this but none of them covers my situation:
> > >
> > > I have two Java applications separated, one is the main application and
> > the
> > > second one is initialized by the first one. This second applications
> > sends
> > > to the Standard Output bytes, which FFMPEG should receive.
> > >
> > > The code that I have so far is the following one...
> > >
> > > public void initStream(String path) {
> > >     File file = new File(path);
> > >     for (File s : file.listFiles()) {
> > >         if (s.getName().equals("ffmpeg.exe")) {
> > >             try {
> > >
> > >                 // Second app, supposedly, writes here.
> > >                 PipedOutputStream output = new PipedOutputStream();
> > >
> > >                 DefaultExecutor executor = new DefaultExecutor();
> > >                 //DefaultExecutor executorFFMPEG = new
> DefaultExecutor();
> > >                 executor.setWorkingDirectory(file);
> > >                 //executor.setWorkingDirectory(file);
> > >
> > >                 CommandLine commandLine = new
> > > CommandLine(s.getParentFile().getAbsolutePath());
> > >                 System.out.println("Path: " + commandLine.toString());
> > >
> > >                 String executeMe = "java -jar streamer.jar";
> > >                 commandLine = CommandLine.parse(executeMe);
> > >
> > >                 System.out.println("[testing] streamer about to
> > launch.");
> > >                 executor.setStreamHandler(new PumpStreamHandler(output,
> > > null));
> > >                 executor.execute(commandLine, new
> > > DefaultExecuteResultHandler());
> > >                 System.out.println("[testing] streamer started.");
> > >
> > >                 PipedInputStream input = new PipedInputStream();
> > >                 output.connect(input);
> > >
> > >                 String feedMe = "ffmpeg"; // more attributes here
> > >                 commandLine = CommandLine.parse(feedMe);
> > >
> > >                 System.out.println("[testing] ffmpeg about to
> launch.");
> > >                 executor.setStreamHandler(new PumpStreamHandler(null,
> > > null, input));
> > >                 executor.execute(commandLine, new
> > > DefaultExecuteResultHandler());
> > >                 System.out.println("[testing] ffmpeg started.");
> > >
> > >             } catch (IOException e) {
> > >                 e.printStackTrace();
> > >             }
> > >         }
> > >     }}
> > >
> > > And the code for the second application (the zone where I send data to
> > > the stdout) is the following one.
> > >
> > > static OutputStream stdout = System.out;
> > >
> > > (more code and other things around here)
> > >
> > > try {
> > >         line = (TargetDataLine) mixer.getLine(info);
> > >         line.open(format);
> > >
> > >         int bytesRead, CHUNK_SIZE = 4096;
> > >         byte[] data = new byte[line.getBufferSize() / 5];
> > >
> > >         line.start();
> > >
> > >         while (true) {
> > >             bytesRead = line.read(data, 0, CHUNK_SIZE);
> > >             stdout.write(data, 0, bytesRead);
> > >             stdout.flush();
> > >         }
> > >
> > >     } catch (LineUnavailableException ex) {
> > >         System.out.println("Line is unavailable.");
> > >         ex.printStackTrace();
> > >     }
> > >
> > > At the moment, no communication seems to be made between both commands
> as
> > > ffmpeg isn't receiving anything.
> > >
> > > Hope you guys can tell what I'm missing out, or if I'm incorrectly
> > working
> > > with the library thinking it works in a way when it works in another
> one.
> > >
> >
>

Reply via email to