Проверяем валидность внутриигровых покупок через Google API

Проблема и решение Я думаю многие знают что такое Freedom. Для тех кто не знает — это приложение под Android, позволяющее делать внутриигровые покупки в других приложениях без траты денег. Описание: Вам надоели предложения в играх и программах что-то купить (расширения, монетки и т.п.)? Покупайте их бесплатно с помощью Freedom! Пользоваться очень просто: устанавливаете, запускаете (первый запуск может занять какое-то время — до нескольких минут), тапаете по приложению — оно запускается. После этого оно возможно пройдёт проверку лицензии, а при покупке из приложения Вы сможете расплачиваться фэйковой карточкой.

Ссылка на статью автора: habrahabr.ru/post/163547/Я до определенной поры игнорировал этот прискорбный факт, тем более что я в какой-то степени согласен с автором, что те кто пользуются этим софтом и так врядли бы купили что-то у меня в игре. Но новый проект над которым мы работаем должен стать мультиплеерным. А это значит, что читеры получат реальное преимущество перед обычными игроками, что меня не особо радует.Покурив вечером мануалы по Google API я решил соорудить собственную проверку валидности покупок. Т.к. мы используем Unity3D + Prime31 IAP, пришлось их немного обработать напильником, чтобы они начали выдавать purchase token.Для меня архитектура этого дела выглядит вот так:

f1f31d675df54452e9f11071c2fa6876.png

Два веб-сервера нужны для того чтобы отделить логику работы конкретной игры от проверки валидности покупки, которая общая для всех игр.

Алгоритм такой:

Клиент совершает покупку и получает токен Клиент делает запрос на веб сервер его игры, передавая токен и тип покупки Веб сервер игры делает запрос к серверу лицензий Сервер лицензий делает запрос к Google API В случае успешного ответа, веб сервер игры начисляет игровую валюту и отправляет клиенту результат Техническая часть Про веб сервер игры я писать не буду, так как это выходит за рамки этой статьи.Сервер лицензий написан на Django. Для тех кто желает написать велосипед самостоятельно — в конце статьи есть куски кода на питоне.GitHub source: github.com/Agasper/django-google-play-check-payment

Установка Создаем виртуальное окружение, клонируем проект и устанавливаем зависимости virtualenv . git clone https://github.com/Agasper/django-google-play-check-payment.git project source ./bin/activate pip install -r ./project/req.txt Создаем аккаунт и генерируем ключи Идем на console.developers.google.com/project Создаем новый проект, например «Payment check» Переходим в Project → APIS & AUTH → APIs и включаем Google Play Android Developer API Идем в Project → APIS & AUTH → Credentials, нажимаем Create new Client ID и создаем новый Service Account Запоминаем e-mail, генерируем и скачиваем новый P12 ключ Переименуйте его в key.p12 и положите в директорию keys в корне проекта Перейдите в play.google.com/apps/publish/ раздел Настройки → Аккаунты и права доступа Нажмите Пригласить пользователя и введите e-mail сервисного аккаунта, который вы создали в пункте 4–5 Дайте этому пользователю права Финансы Проверка Все что написано ниже запускается в тестовом режиме, если вы хотите использовать Django в боевых условиях, то есть отдельные статьи как это настроить. Например вот: habrahabr.ru/post/226419/ ./manage.py runserver 0.0.0.0:8000 Пример запроса: http://host:8000/license? package=&sku=&service=&key=&token= , где: package — название пакета вашего приложения, например: net.solargames.dungeonexplorer2 product_id — идентификатор вашей внутриигровой покупки, например: net.solargames.dungeonexplorer2.gold service — e-mail вашего сервисного аккаунта из пункта 5 выше key — название файла с ключом без расширения, в примере был «key» token — токен покупки, выдается гуглом при совершении покупки на устройстве Ответ в случае успешной покупки: и если кто-то подсунул неверный токен отличаются статусом, в случае успеха он равен нулю.Тут разобраны внутренности проекта, для тех кому интересно Кишки Для работы требуется Google API Python Client, для удобства я статично добавил его в проект.Линк: code.google.com/p/google-api-python-client/source/browse/Вся магия содержится в одной маленькой функции:

from oauth2client.client import SignedJwtAssertionCredentials from apiclient.discovery import build

credentials = SignedJwtAssertionCredentials ( service, key_content, scope='https://www.googleapis.com/auth/androidpublisher')

http = httplib2.Http () http = credentials.authorize (http) service = build («androidpublisher», «v1.1», http=http) result = service.inapppurchases ().get (packageName=package, productId=sku, token=token).execute (http=http) Внутри result лежит dict с параметрами покупки. В случае ошибки возникнет Exception с довольно скудным описанием проблемы

© Habrahabr.ru