1192 lines
56 KiB
Objective-C
1192 lines
56 KiB
Objective-C
//
|
|
// STPPaymentCardTextFieldTest.m
|
|
// Stripe
|
|
//
|
|
// Created by Jack Flintermann on 8/26/15.
|
|
// Copyright (c) 2015 Stripe, Inc. All rights reserved.
|
|
//
|
|
|
|
@import UIKit;
|
|
@import XCTest;
|
|
@import OCMock;
|
|
@import StripeCoreTestUtils;
|
|
|
|
#import "STPFixtures.h"
|
|
|
|
|
|
#import "STPTestingAPIClient.h"
|
|
|
|
@interface STPPaymentCardTextField (Testing)
|
|
@property (nonatomic, readwrite, weak) UIImageView *brandImageView;
|
|
@property (nonatomic, readwrite, weak) STPFormTextField *numberField;
|
|
@property (nonatomic, readwrite, weak) STPFormTextField *expirationField;
|
|
@property (nonatomic, readwrite, weak) STPFormTextField *cvcField;
|
|
@property (nonatomic, readwrite, weak) STPFormTextField *postalCodeField;
|
|
@property (nonatomic, readonly, weak) STPFormTextField *currentFirstResponderField;
|
|
@property (nonatomic, readwrite, strong) STPPaymentCardTextFieldViewModel *viewModel;
|
|
@property (nonatomic, copy) NSNumber *focusedTextFieldForLayout;
|
|
+ (UIImage *)cvcImageForCardBrand:(STPCardBrand)cardBrand;
|
|
+ (UIImage *)brandImageForCardBrand:(STPCardBrand)cardBrand;
|
|
@end
|
|
|
|
/**
|
|
Class that implements STPPaymentCardTextFieldDelegate and uses a block for each delegate method.
|
|
*/
|
|
@interface PaymentCardTextFieldBlockDelegate: NSObject <STPPaymentCardTextFieldDelegate>
|
|
@property (nonatomic, strong, nullable) void (^didChange)(STPPaymentCardTextField *);
|
|
@property (nonatomic, strong, nullable) void (^willEndEditingForReturn)(STPPaymentCardTextField *);
|
|
@property (nonatomic, strong, nullable) void (^didEndEditing)(STPPaymentCardTextField *);
|
|
// add more properties for other delegate methods as this test needs them
|
|
@end
|
|
@implementation PaymentCardTextFieldBlockDelegate
|
|
- (void)paymentCardTextFieldDidChange:(STPPaymentCardTextField *)textField {
|
|
if (self.didChange) {
|
|
self.didChange(textField);
|
|
}
|
|
}
|
|
- (void)paymentCardTextFieldWillEndEditingForReturn:(STPPaymentCardTextField *)textField {
|
|
if (self.willEndEditingForReturn) {
|
|
self.willEndEditingForReturn(textField);
|
|
}
|
|
}
|
|
- (void)paymentCardTextFieldDidEndEditing:(STPPaymentCardTextField *)textField {
|
|
if (self.didEndEditing) {
|
|
self.didEndEditing(textField);
|
|
}
|
|
}
|
|
@end
|
|
|
|
|
|
@interface STPPaymentCardTextFieldTest : XCTestCase
|
|
@end
|
|
|
|
// N.B. It is eexpected for setting the card params to generate API response errors
|
|
// because we are calling to the card metadata service without configuration STPAPIClient
|
|
@implementation STPPaymentCardTextFieldTest
|
|
|
|
+ (void)setUp {
|
|
[super setUp];
|
|
[[STPAPIClient sharedClient] setPublishableKey:STPTestingDefaultPublishableKey];
|
|
}
|
|
|
|
- (void)testIntrinsicContentSize {
|
|
STPPaymentCardTextField *textField = [STPPaymentCardTextField new];
|
|
|
|
UIFont *iOS8SystemFont = [UIFont fontWithName:@"HelveticaNeue" size:18];
|
|
textField.font = iOS8SystemFont;
|
|
XCTAssertEqualWithAccuracy(textField.intrinsicContentSize.height, 44, 0.1);
|
|
XCTAssertEqualWithAccuracy(textField.intrinsicContentSize.width, 247, 0.1);
|
|
|
|
UIFont *iOS9SystemFont = [UIFont systemFontOfSize:18];;
|
|
textField.font = iOS9SystemFont;
|
|
XCTAssertEqualWithAccuracy(textField.intrinsicContentSize.height, 44, 0.1);
|
|
XCTAssertEqualWithAccuracy(textField.intrinsicContentSize.width, 259, 1.0);
|
|
|
|
textField.font = [UIFont fontWithName:@"Avenir" size:44];
|
|
if (@available(iOS 13.0, *)) {
|
|
XCTAssertEqualWithAccuracy(textField.intrinsicContentSize.height, 62, 0.1);
|
|
} else {
|
|
XCTAssertEqualWithAccuracy(textField.intrinsicContentSize.height, 61, 0.1);
|
|
}
|
|
XCTAssertEqualWithAccuracy(textField.intrinsicContentSize.width, 478, 0.1);
|
|
}
|
|
|
|
- (void)testSetCard_numberUnknown {
|
|
STPPaymentCardTextField *sut = [STPPaymentCardTextField new];
|
|
STPPaymentMethodCardParams *card = [STPPaymentMethodCardParams new];
|
|
NSString *number = @"1";
|
|
card.number = number;
|
|
STPPaymentMethodParams *params = [[STPPaymentMethodParams alloc] initWithCard:card billingDetails:nil metadata:nil];
|
|
[sut setPaymentMethodParams:params];
|
|
|
|
NSData *imgData = UIImagePNGRepresentation(sut.brandImageView.image);
|
|
NSData *expectedImgData = UIImagePNGRepresentation([STPPaymentCardTextField errorImageForCardBrand:STPCardBrandUnknown]);
|
|
|
|
XCTAssertNotNil(sut.focusedTextFieldForLayout);
|
|
XCTAssertTrue(sut.focusedTextFieldForLayout.integerValue == STPCardFieldTypeNumber);
|
|
XCTAssertTrue([expectedImgData isEqualToData:imgData]);
|
|
XCTAssertEqualObjects(sut.numberField.text, number);
|
|
XCTAssertEqual(sut.expirationField.text.length, (NSUInteger)0);
|
|
XCTAssertEqual(sut.cvcField.text.length, (NSUInteger)0);
|
|
XCTAssertNil(sut.currentFirstResponderField);
|
|
}
|
|
|
|
- (void)testSetCard_expiration {
|
|
STPPaymentCardTextField *sut = [STPPaymentCardTextField new];
|
|
STPPaymentMethodCardParams *card = [STPPaymentMethodCardParams new];
|
|
card.expMonth = @(10);
|
|
card.expYear = @(99);
|
|
STPPaymentMethodParams *params = [[STPPaymentMethodParams alloc] initWithCard:card billingDetails:nil metadata:nil];
|
|
[sut setPaymentMethodParams:params];
|
|
NSData *imgData = UIImagePNGRepresentation(sut.brandImageView.image);
|
|
NSData *expectedImgData = UIImagePNGRepresentation([STPPaymentCardTextField brandImageForCardBrand:STPCardBrandUnknown]);
|
|
|
|
XCTAssertNotNil(sut.focusedTextFieldForLayout);
|
|
XCTAssertTrue(sut.focusedTextFieldForLayout.integerValue == STPCardFieldTypeNumber);
|
|
XCTAssertTrue([expectedImgData isEqualToData:imgData]);
|
|
XCTAssertEqual(sut.numberField.text.length, (NSUInteger)0);
|
|
XCTAssertEqualObjects(sut.expirationField.text, @"10/99");
|
|
XCTAssertEqual(sut.cvcField.text.length, (NSUInteger)0);
|
|
XCTAssertNil(sut.currentFirstResponderField);
|
|
XCTAssertFalse(sut.isValid);
|
|
}
|
|
|
|
- (void)testSetCard_CVC {
|
|
STPPaymentCardTextField *sut = [STPPaymentCardTextField new];
|
|
STPPaymentMethodCardParams *card = [STPPaymentMethodCardParams new];
|
|
NSString *cvc = @"123";
|
|
card.cvc = cvc;
|
|
STPPaymentMethodParams *params = [[STPPaymentMethodParams alloc] initWithCard:card billingDetails:nil metadata:nil];
|
|
[sut setPaymentMethodParams:params];
|
|
NSData *imgData = UIImagePNGRepresentation(sut.brandImageView.image);
|
|
NSData *expectedImgData = UIImagePNGRepresentation([STPPaymentCardTextField brandImageForCardBrand:STPCardBrandUnknown]);
|
|
|
|
XCTAssertNotNil(sut.focusedTextFieldForLayout);
|
|
XCTAssertTrue(sut.focusedTextFieldForLayout.integerValue == STPCardFieldTypeNumber);
|
|
XCTAssertTrue([expectedImgData isEqualToData:imgData]);
|
|
XCTAssertEqual(sut.numberField.text.length, (NSUInteger)0);
|
|
XCTAssertEqual(sut.expirationField.text.length, (NSUInteger)0);
|
|
XCTAssertEqualObjects(sut.cvcField.text, cvc);
|
|
XCTAssertNil(sut.currentFirstResponderField);
|
|
XCTAssertFalse(sut.isValid);
|
|
}
|
|
|
|
- (void)testSetCard_updatesCVCValidity {
|
|
STPPaymentCardTextField *sut = [STPPaymentCardTextField new];
|
|
sut.numberField.text = @"378282246310005";
|
|
sut.cvcField.text = @"1234";
|
|
sut.expirationField.text = @"10/99";
|
|
XCTAssertTrue(sut.cvcField.validText);
|
|
sut.numberField.text = @"4242424242424242";
|
|
XCTAssertFalse(sut.cvcField.validText);
|
|
}
|
|
|
|
- (void)testSetCard_numberVisa {
|
|
STPPaymentCardTextField *sut = [STPPaymentCardTextField new];
|
|
STPPaymentMethodCardParams *card = [STPPaymentMethodCardParams new];
|
|
NSString *number = @"424242";
|
|
card.number = number;
|
|
STPPaymentMethodParams *params = [[STPPaymentMethodParams alloc] initWithCard:card billingDetails:nil metadata:nil];
|
|
[sut setPaymentMethodParams:params];
|
|
|
|
NSData *imgData = UIImagePNGRepresentation(sut.brandImageView.image);
|
|
NSData *expectedImgData = UIImagePNGRepresentation([STPPaymentCardTextField brandImageForCardBrand:STPCardBrandVisa]);
|
|
|
|
XCTAssertNotNil(sut.focusedTextFieldForLayout);
|
|
XCTAssertTrue(sut.focusedTextFieldForLayout.integerValue == STPCardFieldTypeNumber);
|
|
XCTAssertTrue([expectedImgData isEqualToData:imgData]);
|
|
XCTAssertEqualObjects(sut.numberField.text, number);
|
|
XCTAssertEqual(sut.expirationField.text.length, (NSUInteger)0);
|
|
XCTAssertEqual(sut.cvcField.text.length, (NSUInteger)0);
|
|
XCTAssertEqualObjects(sut.cvcField.placeholder, @"CVC");
|
|
XCTAssertNil(sut.currentFirstResponderField);
|
|
XCTAssertFalse(sut.isValid);
|
|
}
|
|
|
|
- (void)testSetCard_numberVisaInvalid {
|
|
STPPaymentCardTextField *sut = [STPPaymentCardTextField new];
|
|
STPPaymentMethodCardParams *card = [STPPaymentMethodCardParams new];
|
|
NSString *number = @"4242111111111111";
|
|
card.number = number;
|
|
STPPaymentMethodParams *params = [[STPPaymentMethodParams alloc] initWithCard:card billingDetails:nil metadata:nil];
|
|
[sut setPaymentMethodParams:params];
|
|
|
|
NSData *imgData = UIImagePNGRepresentation(sut.brandImageView.image);
|
|
NSData *expectedImgData = UIImagePNGRepresentation([STPPaymentCardTextField errorImageForCardBrand:STPCardBrandVisa]);
|
|
|
|
XCTAssertTrue([expectedImgData isEqualToData:imgData]);
|
|
}
|
|
|
|
- (void)testSetCard_numberAmex {
|
|
STPPaymentCardTextField *sut = [STPPaymentCardTextField new];
|
|
STPPaymentMethodCardParams *card = [STPPaymentMethodCardParams new];
|
|
NSString *number = @"378282";
|
|
card.number = number;
|
|
STPPaymentMethodParams *params = [[STPPaymentMethodParams alloc] initWithCard:card billingDetails:nil metadata:nil];
|
|
[sut setPaymentMethodParams:params];
|
|
|
|
NSData *imgData = UIImagePNGRepresentation(sut.brandImageView.image);
|
|
NSData *expectedImgData = UIImagePNGRepresentation([STPPaymentCardTextField brandImageForCardBrand:STPCardBrandAmex]);
|
|
|
|
XCTAssertNotNil(sut.focusedTextFieldForLayout);
|
|
XCTAssertTrue(sut.focusedTextFieldForLayout.integerValue == STPCardFieldTypeNumber);
|
|
XCTAssertTrue([expectedImgData isEqualToData:imgData]);
|
|
XCTAssertEqualObjects(sut.numberField.text, number);
|
|
XCTAssertEqual(sut.cvcField.text.length, (NSUInteger)0);
|
|
XCTAssertEqualObjects(sut.cvcField.placeholder, @"CVV");
|
|
XCTAssertNil(sut.currentFirstResponderField);
|
|
XCTAssertFalse(sut.isValid);
|
|
}
|
|
|
|
- (void)testSetCard_numberAmexInvalid {
|
|
STPPaymentCardTextField *sut = [STPPaymentCardTextField new];
|
|
STPPaymentMethodCardParams *card = [STPPaymentMethodCardParams new];
|
|
NSString *number = @"378282246311111";
|
|
card.number = number;
|
|
STPPaymentMethodParams *params = [[STPPaymentMethodParams alloc] initWithCard:card billingDetails:nil metadata:nil];
|
|
[sut setPaymentMethodParams:params];
|
|
|
|
NSData *imgData = UIImagePNGRepresentation(sut.brandImageView.image);
|
|
NSData *expectedImgData = UIImagePNGRepresentation([STPPaymentCardTextField errorImageForCardBrand:STPCardBrandAmex]);
|
|
|
|
XCTAssertNotNil(sut.focusedTextFieldForLayout);
|
|
XCTAssertTrue(sut.focusedTextFieldForLayout.integerValue == STPCardFieldTypeNumber);
|
|
XCTAssertTrue([expectedImgData isEqualToData:imgData]);
|
|
}
|
|
|
|
- (void)testSetCard_numberAndExpiration {
|
|
STPPaymentCardTextField *sut = [STPPaymentCardTextField new];
|
|
STPPaymentMethodCardParams *card = [STPPaymentMethodCardParams new];
|
|
NSString *number = @"4242424242424242";
|
|
card.number = number;
|
|
card.expMonth = @(10);
|
|
card.expYear = @(99);
|
|
STPPaymentMethodParams *params = [[STPPaymentMethodParams alloc] initWithCard:card billingDetails:nil metadata:nil];
|
|
[sut setPaymentMethodParams:params];
|
|
|
|
NSData *imgData = UIImagePNGRepresentation(sut.brandImageView.image);
|
|
NSData *expectedImgData = UIImagePNGRepresentation([STPPaymentCardTextField brandImageForCardBrand:STPCardBrandVisa]);
|
|
|
|
XCTAssertNotNil(sut.focusedTextFieldForLayout);
|
|
XCTAssertTrue([expectedImgData isEqualToData:imgData]);
|
|
XCTAssertEqualObjects(sut.numberField.text, number);
|
|
XCTAssertEqualObjects(sut.expirationField.text, @"10/99");
|
|
XCTAssertEqual(sut.cvcField.text.length, (NSUInteger)0);
|
|
XCTAssertNil(sut.currentFirstResponderField);
|
|
XCTAssertFalse(sut.isValid);
|
|
}
|
|
|
|
- (void)testSetCard_partialNumberAndExpiration {
|
|
STPPaymentCardTextField *sut = [STPPaymentCardTextField new];
|
|
STPPaymentMethodCardParams *card = [STPPaymentMethodCardParams new];
|
|
NSString *number = @"424242";
|
|
card.number = number;
|
|
card.expMonth = @(10);
|
|
card.expYear = @(99);
|
|
STPPaymentMethodParams *params = [[STPPaymentMethodParams alloc] initWithCard:card billingDetails:nil metadata:nil];
|
|
[sut setPaymentMethodParams:params];
|
|
|
|
NSData *imgData = UIImagePNGRepresentation(sut.brandImageView.image);
|
|
NSData *expectedImgData = UIImagePNGRepresentation([STPPaymentCardTextField brandImageForCardBrand:STPCardBrandVisa]);
|
|
|
|
XCTAssertNotNil(sut.focusedTextFieldForLayout);
|
|
XCTAssertTrue(sut.focusedTextFieldForLayout.integerValue == STPCardFieldTypeNumber);
|
|
XCTAssertTrue([expectedImgData isEqualToData:imgData]);
|
|
XCTAssertEqualObjects(sut.numberField.text, number);
|
|
XCTAssertEqualObjects(sut.expirationField.text, @"10/99");
|
|
XCTAssertEqual(sut.cvcField.text.length, (NSUInteger)0);
|
|
XCTAssertNil(sut.currentFirstResponderField);
|
|
XCTAssertFalse(sut.isValid);
|
|
}
|
|
|
|
- (void)testSetCard_numberAndCVC {
|
|
STPPaymentCardTextField *sut = [STPPaymentCardTextField new];
|
|
STPPaymentMethodCardParams *card = [STPPaymentMethodCardParams new];
|
|
NSString *number = @"378282246310005";
|
|
NSString *cvc = @"123";
|
|
card.number = number;
|
|
card.cvc = cvc;
|
|
STPPaymentMethodParams *params = [[STPPaymentMethodParams alloc] initWithCard:card billingDetails:nil metadata:nil];
|
|
[sut setPaymentMethodParams:params];
|
|
|
|
NSData *imgData = UIImagePNGRepresentation(sut.brandImageView.image);
|
|
NSData *expectedImgData = UIImagePNGRepresentation([STPPaymentCardTextField brandImageForCardBrand:STPCardBrandAmex]);
|
|
|
|
XCTAssertNotNil(sut.focusedTextFieldForLayout);
|
|
XCTAssertTrue([expectedImgData isEqualToData:imgData]);
|
|
XCTAssertEqualObjects(sut.numberField.text, number);
|
|
XCTAssertEqual(sut.expirationField.text.length, (NSUInteger)0);
|
|
XCTAssertEqualObjects(sut.cvcField.text, cvc);
|
|
XCTAssertNil(sut.currentFirstResponderField);
|
|
XCTAssertFalse(sut.isValid);
|
|
}
|
|
|
|
- (void)testSetCard_expirationAndCVC {
|
|
STPPaymentCardTextField *sut = [STPPaymentCardTextField new];
|
|
STPPaymentMethodCardParams *card = [STPPaymentMethodCardParams new];
|
|
NSString *cvc = @"123";
|
|
card.expMonth = @(10);
|
|
card.expYear = @(99);
|
|
card.cvc = cvc;
|
|
STPPaymentMethodParams *params = [[STPPaymentMethodParams alloc] initWithCard:card billingDetails:nil metadata:nil];
|
|
[sut setPaymentMethodParams:params];
|
|
|
|
NSData *imgData = UIImagePNGRepresentation(sut.brandImageView.image);
|
|
NSData *expectedImgData = UIImagePNGRepresentation([STPPaymentCardTextField brandImageForCardBrand:STPCardBrandUnknown]);
|
|
|
|
XCTAssertNotNil(sut.focusedTextFieldForLayout);
|
|
XCTAssertTrue(sut.focusedTextFieldForLayout.integerValue == STPCardFieldTypeNumber);
|
|
XCTAssertTrue([expectedImgData isEqualToData:imgData]);
|
|
XCTAssertEqual(sut.numberField.text.length, (NSUInteger)0);
|
|
XCTAssertEqualObjects(sut.expirationField.text, @"10/99");
|
|
XCTAssertEqualObjects(sut.cvcField.text, cvc);
|
|
XCTAssertNil(sut.currentFirstResponderField);
|
|
XCTAssertFalse(sut.isValid);
|
|
}
|
|
|
|
- (void)testSetCard_completeCardCountryWithoutPostal {
|
|
STPPaymentCardTextField *sut = [STPPaymentCardTextField new];
|
|
sut.countryCode = @"BZ";
|
|
STPPaymentMethodCardParams *card = [STPPaymentMethodCardParams new];
|
|
NSString *number = @"4242424242424242";
|
|
NSString *cvc = @"123";
|
|
card.number = number;
|
|
card.expMonth = @(10);
|
|
card.expYear = @(99);
|
|
card.cvc = cvc;
|
|
STPPaymentMethodParams *params = [[STPPaymentMethodParams alloc] initWithCard:card billingDetails:nil metadata:nil];
|
|
[sut setPaymentMethodParams:params];
|
|
|
|
NSData *imgData = UIImagePNGRepresentation(sut.brandImageView.image);
|
|
NSData *expectedImgData = UIImagePNGRepresentation([STPPaymentCardTextField brandImageForCardBrand:STPCardBrandVisa]);
|
|
|
|
XCTAssertNotNil(sut.focusedTextFieldForLayout);
|
|
XCTAssertTrue([expectedImgData isEqualToData:imgData]);
|
|
XCTAssertEqualObjects(sut.numberField.text, number);
|
|
XCTAssertEqualObjects(sut.expirationField.text, @"10/99");
|
|
XCTAssertEqualObjects(sut.cvcField.text, cvc);
|
|
XCTAssertNil(sut.currentFirstResponderField);
|
|
XCTAssertTrue(sut.isValid);
|
|
}
|
|
|
|
- (void)testSetCard_completeCardNoPostal {
|
|
STPPaymentCardTextField *sut = [STPPaymentCardTextField new];
|
|
sut.postalCodeEntryEnabled = NO;
|
|
STPPaymentMethodCardParams *card = [STPPaymentMethodCardParams new];
|
|
NSString *number = @"4242424242424242";
|
|
NSString *cvc = @"123";
|
|
card.number = number;
|
|
card.expMonth = @(10);
|
|
card.expYear = @(99);
|
|
card.cvc = cvc;
|
|
STPPaymentMethodParams *params = [[STPPaymentMethodParams alloc] initWithCard:card billingDetails:nil metadata:nil];
|
|
[sut setPaymentMethodParams:params];
|
|
|
|
NSData *imgData = UIImagePNGRepresentation(sut.brandImageView.image);
|
|
NSData *expectedImgData = UIImagePNGRepresentation([STPPaymentCardTextField brandImageForCardBrand:STPCardBrandVisa]);
|
|
|
|
XCTAssertNotNil(sut.focusedTextFieldForLayout);
|
|
XCTAssertTrue([expectedImgData isEqualToData:imgData]);
|
|
XCTAssertEqualObjects(sut.numberField.text, number);
|
|
XCTAssertEqualObjects(sut.expirationField.text, @"10/99");
|
|
XCTAssertEqualObjects(sut.cvcField.text, cvc);
|
|
XCTAssertNil(sut.currentFirstResponderField);
|
|
XCTAssertTrue(sut.isValid);
|
|
}
|
|
|
|
- (void)testSetCard_completeCard {
|
|
STPPaymentCardTextField *sut = [STPPaymentCardTextField new];
|
|
STPPaymentMethodCardParams *card = [STPPaymentMethodCardParams new];
|
|
NSString *number = @"4242424242424242";
|
|
NSString *cvc = @"123";
|
|
card.number = number;
|
|
card.expMonth = @(10);
|
|
card.expYear = @(99);
|
|
card.cvc = cvc;
|
|
|
|
STPPaymentMethodBillingDetails *billingDetails = [[STPPaymentMethodBillingDetails alloc] init];
|
|
billingDetails.address = [[STPPaymentMethodAddress alloc] init];
|
|
billingDetails.address.postalCode = @"90210";
|
|
STPPaymentMethodParams *params = [[STPPaymentMethodParams alloc] initWithCard:card billingDetails:billingDetails metadata:nil];
|
|
[sut setPaymentMethodParams:params];
|
|
|
|
NSData *imgData = UIImagePNGRepresentation(sut.brandImageView.image);
|
|
NSData *expectedImgData = UIImagePNGRepresentation([STPPaymentCardTextField brandImageForCardBrand:STPCardBrandVisa]);
|
|
|
|
XCTAssertNotNil(sut.focusedTextFieldForLayout);
|
|
XCTAssertTrue([expectedImgData isEqualToData:imgData]);
|
|
XCTAssertEqualObjects(sut.numberField.text, number);
|
|
XCTAssertEqualObjects(sut.expirationField.text, @"10/99");
|
|
XCTAssertEqualObjects(sut.cvcField.text, cvc);
|
|
XCTAssertNil(sut.currentFirstResponderField);
|
|
XCTAssertTrue(sut.isValid);
|
|
}
|
|
|
|
- (void)testSetCard_empty {
|
|
STPPaymentCardTextField *sut = [STPPaymentCardTextField new];
|
|
sut.numberField.text = @"4242424242424242";
|
|
sut.cvcField.text = @"123";
|
|
sut.expirationField.text = @"10/99";
|
|
STPPaymentMethodCardParams *card = [STPPaymentMethodCardParams new];
|
|
STPPaymentMethodParams *params = [[STPPaymentMethodParams alloc] initWithCard:card billingDetails:nil metadata:nil];
|
|
[sut setPaymentMethodParams:params];
|
|
|
|
NSData *imgData = UIImagePNGRepresentation(sut.brandImageView.image);
|
|
NSData *expectedImgData = UIImagePNGRepresentation([STPPaymentCardTextField brandImageForCardBrand:STPCardBrandUnknown]);
|
|
|
|
XCTAssertNotNil(sut.focusedTextFieldForLayout);
|
|
XCTAssertTrue(sut.focusedTextFieldForLayout.integerValue == STPCardFieldTypeNumber);
|
|
XCTAssertTrue([expectedImgData isEqualToData:imgData]);
|
|
XCTAssertEqual(sut.numberField.text.length, (NSUInteger)0);
|
|
XCTAssertEqual(sut.expirationField.text.length, (NSUInteger)0);
|
|
XCTAssertEqual(sut.cvcField.text.length, (NSUInteger)0);
|
|
XCTAssertNil(sut.currentFirstResponderField);
|
|
XCTAssertFalse(sut.isValid);
|
|
}
|
|
|
|
#pragma clang diagnostic push
|
|
#pragma clang diagnostic ignored "-Wdeprecated"
|
|
|
|
#pragma clang diagnostic pop
|
|
|
|
- (void)testSettingTextUpdatesViewModelText {
|
|
STPPaymentCardTextField *sut = [STPPaymentCardTextField new];
|
|
sut.numberField.text = @"4242424242424242";
|
|
XCTAssertEqualObjects(sut.viewModel.cardNumber, sut.numberField.text);
|
|
|
|
sut.cvcField.text = @"123";
|
|
XCTAssertEqualObjects(sut.viewModel.cvc, sut.cvcField.text);
|
|
|
|
sut.expirationField.text = @"10/99";
|
|
XCTAssertEqualObjects(sut.viewModel.rawExpiration, sut.expirationField.text);
|
|
XCTAssertEqualObjects(sut.viewModel.expirationMonth, @"10");
|
|
XCTAssertEqualObjects(sut.viewModel.expirationYear, @"99");
|
|
}
|
|
|
|
- (void)testSettingTextUpdatesCardParams {
|
|
STPPaymentCardTextField *sut = [STPPaymentCardTextField new];
|
|
sut.numberField.text = @"4242424242424242";
|
|
sut.cvcField.text = @"123";
|
|
sut.expirationField.text = @"10/99";
|
|
sut.postalCodeField.text = @"90210";
|
|
|
|
STPPaymentMethodCardParams *card = sut.paymentMethodParams.card;
|
|
XCTAssertNotNil(card);
|
|
XCTAssertEqualObjects(card.number, @"4242424242424242");
|
|
XCTAssertEqualObjects(card.cvc, @"123");
|
|
XCTAssertEqual(card.expMonth.integerValue, 10);
|
|
XCTAssertEqual(card.expYear.integerValue, 99);
|
|
XCTAssertEqualObjects(sut.paymentMethodParams.billingDetails.address.postalCode, @"90210");
|
|
}
|
|
|
|
- (void)testSettingBillingDetailsRetainsBillingDetails {
|
|
STPPaymentCardTextField *sut = [STPPaymentCardTextField new];
|
|
STPPaymentMethodCardParams *params = [STPPaymentMethodCardParams new];
|
|
STPPaymentMethodBillingDetails *billingDetails = [[STPPaymentMethodBillingDetails alloc] init];
|
|
billingDetails.name = @"Test test";
|
|
|
|
sut.paymentMethodParams = [STPPaymentMethodParams paramsWithCard:params billingDetails:billingDetails metadata:nil];
|
|
STPPaymentMethodParams *actual = sut.paymentMethodParams;
|
|
|
|
XCTAssertEqualObjects(@"Test test", actual.billingDetails.name);
|
|
}
|
|
|
|
|
|
- (void)testSettingMetadataRetainsMetadata {
|
|
STPPaymentCardTextField *sut = [STPPaymentCardTextField new];
|
|
STPPaymentMethodCardParams *params = [STPPaymentMethodCardParams new];
|
|
sut.paymentMethodParams = [STPPaymentMethodParams paramsWithCard:params billingDetails:nil metadata:@{@"hello": @"test"}];
|
|
STPPaymentMethodParams *actual = sut.paymentMethodParams;
|
|
|
|
XCTAssertEqualObjects(@{@"hello": @"test"}, actual.metadata);
|
|
}
|
|
|
|
|
|
- (void)testSettingPostalCodeUpdatesCardParams {
|
|
STPPaymentCardTextField *sut = [STPPaymentCardTextField new];
|
|
sut.numberField.text = @"4242424242424242";
|
|
sut.cvcField.text = @"123";
|
|
sut.expirationField.text = @"10/99";
|
|
sut.postalCodeField.text = @"90210";
|
|
|
|
STPPaymentMethodCardParams *params = sut.paymentMethodParams.card;
|
|
XCTAssertNotNil(params);
|
|
XCTAssertEqualObjects(params.number, @"4242424242424242");
|
|
XCTAssertEqualObjects(params.cvc, @"123");
|
|
XCTAssertEqual(params.expMonth.integerValue, 10);
|
|
XCTAssertEqual(params.expYear.integerValue, 99);
|
|
}
|
|
|
|
- (void)testEmptyPostalCodeVendsNilAddress {
|
|
STPPaymentCardTextField *sut = [STPPaymentCardTextField new];
|
|
sut.numberField.text = @"4242424242424242";
|
|
sut.cvcField.text = @"123";
|
|
sut.expirationField.text = @"10/99";
|
|
|
|
XCTAssertNil(sut.paymentMethodParams.billingDetails.address.postalCode);
|
|
STPPaymentMethodCardParams *params = sut.paymentMethodParams.card;
|
|
XCTAssertNotNil(params);
|
|
XCTAssertEqualObjects(params.number, @"4242424242424242");
|
|
XCTAssertEqualObjects(params.cvc, @"123");
|
|
XCTAssertEqual(params.expMonth.integerValue, 10);
|
|
XCTAssertEqual(params.expYear.integerValue, 99);
|
|
}
|
|
|
|
|
|
- (void)testAccessingCardParamsDuringSettingCardParams {
|
|
PaymentCardTextFieldBlockDelegate *delegate = [PaymentCardTextFieldBlockDelegate new];
|
|
delegate.didChange = ^(STPPaymentCardTextField *textField) {
|
|
// delegate reads the `cardParams` for any reason it wants
|
|
[[textField paymentMethodParams] card];
|
|
};
|
|
STPPaymentCardTextField *sut = [STPPaymentCardTextField new];
|
|
sut.delegate = delegate;
|
|
|
|
STPPaymentMethodCardParams *params = [STPPaymentMethodCardParams new];
|
|
params.number = @"4242424242424242";
|
|
params.cvc = @"123";
|
|
|
|
sut.paymentMethodParams = [STPPaymentMethodParams paramsWithCard:params billingDetails:nil metadata:nil];
|
|
STPPaymentMethodCardParams *actual = sut.paymentMethodParams.card;
|
|
|
|
XCTAssertEqualObjects(@"4242424242424242", actual.number);
|
|
XCTAssertEqualObjects(@"123", actual.cvc);
|
|
}
|
|
|
|
- (void)testSetCardParamsCopiesObject {
|
|
STPPaymentCardTextField *sut = [STPPaymentCardTextField new];
|
|
STPPaymentMethodCardParams *params = [STPPaymentMethodCardParams new];
|
|
|
|
params.number = @"4242424242424242"; // legit
|
|
sut.paymentMethodParams = [STPPaymentMethodParams paramsWithCard:params billingDetails:nil metadata:nil];
|
|
|
|
// fetching `sut.cardParams` returns a copy, so edits happen to caller's copy
|
|
sut.paymentMethodParams.card.number = @"number 1";
|
|
|
|
// `sut` copied `params` (& `params.address`) when set, so edits to original don't show up
|
|
params.number = @"number 2";
|
|
|
|
XCTAssertEqualObjects(@"4242424242424242", sut.paymentMethodParams.card.number, @"set via setCardParams:");
|
|
|
|
XCTAssertNotEqualObjects(@"number 1", sut.paymentMethodParams.card.number, @"return value from cardParams cannot be edited inline");
|
|
|
|
XCTAssertNotEqualObjects(@"number 2", sut.paymentMethodParams.card.number, @"caller changed their copy after setCardParams:");
|
|
}
|
|
|
|
|
|
// MARK: - paymentMethodParams
|
|
|
|
- (void)testSetCard_numberUnknown_pm {
|
|
STPPaymentCardTextField *sut = [STPPaymentCardTextField new];
|
|
STPPaymentMethodCardParams *card = [STPPaymentMethodCardParams new];
|
|
NSString *number = @"1";
|
|
card.number = number;
|
|
[sut setPaymentMethodParams:[[STPPaymentMethodParams alloc] initWithCard:card billingDetails:nil metadata:nil]];
|
|
|
|
NSData *imgData = UIImagePNGRepresentation(sut.brandImageView.image);
|
|
NSData *expectedImgData = UIImagePNGRepresentation([STPPaymentCardTextField errorImageForCardBrand:STPCardBrandUnknown]);
|
|
|
|
XCTAssertNotNil(sut.focusedTextFieldForLayout);
|
|
XCTAssertTrue(sut.focusedTextFieldForLayout.integerValue == STPCardFieldTypeNumber);
|
|
XCTAssertTrue([expectedImgData isEqualToData:imgData]);
|
|
XCTAssertEqualObjects(sut.numberField.text, number);
|
|
XCTAssertEqual(sut.expirationField.text.length, (NSUInteger)0);
|
|
XCTAssertEqual(sut.cvcField.text.length, (NSUInteger)0);
|
|
XCTAssertNil(sut.currentFirstResponderField);
|
|
}
|
|
|
|
- (void)testSetCard_expiration_pm {
|
|
STPPaymentCardTextField *sut = [STPPaymentCardTextField new];
|
|
STPPaymentMethodCardParams *card = [STPPaymentMethodCardParams new];
|
|
card.expMonth = @(10);
|
|
card.expYear = @(99);
|
|
[sut setPaymentMethodParams:[[STPPaymentMethodParams alloc] initWithCard:card billingDetails:nil metadata:nil]];
|
|
NSData *imgData = UIImagePNGRepresentation(sut.brandImageView.image);
|
|
NSData *expectedImgData = UIImagePNGRepresentation([STPPaymentCardTextField brandImageForCardBrand:STPCardBrandUnknown]);
|
|
|
|
XCTAssertNotNil(sut.focusedTextFieldForLayout);
|
|
XCTAssertTrue(sut.focusedTextFieldForLayout.integerValue == STPCardFieldTypeNumber);
|
|
XCTAssertTrue([expectedImgData isEqualToData:imgData]);
|
|
XCTAssertEqual(sut.numberField.text.length, (NSUInteger)0);
|
|
XCTAssertEqualObjects(sut.expirationField.text, @"10/99");
|
|
XCTAssertEqual(sut.cvcField.text.length, (NSUInteger)0);
|
|
XCTAssertNil(sut.currentFirstResponderField);
|
|
XCTAssertFalse(sut.isValid);
|
|
}
|
|
|
|
- (void)testSetCard_CVC_pm {
|
|
STPPaymentCardTextField *sut = [STPPaymentCardTextField new];
|
|
STPPaymentMethodCardParams *card = [STPPaymentMethodCardParams new];
|
|
NSString *cvc = @"123";
|
|
card.cvc = cvc;
|
|
[sut setPaymentMethodParams:[[STPPaymentMethodParams alloc] initWithCard:card billingDetails:nil metadata:nil]];
|
|
NSData *imgData = UIImagePNGRepresentation(sut.brandImageView.image);
|
|
NSData *expectedImgData = UIImagePNGRepresentation([STPPaymentCardTextField brandImageForCardBrand:STPCardBrandUnknown]);
|
|
|
|
XCTAssertNotNil(sut.focusedTextFieldForLayout);
|
|
XCTAssertTrue(sut.focusedTextFieldForLayout.integerValue == STPCardFieldTypeNumber);
|
|
XCTAssertTrue([expectedImgData isEqualToData:imgData]);
|
|
XCTAssertEqual(sut.numberField.text.length, (NSUInteger)0);
|
|
XCTAssertEqual(sut.expirationField.text.length, (NSUInteger)0);
|
|
XCTAssertEqualObjects(sut.cvcField.text, cvc);
|
|
XCTAssertNil(sut.currentFirstResponderField);
|
|
XCTAssertFalse(sut.isValid);
|
|
}
|
|
|
|
- (void)testSetCard_numberVisa_pm {
|
|
STPPaymentCardTextField *sut = [STPPaymentCardTextField new];
|
|
STPPaymentMethodCardParams *card = [STPPaymentMethodCardParams new];
|
|
NSString *number = @"424242";
|
|
card.number = number;
|
|
[sut setPaymentMethodParams:[[STPPaymentMethodParams alloc] initWithCard:card billingDetails:nil metadata:nil]];
|
|
|
|
NSData *imgData = UIImagePNGRepresentation(sut.brandImageView.image);
|
|
NSData *expectedImgData = UIImagePNGRepresentation([STPPaymentCardTextField brandImageForCardBrand:STPCardBrandVisa]);
|
|
|
|
XCTAssertNotNil(sut.focusedTextFieldForLayout);
|
|
XCTAssertTrue(sut.focusedTextFieldForLayout.integerValue == STPCardFieldTypeNumber);
|
|
XCTAssertTrue([expectedImgData isEqualToData:imgData]);
|
|
XCTAssertEqualObjects(sut.numberField.text, number);
|
|
XCTAssertEqual(sut.expirationField.text.length, (NSUInteger)0);
|
|
XCTAssertEqual(sut.cvcField.text.length, (NSUInteger)0);
|
|
XCTAssertEqualObjects(sut.cvcField.placeholder, @"CVC");
|
|
XCTAssertNil(sut.currentFirstResponderField);
|
|
XCTAssertFalse(sut.isValid);
|
|
}
|
|
|
|
- (void)testSetCard_numberVisaInvalid_pm {
|
|
STPPaymentCardTextField *sut = [STPPaymentCardTextField new];
|
|
STPPaymentMethodCardParams *card = [STPPaymentMethodCardParams new];
|
|
NSString *number = @"4242111111111111";
|
|
card.number = number;
|
|
[sut setPaymentMethodParams:[[STPPaymentMethodParams alloc] initWithCard:card billingDetails:nil metadata:nil]];
|
|
|
|
NSData *imgData = UIImagePNGRepresentation(sut.brandImageView.image);
|
|
NSData *expectedImgData = UIImagePNGRepresentation([STPPaymentCardTextField errorImageForCardBrand:STPCardBrandVisa]);
|
|
|
|
XCTAssertTrue([expectedImgData isEqualToData:imgData]);
|
|
}
|
|
|
|
- (void)testSetCard_numberAmex_pm {
|
|
STPPaymentCardTextField *sut = [STPPaymentCardTextField new];
|
|
STPPaymentMethodCardParams *card = [STPPaymentMethodCardParams new];
|
|
NSString *number = @"378282";
|
|
card.number = number;
|
|
[sut setPaymentMethodParams:[[STPPaymentMethodParams alloc] initWithCard:card billingDetails:nil metadata:nil]];
|
|
|
|
NSData *imgData = UIImagePNGRepresentation(sut.brandImageView.image);
|
|
NSData *expectedImgData = UIImagePNGRepresentation([STPPaymentCardTextField brandImageForCardBrand:STPCardBrandAmex]);
|
|
|
|
XCTAssertNotNil(sut.focusedTextFieldForLayout);
|
|
XCTAssertTrue(sut.focusedTextFieldForLayout.integerValue == STPCardFieldTypeNumber);
|
|
XCTAssertTrue([expectedImgData isEqualToData:imgData]);
|
|
XCTAssertEqualObjects(sut.numberField.text, number);
|
|
XCTAssertEqual(sut.cvcField.text.length, (NSUInteger)0);
|
|
XCTAssertEqualObjects(sut.cvcField.placeholder, @"CVV");
|
|
XCTAssertNil(sut.currentFirstResponderField);
|
|
XCTAssertFalse(sut.isValid);
|
|
}
|
|
|
|
- (void)testSetCard_numberAmexInvalid_pm {
|
|
STPPaymentCardTextField *sut = [STPPaymentCardTextField new];
|
|
STPPaymentMethodCardParams *card = [STPPaymentMethodCardParams new];
|
|
NSString *number = @"378282246311111";
|
|
card.number = number;
|
|
[sut setPaymentMethodParams:[[STPPaymentMethodParams alloc] initWithCard:card billingDetails:nil metadata:nil]];
|
|
|
|
NSData *imgData = UIImagePNGRepresentation(sut.brandImageView.image);
|
|
NSData *expectedImgData = UIImagePNGRepresentation([STPPaymentCardTextField errorImageForCardBrand:STPCardBrandAmex]);
|
|
|
|
XCTAssertNotNil(sut.focusedTextFieldForLayout);
|
|
XCTAssertTrue(sut.focusedTextFieldForLayout.integerValue == STPCardFieldTypeNumber);
|
|
XCTAssertTrue([expectedImgData isEqualToData:imgData]);
|
|
}
|
|
|
|
- (void)testSetCard_numberAndExpiration_pm {
|
|
STPPaymentCardTextField *sut = [STPPaymentCardTextField new];
|
|
STPPaymentMethodCardParams *card = [STPPaymentMethodCardParams new];
|
|
NSString *number = @"4242424242424242";
|
|
card.number = number;
|
|
card.expMonth = @(10);
|
|
card.expYear = @(99);
|
|
[sut setPaymentMethodParams:[[STPPaymentMethodParams alloc] initWithCard:card billingDetails:nil metadata:nil]];
|
|
|
|
NSData *imgData = UIImagePNGRepresentation(sut.brandImageView.image);
|
|
NSData *expectedImgData = UIImagePNGRepresentation([STPPaymentCardTextField brandImageForCardBrand:STPCardBrandVisa]);
|
|
|
|
XCTAssertNotNil(sut.focusedTextFieldForLayout);
|
|
XCTAssertTrue([expectedImgData isEqualToData:imgData]);
|
|
XCTAssertEqualObjects(sut.numberField.text, number);
|
|
XCTAssertEqualObjects(sut.expirationField.text, @"10/99");
|
|
XCTAssertEqual(sut.cvcField.text.length, (NSUInteger)0);
|
|
XCTAssertNil(sut.currentFirstResponderField);
|
|
XCTAssertFalse(sut.isValid);
|
|
}
|
|
|
|
- (void)testSetCard_partialNumberAndExpiration_pm {
|
|
STPPaymentCardTextField *sut = [STPPaymentCardTextField new];
|
|
STPPaymentMethodCardParams *card = [STPPaymentMethodCardParams new];
|
|
NSString *number = @"424242";
|
|
card.number = number;
|
|
card.expMonth = @(10);
|
|
card.expYear = @(99);
|
|
[sut setPaymentMethodParams:[[STPPaymentMethodParams alloc] initWithCard:card billingDetails:nil metadata:nil]];
|
|
|
|
NSData *imgData = UIImagePNGRepresentation(sut.brandImageView.image);
|
|
NSData *expectedImgData = UIImagePNGRepresentation([STPPaymentCardTextField brandImageForCardBrand:STPCardBrandVisa]);
|
|
|
|
XCTAssertNotNil(sut.focusedTextFieldForLayout);
|
|
XCTAssertTrue(sut.focusedTextFieldForLayout.integerValue == STPCardFieldTypeNumber);
|
|
XCTAssertTrue([expectedImgData isEqualToData:imgData]);
|
|
XCTAssertEqualObjects(sut.numberField.text, number);
|
|
XCTAssertEqualObjects(sut.expirationField.text, @"10/99");
|
|
XCTAssertEqual(sut.cvcField.text.length, (NSUInteger)0);
|
|
XCTAssertNil(sut.currentFirstResponderField);
|
|
XCTAssertFalse(sut.isValid);
|
|
}
|
|
|
|
- (void)testSetCard_numberAndCVC_pm {
|
|
STPPaymentCardTextField *sut = [STPPaymentCardTextField new];
|
|
STPPaymentMethodCardParams *card = [STPPaymentMethodCardParams new];
|
|
NSString *number = @"378282246310005";
|
|
NSString *cvc = @"123";
|
|
card.number = number;
|
|
card.cvc = cvc;
|
|
[sut setPaymentMethodParams:[[STPPaymentMethodParams alloc] initWithCard:card billingDetails:nil metadata:nil]];
|
|
|
|
NSData *imgData = UIImagePNGRepresentation(sut.brandImageView.image);
|
|
NSData *expectedImgData = UIImagePNGRepresentation([STPPaymentCardTextField brandImageForCardBrand:STPCardBrandAmex]);
|
|
|
|
XCTAssertNotNil(sut.focusedTextFieldForLayout);
|
|
XCTAssertTrue([expectedImgData isEqualToData:imgData]);
|
|
XCTAssertEqualObjects(sut.numberField.text, number);
|
|
XCTAssertEqual(sut.expirationField.text.length, (NSUInteger)0);
|
|
XCTAssertEqualObjects(sut.cvcField.text, cvc);
|
|
XCTAssertNil(sut.currentFirstResponderField);
|
|
XCTAssertFalse(sut.isValid);
|
|
}
|
|
|
|
- (void)testSetCard_expirationAndCVC_pm {
|
|
STPPaymentCardTextField *sut = [STPPaymentCardTextField new];
|
|
STPPaymentMethodCardParams *card = [STPPaymentMethodCardParams new];
|
|
NSString *cvc = @"123";
|
|
card.expMonth = @(10);
|
|
card.expYear = @(99);
|
|
card.cvc = cvc;
|
|
[sut setPaymentMethodParams:[[STPPaymentMethodParams alloc] initWithCard:card billingDetails:nil metadata:nil]];
|
|
|
|
NSData *imgData = UIImagePNGRepresentation(sut.brandImageView.image);
|
|
NSData *expectedImgData = UIImagePNGRepresentation([STPPaymentCardTextField brandImageForCardBrand:STPCardBrandUnknown]);
|
|
|
|
XCTAssertNotNil(sut.focusedTextFieldForLayout);
|
|
XCTAssertTrue(sut.focusedTextFieldForLayout.integerValue == STPCardFieldTypeNumber);
|
|
XCTAssertTrue([expectedImgData isEqualToData:imgData]);
|
|
XCTAssertEqual(sut.numberField.text.length, (NSUInteger)0);
|
|
XCTAssertEqualObjects(sut.expirationField.text, @"10/99");
|
|
XCTAssertEqualObjects(sut.cvcField.text, cvc);
|
|
XCTAssertNil(sut.currentFirstResponderField);
|
|
XCTAssertFalse(sut.isValid);
|
|
}
|
|
|
|
- (void)testSetCard_completeCardCountryWithoutPostal_pm {
|
|
STPPaymentCardTextField *sut = [STPPaymentCardTextField new];
|
|
sut.countryCode = @"BZ";
|
|
STPPaymentMethodCardParams *card = [STPPaymentMethodCardParams new];
|
|
NSString *number = @"4242424242424242";
|
|
NSString *cvc = @"123";
|
|
card.number = number;
|
|
card.expMonth = @(10);
|
|
card.expYear = @(99);
|
|
card.cvc = cvc;
|
|
[sut setPaymentMethodParams:[[STPPaymentMethodParams alloc] initWithCard:card billingDetails:nil metadata:nil]];
|
|
|
|
NSData *imgData = UIImagePNGRepresentation(sut.brandImageView.image);
|
|
NSData *expectedImgData = UIImagePNGRepresentation([STPPaymentCardTextField brandImageForCardBrand:STPCardBrandVisa]);
|
|
|
|
XCTAssertNotNil(sut.focusedTextFieldForLayout);
|
|
XCTAssertTrue([expectedImgData isEqualToData:imgData]);
|
|
XCTAssertEqualObjects(sut.numberField.text, number);
|
|
XCTAssertEqualObjects(sut.expirationField.text, @"10/99");
|
|
XCTAssertEqualObjects(sut.cvcField.text, cvc);
|
|
XCTAssertNil(sut.currentFirstResponderField);
|
|
XCTAssertTrue(sut.isValid);
|
|
}
|
|
|
|
- (void)testSetCard_completeCardNoPostal_pm {
|
|
STPPaymentCardTextField *sut = [STPPaymentCardTextField new];
|
|
sut.postalCodeEntryEnabled = NO;
|
|
STPPaymentMethodCardParams *card = [STPPaymentMethodCardParams new];
|
|
NSString *number = @"4242424242424242";
|
|
NSString *cvc = @"123";
|
|
card.number = number;
|
|
card.expMonth = @(10);
|
|
card.expYear = @(99);
|
|
card.cvc = cvc;
|
|
[sut setPaymentMethodParams:[[STPPaymentMethodParams alloc] initWithCard:card billingDetails:nil metadata:nil]];
|
|
|
|
NSData *imgData = UIImagePNGRepresentation(sut.brandImageView.image);
|
|
NSData *expectedImgData = UIImagePNGRepresentation([STPPaymentCardTextField brandImageForCardBrand:STPCardBrandVisa]);
|
|
|
|
XCTAssertNotNil(sut.focusedTextFieldForLayout);
|
|
XCTAssertTrue([expectedImgData isEqualToData:imgData]);
|
|
XCTAssertEqualObjects(sut.numberField.text, number);
|
|
XCTAssertEqualObjects(sut.expirationField.text, @"10/99");
|
|
XCTAssertEqualObjects(sut.cvcField.text, cvc);
|
|
XCTAssertNil(sut.currentFirstResponderField);
|
|
XCTAssertTrue(sut.isValid);
|
|
}
|
|
|
|
- (void)testSetCard_completeCard_pm {
|
|
STPPaymentCardTextField *sut = [STPPaymentCardTextField new];
|
|
STPPaymentMethodCardParams *card = [STPPaymentMethodCardParams new];
|
|
NSString *number = @"4242424242424242";
|
|
NSString *cvc = @"123";
|
|
card.number = number;
|
|
card.expMonth = @(10);
|
|
card.expYear = @(99);
|
|
card.cvc = cvc;
|
|
[sut setPaymentMethodParams:[[STPPaymentMethodParams alloc] initWithCard:card billingDetails:[[STPPaymentMethodBillingDetails alloc] initWithPostalCode:@"90210" countryCode:@"US"] metadata:nil]];
|
|
|
|
NSData *imgData = UIImagePNGRepresentation(sut.brandImageView.image);
|
|
NSData *expectedImgData = UIImagePNGRepresentation([STPPaymentCardTextField brandImageForCardBrand:STPCardBrandVisa]);
|
|
|
|
XCTAssertNotNil(sut.focusedTextFieldForLayout);
|
|
XCTAssertTrue([expectedImgData isEqualToData:imgData]);
|
|
XCTAssertEqualObjects(sut.numberField.text, number);
|
|
XCTAssertEqualObjects(sut.expirationField.text, @"10/99");
|
|
XCTAssertEqualObjects(sut.cvcField.text, cvc);
|
|
XCTAssertNil(sut.currentFirstResponderField);
|
|
BOOL isvalid = sut.isValid;
|
|
XCTAssertTrue(isvalid);
|
|
|
|
|
|
STPPaymentMethodParams *paymentMethodParams = sut.paymentMethodParams;
|
|
XCTAssertNotNil(paymentMethodParams);
|
|
|
|
STPPaymentMethodCardParams *sutCardParams = paymentMethodParams.card;
|
|
XCTAssertNotNil(sutCardParams);
|
|
|
|
XCTAssertEqualObjects(sutCardParams.number, card.number);
|
|
XCTAssertEqualObjects(sutCardParams.expMonth, card.expMonth);
|
|
XCTAssertEqualObjects(sutCardParams.expYear, card.expYear);
|
|
XCTAssertEqualObjects(sutCardParams.cvc, card.cvc);
|
|
|
|
STPPaymentMethodBillingDetails *sutBillingDetails = paymentMethodParams.billingDetails;
|
|
XCTAssertNotNil(sutBillingDetails);
|
|
|
|
STPPaymentMethodAddress *sutAddress = sutBillingDetails.address;
|
|
XCTAssertNotNil(sutAddress);
|
|
|
|
XCTAssertEqualObjects(sutAddress.postalCode, @"90210");
|
|
XCTAssertEqualObjects(sutAddress.country, @"US");
|
|
}
|
|
|
|
- (void)testSetCard_empty_pm {
|
|
STPPaymentCardTextField *sut = [STPPaymentCardTextField new];
|
|
sut.numberField.text = @"4242424242424242";
|
|
sut.cvcField.text = @"123";
|
|
sut.expirationField.text = @"10/99";
|
|
STPPaymentMethodCardParams *card = [STPPaymentMethodCardParams new];
|
|
[sut setPaymentMethodParams:[[STPPaymentMethodParams alloc] initWithCard:card billingDetails:nil metadata:nil]];
|
|
|
|
NSData *imgData = UIImagePNGRepresentation(sut.brandImageView.image);
|
|
NSData *expectedImgData = UIImagePNGRepresentation([STPPaymentCardTextField brandImageForCardBrand:STPCardBrandUnknown]);
|
|
|
|
XCTAssertNotNil(sut.focusedTextFieldForLayout);
|
|
XCTAssertTrue(sut.focusedTextFieldForLayout.integerValue == STPCardFieldTypeNumber);
|
|
XCTAssertTrue([expectedImgData isEqualToData:imgData]);
|
|
XCTAssertEqual(sut.numberField.text.length, (NSUInteger)0);
|
|
XCTAssertEqual(sut.expirationField.text.length, (NSUInteger)0);
|
|
XCTAssertEqual(sut.cvcField.text.length, (NSUInteger)0);
|
|
XCTAssertNil(sut.currentFirstResponderField);
|
|
XCTAssertFalse(sut.isValid);
|
|
}
|
|
|
|
@end
|
|
|
|
@interface STPPaymentCardTextFieldUITests : XCTestCase
|
|
@property (nonatomic) UIWindow *window;
|
|
@property (nonatomic) STPPaymentCardTextField *sut;
|
|
@end
|
|
|
|
@implementation STPPaymentCardTextFieldUITests
|
|
|
|
+ (void)setUp {
|
|
[super setUp];
|
|
[[STPAPIClient sharedClient] setPublishableKey:STPTestingDefaultPublishableKey];
|
|
}
|
|
|
|
- (void)setUp {
|
|
[super setUp];
|
|
self.window = [[UIWindow alloc] initWithFrame:[UIScreen mainScreen].bounds];
|
|
STPPaymentCardTextField *textField = [[STPPaymentCardTextField alloc] initWithFrame:self.window.bounds];
|
|
[self.window addSubview:textField];
|
|
XCTAssertTrue([textField.numberField canBecomeFirstResponder], @"text field cannot become first responder");
|
|
self.sut = textField;
|
|
}
|
|
|
|
#pragma mark - UI Tests
|
|
|
|
- (void)testSetCard_allFields_whileEditingNumber {
|
|
XCTAssertTrue([self.sut.numberField becomeFirstResponder], @"text field is not first responder");
|
|
STPPaymentMethodCardParams *card = [STPPaymentMethodCardParams new];
|
|
STPPaymentMethodBillingDetails *billingDetails = [[STPPaymentMethodBillingDetails alloc] init];
|
|
billingDetails.address = [[STPPaymentMethodAddress alloc] init];
|
|
billingDetails.address.postalCode = @"90210";
|
|
NSString *number = @"4242424242424242";
|
|
NSString *cvc = @"123";
|
|
card.number = number;
|
|
card.expMonth = @(10);
|
|
card.expYear = @(99);
|
|
card.cvc = cvc;
|
|
[self.sut setPaymentMethodParams:[STPPaymentMethodParams paramsWithCard:card billingDetails:billingDetails metadata:nil]];
|
|
|
|
NSData *imgData = UIImagePNGRepresentation(self.sut.brandImageView.image);
|
|
NSData *expectedImgData = UIImagePNGRepresentation([STPPaymentCardTextField brandImageForCardBrand:STPCardBrandVisa]);
|
|
|
|
XCTAssertNil(self.sut.focusedTextFieldForLayout);
|
|
XCTAssertTrue([expectedImgData isEqualToData:imgData]);
|
|
XCTAssertEqualObjects(self.sut.numberField.text, number);
|
|
XCTAssertEqualObjects(self.sut.expirationField.text, @"10/99");
|
|
XCTAssertEqualObjects(self.sut.cvcField.text, cvc);
|
|
XCTAssertEqualObjects(self.sut.postalCode, @"90210");
|
|
XCTAssertFalse([self.sut isFirstResponder], @"after `setCardParams:`, if all fields are valid, should resign firstResponder");
|
|
XCTAssertTrue(self.sut.isValid);
|
|
}
|
|
|
|
- (void)testSetCard_partialNumberAndExpiration_whileEditingExpiration {
|
|
XCTAssertTrue([self.sut.expirationField becomeFirstResponder], @"text field is not first responder");
|
|
STPPaymentMethodCardParams *card = [STPPaymentMethodCardParams new];
|
|
NSString *number = @"42";
|
|
card.number = number;
|
|
card.expMonth = @(10);
|
|
card.expYear = @(99);
|
|
[self.sut setPaymentMethodParams:[STPPaymentMethodParams paramsWithCard:card billingDetails:nil metadata:nil]];
|
|
|
|
NSData *imgData = UIImagePNGRepresentation(self.sut.brandImageView.image);
|
|
NSData *expectedImgData = UIImagePNGRepresentation([STPPaymentCardTextField cvcImageForCardBrand:STPCardBrandVisa]);
|
|
|
|
XCTAssertNotNil(self.sut.focusedTextFieldForLayout);
|
|
XCTAssertTrue(self.sut.focusedTextFieldForLayout.integerValue == STPCardFieldTypeCVC);
|
|
XCTAssertTrue([expectedImgData isEqualToData:imgData]);
|
|
XCTAssertEqualObjects(self.sut.numberField.text, number);
|
|
XCTAssertEqualObjects(self.sut.expirationField.text, @"10/99");
|
|
XCTAssertEqual(self.sut.cvcField.text.length, (NSUInteger)0);
|
|
XCTAssertTrue([self.sut.cvcField isFirstResponder], @"after `setCardParams:`, when firstResponder becomes valid, first invalid field should become firstResponder");
|
|
XCTAssertFalse(self.sut.isValid);
|
|
}
|
|
|
|
- (void)testSetCard_number_whileEditingCVC {
|
|
XCTAssertTrue([self.sut.cvcField becomeFirstResponder], @"text field is not first responder");
|
|
STPPaymentMethodCardParams *card = [STPPaymentMethodCardParams new];
|
|
NSString *number = @"4242424242424242";
|
|
card.number = number;
|
|
[self.sut setPaymentMethodParams:[STPPaymentMethodParams paramsWithCard:card billingDetails:nil metadata:nil]];
|
|
|
|
NSData *imgData = UIImagePNGRepresentation(self.sut.brandImageView.image);
|
|
NSData *expectedImgData = UIImagePNGRepresentation([STPPaymentCardTextField cvcImageForCardBrand:STPCardBrandVisa]);
|
|
|
|
XCTAssertNotNil(self.sut.focusedTextFieldForLayout);
|
|
XCTAssertTrue(self.sut.focusedTextFieldForLayout.integerValue == STPCardFieldTypeCVC);
|
|
XCTAssertTrue([expectedImgData isEqualToData:imgData]);
|
|
XCTAssertEqualObjects(self.sut.numberField.text, number);
|
|
XCTAssertEqual(self.sut.expirationField.text.length, (NSUInteger)0);
|
|
XCTAssertEqual(self.sut.cvcField.text.length, (NSUInteger)0);
|
|
XCTAssertTrue([self.sut.cvcField isFirstResponder], @"after `setCardParams:`, if firstResponder is invalid, it should remain firstResponder");
|
|
XCTAssertFalse(self.sut.isValid);
|
|
}
|
|
|
|
- (void)testSetCard_empty_whileEditingNumber {
|
|
self.sut.numberField.text = @"4242424242424242";
|
|
self.sut.cvcField.text = @"123";
|
|
self.sut.expirationField.text = @"10/99";
|
|
XCTAssertTrue([self.sut.numberField becomeFirstResponder], @"text field is not first responder");
|
|
STPPaymentMethodCardParams *card = [STPPaymentMethodCardParams new];
|
|
[self.sut setPaymentMethodParams:[STPPaymentMethodParams paramsWithCard:card billingDetails:nil metadata:nil]];
|
|
|
|
NSData *imgData = UIImagePNGRepresentation(self.sut.brandImageView.image);
|
|
NSData *expectedImgData = UIImagePNGRepresentation([STPPaymentCardTextField brandImageForCardBrand:STPCardBrandUnknown]);
|
|
|
|
XCTAssertNotNil(self.sut.focusedTextFieldForLayout);
|
|
XCTAssertTrue(self.sut.focusedTextFieldForLayout.integerValue == STPCardFieldTypeNumber);
|
|
XCTAssertTrue([expectedImgData isEqualToData:imgData]);
|
|
XCTAssertEqual(self.sut.numberField.text.length, (NSUInteger)0);
|
|
XCTAssertEqual(self.sut.expirationField.text.length, (NSUInteger)0);
|
|
XCTAssertEqual(self.sut.cvcField.text.length, (NSUInteger)0);
|
|
XCTAssertTrue([self.sut.numberField isFirstResponder], @"after `setCardParams:` that clears the text fields, the first invalid field should become firstResponder");
|
|
XCTAssertFalse(self.sut.isValid);
|
|
}
|
|
|
|
- (void)testIsValidKVO {
|
|
id observer = OCMClassMock([UIViewController class]);
|
|
self.sut.numberField.text = @"4242424242424242";
|
|
self.sut.expirationField.text = @"10/99";
|
|
self.sut.postalCodeField.text = @"90210";
|
|
XCTAssertFalse(self.sut.isValid);
|
|
|
|
NSString *expectedKeyPath = @"sut.isValid";
|
|
[self addObserver:observer forKeyPath:expectedKeyPath options:NSKeyValueObservingOptionNew context:nil];
|
|
XCTestExpectation *exp = [self expectationWithDescription:@"observeValue"];
|
|
OCMStub([observer observeValueForKeyPath:[OCMArg any] ofObject:[OCMArg any] change:[OCMArg any] context:nil])
|
|
.andDo(^(NSInvocation *invocation) {
|
|
NSString *keyPath;
|
|
NSDictionary *change;
|
|
[invocation getArgument:&keyPath atIndex:2];
|
|
[invocation getArgument:&change atIndex:4];
|
|
if ([keyPath isEqualToString:expectedKeyPath]) {
|
|
if ([change[@"new"] boolValue]) {
|
|
[exp fulfill];
|
|
[self removeObserver:observer forKeyPath:@"sut.isValid"];
|
|
}
|
|
}
|
|
});
|
|
|
|
self.sut.cvcField.text = @"123";
|
|
|
|
[self waitForExpectationsWithTimeout:TestConstants.STPTestingNetworkRequestTimeout handler:nil];
|
|
}
|
|
|
|
- (void)testBecomeFirstResponder {
|
|
self.sut.postalCodeEntryEnabled = NO;
|
|
XCTAssertTrue([self.sut canBecomeFirstResponder]);
|
|
XCTAssertTrue([self.sut becomeFirstResponder]);
|
|
XCTAssertTrue(self.sut.isFirstResponder);
|
|
|
|
XCTAssertEqual(self.sut.numberField, self.sut.currentFirstResponderField);
|
|
|
|
[self.sut becomeFirstResponder];
|
|
XCTAssertEqual(self.sut.numberField, self.sut.currentFirstResponderField,
|
|
@"Repeated calls to becomeFirstResponder should not change the firstResponder");
|
|
|
|
self.sut.numberField.text = @"4242" "4242" "4242" "4242";
|
|
|
|
// Don't unit test auto-advance from number field here because we don't know the cache state
|
|
|
|
XCTAssertTrue([self.sut.cvcField becomeFirstResponder]);
|
|
XCTAssertEqual(self.sut.cvcField, self.sut.currentFirstResponderField,
|
|
@"We don't block other fields from becoming firstResponder");
|
|
|
|
XCTAssertTrue([self.sut becomeFirstResponder]);
|
|
XCTAssertEqual(self.sut.cvcField, self.sut.currentFirstResponderField,
|
|
@"Calling becomeFirstResponder does not change the currentFirstResponder");
|
|
|
|
self.sut.expirationField.text = @"10/99";
|
|
self.sut.cvcField.text = @"123";
|
|
|
|
[self.sut resignFirstResponder];
|
|
XCTAssertTrue([self.sut canBecomeFirstResponder]);
|
|
XCTAssertTrue([self.sut becomeFirstResponder]);
|
|
|
|
XCTAssertEqual(self.sut.cvcField, self.sut.currentFirstResponderField,
|
|
@"When all fields are valid, the last one should be the preferred firstResponder");
|
|
|
|
self.sut.postalCodeEntryEnabled = YES;
|
|
XCTAssertFalse(self.sut.isValid);
|
|
|
|
[self.sut resignFirstResponder];
|
|
XCTAssertTrue([self.sut becomeFirstResponder]);
|
|
XCTAssertEqual(self.sut.postalCodeField, self.sut.currentFirstResponderField,
|
|
@"When postalCodeEntryEnabled=YES, it should become firstResponder after other fields are valid");
|
|
|
|
self.sut.expirationField.text = @"";
|
|
[self.sut resignFirstResponder];
|
|
XCTAssertTrue([self.sut becomeFirstResponder]);
|
|
XCTAssertEqual(self.sut.expirationField, self.sut.currentFirstResponderField,
|
|
@"Moves firstResponder back to expiration, because it's not valid anymore");
|
|
|
|
self.sut.expirationField.text = @"10/99";
|
|
self.sut.postalCodeField.text = @"90210";
|
|
|
|
[self.sut resignFirstResponder];
|
|
XCTAssertTrue([self.sut becomeFirstResponder]);
|
|
XCTAssertEqual(self.sut.postalCodeField, self.sut.currentFirstResponderField,
|
|
@"When all fields are valid, the last one should be the preferred firstResponder");
|
|
}
|
|
|
|
- (void)testShouldReturnCyclesThroughFields {
|
|
PaymentCardTextFieldBlockDelegate *delegate = [PaymentCardTextFieldBlockDelegate new];
|
|
delegate.willEndEditingForReturn = ^(__unused STPPaymentCardTextField *textField) {
|
|
XCTFail(@"Did not expect editing to end in this test");
|
|
};
|
|
self.sut.delegate = delegate;
|
|
|
|
[self.sut becomeFirstResponder];
|
|
XCTAssertTrue(self.sut.numberField.isFirstResponder);
|
|
|
|
XCTAssertFalse([self.sut.numberField.delegate textFieldShouldReturn:self.sut.numberField], @"shouldReturn = NO");
|
|
XCTAssertTrue(self.sut.expirationField.isFirstResponder, @"with side effect to move 1st responder to next field");
|
|
|
|
XCTAssertFalse([self.sut.expirationField.delegate textFieldShouldReturn:self.sut.expirationField], @"shouldReturn = NO");
|
|
XCTAssertTrue(self.sut.cvcField.isFirstResponder, @"with side effect to move 1st responder to next field");
|
|
|
|
XCTAssertFalse([self.sut.cvcField.delegate textFieldShouldReturn:self.sut.cvcField], @"shouldReturn = NO");
|
|
XCTAssertTrue(self.sut.postalCodeField.isFirstResponder, @"with side effect to move 1st responder to next field");
|
|
|
|
XCTAssertFalse([self.sut.postalCodeField.delegate textFieldShouldReturn:self.sut.postalCodeField], @"shouldReturn = NO");
|
|
XCTAssertTrue(self.sut.numberField.isFirstResponder, @"with side effect to move 1st responder from last field to first invalid field");
|
|
}
|
|
|
|
- (void)testShouldReturnCyclesThroughFieldsWithoutPostal {
|
|
PaymentCardTextFieldBlockDelegate *delegate = [PaymentCardTextFieldBlockDelegate new];
|
|
delegate.willEndEditingForReturn = ^(__unused STPPaymentCardTextField *textField) {
|
|
XCTFail(@"Did not expect editing to end in this test");
|
|
};
|
|
self.sut.delegate = delegate;
|
|
self.sut.postalCodeEntryEnabled = NO;
|
|
|
|
[self.sut becomeFirstResponder];
|
|
XCTAssertTrue(self.sut.numberField.isFirstResponder);
|
|
|
|
XCTAssertFalse([self.sut.numberField.delegate textFieldShouldReturn:self.sut.numberField], @"shouldReturn = NO");
|
|
XCTAssertTrue(self.sut.expirationField.isFirstResponder, @"with side effect to move 1st responder to next field");
|
|
|
|
XCTAssertFalse([self.sut.expirationField.delegate textFieldShouldReturn:self.sut.expirationField], @"shouldReturn = NO");
|
|
XCTAssertTrue(self.sut.cvcField.isFirstResponder, @"with side effect to move 1st responder to next field");
|
|
|
|
XCTAssertFalse([self.sut.cvcField.delegate textFieldShouldReturn:self.sut.cvcField], @"shouldReturn = NO");
|
|
XCTAssertTrue(self.sut.numberField.isFirstResponder, @"with side effect to move 1st responder from last field to first invalid field");
|
|
}
|
|
|
|
- (void)testShouldReturnDismissesWhenValidNoPostalCode {
|
|
__block BOOL hasReturned = NO;
|
|
__block BOOL didEnd = NO;
|
|
|
|
self.sut.postalCodeEntryEnabled = NO;
|
|
[self.sut setPaymentMethodParams:[STPPaymentMethodParams paramsWithCard:[STPFixtures paymentMethodCardParams] billingDetails:nil metadata:nil]];
|
|
|
|
PaymentCardTextFieldBlockDelegate *delegate = [PaymentCardTextFieldBlockDelegate new];
|
|
delegate.willEndEditingForReturn = ^(__unused STPPaymentCardTextField *textField) {
|
|
XCTAssertFalse(didEnd, @"willEnd is called before didEnd");
|
|
XCTAssertFalse(hasReturned, @"willEnd is only called once");
|
|
hasReturned = YES;
|
|
};
|
|
delegate.didEndEditing = ^(__unused STPPaymentCardTextField *textField) {
|
|
XCTAssertTrue(hasReturned, @"didEndEditing should be called after willEnd");
|
|
XCTAssertFalse(didEnd, @"didEnd is only called once");
|
|
didEnd = YES;
|
|
};
|
|
|
|
self.sut.delegate = delegate;
|
|
[self.sut becomeFirstResponder];
|
|
XCTAssertTrue(self.sut.cvcField.isFirstResponder, @"when textfield is filled out, default first responder is the last field");
|
|
|
|
XCTAssertFalse(hasReturned, @"willEndEditingForReturn delegate method should not have been called yet");
|
|
XCTAssertFalse([self.sut.cvcField.delegate textFieldShouldReturn:self.sut.cvcField], @"shouldReturn = NO");
|
|
|
|
XCTAssertNil(self.sut.currentFirstResponderField, @"Should have resigned first responder");
|
|
XCTAssertTrue(hasReturned, @"delegate method has been invoked");
|
|
XCTAssertTrue(didEnd, @"delegate method has been invoked");
|
|
}
|
|
|
|
- (void)testShouldReturnDismissesWhenValid {
|
|
__block BOOL hasReturned = NO;
|
|
__block BOOL didEnd = NO;
|
|
|
|
[self.sut setPaymentMethodParams:[STPPaymentMethodParams paramsWithCard:[STPFixtures paymentMethodCardParams] billingDetails:nil metadata:nil]];
|
|
self.sut.postalCodeField.text = @"90210";
|
|
PaymentCardTextFieldBlockDelegate *delegate = [PaymentCardTextFieldBlockDelegate new];
|
|
delegate.willEndEditingForReturn = ^(__unused STPPaymentCardTextField *textField) {
|
|
XCTAssertFalse(didEnd, @"willEnd is called before didEnd");
|
|
XCTAssertFalse(hasReturned, @"willEnd is only called once");
|
|
hasReturned = YES;
|
|
};
|
|
delegate.didEndEditing = ^(__unused STPPaymentCardTextField *textField) {
|
|
XCTAssertTrue(hasReturned, @"didEndEditing should be called after willEnd");
|
|
XCTAssertFalse(didEnd, @"didEnd is only called once");
|
|
didEnd = YES;
|
|
};
|
|
|
|
self.sut.delegate = delegate;
|
|
[self.sut becomeFirstResponder];
|
|
XCTAssertTrue(self.sut.postalCodeField.isFirstResponder, @"when textfield is filled out, default first responder is the last field");
|
|
|
|
XCTAssertFalse(hasReturned, @"willEndEditingForReturn delegate method should not have been called yet");
|
|
XCTAssertFalse([self.sut.postalCodeField.delegate textFieldShouldReturn:self.sut.postalCodeField], @"shouldReturn = NO");
|
|
|
|
XCTAssertNil(self.sut.currentFirstResponderField, @"Should have resigned first responder");
|
|
XCTAssertTrue(hasReturned, @"delegate method has been invoked");
|
|
XCTAssertTrue(didEnd, @"delegate method has been invoked");
|
|
}
|
|
|
|
@end
|