diff --git a/bin/build-release.sh b/bin/build-release.sh
index b44cba2586b37f168543bebbb201079e347b2be0..18f46d8bf583cd2ca4ea9e4dafb8140b1c0b840d 100755
--- a/bin/build-release.sh
+++ b/bin/build-release.sh
@@ -48,6 +48,7 @@ php "$TARGET/composer.phar" install --no-dev --prefer-dist -o -d "$TARGET"
 
 # Install external modules
 php "$TARGET/composer.phar" require --update-no-dev simplesamlphp/simplesamlphp-module-authfacebook
+php "$TARGET/composer.phar" require --update-no-dev simplesamlphp/simplesamlphp-module-authlinkedin
 php "$TARGET/composer.phar" require --update-no-dev simplesamlphp/simplesamlphp-module-authtwitter
 php "$TARGET/composer.phar" require --update-no-dev simplesamlphp/simplesamlphp-module-authwindowslive
 php "$TARGET/composer.phar" require --update-no-dev simplesamlphp/simplesamlphp-module-cdc
diff --git a/composer.json b/composer.json
index 2c1704bdbcb22f9acc58da9a46f48e486c83cfb0..41404e9a7bb896f5a3fa57119bc7db95d75c94a9 100644
--- a/composer.json
+++ b/composer.json
@@ -42,6 +42,7 @@
         "robrichards/xmlseclibs": "^3.0",
         "simplesamlphp/saml2": "^3.3",
         "simplesamlphp/simplesamlphp-module-authfacebook": "^1.0",
+        "simplesamlphp/simplesamlphp-module-authlinkedin": "^1.0",
         "simplesamlphp/simplesamlphp-module-authtwitter": "^1.0",
         "simplesamlphp/simplesamlphp-module-authwindowslive": "^1.0",
         "simplesamlphp/simplesamlphp-module-cdc": "^1.0",
