diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..88e99d5 --- /dev/null +++ b/.gitignore @@ -0,0 +1,2 @@ +vendor +composer.lock \ No newline at end of file diff --git a/LICENSE.md b/LICENSE.md new file mode 100644 index 0000000..8e2244d --- /dev/null +++ b/LICENSE.md @@ -0,0 +1,21 @@ +The MIT License (MIT) + +Copyright (c) Spatie bvba + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in +all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +THE SOFTWARE. \ No newline at end of file diff --git a/README.md b/README.md new file mode 100644 index 0000000..ce3d343 --- /dev/null +++ b/README.md @@ -0,0 +1,140 @@ +# Authenticate with CoderYouth + +[![Latest Version on Packagist](https://img.shields.io/packagist/v/coderyouth/socialite.svg?style=flat-square)](https://packagist.org/packages/coderyouth/socialite) +[![Total Downloads](https://img.shields.io/packagist/dt/coderyouth/socialite.svg?style=flat-square)](https://packagist.org/packages/coderyouth/socialite) + +## Installation + +### 1. Install the package via composer: + +```bash +composer require coderyouth/socialite +``` + +### 2. Install the service provider + +- Remove `Laravel\Socialite\SocialiteServiceProvider` from your `providers[]` array in `config\app.php` if you have added it already. + +- Add `\SocialiteProviders\Manager\ServiceProvider::class` to your `providers[]` array in `config\app.php`. + +For example: + +``` php +'providers' => [ + // a whole bunch of providers + // remove 'Laravel\Socialite\SocialiteServiceProvider', + \SocialiteProviders\Manager\ServiceProvider::class, // add +]; +``` + +* Note: If you would like to use the Socialite Facade, you need to [install it.](https://github.com/laravel/socialite) + +### 3. Event Listener + +* Add `SocialiteProviders\Manager\SocialiteWasCalled` event to your `listen[]` array in `app/Providers/EventServiceProvider`. + +* Add `'SocialiteProviders\\Imgur\\ImgurExtendSocialite@handle',` to the `SocialiteWasCalled` array. + +For example: + +```php +/** + * The event handler mappings for the application. + * + * @var array + */ +protected $listen = [ + \SocialiteProviders\Manager\SocialiteWasCalled::class => [ + \CoderYouth\Socialite\CoderYouthExtendSocialite::class, + ], +]; +``` + +### 4. Configuration setup + +You will need to add an entry to the services configuration file so that after config files are cached for usage in production environment (Laravel command `artisan config:cache`) all config is still available. + +#### Add to `config/services.php`. + +```php +'coderyouth' => [ + 'client_id' => env('CODERYOUTH_KEY'), + 'client_secret' => env('CODERYOUTH_SECRET'), + 'redirect' => env('CODERYOUTH_REDIRECT') +], +``` + +## Usage + +* [Laravel docs on configuration](http://laravel.com/docs/master/configuration) + +* You should now be able to use it like you would regularly use Socialite (assuming you have the facade installed): + +```php +return Socialite::with('coderyouth')->redirect(); +``` + +### Lumen Support + +You can use Socialite providers with Lumen. Just make sure that you have facade support turned on and that you follow the setup directions properly. + +**Note:** If you are using this with Lumen, all providers will automatically be stateless since **Lumen** does not keep track of state. + +Also, configs cannot be parsed from the `services[]` in Lumen. You can only set the values in the `.env` file as shown exactly in this document. If needed, you can also override a config (shown below). + +### Stateless + +* You can set whether or not you want to use the provider as stateless. + +**Note:** If you are using this with Lumen, all providers will automatically be stateless since **Lumen** does not keep track of state. + +```php +// to turn off stateless +return Socialite::with('coderyouth')->stateless(false)->redirect(); + +// to use stateless +return Socialite::with('coderyouth')->stateless()->redirect(); +``` + +### Overriding a config + +If you need to override the provider's environment or config variables dynamically anywhere in your application, you may use the following: + +```php +$clientId = "secret"; + +$clientSecret = "secret"; + +$redirectUrl = "http://yourdomain.com/api/redirect"; + +$additionalProviderConfig = ['site' => 'meta.stackoverflow.com']; + +$config = new \SocialiteProviders\Manager\Config($clientId, $clientSecret, $redirectUrl, $additionalProviderConfig); +return Socialite::with('coderyouth')->setConfig($config)->redirect(); +``` + +### Retrieving the Access Token Response Body + +Laravel Socialite by default only allows access to the `access_token`. Which can be accessed +via the `\Laravel\Socialite\User->token` public property. Sometimes you need access to the whole response body which +may contain items such as a `refresh_token`. + +You can get the access token response body, after you called the `user()` method in Socialite, by accessing the property `$user->accessTokenResponseBody`; + +```php +$user = Socialite::driver('coderyouth')->user(); +$accessTokenResponseBody = $user->accessTokenResponseBody; +``` + +### Security + +If you discover any security related issues, please email soy@miguelpiedrafita.com instead of using the issue tracker. + +## Credits + +- [Miguel Piedrafita](https://github.com/m1guelpf) +- [All Contributors](../../contributors) + +## License + +The MIT License (MIT). Please see [License File](LICENSE.md) for more information. \ No newline at end of file diff --git a/composer.json b/composer.json new file mode 100644 index 0000000..4245428 --- /dev/null +++ b/composer.json @@ -0,0 +1,18 @@ +{ + "name": "coderyouth/socialite", + "description": "CoderYouth OAuth2 Provider for Laravel Socialite", + "license": "MIT", + "authors": [{ + "name": "Miguel Piedrafita", + "email": "soy@miguelpiedrafita.com" + }], + "require": { + "php": "^5.6 || ^7.0", + "socialiteproviders/manager": "~2.0 || ~3.0" + }, + "autoload": { + "psr-4": { + "CoderYouth\\Socialite\\": "src" + } + } +} diff --git a/src/CoderYouthExtendSocialite.php b/src/CoderYouthExtendSocialite.php new file mode 100644 index 0000000..1f37eae --- /dev/null +++ b/src/CoderYouthExtendSocialite.php @@ -0,0 +1,21 @@ +extendSocialite( + 'coderyouth', + Provider::class + ); + } +} diff --git a/src/Provider.php b/src/Provider.php new file mode 100644 index 0000000..cfcf436 --- /dev/null +++ b/src/Provider.php @@ -0,0 +1,75 @@ +buildAuthUrlFromBase( + 'https://accounts.coderyouth.club/oauth/authorize', + $state + ); + } + + /** + * {@inheritdoc} + */ + protected function getTokenUrl() + { + return 'https://accounts.coderyouth.club/oauth/token'; + } + + /** + * {@inheritdoc} + */ + protected function getUserByToken($token) + { + $response = $this->getHttpClient()->get( + 'https://accounts.coderyouth.club/api/me', + [ + 'headers' => [ + 'Authorization' => 'Bearer '.$token, + ], + ] + ); + + return json_decode($response->getBody()->getContents(), true); + } + + /** + * {@inheritdoc} + */ + protected function mapUserToObject(array $user) + { + return (new User())->setRaw($user)->map([ + 'id' => $user['id'], + 'name' => $user['first_name'].' '.$user['last_name'], + 'email' => $user['email'], + 'avatar' => $user['avatar'], + 'username' => $user['username'], + ]); + } + + /** + * {@inheritdoc} + */ + protected function getTokenFields($code) + { + return array_merge(parent::getTokenFields($code), [ + 'grant_type' => 'authorization_code', + ]); + } +}