Browse Source

youhua

master
4670101279 2 years ago
parent
commit
fed7dea24a
  1. 19
      ruoyi-api/src/main/java/com/ruoyi/api/app/TestApiController.java
  2. 27
      ruoyi-code/src/main/java/com/ruoyi/code/camera/controller/CameraController.java
  3. 1
      ruoyi-code/src/main/java/com/ruoyi/code/camera/scheduled/RegisterServer.java
  4. 19
      ruoyi-code/src/main/java/utils/RegisterUtil.java
  5. 300
      ruoyi-code/src/main/java/utils/RtspConvert.java
  6. 6
      ruoyi-common/pom.xml
  7. 10
      ruoyi-quartz/src/main/java/com/ruoyi/quartz/task/RyTask.java

19
ruoyi-api/src/main/java/com/ruoyi/api/app/TestApiController.java

@ -5,6 +5,7 @@ import lombok.extern.slf4j.Slf4j;
import org.springframework.web.bind.annotation.PostMapping; import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestMapping; import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController; import org.springframework.web.bind.annotation.RestController;
import utils.RtspConvert;
@RestController @RestController
@ -16,4 +17,22 @@ public class TestApiController {
return R.ok(); return R.ok();
} }
@RequestMapping("/openPullM3u8")
public R openPullM3u8(){
RtspConvert convert = new RtspConvert();
String ip = "192.168.1.40";
String userName = "admin";
String pwd = "admin123";
String m3u8 = convert.rtsp2Hls(ip, userName, pwd);
System.out.println("***********************************" + m3u8);
return R.ok();
}
@RequestMapping("/closePullM3u8")
public R closePullM3u8(){
RtspConvert convert = new RtspConvert();
convert.closeAllProcess();
return R.ok();
}
} }

27
ruoyi-code/src/main/java/com/ruoyi/code/camera/controller/CameraController.java

@ -1,5 +1,6 @@
package com.ruoyi.code.camera.controller; package com.ruoyi.code.camera.controller;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.ruoyi.code.camera.domain.Camera; import com.ruoyi.code.camera.domain.Camera;
import com.ruoyi.code.camera.domain.LogInfo; import com.ruoyi.code.camera.domain.LogInfo;
import com.ruoyi.code.camera.service.ICameraService; import com.ruoyi.code.camera.service.ICameraService;
@ -16,10 +17,7 @@ import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.web.bind.annotation.*; import org.springframework.web.bind.annotation.*;
import sdk.java.lib.netmanager.NetEnums; import sdk.java.lib.netmanager.NetEnums;
import sdk.java.lib.netmanager.NetStructs; import sdk.java.lib.netmanager.NetStructs;
import utils.CameraUtil; import utils.*;
import utils.RegisterUtil;
import utils.run_device_cfg;
import utils.run_device_log_search;
import javax.annotation.Resource; import javax.annotation.Resource;
import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletRequest;
@ -267,4 +265,25 @@ public class CameraController extends BaseController
CameraUtil.setNowTime(new NativeLong(Long.parseLong(camera.getLoginId()))); CameraUtil.setNowTime(new NativeLong(Long.parseLong(camera.getLoginId())));
return R.ok(); return R.ok();
} }
@RequestMapping("/resetPullRtsp")
public R resetPullRtsp(){
List<Camera> list = cameraService.list(new QueryWrapper<Camera>().eq("status","0").isNotNull("login_id").ne("login",""));
if(list.isEmpty()){
return R.error("设备未在线");
}
RtspConvert convert = new RtspConvert();
convert.closeAllProcess();
for (Camera camera : list) {
try {
String m3u8 = convert.rtsp2Hls(camera.getIp(), camera.getUsername(), camera.getPassword());
System.out.println("拉流成功,地址:" + m3u8);
Thread.sleep(2000);
} catch (Exception e) {
logger.error(e.getMessage());
return R.error("重启失败");
}
}
return R.ok();
}
} }

1
ruoyi-code/src/main/java/com/ruoyi/code/camera/scheduled/RegisterServer.java

