มิถุนายน 2007
บทนำ
บางครั้งก็ไม่มีอะไรมาแทนที่การดูสิ่งที่ส่งผ่านสายได้ โดยเฉพาะอย่างยิ่งเมื่อเขียนซอฟต์แวร์ที่ใช้บริการบนเว็บ เช่น Google Data APIs ซึ่งการดำเนินการจำนวนมากเกี่ยวข้องกับการส่งคำขอ HTTP หากวิธีอื่นๆ ไม่ได้ผล คุณสามารถยืนยันว่าโปรแกรมทำงานตามที่คาดไว้ได้โดยดูไบต์ที่ส่งและรับจริง ไลบรารีของไคลเอ็นต์จำนวนมากสำหรับ Google Data API มีโหมดการแก้ไขข้อบกพร่องซึ่งแสดงการรับส่งข้อมูล HTTP ซึ่งจะเป็นประโยชน์อย่างยิ่งเมื่อคุณไม่มีสิทธิ์เข้าถึงเครื่องดมแพ็กเก็ต เช่น WireShark หรือ Fiddler
ฉันนับครั้งที่ฉันสาบานได้ว่าโปรแกรมของฉันถูกต้องไม่ได้ แต่เมื่อตรวจสอบการติดตามแพ็กเก็ตก็พบว่ามีอักขระขึ้นบรรทัดใหม่เพิ่มเติมหรือส่วนหัว HTTP ที่ตั้งชื่อผิด การเขียนโปรแกรมกับเว็บเซอร์วิสโดยไม่ดูการรับส่งข้อมูล HTTP ก็เหมือนกับการพยายามร้อยเข็มโดยที่หลับตา
อย่างไรก็ตาม คุณอาจพบว่าตัวเองอยู่ในสถานการณ์ที่ไม่มีเครื่องดมแพ็กเก็ต หรือเครื่องดมแพ็กเก็ตไม่เพียงพอที่จะจัดการกับแพ็กเก็ตที่เข้ารหัส ไม่ต้องกังวล คุณสามารถหลีกเลี่ยงข้อจำกัดนี้ได้โดยใช้ประโยชน์จากกลไกการบันทึกในโปรแกรมบางอย่าง การใช้เครื่องมือบันทึกเหล่านี้จะช่วยให้คุณเห็นข้อมูลที่แลกเปลี่ยนบางส่วนหรือทั้งหมด แม้จะเป็นข้อมูล HTTPS ที่เข้ารหัสหรือโค้ดที่เรียกใช้จากระยะไกลก็ตาม
ในบทความนี้ ฉันได้เขียนโค้ดการวินิจฉัยตัวอย่างใน 3 ภาษาโดยใช้ไลบรารีของไคลเอ็นต์ Google Data API สำหรับ Java .NET และ Python ในแต่ละตัวอย่าง ฉันจะเปิดการบันทึกหรือการแก้ไขข้อบกพร่อง ทำการตรวจสอบสิทธิ์โดยใช้การเข้าสู่ระบบของไคลเอ็นต์ แล้วรับ รายการสเปรดชีตใน Google และพิมพ์ชื่อของสเปรดชีตเหล่านั้น
Java
คุณสามารถใช้java.util.logging
คลาสเพื่อตั้งค่าระดับการบันทึก (และแสดงข้อมูลการเข้าชม) สำหรับออบเจ็กต์หลัก 2-3 รายการใน
ไลบรารีของไคลเอ็นต์ ในตัวอย่างด้านล่าง ฉันเลือกดูส่วนหัว HTTP
และกิจกรรมของตัวแยกวิเคราะห์ XML เพื่อให้เห็นภาพรวมทั้งหมดของสิ่งที่
ส่งผ่านสาย
ไลบรารีไคลเอ็นต์ Java ของ Google Data มีคลาสแยกต่างหากสำหรับ
จัดการคำขอ HTTP และการแยกวิเคราะห์ XML ดังนั้นฉันจึงต้องสร้างออบเจ็กต์ Logger 2 รายการ
รายการหนึ่งสำหรับแต่ละคลาส
com.google.gdata.client.http.HttpGDataRequest
จัดการการรับส่งข้อมูล HTTP
ขณะที่ com.google.gdata.util.XmlParser
มีหน้าที่
แยกวิเคราะห์ XML
อินสแตนซ์ของเครื่องบันทึกจะบันทึกกิจกรรมสำหรับ
HttpGDataRequest
และ XmlParser
และคุณสามารถควบคุม
ระดับรายละเอียดของเอาต์พุตของเครื่องบันทึกแต่ละรายการได้ สำหรับการสาธิตนี้ ฉันเลือกที่จะดูเหตุการณ์ทั้งหมดที่สร้างโดยออบเจ็กต์ HttpGDataRequest
และ XmlParser
เมื่อสร้างและกำหนดค่าเครื่องบันทึกแล้ว ฉันต้องบอกให้เครื่องบันทึกทำอะไรเมื่อได้รับเหตุการณ์จากคลาส ตอนนี้ฉันต้องการเขียนข้อมูลการบันทึกทั้งหมด
ไปยังคอนโซล จึงสร้าง ConsoleHandler
และเพิ่มลงใน Logger ทั้ง 2 รายการ
โค้ดตัวอย่างของฉันมีดังนี้
import com.google.gdata.client.spreadsheet.*;
import com.google.gdata.data.spreadsheet.*;
import com.google.gdata.util.*;
import java.io.*;
import java.net.URL;
import java.util.*;
import java.util.logging.*;
public class PrintSpreadsheetsWithLogging {
public static void main(String [] args) throws AuthenticationException,
ServiceException, IOException {
// Configure the logging mechanisms.
Logger httpLogger = Logger.getLogger("com.google.gdata.client.http.HttpGDataRequest");
httpLogger.setLevel(Level.ALL);
Logger xmlLogger = Logger.getLogger("com.google.gdata.util.XmlParser");
xmlLogger.setLevel(Level.ALL);
// Create a log handler which prints all log events to the console.
ConsoleHandler logHandler = new ConsoleHandler();
logHandler.setLevel(Level.ALL);
httpLogger.addHandler(logHandler);
xmlLogger.addHandler (logHandler);
SpreadsheetService service = new SpreadsheetService("testing-loggingExampleApp-1");
service.setUserCredentials(email, password);
// Get a list of your spreadsheets.
URL metafeedUrl = new URL("http://spreadsheets.google.com/feeds/spreadsheets/private/full ");
SpreadsheetFeed feed = service.getFeed(metafeedUrl, SpreadsheetFeed.class);
// Print the title of each spreadsheet.
List spreadsheets = feed.getEntries();
for (int i = 0; i < spreadsheets.size(); i++) {
SpreadsheetEntry entry = (SpreadsheetEntry)spreadsheets.get(i);
System.out.println("\t" + entry.getTitle().getPlainText());
}
}
}
เมื่อเรียกใช้โปรแกรมนี้ คุณจะเห็นข้อความคล้ายกับต่อไปนี้ในคอนโซล (ฉันตัดส่วนที่ไม่น่าสนใจออกไป)
Jun 7, 2007 10:24:50 AM ...HttpGDataRequest setPrivateHeader FINER: Authorization: <Not Logged> Jun 7, 2007 10:24:50 AM ...HttpGDataRequest setHeader FINER: User-Agent: ... ... Jun 7, 2007 10:25:20 AM ...HttpGDataRequest execute FINE: 200 OK Jun 7, 2007 10:25:20 AM ...HttpGDataRequest execute FINER: Date: Thu, 07 Jun 2007 17:25:24 GMT Jun 7, 2007 10:25:20 AM ...HttpGDataRequest execute FINER: null: HTTP/1.1 200 OK Jun 7, 2007 10:25:20 AM ...HttpGDataRequest execute FINER: Content-Type: application/atom+xml; charset=UTF-8 Jun 7, 2007 10:25:20 AM ...HttpGDataRequest execute FINER: Last-Modified: Thu, 07 Jun 2007 17:25:22 GMT ... Jun 7, 2007 10:25:20 AM ...XmlParser startElement FINE: Start element id Jun 7, 2007 10:25:20 AM ...XmlParser endElement FINE: End element id ... Jun 7, 2007 10:25:20 AM ...XmlParser startElement FINE: Start element title Jun 7, 2007 10:25:20 AM ...XmlParser startElement FINER: Attribute type='text' Jun 7, 2007 10:25:20 AM ...XmlParser endElement FINE: End element title ... Jun 7, 2007 10:25:20 AM ...XmlParser endElement FINE: End element entry ... Jun 7, 2007 10:25:20 AM ...XmlParser endElement FINE: End element feed
บันทึกเหล่านี้อาจมีขนาดใหญ่มาก ดังนั้นคุณอาจต้องเลือกมากขึ้นในการตั้งค่าระดับของเครื่องบันทึก คุณยังสร้างFileHandler
แทนConsoleHandler
เพื่อให้จัดเก็บข้อมูลบันทึกไว้ใช้ในภายหลังได้ด้วย
แน่นอนว่าหากไม่ถนัด Java คุณก็ลองใช้ .NET ได้
.NET
หากต้องการบันทึกการรับส่งข้อมูล HTTP ในไลบรารีของไคลเอ็นต์ .NET คุณสามารถแทนที่โรงงานคำขอเริ่มต้นในไคลเอ็นต์ด้วย GDataLoggingRequestFactory
คำขอ HTTP ในไลบรารี .NET สร้างขึ้นโดย GDataRequestFactory
ซึ่งอยู่ภายในออบเจ็กต์บริการแต่ละรายการ โรงงานคำขอปกติไม่ได้ทำการบันทึกใดๆ แต่ GDataLoggingRequestFactory
ซึ่งเป็นคลาสย่อยของ GDataRequestFactory
มีการบันทึกในตัว คุณระบุเส้นทางแบบเต็มของ
ไฟล์บันทึกได้โดยตั้งค่า CombinedFileName
หลังจากตั้งค่า Request Factory แล้ว คุณต้องแทนที่ Request Factory ในออบเจ็กต์บริการโดยตั้งค่า RequestFactory
ของออบเจ็กต์บริการ
โค้ดของคุณอาจมีลักษณะดังนี้
using System;
using Google.GData.Client;
using Google.GData.Extensions;
using Google.GData.Spreadsheets;
namespace LogginTest
{
class Program
{
static void Main(string[] args)
{
SpreadsheetsService service = new SpreadsheetsService("-exampleApp-1");
service.setUserCredentials(email, password);
Google.GData.Client.GDataLoggingRequestFactory factory = new GDataLoggingRequestFactory("wise", "SpreadsheetsLoggingTest");
factory.MethodOverride = true;
factory.CombinedLogFileName = "c:\\temp\\xmllog.log";
Console.WriteLine("Log file name:" + factory.CombinedLogFileName);
service.RequestFactory = factory;
SpreadsheetQuery query = new SpreadsheetQuery();
SpreadsheetFeed feed = service.Query(query);
Console.WriteLine("Your spreadsheets:");
foreach (SpreadsheetEntry entry in feed.Entries)
{
Console.WriteLine(entry.Title.Text);
}
Console.ReadKey();
}
}
}
ไฟล์บันทึกที่ได้จะมีคำขอและการตอบกลับ XML ต่อไปนี้เป็นตัวอย่างย่อที่ฉันจัดรูปแบบโดยใช้ tidy
<?xml version='1.0' encoding='utf-8'?> <feed xmlns='http://www.w3.org/2005/Atom' xmlns:openSearch='http://a9.com/-/spec/opensearchrss/1.0/'> <id> http://spreadsheets.google.com/feeds/spreadsheets/private/full</id> <updated>2007-06-07T22:05: 02.674Z</updated> <link rel='self' type='application/atom+xml' href='http://spreadsheets.google.com/feeds/spreadsheets/private/full'> </link> ... <entry> <updated>2007-03-28T17:28:57.250Z</updated> <category scheme=' http://schemas.google.com/spreadsheets/2006' term='http://schemas.google.com/spreadsheets/2006#spreadsheet'> <title type='text'>events</title> <content type='text'>events</content> ... </entry> <entry> <updated>2007-05-25T22:11:08.200Z</updated> <category scheme=' http://schemas.google.com/spreadsheets/2006' term='http://schemas.google.com/spreadsheets/2006#spreadsheet'> </category> <title type='text'>UnitTest</title> <content type='text'>UnitTest</content> ... </entry> ... </feed>
แต่คุณอาจสนใจภาษาการเขียนสคริปต์และต้องการใช้ Python
Python
หากต้องการบันทึกการรับส่งข้อมูล HTTP ในไลบรารีของไคลเอ็นต์ Python คุณสามารถแสดงการรับส่งข้อมูลส่วนหัว HTTP ในคอนโซลได้โดยเปิดโหมดแก้ไขข้อบกพร่องในไคลเอ็นต์ HTTP ออบเจ็กต์บริการ มีสมาชิกการแก้ไขข้อบกพร่องซึ่งคุณตั้งค่าเป็น True ได้
การตั้งค่าการแก้ไขข้อบกพร่องเป็น "จริง" จะตั้งค่าสถานะการแก้ไขข้อบกพร่องในออบเจ็กต์ HTTPRequest
พื้นฐานซึ่งอยู่ในออบเจ็กต์บริการ
นี่คือตัวอย่างที่จะแสดงส่วนหัว HTTP ที่ส่งจากเซิร์ฟเวอร์สเปรดชีตเมื่อคุณขอรายการสเปรดชีต
#!/usr/bin/python
import gdata.spreadsheet.service
client = gdata.spreadsheet.service.SpreadsheetsService()
client.debug = True
client.ClientLogin(email, password)
feed = client.GetSpreadsheetsFeed()
for entry in feed.entry:
print entry.title.text
และคุณจะเห็นข้อความคล้ายกับข้อความต่อไปนี้ในคอนโซล
reply: 'HTTP/1.1 200 OK\r\n' header: Content-Type: application/atom+xml; charset=UTF-8 header: Last-Modified: Thu, 07 Jun 2007 18:22:35 GMT header: Cache-Control: max-age=0, must-revalidate, private header: Transfer-Encoding: chunked ... header: Date: Thu, 07 Jun 2007 18:22:35 GMT header: Server: GFE/1.3
เมื่อคุณดำเนินการเพิ่มเติม เช่น การแทรกหรือการอัปเดต คุณจะเห็นข้อมูลคำขอที่เกี่ยวข้องแสดงในคอนโซล
บทสรุป
บทแนะนำสั้นๆ นี้ได้แสดงให้เห็นวิธีเพิ่มฟังก์ชันการบันทึกพื้นฐานลงในโปรแกรม Java, .NET หรือ Python ที่ใช้ไลบรารีของไคลเอ็นต์ Google Data API เทคนิคเหล่านี้มีประโยชน์ในกรณีที่คุณต้องแก้ไขข้อบกพร่องของ HTTP Exchange แต่ไม่มีสิทธิ์เข้าถึงเครื่องดมแพ็กเก็ต ตัวอย่างเหล่านี้เป็นเพียงส่วนหนึ่งเท่านั้น กลไกการบันทึก ที่มีอยู่ในภาษาเหล่านี้ มีประสิทธิภาพมากกว่าที่แสดงที่นี่มาก หากต้องการข้อมูลเพิ่มเติมเกี่ยวกับการบันทึกหรือ Google Data APIs โปรดดู รายการแหล่งข้อมูลด้านล่าง
คุณดูไลบรารีของไคลเอ็นต์ที่กล่าวถึงในบทความนี้ได้ในหน้าเว็บต่อไปนี้
รายการฐานความรู้ที่เกี่ยวข้อง
- ฉันจะดูข้อมูลการบันทึก HTTP ในไลบรารีของไคลเอ็นต์ Java ได้อย่างไร
- ฉันจะดูข้อมูลการบันทึก HTTP ในไลบรารีของไคลเอ็นต์ .NET ได้อย่างไร
- เครื่องมือที่ดีสำหรับการแก้ไขข้อบกพร่องของ HTTP มีอะไรบ้าง
- Google Spreadsheets API คืออะไร
กลุ่มสนทนา: เรามีกลุ่มสนทนาอยู่หลายกลุ่ม และจะมีเพิ่มขึ้นเรื่อยๆ เมื่อเราเปิดตัว Google Data API เพิ่มเติม เราตรวจสอบกลุ่มอย่างสม่ำเสมอ
หากคุณมีคำถามหรือข้อเสนอแนะ เรายินดีรับฟัง เข้าร่วมกลุ่มสนทนา แล้วเริ่มโพสต์