Сегодня у нас статья Якова Ильина об In-App Purchases для iPhone-приложений.

Введение

In-App Purchases — это простой и удобный механизм для организации продаж своих приложений или дополнительных фич непосредственно из своего приложения. In-App Purchases легко встраивается и открывает для Вас новый канал продаж. Взаимодействие с App Store осуществляется с помощью StoreKit.framework, который поставляется вместе с SDK, начиная с версии 3.0.

Общая информация

In-App Purchases бывает трех типов:

  • Consumables
  • Non-Consumables
  • Subscriptions

Consumable – потребляемый тип. Purchase такого типа может покупаться несколько раз. Например, в игре Eliminate игрок покупает себе энергию, которая со временем растрачивается и приходится покупать ее заново, либо ждать три часа, пока энергия востановится.

Non-Consumable— непотребляемый тип. Purchase покупается только один раз. Его обычно используют для разблокировки новых тем, дополнительных уровней и т.п.

Subscription— подписка на что-либо. Например, Вы можете написать iPhone-приложение для Web-сервиса, в котором есть Premium аккаунт, открывающий дополнительные возможности. С помощью Subscription Вы сможете аккаунт активировать, скажем, на месяц или на год.

Реализовать In-App Purchases можно с помощью двух моделей:

  • Встроенная модель
  • Серверная модель

Встроенная модель позволяет разблокировать фичи. Как правило, использование данной модели побуждает разработчиков встраивать их в приложение зарание. При такой реализации, StoreKit отвечает только за оплату фичи. В общем случае, с помощью StoreKit мы можем узнать прошла ли покупка или не прошла.

Серверная модель является более гибкой. В модели принимают участие три сущности: iPhone-приложение, сервер Apple и наш сервер. Все новые фичи хранятся на нашем сервере, поэтому нет необходимости обновлять приложение при добавлении новых фич или продуктов. Работает модель следующим образом:

  1. iPhone-приложение запрашивает список продуктов у своего сервера,
  2. iPhone-приложение отображает новые продукты пользователю,
  3. Пользователь покупает (или не покупает 🙂 )
  4. iPhone-приложение запрашивает покупку у сервера Apple через StoreKit,
  5. StoreKit возвращает ответ,
  6. iPhone-приложение отсылает ответ на свой сервер
  7. Еще раз проверяется ответ (обязательно проверяется, что ответ пришел от Apple),
  8. После этого iPhone-приложение скачивает со своего сервера новый продукт.

В данном посте рассматривается встроенная модель.

Реализация

Работу встроенной модели In-App Purchases я продемонстрирую на тестовом примере AppPurchasesExample. Это небольшое iPhone-приложение с 3 окнами. Первое (оно же главное) окно будет доступно пользователю по-умолчанию. Это окно будет содержать информацию о двух других окнах, разблокировать которые можно только за деньги.

Шаг 1. Создание App ID

Заходим на iPhone Developer Program Portal и открываем вкладку App IDs:

В правом верхнем углу экрана нажимаем New App ID. Затем вводим информацию о приложении. Для своего примера я заполнил форму так:

Для создания Bundle Identifier Apple рекомендует использовать нотацию Reverse DNS, что гарантирует уникальность Вашего Identifier и избавит Вас от дальнейших проблем при публикации приложения.Очень Важно не использовать символ ‘*’ в Bundle Identifier. Если ввести ‘com.wordpress.indiedevelop.*’, то In-App Purchases работать не будет.

Далее необходимо включить In App Purchases для App ID. В списке App IDs, напротив нужного Bundle Identifier в графе Action следует нажать Configure. Появится форма Configure App ID, на которой необходимо включить checkBox ‘Enable In App Purchase’.

Шаг 2. Создание Development профиля
  1. В левом столбце нужно нажать на ‘Provisioning’ и перейти на вкладку ‘Development’.
  2. Нажать ‘New Profile’ и заполнить всю необходимую информацию. Поле Profile Name может быть любое (я записал ‘InAppPurchasesExample Dev’).
  3. В появившемся списке созданный профиль имеет статус pending. Нужно обновить страницу, либо перейти на другую вкладку и обратно, тогда профиль станет доступен для скачивания.
  4. Профиль можно скачивать и устанавливать в xCode. Для установки достаточно просто нажать на профиль двойным кликом, либо перетащить профайл на иконку xCode.

Если профиль установился правильно, тогда в xCode откроется Organizer и вы увидите примерно следующее:

Шаг 3. Создание приложения в iTunes Connect