@ -47,6 +47,7 @@ public class RegisterServer {
private void start(){ private void start(){
String ip = IPUtils.getLocalIpAddress(); String ip = IPUtils.getLocalIpAddress();
System.out.println(ip);
if(sercer_ip.equals(ip)){ if(sercer_ip.equals(ip)){
R result = cameraService.register(); R result = cameraService.register();
if("0".equals(result.get("code").toString())){ if("0".equals(result.get("code").toString())){

19
ruoyi-code/src/main/java/utils/RegisterUtil.java

@ -57,9 +57,10 @@ import java.util.*;
///////////////////////////////////////////////////////////////////////////////////////////////////// /////////////////////////////////////////////////////////////////////////////////////////////////////
@Component @Component
public class RegisterUtil implements ActionListener { public class RegisterUtil implements ActionListener {
//linux服务器
// private String m_jtfServerIP = "192.168.1.219";
//公司windows服务器
private String m_jtfServerIP = "172.16.46.58"; private String m_jtfServerIP = "172.16.46.58";
// private String m_jtfServerIP = "192.168.1.11";
private String m_jtfServerPort = "8020"; private String m_jtfServerPort = "8020";
private String m_jtfDevUsername = "admin"; private String m_jtfDevUsername = "admin";
private String m_jtfDevPassword = "admin123"; private String m_jtfDevPassword = "admin123";
@ -128,7 +129,11 @@ public class RegisterUtil implements ActionListener {
*/ */
public RegisterUtil() public RegisterUtil()
{ {
initialize();
String os = System.getProperty("os.name");
if(os.toLowerCase().startsWith("win")){
initialize();
}
initilizeRyNetLib(); initilizeRyNetLib();
loginListenThreadController = new LoginListenThreadController(this); loginListenThreadController = new LoginListenThreadController(this);
} }
@ -587,8 +592,12 @@ public class RegisterUtil implements ActionListener {
// 用户可以自定义 fDisConnectCB // 用户可以自定义 fDisConnectCB
NetLib.instance.Net_Init(_cbDisConnectCallBack, new NativeLong(1)); NetLib.instance.Net_Init(_cbDisConnectCallBack, new NativeLong(1));
NetLib.instance.Net_SetLogFolder("D:\\soft\\control\\TmpAutoReg"); String os = System.getProperty("os.name");
if(os.toLowerCase().startsWith("win")){
NetLib.instance.Net_SetLogFolder("D:\\soft\\control\\TmpAutoReg");
}else {
NetLib.instance.Net_SetLogFolder("/usr/local/water-monitor-api/TmpAutoReg");
}
NetLib.instance.Net_SetLogOption(7); NetLib.instance.Net_SetLogOption(7);
// GlobalTool.createDirectory(this.m_strFilePath); // GlobalTool.createDirectory(this.m_strFilePath);

300
ruoyi-code/src/main/java/utils/RtspConvert.java

@ -0,0 +1,300 @@
package utils;
import cn.hutool.core.util.RuntimeUtil;
import com.alibaba.fastjson.JSON;
import com.ruoyi.common.config.RuoYiConfig;
import com.ruoyi.common.utils.DateUtils;
import com.ruoyi.common.utils.http.HttpUtils;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.io.FileUtils;
import org.apache.commons.lang3.StringUtils;
import org.springframework.scheduling.annotation.EnableScheduling;
import org.springframework.scheduling.annotation.Scheduled;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import javax.annotation.PreDestroy;
import java.io.*;
import java.util.Date;
import java.util.concurrent.ConcurrentHashMap;
/**
* rtsp hlv协议
*
* @author kzw
*/
@Service
@Slf4j
@EnableScheduling
public class RtspConvert {
//转换map
private static ConcurrentHashMap<String, CoverThread> coverMap = new ConcurrentHashMap<>();
//拉流命令
private static final String ffmpegCmd = "ffmpeg -i \"%s\" -c copy -f hls -hls_time 5.0 -hls_list_size 2 -hls_flags 2 %s";
//ffmpeg -i "rtsp://admin:admin123@192.168.1.40:554/stream/realtime?channel=1&streamtype=0" -c copy -f hls -hls_time 4.0 -hls_list_size 2 -hls_flags 2 "D:\video\test.m3u8"
@PreDestroy
public void closeProcess() {
log.info("关闭ffmpeg转换进程,java程序不一定关闭process进程");
closeAllProcess();
for (String ip : coverMap.keySet()) {
try {
log.error("开始停止{}", ip);
coverMap.get(ip).stopTask();
} catch (Exception e) {
e.printStackTrace();
}
}
}
/**
* ffmpeg -i "rtsp://admin:xxx@192.168.0.251:554/Streaming/Channels/101" -c copy -f hls -hls_time 5.0 -hls_list_size 5 -hls_flags 2 F:\resources\hls\2000\live.m3u8
*/
/**
* 检查设备ip是否能正常访问
*/
private boolean checkDeviceOnline(String ip) {
String res = HttpUtils.sendGet("http://" + ip);
if (StringUtils.isNotBlank(res)) {
return true;
}
return false;
}
/**
* 转换rtsp并获取hls文件路径
*/
public String rtsp2Hls(String ip, String userName, String pwd) {
System.out.println(JSON.toJSON(coverMap));
if (coverMap.containsKey(ip)) {
CoverThread thread = coverMap.get(ip);
if (thread == null || thread.getTaskState() != CoverThread.running) {
} else {
return StringUtils.replace(thread.getM3U8File(), RuoYiConfig.getProfile(), "");
}
}
String rtspUrl = "rtsp://" + userName + ":" + pwd + "@" + ip + ":554/stream/realtime?channel=1&streamtype=0";
String m3u8File = RuoYiConfig.getProfile() + File.separator + "hls"
// String m3u8File = "D:" + File.separator + "ruoyi" + File.separator + "uploadPath" + File.separator + "hls"
+ File.separator + ip.replaceAll("\\.", "_") + File.separator + "live.m3u8";
startTransform(ip, rtspUrl, m3u8File, userName, pwd);
CoverThread thread = coverMap.get(ip);
if (thread != null) {
return StringUtils.replace(thread.getM3U8File(), RuoYiConfig.getProfile(), "");
}
return null;
}
/**
* 开启转换
*/
private void startTransform(String ip, String rtspUrl, String m3u8Path, String userName, String pwd) {
log.info("转换rtsp, {},{},{}", ip, rtspUrl, m3u8Path);
String memKey = "startLive" + ip;
synchronized (memKey.intern()) {
if (coverMap.containsKey(ip)) {
stopTransform(ip);
}
CoverThread thread = new CoverThread(ip, rtspUrl, m3u8Path, userName, pwd);
coverMap.put(ip, thread);
thread.start();
}
}
/**
* 停止转换
*/
public void stopTransform(String ip) {
String memKey = "startLive" + ip;
synchronized (memKey.intern()) {
System.out.println(JSON.toJSON(coverMap));
if (coverMap.containsKey(ip)) {
CoverThread thread = coverMap.get(ip);
if (thread != null && thread.getTaskState() != CoverThread.fail) {
System.out.println("停止转换ip"+ip);
thread.stopTask();
}
}
}
}
/**
* 监控所有的转换线程
*/
@Scheduled(cron = "0 0/8 * * * ?")
public synchronized void monitorThreads() {
for (String ip : coverMap.keySet()) {
CoverThread thread = coverMap.get(ip);
if (thread != null && thread.getTaskState() != CoverThread.running) {
//线程出现异常
rtsp2Hls(ip, thread.getUserName(), thread.getPwd());
}
}
}
public void closeAllProcess(){
String command = "taskkill /f /im ffmpeg.exe";
if(!isWin()){
command = "/usr/local/water-monitor-api/closeFFmpeg.sh";
}
System.out.println("command ["+command+"]");
String result = RuntimeUtil.execForStr(command);
System.out.println("command result ["+result+"]");
coverMap.clear();
}
public boolean isWin(){
String os = System.getProperty("os.name");
return os.toLowerCase().startsWith("win");
}
public class RunThread extends Thread {
private InputStream is;
private String printType;
RunThread(InputStream is, String printType) {
this.is = is;
this.printType = printType;
}
@Override
public void run() {
try {
InputStreamReader isr = new InputStreamReader(is);
BufferedReader br = new BufferedReader(isr);
String line;
while ((line = br.readLine()) != null) {
log.info(printType + ">" + line);
}
} catch (IOException ioe) {
log.info("RunThread error:", ioe);
}
}
}
/**
* 执行命令线程
*/
private class CoverThread extends Thread {
private String ip;
private String rtspUrl;
private String m3u8File;
private String userName;
private String pwd;
private int taskState = 0; //运行状态 0未开始 1进行中 -1失败
private static final int notStart = 0;
private static final int running = 1;
private static final int fail = -1;
private Process process = null;
CoverThread(String ip, String rtspUrl, String m3u8File, String userName, String pwd) {
this.ip = ip;
this.rtspUrl = rtspUrl;
this.m3u8File = m3u8File;
this.userName = userName;
this.pwd = pwd;
setName("m3u8-" + ip);
this.taskState = notStart;
}
@Override
public void run() {
try {
FileUtils.forceMkdir(new File(m3u8File).getParentFile());
if (!checkDeviceOnline(ip)) {
log.warn("设备{},离线", ip);
this.taskState = fail;
return;
}
String command = String.format(ffmpegCmd, rtspUrl, m3u8File);
this.taskState = running;
//判断是操作系统是linu2x还是windows
String[] comds;
if (isWin()) {
comds = new String[]{"cmd", "/c", command};
// comds = new String[]{"cmd", "/c", "start", "/b", "cmd.exe", "/k", command};
} else {
comds = new String[]{"/bin/sh", "-c", command};
}
// 开始执行命令
log.info("执行命令:" + command);
process = Runtime.getRuntime().exec(comds);
//开启线程监听(此处解决 waitFor() 阻塞/锁死 问题)
new RunThread(process.getInputStream(), "INFO").start();
new RunThread(process.getErrorStream(), "ERROR").start();
int flag = process.waitFor();
log.info("结束{}", ip);
} catch (Exception e) {
log.error("出现异常" + e.getMessage(), e);
this.taskState = fail;
} finally {
if (process != null) {
try {
process.exitValue();
} catch (Exception e) {
}
try {
process.destroyForcibly();
} catch (Exception e) {
}
}
}
}
/**
* 获取任务执行状态
*/
public int getTaskState() {
return taskState;
}
/**
* 立即停止任务
*/
public void stopTask() {
if (process != null) {
try {
process.destroy();
} catch (Exception e) {
e.printStackTrace();
}
}
}
public String getM3U8File() {
return this.m3u8File;
}
public String getUserName() {
return userName;
}
public String getPwd() {
return pwd;
}
}
public void openTask(){
}
public static void main(String[] args) throws Exception {
RtspConvert convert = new RtspConvert();
convert.closeAllProcess();
String ip = "192.168.1.40";
String userName = "admin";
String pwd = "admin123";
String m3u8 = convert.rtsp2Hls(ip, userName, pwd);
System.out.println("***********************************" + m3u8);
// Thread.sleep(10 * 1000);
// convert.stopTransform(ip);
// System.out.println("************************************结束**************");
}
}

6
ruoyi-common/pom.xml

@ -149,6 +149,12 @@
<artifactId>bcprov-jdk16</artifactId> <artifactId>bcprov-jdk16</artifactId>
<version>1.46</version> <version>1.46</version>
</dependency> </dependency>
<dependency>
<groupId>cn.hutool</groupId>
<artifactId>hutool-all</artifactId>
<version>5.0.6</version>
</dependency>
</dependencies> </dependencies>
</project> </project>

10
ruoyi-quartz/src/main/java/com/ruoyi/quartz/task/RyTask.java

@ -63,6 +63,16 @@ public class RyTask
} }
} }
//定时时间校准
public void resetCameraTime(){
ICameraService cameraService = BeanUtil.getBean(ICameraService.class);
List<Camera> list = cameraService.list(new QueryWrapper<Camera>().eq("status","1").isNotNull("login_id"));
for (Camera c : list) {
CameraUtil.setNowTime(new NativeLong(Long.parseLong(c.getLoginId())));
sleep(10);
}
}
//重启注册服务 //重启注册服务
public void restartServer(){ public void restartServer(){
ICameraService cameraService = BeanUtil.getBean(ICameraService.class); ICameraService cameraService = BeanUtil.getBean(ICameraService.class);

Loading…
Cancel
Save