Kaynağa Gözat

Added Plex oAuth (First Phase Testing)

causefx 7 yıl önce
ebeveyn
işleme
e3fc969660

+ 2 - 1
api/config/default.php

@@ -188,5 +188,6 @@ return array(
 	'customThemeJava' => '',
 	'minimalLoginScreen' => false,
 	'unsortedTabs' => 'top',
-	'cacheImageSize' => '2'
+	'cacheImageSize' => '2',
+	'plexoAuth' => false
 );

+ 44 - 21
api/functions/api-functions.php

@@ -6,7 +6,7 @@
 function login($array)
 {
 	// Grab username and Password from login form
-	$username = $password = '';
+	$username = $password = $oAuth = $oAuthType = '';
 	foreach ($array['data'] as $items) {
 		foreach ($items as $key => $value) {
 			if ($key == 'name') {
@@ -22,6 +22,7 @@ function login($array)
 	}
 	$username = strtolower($username);
 	$days = (isset($remember)) ? 7 : 1;
+	$oAuth = (isset($oAuth)) ? $oAuth : false;
 	try {
 		$database = new Dibi\Connection([
 			'driver' => 'sqlite3',
@@ -29,31 +30,53 @@ function login($array)
 		]);
 		$authSuccess = false;
 		$function = 'plugin_auth_' . $GLOBALS['authBackend'];
-		$result = $database->fetch('SELECT * FROM users WHERE username = ? COLLATE NOCASE OR email = ? COLLATE NOCASE', $username, $username);
-		switch ($GLOBALS['authType']) {
-			case 'external':
-				if (function_exists($function)) {
-					$authSuccess = $function($username, $password);
-				}
-				break;
-			/** @noinspection PhpMissingBreakStatementInspection */
-			case 'both':
-				if (function_exists($function)) {
-					$authSuccess = $function($username, $password);
-				}
-			// no break
-			default: // Internal
-				if (!$authSuccess) {
-					// perform the internal authentication step
-					if (password_verify($password, $result['password'])) {
-						$authSuccess = true;
+		if (!$oAuth) {
+			$result = $database->fetch('SELECT * FROM users WHERE username = ? COLLATE NOCASE OR email = ? COLLATE NOCASE', $username, $username);
+			switch ($GLOBALS['authType']) {
+				case 'external':
+					if (function_exists($function)) {
+						$authSuccess = $function($username, $password);
 					}
-				}
+					break;
+				/** @noinspection PhpMissingBreakStatementInspection */
+				case 'both':
+					if (function_exists($function)) {
+						$authSuccess = $function($username, $password);
+					}
+				// no break
+				default: // Internal
+					if (!$authSuccess) {
+						// perform the internal authentication step
+						if (password_verify($password, $result['password'])) {
+							$authSuccess = true;
+						}
+					}
+			}
+		} else {
+			// Has oAuth Token!
+			switch ($oAuthType) {
+				case 'plex':
+					$tokenInfo = checkPlexToken($oAuth);
+					if ($tokenInfo) {
+						$authSuccess = array(
+							'username' => $tokenInfo['user']['username'],
+							'email' => $tokenInfo['user']['email'],
+							'image' => $tokenInfo['user']['thumb'],
+							'token' => $tokenInfo['user']['authToken']
+						);
+						$authSuccess = ((!empty($GLOBALS['plexAdmin']) && strtolower($GLOBALS['plexAdmin']) == strtolower($tokenInfo['user']['username'])) || checkPlexUser($tokenInfo['user']['username'])) ? $authSuccess : false;
+					}
+					break;
+				default:
+					return 'error';
+					break;
+			}
+			$result = ($authSuccess) ? $database->fetch('SELECT * FROM users WHERE username = ? COLLATE NOCASE OR email = ? COLLATE NOCASE', $authSuccess['username'], $authSuccess['email']) : '';
 		}
 		if ($authSuccess) {
 			// Make sure user exists in database
 			$userExists = false;
-			$passwordMatches = false;
+			$passwordMatches = ($oAuth) ? true : false;
 			$token = (is_array($authSuccess) && isset($authSuccess['token']) ? $authSuccess['token'] : '');
 			if ($result['username']) {
 				$userExists = true;

+ 24 - 0
api/functions/auth-functions.php

@@ -36,6 +36,30 @@ function authRegister($username, $password, $defaults, $email)
 	return false;
 }
 
+function checkPlexToken($token = '')
+{
+	try {
+		if (($token !== '')) {
+			$url = 'https://plex.tv/users/account.json';
+			$headers = array(
+				'X-Plex-Token' => $token,
+				'Content-Type' => 'application/json',
+				'Accept' => 'application/json'
+			);
+			$response = Requests::get($url, $headers);
+			if ($response->success) {
+				return json_decode($response->body, true);
+			}
+		} else {
+			return false;
+		}
+		
+	} catch (Requests_Exception $e) {
+		writeLog('success', 'Plex Token Check Function - Error: ' . $e->getMessage(), SYSTEM);
+	}
+	return false;
+}
+
 function checkPlexUser($username)
 {
 	try {

+ 22 - 0
api/functions/organizr-functions.php

@@ -473,6 +473,13 @@ function getSettingsMain()
 				'href' => '#auth-plex-machine-form',
 				'attr' => 'data-effect="mfp-3d-unfold"'
 			),
+			array(
+				'type' => 'switch',
+				'name' => 'plexoAuth',
+				'label' => 'Enable Plex oAuth',
+				'class' => 'popup-with-form plexAuth switchAuth',
+				'value' => $GLOBALS['plexoAuth']
+			),
 			array(
 				'type' => 'input',
 				'name' => 'authBackendHost',
@@ -1279,6 +1286,21 @@ function showLogin()
 	}
 }
 
+function showoAuth()
+{
+	$buttons = '';
+	if ($GLOBALS['plexoAuth']) {
+		$buttons .= '<a href="javascript:void(0)" onclick="oAuth(\'plex\')" class="btn bg-plex text-muted" data-toggle="tooltip" title="" data-original-title="Login with Plex"> <i aria-hidden="true" class="mdi mdi-plex"></i> </a>';
+	}
+	return ($buttons) ? '
+		<div class="row">
+            <div class="col-xs-12 col-sm-12 col-md-12 m-t-10 text-center">
+                <div class="social">' . $buttons . '</div>
+            </div>
+        </div>
+	' : '';
+}
+
 function getImages()
 {
 	$dirname = dirname(__DIR__, 2) . DIRECTORY_SEPARATOR . 'plugins' . DIRECTORY_SEPARATOR . 'images' . DIRECTORY_SEPARATOR . 'tabs' . DIRECTORY_SEPARATOR;

+ 20 - 4
api/pages/login.php

@@ -7,6 +7,20 @@ $pageLogin = '
     <div class="white-box">
       <form class="form-horizontal" id="loginform" onsubmit="return false;">
         <a href="javascript:void(0)" class="text-center db visible-xs" id="login-logo">' . logoOrText() . '</a>
+        <div id="oAuth-div" class="form-group hidden">
+          <div class="col-xs-12">
+            <div class="panel panel-success animated tada">
+                <div class="panel-heading"> oAuth
+                    <div class="pull-right"><a href="#" data-perform="panel-collapse"><i class="ti-minus"></i></a> <a href="#" data-perform="panel-dismiss"><i class="ti-close"></i></a> </div>
+                </div>
+                <div class="panel-wrapper collapse in" aria-expanded="true">
+                    <div class="panel-body">
+	                   oAuth Was Successful - Please wait...
+                    </div>
+                </div>
+            </div>
+          </div>
+        </div>
 		<div id="tfa-div" class="form-group hidden">
           <div class="col-xs-12">
             <div class="panel panel-warning animated tada">
@@ -26,19 +40,19 @@ $pageLogin = '
         </div>
         <div class="form-group m-t-40">
           <div class="col-xs-12">
-            <input class="form-control" name="username" type="text" required="" placeholder="Username" autofocus>
+            <input id="login-username-Input" class="form-control" name="username" type="text" required="" placeholder="Username" autofocus>
           </div>
         </div>
         <div class="form-group">
           <div class="col-xs-12">
-            <input class="form-control" name="password" type="password" required="" placeholder="Password" lang="en">
+            <input id="login-password-Input" class="form-control" name="password" type="password" required="" placeholder="Password" lang="en">
           </div>
         </div>
         <div class="form-group">
           <div class="col-md-12">
             <div class="checkbox checkbox-primary pull-left p-t-0 remember-me">
               <input id="checkbox-login" name="remember" type="checkbox" checked>
-              <label for="checkbox-signup" lang="en">Remember Me</label>
+              <label for="checkbox-login" lang="en">Remember Me</label>
             </div>
         	</div>
         </div>
@@ -47,9 +61,11 @@ $pageLogin = '
             <button class="btn btn-info btn-lg btn-block text-uppercase waves-effect waves-light login-button" type="submit" lang="en">Login</button>
           </div>
         </div>
-
+		' . showoAuth() . '
         <div class="form-group m-b-0">
           <div class="col-sm-12 text-center">
+          	<input id="oAuth-Input" class="form-control" name="oAuth" type="hidden">
+            <input id="oAuthType-Input" class="form-control" name="oAuthType" type="hidden">
             ' . showLogin() . '
           </div>
         </div>

+ 73 - 0
js/functions.js

@@ -4678,6 +4678,79 @@ function homepageCalendar(timeout){
 	if(typeof timeouts['calendar'] !== 'undefined'){ clearTimeout(timeouts['calendar']); }
 	timeouts['calendar'] = setTimeout(function(){ homepageCalendar(timeout); }, timeout);
 }
+function oAuthLoop(type,code) {
+    switch(type) {
+        case 'plex':
+            return $.ajax({
+                type: 'GET',
+                headers: {
+                    'X-Plex-Product':'Organizr',
+                    'X-Plex-Version':'2.0',
+                    'X-Plex-Client-Identifier':'01010101-10101010'
+                },
+                url: 'https://plex.tv/api/v2/pins/'+code,
+            });
+        default:
+            break;
+    }
+}
+function oAuth(type){
+    switch(type){
+        case 'plex':
+            $.ajax({
+                type: 'POST',
+                headers: {
+                    'X-Plex-Product':'Organizr',
+                    'X-Plex-Version':'2.0',
+                    'X-Plex-Client-Identifier':'01010101-10101010'
+                },
+                url: 'https://plex.tv/api/v2/pins?strong=true',
+                cache: false,
+                async: true,
+                complete: function(xhr, status) {
+                    if (xhr.status === 201) {
+                        var result = $.parseXML(xhr.responseText),
+                        $xml = $( result ), $title = $xml.find( "pin" ), $id = $title.find("id");
+                        var id = $title['0'].attributes.id.value;
+                        var code = $title['0'].attributes.code.value;
+
+                        window.open(`https://app.plex.tv/auth/#!?clientID=01010101-10101010&code=`+code, "Organizr!!", `menubar=no,location=no,resizable=no,scrollbars=no,status=no,width=1050,height=1050,left=0`);
+                        console.log(id,code);
+                        var loopAuth = setInterval(function(){
+                            // Do your update stuff...
+                            var success =  oAuthLoop('plex',id).success(function(data) {
+                                $xml = $( data ), $title = $xml.find( "pin" ), $id = $title.find("id");
+                                var id = $title['0'].attributes.id.value;
+                                var code = $title['0'].attributes.code.value;
+                                var authToken = $title['0'].attributes.authToken.value;
+                                success = (authToken !== '') ? authToken : false;
+                                console.log('checking: ' + id);
+                                if(success !== false){
+                                    clearInterval(loopAuth);
+                                    console.log('stopping loop cuz we good to go!');
+                                    $('#oAuth-Input').val(success);
+                                    $('#oAuthType-Input').val('plex');
+                                    $('#login-username-Input').addClass('hidden');
+                                    $('#login-password-Input').addClass('hidden');
+                                    $('#oAuth-div').removeClass('hidden');
+                                    $('.login-button').trigger('click');
+                                }
+                            });
+                        }, 1000);
+                    } else {
+                        console.log('An error - will add message later');
+                    }
+                }
+            });
+
+
+
+
+            break;
+        default:
+            break;
+    }
+}
 function clearAJAX(id='all'){
 	if(id == 'all'){
 		$.each(timeouts, function(i,v) {