0

我正在研究使用Google雲端存儲的應用程序。我想使用JSON_API來管理上傳/下載用戶提供的圖片。我的目標是使用我的服務帳戶方法獲取access_token,並將其從JSON_API JavaScript客戶端API傳遞出去。如何將服務OAuth access_token從PHP傳遞到JavaScript

這是我看中的褲子類搶的access_token:

<?php 

require_once 'google-api-php-client/src/Google_Client.php'; 
require_once 'google-api-php-client/src/contrib/Google_StorageService.php'; 

class Model_Storage_Auth 
{ 
    const CLIENT_ID = "clientid.apps.googleusercontent.com"; 
    const SERVICE_ACCOUNT_NAME = "[email protected]"; 
    const KEY_FILE = "/super/secret/path/key.p12"; 
    const ACCESS_TOKEN = 'access_token'; 
    const APP_NAME = 'Fancy App'; 

    private $google_client; 

    function __construct() 
    { 
     $this->google_client = new Google_Client(); 
     $this->google_client->setApplicationName(self::APP_NAME); 
    } 

    public function getToken() 
    { 
     //return '{}'; 
     if(is_null($this->google_client->getAccessToken())) 
     { 
      try{$this->google_client->setAccessToken(Session::get(self::ACCESS_TOKEN, '{}'));}catch(Exception $e){} 
      if(is_null($this->google_client->getAccessToken())) 
      { 
       $scope = array(); 
       $scope[] = 'https://www.googleapis.com/auth/devstorage.full_control'; 
       $key = file_get_contents(self::KEY_FILE); 
       $this->google_client->setAssertionCredentials(new Google_AssertionCredentials(
        self::SERVICE_ACCOUNT_NAME, 
        $scope, 
        $key) 
       ); 
       $this->google_client->setClientId(self::CLIENT_ID); 
       Google_Client::$auth->refreshTokenWithAssertion(); 
       $token = $this->google_client->getAccessToken(); 
       Session::set(self::ACCESS_TOKEN, $token); 
      } 
     } 
     return $this->google_client->getAccessToken(); 
    } 

} 

我把谷歌的JavaScript示例,並修改了它一點點地嘗試添加自己的實現,那就是:

<?php 
$access_token = json_decode(html_entity_decode($access_token), true); 
?> 

<!-- 
    Copyright (c) 2012 Google Inc. 

    Licensed under the Apache License, Version 2.0 (the "License"); you may not 
    use this file except in compliance with the License. You may obtain a copy of 
    the License at 

    http://www.apache.org/licenses/LICENSE-2.0 

    Unless required by applicable law or agreed to in writing, software 
    distributed under the License is distributed on an "AS IS" BASIS, WITHOUT 
    WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the 
    License for the specific language governing permissions and limitations under 
    the License. 

    To run this sample, replace YOUR_API_KEY with your application's API key. 
    It can be found at https://code.google.com/apis/console under API 
    Access. Activate the Google Cloud Storage service at 
    https://code.google.com/apis/console/ under Services 
