mirror of https://bitbucket.org/ausocean/av.git
rtmp: fix parseURL panic and improve playpath handling
This commit is contained in:
parent
8023b0d9d7
commit
30711a54fa
|
@ -78,26 +78,34 @@ func parseURL(addr string) (protocol int32, host string, port uint16, app, playp
|
||||||
if !path.IsAbs(u.Path) {
|
if !path.IsAbs(u.Path) {
|
||||||
return protocol, host, port, app, playpath, nil
|
return protocol, host, port, app, playpath, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
elems := strings.SplitN(u.Path[1:], "/", 3)
|
elems := strings.SplitN(u.Path[1:], "/", 3)
|
||||||
app = elems[0]
|
app = elems[0]
|
||||||
if app == "" {
|
if len(elems[len(elems)-1]) == 0 {
|
||||||
|
elems = elems[:len(elems)-1]
|
||||||
|
}
|
||||||
|
if app == "" || len(elems) < 2 {
|
||||||
return protocol, host, port, app, playpath, errInvalidURL
|
return protocol, host, port, app, playpath, errInvalidURL
|
||||||
}
|
}
|
||||||
playpath = elems[1]
|
|
||||||
if len(elems) == 3 && len(elems[2]) != 0 {
|
|
||||||
playpath = path.Join(elems[1:]...)
|
playpath = path.Join(elems[1:]...)
|
||||||
switch ext := path.Ext(playpath); ext {
|
switch ext := path.Ext(playpath); ext {
|
||||||
case ".f4v", ".mp4":
|
case ".f4v", ".mp4":
|
||||||
playpath = "mp4:" + playpath[:len(playpath)-len(ext)]
|
playpath = playpath[:len(playpath)-len(ext)]
|
||||||
|
if !strings.HasPrefix(playpath, "mp4:") {
|
||||||
|
playpath = "mp4:" + playpath
|
||||||
|
}
|
||||||
case ".mp3":
|
case ".mp3":
|
||||||
playpath = "mp3:" + playpath[:len(playpath)-len(ext)]
|
playpath = playpath[:len(playpath)-len(ext)]
|
||||||
|
if !strings.HasPrefix(playpath, "mp3:") {
|
||||||
|
playpath = "mp3:" + playpath
|
||||||
|
}
|
||||||
case ".flv":
|
case ".flv":
|
||||||
playpath = playpath[:len(playpath)-len(ext)]
|
playpath = playpath[:len(playpath)-len(ext)]
|
||||||
}
|
}
|
||||||
if u.RawQuery != "" {
|
if u.RawQuery != "" {
|
||||||
playpath += "?" + u.RawQuery
|
playpath += "?" + u.RawQuery
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
switch {
|
switch {
|
||||||
case port != 0:
|
case port != 0:
|
||||||
|
|
|
@ -0,0 +1,200 @@
|
||||||
|
/*
|
||||||
|
NAME
|
||||||
|
parseurl_test.go
|
||||||
|
|
||||||
|
DESCRIPTION
|
||||||
|
See Readme.md
|
||||||
|
|
||||||
|
AUTHOR
|
||||||
|
Dan Kortschak <dan@ausocean.org>
|
||||||
|
|
||||||
|
LICENSE
|
||||||
|
parseurl.go is Copyright (C) 2019 the Australian Ocean Lab (AusOcean)
|
||||||
|
|
||||||
|
It is free software: you can redistribute it and/or modify them
|
||||||
|
under the terms of the GNU General Public License as published by the
|
||||||
|
Free Software Foundation, either version 3 of the License, or (at your
|
||||||
|
option) any later version.
|
||||||
|
|
||||||
|
It is distributed in the hope that it will be useful, but WITHOUT
|
||||||
|
ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||||
|
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||||
|
for more details.
|
||||||
|
|
||||||
|
You should have received a copy of the GNU General Public License
|
||||||
|
along with revid in gpl.txt. If not, see http://www.gnu.org/licenses.
|
||||||
|
*/
|
||||||
|
package rtmp
|
||||||
|
|
||||||
|
import (
|
||||||
|
"testing"
|
||||||
|
)
|
||||||
|
|
||||||
|
var parseURLTests = []struct {
|
||||||
|
url string
|
||||||
|
wantProtocol int32
|
||||||
|
wantHost string
|
||||||
|
wantPort uint16
|
||||||
|
wantApp string
|
||||||
|
wantPlaypath string
|
||||||
|
wantErr error
|
||||||
|
}{
|
||||||
|
{
|
||||||
|
url: "rtmp://addr",
|
||||||
|
wantHost: "addr",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
url: "rtmp://addr/",
|
||||||
|
wantErr: errInvalidURL,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
url: "rtmp://addr/live2",
|
||||||
|
wantErr: errInvalidURL,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
url: "rtmp://addr/live2/",
|
||||||
|
wantErr: errInvalidURL,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
url: "rtmp://addr/appname/key",
|
||||||
|
wantHost: "addr",
|
||||||
|
wantPort: 1935,
|
||||||
|
wantApp: "appname",
|
||||||
|
wantPlaypath: "key",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
url: "rtmp://addr/appname/instancename",
|
||||||
|
wantHost: "addr",
|
||||||
|
wantPort: 1935,
|
||||||
|
wantApp: "appname",
|
||||||
|
wantPlaypath: "instancename",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
url: "rtmp://addr/appname/instancename/",
|
||||||
|
wantHost: "addr",
|
||||||
|
wantPort: 1935,
|
||||||
|
wantApp: "appname",
|
||||||
|
wantPlaypath: "instancename",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
url: "rtmp://addr/appname/mp4:path.f4v",
|
||||||
|
wantHost: "addr",
|
||||||
|
wantPort: 1935,
|
||||||
|
wantApp: "appname",
|
||||||
|
wantPlaypath: "mp4:path",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
url: "rtmp://addr/appname/mp4:path.f4v?param1=value1¶m2=value2",
|
||||||
|
wantHost: "addr",
|
||||||
|
wantPort: 1935,
|
||||||
|
wantApp: "appname",
|
||||||
|
wantPlaypath: "mp4:path?param1=value1¶m2=value2",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
url: "rtmp://addr/appname/mp4:path/to/file.f4v",
|
||||||
|
wantHost: "addr",
|
||||||
|
wantPort: 1935,
|
||||||
|
wantApp: "appname",
|
||||||
|
wantPlaypath: "mp4:path/to/file",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
url: "rtmp://addr/appname/mp4:path/to/file.f4v?param1=value1¶m2=value2",
|
||||||
|
wantHost: "addr",
|
||||||
|
wantPort: 1935,
|
||||||
|
wantApp: "appname",
|
||||||
|
wantPlaypath: "mp4:path/to/file?param1=value1¶m2=value2",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
url: "rtmp://addr/appname/path.mp4",
|
||||||
|
wantHost: "addr",
|
||||||
|
wantPort: 1935,
|
||||||
|
wantApp: "appname",
|
||||||
|
wantPlaypath: "mp4:path",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
url: "rtmp://addr/appname/path.mp4?param1=value1¶m2=value2",
|
||||||
|
wantHost: "addr",
|
||||||
|
wantPort: 1935,
|
||||||
|
wantApp: "appname",
|
||||||
|
wantPlaypath: "mp4:path?param1=value1¶m2=value2",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
url: "rtmp://addr/appname/path/to/file.mp4",
|
||||||
|
wantHost: "addr",
|
||||||
|
wantPort: 1935,
|
||||||
|
wantApp: "appname",
|
||||||
|
wantPlaypath: "mp4:path/to/file",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
url: "rtmp://addr/appname/path/to/file.mp4?param1=value1¶m2=value2",
|
||||||
|
wantHost: "addr",
|
||||||
|
wantPort: 1935,
|
||||||
|
wantApp: "appname",
|
||||||
|
wantPlaypath: "mp4:path/to/file?param1=value1¶m2=value2",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
url: "rtmp://addr/appname/path.flv",
|
||||||
|
wantHost: "addr",
|
||||||
|
wantPort: 1935,
|
||||||
|
wantApp: "appname",
|
||||||
|
wantPlaypath: "path",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
url: "rtmp://addr/appname/path.flv?param1=value1¶m2=value2",
|
||||||
|
wantHost: "addr",
|
||||||
|
wantPort: 1935,
|
||||||
|
wantApp: "appname",
|
||||||
|
wantPlaypath: "path?param1=value1¶m2=value2",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
url: "rtmp://addr/appname/path/to/file.flv",
|
||||||
|
wantHost: "addr",
|
||||||
|
wantPort: 1935,
|
||||||
|
wantApp: "appname",
|
||||||
|
wantPlaypath: "path/to/file",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
url: "rtmp://addr/appname/path/to/file.flv?param1=value1¶m2=value2",
|
||||||
|
wantHost: "addr",
|
||||||
|
wantPort: 1935,
|
||||||
|
wantApp: "appname",
|
||||||
|
wantPlaypath: "path/to/file?param1=value1¶m2=value2",
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestParseURL(t *testing.T) {
|
||||||
|
for _, test := range parseURLTests {
|
||||||
|
func() {
|
||||||
|
defer func() {
|
||||||
|
p := recover()
|
||||||
|
if p != nil {
|
||||||
|
t.Errorf("unexpected panic for %q: %v", test.url, p)
|
||||||
|
}
|
||||||
|
}()
|
||||||
|
|
||||||
|
protocol, host, port, app, playpath, err := parseURL(test.url)
|
||||||
|
if err != test.wantErr {
|
||||||
|
t.Errorf("unexpected error for %q: got:%v want:%v", test.url, err, test.wantErr)
|
||||||
|
return
|
||||||
|
}
|
||||||
|
if err != nil {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
if protocol != test.wantProtocol {
|
||||||
|
t.Errorf("unexpected protocol for %q: got:%v want:%v", test.url, protocol, test.wantProtocol)
|
||||||
|
}
|
||||||
|
if host != test.wantHost {
|
||||||
|
t.Errorf("unexpected host for %q: got:%v want:%v", test.url, host, test.wantHost)
|
||||||
|
}
|
||||||
|
if port != test.wantPort {
|
||||||
|
t.Errorf("unexpected port for %q: got:%v want:%v", test.url, port, test.wantPort)
|
||||||
|
}
|
||||||
|
if app != test.wantApp {
|
||||||
|
t.Errorf("unexpected app for %q: got:%v want:%v", test.url, app, test.wantApp)
|
||||||
|
}
|
||||||
|
if playpath != test.wantPlaypath {
|
||||||
|
t.Errorf("unexpected playpath for %q: got:%v want:%v", test.url, playpath, test.wantPlaypath)
|
||||||
|
}
|
||||||
|
}()
|
||||||
|
}
|
||||||
|
}
|
Loading…
Reference in New Issue