Go
Not registered? Sign up!

Servlet Streaming

Google Translate
8 posts | return to the Modules forum | get the rss feed for this thread

Dec. 02, 2008Derek Knapp

well here is my attempt at writing xmoov-php for java servlets, it kinda works.. except you can't jump around with the slider, even parts that have been downloaded :(

i assume each time you move the slider to a part that hasn't been downloaded... it should make a new call to the streamer, with a new start position??? i only seem to be getting one request, at start = 0


package wyd;

import java.io.File;
import java.io.IOException;
import java.io.OutputStream;
import java.io.PrintWriter;
import java.io.RandomAccessFile;
import java.util.Enumeration;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

/**
*
* @author Derek Knapp
*/
public class watch extends HttpServlet
{
// SCRIPT CONFIGURATION

//------------------------------------------------------------------------------------------
// MEDIA PATH
//
// you can configure these settings to point to video files outside the public html folder.
//------------------------------------------------------------------------------------------

// points to server root
public static final String XMOOV_PATH_ROOT = "";

// points to the folder containing the video files.
public static final String XMOOV_PATH_FILES = "/ffmpeg/out/";



//------------------------------------------------------------------------------------------
// SCRIPT BEHAVIOR
//------------------------------------------------------------------------------------------

//set to TRUE to use bandwidth limiting.
public static final Boolean XMOOV_CONF_LIMIT_BANDWIDTH = true;

//set to FALSE to prohibit caching of video files.
public static final Boolean XMOOV_CONF_ALLOW_FILE_CACHE = false;



//------------------------------------------------------------------------------------------
// BANDWIDTH SETTINGS
//
// these settings are only needed when using bandwidth limiting.
//
// bandwidth is limited my sending a limited amount of video data(XMOOV_BW_PACKET_SIZE),
// in specified time intervals(XMOOV_BW_PACKET_INTERVAL).
// avoid time intervals over 1.5 seconds for best results.
//
// you can also control bandwidth limiting via http command using your video player.
// the function getBandwidthLimit($part) holds three preconfigured presets(low, mid, high),
// which can be changed to meet your needs
//------------------------------------------------------------------------------------------

//set how many kilobytes will be sent per time interval
public static final Integer XMOOV_BW_PACKET_SIZE = 90;

//set the time interval in which data packets will be sent in seconds.
public static final Double XMOOV_BW_PACKET_INTERVAL = 1.5;

//set to TRUE to control bandwidth externally via http.
public static final Boolean XMOOV_CONF_ALLOW_DYNAMIC_BANDWIDTH = true;



//------------------------------------------------------------------------------------------
// DYNAMIC BANDWIDTH CONTROL
//------------------------------------------------------------------------------------------

private Double getBandwidthIntervalLimit()
{
/*
switch($_GET[XMOOV_GET_BANDWIDTH])
{
case 'low' :
return 0.5;
break;
case 'mid' :
return 0.5;
break;
case 'high' :
return 0.2;
break;
case 'off' :
return 0;
break;
default :
return XMOOV_BW_PACKET_INTERVAL;
break;
*/
return XMOOV_BW_PACKET_INTERVAL;
}

private Integer getBandwidthSizeLimit()
{
/*
switch($_GET[XMOOV_GET_BANDWIDTH])
{
case 'low' :
return 20;
break;
case 'mid' :
return 40;
break;
case 'high' :
return 90;
break;
default :
return XMOOV_BW_PACKET_SIZE;
break;
}
*/
return XMOOV_BW_PACKET_SIZE;
}



//------------------------------------------------------------------------------------------
// INCOMING GET VARIABLES CONFIGURATION
//
// use these settings to configure how video files, seek position and bandwidth settings are accessed by your player
//------------------------------------------------------------------------------------------

public static final String XMOOV_GET_FILE = "file";
public static final String XMOOV_GET_POSITION = "start";
public static final String XMOOV_GET_AUTHENTICATION = "key";
public static final String XMOOV_GET_BANDWIDTH = "bw";



// END SCRIPT CONFIGURATION - do not change anything beyond this point if you do not know what you are doing



//------------------------------------------------------------------------------------------
// PROCESS FILE REQUEST
//------------------------------------------------------------------------------------------

public static final byte[] FLV_HEADER = new byte[]{
(byte) 0x46, (byte) 0x4C, (byte) 0x56,
(byte) 0x01,
(byte) 0x05,
(byte) 0x00, (byte) 0x00, (byte) 0x00, (byte) 0x09,
(byte) 0x00, (byte) 0x00, (byte) 0x00, (byte) 0x09
};

/**
* Processes requests for both HTTP <code>GET</code> and <code>POST</code> methods.
* @param request servlet request
* @param response servlet response
* @throws ServletException if a servlet-specific error occurs
* @throws IOException if an I/O error occurs
*/
protected void processRequest(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException
{
Enumeration en = request.getParameterNames();
String str = "-----------------\n";
while (en.hasMoreElements())
{
String s = (String) en.nextElement();
str += s + " = " + request.getParameter(s) + "\n";
}
str += "-----------------\n";
System.out.println(str);

if (request.getParameter(XMOOV_GET_FILE) != null && request.getParameter(XMOOV_GET_POSITION) != null)
{
// PROCESS VARIABLES

// get seek position
Long seekPos = Long.valueOf(request.getParameter(XMOOV_GET_POSITION));
// get file name
String fileName = request.getParameter(XMOOV_GET_FILE);
// assemble file path
String file = XMOOV_PATH_ROOT + XMOOV_PATH_FILES + fileName;

// assemble packet interval
Double packet_interval = (XMOOV_CONF_ALLOW_DYNAMIC_BANDWIDTH && request.getParameter(XMOOV_GET_BANDWIDTH) != null) ? getBandwidthIntervalLimit() : XMOOV_BW_PACKET_INTERVAL;
// assemble packet size
Integer packet_size = ((XMOOV_CONF_ALLOW_DYNAMIC_BANDWIDTH && request.getParameter(XMOOV_GET_BANDWIDTH) != null) ? getBandwidthSizeLimit() : XMOOV_BW_PACKET_SIZE) * 1042;

File f = new File(file);

if (!f.exists())
{
PrintWriter out = response.getWriter();
out.println("<b>ERROR:</b> xmoov-php could not find (" + fileName + ") please check your settings.");
System.out.println("<b>ERROR:</b> xmoov-php could not find (" + fileName + ") please check your settings.");
out.close();
return;
}
else
{
OutputStream out = response.getOutputStream();
RandomAccessFile fh = new RandomAccessFile(f, "r");

Long fileSize = fh.length() - ((seekPos > 0) ? seekPos + 1 : 0);

// SEND HEADERS
if (!XMOOV_CONF_ALLOW_FILE_CACHE)
{
// prohibit caching (different methods for different clients)
response.addHeader("Expires", "Thu, 19 Nov 1981 08:52:00 GMT");
response.addHeader("Cache-Control", "no-store, no-cache, must-revalidate, post-check=0, pre-check=0");
response.addHeader("Pragma", "no-cache");
}

// content headers
response.setContentType("video/x-flv");
response.addHeader("Content-Disposition", "attachment; filename=\"" + fileName + "\"");
response.setContentLength(fileSize.intValue());

// FLV file format header
if (seekPos != 0)
{
out.write(FLV_HEADER);
}

// seek to requested file position
fh.seek(seekPos);

// output file
while (fh.getFilePointer() < fh.length())
{
// use bandwidth limiting
if (XMOOV_CONF_LIMIT_BANDWIDTH && packet_interval > 0)
{
// get start time
Long time_start = System.currentTimeMillis();
// output packet
byte[] buf = new byte[packet_size];
fh.read(buf);
out.write(buf);
// get end time
Long time_stop = System.currentTimeMillis();
// wait if output is slower than $packet_interval
Long time_difference = time_stop - time_start;
if (time_difference < packet_interval)
{
try
{
Thread.sleep((long)(packet_interval * 1000) - time_difference * 1000);
}
catch (Exception e)
{
}
}
}
else
{
// output file without bandwidth limiting
byte[] buf = new byte[1024];
fh.read(buf);
out.write(buf);
}
}
}
}
}

/**
* Handles the HTTP <code>GET</code> method.
* @param request servlet request
* @param response servlet response
* @throws ServletException if a servlet-specific error occurs
* @throws IOException if an I/O error occurs
*/
@Override
protected void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException
{
processRequest(request, response);
}

/**
* Handles the HTTP <code>POST</code> method.
* @param request servlet request
* @param response servlet response
* @throws ServletException if a servlet-specific error occurs
* @throws IOException if an I/O error occurs
*/
@Override
protected void doPost(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException
{
processRequest(request, response);
}

/**
* Returns a short description of the servlet.
* @return a String containing servlet description
*/
@Override
public String getServletInfo()
{
return "stream video";
}
}

Dec. 02, 2008Derek Knapp

oh and this is all i see in my log file

[#|2008-12-02T21:10:23.734-0500|INFO|sun-appserver9.1|javax.enterprise.system.stream.out|_ThreadID=21;_ThreadName=httpSSLWorkerThread-80-1;|
-----------------
file = d2500fb3-e77a-4a16-ab7e-57be6745e0b2
start = 0
id = ply
client = FLASH WIN 10,0,12,36
version = 4.2.95
width = 420
-----------------
|#]

Dec. 02, 2008Derek Knapp

here is the code for the player


<p id='${item.guid}' class="media">Here the video will be shown.</p>

<script type='text/javascript'>
var s1 = new SWFObject('/wyd-war/player/player.swf','ply','420','250','9','#ffffff');
s1.addParam('allowfullscreen','true');
s1.addParam('flashvars','file=${item.guid}&type=video&streamscript=/wyd-war/watch');
s1.write('${item.guid}');
</script>

Dec. 02, 2008Derek Knapp

ok so it was my flash video, i guess it didnt have the required meta data

Jun. 24, 2009doesn't compile!

Your code doesn't compile at all.

Is it a joke or what ? You have tons of basic errors all around...

JR ;-/

Aug. 19, 2009Tavo

The code compile (my case) but when i call from flex proyect, give me error (discordant arguments).

:( If i resolve the problem, i will publish.

Greetings.

Sep. 22, 2009Tavo

well... i don't resolve the problem, but this was the motivation for implements the same functionality for our pourposes. Actually we have a server that read a flv file and return the stream. If you want know the code, please notify me. Greetings.

Oct. 02, 2009Cay Horstmann

Thanks very much! The servlet works perfectly for me. This was much easier than I thought it would be. I made one change, setting

String file = XMOOV_PATH_ROOT != null ? XMOOV_PATH_ROOT + XMOOV_PATH_FILES + fileName : getServletContext().getRealPath("/" + XMOOV_PATH_FILES + fileName);

That way, you can put your videos into the context directory. I like that because I can then give users the option of downloading the video if their connection (or my server) is slow.

Add a reaction

You can also return to the category or try this search for related threads.


 

Search the Forums

Go

Support

Support Here are some helpful links to learn more about the JW Player™:

Monetize Your Video

Monetize Your Video Earn money with ads from LongTail's AdSolution. Watch our demos and sign up now!

Why Buy a License?

Why Buy a License? If you don’t buy a commercial license, you cannot use a JW Player™ on (i) a site that has ads; (ii) a corporate site; or a (iii) CMS. Our licenses are very inexpensive, so what are you waiting for? Buy a license today.