--> 
<!DOCTYPE html> 
<html> 
    <head> 
    <meta charset='utf-8' /> 
    <script src="https://ajax.googleapis.com/ajax/libs/jquery/1.8.3/jquery.min.js"></script> 
    <script src="https://apis.google.com/js/client.js"></script> 
    <script type="text/javascript"> 

    /** 
    * The number of your Google Cloud Storage Project. 
    */ 
    var projectNumber = 'HAS REAL NUMBER IN MINE'; 

    /** 
    * Enter a client ID for a web application from the Google Developer 
    * Console. In your Developer Console project, add a JavaScript origin 
    * that corresponds to the domain from where you will be running the 
    * script. 
    */ 
    var clientId = 'YOUR_CLIENT_ID'; 

    /** 
    * Enter the API key from the Google Developer Console, by following these 
    * steps: 
    * 1) Visit https://code.google.com/apis/console/?api=storage 
    * 2) Click on "API Access" in the left column 
    * 3) Find section "Simple API Access" and use the "API key." If sample is 
    * being run on localhost then delete all "Referers" and save. Setting 
    * should display "Any referer allowed." 
    */ 
    var apiKey = 'YOUR_API_KEY'; 

    /** 
    * To enter one or more authentication scopes, refer to the documentation 
    * for the API. 
    */ 
    var scopes = 'https://www.googleapis.com/auth/devstorage.full_control'; 

    /** 
    * Constants for request parameters. Fill these values in with your custom 
    * information. 
    */ 
    var API_VERSION = 'v1beta1'; 
    var PROJECT = projectNumber; 

    /** 
    * The name of the new bucket to create. 
    */ 
    var BUCKET = 'code-sample-bucket'; 

    /** 
    * The name of the object inserted via insertObject method. 
    */ 
    var object = ""; 

    /** 
    * Get this value from the API console. 
    */ 
    var GROUP = 
    'group-0000000000000000000000000000000000000000000000000000000000000000'; 

    /** 
    * Valid values are user-userId, user-email, group-groupId, group-email, 
    * allUsers, allAuthenticatedUsers 
    */ 
    var ENTITY = 'allUsers'; 

    /** 
    * Valid values are READER, OWNER 
    */ 
    var ROLE = 'READER'; 

    /** 
    * Valid values are READER, OWNER 
    */ 
    var ROLE_OBJECT = 'READER'; 

    /** 
    * A list of example calls to the Google Cloud Storage JavaScript client 
    * library, as well as associated explanations of each call. 
    */ 
    var listApiRequestExplanations = { 
     'listBuckets': 'This API call queries the Google Cloud Storage API ' + 
     'for a list of buckets in your project, and returns the result as ' + 
     'a list of Google Cloud Storage buckets.', 

     'listObjects': 'This API call queries the Google Cloud Storage API ' + 
     'for a list of objects in your bucket, and returns the result as ' + 
     'a list of Google Cloud Storage objects.', 

     'listBucketsAccessControls': 'This API call queries the Google Cloud ' + 
     'Storage API for the list of access control lists on buckets in your ' + 
     'project and returns the result as a list of Google Cloud Storage ' + 
     'Access Control Lists.', 

     'listObjectsAccessControls': 'This API call queries the Google Cloud ' + 
     'Storage API for the list of access control lists on objects in your ' + 
     'bucket and returns the result as a list of Google Cloud Storage ' + 
     'Access Control Lists.', 

     'getBucket': 'This API call queries the Google Cloud Storage API ' + 
     'for a bucket in your project, and returns the result as a ' + 
     'Google Cloud Storage bucket.', 

     'getBucketAccessControls': 'This API call queries the Google Cloud ' + 
     'Storage API for the access control list on a specific bucket ' + 
     'and returns the result as a Google Cloud Storage Access Control List.', 

     'getObjectAccessControls': 'This API call queries the Google Cloud ' + 
     'Storage API for the access control list on a specific object ' + 
     'and returns the result as a Google Cloud Storage Access Control List.', 

     'insertBucket': 'This API call uses the Google Cloud Storage API ' + 
     'to insert a bucket into your project.', 

     'insertObject': 'This API call uses the Google Cloud Storage API ' + 
     'to insert an object into your bucket.', 

     'insertBucketAccessControls': 'This API uses the Google Cloud ' + 
     'Storage API to insert an access control list on a specific bucket ' + 
     'and returns the result as a Google Cloud Storage Access Control List.', 

     'insertObjectAccessControls': 'This API uses the Google Cloud ' + 
     'Storage API to insert an access control list on a specific object ' + 
     'and returns the result as a Google Cloud Storage Access Control List.', 

     'deleteBucket': 'This API uses the Google Cloud Storage API to delete ' + 
     'an empty bucket and returns an empty response to indicate success.', 

     'deleteObject': 'This API uses the Google Cloud Storage API to delete ' + 
     'an object and returns an empty response to indicate success.' 
    }; 

    /** 
    * Google Cloud Storage API request to retrieve the list of buckets in 
    * your Google Cloud Storage project. 
    */ 
    function listBuckets() { 
     var request = gapi.client.storage.buckets.list({ 
     'projectId': PROJECT 
     }); 
     executeRequest(request, 'listBuckets'); 
    } 

    /** 
    * Google Cloud Storage API request to retrieve the list of objects in 
    * your Google Cloud Storage project. 
    */ 
    function listObjects() { 
     var request = gapi.client.storage.objects.list({ 
     'bucket': BUCKET 
     }); 
     executeRequest(request, 'listObjects'); 
    } 

    /** 
    * Google Cloud Storage API request to retrieve the access control list on 
    * a bucket in your Google Cloud Storage project. 
    */ 
    function listBucketsAccessControls() { 
     var request = gapi.client.storage.bucketAccessControls.list({ 
      'bucket': BUCKET 
     }); 
     executeRequest(request, 'listBucketsAccessControls'); 
    } 

    /** 
    * Google Cloud Storage API request to retrieve the access control list on 
    * an object in your Google Cloud Storage project. 
    */ 
    function listObjectsAccessControls() { 
     var request = gapi.client.storage.objectAccessControls.list({ 
      'bucket': BUCKET, 
      'object': object 
     }); 
     executeRequest(request, 'listObjectsAccessControls'); 
    } 

    /** 
    * Google Cloud Storage API request to retrieve a bucket in 
    * your Google Cloud Storage project. 
    */ 
    function getBucket() { 
     var request = gapi.client.storage.buckets.get({ 
     'bucket': BUCKET 
     }); 
     executeRequest(request, 'getBucket'); 
    } 

    /** 
    * Google Cloud Storage API request to retrieve a bucket's Access Control 
    * List in your Google Cloud Storage project. 
    */ 
    function getBucketAccessControls() { 
     var request = gapi.client.storage.bucketAccessControls.get({ 
     'bucket': BUCKET, 
     'entity': GROUP 
     }); 
     executeRequest(request, 'getBucketAccessControls'); 
    } 

    /** 
    * Google Cloud Storage API request to retrieve an object's Access Control 
    * List in your Google Cloud Storage project. 
    */ 
    function getObjectAccessControls() { 
     var request = gapi.client.storage.objectAccessControls.get({ 
     'bucket': BUCKET, 
     'object': object, 
     'entity': GROUP 
     }); 
     executeRequest(request, 'getObjectAccessControls'); 
    } 

    /** 
    * Google Cloud Storage API request to insert a bucket into 
    * your Google Cloud Storage project. 
    */ 
    function insertBucket() { 
     resource = { 
     'id': BUCKET, 
     'projectId': PROJECT 
     }; 

     var request = gapi.client.storage.buckets.insert({ 
      'resource': resource 
     }); 
     executeRequest(request, 'insertBucket'); 
    } 

    /** 
    * Google Cloud Storage API request to insert an object into 
    * your Google Cloud Storage bucket. 
    */ 
    function insertObject(event) { 
     try{ 
     var fileData = event.target.files[0]; 
     } 
     catch(e) { 
     //'Insert Object' selected from the API Commands select list 
     //Display insert object button and then exit function 
     filePicker.style.display = 'block'; 
     return; 
     } 
     const boundary = '-------314159265358979323846'; 
     const delimiter = "\r\n--" + boundary + "\r\n"; 
     const close_delim = "\r\n--" + boundary + "--"; 

     var reader = new FileReader(); 
     reader.readAsBinaryString(fileData); 
     reader.onload = function(e) { 
     var contentType = fileData.type || 'application/octet-stream'; 
     var metadata = { 
      'name': fileData.name, 
      'mimeType': contentType 
     }; 

     var base64Data = btoa(reader.result); 
     var multipartRequestBody = 
      delimiter + 
      'Content-Type: application/json\r\n\r\n' + 
      JSON.stringify(metadata) + 
      delimiter + 
      'Content-Type: ' + contentType + '\r\n' + 
      'Content-Transfer-Encoding: base64\r\n' + 
      '\r\n' + 
      base64Data + 
      close_delim; 

     //Note: gapi.client.storage.objects.insert() can only insert 
     //small objects (under 64k) so to support larger file sizes 
     //we're using the generic HTTP request method gapi.client.request() 
     var request = gapi.client.request({ 
      'path': '/upload/storage/v1beta2/b/' + BUCKET + '/o', 
      'method': 'POST', 
      'params': {'uploadType': 'multipart'}, 
      'headers': { 
      'Content-Type': 'multipart/mixed; boundary="' + boundary + '"' 
      }, 
      'body': multipartRequestBody}); 
      //Remove the current API result entry in the main-content div 
      listChildren = document.getElementById('main-content').childNodes; 
      if (listChildren.length > 1) { 
      listChildren[1].parentNode.removeChild(listChildren[1]); 
      } 
     try{ 
      //Execute the insert object request 
      executeRequest(request, 'insertObject'); 
      //Store the name of the inserted object 
      object = fileData.name;  
     } 
     catch(e) { 
      alert('An error has occurred: ' + e.message); 
     } 
     } 
    } 

    /** 
    * Google Cloud Storage API request to insert an Access Control List into 
    * your Google Cloud Storage bucket. 
    */ 
    function insertBucketAccessControls() { 
     resource = { 
     'entity': ENTITY, 
     'role': ROLE 
     }; 

     var request = gapi.client.storage.bucketAccessControls.insert({ 
      'bucket': BUCKET, 
      'resource': resource 
     }); 
     executeRequest(request, 'insertBucketAccessControls'); 
    } 

    /** 
    * Google Cloud Storage API request to insert an Access Control List into 
    * your Google Cloud Storage object. 
    */ 
    function insertObjectAccessControls() { 
     resource = { 
     'entity': ENTITY, 
     'role': ROLE_OBJECT 
     }; 

     var request = gapi.client.storage.objectAccessControls.insert({ 
      'bucket': BUCKET, 
      'object': object, 
      'resource': resource 
     }); 
     executeRequest(request, 'insertObjectAccessControls'); 
    } 

    /** 
    * Google Cloud Storage API request to delete a Google Cloud Storage bucket. 
    */ 
    function deleteBucket() { 
     var request = gapi.client.storage.buckets.delete({ 
      'bucket': BUCKET 
     }); 
     executeRequest(request, 'deleteBucket'); 
    } 

    /** 
    * Google Cloud Storage API request to delete a Google Cloud Storage object. 
    */ 
    function deleteObject() { 
     var request = gapi.client.storage.objects.delete({ 
      'bucket': BUCKET, 
      'object': object 
     }); 
     executeRequest(request, 'deleteObject'); 
    } 

    /** 
    * Removes the current API result entry in the main-content div, adds the 
    * results of the entry for your function. 
    * @param {string} apiRequestName The name of the example API request. 
    */ 
    function updateApiResultEntry(apiRequestName) { 
     listChildren = document.getElementById('main-content') 
     .childNodes; 
     if (listChildren.length > 1) { 
     listChildren[1].parentNode.removeChild(listChildren[1]); 
     } 
     if (apiRequestName != 'null') { 
     window[apiRequestName].apply(this); 
     } 
    } 

    /** 
    * Determines which API request has been selected, and makes a call to add 
    * its result entry. 
    */ 
    function runSelectedApiRequest() { 
     var curElement = document.getElementById('api-selection-options'); 
     var apiRequestName = curElement.options[curElement.selectedIndex].value; 
     updateApiResultEntry(apiRequestName); 
    } 

    /** 
    * Binds event listeners to handle a newly selected API request. 
    */ 
    function addSelectionSwitchingListeners() { 
     document.getElementById('api-selection-options') 
     .addEventListener('change', 
     runSelectedApiRequest, false); 
    } 

    /** 
    * Template for getting JavaScript sample code snippets. 
    * @param {string} method The name of the Google Cloud Storage request 
    * @param {string} params The parameters passed to method 
    */ 
    function getCodeSnippet(method, params) { 
     var objConstruction = "// Declare your parameter object\n"; 
     objConstruction += "var params = {};"; 
     objConstruction += "\n\n"; 

     var param = "// Initialize your parameters \n"; 
     for (i in params) { 
     param += "params['" + i + "'] = "; 
     param += JSON.stringify(params[i], null, '\t'); 
     param += ";"; 
     param += "\n"; 
     } 
     param += "\n"; 

     var methodCall = "// Make a request to the Google Cloud Storage API \n"; 
     methodCall += "var request = gapi.client." + method + "(params);"; 
     return objConstruction + param + methodCall; 
    } 


    /** 
    * Executes your Google Cloud Storage request object and, subsequently, 
    * inserts the response into the page. 
    * @param {string} request A Google Cloud Storage request object issued 
    * from the Google Cloud Storage JavaScript client library. 
    * @param {string} apiRequestName The name of the example API request. 
    */ 
    function executeRequest(request, apiRequestName) { 
     request.execute(function(resp) { 
     console.log(resp); 
     var apiRequestNode = document.createElement('div'); 
     apiRequestNode.id = apiRequestName; 

     var apiRequestNodeHeader = document.createElement('h2'); 
     apiRequestNodeHeader.innerHTML = apiRequestName; 

     var apiRequestExplanationNode = document.createElement('div'); 
     apiRequestExplanationNode.id = apiRequestName + 'RequestExplanation'; 

     var apiRequestExplanationNodeHeader = document.createElement('h3'); 
     apiRequestExplanationNodeHeader.innerHTML = 'API Request Explanation'; 
     apiRequestExplanationNode.appendChild(apiRequestExplanationNodeHeader); 

     var apiRequestExplanationEntry = document.createElement('p'); 
     apiRequestExplanationEntry.innerHTML = 
      listApiRequestExplanations[apiRequestName]; 
     apiRequestExplanationNode.appendChild(apiRequestExplanationEntry); 

     apiRequestNode.appendChild(apiRequestNodeHeader); 
     apiRequestNode.appendChild(apiRequestExplanationNode); 

     var apiRequestCodeSnippetNode = document.createElement('div'); 
     apiRequestCodeSnippetNode.id = apiRequestName + 'CodeSnippet'; 

     var apiRequestCodeSnippetHeader = document.createElement('h3'); 
     apiRequestCodeSnippetHeader.innerHTML = 'API Request Code Snippet'; 
     apiRequestCodeSnippetNode.appendChild(apiRequestCodeSnippetHeader); 

     var apiRequestCodeSnippetEntry = document.createElement('pre'); 

     //If the selected API command is not 'insertObject', pass the request 
     //paramaters to the getCodeSnippet method call as 'request.B.rpcParams' 
     //else pass request paramaters as 'request.B' 
     if (apiRequestName != 'insertObject') { 
      apiRequestCodeSnippetEntry.innerHTML = 
      getCodeSnippet(request.B.method, request.B.rpcParams); 
      //Selected API Command is not 'insertObject' 
      //hide insert object button 
      filePicker.style.display = 'none'; 
     } else { 
      apiRequestCodeSnippetEntry.innerHTML = 
      getCodeSnippet(request.B.method, request.B); 
     } 
     apiRequestCodeSnippetNode.appendChild(apiRequestCodeSnippetEntry); 
     apiRequestNode.appendChild(apiRequestCodeSnippetNode); 

     var apiResponseNode = document.createElement('div'); 
     apiResponseNode.id = apiRequestName + 'Response'; 

     var apiResponseHeader = document.createElement('h3'); 
     apiResponseHeader.innerHTML = 'API Response'; 
     apiResponseNode.appendChild(apiResponseHeader); 

     var apiResponseEntry = document.createElement('pre'); 
     apiResponseEntry.innerHTML = JSON.stringify(resp, null, ' '); 

     apiResponseNode.appendChild(apiResponseEntry); 
     apiRequestNode.appendChild(apiResponseNode); 

     var content = document.getElementById('main-content'); 
     content.appendChild(apiRequestNode); 
     }); 
    } 

    /** 
    * Set required API keys and check authentication status. 
    */ 
    function handleClientLoad() { 
     gapi.client.setApiKey(apiKey); 
     window.setTimeout(checkAuth, 1); 
    } 

    /** 
    * Authorize Google Cloud Storage API. 
    */ 
    function checkAuth() { 
     gapi.auth.authorize({ 
     client_id: clientId, 
     scope: scopes, 
     immediate: true 
     }, handleAuthResult); 
    } 

    /** 
    * Handle authorization. 
    */ 
    function handleAuthResult(authResult) { 
     var authorizeButton = document.getElementById('authorize-button'); 
     if (authResult && !authResult.error) { 
     authorizeButton.style.visibility = 'hidden'; 
     initializeApi(); 
    filePicker.onchange = insertObject; 
     } else { 
     authorizeButton.style.visibility = ''; 
     authorizeButton.onclick = handleAuthClick; 
     } console.log(gapi.auth); 
    } 

    /** 
    * Handle authorization click event. 
    */ 
    function handleAuthClick(event) { 
     gapi.auth.authorize({ 
     client_id: clientId, 
     scope: scopes, 
     immediate: false 
     }, handleAuthResult); 
     return false; 
    } 

    /** 
    * Load Google Cloud Storage API v1beta12. 
    */ 
    function initializeApi() { 
     gapi.client.load('storage', API_VERSION); 
    } 

    /** 
    * Driver for sample application. 
    */ 
    $(window) 
     .bind('load', function() { 
     gapi.auth.setToken('<?php print $access_token["access_token"]; ?>'); 
     gapi.auth.token= '<?php print $access_token["access_token"]; ?>'; 
     console.log(gapi.auth.getToken()); 
     addSelectionSwitchingListeners(); 
     handleClientLoad(); 
    }); 
    </script> 
    </head> 
    <body> 
    <!--Add a button for the user to click to initiate auth sequence --> 
    <button id="authorize-button" style="visibility: hidden">Authorize</button> 
    <header> 
     <h1>Google Cloud Storage JavaScript Client Library Application</h1> 
    </header> 
    <label id="api-label">Try a sample API call!</label> 
    <select id="api-selection-options"> 
     <option value="null"> 
     Please select an example API call from the dropdown menu 
     </option> 
     <option value="listBuckets"> 
     List Buckets 
     </option> 
     <option value="listObjects"> 
     List Objects 
     </option> 
     <option value="listBucketsAccessControls"> 
     List Buckets Access Control List 
     </option> 
     <option value="listObjectsAccessControls"> 
     List Objects Access Control List 
     </option> 
     <option value="getBucket"> 
     Get Bucket 
     </option> 
     <option value="getBucketAccessControls"> 
     Get Bucket Access Controls 
     </option> 
     <option value="getObjectAccessControls"> 
     Get Object Access Controls 
     </option> 
     <option value="insertBucket"> 
     Insert Bucket 
     </option> 
     <option value="insertObject"> 
     Insert Object 
     </option> 
     <option value="insertBucketAccessControls"> 
     Insert Bucket Access Controls 
     </option> 
     <option value="insertObjectAccessControls"> 
     Insert Object Access Controls 
     </option> 
     <option value="deleteBucket"> 
     Delete Bucket 
     </option> 
     <option value="deleteObject"> 
     Delete Object 
     </option> 
    </select> 
    <br/> 
    <input type="file" id="filePicker" style="display: none" /> 
    <div id="main-content"> 
    </div> 
    </body> 
