Skip to content
项目
群组
代码片段
帮助
当前项目
正在载入...
登录 / 注册
切换导航面板
Z
ZLMediaKit
概览
Overview
Details
Activity
Cycle Analytics
版本库
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
问题
0
Issues
0
列表
Board
标记
里程碑
合并请求
0
Merge Requests
0
CI / CD
CI / CD
流水线
作业
日程表
图表
维基
Wiki
代码片段
Snippets
成员
Collapse sidebar
Close sidebar
活动
图像
聊天
创建新问题
作业
提交
Issue Boards
Open sidebar
张翔宇
ZLMediaKit
Commits
63f22ee6
Commit
63f22ee6
authored
3 years ago
by
ziyue
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
截图失败时,返回ffmpeg日志; ffmpeg命令支持相对路径
parent
a3d696d8
隐藏空白字符变更
内嵌
并排
正在显示
5 个修改的文件
包含
46 行增加
和
25 行删除
+46
-25
server/FFmpegSource.cpp
+22
-16
server/FFmpegSource.h
+3
-1
server/Process.cpp
+5
-1
server/Process.h
+1
-1
server/WebApi.cpp
+15
-6
没有找到文件。
server/FFmpegSource.cpp
查看文件 @
63f22ee6
...
...
@@ -91,8 +91,9 @@ void FFmpegSource::play(const string &ffmpeg_cmd_key, const string &src_url,cons
}
char
cmd
[
1024
]
=
{
0
};
snprintf
(
cmd
,
sizeof
(
cmd
),
ffmpeg_cmd
.
data
(),
ffmpeg_bin
.
data
(),
src_url
.
data
(),
dst_url
.
data
());
_process
.
run
(
cmd
,
ffmpeg_log
.
empty
()
?
""
:
File
::
absolutePath
(
""
,
ffmpeg_log
));
snprintf
(
cmd
,
sizeof
(
cmd
),
ffmpeg_cmd
.
data
(),
File
::
absolutePath
(
""
,
ffmpeg_bin
).
data
(),
src_url
.
data
(),
dst_url
.
data
());
auto
log_file
=
ffmpeg_log
.
empty
()
?
""
:
File
::
absolutePath
(
""
,
ffmpeg_log
);
_process
.
run
(
cmd
,
log_file
);
InfoL
<<
cmd
;
if
(
is_local_ip
(
_media_info
.
_host
))
{
...
...
@@ -312,7 +313,7 @@ void FFmpegSource::onGetMediaSource(const MediaSource::Ptr &src) {
}
}
void
FFmpegSnap
::
makeSnap
(
const
string
&
play_url
,
const
string
&
save_path
,
float
timeout_sec
,
const
function
<
void
(
bool
)
>
&
cb
)
{
void
FFmpegSnap
::
makeSnap
(
const
string
&
play_url
,
const
string
&
save_path
,
float
timeout_sec
,
const
onSnap
&
cb
)
{
GET_CONFIG
(
string
,
ffmpeg_bin
,
FFmpeg
::
kBin
);
GET_CONFIG
(
string
,
ffmpeg_snap
,
FFmpeg
::
kSnap
);
GET_CONFIG
(
string
,
ffmpeg_log
,
FFmpeg
::
kLog
);
...
...
@@ -321,28 +322,33 @@ void FFmpegSnap::makeSnap(const string &play_url, const string &save_path, float
auto
elapsed_ms
=
ticker
.
elapsedTime
();
if
(
elapsed_ms
>
timeout_sec
*
1000
)
{
//超时,后台线程负载太高,当代太久才启动该任务
cb
(
false
);
cb
(
false
,
"wait work poller schedule snap task timeout"
);
return
;
}
char
cmd
[
1024
]
=
{
0
};
snprintf
(
cmd
,
sizeof
(
cmd
),
ffmpeg_snap
.
data
(),
ffmpeg_bin
.
data
(),
play_url
.
data
(),
save_path
.
data
());
char
cmd
[
2048
]
=
{
0
};
snprintf
(
cmd
,
sizeof
(
cmd
),
ffmpeg_snap
.
data
(),
File
::
absolutePath
(
""
,
ffmpeg_bin
).
data
(),
play_url
.
data
(),
save_path
.
data
());
std
::
shared_ptr
<
Process
>
process
=
std
::
make_shared
<
Process
>
();
process
->
run
(
cmd
,
ffmpeg_log
.
empty
()
?
""
:
File
::
absolutePath
(
""
,
ffmpeg_log
));
auto
log_file
=
ffmpeg_log
.
empty
()
?
ffmpeg_log
:
File
::
absolutePath
(
""
,
ffmpeg_log
);
process
->
run
(
cmd
,
log_file
);
//定时器延时应该减去后台任务启动的延时
auto
delayTask
=
EventPollerPool
::
Instance
().
getPoller
()
->
doDelayTask
((
uint64_t
)(
timeout_sec
*
1000
-
elapsed_ms
),[
process
,
cb
](){
if
(
process
->
wait
(
false
)){
//FFmpeg进程还在运行,超时就关闭它
process
->
kill
(
2000
);
}
return
0
;
});
auto
delayTask
=
EventPollerPool
::
Instance
().
getPoller
()
->
doDelayTask
(
(
uint64_t
)(
timeout_sec
*
1000
-
elapsed_ms
),
[
process
,
cb
,
log_file
,
save_path
]()
{
if
(
process
->
wait
(
false
))
{
// FFmpeg进程还在运行,超时就关闭它
process
->
kill
(
2000
);
}
return
0
;
});
//等待FFmpeg进程退出
process
->
wait
(
true
);
//FFmpeg进程退出了可以取消定时器了
//
FFmpeg进程退出了可以取消定时器了
delayTask
->
cancel
();
//执行回调函数
cb
(
process
->
exit_code
()
==
0
);
bool
success
=
process
->
exit_code
()
==
0
&&
File
::
fileSize
(
save_path
.
data
());
cb
(
success
,
(
!
success
&&
!
log_file
.
empty
())
?
File
::
loadFile
(
log_file
.
data
())
:
""
);
});
}
This diff is collapsed.
Click to expand it.
server/FFmpegSource.h
查看文件 @
63f22ee6
...
...
@@ -25,12 +25,14 @@ namespace FFmpeg {
class
FFmpegSnap
{
public
:
using
onSnap
=
std
::
function
<
void
(
bool
success
,
const
std
::
string
&
err_msg
)
>
;
/// 创建截图
/// \param play_url 播放url地址,只要FFmpeg支持即可
/// \param save_path 截图jpeg文件保存路径
/// \param timeout_sec 生成截图超时时间(防止阻塞太久)
/// \param cb 生成截图成功与否回调
static
void
makeSnap
(
const
std
::
string
&
play_url
,
const
std
::
string
&
save_path
,
float
timeout_sec
,
const
std
::
function
<
void
(
bool
)
>
&
cb
);
static
void
makeSnap
(
const
std
::
string
&
play_url
,
const
std
::
string
&
save_path
,
float
timeout_sec
,
const
onSnap
&
cb
);
private
:
FFmpegSnap
()
=
delete
;
~
FFmpegSnap
()
=
delete
;
...
...
This diff is collapsed.
Click to expand it.
server/Process.cpp
查看文件 @
63f22ee6
...
...
@@ -30,7 +30,7 @@
using
namespace
toolkit
;
using
namespace
std
;
void
Process
::
run
(
const
string
&
cmd
,
const
string
&
log_file_tmp
)
{
void
Process
::
run
(
const
string
&
cmd
,
string
&
log_file_tmp
)
{
kill
(
2000
);
#ifdef _WIN32
STARTUPINFO
si
=
{
0
};
...
...
@@ -42,6 +42,7 @@ void Process::run(const string &cmd, const string &log_file_tmp) {
}
else
{
log_file
=
StrPrinter
<<
log_file_tmp
<<
"."
<<
getCurrentMillisecond
();
}
log_file_tmp
=
log_file
;
//重定向shell日志至文件
auto
fp
=
File
::
create_file
(
log_file
.
data
(),
"ab"
);
...
...
@@ -92,6 +93,8 @@ void Process::run(const string &cmd, const string &log_file_tmp) {
//在启动子进程时,暂时禁用SIGINT、SIGTERM信号
signal
(
SIGINT
,
SIG_IGN
);
signal
(
SIGTERM
,
SIG_IGN
);
signal
(
SIGSEGV
,
SIG_IGN
);
signal
(
SIGABRT
,
SIG_IGN
);
//重定向shell日志至文件
auto
fp
=
File
::
create_file
(
log_file
.
data
(),
"ab"
);
...
...
@@ -148,6 +151,7 @@ void Process::run(const string &cmd, const string &log_file_tmp) {
}
else
{
log_file
=
StrPrinter
<<
log_file_tmp
<<
"."
<<
_pid
;
}
log_file_tmp
=
log_file
;
InfoL
<<
"start child process "
<<
_pid
<<
", log file:"
<<
log_file
;
#endif // _WIN32
}
...
...
This diff is collapsed.
Click to expand it.
server/Process.h
查看文件 @
63f22ee6
...
...
@@ -24,7 +24,7 @@ class Process {
public
:
Process
();
~
Process
();
void
run
(
const
std
::
string
&
cmd
,
const
std
::
string
&
log_file
);
void
run
(
const
std
::
string
&
cmd
,
std
::
string
&
log_file
);
void
kill
(
int
max_delay
,
bool
force
=
false
);
bool
wait
(
bool
block
=
true
);
int
exit_code
();
...
...
This diff is collapsed.
Click to expand it.
server/WebApi.cpp
查看文件 @
63f22ee6
...
...
@@ -1251,14 +1251,23 @@ void installWebApi() {
static
auto
responseSnap
=
[](
const
string
&
snap_path
,
const
HttpSession
::
KeyValue
&
headerIn
,
const
HttpSession
::
HttpResponseInvoker
&
invoker
)
{
const
HttpSession
::
HttpResponseInvoker
&
invoker
,
const
string
&
err_msg
=
""
)
{
static
bool
s_snap_success_once
=
false
;
StrCaseMap
headerOut
;
GET_CONFIG
(
string
,
defaultSnap
,
API
::
kDefaultSnap
);
if
(
!
File
::
fileSize
(
snap_path
.
data
())
&&
!
defaultSnap
.
empty
())
{
//空文件且设置了预设图,则返回预设图片(也就是FFmpeg生成截图中空档期的默认图片)
const_cast
<
string
&>
(
snap_path
)
=
File
::
absolutePath
(
defaultSnap
,
""
);
if
(
!
File
::
fileSize
(
snap_path
.
data
()))
{
if
(
!
err_msg
.
empty
()
&&
(
!
s_snap_success_once
||
defaultSnap
.
empty
()))
{
//重来没截图成功过或者默认截图图片为空,那么直接返回FFmpeg错误日志
headerOut
[
"Content-Type"
]
=
HttpFileManager
::
getContentType
(
".txt"
);
invoker
.
responseFile
(
headerIn
,
headerOut
,
err_msg
,
false
,
false
);
return
;
}
//截图成功过一次,那么认为配置无错误,截图失败时,返回预设默认图片
const_cast
<
string
&>
(
snap_path
)
=
File
::
absolutePath
(
""
,
defaultSnap
);
headerOut
[
"Content-Type"
]
=
HttpFileManager
::
getContentType
(
snap_path
.
data
());
}
else
{
s_snap_success_once
=
true
;
//之前生成的截图文件,我们默认为jpeg格式
headerOut
[
"Content-Type"
]
=
HttpFileManager
::
getContentType
(
".jpeg"
);
}
...
...
@@ -1317,7 +1326,7 @@ void installWebApi() {
//启动FFmpeg进程,开始截图,生成临时文件,截图成功后替换为正式文件
auto
new_snap_tmp
=
new_snap
+
".tmp"
;
FFmpegSnap
::
makeSnap
(
allArgs
[
"url"
],
new_snap_tmp
,
allArgs
[
"timeout_sec"
],
[
invoker
,
allArgs
,
new_snap
,
new_snap_tmp
](
bool
success
)
{
FFmpegSnap
::
makeSnap
(
allArgs
[
"url"
],
new_snap_tmp
,
allArgs
[
"timeout_sec"
],
[
invoker
,
allArgs
,
new_snap
,
new_snap_tmp
](
bool
success
,
const
string
&
err_msg
)
{
if
(
!
success
)
{
//生成截图失败,可能残留空文件
File
::
delete_file
(
new_snap_tmp
.
data
());
...
...
@@ -1326,7 +1335,7 @@ void installWebApi() {
File
::
delete_file
(
new_snap
.
data
());
rename
(
new_snap_tmp
.
data
(),
new_snap
.
data
());
}
responseSnap
(
new_snap
,
allArgs
.
getParser
().
getHeader
(),
invoker
);
responseSnap
(
new_snap
,
allArgs
.
getParser
().
getHeader
(),
invoker
,
err_msg
);
});
});
...
...
This diff is collapsed.
Click to expand it.
编写
预览
Markdown
格式
0%
重试
或
添加新文件
添加附件
取消
您添加了
0
人
到此讨论。请谨慎行事。
请先完成此评论的编辑!
取消
请
注册
或者
登录
后发表评论