是否可以限制用户提供的访问权限以使其为只读

时间:2013-09-19 15:47:48

标签: youtube-api

我正在尝试使用YouTube Data API V2.0为我们客户的视频/频道提供数据分析。我有一个开发人员密钥和我的客户端生成的令牌,并成功找出了如何检索该信息。我的问题是,当我的客户使用该应用程序生成YouTube令牌时,我们要求的访问意味着一切,并能够“管理”他们的帐户。

这是客户主要关注的问题,他们不希望我们拥有这种完全访问权限。有没有办法获得仅使用只读权限生成的令牌?

非常感谢您的帮助!

1 个答案:

答案 0 :(得分:0)

我已成功使用https://googleapis.com/auth/youtube.readonly作为范围;如果你在初始oAuth流程中只要求那个范围(而不是同时为https://googleapis.com/auth/youtube,那就是覆盖只读范围的管理范围),那么每当你尝试一个范围时你都会得到403错误需要管理权限的操作(插入,上传,更新,删除)。

如果您正在使用它们,那么v3的google-api客户端可以非常顺利地处理这个问题。如果您已编写自己的oAuth流控制,请确保在请求初始令牌时拥有唯一的只读范围。

编辑回复评论:要查看此操作(我将使用javascript显示),您可以使用API​​文档提供的sample code创建一个简单的演示。这是一般过程:

1)在Google API控制台中,创建“项目”并为该项目授权YouTube API(在“服务”标签下)。此外,为Web应用程序创建客户端ID(在API访问选项卡下),并在您的域中添加为授权的Javascript域。

2)在您的服务器上,创建和HTML文件作为您的界面(在此示例中,它旨在让您创建新的播放列表并向其添加项目)。这是代码,直接来自文档:

<!doctype html>
<html>
  <head>
    <title>Playlist Updates</title>
  </head>
  <body>
    <div id="login-container" class="pre-auth">This application requires access to your YouTube account.
      Please <a href="#" id="login-link">authorize</a> to continue.
    </div>
    <div id="buttons">
      <button id="playlist-button" disabled onclick="createPlaylist()">Create a new Private Playlist</button>
      <br>
      <label>Current Playlist Id: <input id="playlist-id" value='' type="text"/></label>
      <br>
      <label>Video Id: <input id="video-id" value='GZG9G5txtaE' type="text"/></label><button onclick="addVideoToPlaylist()">Add to current playlist</button>
    </div>
    <h3>Playlist: <span id="playlist-title"></span></h3>
    <p id="playlist-description"></p>
    <div id="playlist-container">
      <span id="status">No Videos</span>
    </div>
    <script src="//ajax.googleapis.com/ajax/libs/jquery/1.8.2/jquery.min.js"></script>
    <script src="auth.js"></script>
    <script src="playlist_updates.js"></script>
    <script src="https://apis.google.com/js/client.js?onload=googleApiClientReady"></script>
  </body>
</html>

3)在同一个位置,使用此代码创建脚本“playlist_updates.js”(再次直接从文档中):

// Some variables to remember state.
var playlistId, channelId;

// Once the api loads call a function to get the channel information.
function handleAPILoaded() {
  enableForm();
}

// Enable a form to create a playlist.
function enableForm() {
  $('#playlist-button').attr('disabled', false);
}

// Create a private playlist.
function createPlaylist() {
  var request = gapi.client.youtube.playlists.insert({
    part: 'snippet,status',
    resource: {
      snippet: {
        title: 'Test Playlist',
        description: 'A private playlist created with the YouTube API'
      },
      status: {
        privacyStatus: 'private'
      }
    }
  });
  request.execute(function(response) {
    var result = response.result;
    if (result) {
      playlistId = result.id;
      $('#playlist-id').val(playlistId);
      $('#playlist-title').html(result.snippet.title);
      $('#playlist-description').html(result.snippet.description);
    } else {
      $('#status').html('Could not create playlist');
    }
  });
}

// Add a video id from a form to a playlist.
function addVideoToPlaylist() {
  addToPlaylist($('#video-id').val());
}

