提醒:本文最后更新于 1811 天前,文中所描述的信息可能已发生改变,请仔细核实。
SILK v3编码是Skype向第三方开发人员和硬件制造商提供免版税认证(RF)的Silk宽带音频编码器,Skype后来将其开源。具体可见Wikipedia。
但是现在很难找齐源码,或者说懒得找。
一年前寻找的时候,很少看到。今年过年正好要转换QQ的语音信息(去年又是微信的语言信息),就找了下,顺便做成Shell脚本,具体可见Github项目地址:https://github.com/kn007/silk-v3-decoder。
需要gcc和ffmpeg。gcc是拿来编译silk v3 decoder源码,ffmpeg是拿来转换格式的。
调用很简单,只需一句命令:
sh convert.sh 33921FF3774A773BB193B6FD4AD7C33E.slk mp3
其中:“33921FF3774A773BB193B6FD4AD7C33E.slk”是你要转换的源文件(QQ常见为slk,微信常见为amr);后面的“mp3”是你要输出的格式。
首次使用会编译silk v3 decoder,第二次以后就不用了。
其他的没什么。略微改下,利用nginx+lua或直接用python都可以做成在线版本,暂时没什么时间,就先不搞了。反正本地能用就达到目的了。
注:如果你使用了该代码于商业目的,希望你能赞助我,谢谢!
彩蛋,33921FF3774A773BB193B6FD4AD7C33E.slk.mp3,调试时唱的歌(掩面,太难听。。。
那些忽悠帮你们写功能开发,然后不给钱的,已经好几起了。只想说这样搞,我是不会再更新了。
转载请注明转自: kn007的个人博客 的《解码转换QQ微信的SILK v3编码音频为MP3或其他格式》


我使用的手机微信进行录音,得到的silk格式文件,但是用的你github上的程序进行解码,告知我我的silk文件可能不是silk v3版本的文件。。我应该怎么处理这块?
@kiss: 你用mac还是linux还是win?
使用ios还是Android,提问题的时候,写上基本环境。
win的话,用silk2mp3,你点下Try AMR试试。
linux,都会用linux了,自己看下用beta行不行,fix了amr。
mac同linux。
@kn007: 我手机是安卓,然后linux 进行转换,我看你的文档有提到参数,我想问下,参数列表在哪能看到?
@kiss: 用shell看bin文件啊
@kn007: maybe not a silk v3 encoded file 这个是 sh silk-v3-decoder/converter.sh tmp_c8f24f0422407d0ff09c324548d9c713c4fd4223766ca44ad93a5061f5cd774f.silk pcm 这条命令报的错。maybe not a audio file. 这个是 sh silk-v3-decoder/converter_beta.sh tmp_c8f24f0422407d0ff09c324548d9c713c4fd4223766ca44ad93a5061f5cd774f.silk pcm 这个命令报的错

@kiss: 你自己右键编辑你那个tmp文件看看是什么头
@kiss: 出现这种错的,大部分是小程序的。普通聊天应该不至于。
@kn007: 对。就是小程序。#!SILK_V3 开头是这个
@kiss: 。。。那你没说清楚。。。
如果是这个头并且是小程序的,那没办法。
因为小程序的有些被加密了,腾讯没有透露加密方式。
@kn007: windows的插件 正常转了。linux 不行。奇怪了
@kiss: 那没什么道理啊。。。是不是没权限。。。
@kn007: windows 用的事特殊编码(实验性功能),正常解码了
linux 使用bate 告知没有这个文件,奇怪。我看看什么权限。
@kn007: 抱歉,我说错了。windows 是普通解码,不过我先择了try amr。linux 这个选项怎咩勾选?
@kiss: beta版就是。
@kn007: 转码出来的语音意思都错了。应该是强制转码的问题。哎。郁闷
@kiss: 使用try amr是一定成功转换成功的。但是能不能听就是另外一回事了。。。
@kn007: 厉害了。。哈哈哈。反正我搞不定了。烦死
作者您好 ,我用你的软件Linux能转换电脑调试小程序的silk成webm,有大小
但是手机测试的时候上传的音是没法转换。
手机小程序下载的silk 能用windows的工具转
@ludi: 没明白你意思,理清逻辑重新描述
@kn007: 我这里有一套小程序语音识别的程序,里面用到的是您的代码。
我这里弄了又一段时间了。目前有一个问题就是。电脑调试小程序产生的silk音频,能转换成webm,但是手机调试的时候产生的silk,他产生了webm文件,但是是空的。
@ludi: 我还是没看明白。你不用说前因后果,请说实际情况。
电脑调试是怎么调试法?
手机调试又是怎么调试?
@ludi: 你说说你是怎么用,然后出现什么问题,过程告诉我。你跟我说结果是不行,我也只能知道你说不行。
@kn007: 一套小程序,语音识别领红包。后台是php thinkphp3.2
通过百度语音识别,上传之前要吧silk转成pcm,但是一顿操作猛如虎之后还是只有电脑调试时候产生的silk能被转换成webm,手机产生的silk无法转换,但是整个流程下来都是无法识别。
博主要不我把程序全部发给你?
我不太好表达。。好尴尬
@ludi: 简单理解一下,电脑调试一切正常,对吧。
但上线业务就不行了?
另外小程序sdk调试语音,与实际微信小程序的语音是不同的,如果你没上线业务,可以先上线测试一下。
@ludi: 另外为何要转成webm?小程序可以识别silk的(特殊编码)
@kn007: 转百度语音pcm 递交给百度识别。
@ludi: pcm的我知道,我说的是webm
@ludi: 按你说的,那么正常流程就是
小程序语音=>pcm=>百度=>代码逻辑。
不是么?
你现在哪一段出问题
@kn007: 就是下面,先转成webm再转成pcm,其实我也没看懂。。
@ludi: 小程序要么是silk要么就是webm,两者都是直接转pcm就行了。
@kn007: 好的。那silk-v3开头的silk文件,转pcm是用ffmpeg还是用你的脚本!?
我试试,给你个赞赏 谢谢博主!
@ludi: 用我的脚本啊,ffmpeg根本不能转换。
兄弟复制代码后,你要理解代码,好吧。
@kn007: 懂了!
手机的silk转webm是0 kb 什么也没有
@ludi: 怎么转法是0kb?
'webmExt' => 'webm',
//执行脚本silk-v3转码
$cmd ="sh ./silk-v3/converter.sh ../".$this->ffmpeg['file'].' '.$this->ffConfig['webmExt'];
文件是产生了,但是是空的,0KB文件。
@ludi: 他这个webm是php生成的,不是silk生成的
ffmpeg = $ffmpeg;
$fileNameExt = basename($this->ffmpeg['file']);
$fileInfo = explode('.',$fileNameExt);
$path = dirname($this->ffmpeg['file']);
$this->ffConfig=[
'filePath' => $path.'/', //文件路径
'fileName' => $fileInfo[0], //不带后缀文件名
'fileExt' => $fileInfo[1], //带后缀文件名
'fileNameExt' => $fileNameExt, //带后缀文件名
'webmExt' => 'webm', //新生成解密的临时文件后缀
'pcmExt' => 'pcm', //转码后临时文件pcm后缀
];
}
public function audioTotext(){
//文件不存在
if(!file_exists($this->ffmpeg['file'])){
return false;
}
$str = file_get_contents($this->ffmpeg['file']);//将整个文件内容读入到一个字符串中
//不带后缀的文件
$newFile = $this->ffConfig['filePath'].$this->ffConfig['fileName'];
// var_dump($newFile);
$ext = $this->ffConfig['webmExt'];
if(strstr($str,'data:audio')){
$file = str_replace("data:audio/webm;base64,", '', $str);
$file = base64_decode($file);
//生成临时文件
file_put_contents($newFile.'.'. $this->ffConfig['webmExt'], $file);
}else{
//执行脚本silk-v3转码
$cmd ="sh ./silk-v3/converter.sh ../".$this->ffmpeg['file'].' '.$this->ffConfig['webmExt'];
$res = shell_exec($cmd);
if(!strstr($res,'[OK]')){
return false;
}
}
// var_dump(file_get_contents($this->ffmpeg['file']));
//执行脚本转码并返回转码信息
$cmd ="ffmpeg -y -i {$newFile}.$ext -acodec pcm_s16le -f s16le -ac 1 -ar 16000 {$newFile}.{$this->ffConfig['pcmExt']}";
$res = shell_exec($cmd);
//命令执行失败的情况
if(!file_exists($this->ffmpeg['file'])){
unlink($newFile.$this->ffConfig['webmExt']);
return false;
}
preg_match("/size=(.*?) time=(.*?) bitrate= (.*?)kbits\/s /", $res, $matches);
return ['vedio'=>$newFile.'.'.$this->ffConfig['pcmExt'],'vedioInfo'=>$matches]?:[];
}
}
@ludi: 你这代码,简单看,逻辑没问题,你现在执行到哪段出错呢。而且既然会写,基本排查总会吧,自己根据代码定位一下问题。
@kn007: 我到脚本根目录 直接 sh converter.sh 1.silk pcm
【warning】 convert 1.silk false,maybe ffmpeg no format handler for pcm
@ludi: 错误信息很明显,pcm首先ffmpeg是没办法直接转的,需要定义方法。你先搜下pcm是什么意思吧。。。
@ludi: 你好,请问下你这个问题解决了吗?我遇到个和你这个差不多的
@ludi: 请问,微信语音格式以#!SILK_V3开头,需要利用silk-v3-decoder对silk文件进行转码,但是报"maybe not a silk v3 encoded file"错的bug解决了么?我遇到了同样的问题哇。
sh converter.sh 1.silk webm
webm 文件产生成功,但是里面是空的
@ludi: 那你要看下ffmpeg的版本和权限问题了。
你好! 我使用微信小程序 录音的文件是webm 格式的文件,我需要把这个文件转成pcm 或者wav 通过百度进行识别成文字,但是使用您的脚本行不通,请问有别的办法吗
@饶jj: 请让懂编程的完成这件事,或者看之前评论。
@饶jj: 这个问题非常简单,逻辑也简单。
我回答过很多次了,不想重复了。
判断是base64的webm,或者是silk v3。
前者用ffmpeg,后者用silk v3 decoder。
得到文件后,百度识别。
@kn007: 实在不好意思,我也遇到了一样的问题,安卓手机微信小程序,录入的语音格式以#!SILK_V3开头,需要利用silk-v3-decoder对silk文件进行转码,转码格式为.webm,但是转码时,报"maybe not a silk v3 encoded file"错。
逻辑代码如下:
if(strstr($str,'data:audio')){
$file = str_replace("data:audio/webm;base64,", '', $str);
$file = base64_decode($file);
//生成临时文件
file_put_contents($newFile.'.'. $this->ffConfig['webmExt'], $file);
}else{
//执行脚本silk-v3转码
$cmd ="sh ./silk-v3/converter.sh ../".$this->ffmpeg['file'].' '.$this->ffConfig['pcmExt'];
$res = shell_exec($cmd);//执行脚本命令,并获取返回信息
if(!strstr($res,'[OK]')){
return $res;//我经过调试,定位到是此处报错,且报错信息显示,是此行往上的第三行报错。
}
}
经过对服务器文件检查,ffmpeg、converter.sh及.silk文件权限都是0777,权限无错。
请问,要如何才能转码成功呢?
@梅子: 好啦,再遇到安卓手机微信小程序,录入的语音格式以#!SILK_V3开头,需要利用silk-v3-decoder对silk文件进行转码,转码格式为.webm,但是转码时,报"maybe not a silk v3 encoded file"错这个问题的朋友,看这里,我解决了我的问题。
首先,在服务器将silk文件夹即其子文件权限都设置为777,否则无法访问decoder,就会报"maybe not a silk v3 encoded file"错。
然后,将$cmd ="sh ./silk-v3/converter.sh ../".$this->ffmpeg['file'].' '.$this->ffConfig['pcmExt'];
修改为$cmd ="sh ./silk-v3/converter.sh ../".$this->ffmpeg['file'].' '.$this->ffConfig['webmExt'];
即将最后的文件后缀名修改为webm,不要设置为pcm,否则会报"maybe ffmpeg no format handler for pcm"错。
改完后就行啦。
[root@iZwz9ilmai38ophsu3t6wgZ ~]# sh /usr/local/silk-v3/converter.sh data/upload/default/20180202/5a73d1c25b174.silk mp3
[Warning] Convert data/upload/default/20180202/5a73d1c25b174.silk false, maybe not a silk v3 encoded file.
[root@iZwz9ilmai38ophsu3t6wgZ ~]#
[root@iZwz9ilmai38ophsu3t6wgZ ~]# sh /usr/local/silk-v3/converter.sh /usr/local/test/2.silk mp3
[OK] Convert /usr/local/test/2.silk To /usr/local/test/2.mp3 Finish.
[root@iZwz9ilmai38ophsu3t6wgZ ~]# sh /usr/local/silk-v3/converter.sh /usr/local/test/3.silk mp3
[OK] Convert /usr/local/test/3.silk To /usr/local/test/3.mp3 Finish.
[root@iZwz9ilmai38ophsu3t6wgZ ~]# sh /usr/local/silk-v3/converter.sh /usr/local/test/4.silk mp3
[OK] Convert /usr/local/test/4.silk To /usr/local/test/4.mp3 Finish.
[root@iZwz9ilmai38ophsu3t6wgZ ~]#
博主,这个问题很奇怪,微信生成的 silk文件,转mp3文件. 在上传的目录直接转,提示maybe not a silk v3 encoded file..
然后我把文件移动到urs/local/test目录下面,再转换就可以成功.这个是什么问题呢?
@szadv: 权限问题。
请补基础知识。
把文件单独设置为 755 权限后执行
[root@iZwz9ilmai38ophsu3t6wgZ ~]# sh /usr/local/silk-v3/converter.sh data/upload/default/20180202/5a73d82c793d3.silk mp3
[Warning] Convert data/upload/default/20180202/5a73d82c793d3.silk false, maybe not a silk v3 encoded file.
报的是这个错误了.maybe not a silk v3 encoded file.
复制同样的文件 重命名为11.silk,复制到usr/local/test 目录后 执行结果
[root@iZwz9ilmai38ophsu3t6wgZ ~]# sh /usr/local/silk-v3/converter.sh /usr/local/test/11.silk mp3
[OK] Convert /usr/local/test/11.silk To /usr/local/test/11.mp3 Finish.
[root@iZwz9ilmai38ophsu3t6wgZ ~]# ^C
这个又是怎么回事呢,需要怎么处理呢?
@szadv: 另外一个情况是用模拟器生成的silk文件移动到 /usr/local/test/下执行会报错.
用真机生成的文件就正常.
[root@iZwz9ilmai38ophsu3t6wgZ ~]# sh /usr/local/silk-v3/converter.sh /usr/local/test/5a73e1d111cba.silk mp3
[OK] Convert /usr/local/test/5a73e1d111cba.silk To /usr/local/test/5a73e1d111cba.mp3 Finish.
[root@iZwz9ilmai38ophsu3t6wgZ ~]# sh /usr/local/silk-v3/converter.sh /usr/local/test/5a73e21172a76.silk mp3
[Warning] Convert /usr/local/test/5a73e21172a76.silk false, maybe not a silk v3 encoded file.
@szadv: 权限所属人呢?
这种问题我不想答了
@kn007: 都是用了旧的小程序录音接口,新的小程序录音接口已经可以直接生成mp3格式~您也是有耐心回答问题
@yogogo: 一般都有耐心,但是抄代码的,还有基础问题,真的不想答,答了一个,会有第二个。明明之前已经说过的问题,还要重复几十遍,无奈。
请问,微信小程序导出的silk文件,sh converter.sh 89697729097b02f1f743abca05fce24f.silk mp3
[Warning] Convert 89697729097b02f1f743abca05fce24f.silk false, maybe ffmpeg no format handler for mp3. 如果转mp2就没问题,是怎么回事啊?
@007: 是不是得先让ffmpeg支持MP3转换啊?感觉ffmpeg安装是重头戏
@007: 肯定要ffmpeg支持mp3啊。要不转换不了。
@kn007: 好的,麻烦能给个ffmpeg支持MP3正确安装步骤吗?谢谢啦!
@kn007: 安装好ffmpeg了,谢谢啦