package com.github.bluesbruce.spring.service; import com.github.bluesbruce.ffch.CommandManager; import com.github.bluesbruce.ffch.CommandManagerImpl; import com.github.bluesbruce.ffch.commandbuidler.CommandBuidlerFactory; import com.github.bluesbruce.ffch.data.CommandTasker; import com.alibaba.fastjson.JSONObject; import com.github.bluesbruce.spring.config.CmdParam; import com.github.bluesbruce.spring.mqttService.HttpURLConnectionUtil; import com.github.bluesbruce.spring.mqttService.send.MqttProviderConfig; import lombok.extern.slf4j.Slf4j; import org.h2.util.StringUtils; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.stereotype.Service; import org.springframework.util.ObjectUtils; import java.util.Collection; import java.util.List; import static com.github.bluesbruce.ffch.util.PropertiesUtil.load; @Service @Slf4j public class RtmpLiveService { /** * 加载配置文件的推拉流地址 */ public static final CmdParam cmdParam = load("/loadCmd.properties", CmdParam.class); @Autowired private MqttProviderConfig mqttProviderConfig; public static final CommandManager manager = new CommandManagerImpl(); /** * h获取通道并推送 */ public void pushServer(String code) throws InterruptedException { //CommandManager manager = new CommandManagerImpl(); String reTopic = cmdParam.getMqttTopic().replace("live", "result"); JSONObject jsonObject = new JSONObject(); Collection infoList = manager.queryAll(); log.info(infoList.toString()); if (infoList.size() > 0) { //manager.stopAll(); //manager.destory(); //Thread.sleep(3000); /*jsonObject.put("code", -1); jsonObject.put("msg", "推流服务已启动,请勿重复启动"); //推流失败 mqttProviderConfig.publish(2,false,reTopic,jsonObject.toJSONString());*/ log.info("任务运行中"); return; } String pushUrl = ""; if (cmdParam.getType() == 2) { log.info("获取流媒体通道"); //TODO 获取通道服务推拉流地址 JSONObject object = getChenl(); if (!ObjectUtils.isEmpty(object)) { code = object.get("code").toString(); object.put("code", 0); object.put("msg", "获取通道成功"); mqttProviderConfig.publish(2, false, reTopic, object.toJSONString()); } else { log.info("获取通道失败"); object.put("code", -1); object.put("msg", "获取通道失败"); mqttProviderConfig.publish(2, false, reTopic, object.toJSONString()); return; } runRtmp(pushUrl, cmdParam.getPlayUrl(), code); //TODO end } else if (cmdParam.getType() == 1) { log.info("使用固定流媒体通道"); pushUrl = cmdParam.getPushUrl(); runRtmp(pushUrl, cmdParam.getPlayUrl(), code); } else if (cmdParam.getType() == 3) { runRtmp2to2(cmdParam.getPlayUrl()); } else if (cmdParam.getType() == 4) { runRtmp1to2(cmdParam.getPlayUrl()); } } private void runRtmp2to2(String playUrl) throws InterruptedException { try { String reTopic = cmdParam.getMqttTopic().replace("live", "result"); String taskId = manager.start("test1", CommandBuidlerFactory.createBuidler() .add("ffmpeg").add("-i", playUrl) .add("-rtsp_transport", "tcp") .add("-vcodec", "copy") .add("-acodec", "copy") .add("-f", "flv") .add("-b:v", "2M") .add("-maxrate", "2M") .add("-bufsize", "1M") .add("-y").add(cmdParam.getPushUrl())); Thread.sleep(3000); String taskId2 = manager.start("test2", CommandBuidlerFactory.createBuidler() .add("ffmpeg").add("-i", playUrl) .add("-rtsp_transport", "tcp") .add("-vcodec", "copy") .add("-acodec", "copy") .add("-f", "flv") .add("-b:v", "2M") .add("-maxrate", "2M") .add("-bufsize", "1M") .add("-y").add(cmdParam.getPushUrl2())); JSONObject jsonObject = new JSONObject(); if (StringUtils.isNullOrEmpty(taskId) && StringUtils.isNullOrEmpty(taskId2)) { jsonObject.put("code", -1); jsonObject.put("msg", "推流服务失败"); //推流失败 mqttProviderConfig.publish(2, false, reTopic, jsonObject.toJSONString()); // 停止全部任务 manager.stopAll(); return; } else { jsonObject.put("code", 0); jsonObject.put("msg", "推流服务启动成功"); mqttProviderConfig.publish(2, false, reTopic, jsonObject.toJSONString()); } Thread.sleep(cmdParam.getTime()); log.info(manager.queryAll().toString()); // 停止全部任务 manager.stopAll(); manager.destory(); } catch (Exception e) { e.printStackTrace(); } } private void runRtmp1to2(String playUrl) { try { //单进程 多路 String reTopic = cmdParam.getMqttTopic().replace("live", "result"); String taskId = manager.start("test4", CommandBuidlerFactory.createBuidler() .add("ffmpeg").add("-i", playUrl) .add("-rtsp_transport", "tcp") .add("-vcodec", "copy") .add("-acodec", "copy") .add("-b:v", "2M") .add("-maxrate", "2M") .add("-bufsize", "1M") //多路推流测试 .add("-map", "0") .add("-f").add(cmdParam.getPushUrlMap())); JSONObject jsonObject = new JSONObject(); if (StringUtils.isNullOrEmpty(taskId)) { jsonObject.put("code", -1); jsonObject.put("msg", "推流服务失败"); //推流失败 mqttProviderConfig.publish(2, false, reTopic, jsonObject.toJSONString()); // 停止全部任务 manager.stopAll(); return; } else { jsonObject.put("code", 0); jsonObject.put("msg", "推流服务启动成功"); mqttProviderConfig.publish(2, false, reTopic, jsonObject.toJSONString()); } Thread.sleep(cmdParam.getTime()); log.info(manager.queryAll().toString()); // 停止全部任务 manager.stopAll(); manager.destory(); } catch (Exception e) { e.printStackTrace(); } } /** * 获取阿里云通道 * * @return */ private JSONObject getChenl() { String result = HttpURLConnectionUtil.doGet("https://streaming.t-aaron.com/livechannel/getLiveChannelList"); if (!StringUtils.isNullOrEmpty(result)) { try { JSONObject object = JSONObject.parseObject(result); List objectList = (List) object.get("data"); if (objectList.size() > 0) { log.info("获取到通道列表{}", objectList); for (int i = 0; i < objectList.size(); i++) { JSONObject chenl = objectList.get(i); //设置通道占用 JSONObject param = new JSONObject(); param.put("code", chenl.get("code").toString()); String resultOn = HttpURLConnectionUtil.doPut("https://streaming.t-aaron.com/livechannel/useLiveChannel", param.toJSONString()); if (!StringUtils.isNullOrEmpty(resultOn)) { JSONObject objectResult = JSONObject.parseObject(resultOn); if (objectResult.get("code").toString().equals("0")) { log.info("占用通道{}", objectList.get(i)); return objectList.get(i); } } } } } catch (Exception e) { log.error("", e); } } else { return null; } return null; } /** * 根据推拉流地址推动 * * @param pushUrl * @param playUrl */ public void runRtmp(String pushUrl, String playUrl, String code) { try { log.info("获取播流地址:{}"); //CommandManager manager = new CommandManagerImpl(); String taskId = manager.start(code, CommandBuidlerFactory.createBuidler() .add("ffmpeg").add("-i", playUrl) .add("-rtsp_transport", "tcp") .add("-vcodec", "copy") .add("-acodec", "copy") .add("-f", "flv") .add("-b:v", "2M") .add("-maxrate", "2M") .add("-bufsize", "1M") .add("-v", "trace ") .add("-y").add(pushUrl)); cmdParam.getMqttTopic(); String reTopic = cmdParam.getMqttTopic().replace("live", "result"); log.info(manager.queryAll().toString()); JSONObject jsonObject = new JSONObject(); if (StringUtils.isNullOrEmpty(taskId)) { jsonObject.put("code", -1); jsonObject.put("msg", "推流服务失败"); //推流失败 mqttProviderConfig.publish(2, false, reTopic, jsonObject.toJSONString()); // 停止全部任务 manager.stopAll(); return; } else { jsonObject.put("code", 0); jsonObject.put("msg", "推流服务启动成功"); mqttProviderConfig.publish(2, false, reTopic, jsonObject.toJSONString()); } Thread.sleep(cmdParam.getTime()); log.info(manager.queryAll().toString()); // 停止全部任务 manager.stopAll(); manager.destory(); } catch (Exception e) { log.error("", e); } //ds.close(); } public void stopRtmp() { try { log.info("停止推流"); //CommandManager manager = new CommandManagerImpl(); // 停止全部任务 int index = manager.stopAll(); manager.destory(); JSONObject jsonObject = new JSONObject(); String reTopic = cmdParam.getMqttTopic().replace("live", "result"); if (index == 0) { jsonObject.put("code", -1); jsonObject.put("msg", "推流服务关闭失败"); //推流失败 mqttProviderConfig.publish(2, false, reTopic, jsonObject.toJSONString()); // 停止全部任务 manager.stopAll(); return; } else if (index > 0) { jsonObject.put("code", 0); jsonObject.put("msg", "推流服务关闭成功"); returnChenl(); mqttProviderConfig.publish(2, false, reTopic, jsonObject.toJSONString()); } } catch (Exception e) { log.error("", e); } //ds.close(); } /** * 释放阿里云通道 * * @return */ private JSONObject returnChenl() { try { String result = HttpURLConnectionUtil.doGet("https://streaming.t-aaron.com/livechannel/getLiveChannelList"); if (!StringUtils.isNullOrEmpty(result)) { JSONObject object = JSONObject.parseObject(result); List objectList = (List) object.get("data"); if (objectList.size() > 0) { log.info("获取到通道列表{}", objectList); for (int i = 0; i < objectList.size(); i++) { JSONObject chenl = objectList.get(i); //设置通道占用 JSONObject param = new JSONObject(); param.put("code", chenl.get("code").toString()); String resultOn = HttpURLConnectionUtil.doPut("https://streaming.t-aaron.com/livechannel/useLiveChannel", param.toJSONString()); if (!StringUtils.isNullOrEmpty(resultOn)) { JSONObject objectResult = JSONObject.parseObject(resultOn); if (objectResult.get("code").toString().equals("0")) { log.info("占用通道{}", objectList.get(i)); return objectList.get(i); } } } } } else { return null; } return null; } catch (Exception e) { log.error("", e); } return null; } }