下載 raywenderlich.com 上的 iOS/android/Unity 視頻、源碼

raywenderlich 簡介

www.raywenderlich.com 對於 iOS 開發人員來講必定不陌生,這多是 iOS 初級教程裏面被推薦最多的網站了吧。javascript

其實它不只有 iOS 的開發教程,後面還出了 android 和 Unity 的開發教程。java

教程簡明實用,有原理介紹還有代碼實現,直接能夠看到實現效果,很是推薦你們也能寫成像它上面的教程。python

raywenderlich 官文介紹

  • 90kDAILY PAGEVIEWS
  • 2049ARTICLES
  • 2921VIDEOS & SCREENCASTS
  • 244TEAM MEMBERS

raywenderlich.com is a community site focused on creating high quality programming tutorials.android

We pride ourselves on creating the highest-quality video courses, books, and written tutorials on the Internet.ios

Every tutorial on our site goes through three rounds of editing before publication, to make sure each tutorial works 100%, is technically accurate, and provides comprehensive coverage of the topic.git

Thousands of developers and designers of all backgrounds, from all over the world, come to raywenderlich.com to teach and learn.github

We pay our authors and editor for all of their work, using the highest rates in the industry.正則表達式

Our goal is to create an environment where talented developers and teachers can make a living through their work, or advance their career by being recognized as an expert.chrome

下載 raywenderlich 資源

5 月 2 日收到 Ray Wenderlich ray@raywenderlich.com 的訂閱郵件。json

Ray Wenderlich <ray@raywenderlich.com>.png

五一週末免費開放視頻 3 天,太好了,爲了之後也有時間觀看,我決定把視頻下載下來。

youtube-dl

最早找到 github.com/ytdl-org/yo…,這上面提供多種視頻下載。

代碼 clone 下來一運行,報錯!登陸不成功。

這個難不倒我,使用 Chrome 開發者工具,找到 Header 裏面有一個

'Authorization': 'Token ..'
複製代碼

打開 Postman,添加 Authorization

Authorization.png

Hersers 界面以下:

Headers.png

獲得 json 文件:

{
    "video": {
        "id": 246,
        "name": "PDF Printing",
        "description": "Create a PDF file. We’ll create a budget report that you could then share.",
        "author_notes": "",
        "duration": 589,
        "pretty_duration": "9 minutes 49 seconds",
        "featured": false,
        "episode": 6,
        "format": "course",
        "language": null,
        "platform": null,
        "editor": null,
        "meta_description": null,
        "released_at": "2016-05-13T16:00:00.000Z",
        "difficulty": "intermediate",
        "created_at": "2016-08-04T02:56:51.175Z",
        "updated_at": "2019-04-28T10:01:25.399Z",
        "free": true,
        "attachments": [
            {
                "id": 4605,
                "url": "https://files.betamax.raywenderlich.com/attachments/videos/246/CG-Int-MyList-06.png",
                "kind": "watchlist_artwork",
                "filename": "CG-Int-MyList-06.png",
                "retina": false
            },
            {
                "id": 4606,
                "url": "https://files.betamax.raywenderlich.com/attachments/videos/246/CG-Int-MyList-06%402x.png",
                "kind": "watchlist_artwork",
                "filename": "CG-Int-MyList-06@2x.png",
                "retina": true
            },
            {
                "id": 4607,
                "url": "https://files.betamax.raywenderlich.com/attachments/videos/246/CG-Int-VideoBanner-06.png",
                "kind": "video_banner",
                "filename": "CG-Int-VideoBanner-06.png",
                "retina": false
            },
            {
                "id": 4608,
                "url": "https://files.betamax.raywenderlich.com/attachments/videos/246/CG-Int-VideoBanner-06%402x.png",
                "kind": "video_banner",
                "filename": "CG-Int-VideoBanner-06@2x.png",
                "retina": true
            },
            {
                "id": 1736,
                "url": "https://files.betamax.raywenderlich.com/attachments/videos/246/005_IntCoreGraphics_PDF.zip",
                "kind": "materials",
                "filename": "005_IntCoreGraphics_PDF.zip",
                "retina": false
            }
        ],
        "authors": [
            {
                "id": 25,
                "role": "instructor",
                "user": {
                    "id": 9,
                    "external_id": "8f5ca72a-11f3-11e6-b121-2380095a6428",
                    "email": "caroline@archway.com.au",
                    "username": "Caroline",
                    "avatar_url": "https://www.gravatar.com/avatar/bfe2a965cd6136b9e2b485c959a57aff.jpg?d=https%3A%2F%2Fwolverine.raywenderlich.com%2Fv3-resources%2Fimages%2Fdefault-account-avatar_2x.png\u0026s=480",
                    "name": "Caroline Begbie"
                }
            }
        ],
        "clips": [
            {
                "id": 253,
                "provider_id": "164661205",
                "provider_url": "https://vimeo.com/164661205",
                "pretty_duration": "9m 49s",
                "clip_type": "primary_content",
                "attachments": [
                    {
                        "id": 5470,
                        "url": "https://files.betamax.raywenderlich.com/attachments/clips/253/164661205.vtt",
                        "kind": "subtitles",
                        "filename": "#164661205.vtt",
                        "retina": false
                    },
                    {
                        "id": 1735,
                        "url": "https://player.vimeo.com/external/164661205.m3u8?s=96740a5872b5272dc2e5b1a29af7b33a92e3739e\u0026oauth2_token_id=897711146",
                        "kind": "stream",
                        "filename": "#164661205",
                        "retina": false
                    },
                    {
                        "id": 24274,
                        "url": "https://player.vimeo.com/external/164661205.sd.mp4?s=dc9fad611715e5efa3e2544989877c3de083a2a5\u0026profile_id=165\u0026oauth2_token_id=897711146",
                        "kind": "sd_video_file",
                        "filename": "164661205.sd.mp4",
                        "retina": false
                    },
                    {
                        "id": 24275,
                        "url": "https://player.vimeo.com/external/164661205.hd.mp4?s=327799fd9b66832d7f7a53fa1a3d76cd8f9b902a\u0026profile_id=174\u0026oauth2_token_id=897711146",
                        "kind": "hd_video_file",
                        "filename": "164661205.hd.mp4",
                        "retina": false
                    }
                ]
            }
        ],
        "categories": [
            {
                "id": 27,
                "name": "carolus: Graphics \u0026 Animation"
            },
            {
                "id": 42,
                "name": "domain: ios"
            },
            {
                "id": 6,
                "name": "Graphics"
            }
        ]
    }
}
複製代碼

