PHPackages                             znerol/oauth2-server-storeauth-grant - PHPackages - PHPackages  [Skip to content](#main-content)[PHPackages](/)[Directory](/)[Categories](/categories)[Trending](/trending)[Leaderboard](/leaderboard)[Changelog](/changelog)[Analyze](/analyze)[Collections](/collections)[Log in](/login)[Sign up](/register)

1. [Directory](/)
2. /
3. [Authentication &amp; Authorization](/categories/authentication)
4. /
5. znerol/oauth2-server-storeauth-grant

ActiveLibrary[Authentication &amp; Authorization](/categories/authentication)

znerol/oauth2-server-storeauth-grant
====================================

Google Billing / Apple StoreKit OAuth2 Grant Extension for PHP OAuth 2.0 Server

2.0.0(1y ago)0160MITPHPPHP ^8.2

Since Jun 20Pushed 1y ago1 watchersCompare

[ Source](https://github.com/znerol/oauth2-server-storeauth-grant)[ Packagist](https://packagist.org/packages/znerol/oauth2-server-storeauth-grant)[ RSS](/packages/znerol-oauth2-server-storeauth-grant/feed)WikiDiscussions main Synced 2d ago

READMEChangelogDependencies (14)Versions (6)Used By (0)

Google Billing / Apple StoreKit OAuth2 Grant Extension for PHP OAuth 2.0 Server
===============================================================================

[](#google-billing--apple-storekit-oauth2-grant-extension-for-php-oauth-20-server)

An OAuth 2 [extension grant](https://datatracker.ietf.org/doc/html/rfc6749#section-4.5) which validates a Google Billing purchase or an Apple StoreKit transaction and returns an access token restricted to the specified SKU/product.

Dependencies
------------

[](#dependencies)

Some PSR-18 HTTP client.

Flow (Android Billing)
----------------------

[](#flow-android-billing)

The client sends a POST request with following body parameters to the authorization server:

- `grant_type` with the value `urn:uuid:ea31e77f-cb72-486f-b5c4-deef43e839f3`
- `client_id` with the client’s ID
- `scope` with a space-delimited list of requested scope permissions
- `purchase_token` with the android billing purchase token

The authorization server will respond with a JSON object containing the following properties:

- `token_type` with the value `Bearer`
- `expires_in` with an integer representing the TTL of the access token
- `access_token` a JWT signed with the authorization server’s private key

Flow (Apple StoreKit)
---------------------

[](#flow-apple-storekit)

The client sends a POST request with following body parameters to the authorization server:

- `grant_type` with the value: `urn:uuid:c7e545a5-d72b-4294-a173-bb1858aae099`
- `client_id` with the client’s ID
- `scope` with a space-delimited list of requested scope permissions
- `transaction_id` with the StoreKit transaction id

The authorization server will respond with a JSON object containing the following properties:

- `token_type` with the value `Bearer`
- `expires_in` with an integer representing the TTL of the access token
- `access_token` a JWT signed with the authorization server’s private key

Setup
-----

[](#setup)

Wherever you initialize your objects, initialize a new instance of the authorization server and bind the storage interfaces and authorization code grant:

```
// Init our repositories
$clientRepository = new ClientRepository(); // instance of ClientRepositoryInterface
$scopeRepository = new ScopeRepository(); // instance of ScopeRepositoryInterface
$accessTokenRepository = new AccessTokenRepository(); // instance of AccessTokenRepositoryInterface

// Path to public and private keys
$privateKey = 'file://path/to/private.key';
//$privateKey = new CryptKey('file://path/to/private.key', 'passphrase'); // if private key has a pass phrase
$encryptionKey = 'lxZFUEsBCJ2Yb14IF2ygAHI5N4+ZAUXXaSeeJm6+twsUmIen'; // generate using base64_encode(random_bytes(32))

// Setup the authorization server
$server = new \League\OAuth2\Server\AuthorizationServer(
    $clientRepository,
    $accessTokenRepository,
    $scopeRepository,
    $privateKey,
    $encryptionKey
);
```

For google non-consumables:

```
// Init non-consumable product repository
$productRepository = ProductRepository() // instance of NonConsumableRepositoryInterface

// Init google client factory
$googleClientFactory = GoogleClientFactory() // instance of GoogleProductPurchaseFactoryInterface

// Enable the Android purchases product grant on the server
$packageName = 'com.some.thing';
$clientCredentials = // path to google api service account client credentials
$server->enableGrantType(
    new \StoreAuth\OAuth2\Server\Grant\GoogleNonConsumable($productRepository, $googleClientFactory),
    new \DateInterval('PT1H') // access tokens will expire after 1 hour
);
```

For apple non-consumables:

```
// Init non-consumable product repository
$productRepository = ProductRepository() // instance of NonConsumableRepositoryInterface

// Init apple client factory
$appleClientFactory = AppleClientFactory() // instance of AppleMostRecentTransactionFactoryInterface

// Enable the Apple transactions grant on the server
$server->enableGrantType(
    new \StoreAuth\OAuth2\Server\Grant\AppleNonConsumable($productRepository, $appleClientFactory),
    new \DateInterval('PT1H') // access tokens will expire after 1 hour
);
```

License
-------

[](#license)

[MIT License](https://opensource.org/license/mit)

###  Health Score

31

—

LowBetter than 66% of packages

Maintenance41

Moderate activity, may be stable

Popularity10

Limited adoption so far

Community7

Small or concentrated contributor base

Maturity57

Maturing project, gaining track record

 Bus Factor1

Top contributor holds 100% of commits — single point of failure

How is this calculated?**Maintenance (25%)** — Last commit recency, latest release date, and issue-to-star ratio. Uses a 2-year decay window.

**Popularity (30%)** — Total and monthly downloads, GitHub stars, and forks. Logarithmic scaling prevents top-heavy scores.

**Community (15%)** — Contributors, dependents, forks, watchers, and maintainers. Measures real ecosystem engagement.

**Maturity (30%)** — Project age, version count, PHP version support, and release stability.

###  Release Activity

Cadence

Every ~83 days

Total

4

Last Release

495d ago

Major Versions

1.0.2 → 2.0.02025-02-24

### Community

Maintainers

![](https://avatars.githubusercontent.com/u/23288?v=4)[znerol](/maintainers/znerol)[@znerol](https://github.com/znerol)

---

Top Contributors

[![znerol](https://avatars.githubusercontent.com/u/23288?v=4)](https://github.com/znerol "znerol (15 commits)")

###  Code Quality

TestsPHPUnit

Static AnalysisPHPStan

Code StylePHP\_CodeSniffer

Type Coverage Yes

### Embed Badge

![Health badge](/badges/znerol-oauth2-server-storeauth-grant/health.svg)

```
[![Health](https://phpackages.com/badges/znerol-oauth2-server-storeauth-grant/health.svg)](https://phpackages.com/packages/znerol-oauth2-server-storeauth-grant)
```

###  Alternatives

[shopware/platform

The Shopware e-commerce core

3.4k1.5M3](/packages/shopware-platform)[tempest/framework

The PHP framework that gets out of your way.

2.2k34.4k15](/packages/tempest-framework)[shopware/core

Shopware platform is the core for all Shopware ecommerce products.

585.6M572](/packages/shopware-core)[cakephp/cakephp

The CakePHP framework

8.9k19.5M1.8k](/packages/cakephp-cakephp)[flow-php/flow

PHP ETL - Extract Transform Load - Data processing framework

85036.3k](/packages/flow-php-flow)[aporat/store-receipt-validator

PHP receipt validator for Apple App Store and Amazon Appstore

6544.0M13](/packages/aporat-store-receipt-validator)

PHPackages © 2026

[Directory](/)[Categories](/categories)[Trending](/trending)[Changelog](/changelog)[Analyze](/analyze)