diff --git a/modules/authlinkedin/default-disable b/modules/authlinkedin/default-disable
deleted file mode 100644
index fa0bd82e2df7bd79d57593d35bc53c1f9d3ef71f..0000000000000000000000000000000000000000
--- a/modules/authlinkedin/default-disable
+++ /dev/null
@@ -1,3 +0,0 @@
-This file indicates that the default state of this module
-is disabled. To enable, create a file named enable in the
-same directory as this file.
diff --git a/modules/authlinkedin/docs/oauthlinkedin.md b/modules/authlinkedin/docs/oauthlinkedin.md
deleted file mode 100644
index df437006f6b5c3bcd75a5005d95b55a2fc4da0ae..0000000000000000000000000000000000000000
--- a/modules/authlinkedin/docs/oauthlinkedin.md
+++ /dev/null
@@ -1,26 +0,0 @@
-Using the LinkedIn authentication source with SimpleSAMLphp
-===========================================================
-
-Remember to configure `authsources.php`, with both Consumer key and secret. Optionally you can set which attributes are requested from LinkedIn, the list of available attributes can be found here <https://developer.linkedin.com/docs/fields>.
-
-To get an API key and a secret, register the application at:
-
- * <https://www.linkedin.com/secure/developer>
-
-Set the callback URL to be:
-
- * `http://sp.example.org/simplesaml/module.php/authlinkedin/linkback.php`
-
-Replace `sp.example.org` with your hostname.
-
-## Testing authentication
-
-On the SimpleSAMLphp frontpage, go to the *Authentication* tab, and use the link:
-
-  * *Test configured authentication sources*
-
-Then choose the *linkedin* authentication source.
-
-Expected behaviour would then be that you are sent to LinkedIn and asked to login.
-There is no consent screen for attribute release.
-
diff --git a/modules/authlinkedin/lib/Auth/Source/LinkedIn.php b/modules/authlinkedin/lib/Auth/Source/LinkedIn.php
deleted file mode 100644
index f270834c73b5b47e20aad2a478264c763e03d2fa..0000000000000000000000000000000000000000
--- a/modules/authlinkedin/lib/Auth/Source/LinkedIn.php
+++ /dev/null
@@ -1,200 +0,0 @@
-<?php
-
-namespace SimpleSAML\Module\authlinkedin\Auth\Source;
-
-require_once(dirname(dirname(dirname(dirname(dirname(__FILE__))))).'/oauth/libextinc/OAuth.php');
-
-/**
- * Authenticate using LinkedIn.
- *
- * @author Brook Schofield, TERENA.
- * @package SimpleSAMLphp
- */
-
-class LinkedIn extends \SimpleSAML\Auth\Source
-{
-    /**
-     * The string used to identify our states.
-     */
-    const STAGE_INIT = 'authlinkedin:init';
-
-    /**
-     * The key of the AuthId field in the state.
-     */
-    const AUTHID = 'authlinkedin:AuthId';
-
-    /** @var string */
-    private $key;
-
-    /** @var string */
-    private $secret;
-
-    /** @var string */
-    private $attributes;
-
-
-    /**
-     * Constructor for this authentication source.
-     *
-     * @param array $info  Information about this authentication source.
-     * @param array $config  Configuration.
-     * @throws \Exception
-     */
-    public function __construct($info, $config)
-    {
-        assert(is_array($info));
-        assert(is_array($config));
-
-        // Call the parent constructor first, as required by the interface
-        parent::__construct($info, $config);
-
-        if (!array_key_exists('key', $config)) {
-            throw new \Exception('LinkedIn authentication source is not properly configured: missing [key]');
-        }
-
-        $this->key = $config['key'];
-
-        if (!array_key_exists('secret', $config)) {
-            throw new \Exception('LinkedIn authentication source is not properly configured: missing [secret]');
-        }
-
-        $this->secret = $config['secret'];
-
-        if (array_key_exists('attributes', $config)) {
-            $this->attributes = $config['attributes'];
-        } else {
-            // Default values if the attributes are not set in config (ref https://developer.linkedin.com/docs/fields)
-            $this->attributes = 'id,first-name,last-name,headline,summary,specialties,picture-url,email-address';
-        }
-    }
-
-
-    /**
-     * Log-in using LinkedIn platform
-     * Documentation at: http://developer.linkedin.com/docs/DOC-1008
-     *
-     * @param array &$state  Information about the current authentication.
-     * @return void
-     */
-    public function authenticate(&$state)
-    {
-        assert(is_array($state));
-
-        // We are going to need the authId in order to retrieve this authentication source later
-        $state[self::AUTHID] = $this->authId;
-
-        $stateID = \SimpleSAML\Auth\State::getStateId($state);
-        \SimpleSAML\Logger::debug('authlinkedin auth state id = '.$stateID);
-
-        $consumer = new \SimpleSAML\Module\oauth\Consumer($this->key, $this->secret);
-
-        // Get the request token
-        $requestToken = $consumer->getRequestToken(
-            'https://api.linkedin.com/uas/oauth/requestToken',
-            [
-                'oauth_callback' => \SimpleSAML\Module::getModuleUrl('authlinkedin').'/linkback.php?stateid='.$stateID
-            ]
-        );
-
-        \SimpleSAML\Logger::debug(
-            "Got a request token from the OAuth service provider [".
-            $requestToken->key."] with the secret [".$requestToken->secret."]"
-        );
-
-        $state['authlinkedin:requestToken'] = $requestToken;
-
-        // Update the state
-        \SimpleSAML\Auth\State::saveState($state, self::STAGE_INIT);
-
-        // Authorize the request token
-        $consumer->getAuthorizeRequest('https://www.linkedin.com/uas/oauth/authenticate', $requestToken);
-    }
-
-
-    /**
-     * @param array &$state
-     * @return void
-     */
-    public function finalStep(&$state)
-    {
-        $requestToken = $state['authlinkedin:requestToken'];
-
-        $consumer = new \SimpleSAML\Module\oauth\Consumer($this->key, $this->secret);
-
-        \SimpleSAML\Logger::debug(
-            "oauth: Using this request token [".
-            $requestToken->key."] with the secret [".$requestToken->secret."]"
-        );
-
-        // Replace the request token with an access token (via GET method)
-        $accessToken = $consumer->getAccessToken(
-            'https://api.linkedin.com/uas/oauth/accessToken',
-            $requestToken,
-            ['oauth_verifier' => $state['authlinkedin:oauth_verifier']]
-        );
-
-        \SimpleSAML\Logger::debug(
-            "Got an access token from the OAuth service provider [".
-            $accessToken->key."] with the secret [".$accessToken->secret."]"
-        );
-
-        $userdata = $consumer->getUserInfo(
-            'https://api.linkedin.com/v1/people/~:('.$this->attributes.')',
-            $accessToken,
-            ['http' => ['header' => 'x-li-format: json']]
-        );
-
-        $attributes = $this->flatten($userdata, 'linkedin.');
-
-        // TODO: pass accessToken: key, secret + expiry as attributes?
-
-        if (array_key_exists('id', $userdata)) {
-            $attributes['linkedin_targetedID'] = ['http://linkedin.com!'.$userdata['id']];
-            $attributes['linkedin_user'] = [$userdata['id'].'@linkedin.com'];
-        }
-
-        \SimpleSAML\Logger::debug('LinkedIn Returned Attributes: '.implode(", ", array_keys($attributes)));
-
-        $state['Attributes'] = $attributes;
-    }
-
-    /**
-     * takes an associative array, traverses it and returns the keys concatenated with a dot
-     *
-     * e.g.:
-     *
-     * [
-     *   'linkedin' => [
-     *     'location' =>  [
-     *       'id' => '123456'
-     *       'country' => [
-     *          'code' => 'de'
-     *       ]
-     *   ]
-     * ]
-     *
-     * become:
-     *
-     * [
-     *   'linkedin.location.id' => [0 => '123456'],
-     *   'linkedin.location.country.code' => [0 => 'de']
-     * ]
-     *
-     * @param array $array
-     * @param string $prefix
-     *
-     * @return array the array with the new concatenated keys
-     */
-    protected function flatten($array, $prefix = '')
-    {
-        $result = [];
-        foreach ($array as $key => $value) {
-            if (is_array($value)) {
-                $result = $result + $this->flatten($value, $prefix.$key.'.');
-            } else {
-                $result[$prefix.$key] = [$value];
-            }
-        }
-        return $result;
-    }
-}
diff --git a/modules/authlinkedin/www/linkback.php b/modules/authlinkedin/www/linkback.php
deleted file mode 100644
index 922e157fccc47364a60220ab511bf1366cae153b..0000000000000000000000000000000000000000
--- a/modules/authlinkedin/www/linkback.php
+++ /dev/null
@@ -1,34 +0,0 @@
-<?php
-
-/**
- * Handle linkback() response from LinkedIn.
- */
-
-if (!array_key_exists('stateid', $_REQUEST)) {
-    throw new \Exception('Lost OAuth Client State');
-}
-$state = \SimpleSAML\Auth\State::loadState(
-    $_REQUEST['stateid'],
-    \SimpleSAML\Module\authlinkedin\Auth\Source\LinkedIn::STAGE_INIT
-);
-
-// http://developer.linkedin.com/docs/DOC-1008#2_Redirect_the_User_to_our_Authorization_Server
-if (array_key_exists('oauth_verifier', $_REQUEST)) {
-    $state['authlinkedin:oauth_verifier'] = $_REQUEST['oauth_verifier'];
-} else {
-    throw new Exception('OAuth verifier not returned.');
-}
-
-// Find authentication source
-assert(array_key_exists(\SimpleSAML\Module\authlinkedin\Auth\Source\LinkedIn::AUTHID, $state));
-$sourceId = $state[\SimpleSAML\Module\authlinkedin\Auth\Source\LinkedIn::AUTHID];
-
-/** @var \SimpleSAML\Module\authlinkedin\Auth\Source\LinkedIn|null $source */
-$source = \SimpleSAML\Auth\Source::getById($sourceId);
-if ($source === null) {
-    throw new \Exception('Could not find authentication source with id '.$sourceId);
-}
-
-$source->finalStep($state);
-
-\SimpleSAML\Auth\Source::completeAuth($state);