排行榜 统计
  • 建站日期:2020-07-15
  • 文章总数:64 篇
  • 评论总数:1454 条
  • 分类总数:6 个
  • 最后更新:一天前

图集短视频去水印云函数开发实践——抖音

本文阅读 4 分钟
首页 精品教程 正文

我记得以前好像写过一次抖音去水印云函数代码,这次主要是利用云开发做了抖音视频和图集,快手视频和图集,以及小红书,本站视频去水印解析代码。无需第三方API,直接使用云函数JS实现。

先说一下抖音去水印吧,这个应该是最普遍的,基本上哪里都能看到,当然需求也应该是最多的。如何获取到抖音短视频或图集的链接就不说了,这里以获取到一个短视频或图集链接开始,例如:

https://v.douyin.com/iSMn612Y/

这是一个抖音图集链接,获取到图片后我们需要获取到链接的重定向地址,代码如下:

async getRedirectUrl(url) {
    try {
      console.log("开始获取重定向URL:", url);
      const response = await this.curl(url, {
        method: "GET",
        dataType: "text",
        followRedirect: false,
      });
      console.log("重定向响应状态码:", response.status);
      console.log("重定向响应头:", response.headers);
      const redirectUrl = response.headers.location || url;
      console.log("最终重定向URL:", redirectUrl);
      return redirectUrl;
    } catch (error) {
      console.error("获取重定向URL时出错:", error);
      throw error;
    }
  }

这样我们会获取到图集的详细地址,如下:

https://www.iesdouyin.com/share/note/7413711897830116608/?from_ssr=1&did=MS4wLjABAAAA_ZRjnl9xURp2Nui6mSbdBZD-zKuxZ_4XCrORVrlZnOyHvVKSTMMbXZ7WEc7q938F&mid=7386529472516376593&ts=1729489810&region=CN&share_sign=EZcWgkQkqoMwZxaIuvyxXW0TN2cWPoFVkJJ8ZkaxKZU-&tt_from=share_to&with_sec_did=1&from_aid=1128&titleType=title&utm_source=share_to&utm_medium=ios&activity_info=%7B%22social_share_time%22:%221729491670%22,%22social_author_id%22:%223971887811007315%22,%22social_share_id%22:%223971887811007315_1729491670%22,%22social_share_user_id%22:%223971887811007315%22%7D&timestamp=1729491669&share_version=310700&u_code=43k49fd35049&iid=MS4wLjABAAAAnlTijq4kdbAmlGgBbFVcvoPYhMp5oMFVOQh6-bg_fGd-_GapZ0AE5mNge6ItbVJ8&utm_campaign=client_share&app=aweme&schema_type=37

挺长的,但是我们只需要两个参数就行了,一个是链接中的note然后就是后面的ID,其中note主要是为了区分短视频和图集的,然后重要的就是视频的ID,得到分类和ID后,就可以开始进行下一步了。

// 构造请求头
const headers = {
        "User-Agent": "Mozilla/5.0 (iPhone; CPU iPhone OS 16_6 like Mac OS X) AppleWebKit/605.1.15 (KHTML, like Gecko) Version/16.6 Mobile/15E148 Safari/604.1 Edg/122.0.0.0",
      };

// 发送请求获取信息
const response = await this.curl(`https://www.iesdouyin.com/share/${isImage ? "note" : "video"}/${id}`, {
          headers: headers,
          dataType: "text",
      });
这样视频或图集的信息就藏在这个响应中,但是数据很乱,只要找到需要的参数就行了。

// 解析响应数据
      const pattern = /window\._ROUTER_DATA\s*=\s*(.*?)<\/script>/s;
      const matches = response.data.match(pattern);
      if (!matches || !matches[1]) {
        return {
          code: 201,
          msg: "解析失败:无法匹配信息"
        };
      }

      const info = JSON.parse(matches[1].trim());
      console.log("info:", info);

      return isImage ? this.parseImageData(info) : this.parseVideoData(info);
