Tháng 2 năm 2009
Giới thiệu
" Ruby ở đâu trong danh sách client library?"
Nhờ sự thích thú mãnh liệt của các nhà phát triển và sự nổi tiếng lâu dài của Ruby on Rails (RoR), đồng nghiệp của tôi, Jeff Fisher đã tạo dựng một thư viện tiện ích Ruby từ độ sâu tối đa của Núi Doom. Xin lưu ý rằng đây không phải là một thư viện ứng dụng đầy đủ, nhưng xử lý các nguyên tắc cơ bản như xác thực và thao tác XML cơ bản. Ngoài ra, mô-đun này cũng yêu cầu bạn làm việc trực tiếp với nguồn cấp dữ liệu Atom bằng cách sử dụng mô-đun REXML và đích.
Đối tượng người xem
Bài viết này dành cho những nhà phát triển quan tâm đến việc truy cập API dữ liệu của Google bằng Ruby, cụ thể là Ruby on Rails. Phương thức này giả định rằng người đọc đã quen thuộc với ngôn ngữ lập trình Ruby và khung phát triển web của Rails. Tôi tập trung vào API danh sách tài liệu cho hầu hết các mẫu, nhưng có thể áp dụng các khái niệm tương tự cho bất kỳ API dữ liệu nào.
Bắt đầu
Yêu cầu
Cài đặt Thư viện tiện ích Ruby dữ liệu của Google
Để lấy thư viện, bạn có thể tải nguồn thư viện xuống trực tiếp từ dự án lưu trữ hoặc cài đặt thư viện:
sudo gem install gdata
Mẹo: Để đo lường chính xác, hãy chạy gem list --local
để xác minh rằng thư viện đã được cài đặt đúng cách.
Xác thực
ClientLogin
ClientLogin cho phép ứng dụng của bạn đăng nhập theo cách có lập trình vào tài khoản Google hoặc G Suite của họ. Khi xác thực thông tin đăng nhập của người dùng, Google sẽ phát hành một Mã thông báo xác thực để tham chiếu trong các yêu cầu API tiếp theo. Mã thông báo này vẫn có hiệu lực trong một khoảng thời gian nhất định, được xác định theo dịch vụ bất kỳ của Google mà bạn đang sử dụng. Vì lý do bảo mật và để cung cấp cho người dùng trải nghiệm tốt nhất, bạn chỉ nên sử dụng ClientLogin khi phát triển các ứng dụng được cài đặt và dành cho máy tính. Đối với các ứng dụng web, bạn nên sử dụng AuthSub hoặc OAuth.
Thư viện Ruby có một lớp ứng dụng cho mỗi API. Ví dụ: sử dụng đoạn mã sau để đăng nhập user@gmail.com
vào API dữ liệu danh sách tài liệu:
client = GData::Client::DocList.new client.clientlogin('user@gmail.com', 'pa$$word')
The YouTube Data API would be:
client = GData::Client::YouTube.new client.clientlogin('user@gmail.com', 'pa$$word')
Xem danh sách đầy đủ các lớp dịch vụ được triển khai.
Nếu một dịch vụ không có lớp ứng dụng, hãy sử dụng lớp GData::Client::Base
.
Ví dụ: mã sau đây buộc người dùng đăng nhập bằng tài khoản G Suite.
client_login_handler = GData::Auth::ClientLogin
.new('writely', :account_type => 'HOSTED')
token = client_login_handler.get_token('user@example.com', 'pa$$word', 'google-RailsArticleSample-v1')
client = GData::Client::Base.new(:auth_handler => client_login_handler)
Lưu ý: Theo mặc định, thư viện sử dụng HOSTED_OR_GOOGLE
cho accountType
. Giá trị có thể là HOSTED_OR_GOOGLE
, HOSTED
hoặc GOOGLE
.
Một trong những nhược điểm của việc sử dụng ClientLogin là ứng dụng của bạn có thể bị gửi hình ảnh xác thực CAPTCHA trên các lần đăng nhập không thành công. Nếu điều đó xảy ra, bạn có thể xử lý lỗi bằng cách gọi phương thức clientlogin()
kèm theo các tham số bổ sung: client.clientlogin(username, password, captcha_token, captcha_answer)
. Tham khảo tài liệu Xác thực ứng dụng đã cài đặt đầy đủ để biết thêm thông tin về cách xử lý CAPTCHA.
AuthSub
Tạo URL AuthSubRequest
scope = 'http://www.google.com/calendar/feeds/' next_url = 'http://example.com/change/to/your/app' secure = false # set secure = true for signed AuthSub requests sess = true authsub_link = GData::Auth::AuthSub.get_url(next_url, scope, secure, sess)
Khối mã trước đó tạo URL sau trong authsub_link
:
https://www.google.com/accounts/AuthSubRequest?next=http%3A%2F%2Fexample.com%2Fchange%2Fto%2Fyour%2Fapp&scope=http%3A%2F%2Fwww.google.com%2Fcalendar%2Ffeeds%2F&session=1&secure=0
Bạn cũng có thể sử dụng phương thức authsub_url
của đối tượng ứng dụng. Mỗi lớp dịch vụ đã đặt một thuộc tính authsub_scope
mặc định nên bạn không cần chỉ định thuộc tính của riêng mình.
client = GData::Client::DocList.new next_url = 'http://example.com/change/to/your/app' secure = false # set secure = true for signed AuthSub requests sess = true domain = 'example.com' # force users to login to a G Suite hosted domain authsub_link = client.authsub_url(next_url, secure, sess, domain)
Khối mã trước đó tạo URL sau:
https://www.google.com/accounts/AuthSubRequest?next=http%3A%2F%2Fexample.com%2Fchange%2Fto%2Fyour%2Fapp&scope=http%3A%2F%2Fdocs.google.com%2Ffeeds%2F&session=1&secure=0&hd=example.com
Nâng cấp mã thông báo sử dụng một lần lên mã thông báo phiên
AuthSub sẽ chuyển hướng người dùng quay lại http://example.com/change/to/your/app?token=SINGLE_USE_TOKEN
sau khi họ cấp quyền truy cập vào dữ liệu của mình. Vui lòng lưu ý URL chỉ là next_url
của chúng tôi với mã thông báo sử dụng một lần được thêm vào dưới dạng tham số truy vấn.
Tiếp theo, hãy đổi mã thông báo dùng một lần để có mã thông báo phiên hoạt động dài hạn:
client.authsub_token = params[:token] # extract the single-use token from the URL query params session[:token] = client.auth_handler.upgrade() client.authsub_token = session[:token] if session[:token]
AuthSub an toàn rất giống nhau. Việc bổ sung duy nhất là đặt khóa riêng tư của bạn trước khi nâng cấp mã thông báo:
PRIVATE_KEY = '/path/to/private_key.pem' client.authsub_token = params[:token] client.authsub_private_key = PRIVATE_KEY session[:token] = client.auth_handler.upgrade() client.authsub_token = session[:token] if session[:token]
Lưu ý: Để sử dụng mã thông báo an toàn, hãy nhớ đặt secure=true
khi yêu cầu mã thông báo sử dụng một lần. Xem Tạo URL AuthSubRequest ở trên.
Quản lý mã thông báo
AuthSub cung cấp thêm hai trình xử lý, AuthSubTokenInfo và
AuthSubRevocationToken để quản lý các mã thông báo. AuthSubTokenInfo
rất hữu ích trong việc kiểm tra
tính hợp lệ của mã thông báo. AuthSubRevokeToken
cho phép người dùng ngừng truy cập vào dữ liệu của họ. Ứng dụng của bạn nên sử dụng AuthSubRevokeToken
là phương pháp hay nhất. Cả hai phương thức đều được hỗ trợ trong thư viện Ruby.
Để truy vấn siêu dữ liệu của mã thông báo:
client.auth_handler.info
Cách thu hồi mã thông báo phiên:
client.auth_handler.revoke
Xem tài liệu đầy đủ về Xác thực AuthSub cho ứng dụng web để biết đầy đủ thông tin về AuthSub.
OAuth
Tại thời điểm viết bài viết này, OAuth chưa được thêm vào mô-đun GData::Auth
.
Việc sử dụng OAuth trong thư viện tiện ích phải tương đối đơn giản khi sử dụng OAuth-plugin hoặc
Ruby OAuth Trong cả hai trường hợp, bạn sẽ cần tạo đối tượng GData::HTTP::Request
và truyền đối tượng đó vào tiêu đề Authorization
mà mỗi thư viện tạo ra.
Truy cập vào nguồn cấp dữ liệu
GET (tìm nạp dữ liệu)
Sau khi bạn thiết lập đối tượng khách hàng, hãy sử dụng phương thức get()
của đối tượng đó để truy vấn nguồn cấp dữ liệu của Google. suất mùa của JavaScript có thể dùng để truy xuất các phần tử Atom cụ thể. Sau đây là ví dụ về cách truy xuất Tài liệu Google của người dùng:
feed = client.get('http://docs.google.com/feeds/documents/private/full').to_xml feed.elements.each('entry') do |entry| puts 'title: ' + entry.elements['title'].text puts 'type: ' + entry.elements['category'].attribute('label').value puts 'updated: ' + entry.elements['updated'].text puts 'id: ' + entry.elements['id'].text # Extract the href value from each <atom:link> links = {} entry.elements.each('link') do |link| links[link.attribute('rel').value] = link.attribute('href').value end puts links.to_s end
POST (tạo dữ liệu mới)
Sử dụng phương thức post()
của ứng dụng để tạo dữ liệu mới trên máy chủ. Ví dụ sau sẽ thêm new_writer@example.com
làm cộng tác viên vào tài liệu có mã nhận dạng: doc_id
.
# Return documents the authenticated user owns feed = client.get('http://docs.google.com/feeds/documents/private/full/-/mine').to_xml entry = feed.elements['entry'] # first <atom:entry> acl_entry = <<-EOF <entry xmlns="http://www.w3.org/2005/Atom" xmlns:gAcl='http://schemas.google.com/acl/2007'> <category scheme='http://schemas.google.com/g/2005#kind' term='http://schemas.google.com/acl/2007#accessRule'/> <gAcl:role value='writer'/> <gAcl:scope type='user' value='new_writer@example.com'/> </entry> EOF # Regex the document id out from the full <atom:id>. # http://docs.google.com/feeds/documents/private/full/document%3Adfrk14g25fdsdwf -> document%3Adfrk14g25fdsdwf doc_id = entry.elements['id'].text[/full\/(.*%3[aA].*)$/, 1] response = client.post("http://docs.google.com/feeds/acl/private/full/#{doc_id}", acl_entry)
PUT (cập nhật dữ liệu)
Để cập nhật dữ liệu trên máy chủ, hãy sử dụng phương thức put()
của ứng dụng. Ví dụ sau sẽ cập nhật tiêu đề của tài liệu.
Giả sử bạn có một nguồn cấp dữ liệu qua truy vấn trước đó.
entry = feed.elements['entry'] # first <atom:entry> # Update the document's title entry.elements['title'].text = 'Updated title' entry.add_namespace('http://www.w3.org/2005/Atom') entry.add_namespace('gd','http://schemas.google.com/g/2005') edit_uri = entry.elements["link[@rel='edit']"].attributes['href'] response = client.put(edit_uri, entry.to_s)
DELETE
Để xoá <atom:entry> hoặc dữ liệu khác khỏi máy chủ, hãy sử dụng phương thức delete()
.
Ví dụ sau đây sẽ xoá một tài liệu. Mã giả định bạn có một mục nhập tài liệu từ truy vấn trước đó.
entry = feed.elements['entry'] # first <atom:entry> edit_uri = entry.elements["link[@rel='edit']"].attributes['href'] client.headers['If-Match'] = entry.attribute('etag').value # make sure we don't nuke another client's updates client.delete(edit_uri)
Tạo ứng dụng Rails mới
Thông thường, bài tập đầu tiên để tạo ứng dụng Rails mới là chạy trình tạo scaffold để tạo tệp MVC.
Sau đó, trình duyệt này sẽ chạy rake db:migrate
để thiết lập bảng cơ sở dữ liệu. Tuy nhiên, vì ứng dụng của chúng tôi sẽ truy vấn API Danh sách tài liệu của Google để tạo dữ liệu, nên chúng tôi không cần phải có giàn giáo hoặc cơ sở dữ liệu chung. Thay vào đó, hãy tạo một ứng dụng mới và tay điều khiển đơn giản:
rails doclist cd doclist ruby script/generate controller doclist
và thực hiện các thay đổi sau đối với config/environment.rb
:
config.frameworks -= [ :active_record, :active_resource, :action_mailer ] config.gem 'gdata', :lib => 'gdata'
Dòng đầu tiên ngắt kết nối ActiveRecord
khỏi ứng dụng.
Dòng thứ hai tải đá quý gdata
khi khởi động.
Cuối cùng, tôi chọn kết nối tuyến đường mặc định ("/
") với thao tác documents
trong DoclistController
.
Thêm dòng này vào config/routes.rb
:
map.root :controller => 'doclist', :action => 'all'
Khởi động bộ điều khiển
Vì chúng ta không tạo giàn giáo, nên hãy thêm một thao tác có tên là "all
" vào DoclistController
theo cách thủ công trong app/controllers/doclist_controller.rb
.
class DoclistController < ApplicationController def all @foo = 'I pity the foo!' end end
và tạo all.html.erb
trong app/views/doclist/
:
<%= @foo %>
Kích hoạt máy chủ web và bắt đầu phát triển
Bây giờ, bạn có thể khởi động máy chủ web mặc định bằng cách gọi ruby script/server
.
Nếu tất cả đều ổn, việc trỏ trình duyệt của bạn đến http://localhost:3000/
sẽ hiển thị 'I pity the foo!
'.
Mẹo: Đừng quên xóa hoặc đổi tên public/index.html
.
Sau khi bạn đã thực hiện được mọi việc, hãy xem
DoclistController
và
ApplicationController
cuối cùng của tôi về thịt
của dự án Trình quản lý danh sách. Bạn cũng nên xem ContactsController
để xử lý các lệnh gọi đến API Danh bạ Google.
Kết luận
Phần khó nhất trong việc tạo ứng dụng Google Data Rails là định cấu hình Rails! Tuy nhiên, giây đầy đủ là việc triển khai ứng dụng. Do đó, tôi thực sự khuyên bạn nên sử dụng mod_rails cho Apache. Việc thiết lập, cài đặt và chạy ứng dụng rất dễ dàng. Bạn có thể hoạt động ngay lập tức!
Tài nguyên
- Danh sách các API dữ liệu của Google
- Trang dự án Thư viện tiện ích Ruby dữ liệu của Google
- Bài viết: Sử dụng Ruby với API Dữ liệu của Google
- Tải Ruby xuống
- Tải RubyGems and Rails xuống
Phụ lục
Ví dụ
Trình quản lý danh sách DocList là một mẫu Ruby on Rails đầy đủ minh hoạ các chủ đề được thảo luận trong bài viết này. Bạn có thể sử dụng mã nguồn đầy đủ để lưu trữ dự án.