如何在Java中生成.torrent?

我想用Java生成一个.torrent文件,但是我不想要一个可以做任何事情的大型API,比如抓取跟踪器,播种等等。这只适用于生成元数据的客户端。 有哪些轻量级解决方案 我只生成一个.zip文件的.torrent。

谢谢!

我已经把这个自包含的Java代码放在一起,用一个文件准备一个.torrent文件。

.torrent文件是通过调用createTorrent()传递.torrent文件的名称,共享文件的名称和跟踪器URL来创建的。

createTorrent()使用hashPieces()使用Java的MessageDigest类来散列文件片段 。 然后createTorrent()准备包含torrent元数据的元信息字典 。 然后使用encode*()方法以适当的bencode格式序列化该字典,并保存在.torrent文件中。

有关详细信息,请参阅BitTorrent规范 。

 public class Torrent { private static void encodeObject(Object o, OutputStream out) throws IOException { if (o instanceof String) encodeString((String)o, out); else if (o instanceof Map) encodeMap((Map)o, out); else if (o instanceof byte[]) encodeBytes((byte[])o, out); else if (o instanceof Number) encodeLong(((Number) o).longValue(), out); else throw new Error("Unencodable type"); } private static void encodeLong(long value, OutputStream out) throws IOException { out.write('i'); out.write(Long.toString(value).getBytes("US-ASCII")); out.write('e'); } private static void encodeBytes(byte[] bytes, OutputStream out) throws IOException { out.write(Integer.toString(bytes.length).getBytes("US-ASCII")); out.write(':'); out.write(bytes); } private static void encodeString(String str, OutputStream out) throws IOException { encodeBytes(str.getBytes("UTF-8"), out); } private static void encodeMap(Map map, OutputStream out) throws IOException{ // Sort the map. A generic encoder should sort by key bytes SortedMap sortedMap = new TreeMap(map); out.write('d'); for (Entry e : sortedMap.entrySet()) { encodeString(e.getKey(), out); encodeObject(e.getValue(), out); } out.write('e'); } private static byte[] hashPieces(File file, int pieceLength) throws IOException { MessageDigest sha1; try { sha1 = MessageDigest.getInstance("SHA"); } catch (NoSuchAlgorithmException e) { throw new Error("SHA1 not supported"); } InputStream in = new FileInputStream(file); ByteArrayOutputStream pieces = new ByteArrayOutputStream(); byte[] bytes = new byte[pieceLength]; int pieceByteCount = 0, readCount = in.read(bytes, 0, pieceLength); while (readCount != -1) { pieceByteCount += readCount; sha1.update(bytes, 0, readCount); if (pieceByteCount == pieceLength) { pieceByteCount = 0; pieces.write(sha1.digest()); } readCount = in.read(bytes, 0, pieceLength-pieceByteCount); } in.close(); if (pieceByteCount > 0) pieces.write(sha1.digest()); return pieces.toByteArray(); } public static void createTorrent(File file, File sharedFile, String announceURL) throws IOException { final int pieceLength = 512*1024; Map info = new HashMap(); info.put("name", sharedFile.getName()); info.put("length", sharedFile.length()); info.put("piece length", pieceLength); info.put("pieces", hashPieces(sharedFile, pieceLength)); Map metainfo = new HashMap(); metainfo.put("announce", announceURL); metainfo.put("info", info); OutputStream out = new FileOutputStream(file); encodeMap(metainfo, out); out.close(); } public static void main(String[] args) throws Exception { createTorrent(new File("C:/x.torrent"), new File("C:/file"), "http://example.com/announce"); } } 

代码编辑:使其更紧凑,修复方法可见性,在适当的地方使用字符文字,使用instanceof Number 。 最近使用块I / O读取文件,因为我试图将它用于实际,而字节I / O只是很慢,

我将从Java Bittorrent API开始。 jar子大约70Kb,但你可以通过删除创建种子所不需要的类来将其剥离。 SDK有一个示例ExampleCreateTorrent.java,说明如何完全按照您的需要进行操作。

您还可以了解它是如何在开源Java客户端(如Azureus)中实现的。