上述代码中可以得到原始数据,然后图片和视频的分别进行解析得到数据,如下:

  // 解析视频数据  
  parseVideoData(videoInfo) {
    const itemData = this.safeGet(videoInfo, 'loaderData.video_(id)/page.videoInfoRes.item_list.0', {});
    
    // 尝试获取无水印视频链接
    let videoUrl = this.getNoWatermarkVideoUrl(itemData);

    return {
      code: 200,
      msg: "解析成功",
      data: {
        type: "video",
        author: this.safeGet(itemData, 'author.nickname', ''),
        uid: this.safeGet(itemData, 'author.unique_id', ''),
        avatar: this.safeGet(itemData, 'author.avatar_medium.url_list.0', ''),
        like: this.safeGet(itemData, 'statistics.digg_count', 0),
        time: this.safeGet(itemData, 'create_time', ''),
        title: this.safeGet(itemData, 'desc', ''),
        cover: this.safeGet(itemData, 'video.cover.url_list.0', ''),
        url: videoUrl,
        music: {
          author: this.safeGet(itemData, 'music.author', ''),
          avatar: this.safeGet(itemData, 'music.cover_large.url_list.0', ''),
        },
        view_count: this.safeGet(itemData, 'statistics.play_count', 0),
        share_count: this.safeGet(itemData, 'statistics.share_count', 0),
        platform: "douyin",
      },
    };
  }
  // 尝试获取无水印视频链接
  getNoWatermarkVideoUrl(itemData) {
    let videoUrl = '';
    
    // 方法1:尝试从 play_addr 中获取无水印链接
    const playAddr = this.safeGet(itemData, 'video.play_addr', {});
    videoUrl = this.safeGet(playAddr, 'url_list.0', '');
    
    // 如果获取到的 URL 包含 "playwm",尝试将其替换为 "play"
    if (videoUrl.includes('playwm')) {
      videoUrl = videoUrl.replace('playwm', 'play');
    }
    
    // 方法2:如果上面的方法失败,尝试从 download_addr 获取
    if (!videoUrl) {
      const downloadAddr = this.safeGet(itemData, 'video.download_addr', {});
      videoUrl = this.safeGet(downloadAddr, 'url_list.0', '');
    }
    
    // 方法3:如果还是失败,使用原始的 play_addr
    if (!videoUrl) {
      videoUrl = this.safeGet(itemData, 'video.play_addr.url_list.0', '');
    }
    return videoUrl;
  }

上面是视频具体的解析方案,然后下面是图片的解析方案,

parseImageData(imageInfo) {
    const noteData = this.safeGet(imageInfo, 'loaderData.note_(id)/page.videoInfoRes.item_list.0', null);
    if (!noteData) {
      return {
        code: 404,
        msg: "未找到图集信息"
      };
    }
    const imageList = noteData.images || [];
    return {
      code: 200,
      msg: "解析成功",
      data: {
        type: "image_set",
        author: this.safeGet(noteData, 'author.nickname', ''),
        uid: this.safeGet(noteData, 'author.unique_id', ''),
        avatar: this.safeGet(noteData, 'author.avatar_medium.url_list.0', ''),
        like_count: this.safeGet(noteData, 'statistics.digg_count', 0),
        comment_count: this.safeGet(noteData, 'statistics.comment_count', 0),
        time: noteData.create_time,
        title: noteData.desc,
        cover: this.safeGet(imageList, '0.url_list.0', ''),
        images: imageList.map((img) => ({
          url: this.safeGet(img, 'url_list.0', ''),
          width: img.width,
          height: img.height,
        })),
        view_count: this.safeGet(noteData, 'statistics.play_count', 0),
        share_count: this.safeGet(noteData, 'statistics.share_count', 0),
        platform: "douyin",
      },
    };
  }

当然其实得到参数后你想怎么处理就怎么处理了,所以到这里就结束了。最后代码中safeGet是一个用于代码?.的函数,因为我测试node18支持,但是node12好像不支持?.。

// 安全获取对象属性
  safeGet(obj, path, defaultValue = '') {
    return path.split('.').reduce((acc, part) => {
      if (acc && typeof acc === 'object' && part in acc) {
        return acc[part];
      }
      return defaultValue;
    }, obj);
  }

大致就是这些了,明天在更新快手如何获取无水印视频及图集吧,有什么问题可以留言哦~

本文来自投稿,不代表本站立场,如若转载,请注明出处:https://www.i4qq.com/jpjc/dydspqsyyhskf.html
开源原创智能水印相机微信小程序
« 上一篇 03-28

发表评论

成为第一个评论的人

作者信息

热门文章

标签TAG

热评文章