研究虾米高品质歌曲地址,遇到问题,编解码高手来看看

2013-08-02 22:37:58 +08:00
 jacy
通过对在线播放器抓包,发现播放器首先发送这个:
http://www.xiami.com/song/gethqsong/sid/歌曲id
会返回一段json数据,比如:
{"status":1,"location":"8h2fmFfmxu4wMVVzVBtFiihTgcP9EYRq2Rlt%l.%IqhRU84gVjIOp2ec28S%HtJDts9Wm%F.oFdV5jqomIfI%I3mxmh4TESg%kxFG2A3i%GzYeFo5ZyLu5%.a2u1g4wtECOTp2"}
然后就下载歌曲了,地址是:
http://m3.file.xiami.com/h/hGufTI8d4z1mgqSVTYgxch0e4uPRHjSFw49UtqgotwE8Jo0MY4DmkZCVRgtIxyOVqVsfFLTz2j9IGupVRIW%2BlOmI
可以肯定地址是根据location中算出来的,但是没看出是怎样编码的,如果不是常用的,那么还得反编译播放器的swf文件了。
发到这看看有人能否解出。
另外即使同一个歌曲每次的数据和地址都会变化,但是老的地址在一定时间内还是可以访问下载到的。
4208 次点击
所在节点    编程
7 条回复
jacy
2013-08-02 22:42:45 +08:00
长的英文不会自动换行啊-_-||
双击复制下来,粘贴到回复框看完整的数据
jacy
2013-08-02 22:57:19 +08:00
经过反编译,确实不是常用编码,是虾米自己的算法,找到as文件了,不太会,谁翻译一下

package xiami
{
import com.adobe.serialization.json.*;
import flash.events.*;
import flash.net.*;

public class HQlocationDecode extends EventDispatcher
{
private var _url:String;
private var _isHQ:Boolean;
private static const getHQlocationUrl:String = "http://www.xiami.com/song/gethqsong/sid/";
private static const getTrylocationUrl:String = "http://www.xiami.com/song/gethqsong";

public function HQlocationDecode()
{
return;
}// end function

public function getTryLoation(param1:int, param2:String = null, param3:int = 0) : void
{
var _loc_4:* = new URLRequest(getTrylocationUrl);
var _loc_5:* = new URLVariables();
new URLVariables().sid = param1;
_loc_5.type = param2;
_loc_5.typeId = param3;
_loc_4.data = _loc_5;
var _loc_6:* = new URLLoader();
new URLLoader().addEventListener(Event.COMPLETE, this.loadCompleteHandler);
_loc_6.addEventListener(IOErrorEvent.IO_ERROR, this.errorHandler);
_loc_6.load(_loc_4);
return;
}// end function

public function getHQLocation(param1:int, param2:String = null, param3:int = 0) : void
{
var _loc_4:* = new URLRequest(getHQlocationUrl + param1);
var _loc_5:* = new URLLoader();
new URLLoader().addEventListener(Event.COMPLETE, this.loadCompleteHandler);
_loc_5.addEventListener(IOErrorEvent.IO_ERROR, this.errorHandler);
_loc_5.load(_loc_4);
return;
}// end function

private function loadCompleteHandler(event:Event) : void
{
var _loc_4:* = undefined;
var _loc_2:* = event.target.data;
var _loc_3:* = JSON.decode(_loc_2).status;
if (_loc_3 == 1)
{
this._isHQ = true;
_loc_4 = JSON.decode(_loc_2).location;
this._url = this.getLocation(_loc_4);
}
else
{
this._isHQ = false;
this._url = null;
}
dispatchEvent(new Event(Event.COMPLETE));
return;
}// end function

private function errorHandler(event:Event) : void
{
this._isHQ = false;
dispatchEvent(new IOErrorEvent(IOErrorEvent.IO_ERROR));
return;
}// end function

public function get url() : String
{
return this._url;
}// end function

public function get isHQ() : Boolean
{
return this._isHQ;
}// end function

public function getLocation(param1:String) : String
{
var _loc_10:* = undefined;
var _loc_2:* = Number(param1.charAt(0));
var _loc_3:* = param1.substring(1);
var _loc_4:* = Math.floor(_loc_3.length / _loc_2);
var _loc_5:* = _loc_3.length % _loc_2;
var _loc_6:* = new Array();
var _loc_7:* = 0;
while (_loc_7 < _loc_5)
{

if (_loc_6[_loc_7] == undefined)
{
_loc_6[_loc_7] = "";
}
_loc_6[_loc_7] = _loc_3.substr((_loc_4 + 1) * _loc_7, (_loc_4 + 1));
_loc_7 = _loc_7 + 1;
}
_loc_7 = _loc_5;
while (_loc_7 < _loc_2)
{

_loc_6[_loc_7] = _loc_3.substr(_loc_4 * (_loc_7 - _loc_5) + (_loc_4 + 1) * _loc_5, _loc_4);
_loc_7 = _loc_7 + 1;
}
var _loc_8:* = "";
_loc_7 = 0;
while (_loc_7 < _loc_6[0].length)
{

_loc_10 = 0;
while (_loc_10 < _loc_6.length)
{

_loc_8 = _loc_8 + _loc_6[_loc_10].charAt(_loc_7);
_loc_10 = _loc_10 + 1;
}
_loc_7 = _loc_7 + 1;
}
_loc_8 = unescape(_loc_8);
var _loc_9:* = "";
_loc_7 = 0;
while (_loc_7 < _loc_8.length)
{

if (_loc_8.charAt(_loc_7) == "^")
{
_loc_9 = _loc_9 + "0";
}
else
{
_loc_9 = _loc_9 + _loc_8.charAt(_loc_7);
}
_loc_7 = _loc_7 + 1;
}
_loc_9 = _loc_9.replace("+", " ");
return _loc_9;
}// end function

}
}
PeterD
2013-08-03 16:32:52 +08:00
dndx
2013-08-03 16:45:04 +08:00
pubby
2013-08-03 16:56:12 +08:00
还好了,算法是固定的,改写成你需要的语言就可以解码了。

以前破解百度指数算法的时候,他是每几小时随机变化的加解密算法,而且编译在swf文件里面。当时不得不对照《ActionScript Virtual Machine 2 (AVM2) Overview》写了个简单的ABC(ActionScript Byte Code)模拟器来解码 :(
jjplay
2013-08-03 17:00:11 +08:00
很早 算不上研究,找到了3L 那人的文章,最终下载的还是低品质的~
jacy
2013-08-04 12:01:33 +08:00
晕哦,谢了,不过你们回复太慢了,我已经自己做好了
http://v2ex.com/t/77863
可以下载高品质哦

这是一个专为移动设备优化的页面(即为了让你能够在 Google 搜索结果里秒开这个页面),如果你希望参与 V2EX 社区的讨论,你可以继续到 V2EX 上打开本讨论主题的完整版本。

https://www.v2ex.com/t/77815

V2EX 是创意工作者们的社区,是一个分享自己正在做的有趣事物、交流想法,可以遇见新朋友甚至新机会的地方。

V2EX is a community of developers, designers and creative people.

© 2021 V2EX