diff --git a/.travis.yml b/.travis.yml index f12b29a..43a889e 100644 --- a/.travis.yml +++ b/.travis.yml @@ -3,7 +3,9 @@ osx_image: xcode7.1 before_install: - brew update - brew install carthage -script: xctool -project YTVimeoExtractor.xcodeproj -scheme YTVimeoExtractor test +script: xctool -project YTVimeoExtractor.xcodeproj -scheme YTVimeoExtractor build test GCC_INSTRUMENT_PROGRAM_FLOW_ARCS=YES GCC_GENERATE_TEST_COVERAGE_FILES=YES +after_success: + - bash <(curl -s https://codecov.io/bash) before_deploy: - carthage build --no-skip-current - carthage archive YTVimeoExtractor diff --git a/CHANGELOG.md b/CHANGELOG.md index 70e1668..3219587 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,3 +1,9 @@ + +### Version 1.2.0 + +* New `HTTPLiveStreamURL` property on the `YTVimeoVideo` class. ([#38](https://github.com/lilfaf/YTVimeoExtractor/issues/38)) +* Add `YTVimeoVideoQualityMedium540` enum value on the `YTVimeoVideo` class. ([#40](https://github.com/lilfaf/YTVimeoExtractor/issues/40)) + ### Version 1.1.0 * The `streamURLs` and `thumbnailURLs` are now dictionaries that contain NSURLs ([e179efc](https://github.com/lilfaf/YTVimeoExtractor/commit/e179efc395ea8f287a9a9acb1b4b1398e92e24ce), [385ae37](https://github.com/lilfaf/YTVimeoExtractor/commit/385ae372660f52a0061b3c73f7d5df0cd5b33cc3)) diff --git a/README.md b/README.md index ebae879..95a42c0 100644 --- a/README.md +++ b/README.md @@ -3,6 +3,10 @@ [![Build Status](https://travis-ci.org/lilfaf/YTVimeoExtractor.svg?branch=master)](https://travis-ci.org/lilfaf/YTVimeoExtractor) [![Carthage compatible](https://img.shields.io/badge/Carthage-compatible-4BC51D.svg?style=flat)](https://github.com/Carthage/Carthage) +[![codecov.io](https://codecov.io/github/lilfaf/YTVimeoExtractor/coverage.svg?branch=development)](https://codecov.io/github/lilfaf/YTVimeoExtractor?branch=development) +[![GitHub release](https://img.shields.io/github/release/lilfaf/YTVimeoExtractor.svg)](https://github.com/lilfaf/YTVimeoExtractor/releases) +[![CocoaPods Platform Status](https://img.shields.io/cocoapods/p/YTVimeoExtractor.svg)](https://github.com/lilfaf/YTVimeoExtractor/releases) +[![CocoaPods Docs](https://img.shields.io/cocoapods/metrics/doc-percent/YTVimeoExtractor.svg)](http://cocoadocs.org/docsets/YTVimeoExtractor/) YTVimeoExtractor extracts the MP4 streams of Vimeo videos, which then can be used to play via a `MPMoviePlayerViewController` or `AVPlayerView`. @@ -20,7 +24,7 @@ YTVimeoExtractor extracts the MP4 streams of Vimeo videos, which then can be use | `YTVimeoExtractor` | The `YTVimeoExtractor` is the main class and its sole purpose is to fetch information about Vimeo videos. Use the two main methods `fetchVideoWithIdentifier:withReferer:completionHandler:` or `fetchVideoWithVimeoURL:withReferer:completionHandler:` to obtain video information. | | `YTVimeoExtractorOperation` | `YTVimeoExtractorOperation` is a subclass of `NSOperation` and is used to fetch and parse out information about Vimeo videos. This a low level class. Generally speaking, you should use the higher level `YTVimeoExtractor` class. | |`YTVimeoURLParser` | `YTVimeoURLParser` is used to validate and parse put Vimeo URLs. The main purpose of the class is to check if a given URL can be handled by the `YTVimeoExtractor` class.| -|`YTVimeoVideo`| `YTVimeoVideo` represents a Vimeo video. Use this class to access information about a particular video. Generally, you should not initialize this class, instead use the two main methods of the `YTVimeoExtractor` class.| +|`YTVimeoVideo`| `YTVimeoVideo` represents a Vimeo video. Use this class to access information about a particular video. Do not manually initialize a `YTVimeoVideo` object. Using the `-init` method will throw an exception, instead use the two main methods of the `YTVimeoExtractor` class to obtain a `YTVimeoVideo` object. | ## Installation diff --git a/YTVimeoExtractor Demo/YTVimeoExtractor OS X Demo/ViewController.m b/YTVimeoExtractor Demo/YTVimeoExtractor OS X Demo/ViewController.m index df4d90c..659118f 100644 --- a/YTVimeoExtractor Demo/YTVimeoExtractor OS X Demo/ViewController.m +++ b/YTVimeoExtractor Demo/YTVimeoExtractor OS X Demo/ViewController.m @@ -35,7 +35,6 @@ - (IBAction)playAction:(id)sender { //Will get the highest available quality. NSURL *highQualityURL = [video highestQualityStreamURL]; - AVPlayer *player = [[AVPlayer alloc]initWithURL:highQualityURL]; self.playerView.player = player; diff --git a/YTVimeoExtractor.framework.zip b/YTVimeoExtractor.framework.zip index 03f2116..47d39f7 100644 Binary files a/YTVimeoExtractor.framework.zip and b/YTVimeoExtractor.framework.zip differ diff --git a/YTVimeoExtractor.xcodeproj/project.pbxproj b/YTVimeoExtractor.xcodeproj/project.pbxproj index c04ffac..544dca6 100644 --- a/YTVimeoExtractor.xcodeproj/project.pbxproj +++ b/YTVimeoExtractor.xcodeproj/project.pbxproj @@ -7,6 +7,7 @@ objects = { /* Begin PBXBuildFile section */ + 019F95101C984EF400E2A405 /* YTVimeoVideo+Private.h in Headers */ = {isa = PBXBuildFile; fileRef = 019F950F1C984EF400E2A405 /* YTVimeoVideo+Private.h */; settings = {ATTRIBUTES = (Private, ); }; }; 01AC343A1C1F21290015CAA6 /* YTVimeoExtractor.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 01AC342F1C1F21280015CAA6 /* YTVimeoExtractor.framework */; }; 01AC34521C1F21750015CAA6 /* YTVimeoError.h in Headers */ = {isa = PBXBuildFile; fileRef = 01AC34491C1F21750015CAA6 /* YTVimeoError.h */; settings = {ATTRIBUTES = (Public, ); }; }; 01AC34531C1F21750015CAA6 /* YTVimeoExtractor.h in Headers */ = {isa = PBXBuildFile; fileRef = 01AC344A1C1F21750015CAA6 /* YTVimeoExtractor.h */; settings = {ATTRIBUTES = (Public, ); }; }; @@ -36,6 +37,7 @@ /* End PBXContainerItemProxy section */ /* Begin PBXFileReference section */ + 019F950F1C984EF400E2A405 /* YTVimeoVideo+Private.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = "YTVimeoVideo+Private.h"; sourceTree = ""; }; 01AC342F1C1F21280015CAA6 /* YTVimeoExtractor.framework */ = {isa = PBXFileReference; explicitFileType = wrapper.framework; includeInIndex = 0; path = YTVimeoExtractor.framework; sourceTree = BUILT_PRODUCTS_DIR; }; 01AC34341C1F21290015CAA6 /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = ""; }; 01AC34391C1F21290015CAA6 /* YTVimeoExtractorTests.xctest */ = {isa = PBXFileReference; explicitFileType = wrapper.cfbundle; includeInIndex = 0; path = YTVimeoExtractorTests.xctest; sourceTree = BUILT_PRODUCTS_DIR; }; @@ -106,6 +108,7 @@ 01AC344F1C1F21750015CAA6 /* YTVimeoURLParser.m */, 01AC34501C1F21750015CAA6 /* YTVimeoVideo.h */, 01AC34511C1F21750015CAA6 /* YTVimeoVideo.m */, + 019F950F1C984EF400E2A405 /* YTVimeoVideo+Private.h */, 01AC34341C1F21290015CAA6 /* Info.plist */, ); path = YTVimeoExtractor; @@ -136,6 +139,7 @@ 01AC34571C1F21750015CAA6 /* YTVimeoURLParser.h in Headers */, 01AC34531C1F21750015CAA6 /* YTVimeoExtractor.h in Headers */, 01AC34551C1F21750015CAA6 /* YTVimeoExtractorOperation.h in Headers */, + 019F95101C984EF400E2A405 /* YTVimeoVideo+Private.h in Headers */, 01AC34591C1F21750015CAA6 /* YTVimeoVideo.h in Headers */, ); runOnlyForDeploymentPostprocessing = 0; diff --git a/YTVimeoExtractor/Info.plist b/YTVimeoExtractor/Info.plist index 6be6456..323ee7e 100644 --- a/YTVimeoExtractor/Info.plist +++ b/YTVimeoExtractor/Info.plist @@ -15,11 +15,11 @@ CFBundlePackageType FMWK CFBundleShortVersionString - 1.1.0 + 1.2.0 CFBundleSignature ???? CFBundleVersion - 1.1.0 + 1.2.0 NSHumanReadableCopyright Copyright © 2015 Louis Larpin. All rights reserved. NSPrincipalClass diff --git a/YTVimeoExtractor/YTVimeoError.h b/YTVimeoExtractor/YTVimeoError.h index 32fa88b..669d992 100644 --- a/YTVimeoExtractor/YTVimeoError.h +++ b/YTVimeoExtractor/YTVimeoError.h @@ -1,6 +1,6 @@ // // YTVimeoError.h -// Sample +// YTVimeoExtractor // // Created by Soneé Delano John on 11/28/15. // Copyright © 2015 Louis Larpin. All rights reserved. diff --git a/YTVimeoExtractor/YTVimeoExtractor.h b/YTVimeoExtractor/YTVimeoExtractor.h index 1c01fbb..224d985 100644 --- a/YTVimeoExtractor/YTVimeoExtractor.h +++ b/YTVimeoExtractor/YTVimeoExtractor.h @@ -5,6 +5,12 @@ // Created by Louis Larpin on 18/02/13. // +#if !__has_feature(nullability) +#define NS_ASSUME_NONNULL_BEGIN +#define NS_ASSUME_NONNULL_END +#define nullable +#endif + #import #import "YTVimeoError.h" #import "YTVimeoExtractorOperation.h" @@ -42,7 +48,7 @@ NS_ASSUME_NONNULL_BEGIN * @param referer The referer, if the Vimeo video has domain-level restrictions. If this value is `nil` then a default one will be used. * @param completionHandler A block to execute when the extraction process is finished, which is executed on the main thread. If the completion handler is nil, this method throws an exception. The block has, two parameters a `YTVimeoVideo` object if, the operation was completed successfully and a `NSError` object describing the network or parsing error that may have occurred. */ --(void)fetchVideoWithIdentifier:(NSString *_Nonnull)videoIdentifier withReferer:(NSString *__nullable)referer completionHandler:(void (^_Nonnull)(YTVimeoVideo * __nullable video, NSError * __nullable error))completionHandler; +-(void)fetchVideoWithIdentifier:(NSString *)videoIdentifier withReferer:(NSString *__nullable)referer completionHandler:(void (^)(YTVimeoVideo * __nullable video, NSError * __nullable error))completionHandler; /** * Starts an asynchronous operation for the specified video URL, and referer, then calls a handler upon completion. @@ -51,7 +57,7 @@ NS_ASSUME_NONNULL_BEGIN * @param referer The referer, if the Vimeo video has domain-level restrictions. If this value is `nil` then a default one will be used. * @param completionHandler A block to execute when the extraction process is finished, which is executed on the main thread. If the completion handler is nil, this method throws an exception. The block has, two parameters a `YTVimeoVideo` object if, the operation was completed successfully and a `NSError` object describing the network or parsing error that may have occurred. */ --(void)fetchVideoWithVimeoURL:(NSString *_Nonnull)videoURL withReferer:(NSString *__nullable)referer completionHandler:(void (^_Nonnull)(YTVimeoVideo * __nullable video, NSError * __nullable error))completionHandler; +-(void)fetchVideoWithVimeoURL:(NSString *)videoURL withReferer:(NSString *__nullable)referer completionHandler:(void (^)(YTVimeoVideo * __nullable video, NSError * __nullable error))completionHandler; @end NS_ASSUME_NONNULL_END diff --git a/YTVimeoExtractor/YTVimeoExtractor.m b/YTVimeoExtractor/YTVimeoExtractor.m index 66b9ee7..85e09d2 100644 --- a/YTVimeoExtractor/YTVimeoExtractor.m +++ b/YTVimeoExtractor/YTVimeoExtractor.m @@ -26,8 +26,11 @@ +(instancetype)sharedExtractor{ return sharedExtractor; } -- (id)init { - if (self = [super init]) { +- (instancetype)init { + + self = [super init]; + + if (self) { _extractorOperationQueue = [[NSOperationQueue alloc]init]; if ([_extractorOperationQueue respondsToSelector:@selector(qualityOfService)]) { diff --git a/YTVimeoExtractor/YTVimeoExtractorOperation.h b/YTVimeoExtractor/YTVimeoExtractorOperation.h index a51153b..984ab05 100644 --- a/YTVimeoExtractor/YTVimeoExtractorOperation.h +++ b/YTVimeoExtractor/YTVimeoExtractorOperation.h @@ -1,14 +1,22 @@ // // YTVimeoExtractorOperation.h -// Sample +// YTVimeoExtractor // // Created by Soneé Delano John on 11/28/15. // Copyright © 2015 Louis Larpin. All rights reserved. // +#if !__has_feature(nullability) +#define NS_ASSUME_NONNULL_BEGIN +#define NS_ASSUME_NONNULL_END +#define nullable +#endif + #import #import "YTVimeoVideo.h" +NS_ASSUME_NONNULL_BEGIN + /** `YTVimeoExtractorOperation` is a subclass of NSOperation and is used to fetch and parse out information about Vimeo videos. This a low level class. Generally, you should use the higher level `YTVimeoExtractor` class. */ @@ -27,7 +35,7 @@ * * @return An initialized `YTVimeoExtractorOperation` object. */ --(instancetype)initWithVideoIdentifier:(NSString *)videoIdentifier referer:(NSString *)videoReferer; +-(instancetype)initWithVideoIdentifier:(NSString *)videoIdentifier referer:(NSString *_Nullable)videoReferer; /** * Creates a new extractor operation with the specified Vimeo video URL and referer. * @@ -37,7 +45,7 @@ * @return An initialized `YTVimeoExtractorOperation` object. */ -- (instancetype)initWithURL:(NSString *)videoURL referer:(NSString *)videoReferer; +- (instancetype)initWithURL:(NSString *)videoURL referer:(NSString *_Nullable)videoReferer; /** * ------------------------------------ @@ -48,13 +56,15 @@ /** * Returns a `YTVimeoVideo` object if the operation finished successfully. Otherwise, will be `nil`. */ -@property (nonatomic, readonly) YTVimeoVideo *operationVideo; +@property (nonatomic, readonly, nullable) YTVimeoVideo *operationVideo; /** * The data that the operation parsed out. This value may be nil. */ -@property (nonatomic, readonly) NSDictionary *jsonDict; +@property (nonatomic, readonly, nullable) NSDictionary *jsonDict; /** * Any errors that may have occurred during the operation. Will be `nil` if the operation finished unsuccessfully. Otherwise, will return an error of the `YTVimeoVideoErrorDomain` domain. */ -@property (nonatomic, readonly) NSError *error; +@property (nonatomic, readonly, nullable) NSError *error; + +NS_ASSUME_NONNULL_END @end diff --git a/YTVimeoExtractor/YTVimeoExtractorOperation.m b/YTVimeoExtractor/YTVimeoExtractorOperation.m index 7995994..249d173 100644 --- a/YTVimeoExtractor/YTVimeoExtractorOperation.m +++ b/YTVimeoExtractor/YTVimeoExtractorOperation.m @@ -1,18 +1,16 @@ // // YTVimeoExtractorOperation.m -// Sample +// YTVimeoExtractor // // Created by Soneé Delano John on 11/28/15. // Copyright © 2015 Louis Larpin. All rights reserved. // #import "YTVimeoExtractorOperation.h" -#import "YTVimeoExtractor.h" #import "YTVimeoVideo.h" +#import "YTVimeoVideo+Private.h" #import "YTVimeoError.h" - - NSString *const YTVimeoURL = @"https://vimeo.com/%@"; NSString *const YTVimeoPlayerConfigURL = @"https://player.vimeo.com/video/%@/config"; @@ -42,8 +40,11 @@ - (instancetype) init -(instancetype)initWithVideoIdentifier:(NSString *)videoIdentifier referer:(NSString *)videoReferer{ NSParameterAssert(videoIdentifier); - if (!(self = [super init])) - return nil; + + self = [super init]; + + if (self) { + _videoIdentifier = videoIdentifier; _vimeoURL = [NSURL URLWithString:[NSString stringWithFormat:YTVimeoPlayerConfigURL, videoIdentifier]]; @@ -52,6 +53,8 @@ -(instancetype)initWithVideoIdentifier:(NSString *)videoIdentifier referer:(NSSt _referer = videoReferer; } else { _referer = [NSString stringWithFormat:YTVimeoURL, videoIdentifier]; + } + } return self; diff --git a/YTVimeoExtractor/YTVimeoURLParser.h b/YTVimeoExtractor/YTVimeoURLParser.h index bad036b..8049bb5 100644 --- a/YTVimeoExtractor/YTVimeoURLParser.h +++ b/YTVimeoExtractor/YTVimeoURLParser.h @@ -1,6 +1,6 @@ // // YTVimeoURLParser.h -// Sample +// YTVimeoExtractor // // Created by Soneé Delano John on 12/2/15. // Copyright © 2015 Louis Larpin. All rights reserved. diff --git a/YTVimeoExtractor/YTVimeoURLParser.m b/YTVimeoExtractor/YTVimeoURLParser.m index c746353..f8f8549 100644 --- a/YTVimeoExtractor/YTVimeoURLParser.m +++ b/YTVimeoExtractor/YTVimeoURLParser.m @@ -1,6 +1,6 @@ // // YTVimeoURLParser.m -// Sample +// YTVimeoExtractor // // Created by Soneé Delano John on 12/2/15. // Copyright © 2015 Louis Larpin. All rights reserved. diff --git a/YTVimeoExtractor/YTVimeoVideo+Private.h b/YTVimeoExtractor/YTVimeoVideo+Private.h new file mode 100644 index 0000000..0cf7a42 --- /dev/null +++ b/YTVimeoExtractor/YTVimeoVideo+Private.h @@ -0,0 +1,35 @@ +// +// YTVimeoVideo+Private.h +// YTVimeoExtractor +// +// Created by Soneé John on 3/15/16. +// Copyright © 2016 Louis Larpin. All rights reserved. +// +#if !__has_feature(nullability) +#define NS_ASSUME_NONNULL_BEGIN +#define NS_ASSUME_NONNULL_END +#define nullable +#endif + +#import "YTVimeoVideo.h" +NS_ASSUME_NONNULL_BEGIN +@interface YTVimeoVideo () + +/** + * Initializes a `YTVimeoVideo` video object with the specified identifier and info. + * + * @param identifier A Vimeo video identifier. This parameter should not be `nil` + * @param info The dictionary that the class will use to parse out the data. This parameter should not be `nil` + * + * @return A newly initialized `YTVimeoVideo` object. + */ +- (instancetype) initWithIdentifier:(NSString *)identifier info:(NSDictionary *)info; +/** + * Starts extracting information about the Vimeo video. + * + * @param completionHandler A block to execute when the extraction process is finished. The completion handler is executed on the main thread. If the completion handler is nil, this method throws an exception. + */ +- (void)extractVideoInfoWithCompletionHandler:(void (^)(NSError *error))completionHandler; + +NS_ASSUME_NONNULL_END +@end \ No newline at end of file diff --git a/YTVimeoExtractor/YTVimeoVideo.h b/YTVimeoExtractor/YTVimeoVideo.h index ae93b7f..5ce7494 100644 --- a/YTVimeoExtractor/YTVimeoVideo.h +++ b/YTVimeoExtractor/YTVimeoVideo.h @@ -1,12 +1,21 @@ // // YTVimeoVideo.h -// Sample +// YTVimeoExtractor // // Created by Soneé Delano John on 11/28/15. // Copyright © 2015 Louis Larpin. All rights reserved. // +#if !__has_feature(nullability) +#define NS_ASSUME_NONNULL_BEGIN +#define NS_ASSUME_NONNULL_END +#define nullable +#endif + #import + +NS_ASSUME_NONNULL_BEGIN + /** * The various thumbnails of Vimeo videos. These values are used as keys in the `<[YTVimeoVideo thumbnailURLs]>` property. */ @@ -40,6 +49,10 @@ typedef NS_ENUM(NSUInteger, YTVimeoVideoQuality) { * A stream URL for a video of medium quality with a height of 480 pixels. */ YTVimeoVideoQualityMedium480 = 480, + /** + * A stream URL for a video of medium quality with a height of 540 pixels. + */ + YTVimeoVideoQualityMedium540 = 540, /** * A stream URL for a video of HD quality with a height of 720 pixels. */ @@ -50,38 +63,22 @@ typedef NS_ENUM(NSUInteger, YTVimeoVideoQuality) { YTVimeoVideoQualityHD1080 = 1080, }; -/// YTVimeoVideo represents a Vimeo video. Use this class to access information about a particular video. Generally, you should not initialize this class, instead use the `<-[YTVimeoExtractor fetchVideoWithVimeoURL:withReferer:completionHandler:]>` or `<-[YTVimeoExtractor fetchVideoWithIdentifier:withReferer:completionHandler:]>` methods to get a `YTVimeoVideo` object. -@interface YTVimeoVideo : NSObject - /** - * ------------------ - * @name Initializing - * ------------------ - */ +`YTVimeoVideo`represents a YouTube video. Use this class to access information about a particular video. -/** - * Initializes a `YTVimeoVideo` video object with the specified identifier and info. - * - * @param identifier A Vimeo video identifier. This parameter should not be `nil` - * @param info The dictionary that the class will use to parse out the data. This parameter should not be `nil` - * - * @return A newly initialized `YTVimeoVideo` object. - */ -- (nullable instancetype) initWithIdentifier:(NSString *_Nonnull)identifier info:(NSDictionary *_Nonnull)info; +@see `YTVimeoExtractor` to obtain a `YTVimeoVideo` object. -/** - * ---------------------------- - * @name Extracting Information - * ---------------------------- - */ +@warning Do not manually initialize a `YTVimeoVideo` object. Using the `-init` method will throw an exception. -/** - * Starts extracting information about the Vimeo video. - * - * @param completionHandler A block to execute when the extraction process is finished. The completion handler is executed on the main thread. If the completion handler is nil, this method throws an exception. - */ -- (void)extractVideoInfoWithCompletionHandler:(void (^_Nonnull)(NSError * __nullable error))completionHandler; +## Subclassing Notes +It is very important that you do not create a subclass of `YTVimeoVideo` + +## NSObject Notes + +`YTVimeoVideo` uses the `identifier` to determine the equality between two `YTVimeoVideo` objects. Calling `-isEqual:` on two `YTVimeoVideo` objects that contain the same identifiers will return `YES`, otherwise `-isEqual:` will return `NO`. +*/ +@interface YTVimeoVideo : NSObject /** * ---------------------------- * @name Accessing Information @@ -90,11 +87,11 @@ typedef NS_ENUM(NSUInteger, YTVimeoVideoQuality) { /** * The Vimeo video identifier. */ -@property (nonatomic, readonly) NSString *__nullable identifier; +@property (nonatomic, readonly) NSString *identifier; /** * The title of the video. */ -@property (nonatomic, readonly) NSString *__nullable title; +@property (nonatomic, readonly) NSString *title; /** * The duration of the video in seconds. */ @@ -104,29 +101,44 @@ typedef NS_ENUM(NSUInteger, YTVimeoVideoQuality) { * A `NSDictionary` object that contains the various stream URLs. * @see YTVimeoVideoQuality */ -@property (nonatomic, readonly) NSDictionary *__nullable streamURLs; +#if __has_feature(objc_generics) +@property (nonatomic, readonly) NSDictionary *streamURLs; +#else +@property (nonatomic, readonly) NSDictionary *streamURLs; +#endif + /** * A `NSDictionary` object that contains the various thumbnail URLs. * @see YTVimeoVideoThumbnailQuality */ +#if __has_feature(objc_generics) @property (nonatomic, readonly) NSDictionary *__nullable thumbnailURLs; +#else +@property (nonatomic, readonly) NSDictionary *thumbnailURLs; +#endif + /** * A `NSDictionary` object that contains all the metadata about the video. */ -@property (nonatomic, readonly) NSDictionary *__nullable metaData; +@property (nonatomic, readonly) NSDictionary *metaData; /** - * Get the highest quality stream URL. + * Extracts the highest quality stream URL. * * @see YTVimeoVideoQuality * @return The highest quality stream URL. */ --(NSURL *__nullable)highestQualityStreamURL; +-(NSURL *)highestQualityStreamURL; /** - * Get the lowest quality stream URL. + * Extracts the lowest quality stream URL. * * @see YTVimeoVideoQuality * @return The lowest quality stream URL. */ --(NSURL *__nullable)lowestQualityStreamURL; +-(NSURL *)lowestQualityStreamURL; +/** + * The HTTP Live Stream URL for the video. + */ +@property (nonatomic, readonly, nullable) NSURL *HTTPLiveStreamURL; +NS_ASSUME_NONNULL_END @end diff --git a/YTVimeoExtractor/YTVimeoVideo.m b/YTVimeoExtractor/YTVimeoVideo.m index 3dd9e4f..5ba744f 100644 --- a/YTVimeoExtractor/YTVimeoVideo.m +++ b/YTVimeoExtractor/YTVimeoVideo.m @@ -1,6 +1,6 @@ // // YTVimeoVideo.m -// Sample +// YTVimeoExtractor // // Created by Soneé Delano John on 11/28/15. // Copyright © 2015 Louis Larpin. All rights reserved. @@ -8,7 +8,7 @@ #import "YTVimeoVideo.h" #import "YTVimeoError.h" - +#import "YTVimeoVideo+Private.h" @interface YTVimeoVideo () @property (nonatomic, strong) NSDictionary *infoDict; @@ -27,11 +27,15 @@ - (instancetype)initWithIdentifier:(NSString *)identifier info:(NSDictionary *)i NSParameterAssert(identifier); NSParameterAssert(info); - if (!(self = [super init])) - return nil; // LCOV_EXCL_LINE + self = [super init]; + + if (self) { + _infoDict = [info copy]; _identifier = identifier; - + + } + return self; } #pragma mark - @@ -67,6 +71,7 @@ - (void)extractVideoInfoWithCompletionHandler:(void (^)(NSError *error))completi NSMutableDictionary *streamURLs = [NSMutableDictionary new]; NSMutableDictionary *thumbnailURLs = [NSMutableDictionary new]; + _HTTPLiveStreamURL = [NSURL URLWithString:[self.infoDict valueForKeyPath:@"request.files.hls.url"]]; for (NSDictionary *info in filesInfo) { @@ -113,19 +118,30 @@ - (void)extractVideoInfoWithCompletionHandler:(void (^)(NSError *error))completi #pragma mark - -(NSURL *)highestQualityStreamURL{ - NSURL *url = self.streamURLs[@(YTVimeoVideoQualityHD1080)] ?: self.streamURLs[@(YTVimeoVideoQualityHD720)] ?: self.streamURLs [@(YTVimeoVideoQualityMedium480)]?: self.streamURLs[@(YTVimeoVideoQualityMedium360)]?:self.streamURLs[@(YTVimeoVideoQualityLow270)]; + NSURL *url = self.streamURLs[@(YTVimeoVideoQualityHD1080)] ?: self.streamURLs[@(YTVimeoVideoQualityHD720)]?: self.streamURLs[@(YTVimeoVideoQualityMedium540)]?: self.streamURLs [@(YTVimeoVideoQualityMedium480)]?: self.streamURLs[@(YTVimeoVideoQualityMedium360)]?:self.streamURLs[@(YTVimeoVideoQualityLow270)]; return url; } -(NSURL *)lowestQualityStreamURL{ - NSURL *url = self.streamURLs[@(YTVimeoVideoQualityLow270)] ?: self.streamURLs[@(YTVimeoVideoQualityMedium360)] ?: self.streamURLs [@(YTVimeoVideoQualityMedium480)]?: self.streamURLs[@(YTVimeoVideoQualityHD720)]?:self.streamURLs[@(YTVimeoVideoQualityHD1080)]; + NSURL *url = self.streamURLs[@(YTVimeoVideoQualityLow270)] ?: self.streamURLs[@(YTVimeoVideoQualityMedium360)] ?: self.streamURLs [@(YTVimeoVideoQualityMedium480)]?: self.streamURLs[@(YTVimeoVideoQualityMedium540)]?: self.streamURLs[@(YTVimeoVideoQualityHD720)]?:self.streamURLs[@(YTVimeoVideoQualityHD1080)]; return url; } #pragma mark - NSObject + +- (BOOL) isEqual:(id)object +{ + return [object isKindOfClass:[YTVimeoVideo class]] && [((YTVimeoVideo *)object).identifier isEqual:self.identifier]; +} + +-(NSUInteger)hash{ + + return self.identifier.hash; +} + - (NSString *) description { return [NSString stringWithFormat:@"[%@] %@", self.identifier, self.title]; diff --git a/YTVimeoExtractorTests/YTVimeoExtractorOperationTestCase.m b/YTVimeoExtractorTests/YTVimeoExtractorOperationTestCase.m index 6a762d8..9f7b8a9 100644 --- a/YTVimeoExtractorTests/YTVimeoExtractorOperationTestCase.m +++ b/YTVimeoExtractorTests/YTVimeoExtractorOperationTestCase.m @@ -1,6 +1,6 @@ // // YTVimeoExtractorOperationTestCase.m -// Sample +// YTVimeoExtractor // // Created by Soneé John on 12/7/15. // Copyright © 2015 Louis Larpin. All rights reserved. diff --git a/YTVimeoExtractorTests/YTVimeoExtractorTestCase.m b/YTVimeoExtractorTests/YTVimeoExtractorTestCase.m index 1cbda59..536546e 100644 --- a/YTVimeoExtractorTests/YTVimeoExtractorTestCase.m +++ b/YTVimeoExtractorTests/YTVimeoExtractorTestCase.m @@ -1,6 +1,6 @@ // // YTVimeoExtractorTestCase.m -// Sample +// YTVimeoExtractor // // Created by Soneé John on 12/13/15. // Copyright © 2015 Louis Larpin. All rights reserved. diff --git a/YTVimeoExtractorTests/YTVimeoURLParserTestCase.m b/YTVimeoExtractorTests/YTVimeoURLParserTestCase.m index 9480e52..fe812ee 100644 --- a/YTVimeoExtractorTests/YTVimeoURLParserTestCase.m +++ b/YTVimeoExtractorTests/YTVimeoURLParserTestCase.m @@ -1,6 +1,6 @@ // // YTVimeoURLParserTestCase.m -// Sample +// YTVimeoExtractor // // Created by Soneé Delano John on 12/2/15. // Copyright © 2015 Louis Larpin. All rights reserved. diff --git a/YTVimeoExtractorTests/YTVimeoVideoTestCase.m b/YTVimeoExtractorTests/YTVimeoVideoTestCase.m index f46a28b..eceb4c8 100644 --- a/YTVimeoExtractorTests/YTVimeoVideoTestCase.m +++ b/YTVimeoExtractorTests/YTVimeoVideoTestCase.m @@ -1,6 +1,6 @@ // // YTVimeoVideoTestCase.m -// Sample +// YTVimeoExtractor // // Created by Soneé Delano John on 12/2/15. // Copyright © 2015 Louis Larpin. All rights reserved. @@ -10,6 +10,7 @@ #import "YTVimeoVideo.h" #import "YTVimeoExtractorOperation.h" #import "YTVimeoError.h" +#import "YTVimeoVideo+Private.h" @interface YTVimeoVideoTestCase : XCTestCase @end @@ -187,4 +188,33 @@ -(void)testPrivateVideo{ [self waitForExpectationsWithTimeout:15 handler:nil]; } +#pragma mark - + +-(void)testEquality{ + + __weak XCTestExpectation *expectation = [self expectationWithDescription:@""]; + + YTVimeoExtractorOperation *operation = [[YTVimeoExtractorOperation alloc]initWithVideoIdentifier:@"148222047" referer:nil]; + + operation.completionBlock = ^{ +#pragma clang diagnostic push +#pragma clang diagnostic ignored "-Warc-retain-cycles" + + YTVimeoVideo *video1 = [[YTVimeoVideo alloc]initWithIdentifier:@"148222047" info:operation.jsonDict]; + YTVimeoVideo *video2 = [[YTVimeoVideo alloc]initWithIdentifier:@"148222047" info:operation.jsonDict]; + + XCTAssertEqualObjects(video1, video2, @"Both objects should be equal."); + [expectation fulfill]; + + +#pragma clang diagnostic pop + + + }; + + [operation start]; + + [self waitForExpectationsWithTimeout:15 handler:nil]; +} + @end