音乐链接是直接的MP3/OGG等URL(最简单)

这是最理想的情况,网页的HTML代码中直接包含了一个指向音乐文件的链接。

java代码如何获取网页的音乐链接
(图片来源网络,侵删)

例如HTML代码可能是这样的:

<a href="http://example.com/music/song.mp3">Download Song</a>
<!-- 或者是 audio 标签 -->
<audio src="http://example.com/music/song.mp3" controls></audio>

方法:使用Jsoup解析HTML

Jsoup是一个强大的Java HTML解析库,非常适合这种任务。

添加Jsoup依赖

如果你使用Maven,在pom.xml中添加:

java代码如何获取网页的音乐链接
(图片来源网络,侵删)
<dependency>
    <groupId>org.jsoup</groupId>
    <artifactId>jsoup</artifactId>
    <version>1.17.2</version> <!-- 使用最新版本 -->
</dependency>

Java代码示例

import org.jsoup.Jsoup;
import org.jsoup.nodes.Document;
import org.jsoup.nodes.Element;
import org.jsoup.select.Elements;
import java.io.IOException;
public class MusicLinkExtractor {
    public static void main(String[] args) {
        String url = "http://example.com/music-page.html"; // 替换成你目标网页的URL
        try {
            // 1. 获取并解析HTML文档
            // User-Agent 可以模拟浏览器访问,避免被一些网站拒绝
            Document doc = Jsoup.connect(url)
                                 .userAgent("Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/91.0.4472.124 Safari/537.36")
                                 .get();
            // 2. 使用CSS选择器查找所有包含音乐链接的元素
            // 查找所有 href 属性以 .mp3, .ogg, .wav 等结尾的 <a> 标签
            Elements musicLinks = doc.select("a[href$=.mp3], a[href$=.ogg], a[href$=.wav], a[href$=.m4a]");
            // 查找所有 <audio> 标签中的 src 属性
            Elements audioTags = doc.select("audio[src]");
            // 合并结果
            musicLinks.addAll(audioTags);
            // 3. 遍历并提取链接
            System.out.println("找到以下音乐链接:");
            if (musicLinks.isEmpty()) {
                System.out.println("未找到直接的音乐链接。");
            } else {
                for (Element element : musicLinks) {
                    // <a> 标签的链接在 href 属性,<audio> 标签的链接在 src 属性
                    String link = element.attr("href").isEmpty() ? element.attr("src") : element.attr("href");
                    System.out.println(link);
                }
            }
        } catch (IOException e) {
            System.err.println("获取网页时发生错误: " + e.getMessage());
            e.printStackTrace();
        }
    }
}

音乐链接在JavaScript代码中(较常见)

很多现代网站为了安全和动态加载,会将音乐文件的URL隐藏在JavaScript代码里,你直接查看HTML源代码是找不到的。

例如HTML/JavaScript代码可能是这样的:

<script>
    var musicConfig = {
        songUrl: "https://cdn.example.com/secret/path/to/music.mp3",
        title: "A Great Song"
    };
    // ... 其他JS代码
</script>

方法:结合Jsoup和正则表达式

我们需要先用Jsoup获取整个HTML/JS内容,然后用正则表达式来提取我们想要的URL。

java代码如何获取网页的音乐链接
(图片来源网络,侵删)

Java代码示例

import org.jsoup.Jsoup;
import org.jsoup.nodes.Document;
import java.io.IOException;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
public class JsMusicLinkExtractor {
    public static void main(String[] args) {
        String url = "http://example.com/dynamic-music-page.html"; // 替换成目标URL
        try {
            Document doc = Jsoup.connect(url)
                                 .userAgent("Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/91.0.4472.124 Safari/537.36")
                                 .get();
            // 获取页面的所有HTML内容,包括 <script> 标签内的JS代码
            String htmlContent = doc.html();
            // 定义一个正则表达式来匹配音乐URL
            // 这个正则表达式会查找 "songUrl" 后面跟着的字符串,并尝试捕获其中的URL
            // 注意:这个正则表达式需要根据实际JS代码的结构进行调整!
            // 这里只是一个通用示例。
            String regex = "(?i)musicConfig\\s*=\\s*\\{[^}]*songUrl\\s*:\\s*[\"']([^\"']+)[\"'][^}]*\\}";
            Pattern pattern = Pattern.compile(regex);
            Matcher matcher = pattern.matcher(htmlContent);
            System.out.println("在JavaScript中查找音乐链接...");
            if (matcher.find()) {
                String musicLink = matcher.group(1); // group(1) 是第一个括号 () 捕获的内容
                System.out.println("找到音乐链接: " + musicLink);
            } else {
                System.out.println("未在JavaScript中找到匹配的音乐链接。");
                System.out.println("请检查正则表达式是否与网页的JS结构匹配。");
            }
        } catch (IOException e) {
            System.err.println("获取网页时发生错误: " + e.getMessage());
            e.printStackTrace();
        }
    }
}