// Add a video to a playlist.
function addToPlaylist(id, startPos, endPos) {
  var details = {
    videoId: id,
    kind: 'youtube#video'
  }
  if (startPos != undefined) {
    details['startAt'] = startPos;
  }
  if (endPos != undefined) {
    details['endAt'] = endPos;
  }
  var request = gapi.client.youtube.playlistItems.insert({
    part: 'snippet',
    resource: {
      snippet: {
        playlistId: playlistId,
        resourceId: details
      }
    }
  });
  request.execute(function(response) {
    $('#status').html('<pre>' + JSON.stringify(response.result) + '</pre>');
  });
}

最后,创建文件“auth.js” - 这是实际执行oAuth2流程的代码:

// The client id is obtained from the Google APIs Console at https://code.google.com/apis/console
// If you run access this code from a server other than http://localhost, you need to register
// your own client id.
var OAUTH2_CLIENT_ID = '__YOUR_CLIENT_ID__';
var OAUTH2_SCOPES = [
  'https://www.googleapis.com/auth/youtube'
];

// This callback is invoked by the Google APIs JS client automatically when it is loaded.
googleApiClientReady = function() {
  gapi.auth.init(function() {
    window.setTimeout(checkAuth, 1);
  });
}

// Attempt the immediate OAuth 2 client flow as soon as the page is loaded.
// If the currently logged in Google Account has previously authorized OAUTH2_CLIENT_ID, then
// it will succeed with no user intervention. Otherwise, it will fail and the user interface
// to prompt for authorization needs to be displayed.
function checkAuth() {
  gapi.auth.authorize({
    client_id: OAUTH2_CLIENT_ID,
    scope: OAUTH2_SCOPES,
    immediate: true
  }, handleAuthResult);
}

// Handles the result of a gapi.auth.authorize() call.
function handleAuthResult(authResult) {
  if (authResult) {
    // Auth was successful; hide the things related to prompting for auth and show the things
    // that should be visible after auth succeeds.
    $('.pre-auth').hide();
    loadAPIClientInterfaces();
  } else {
    // Make the #login-link clickable, and attempt a non-immediate OAuth 2 client flow.
    // The current function will be called when that flow is complete.
    $('#login-link').click(function() {
      gapi.auth.authorize({
        client_id: OAUTH2_CLIENT_ID,
        scope: OAUTH2_SCOPES,
        immediate: false
        }, handleAuthResult);
    });
  }
}

// Loads the client interface for the YouTube Analytics and Data APIs.
// This is required before using the Google APIs JS client; more info is available at
// http://code.google.com/p/google-api-javascript-client/wiki/GettingStarted#Loading_the_Client
function loadAPIClientInterfaces() {
  gapi.client.load('youtube', 'v3', function() {
    handleAPILoaded();
  });
}

请注意OAUTH2_SCOPES常量。它设置为允许完全管理访问,因此,如果您随后访问浏览器中的html页面并单击“授权”链接,您应该会看到一个窗口,要求您授予您的域访问权限以管理您的YouTube帐户。这样做,然后代码变得有用......您可以添加播放列表和播放列表项目到您的内容。

然而,如果您修改auth.js以便OAUTH2_SCOPES如下所示:

var OAUTH2_SCOPES = [
        'https://www.googleapis.com/auth/youtube.readonly'
];

并清除您的Cookie(以避免继承您已授予的权限...只需关闭浏览器并重新启动就足够了),然后再试一次(访问HTML,点击授权链接),您会看到这次它要求您仅授予查看帐户的权限,而不是管理它。如果您授予该权限,那么当您尝试通过界面添加播放列表时,您将收到一条错误消息,显示您无法创建播放列表。

如果您不使用javascript,而是使用服务器端语言,正如我所提到的那样,gapi客户端非常流畅。但是,在这些客户端中处理oAuth2作用域并不是那么透明,并且它们在设计上是“贪婪的”(因为它将服务端点抽象为对象,它将请求它需要做的最彻底的范围该端点上的任何操作......所以即使您只打算进行列表调用,如果服务也有更新操作,客户端也会请求完全管理权限)。但是,如果您想要进入客户端代码,则可以对其进行修改 - 或者您可以将其用作创建自己的简化客户端的模型,您可以在范围方面进行精细控制。

在不了解您的基础技术的情况下,这就像我一样彻底。希望解释有所帮助!