diff --git a/src/webui/static/app/dvb.js b/src/webui/static/app/dvb.js
index d0c257b0..c82611a3 100644
--- a/src/webui/static/app/dvb.js
+++ b/src/webui/static/app/dvb.js
@@ -371,7 +371,7 @@ tvheadend.dvb_services = function(adapterId) {
dataIndex: 'id',
width: 50,
renderer: function(value, metadata, record, row, col, store) {
- url = makeRTSPprefix() + 'service/' + value
+ url = 'stream/service/' + value
return 'Play'
}
},
diff --git a/src/webui/webui.c b/src/webui/webui.c
index eda7f4bd..6316eaf1 100644
--- a/src/webui/webui.c
+++ b/src/webui/webui.c
@@ -284,6 +284,39 @@ http_stream_playlist(http_connection_t *hc)
pthread_mutex_unlock(&global_lock);
}
+/**
+ * Subscribes to a service and starts the streaming loop
+ */
+static int
+http_stream_service(http_connection_t *hc, service_t *service)
+{
+ streaming_queue_t sq;
+ th_subscription_t *s;
+
+ pthread_mutex_lock(&global_lock);
+
+ streaming_queue_init(&sq, ~SMT_TO_MASK(SUBSCRIPTION_RAW_MPEGTS));
+
+ s = subscription_create_from_service(service,
+ "HTTP", &sq.sq_st,
+ SUBSCRIPTION_RAW_MPEGTS);
+
+
+ pthread_mutex_unlock(&global_lock);
+
+ //We won't get a START command, send http-header here.
+ http_output_content(hc, "video/mp2t");
+
+ http_stream_run(hc, &sq);
+
+ pthread_mutex_lock(&global_lock);
+ subscription_unsubscribe(s);
+ pthread_mutex_unlock(&global_lock);
+ streaming_queue_deinit(&sq);
+
+ return 0;
+}
+
/**
* Subscribes to a channel and starts the streaming loop
*/
@@ -319,12 +352,14 @@ http_stream_channel(http_connection_t *hc, channel_t *ch)
/**
* Handle the http request. http://tvheadend/stream/channelid/
* http://tvheadend/stream/channel/
+ * http://tvheadend/stream/service/
*/
static int
http_stream(http_connection_t *hc, const char *remain, void *opaque)
{
char *components[2];
channel_t *ch = NULL;
+ service_t *service = NULL;
if(http_access_verify(hc, ACCESS_STREAMING)) {
http_error(hc, HTTP_STATUS_UNAUTHORIZED);
@@ -351,16 +386,20 @@ http_stream(http_connection_t *hc, const char *remain, void *opaque)
ch = channel_find_by_identifier(atoi(components[1]));
} else if(!strcmp(components[0], "channel")) {
ch = channel_find_by_name(components[1], 0, 0);
+ } else if(!strcmp(components[0], "service")) {
+ service = service_find_by_identifier(components[1]);
}
pthread_mutex_unlock(&global_lock);
- if(ch == NULL) {
+ if(ch != NULL) {
+ return http_stream_channel(hc, ch);
+ } else if(service != NULL) {
+ return http_stream_service(hc, service);
+ } else {
http_error(hc, HTTP_STATUS_BAD_REQUEST);
return HTTP_STATUS_BAD_REQUEST;
}
-
- return http_stream_channel(hc, ch);
}