Real-time audio streaming using HTTP - choosing the protocol and Java implementation -


i'm trying implement simple http server real-time audio (in java). suppose there website can see list of songs playing 1 after another. when client connects server - lets in middle of song - i'm thinking use "range" http header , send data range starting part of song. if during download connection temporary lost (and song finished) - should server send previous song part , finish - or should server send parts of song playing @ moment? best practices/principles?

ps - i'm not looking 3rd party software audio streaming.

edit:
after research in available real-time streaming technologies, see these goals:
1. choosing protocol simple real-time audio streaming
2. protocol implementation in java (server side)

you cannot arbitrarily cut media , expect player able play it. works bare mpeg streams, other containers , codecs can have trouble. because of don't send partial files unless client has rest of it.

you have problem of when song ends , you're on next.

there 2 ways implement this. 1 of have static media available clients , seek correct time in audio client-side.

the way choose create internet radio stream hears same thing @ same time because have common buffer chunks copied , sent clients same time. now, if either need use codecs/containers support arbitrary splicing (mp3 or aac) or re-wrap streams container sent client. complicated problem, it's best if use off-the-shelf this, icecast. know you're not looking third-party solutions, that's best way. if want yourself, you'll have reimplement of it, or support mpeg streams only.

edit: comment:

could explain more data stream format, [24,576 bytes of stream] [metablock] [24,576 bytes of stream] [metablock] etc.. how separate blocks, , contents of metablocks?

if wish, can mux shoutcast-style metadata stream. not clients support this. if do, send following header in request:

icy-metadata: 1 

if see header , value, can optionally include metadata in stream. metadata injected after every chunk of stream data. include metadata, first need decide how big stream chunks are. far apart, , metadata won't align stream. close , in theory wasting bandwidth (but not much, since unchanging metadata block byte long). stick 8kb. it's not uncommon see 16kb , 32kb. output chunk size, metadata interval, in response headers:

icy-metaint: 8192 

to things started, send 8192 bytes (8kb) of audio stream data client.

now it's time metadata block. start string, this:

streamtitle='this stream title';streamurl=''; 

you can pass in streamurl or other fields, streamtitle used clients these days. (streamurl used have ability popup browser capitalizing letters or something, don't remember certainty trigger was. it's no longer used.) convert string buffer , pad null bytes (0x00) nearest evenly divisible block of 16. is, if string version of metadata block 51 bytes long, need 64 bytes long add 13 bytes of nul padding.

a quick note on character set. many clients support utf-8 in metadata. don't. also, if have use apostrophe ' in metadata, needs escaped. unfortunately there doesn't seem standard way of doing this. backslash works. repeating character works. different players work differently. experiment winamp , see likes, "official" can get. else broken client. (if wanted crafty, determine client user-agent request header , adjust escaping accordingly.)

now have metadata block, need add 1 byte front of indicates how long is, divided 16. if have 64-byte metadata, add byte 0x04 front of indicates our metadata 64 bytes long. gives in total 65-byte metadata block send client. send it.

from here, enter loop again, sending 8kb of stream data before inserting metadata. time around though since don't want change metadata, send 0x00 our metadata block. again, since first byte indicates length of chunk, , we're not updating title, tell client length 0. send strings when changing.


Comments