</html> 

有沒有人有任何想法?我不是成功的,因爲我的控制檯打印了這一點:

as an error loading the page https://accounts.google.com/o/oauth2/auth?client_id=YOUR_CLIENT_ID&scope=ht…ifechurch.tv&response_type=token&state=412841043%7C0.2670569503&authuser=0 

回答

1

雖然有可能在服務帳戶服務器代碼來獲取訪問令牌,然後包括作爲一個網頁的一部分,或允許瀏覽器直接訪問Google雲端存儲的Javascript響應 - 這通常是一種非常危險的方式,因爲訪問令牌將允許任何人訪問您的所有云存儲資源 - 沒有機會獲得您信任的服務器端代碼能夠應用特定於您的應用程序的訪問控制限制(例如,允許您的應用程序的用戶上傳/下載他們應該有權訪問的文件/對象)。

然而,直接文件上傳/下載到雲存儲可能會以稍微不同的方式實現。 Google雲端存儲支持簽名的URL - 這是一個您可以在服務器代碼中生成的URL(使用您用於獲取訪問令牌的相同私鑰),以便承載者可以上傳或下載特定文件一段的時間。

這個文件可以在這裏找到: https://developers.google.com/storage/docs/accesscontrol#Signed-URLs

而且從PHP這裏一個例子: https://groups.google.com/forum/#!msg/google-api-php-client/jaRYDWdpteQ/xbNTLfDhUggJ

一旦你生成您的服務器上這個網址,你可以通過瀏覽器,這反過來又可以然後直接輸入該URL,或直接從它獲取,而無需使用任何特殊的Google Javascript庫。例如:Google Storage REST PUT With Signed URLs

+0

因此,我將能夠使用此方法直接上傳圖片嗎? – RyanDawkins

+0

是的!有關示例,請參閱http://commondatastorage.googleapis.com/io2012/presentations/live%20to%20website/308.pdf的幻燈片15-18。在這個例子中,服務器端部分是Python,但上面的鏈接顯示了PHP的等價物。 – aeijdenberg

+0

我很難弄清楚簽名是什麼,以及如何生成它。此外,這部分是什麼?'application/x-www-form- urlencoded' – RyanDawkins

0

我最近完成了一個類似的項目,使用Ajax訪問我的PHP類,該類控制訪問令牌更新,連接URls等。由於它通過HTTPS進行實時連接,因此代碼中不會顯示敏感信息,然後我可以將相關數據直接加載到JavaScript中。

希望這有助於