重要提示: 正则表达式是这种方法的难点,因为它非常脆弱,网站一旦修改JS代码,你的正则表达式就可能失效,你需要使用浏览器的开发者工具(F12)来分析JS代码,并编写针对性的正则表达式。


音乐是通过API动态加载的(最复杂)

最高级的情况是,网页本身不包含任何音乐链接,而是通过一个API(通常是AJAX请求)从服务器获取音乐播放列表或单个音乐的URL。

如何识别这种情况?

  1. 在浏览器中打开目标音乐页面。
  2. 按F12打开开发者工具,切换到 "网络" (Network) 选项卡。
  3. 刷新页面,然后播放音乐。
  4. 在网络请求列表中,筛选 "XHR" 或 "Fetch" 请求。
  5. 查看这些请求,找到一个响应数据中包含音乐URL的请求。

方法:模拟HTTP请求解析JSON

你需要手动分析这个API请求的细节(请求URL、请求方法、请求头、参数等),然后用Java代码模拟这个请求,最后解析返回的JSON数据。

Java代码示例(使用OkHttp和Gson库)

添加依赖

<!-- OkHttp for HTTP requests -->
<dependency>
    <groupId>com.squareup.okhttp3</groupId>
    <artifactId>okhttp</artifactId>
    <version>4.12.0</version> <!-- 使用最新版本 -->
</dependency>
<!-- Gson for JSON parsing -->
<dependency>
    <groupId>com.google.code.gson</groupId>
    <artifactId>gson</artifactId>
    <version>2.10.1</version> <!-- 使用最新版本 -->
</dependency>

模拟请求并解析

假设我们通过分析发现,API请求是 GEThttps://api.example.com/v1/song/123,并且需要 Authorization 请求头。

import com.google.gson.Gson;
import com.google.gson.JsonObject;
import okhttp3.OkHttpClient;
import okhttp3.Request;
import okhttp3.Response;
import java.io.IOException;
public class ApiMusicLinkExtractor {
    public static void main(String[] args) {
        // !!! 这些信息都需要你自己通过浏览器开发者工具分析得到 !!!
        String apiUrl = "https://api.example.com/v1/song/123";
        String authToken = "Bearer your_api_token_here"; // 可能是Token, Cookie等
        // 创建OkHttpClient实例
        OkHttpClient client = new OkHttpClient();
        // 构建请求
        Request request = new Request.Builder()
                .url(apiUrl)
                .addHeader("Authorization", authToken) // 添加必要的请求头
                .addHeader("User-Agent", "Mozilla/5.0...") // 模拟浏览器
                .build();
        try (Response response = client.newCall(request).execute()) {
            if (!response.isSuccessful()) {
                throw new IOException("Unexpected code " + response + " for API request");
            }
            // 获取响应体的JSON字符串
            String responseBody = response.body().string();
            System.out.println("API响应原始JSON: " + responseBody);
            // 使用Gson解析JSON
            Gson gson = new Gson();
            JsonObject jsonObject = gson.fromJson(responseBody, JsonObject.class);
            // 根据JSON结构提取URL
            // 假设JSON结构是: {"data": {"url": "http://music.link.mp3"}}
            if (jsonObject.has("data") && jsonObject.get("data").isJsonObject()) {
                JsonObject data = jsonObject.getAsJsonObject("data");
                if (data.has("url")) {
                    String musicLink = data.get("url").getAsString();
                    System.out.println("从API解析出的音乐链接: " + musicLink);
                    return;
                }
            }
            System.out.println("无法从API响应中解析出音乐链接,请检查JSON结构。");
        } catch (IOException e) {
            System.err.println("请求API时发生错误: " + e.getMessage());
            e.printStackTrace();
        }
    }
}

总结与建议

情况 特点 推荐工具 难度
直接链接 HTML源码中可直接找到 .mp3, .ogg 等URL Jsoup ★☆☆☆☆
JavaScript中 链接被隐藏在<script>标签的JS代码里 Jsoup + 正则表达式 ★★★☆☆
API动态加载 链接通过XHR/Fetch请求从服务器获取 OkHttp + Gson ★★★★☆

给你的建议:

  1. 先从最简单的情况开始:尝试用情况一的方法,看看能否直接获取链接。
  2. 如果不行,打开浏览器开发者工具:按F12,仔细检查网页的HTML和JavaScript代码,看看链接是否在JS里(情况二)。
  3. 如果链接在JS里,并且很复杂:尝试分析这个JS是如何获取链接的,看它是否内部又发了一个API请求,如果是,那就需要进入情况三的深度分析。
  4. 关于合法性和版权:在抓取和使用任何网络资源前,请务必确认你拥有该权限或该行为符合网站的robots.txt规定和相关法律法规,请尊重版权。

对于大多数普通用户来说,情况一情况二已经能解决90%以上的问题了。情况三需要较多的网络知识和耐心。