1
0
Fork 0
mirror of https://github.com/ossrs/srs.git synced 2025-03-09 15:49:59 +00:00

for #369, support RTMP 302 api at protocol level.

This commit is contained in:
winlin 2016-01-08 18:17:37 +08:00
parent f1e7e9d933
commit d24aef50ba
7 changed files with 86 additions and 3 deletions

View file

@ -137,7 +137,7 @@ package
var ms:NetStream = this.media_stream;
if (!ms) {
log("stream is null, ignore timer event.");
//log("stream is null, ignore timer event.");
return;
}
@ -396,6 +396,26 @@ package
update_context_items();
}
// reject by server, maybe redirect.
if (evt.info.code == "NetConnection.Connect.Rejected") {
// RTMP 302 redirect.
if (evt.info.hasOwnProperty("ex") && evt.info.ex.code == 302) {
var streamName:String = url.substr(url.lastIndexOf("/") + 1);
url = evt.info.ex.redirect + "/" + streamName;
log("Async RTMP 302 Redirect to: " + url);
// notify server.
media_conn.call("Redirected", null, evt.info.ex.redirect);
// do 302.
setTimeout(function(){
log("Async RTMP 302 Redirected.");
js_call_play(url, _width, _height, buffer_time, max_buffer_time, volume);
}, 1000);
return;
}
}
// TODO: FIXME: failed event.
if (evt.info.code != "NetConnection.Connect.Success") {
return;

View file

@ -26,7 +26,8 @@ CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
bool srs_is_system_control_error(int error_code)
{
return error_code == ERROR_CONTROL_RTMP_CLOSE
|| error_code == ERROR_CONTROL_REPUBLISH;
|| error_code == ERROR_CONTROL_REPUBLISH
|| error_code == ERROR_CONTROL_REDIRECT;
}
bool srs_is_client_gracefully_close(int error_code)

View file

@ -161,6 +161,9 @@ CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
//
// system control message,
// not an error, but special control logic.
//
// connection is redirect to another server.
#define ERROR_CONTROL_REDIRECT 2997
// sys ctl: rtmp close stream, support replay.
#define ERROR_CONTROL_RTMP_CLOSE 2998
// FMLE stop publish and republish.

View file

@ -306,7 +306,9 @@ string srs_generate_rtmp_url(string server, int port, string vhost, string app,
ss << "...vhost..." << vhost;
}
ss << "/" << stream;
if (!stream.empty()) {
ss << "/" << stream;
}
return ss.str();
}

View file

@ -2575,6 +2575,57 @@ int SrsRtmpServer::response_connect_app(SrsRequest *req, const char* server_ip)
return ret;
}
#define SRS_RTMP_REDIRECT_TIMEOUT 3000
int SrsRtmpServer::redirect(SrsRequest* r, string host, int port, bool& accepted)
{
int ret = ERROR_SUCCESS;
if (true) {
string url = srs_generate_rtmp_url(host, port, r->vhost, r->app, "");
SrsAmf0Object* ex = SrsAmf0Any::object();
ex->set("code", SrsAmf0Any::number(302));
ex->set("redirect", SrsAmf0Any::str(url.c_str()));
SrsOnStatusCallPacket* pkt = new SrsOnStatusCallPacket();
pkt->data->set(StatusLevel, SrsAmf0Any::str(StatusLevelError));
pkt->data->set(StatusCode, SrsAmf0Any::str(StatusCodeConnectRejected));
pkt->data->set(StatusDescription, SrsAmf0Any::str("RTMP 302 Redirect"));
pkt->data->set("ex", ex);
if ((ret = protocol->send_and_free_packet(pkt, 0)) != ERROR_SUCCESS) {
srs_error("send redirect/rejected message failed. ret=%d", ret);
return ret;
}
srs_info("send redirect/rejected message success.");
}
// client must response a call message.
// or we never know whether the client is ok to redirect.
protocol->set_recv_timeout(SRS_RTMP_REDIRECT_TIMEOUT * 1000);
if (true) {
SrsCommonMessage* msg = NULL;
SrsCallPacket* pkt = NULL;
if ((ret = expect_message<SrsCallPacket>(&msg, &pkt)) != ERROR_SUCCESS) {
// ignore any error of redirect response.
return ERROR_SUCCESS;
}
SrsAutoFree(SrsCommonMessage, msg);
SrsAutoFree(SrsCallPacket, pkt);
string message;
if (pkt->arguments && pkt->arguments->is_string()) {
message = pkt->arguments->to_str();
srs_info("confirm redirected to %s", message.c_str());
accepted = true;
}
srs_info("get redirect response message");
}
return ret;
}
void SrsRtmpServer::response_connect_reject(SrsRequest* /*req*/, const char* desc)
{
int ret = ERROR_SUCCESS;

View file

@ -929,6 +929,12 @@ public:
* @param server_ip the ip of server.
*/
virtual int response_connect_app(SrsRequest* req, const char* server_ip = NULL);
/**
* redirect the connection to another rtmp server.
* @param the hostname or ip of target.
* @param whether the client accept the redirect.
*/
virtual int redirect(SrsRequest* r, std::string host, int port, bool& accepted);
/**
* reject the connect app request.
*/