Для того, чтобы протестировать наше In-App Purchase приложение, его нужно обязательно создать в iTunes Connect. Чтобы это сделать:

  1. Необходимо перейти в iTunes Connect и нажать ‘Manage Your Applications->Add New Application’.
  2. На вопрос ‘Does your product contain encryption?’ ответить отрицательно.
  3. Заполнить форму, где нужно указать имя приложения, описание, номер версии, категорию и т.д. Все достаточно тривиально. Затруднения может вызвать разве что поле ‘SKU Number’. Это поле должно быть уникальным, я ввел в нем ‘IAPEX’ (сокращение от In-App Purchases Example).
  4. На форме ‘Upload’ необходимо выставить флаг ‘Upload application binary later’. Все остальные параметры и формы для тестого примера никакого значения не имеют.
Шаг 4. Создание In-App Purchases в iTunes Connect
  1. В iTunes Connect необходимо нажать ‘Manage Your In App Purchases->Create New’ и выбрать необходимое приложение.
  2. Выбрать Bundle ID и заполнить инфрормацию о Purchase (тип, название, цену и т.д.) Также нужно ввести ‘Product ID’, который может быть произвольным, но я советую использовать Reverse DNS. Лучше всего Product ID формировать из Bundle ID вашего приложения и имени фичи. Для моего примера это выглядит так:

Для тестового приложения я создал два In-App продукта с Product Id ‘com.wordpress.indiedevelop.InAppPurchasesExample.f1’ и ‘com.wordpress.indiedevelop.InAppPurchasesExample.f2’. Обе фичи с типом Non-Consumables.

Шаг 5. Создание тестового пользователя

Для тестирования In-App Purchases необходимо создать хотя бы одного тестового пользователя. Делается это просто:

  1. В iTunes Connect необходимо перейти на ‘Manage Users->In App Purchase Test User’
  2. Нажать ‘Add New User’
  3. Ввести информацию о пользователе

E-mail пользователя не обязательно должен быть реальным. Для своего примера я создал одного тестового пользователя:

Важный момент. Если у Вас не закончен контракт с Apple, тогда In-App Purchase работать у Вас не будет. Для того, чтобы закончить контракт, необходимо указать Contact Info, Bank Info и Tax Info.

Шаг 6. Программирование

Для своего тестового примера я создал каркас проекта и User Interface:

Для работы с App Store я рекомендую использовать MKStoreKit, разработанный в 2009 году разработчиком Кумаром (Mugunth Kumar). Данный набор классов значительно облегчит работу со StoreKit. Кроме MKStoreKit, в проект необходимо добавить StoreKit.framework.

В своем примере я использую слегка модернизированную первую весрию MKStoreKit. Для удобства я добавил к классу MKStoreManager делегат следующего вида:

@protocol MKStoreKitDelegate @optional
- (void)productAPurchased;
- (void)productBPurchased;
- (void)failed;
@end

Делегату посылается сообщение productAPurchased когда куплена фича 1, productBPurchased — когда куплена фича 2 и failed — когда пользователь либо отменил покупку, либо покупка не прошла.

Класс-Singleton MKStoreManager является основным в MKStoreKit. Так выглядит его объявление:

@interface MKStoreManager : NSObject<SKProductsRequestDelegate> {
    ...
}

// делегат
@property (nonatomic, retain) id<MKStoreKitDelegate> delegate;
// продукты, доступные для покупки
@property (nonatomic, retain) NSMutableArray *purchasableObjects;

// фабричный метод для Singleton
+ (MKStoreManager*)sharedManager;

// методы для покупки фич
- (void) buyFeatureA;
- (void) buyFeatureB;

// методы позволяют узнать куплена ли фича
+ (BOOL) featureAPurchased;
+ (BOOL) featureBPurchased;
...
@end

Рассмотрим использование класса на моем тестовом примере.

Сначала в файле MKStoreManager.m я прописал Product ID своих фич:

static NSString *featureAId = @"com.wordpress.indiedevelop.InAppPurchasesExample.f1";
static NSString *featureBId = @"com.wordpress.indiedevelop.InAppPurchasesExample.f2";

Также нужно проверить были ли куплены фичи программы. Основной класс примера унаследован от UIViewController, поэтому код проверки целесообразно встроить в метод viewDidLoad:

- (void)viewDidLoad {
  [super viewDidLoad];

  [MKStoreManager sharedManager].delegate = self; // назначаем делагата для объекта MKStoreManager

  if ([MKStoreManager featureAPurchased]) // если куплена фича 1
  {
    feature1Button.hidden = YES; // скрываем кнопку 'Купить фичу 1'
    seeFeature1Button.hidden = NO; // показываем кнопку 'Перейти на фичу 1'
  }

  if ([MKStoreManager featureBPurchased]) // если куплена фича 2
  {
    feature2Button.hidden = YES; // скрываем кнопку 'Купить фичу 2'
    seeFeature2Button.hidden = NO; // показываем кнопку 'Перейти на фичу 2'
  }
}

Внутри MKStoreKit информация о том, куплен ли продукт сохраняется через NSUserDefaults, поэтому при удалении приложения информация сбрасывается. Однако, пользователь не будет покупать фичи два раза, поскольку StoreKit откроет доступ к фиче бесплатно.

