├── .editorconfig ├── CHANGELOG.MD ├── LICENSE ├── README.md ├── composer.json └── src └── Provider ├── ResourceOwner.php └── Slack.php /.editorconfig: -------------------------------------------------------------------------------- 1 | root = true 2 | 3 | [*] 4 | charset = utf-8 5 | indent_size = 4 6 | indent_style = space 7 | end_of_line = lf 8 | insert_final_newline = true 9 | trim_trailing_whitespace = true 10 | -------------------------------------------------------------------------------- /CHANGELOG.MD: -------------------------------------------------------------------------------- 1 | # CHANGELOG 2 | 3 | ## 0.1.0 4 | 5 | ### Added 6 | - Basic slack resource owner 7 | - Initial commit 8 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | The MIT License (MIT) 2 | 3 | Copyright (c) 2015 Madewithlove 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy of 6 | this software and associated documentation files (the "Software"), to deal in 7 | the Software without restriction, including without limitation the rights to 8 | use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of 9 | the Software, and to permit persons to whom the Software is furnished to do so, 10 | subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS 17 | FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 18 | COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER 19 | IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN 20 | CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 21 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # Slack Provider for OAuth 2.0 Client 2 | [![Latest Version](https://img.shields.io/github/release/bramdevries/oauth2-slack.svg?style=flat-square)](https://github.com/bramdevries/oauth2-slack/releases) 3 | [![Software License](https://img.shields.io/badge/license-MIT-brightgreen.svg?style=flat-square)](LICENSE.md) 4 | [![Build Status](https://img.shields.io/travis/bramdevries/oauth2-slack/master.svg?style=flat-square)](https://travis-ci.org/bramdevries/oauth2-slack) 5 | [![Total Downloads](https://img.shields.io/packagist/dt/bramdevries/oauth2-slack.svg?style=flat-square)](https://packagist.org/packages/bramdevries/oauth2-slack) 6 | 7 | This package provides Slack OAuth 2.0 support for the PHP League's [OAuth 2.0 Client](https://github.com/thephpleague/oauth2-client). 8 | 9 | ## Installation 10 | 11 | To install, use composer: 12 | 13 | ``` 14 | composer require bramdevries/oauth2-slack 15 | ``` 16 | 17 | ## Usage 18 | 19 | Usage is the same as The League's OAuth client, using `\League\OAuth2\Client\Provider\Slack` as the provider. 20 | 21 | ### Authorization Code Flow 22 | 23 | ```php 24 | $provider = new League\OAuth2\Client\Provider\Slack([ 25 | 'clientId' => '{slack-client-id}', 26 | 'clientSecret' => '{slack-client-secret}', 27 | 'redirectUri' => 'https://example.com/callback-url', 28 | ]); 29 | 30 | if (!isset($_GET['code'])) { 31 | 32 | // If we don't have an authorization code then get one 33 | $authUrl = $provider->getAuthorizationUrl(); 34 | $_SESSION['oauth2state'] = $provider->getState(); 35 | header('Location: '.$authUrl); 36 | exit; 37 | 38 | // Check given state against previously stored one to mitigate CSRF attack 39 | } elseif (empty($_GET['state']) || ($_GET['state'] !== $_SESSION['oauth2state'])) { 40 | 41 | unset($_SESSION['oauth2state']); 42 | exit('Invalid state'); 43 | 44 | } else { 45 | 46 | // Try to get an access token (using the authorization code grant) 47 | $token = $provider->getAccessToken('authorization_code', [ 48 | 'code' => $_GET['code'] 49 | ]); 50 | 51 | // Optional: Now you have a token you can look up a users profile data 52 | try { 53 | 54 | // We got an access token, let's now get the user's details 55 | $user = $provider->getResourceOwner($token); 56 | 57 | // Use these details to create a new profile 58 | printf('Hello %s!', $user->getNickname()); 59 | 60 | } catch (Exception $e) { 61 | 62 | // Failed to get user details 63 | exit('Oh dear...'); 64 | } 65 | 66 | // Use this to interact with an API on the users behalf 67 | echo $token->getToken(); 68 | } 69 | ``` 70 | 71 | ### Managing Scopes 72 | 73 | When creating your Slack authorization URL, you can specify the state and scopes your application may authorize. 74 | 75 | ```php 76 | $options = [ 77 | 'state' => 'OPTIONAL_CUSTOM_CONFIGURED_STATE', 78 | 'scope' => ['identify','read','post'] // array or string 79 | ]; 80 | 81 | $authorizationUrl = $provider->getAuthorizationUrl($options); 82 | ``` 83 | If neither are defined, the provider will utilize internal defaults. 84 | 85 | At the time of authoring this documentation, the [following scopes are available](https://api.slack.com/docs/oauth). 86 | 87 | - identify 88 | - read 89 | - post 90 | - client 91 | - admin 92 | 93 | ## Testing 94 | 95 | ``` bash 96 | $ ./vendor/bin/phpunit 97 | ``` 98 | ## Credits 99 | 100 | - [Bram Devries](https://github.com/bramdevries) 101 | - [All Contributors](https://github.com/bramdevries/oauth2-slack/contributors) 102 | 103 | 104 | ## License 105 | 106 | The MIT License (MIT). Please see [License File](https://github.com/bramdevries/oauth2-slack/blob/master/LICENSE) for more information. 107 | -------------------------------------------------------------------------------- /composer.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "bramdevries/oauth2-slack", 3 | "description": "Slack OAuth 2.0 Client Provider for The PHP League OAuth2-Client", 4 | "license": "MIT", 5 | "authors": [ 6 | { 7 | "name": "Bram Devries", 8 | "email": "bram@madewithlove.be", 9 | "homepage": "https://github.com/bramdevries" 10 | } 11 | ], 12 | "keywords": [ 13 | "oauth", 14 | "oauth2", 15 | "client", 16 | "authorization", 17 | "authorisation", 18 | "slack" 19 | ], 20 | "require": { 21 | "php": ">=5.5.0", 22 | "league/oauth2-client": "~1.0" 23 | }, 24 | "require-dev": { 25 | "phpunit/phpunit": "^4.8", 26 | "mockery/mockery": "^0.9.4" 27 | }, 28 | "autoload": { 29 | "psr-4": { 30 | "Bramdevries\\Oauth\\Client\\": "src" 31 | } 32 | }, 33 | "autoload-dev": { 34 | "psr-4": { 35 | "Bramdevries\\Oauth\\Client\\": "spec" 36 | } 37 | }, 38 | "scripts": { 39 | "test": "phpunit" 40 | } 41 | } 42 | -------------------------------------------------------------------------------- /src/Provider/ResourceOwner.php: -------------------------------------------------------------------------------- 1 | details = $details; 22 | } 23 | 24 | /** 25 | * @return string 26 | */ 27 | public function getId() 28 | { 29 | return $this->details['user_id']; 30 | } 31 | 32 | /** 33 | * @return array 34 | */ 35 | public function toArray() 36 | { 37 | return $this->details; 38 | } 39 | 40 | } 41 | -------------------------------------------------------------------------------- /src/Provider/Slack.php: -------------------------------------------------------------------------------- 1 | domain.'/oauth/authorize'; 24 | } 25 | 26 | /** 27 | * @param array $params 28 | * 29 | * @return string 30 | */ 31 | public function getBaseAccessTokenUrl(array $params) 32 | { 33 | return $this->domain.'/api/oauth.access'; 34 | } 35 | 36 | /** 37 | * @param AccessToken $token 38 | * 39 | * @return string 40 | */ 41 | public function getResourceOwnerDetailsUrl(AccessToken $token) 42 | { 43 | return $this->domain.'/api/auth.test?token='.$token->getToken(); 44 | } 45 | 46 | /** 47 | * @return array 48 | */ 49 | protected function getDefaultScopes() 50 | { 51 | return []; 52 | } 53 | 54 | /** 55 | * @param ResponseInterface $response 56 | * @param array|string $data 57 | * 58 | * @throws IdentityProviderException 59 | */ 60 | protected function checkResponse(ResponseInterface $response, $data) 61 | { 62 | if (!$data['ok'] || $response->getStatusCode() >= 400) { 63 | throw new IdentityProviderException( 64 | $data['error'] ?: $response->getReasonPhrase(), 65 | $response->getStatusCode(), 66 | $response 67 | ); 68 | } 69 | } 70 | 71 | /** 72 | * @param array $response 73 | * @param AccessToken $token 74 | * 75 | * @return ResourceOwner 76 | */ 77 | protected function createResourceOwner(array $response, AccessToken $token) 78 | { 79 | return new ResourceOwner($response); 80 | } 81 | 82 | } 83 | --------------------------------------------------------------------------------