目录
之前的项目是java的,我需要的是纯前端的js客户端,通过js客户端播放视频,然后用unity打包的webgl和js客户端交互,实现在unity的webgl中播放视频的效果。
之前的demo是:https://github.com/Kurento/kurento-tutorial-java里面的kurento-player,能够实现在网页里面播放rtsp视频,通过webrtc的方式播放的。
另外还有一套js的demo:https://github.com/Kurento/kurento-tutorial-js
一、获取js文件
但是我现在的问题是无论是java的还是js的,相关的js引用文件弄不到。
java的:
<link rel="stylesheet"
href="webjars/bootstrap/dist/css/bootstrap.min.css">
<link rel="stylesheet"
href="webjars/ekko-lightbox/dist/ekko-lightbox.min.css">
<link rel="stylesheet" href="webjars/demo-console/index.css">
<link rel="stylesheet" href="css/kurento.css">
<script src="webjars/jquery/dist/jquery.min.js"></script>
<script src="webjars/bootstrap/dist/js/bootstrap.min.js"></script>
<script src="webjars/ekko-lightbox/dist/ekko-lightbox.min.js"></script>
<script src="/webjars/webrtc-adapter/release/adapter.js"></script>
<script src="webjars/demo-console/index.js"></script>
<script src="js/kurento-utils.js"></script>
<script src="js/index.js"></script>
js的:
<link rel="stylesheet" href="bower_components/bootstrap/dist/css/bootstrap.min.css">
<link rel="stylesheet" href="bower_components/demo-console/index.css">
<link rel="stylesheet" href="bower_components/ekko-lightbox/dist/ekko-lightbox.min.css">
<link rel="stylesheet" href="css/kurento.css">
<script src="bower_components/jquery/dist/jquery.min.js"></script>
<script src="bower_components/bootstrap/dist/js/bootstrap.min.js"></script>
<script src="bower_components/demo-console/index.js"></script>
<script src="bower_components/ekko-lightbox/dist/ekko-lightbox.min.js"></script>
<script src="bower_components/ekko-lightbox/dist/ekko-lightbox.min.js"></script>
<script src="bower_components/webrtc-adapter/release/adapter.js"></script>
<script src="bower_components/kurento-client/js/kurento-client.js"></script>
<script src="bower_components/kurento-utils/js/kurento-utils.js"></script>
<script src="js/index.js"></script>
没有这方面的知识啊。
虽然前面的kurento-player在idea中启动后,能打开网页。
在Sources里面能够看到这些文件,但是不知道怎么拷贝出来。
用笨办法,手动把这些文件一个个创建,拷贝内容出来。其他都好办,就几个文件,boostrap的css里面好多文件
查了一些webjars的资料,大概知道这个是什么东西,但是还是拷贝不出来。
搜索到了个https://jar-download.com/artifacts/org.webjars/bootstrap,能够下载bootstrap-3.3.6.jar文件(因为前面的Sources里面的bootstrap是3.3.6)
直接解压jar文件,能够得到具体的内容:
拷贝到手动创建的webjars里面的bootstrap/dist文件夹里面
在chrome里面打卡index.html
有两个adapter.js文件找不到,分别在index.html和kurento-utils.js里面,发现都是
/webjars/webrtc-adapter/release/adapter.js
改成
webjars/webrtc-adapter/release/adapter.js
再打开,就没有找不到文件的情况了。
tutorial-js里面的kurento-client-js是从https://github.com/Kurento/kurento-client-bower/tree/master/js拿到的。虽然最后没用了。
—————————————————————————————————————————————————-
二、通信
启动后,发现通信地址有问题
修改index.js
var host=location.host;
if(host===""){
host="127.0.0.1:8444";
}
console.log("host",host);
var ws = new WebSocket('wss://' + host + '/player');
ws.onerror=function(error){
console.error("onerror",error);
}
ws.onopen=function(msg){
console.log("onopen",msg);
}
结果
后端打印信息:
也就是说,不能从文件连接
把文件放到iis里面,修改代码
var host=location.host;
//if(host==="")
{
host="127.0.0.1:8444";
}
console.log("host",host);
var ws = new WebSocket('wss://' + host + '/player');
也是一样的
没有专业知识,这个时候我只能先自己猜测尝试了。
——————————————
wss改成ws
application.properties改成,去掉ssl部分。
server.port=8444
#server.ssl.key-store=classpath:keystore.jks
#server.ssl.key-store-password=kurento
#server.ssl.key-store-type=JKS
#server.ssl.key-alias=kurento-selfsigned
前端的wss改成ws。
进入页面不用https。
可以正常播放。
在另一台电脑上的ubuntu中,运行kurento,在其他电脑上登陆播放。
1.wss,https://192.168.1.150:8443/#,其他电脑,可以播放
2.ws,http://192.168.1.150:8444/#,其他电脑不能播放,自己电脑可以播放。
——————————————
不过,从kurento-player-js里面启动也还是一样的。
好吧。看看https://github.com/Kurento/kurento-tutorial-js怎么弄的。
—————————————————————————————————————–
1.跨域问题
wss情况下,修改Player.java
@Override
public void registerWebSocketHandlers(WebSocketHandlerRegistry registry) {
registry.addHandler(handler(), "/player")
.setAllowedOrigins("*")//支持跨域
//.withSockJS()//这个加上的话原来的页面,视频出不来,SockJS是一个前端js库
;
}
参考:Spring Boot WebSocket从入门到放弃
———————————————————————
2.java.io.EOFException:null
想到原来的kurento-rtsp2webrtc结合现状的java服务端是否可以,试了一下,结果出现个java.io.EOFException:null问题。
发现是前端WebSocket初始化时用了’binary’参数的话会导致该问题。
kWebsocket = new WebSocket(kaddress.value, 'binary');
改成
kWebsocket = new WebSocket(kaddress.value);
继续改回用现在的kurento-player-js测试。
3.websocket发送文本长度问题
将kurento-player-js放到iis里面,连接另一台ubunto电脑的kurento的java服务端,能连接上,短文本发送测试可以(”{id:1}”),但是长文本就会出错,并导致websocket关闭,无法发送后续文本。
The decoded text message was too big for the output buffer and the endpoint does not support partial messages
和原来的网页对比一下,原来只发送了5942个,纯17359个。先处理文本长度限制问题,不行再看看差异。
查资料,首先会查到,设置org.apache.tomcat.websocket.textBufferSize。
参考:springboot框架中使用websocket传输内容过长的问题解决
试了,不行。还试着在application.properties里面设置org.apache.tomcat.websocket.textBufferSize=1024000。
然后会查到,设置configureWebSocketTransport,参考:Spring Stomp over Websocket: Message/Buffer/Cache/Stream limits
但是代码里面的基类不是AbstractWebSocketMessageBrokerConfigurer ,而是TextWebSocketHandler。
TextWebSocketHandler里面只有一个handleBinaryMessage
public class TextWebSocketHandler extends AbstractWebSocketHandler {
public TextWebSocketHandler() {
}
protected void handleBinaryMessage(WebSocketSession session, BinaryMessage message) {
try {
session.close(CloseStatus.NOT_ACCEPTABLE.withReason("Binary messages not supported"));
} catch (IOException var4) {
}
}
}
再往上是AbstractWebSocketHandler
public abstract class AbstractWebSocketHandler implements WebSocketHandler {
public AbstractWebSocketHandler() {
}
public void afterConnectionEstablished(WebSocketSession session) throws Exception {
}
public void handleMessage(WebSocketSession session, WebSocketMessage<?> message) throws Exception {
if (message instanceof TextMessage) {
this.handleTextMessage(session, (TextMessage)message);
} else if (message instanceof BinaryMessage) {
this.handleBinaryMessage(session, (BinaryMessage)message);
} else {
if (!(message instanceof PongMessage)) {
throw new IllegalStateException("Unexpected WebSocket message type: " + message);
}
this.handlePongMessage(session, (PongMessage)message);
}
}
protected void handleTextMessage(WebSocketSession session, TextMessage message) throws Exception {
}
protected void handleBinaryMessage(WebSocketSession session, BinaryMessage message) throws Exception {
}
protected void handlePongMessage(WebSocketSession session, PongMessage message) throws Exception {
}
public void handleTransportError(WebSocketSession session, Throwable exception) throws Exception {
}
public void afterConnectionClosed(WebSocketSession session, CloseStatus status) throws Exception {
}
public boolean supportsPartialMessages() {
return false;
}
}
发现个supportsPartialMessages,这个正好和提示的后半部分一致“the endpoint does not support partial messages”。
这里是false,改成true。
在PlayerHandler里面加上supportsPartialMessages
@Override
public boolean supportsPartialMessages(){
log.info("supportsPartialMessages true !!!!!!!!!!!!!!!!!!!!!!");
return true;
}
再测试,服务端能够收到信息了,但是因为被分成几次发送了,需要处理一下。
在PlayerHandler里面加上GetJsonMessage
private String lastText="";
private JsonObject GetJsonMessage( TextMessage message){
try {
JsonObject jsonMessage=null;
log.info("[TextMessage]: "+message.toString());
String text=message.getPayload();
log.info(String.format("[Payload]: %b,%b,%d,%s",
text.startsWith("{"),text.endsWith("}"),text.length(),text));
if(text.startsWith("{")&&text.endsWith("}")){
jsonMessage = gson.fromJson(text, JsonObject.class);
log.info("[JsonObject1]: "+jsonMessage.toString());
}
else{
lastText+=text;
if(lastText.endsWith("}")){
jsonMessage = gson.fromJson(lastText, JsonObject.class);
log.info("[JsonObject2]: "+jsonMessage.toString());
lastText="";
}
else{
log.info("[wait form json end]");
}
}
return jsonMessage;
}
catch (Exception ex){
log.error(ex.toString());
return null;
}
}
@Override
public void handleTextMessage(WebSocketSession session, TextMessage message) throws Exception {
log.info(">> PlayerHandler.handleTextMessage");
JsonObject jsonMessage=GetJsonMessage(message);
if(jsonMessage==null)return;
String sessionId = session.getId();
log.debug("Incoming message {} from sessionId", jsonMessage, sessionId);
//..................
}
(就这部分是纯原创的,可能写的差了点,能达到效果)
调试结果,正常能够收到消息后,网页里面视频就能出来了!哈哈哈!!!!
代码整理一下,上传git,包括服务端和客户端(前端)部分
https://github.com/llhswwha/kurento-player-rtsp2webrtc-jsclient
我这有点杂了,前端虽然是js的,但是需要连接java服务端。而kurento-tutorial-js是直接用js连接kms服务,kurento-tutorial-java是java连接kms服务,同时是前端服务端是一个springboot项目。
经测试,前端代码,用浏览器打开index.html页面也能播放视频成功。不需要放到iis里面。
4.wss问题
试着在第3台电脑访问http://192.168.1.16/kurento-player-js/#,结果:
(第1台电脑是ubuntu,ip是192.168.1.150,运行kurento和java服务端;第2台电脑是windows,ip是192.168.1.16,运行iis)
WebSocket connection to 'wss://192.168.1.150:8443/player' failed: Error in connection establishment: net::ERR_CERT_AUTHORITY_INVALID
查了一下ERR_CERT_AUTHORITY_INVALID,是证书问题,也就是ssl的问题。
因为之前测试都是在16电脑上连接150的,而最开始连接150的页面时,有从网页上选择“继续访问不安全网页”,所以后续的访问都没有限制。
把java服务端改一下,不用ssl。
结果,可以!!
单独的html文件拷贝过去,也能打开播放视频。
5.websocket连接还没建立就点击Start按钮
现在先根据
Uncaught DOMException: Failed to execute 'send' on 'WebSocket': Still in CONNECTING state.
修改一下index.js,判断ws是否连接,没有连接上的话,等连接上后在播放。
var isStartPlayAfterOpen=false;
function start() {
// Disable start button
setState(I_AM_STARTING);
showSpinner(video);
isClickStart=true;
console.log("start",ws.readyState);
if(ws.readyState==0){
//alert("网络正在连接中,请稍后。")
console.log("网络正在连接中,请稍后。",ws.readyState);
isStartPlayAfterOpen=true;
return;
}
var mode = $('input[name="mode"]:checked').val();
//.............
}
var ws = new WebSocket('ws://' + host + '/player');
ws.onerror=function(error){
console.error("onerror",error);
}
ws.onopen=function(msg){
console.log("onopen",msg,this);
this.send("{id:1}");//测试服务端代码
if(isStartPlayAfterOpen){//websocket连接上后就播放
start();
}
}
三、页面修改
把index.js里面的websocket地址播放,放到网页里面,可以在页面上修改。不然wss和ws切换啊,都要改代码。
index.html修改
<div class="row">
<div class="col-md-12">
<input type="text" id="serverurl"
value="ws://192.168.1.150:8444/player"
style="width: 100%">
</div>
</div>
<div class="row">
<div class="col-md-12">
<input type="text" id="videourl"
value="rtsp://iom:123456@192.168.1.134:554/cam/realmonitor?channel=1&subtype=0"
style="width: 100%">
</div>
</div>
index.js修改
var ws=null;
function intWebSocket(url){
if(ws!=null&&ws.url===url){
console.log("intWebSocket same url",url);
return;
}
console.log("intWebSocket",url);
ws = new WebSocket(url);
ws.onerror=function(error){
console.error("onerror",error);
}
ws.onopen=function(msg){
console.log("onopen",msg,this);
this.send("{id:1}");//测试服务端代码
if(isStartPlayAfterOpen){//websocket连接上后就播放
start();
}
}
ws.onclose=function(msg){
console.error("onclose",msg);
}
ws.onmessage = function(message) {
//......
}
}
function start() {
var serverurl = document.getElementById('serverurl').value;
intWebSocket(serverurl);
// Disable start button
setState(I_AM_STARTING);
showSpinner(video);
//....
}
好了,代码更新上去,接下来要用结合unity了。
版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 举报,一经查实,本站将立刻删除。
如需转载请保留出处:https://bianchenghao.cn/36031.html