สิงหาคม 2007
- บทนํา: เหตุใด AuthSub จึงสําคัญ
- การจัดการการใช้งาน
- การตรวจสอบสิทธิ์ (ลงทะเบียน) ที่ปลอดภัย
- ทํารายการโค้ดให้เสร็จสมบูรณ์
- สรุป
บทนํา: เหตุใด AuthSub จึงสําคัญ
ข้อดีอย่างหนึ่งของ Google Data API ("GData") คือช่วยให้นักพัฒนาซอฟต์แวร์สร้างแอปพลิเคชันที่โต้ตอบกับบริการของ Google ได้ ยิ่งไปกว่านั้น ยังช่วยให้คุณสามารถเข้าถึงข้อมูลผู้ใช้ส่วนตัวสําหรับการใช้งานในแอปพลิเคชันได้ API ช่วยให้คุณเขียนแอปพลิเคชันเพื่อซิงค์ นําเข้า ส่งออก และจัดการข้อมูลดังกล่าวได้ แม้ว่า API เหล่านี้จะมอบความสามารถที่มีประสิทธิภาพเหล่านี้ให้แก่คุณ แต่อย่าลืมเลือกใช้อย่างมีความรับผิดชอบ เนื่องจากข้อมูลผู้ใช้เป็นข้อมูลส่วนตัวอยู่แล้ว คุณจึงต้องการเข้าถึงข้อมูลดังกล่าวอย่างปลอดภัย ส่วนสําคัญคือสามารถตรวจสอบสิทธิ์ เซิร์ฟเวอร์ของ Google ได้อย่างปลอดภัย
สมมติว่าคุณมีเว็บแอปพลิเคชันใหม่ที่ยอดเยี่ยมซึ่งคุณต้องการเชื่อมโยงกับข้อมูลที่เก็บไว้ในบริการเว็บของ Google ตอนนี้คุณต้องการตรวจสอบสิทธิ์เพื่อเข้าถึงข้อมูลส่วนตัวนี้ ทําไมไม่ใช้แค่วิธีง่ายๆ เช่น ClientLogin เยี่ยมเลยครับ เคล็ดลับสบายๆ ก็คือคุณจะจัดการข้อมูลส่วนตัวได้มากขึ้น นั่นคือข้อมูลเข้าสู่ระบบของผู้ใช้ ClientLogin กําหนดให้แอปพลิเคชันของคุณขอชื่อผู้ใช้ Google และรหัสผ่านของผู้ใช้ สามารถใช้สําหรับแอปพลิเคชันเดสก์ท็อปที่ทํางานบนเครื่องส่วนตัวของผู้ใช้ แต่ไม่เหมาะสําหรับแอปพลิเคชันบนเว็บ นอกจากความรับผิดในการจัดการข้อมูลเข้าสู่ระบบเหล่านี้บนเซิร์ฟเวอร์ของคุณเองแล้ว อาจเป็นไปได้ว่าผู้ใช้ขาประจําของคุณอาจกลัวว่าจะเก็บข้อมูลของผู้ใช้ ปัญหาที่พบบ่อยอีกประการหนึ่งคือ ผู้ใช้ต้องการให้สิทธิ์เข้าถึงโปรแกรมแก่บริการใดบริการหนึ่งเท่านั้น (เช่น กิจกรรมใน Google ปฏิทิน) แต่ไม่ให้สิทธิ์แก่บริการอื่น (เช่น Google เอกสาร) AuthSub ช่วยแก้ปัญหาทั้งสองโดยให้ผู้ใช้ตรวจสอบสิทธิ์ผ่านเซิร์ฟเวอร์ของ Google และอนุญาตให้โปรแกรมขอสิทธิ์เข้าถึงที่จําเป็นเท่านั้น
เมื่อคุณได้อ่านทฤษฎีเบื้องหลัง AuthSub อย่างเพียงพอแล้ว ต่อไปก็มาดูการเขียนโค้ดกัน! สําหรับบทความนี้ ฉันเลือกที่จะทําให้สิ่งต่างๆ เรียบง่ายและทําทุกอย่างภายในหน้า ASP เดียว แต่คุณควรจะสามารถผสานรวมเทคนิคที่แสดงไว้ที่นี่กับแอปพลิเคชันของคุณเองได้อย่างง่ายดาย
การตรวจสอบสิทธิ์การจัดการ
ต้องทําอย่างไรจึงจะใช้ AuthSub ในเว็บแอปพลิเคชันได้ ก่อนอื่นจะมีการนําเข้ามาตรฐานจากไลบรารีของไคลเอ็นต์ GData ดังนี้
<%@ Import Namespace="Google.GData.Client" %> <%@ Import Namespace="Google.GData.Extensions" %> <%@ Import Namespace="System.Net" %>
ขั้นตอนแรกที่ต้องทําคือการส่งผู้ใช้ไปยัง URL ที่สร้างขึ้นพิเศษ ซึ่งทําให้เซิร์ฟเวอร์ของ Google จัดการการตรวจสอบสิทธิ์ จากนั้นจึงเปลี่ยนเส้นทางผู้ใช้กลับไปยังเว็บไซต์ของคุณได้ โชคดีที่คุณไม่จําเป็นต้องสร้าง URL นี้ด้วยตนเอง เนื่องจากมีวิธีให้คุณดําเนินการ ยกตัวอย่างเช่น:
authSubUrl = AuthSubUtil.getRequestUrl(target, scope, secure, session);
- target เป็นสตริงที่มี URL ไปยังเว็บแอปพลิเคชัน นี่คือที่ที่จะเปลี่ยนเส้นทางผู้ใช้หลังจากตรวจสอบสิทธิ์
- ขอบเขต สตริงนี้กําหนดโดย API ที่คุณใช้ ฟีดดังกล่าวตรงกับฟีดใน GData API เช่น ฟีดที่มีข้อมูลปฏิทินทั้งหมดของผู้ใช้คือ "http://www.google.com/calendar/feeds/default/private/full"
- ปลอดภัย บูลีนนี้บอกให้เซิร์ฟเวอร์ที่คุณลงทะเบียนกับ Google และจะลงนามคําขอไปยังเซิร์ฟเวอร์แบบเข้ารหัส โดยปกติแล้วอาร์กิวเมนต์นี้จะเป็นเท็จโดยค่าเริ่มต้น โดยเฉพาะอย่างยิ่งเมื่อทํางานในสภาพแวดล้อมการทดสอบ
- session ซึ่งเป็นบูลีนอื่นที่ระบุว่าคุณต้องการใช้ "โทเค็นเซสชัน" แทนที่จะเป็น "โทเค็นแบบใช้ครั้งเดียว" บทบาทของอาร์กิวเมนต์นี้จะชัดเจนขึ้นในอีกสักครู่
หลังจากที่ผู้ใช้คลิกใน URL ที่สร้างขึ้น ระบบจะนําผู้ใช้ไปยังหน้าบัญชี Google เพื่อให้ผู้ใช้ลงชื่อเข้าใช้บัญชี Google ได้ ระบบจะเปลี่ยนเส้นทางผู้ใช้กลับไปยังหน้าเว็บที่คุณระบุในตัวแปร "target" แต่มีพารามิเตอร์การค้นหา "token" ซึ่งมีโทเค็นแบบใช้ครั้งเดียว โดยปกติโทเค็นนี้จะใช้งานได้เพียงครั้งเดียว กล่าวคือ สามารถใช้การดําเนินการ 1 รายการในฟีดหนึ่งๆ ได้ อย่างไรก็ตาม หากคุณระบุพารามิเตอร์ "เซสชัน" เป็น true Exchange จะแลกเปลี่ยนเป็น "โทเค็นเซสชัน" ซึ่งนํามาใช้ซ้ําได้จนกว่าผู้ใช้จะจบเซสชัน ซึ่งทําได้ดังนี้
String token = Request.QueryString["token"]; Session["token"] = AuthSubUtil.exchangeForSessionToken(token, null).ToString();
ในส่วนนี้ คุณสามารถดึงโทเค็นจากพารามิเตอร์การค้นหาแล้วแลกเปลี่ยนกับ "โทเค็นเซสชัน" จากนั้น คุณจึงสามารถจัดเก็บโทเค็นไว้ใช้ภายหลังได้ คุณเลือกที่จะเก็บโทเค็นนี้ไว้ในอาร์เรย์ Session
ของ .NET แบบอัตโนมัติได้ แล้วเลือกไม่เก็บโทเค็นไว้ในฐานข้อมูล ขั้นตอนถัดไปคือการใช้โทเค็นนี้เพื่อสร้างคําขอที่มีการตรวจสอบสิทธิ์
GAuthSubRequestFactory authFactory = new GAuthSubRequestFactory("cl", "My-Cool-Application"); authFactory.Token = (String) Session["token"]; CalendarService service = new CalendarService(authFactory.ApplicationName); service.RequestFactory = authFactory;
คุณตั้งค่าออบเจ็กต์ CalendarService เพื่อโต้ตอบกับ Google Calendar API ได้โดยใช้ AuthSub สําหรับการตรวจสอบสิทธิ์ โปรดทราบว่า "cl" ที่ใช้ในเครื่องมือสร้างสําหรับ GAuthSubRequestFactory
คือชื่อบริการสําหรับปฏิทิน คุณไปที่คําถามที่พบบ่อยเกี่ยวกับ Google Data API เพื่อดูชื่อบริการอื่นๆ ได้
การตรวจสอบสิทธิ์ (ลงทะเบียน) ที่ปลอดภัย
หากเลือกที่จะลงทะเบียนเว็บแอปพลิเคชัน คุณจะเปิดใช้การรักษาความปลอดภัยเพิ่มเติมในขณะที่ใช้ AuthSub ได้ วิธีนี้จะช่วยให้คุณลงนามคําขอทั้งหมดที่เกิดจากโค้ดแบบดิจิทัลได้ ทําให้ผู้อื่นใช้โทเค็น AuthSub ที่ออกให้คุณไม่ได้ เว้นแต่จะมีคีย์ส่วนตัว ขั้นตอนแรกคือคุณกําลังสร้างลิงก์ AuthSub ที่ถูกต้องเมื่อเรียกใช้ AuthSubUtil.getRequestUrl
โดยการตั้งค่าอาร์กิวเมนต์ "ปลอดภัย" เป็น true คุณต้องทําการเปลี่ยนแปลงโค้ดอื่นอีก 2 รายการ ดังนี้
String token = Request.QueryString["token"]; Session["token"] = AuthSubUtil.exchangeForSessionToken(token, rsaKey).ToString(); ... authFactory.PrivateKey = rsaKey;
ก่อนอื่นให้สังเกตแทนที่จะเป็น null
แทน คุณส่งตัวแปร "rsaKey" ไปยังเมธอด exchangeForSessionToken
แล้ว และใช้ตัวแปรเดียวกันนี้เพื่อตั้งค่าพร็อพเพอร์ตี้ของ GAuthSubRequestFactory
เมื่อตั้งค่าการเชื่อมต่อกับบริการ ตัวแปร "rsaKey" คือ RSACryptoServiceProvider
ที่สอดคล้องกับคอมโพเนนต์คีย์ส่วนตัวของใบรับรอง x509 ที่คุณลงทะเบียนกับ Google
การสร้างคีย์ส่วนตัว RSA และใบรับรองแบบ Self-signed อาจสร้างความสับสนได้เล็กน้อย โดยเฉพาะอย่างยิ่งเนื่องจากเฟรมเวิร์ก .NET ไม่เข้าใจคีย์หรือใบรับรองที่จัดเก็บไว้ในรูปแบบ PEM คําสั่งต่อไปนี้แสดงวิธีสร้างคีย์ส่วนตัวและใบรับรองสาธารณะโดยใช้ชุดเครื่องมือ OpenSSL
openssl req -x509 -nodes -days 365 -newkey rsa:1024 -sha1 -subj \ '/C=US/ST=CA/L=Mountain View/CN=www.example.com' -keyout \ test_key.pem -out test_cert.pem openssl pkcs12 -export -in test_cert.pem -inkey test_key.pem \ -out test_cert.pfx -name "Testing Certificate"
ขั้นตอนแรกจะสร้างคีย์ส่วนตัวและใบรับรอง X509 สาธารณะทั้งในรูปแบบ PEM ที่มีชื่อว่า "test_key.pem" และ "test_cert.pem" ตามลําดับ โปรดทราบว่าใบรับรองได้รับการตั้งค่าให้ลงทะเบียนกับ "www.example.com" ในเมาน์เทนวิว รัฐแคลิฟอร์เนีย สหรัฐอเมริกา แทนค่าที่เหมาะสมสําหรับบริษัทของคุณที่นี่ ไฟล์ "test_cert.pem" มีข้อมูลที่คุณต้องส่งในหน้าการลงทะเบียน AuthSub
ขั้นตอนที่ 2 จะสร้างไฟล์ PFX จากคีย์ส่วนตัวและใบรับรองของคุณ ไฟล์นี้นําเข้าไปยังไลบรารีของไคลเอ็นต์ .NET เพื่อลงนามในคําขอแบบดิจิทัลไปยัง GData API ได้ โค้ดต่อไปนี้จะแสดงวิธีนําเข้าคีย์ส่วนตัวจากไฟล์ PFX ไปยังเว็บแอปพลิเคชัน
protected AsymmetricAlgorithm getRsaKey() { X509Certificate2 cert = new X509Certificate2("C:/MyAspSite/test_cert.pfx",""); RSACryptoServiceProvider privateKey = cert.PrivateKey as RSACryptoServiceProvider; return privateKey; }
ฟังก์ชัน getRsaKey()
ที่กําหนดโดยข้อมูลโค้ดนี้ใช้แทนตัวแปร "rsaKey" ที่แสดงด้านบนได้เมื่อใช้การตรวจสอบสิทธิ์กับ API โดยปกติแล้ว ควรแทนที่เส้นทางไฟล์ด้วยตําแหน่งที่เหมาะสมของไฟล์ PFX ที่คุณสร้าง
กรอกรหัสให้สมบูรณ์
วิธีที่ง่ายที่สุดในการแสดงวิธีใช้วิธีการที่แสดงไว้ในส่วนก่อนหน้าคือการใช้ตัวอย่างจริง ตัวอย่างโค้ดต่อไปนี้คือหน้า ASP แบบง่ายที่ใช้ AuthSub เพื่อตรวจสอบสิทธิ์ผู้ใช้ จากนั้นพิมพ์กิจกรรมใน Google ปฏิทินของผู้ใช้
<%@ Page Language="C#" AutoEventWireup="true" CodeFile="Default.aspx.cs" Inherits="_Default" %> <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd"> <%@ Import Namespace="Google.GData.Client" %> <%@ Import Namespace="Google.GData.Extensions" %> <%@ Import Namespace="Google.GData.Calendar" %> <%@ Import Namespace="System.Net" %> <script runat="server"> void PrintCalendar() { GAuthSubRequestFactory authFactory = new GAuthSubRequestFactory("cl", "TesterApp"); authFactory.Token = (String) Session["token"]; CalendarService service = new CalendarService(authFactory.ApplicationName); service.RequestFactory = authFactory; EventQuery query = new EventQuery(); query.Uri = new Uri("http://www.google.com/calendar/feeds/default/private/full"); try { EventFeed calFeed = service.Query(query); foreach (Google.GData.Calendar.EventEntry entry in calFeed.Entries) { Response.Write("Event: " + entry.Title.Text + "<br/>"); } } catch (GDataRequestException gdre) { HttpWebResponse response = (HttpWebResponse)gdre.Response; //bad auth token, clear session and refresh the page if (response.StatusCode == HttpStatusCode.Unauthorized) { Session.Clear(); Response.Redirect(Request.Url.AbsolutePath, true); } else { Response.Write("Error processing request: " + gdre.ToString()); } } } </script> <html xmlns="http://www.w3.org/1999/xhtml" > <head runat="server"> <title>Test Site</title> </head> <body> <form id="form1" runat="server"> <h1>AuthSub Sample Page</h1> <div> <% GotoAuthSubLink.Visible = false; if (Session["token"] != null) { PrintCalendar(); } else if (Request.QueryString["token"] != null) { String token = Request.QueryString["token"]; Session["token"] = AuthSubUtil.exchangeForSessionToken(token, null).ToString(); Response.Redirect(Request.Url.AbsolutePath, true); } else //no auth data, print link { GotoAuthSubLink.Text = "Login to your Google Account"; GotoAuthSubLink.Visible = true; GotoAuthSubLink.NavigateUrl = AuthSubUtil.getRequestUrl(Request.Url.ToString(), "http://www.google.com/calendar/feeds/",false,true); } %> <asp:HyperLink ID="GotoAuthSubLink" runat="server"/> </div> </form> </body> </html>
บทสรุป
AuthSub ช่วยให้เว็บแอปพลิเคชันสามารถเข้าถึงข้อมูลที่จัดเก็บไว้ในบัญชี Google ของผู้ใช้ด้วยวิธีที่ปลอดภัยและควบคุมได้ การใช้ไลบรารีของไคลเอ็นต์ .NET ช่วยให้การผสานรวมเว็บไซต์ที่ใช้ ASP กับบริการของ Google เป็นเรื่องง่าย บทความนี้มีจุดประสงค์เพื่อเริ่มต้นใช้งาน แต่คุณมีแหล่งข้อมูลเพิ่มเติมที่แนะนําให้ทําดังนี้