Дальше нужно реализовать методы ‘Купить’. Они привязаны к событию TouchUpInside соотвествующих кнопок:

-(IBAction)feature1ButtonPressed
{
  [self showLockView]; // показываем пользователю, что происходит загрузка
  [[MKStoreManager sharedManager] buyFeatureA]; // посылаем сообщение магазину 'Купить фичу 1'
}

-(IBAction)feature2ButtonPressed
{
  [self showLockView]; // показываем пользователю, что происходит загрузка
  [[MKStoreManager sharedManager] buyFeatureB]; // посылаем сообщение магазину 'Купить фичу 2'
}

Далее я реализовал методы делегата MKStoreKitDelegate:

// фича 1 куплена
- (void)productAPurchased
{
  [self hideLockView]; // скрываем отображение загрузки
  feature1Button.hidden = YES; // скрываем кнопку 'Купить'
  seeFeature1Button.hidden = NO; // показываем кнопку 'Перейти'
}

// фича 2 куплена
- (void)productBPurchased
{
  [self hideLockView]; // скрываем отображение загрузки
  feature2Button.hidden = YES; // скрываем кнопку 'Купить'
  seeFeature2Button.hidden = NO; // показываем кнопку 'Перейти'
}

// покупка не прошла, либо была отменена
- (void)failed
{
  [self hideLockView]; // скрываем отображение загрузки
}

Новые фичи реализованы в виде отдельных UIView под управлением UIViewController. Переход на новые фичи я реализовал с помощь UINavigationController:

// перейти на фичу 1
-(IBAction)seeFeature1
{
  [self.navigationController pushViewController:feature1ViewController animated:YES];
}

// перейти на фичу 2
-(IBAction)seeFeature2
{
  [self.navigationController pushViewController:feature2ViewController animated:YES];
}

Также при манипуляции с магазином можно добавить проверку на его доступность. Это делается так:

if ([SKPaymentQueue canMakePayments])
{
... // Отобразить магазин пользователю
}
else
{
... // Уведомить пользователя, что Purchases недоступны
}

Как видите все достаточно просто. Остается скопилировать и тестировать 🙂

Шаг 7. Тестирование

Чтобы протестировать In-App Purchases нужно скомпилировать, установить и запустить приложение. При тестировании следует помнить следующее:

  1. Тестировать Purchases можно только на устройстве.
  2. Перед тестированием необходимо выйти из iTunes на своем iPhone. Это делается через ‘Settings->Store->Sign Out’.
  3. При тестировании, в сообщениях с предложением купить фичу, будет появляться [Environment: sandbox] — это признак тестового режима.
  4. Тестировать можно только тест-аккаунтами (см. Шаг 5)
Тестовый пример InAppPurchasesExample

В результате у меня получилось приложение, которое может разблокировать два дополнительных окна. Это приложение можно использовать в качестве примера для создания своих In-App Purchase проектов.

Исходный код

Оригинал статьи в блоге автора.

Скриншоты:

Previous ArticleNext Article
Технический директор IT-Dimension, компании-разработчика кросс-платформенного программного обеспечения

This post has 1 Comment

1

Leave a Reply

Your email address will not be published. Required fields are marked *

Ж.

Жесть какая! .NET для iPhone!

И вот такое бывает… живут себе люди, и тут БДЫЩЬ! и такая вещь случается, после которой “Ваш мир уже никогда не будет таким как раньше” (с).

Компания Novell после полуторамесячного бета-тестирования выпустила финальную версию среды разработки MonoTouch 1.0.

Теперь приложения на .NET можно запускать и на iPod/iPhone.

К сожалению, для того чтобы разрабатывать с использованием MonoTouch, все еще необходимым требованием является наличие Mac машины и установленного iPhone SDK. В комплект MonoTouch включены утилиты и библиотеки, необходимые для интеграции с iPhone SDK  и XCode IDE, а также с MonoDevelop IDE.

.NET для iPhone – это чудесно. Но MonoTouch – штука платная, персональная лицензия стоит $399, Enterprise лицензия на 5 пользователей – $3999.

В.

Взломать приложение для iPhone теперь проще простого

CrackulousВ сети появилась информация о программе Crackulous для iPhone, которая позволяет буквально одним кликом взломать защиту любого приложения из магазина AppStore. После взлома приложение можно устанавливать на любой другой iPhone или iPod Touch.

Аналогичные инструменты были доступны и раньше, но в силу своей сложности они так и не получили широкого распространения, так что найти в интернете взломанные версии программ для iPhone было довольно тяжело.

Неприятная новость для разработчиков, которые зарабатывают на продажах ПО через AppStore заключается в том, что в скором времени авторы программы обещают выложить и исходники.

Хотя есть примеры, когда взлом приложения для iPhone помог значительно увеличить популярность и продажи.