Skip to content

Instantly share code, notes, and snippets.

@ApolloZhu
Created November 22, 2018 03:50
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save ApolloZhu/5031907931fc6bc031a7013bd8075029 to your computer and use it in GitHub Desktop.
Save ApolloZhu/5031907931fc6bc031a7013bd8075029 to your computer and use it in GitHub Desktop.
Get the first 250 or 1000 followers of a user on bilibili
let id: Int = /*Replace with your bilibili user id*/
// You can simply copy paste the entire cookie, but the following is the minimum:
// If id is different from DedeUserID (i.e. you don't own such account), this doesn't matter
let cookie = "DedeUserID=XXXX;DedeUserID__ckMd5=XXXXXXXXXXXXXXXX;SESSDATA=XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX;"
///////////////////////////////////////
// Code //
///////////////////////////////////////
import Foundation
struct User: Codable {
let mid: Int
let uname: String
}
struct Wrapper: Codable {
let data: Data
struct Data: Codable {
let list: [User]
let total: Int
}
}
func fetchFollowersOfUser(
_ id: Int = id, page: Int, pageSize: Int = 50,
then process: @escaping (_ total: Int, _ list: [User]) -> Void
) {
let url = URL(string: "http://api.bilibili.com/x/relation/followers?vmid=\(id)&pn=\(page)&ps=\(pageSize)")
var request = URLRequest(url: url!)
request.addValue(cookie, forHTTPHeaderField: "Cookie")
URLSession.shared.dataTask(with: request) { (data, _, error) in
guard let data = data else { fatalError(error?.localizedDescription ?? "Failed") }
do {
let wrapped = try JSONDecoder().decode(Wrapper.self, from: data)
process(wrapped.data.total, wrapped.data.list)
} catch {
print(String(data: data, encoding: .utf8)!)
process(0, [])
}
}.resume()
}
var allFollowers = [User]()
var page = 1
func run() {
fetchFollowersOfUser(page: page) { (total, list) in
if list.count == 50 {
allFollowers += list
page += 1
print("\(allFollowers.count)/\(total)")
run()
} else {
try! allFollowers.sorted {
$0.mid < $1.mid
}.reduce("") {
"\($0)\($1.mid) \($1.uname)\n"
}.write(toFile: "\(id).txt", atomically: true, encoding: .utf8)
exit(0)
}
}
}
run()
RunLoop.current.run()
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment