-
-
Save fousa/5709fb7c84e5b53dbdae508c9cb4fadc to your computer and use it in GitHub Desktop.
class FairPlayer: AVPlayer { | |
private let queue = DispatchQueue(label: "com.icapps.fairplay.queue") | |
func play(asset: AVURLAsset) { | |
// Set the resource loader delegate to this class. The `resourceLoader`'s delegate will be | |
// triggered when FairPlay handling is required. | |
asset.resourceLoader.setDelegate(self, queue: queue) | |
// Load the asset in the player. | |
let item = AVPlayerItem(asset: asset) | |
// Set the current item in this player instance. | |
replaceCurrentItem(with: item) | |
// Start playing the item. From the moment the `play` is triggered the `resourceLoader` will | |
// do the rest of the work. | |
play() | |
} | |
} | |
extension FairPlayer: AVAssetResourceLoaderDelegate { | |
func resourceLoader(_ resourceLoader: AVAssetResourceLoader, shouldWaitForLoadingOfRequestedResource loadingRequest: AVAssetResourceLoadingRequest) -> Bool { | |
// We first check if a url is set in the manifest. | |
guard let url = loadingRequest.request.url else { | |
print("๐", #function, "Unable to read the url/host data.") | |
loadingRequest.finishLoading(with: NSError(domain: "com.icapps.error", code: -1, userInfo: nil)) | |
return false | |
} | |
print("๐", #function, url) | |
// When the url is correctly found we try to load the certificate date. Watch out! For this | |
// example the certificate resides inside the bundle. But it should be preferably fetched from | |
// the server. | |
guard | |
let certificateURL = Bundle.main.url(forResource: "certificate", withExtension: "der"), | |
let certificateData = try? Data(contentsOf: certificateURL) else { | |
print("๐", #function, "Unable to read the certificate data.") | |
loadingRequest.finishLoading(with: NSError(domain: "com.icapps.error", code: -2, userInfo: nil)) | |
return false | |
} | |
// Request the Server Playback Context. | |
let contentId = "hls.icapps.com" | |
guard | |
let contentIdData = contentId.data(using: String.Encoding.utf8), | |
let spcData = try? loadingRequest.streamingContentKeyRequestData(forApp: certificateData, contentIdentifier: contentIdData, options: nil), | |
let dataRequest = loadingRequest.dataRequest else { | |
loadingRequest.finishLoading(with: NSError(domain: "com.icapps.error", code: -3, userInfo: nil)) | |
print("๐", #function, "Unable to read the SPC data.") | |
return false | |
} | |
// Request the Content Key Context from the Key Server Module. | |
let ckcURL = URL(string: "https://hls.icapps.com/ckc")! | |
var request = URLRequest(url: ckcURL) | |
request.httpMethod = "POST" | |
request.httpBody = spcData | |
let session = URLSession(configuration: URLSessionConfiguration.default) | |
let task = session.dataTask(with: request) { data, response, error in | |
if let data = data { | |
// The CKC is correctly returned and is now send to the `AVPlayer` instance so we | |
// can continue to play the stream. | |
dataRequest.respond(with: data) | |
loadingRequest.finishLoading() | |
} else { | |
print("๐", #function, "Unable to fetch the CKC.") | |
loadingRequest.finishLoading(with: NSError(domain: "com.icapps.error", code: -4, userInfo: nil)) | |
} | |
} | |
task.resume() | |
return true | |
} | |
} |
What is specifically "contentId " here?
Can anybody please throw some light?
Any luck here?
@yksingh12 @linkmanishgupta for me it was URI that is provided in m3u8 manifest, for example:
#EXT-X-KEY:METHOD=SAMPLE-AES,URI="skd://contentId",KEYFORMAT="com.apple.streamingkeydelivery",KEYFORMATVERSIONS="1"
What is specifically "contentId " here?
contentId
or AssetId
depends on your DRM supplier. I saw some implementations that uses some Identifier for the media. It could be the media code, for example. I saw some implementations using a key inside this URL skd://whatever
. Found the Docs about how to integrate with your supplier.
content id is host url "contentId = url.host"
@yksingh12 @linkmanishgupta for me it was URI that is provided in m3u8 manifest, for example:
#EXT-X-KEY:METHOD=SAMPLE-AES,URI="skd://contentId",KEYFORMAT="com.apple.streamingkeydelivery",KEYFORMATVERSIONS="1"
where could I edit this? I want to be able to test the fairplay. Thank you very much
What is specifically "contentId " here?
Can anybody please throw some light?