固然如今已經不行了。

{
    "error": "video not available"
}
複製代碼

youtube-dl 是能夠登陸 raywenderlich,但是又報 Vimeo 登陸錯誤。

嘆!

另闢蹊徑吧,咱們來解析一下 json 文件吧。我發現

{
    "video": {
        "name": "PDF Printing",
        "clips": [
            {
                "attachments": [
                    {
                        "id": 1735,
                        "url": "https://player.vimeo.com/external/164661205.m3u8?s=96740a5872b5272dc2e5b1a29af7b33a92e3739e\u0026oauth2_token_id=897711146",
                        "kind": "stream",
                        "filename": "#164661205",
                        "retina": false
                    }
                ]
            }
        ]
    }
}
複製代碼

找到 "kind": "stream" 內容,使用 FFmpeg 下載。

$ ffmpeg -i "https://player.vimeo.com/external/164661205.m3u8?s=96740a5872b5272dc2e5b1a29af7b33a92e3739e\u0026oauth2_token_id=897711146" "PDF Printing.mp4"
複製代碼

好的,能夠下載。可是這個下載速度也實在是太慢了吧!

放個人服務器上面下載,結果 FFmpegCPU 錯誤,我...

我在 google 上面找啊找,找啊找,仍是找不着解決方法。

實在不行,我多開幾個終端慢慢下吧。

下載資源(PDF,源碼)

經過解析上面的 json 文件,看到還有附件呢,正好前幾天有人在 B站 問我要 Ray Wenderlich Video Tutorial - Introducing Custom Controls 的源碼,我把源碼也下載下來吧。

這個實現比較簡單,直接放出源碼。

import requests
from bs4 import BeautifulSoup
import os

base_url = 'https://www.raywenderlich.com'

headers = {
                "Accept" : "application/json, text/javascript, */*; q=0.01",
                "Authorization" : "Bearer xxx",
                "Origin" : "https://www.raywenderlich.com",
                "Referer" : "https://www.raywenderlich.com/",
                "User-Agent" : "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_14_4) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/73.0.3683.103 Safari/537.36",
                "X-CSRF-Token" : "qnaS...",
                "X-Requested-With" : "XMLHttpRequest",
            }

def download(url):
    r = requests.get(url, headers=headers)

    result = raywenderlich_from_dict(r.json())
    name = result.video.name.replace('&', '').replace(':', '').replace('?', '')
    attachments = result.video.attachments

    _id = result.video.id
    _name = result.video.name.replace('&', '').replace(':', '').replace('?', '')

    for attachment in attachments:
        filename = attachment.filename
        url = attachment.url
        cmd = 'wget -O "%s. %s %s" %s' % (_id, _name, filename, url)
        os.system(cmd.encode('utf-8'))

if __name__ == '__main__':
    for i in range(2789):
        url = 'https://videos.raywenderlich.com/api/v1/videos/%s.json' % I
        print(url)
        try:
            download(url)
        except:
            print(i)
複製代碼

這樣就能夠下載全部附件了。

再戰視頻下載

次日我又從服務器運行 youtube-dl,竟然不報錯了,太棒了,趕忙下載。

不過 youtube-dl 只能下 youtube-dl 裏面的 Video Course 系列視頻,而不能下載 Screencast 單個視頻。原來 _VALID_URL 是不匹配,並且裏面的內容也不同。

是可忍,孰不可忍。

直接動手改代碼

$ git checkout -b raywenderlich_screencast
複製代碼

修改 raywenderlich.md

class RayWenderlichIE(InfoExtractor):
    _VALID_URL = r'''(?x) https?:// (?: videos\.raywenderlich\.com/courses| (?:www\.)?raywenderlich\.com )/ (?P<id>[^/]+) 複製代碼

實現內容比以前更簡單了,直接從 thumbnail 中找到 video_id 就行了,不過 thumbnail 有時候是空的,好說,正則表達式大法伺候。

因而又安心的睡覺去了。

嘀嘀嘀!原來是磁盤滿了,再哭。

好吧,我一咬牙,一跺腳,再買一個磁盤大點的服務器(就買一個月吧,實在是沒錢了)。

慢慢下載去吧。

噓。噓。噓。。。

次日磁盤又滿了,趕忙下載 BaiduPCS-Go

快點上傳啊,我求求你了。結果沒用,好的時候有好幾 M 的速度,一下子又只剩下幾 k。

最後結果:共有 2K 多的視頻,我下載了 1K 多的視頻。

總結

  1. 時間真的比金錢重要。
  2. 提早作好準備。

關注個人公衆號,AI開發日誌(AIDevLog) / iOS開發日誌(iOSDevLog)。

image

image

有須要資源的能夠聯繫我,直接共享容易封,我也在慢慢上傳 B站

有條件的請去官網 www.raywenderlich.com 觀看

相關文章
相關標籤/搜索