ส่วนประกอบอินดี้ที่ใช้ใน Delphi ตัวอย่างการทำงานกับส่วนประกอบ Indy UDP (เซิร์ฟเวอร์ ไคลเอนต์) ใน Delphi

โดยสรุป Indy เป็นส่วนประกอบสำหรับการทำงานที่สะดวกสบายกับโปรโตคอลอินเทอร์เน็ตยอดนิยม หลักการทำงานขึ้นอยู่กับการใช้ซ็อกเก็ตในโหมดบล็อก อินดี้มีความน่าสนใจและสะดวกเพราะค่อนข้างเป็นนามธรรม และการเขียนโปรแกรมใน Indy ก็มีเพียงแค่การเขียนโปรแกรมเชิงเส้นเท่านั้น อย่างไรก็ตามบทความที่แปลมีการเผยแพร่อย่างกว้างขวางบนอินเทอร์เน็ตซึ่งมีคำว่า "โหมดการบล็อกไม่ใช่ปีศาจ" :)) ครั้งหนึ่งฉันรู้สึกขบขันกับการแปลนี้มาก บทความนี้เป็นส่วนหนึ่งของหนังสือ "Depths of Indy" โดย Hoover และ Hariri โดยหลักการแล้ว ในการทำงานร่วมกับ Indy คุณไม่จำเป็นต้องอ่านทั้งหมด แต่ฉันยังคงแนะนำให้ทำความคุ้นเคยกับหลักการทำงานของโปรโตคอลอินเทอร์เน็ต ส่วนระบอบการปกครองแบบ "ปีศาจ" นั้น การเรียกซ็อกเก็ตการบล็อคไม่ส่งคืนการควบคุมจริง ๆ จนกว่าจะเสร็จสิ้นภารกิจ เมื่อมีการเรียกบนเธรดหลัก อินเทอร์เฟซของแอปพลิเคชันอาจหยุดทำงาน เพื่อหลีกเลี่ยงสถานการณ์ที่ไม่พึงประสงค์นี้ นักพัฒนาชาวอินเดียจึงได้สร้างส่วนประกอบ TIdAntiFreeze คุณเพียงแค่ต้องโยนมันลงในแบบฟอร์ม - และอินเทอร์เฟซผู้ใช้จะถูกวาดใหม่อย่างง่ายดายในขณะที่ทำการบล็อคการโทร

คุณคงคุ้นเคยกับเนื้อหาของแท็บต่างๆ "Indy (...)" ใน Delphi แล้ว มีองค์ประกอบมากมายและแต่ละองค์ประกอบก็มีประโยชน์ได้ ตัวฉันเองไม่ได้ทำงานร่วมกับทุกคนเพราะฉันไม่เห็นความจำเป็นที่จะต้องศึกษาพวกเขาโดยไม่ต้องทำงานเฉพาะเจาะจง

การแจกจ่าย Delphi ขั้นพื้นฐานประกอบด้วย Indy v.9 พร้อมเพนนี มันอาจจะแนะนำให้อัพเกรดเป็นมากกว่านี้ทันที เวอร์ชั่นใหม่(เช่น ตอนนี้ฉันมี 10.0.76 แต่ดูเหมือนว่าจะมีอันหลังด้วย)

มีส่วนประกอบไคลเอนต์และเซิร์ฟเวอร์สำหรับการทำงานกับโปรโตคอลเดียวกัน Indy ทำให้การพัฒนาแอปพลิเคชันง่ายขึ้นมาก ต่างจากตัวเลือกในการพัฒนาฟังก์ชันการทำงานเดียวกันบนซ็อกเก็ต ตัวอย่างเช่น เมื่อต้องการสร้างการเชื่อมต่อกับเซิร์ฟเวอร์ คุณควรเรียกใช้เมธอด Connect การสร้างการเชื่อมต่อที่สำเร็จจะถูกทำเครื่องหมายด้วยวิธีการที่ส่งคืนโดยไม่ทำให้เกิดข้อยกเว้น หากไม่ได้สร้างการเชื่อมต่อ จะมีข้อยกเว้นเกิดขึ้น

ตัวอย่าง "เชิงวิชาการ" (โค้ดใช้งานไม่ได้ ห้ามเรียกใช้ :)):

ด้วย IndyClient ทำ
เริ่ม
โฮสต์:= "test.com";
พอร์ต:= 2000;
เชื่อมต่อ;
พยายาม
// ทำงานกับข้อมูล (อ่าน, เขียน...)
ในที่สุด
ตัดการเชื่อมต่อ;
จบ;
จบ;

คุณสามารถตั้งค่าโฮสต์และพอร์ตในตัวตรวจสอบวัตถุหรือในรันไทม์ได้

เหตุใดคุณจึงใช้ส่วนประกอบ Indy ในการแยกวิเคราะห์งานได้ ของใช้ต่างๆ! สิ่งที่ง่ายที่สุดคือการรับเนื้อหาของหน้า (ทุกคนคงเคยเจอสิ่งนี้แล้ว) โดยใช้ส่วนประกอบ IdHTTP:

วาร์
rcvrdata: TMemoryStream;
idHttp1: TidHttp;
เริ่ม
idHttp1:= TidHttp.Create (ไม่มี);
rcvrdata:= TMemoryStream.สร้าง;
idHttp1.Request.UserAgent:= "Mozilla/4.0 (เข้ากันได้; MSIE 5.5; Windows 98)";
idHttp1.Request.AcceptLanguage:= "ru";
idHttp1.Response.KeepAlive:= จริง;
idHttp1.HandleRedirects:= จริง;
พยายาม
idHttp1.Get(แก้ไข1.ข้อความ, rcvrdata);
ในที่สุด
idHttp1.ฟรี;
จบ;
ถ้า rcvrdata.Size > 0 ให้เริ่มต้น
ShowMessage("ได้รับแล้ว" + inttostr(rcvrdata.Size));
rcvrdata.SaveToFile("c:\111.tmp");
จบ;
rcvrdata.ฟรี;
จบ;

อย่างที่คุณเห็น คุณไม่เพียงแต่สามารถรับเนื้อหาของหน้าเท่านั้น แต่ยังจำลองการโหลดเอกสารจากไคลเอนต์เฉพาะอีกด้วย โดยทั่วไปส่วนประกอบ Indy มีประโยชน์สำหรับการสร้างส่วนหัวและคำขอ POST ข้อมูลเพิ่มเติมเกี่ยวกับเรื่องนี้พร้อมตัวอย่างในครั้งต่อไป

หากต้องการติดตามข่าวสารล่าสุดเกี่ยวกับการอัปเดตบล็อกคุณสามารถทำได้

ส่วนประกอบอินดี้ที่ใช้ใน Delphi 6

นอกเหนือจากบริการอินเทอร์เน็ตและโปรโตคอลขั้นพื้นฐานแล้ว ยังมีบริการเพิ่มเติมอีกมากมาย ซึ่งนักพัฒนาอินเทอร์เน็ตมักใช้ความสามารถนี้ นอกจากนี้ ความสามารถในการแสดงข้อมูลโดยใช้เบราว์เซอร์อาจไม่ใช่วิธีแก้ปัญหาที่ยอมรับได้สำหรับแอปพลิเคชันอินเทอร์เน็ตเสมอไป ในกรณีนี้ มีความสมเหตุสมผลที่จะใช้โครงสร้างพื้นฐานอินเทอร์เน็ตสำหรับการแลกเปลี่ยนข้อมูล และแสดงข้อมูลโดยใช้แอปพลิเคชันไคลเอนต์ที่ซับซ้อนมากขึ้นที่พัฒนาขึ้น เช่น ใน Delphi

สมมติว่าคุณต้องใช้ตรรกะเซิร์ฟเวอร์พิเศษที่ไม่รวมอยู่ในเว็บเซิร์ฟเวอร์มาตรฐาน เพื่อแก้ไขปัญหาประเภทนี้ Delphi ได้รวมไลบรารี Internet Direct (Indy) จาก Nevrona Designs (http://www.nevrona.com/Indy/) ไลบรารีนี้พัฒนาขึ้นสำหรับ Borland Delphi โดยเฉพาะ มีอยู่แล้ว 8 เวอร์ชัน ซึ่งเวอร์ชันสุดท้ายรวมอยู่ใน Delphi เวอร์ชันใหม่ ชุดส่วนประกอบแบ่งออกเป็นสามกลุ่ม: ไคลเอนต์ (Indy Client), เซิร์ฟเวอร์ (Indy Servers) และเสริม (Indy Misc)

ลูกค้า Indy และเซิร์ฟเวอร์ Indy

ส่วนประกอบ Indy Client และ Indy Servers ส่วนใหญ่เป็นคู่ที่สอดคล้องกับส่วนของไคลเอนต์และเซิร์ฟเวอร์ของโปรโตคอลและบริการ (ยกเว้นเซิร์ฟเวอร์บางตัว ซึ่งส่วนใหญ่เป็นเซิร์ฟเวอร์ ส่วนประกอบเช่น TunnelMaster และ TunnelSlave) และอนุญาตให้ใช้โปรโตคอล เช่น TCP/IP , UDP, NNTP, SMTP, FTP, HTTP รวมถึงบริการ ECHO, FINGER, WHOIS เป็นต้น

ส่วนประกอบไคลเอนต์ Indy เขียนโดยใช้ซ็อกเก็ต ซ็อกเก็ตฝั่งไคลเอ็นต์จำเป็นต้องเชื่อมต่อกับเซิร์ฟเวอร์ หากสร้างการเชื่อมต่อแล้ว ไคลเอนต์และเซิร์ฟเวอร์สามารถเริ่มแลกเปลี่ยนข้อความได้ ข้อความเหล่านี้มีลักษณะที่แตกต่างกัน แต่โดยปกติแล้วการแลกเปลี่ยนจะเกิดขึ้นโดยใช้โปรโตคอลเฉพาะ (เช่น HTTP)

TIdTCPClient และ TIdTCPServer

ส่วนประกอบเหล่านี้ใช้เพื่อรองรับหนึ่งในโปรโตคอลเครือข่ายหลัก - TCP (Transmission Control Protocol) และยังเป็นคลาสพื้นฐานสำหรับส่วนประกอบ TIdSMTP และ TIdFTP คลาส TIdTCPServer มีคุณสมบัติ ThreadMgr ที่มีค่าเริ่มต้นเป็นศูนย์ ถ้า ThreadMgr เป็นศูนย์เมื่อเปิดใช้งาน TIdTCPServer คลาส TIdThreadMgrDeafault จะถูกสร้างขึ้นโดยปริยาย มิฉะนั้น จะใช้ตัวจัดการกระบวนการที่ติดตั้งไว้

TIdUDPClient และ TIdUDPServer

ส่วนประกอบเหล่านี้ใช้เพื่อรองรับ โปรโตคอลเครือข่าย UDP (User Datagram Protocol) และยังเป็นคลาสพื้นฐานสำหรับส่วนประกอบ Indy อื่นๆ อีกจำนวนหนึ่ง

TIdChargenServer

ส่วนประกอบนี้ใช้เพื่อสร้างสัญลักษณ์สุ่ม โดยปกติแล้วใช้เพื่อการทดสอบ

TIdDayTime และ TIdDayTimeServer

ส่วนประกอบต่างๆ ใช้เพื่อให้บริการด้านเวลา ไคลเอนต์ร้องขอและเซิร์ฟเวอร์รายงานวันที่และเวลาปัจจุบัน

TIdDNSResolver

นี่คือส่วนประกอบไคลเอนต์ที่ให้บริการคำขอจากเซิร์ฟเวอร์ DNS (บริการชื่อโดเมน) การสืบค้นเซิร์ฟเวอร์ DNS ได้รับการออกแบบมาเพื่อแทนที่ชื่อคอมพิวเตอร์ด้วยที่อยู่ IP TIdDNSResolver เป็นผู้สืบทอดของคลาส TIdUDPClient

TIdDICTเซิร์ฟเวอร์

ส่วนประกอบเซิร์ฟเวอร์ที่รองรับ Dictionary Server Protocol (DICT) ซึ่งเป็นพจนานุกรมฝั่งเซิร์ฟเวอร์ที่ใช้โปรโตคอล TCP ที่อนุญาตให้ไคลเอนต์เข้าถึงพจนานุกรมภาษาธรรมชาติ

TIdDISCARDเซิร์ฟเวอร์

ส่วนประกอบเซิร์ฟเวอร์ที่รองรับเซิร์ฟเวอร์บันทึก การบันทึกสามารถใช้เป็นเครื่องมือแก้ไขและวัดผลได้ บริการบันทึกจะส่งข้อมูลใดๆ ให้กับใครก็ตามที่ยินดีรับข้อมูลนั้น

TI dEcho และ TI dECHOServer

ส่วนประกอบต่างๆ ได้รับการออกแบบมาเพื่อให้บริการตอบสนอง ซึ่งโดยทั่วไปจะใช้เพื่อตรวจสอบความสมบูรณ์ของเครือข่าย ลูกค้าส่งข้อความไปยังเซิร์ฟเวอร์ เซิร์ฟเวอร์ส่งข้อความกลับไปยังลูกค้า หากข้อความอ่านไม่ออก แสดงว่าเครือข่ายทำงานผิดปกติ

TIdFinger และ TIdFingerServer

ส่วนประกอบต่างๆ ได้รับการออกแบบมาเพื่อจัดเตรียมโปรโตคอลที่ช่วยให้ผู้ใช้สามารถสืบค้นข้อมูลเกี่ยวกับการมีอยู่ของผู้ใช้รายอื่นในระบบได้ เซิร์ฟเวอร์บางแห่งจัดการคำขอไคลเอ็นต์ดังกล่าว การใช้ส่วนประกอบคู่นี้จะช่วยให้คุณสามารถให้บริการตามคำขอของลูกค้าที่กำหนดว่ามีผู้ใช้รายอื่นอยู่ในระบบ

TIdFTP

ส่วนประกอบนี้รวมถึงการรองรับโปรโตคอลการถ่ายโอนไฟล์อย่างเต็มรูปแบบ - FTP (File Transfer Protocol) รองรับการถ่ายโอนข้อมูลแบบพาสซีฟและแอคทีฟ รวมถึงการดำเนินการเช่น GET และ PUT การลบไดเร็กทอรี การรับโควต้า ขนาดไฟล์และไดเร็กทอรี TI dFTP ใช้คลาส TIdSimpleServer เพื่อดำเนินการ เมื่อดำเนินการถ่ายโอนไฟล์ FTP การเชื่อมต่อ TCP รองจะถูกเปิดสำหรับการถ่ายโอนข้อมูล และจะปิดลงเมื่อมีการถ่ายโอนข้อมูล การเชื่อมต่อนี้เรียกว่า “ดาต้าลิงค์” ซึ่งเป็นลักษณะเฉพาะสำหรับแต่ละไฟล์ที่กำลังถ่ายโอน

TIdGopher และ TIdGopherServer

ส่วนประกอบเหล่านี้ได้รับการออกแบบเพื่อให้มีโปรโตคอลเครือข่ายที่ถูกแทนที่ เมื่อเร็วๆ นี้จาก WWW (โลก ไวด์เว็บ) โปรโตคอล HTTP เซิร์ฟเวอร์ที่ใช้โปรโตคอลนี้จัดเตรียมระบบสนับสนุนโฟลว์เอกสารแบบกระจายแบบลำดับชั้น ตัวอย่างของส่วนประกอบคู่นี้ ซึ่งอยู่ในไดเร็กทอรี \demos\indy\GopherClient และ \demos\indy\GopherServer แสดงให้เห็นว่าโปรโตคอลนี้สามารถใช้เพื่อจัดเตรียมได้อย่างไร เครือข่ายท้องถิ่นข้อมูลเกี่ยวกับไฟล์ที่อยู่ในคอมพิวเตอร์ของคุณรวมถึงไฟล์ที่ปิด

TIdHostNameServer

ส่วนประกอบเซิร์ฟเวอร์ที่ออกแบบมาเพื่อส่งชื่อเซิร์ฟเวอร์ภายในเครื่องไปยังไคลเอนต์

TIdHTTP และ TIdHTTPServer

ส่วนประกอบต่างๆ ใช้เพื่อจัดเตรียมโปรโตคอลเครือข่าย HTTP (รองรับเวอร์ชัน 1.0 และ 1.1 รวมถึงการดำเนินการ GET, POST และ HEAD) นอกจากนี้ยังมีการสนับสนุนสำหรับการตรวจสอบสิทธิ์และการใช้พร็อกซีเซิร์ฟเวอร์ ส่วนประกอบเซิร์ฟเวอร์ใช้เพื่อให้บริการแก่เว็บเซิร์ฟเวอร์อื่นที่รองรับโปรโตคอลที่กำหนด TIdHTTPServer อำนวยความสะดวกในการใช้งานฟังก์ชันต่างๆ เช่น คุกกี้ การจัดการสถานะ ฯลฯ

TIdIcmpClient

ส่วนประกอบไคลเอ็นต์ที่ออกแบบมาเพื่อจัดเตรียม Internet Control Message Protocol (ICMP) ซึ่งใช้ในการดำเนินการ Ping และการติดตามเครือข่าย

TIdPOP3

ส่วนประกอบไคลเอ็นต์ที่ออกแบบมาเพื่อจัดเตรียม Post Office Protocol (POP) รวมถึงการสนับสนุนการเข้ารหัสและถอดรหัส MIME และการส่งอักขระแบบหลายไบต์

TIdIMAP4เซิร์ฟเวอร์

ส่วนประกอบเซิร์ฟเวอร์ที่ออกแบบมาเพื่อรองรับการดำเนินการ IMAP (Internet Message Access Protocol) บนเซิร์ฟเวอร์ โปรโตคอลช่วยให้คุณค้นหาข้อความได้ อีเมลบนเซิร์ฟเวอร์ ความแตกต่างระหว่างโปรโตคอล IMAP และ POP คือต้องใช้โปรโตคอล POP หน่วยความจำเพิ่มเติมเพื่อจัดเก็บข้อมูล และโปรโตคอล IMAP จะเข้าถึงเซิร์ฟเวอร์แทนเครื่องไคลเอ็นต์ IMAP4 ถูกสร้างขึ้นเพื่อแทนที่ POP3 แต่ POP3 ยังคงเป็นมาตรฐานที่ใช้กันอย่างแพร่หลายจนถึงทุกวันนี้

TIdIRCเซิร์ฟเวอร์

ส่วนประกอบเซิร์ฟเวอร์ที่ออกแบบมาเพื่อรองรับการดำเนินการบริการที่ใช้บ่อยที่สุดบนอินเทอร์เน็ต หรือที่เรียกกันทั่วไปว่าแชท ส่วนประกอบให้พื้นฐาน การก่อสร้างตึกสำหรับเซิร์ฟเวอร์ IRC (Internet Relay Chat)

TIdMappedPortTCP

ส่วนประกอบเซิร์ฟเวอร์ที่ออกแบบมาเพื่อสร้างพอร์ตที่แมป ซึ่งมักใช้ในพร็อกซีเซิร์ฟเวอร์ วิธีการของส่วนประกอบนี้ช่วยให้คุณสามารถแมปพอร์ตหนึ่งไปยังอีกพอร์ตหนึ่งได้ ตัวอย่างเช่น พอร์ต 80 สามารถแมปกับพอร์ต 3000 ได้ และคำขอทั้งหมดไปยังพอร์ตแรก (พอร์ต 80) จะถูกส่งต่อไปยังพอร์ตที่สอง (พอร์ต 3000)

TIdNNTP และ TIdNNTPServer

ส่วนประกอบเหล่านี้จำเป็นเพื่อรองรับ Network News Transfer Protocol (NNTP) ที่ใช้ในบริการข่าว คอมโพเนนต์ไคลเอ็นต์ประกอบด้วยการสนับสนุนสำหรับการเข้ารหัสและถอดรหัส MIME ตลอดจนการสนับสนุนอักขระหลายไบต์และการเข้ารหัสสำรอง ส่วนประกอบเซิร์ฟเวอร์ช่วยให้คุณสร้างเซิร์ฟเวอร์ข่าวได้ สิ่งสำคัญคือต้องทราบว่า TIdNNTPServer ไม่ใช่เซิร์ฟเวอร์ข่าวที่มีคุณสมบัติครบถ้วน แต่เป็นส่วนประกอบที่ให้ฟังก์ชันพื้นฐานสำหรับเซิร์ฟเวอร์ดังกล่าว

TIdQOTD และ TIdQOTDServer

ส่วนประกอบต่างๆ ใช้เพื่อให้บริการใบเสนอราคาประจำวัน ส่วนประกอบไคลเอนต์เชื่อมต่อกับอินสแตนซ์ส่วนประกอบเซิร์ฟเวอร์เพื่อรับใบเสนอราคารายวัน แต่ละอินสแตนซ์ของเซิร์ฟเวอร์มีฐานข้อมูลการอ้างอิงที่ไม่ซ้ำกัน

TIdSMTP

คอมโพเนนต์ไคลเอ็นต์ที่ออกแบบมาเพื่อใช้ในแอปพลิเคชัน Simple Mail Transfer Protocol (SMTP) ซึ่งให้การสนับสนุนการตรวจสอบสิทธิ์ การเข้ารหัสและถอดรหัส MIME และการสนับสนุนอักขระแบบหลายไบต์

TIdSNTP

ส่วนประกอบไคลเอนต์ที่ออกแบบมาเพื่อให้บริการ SNTP (Simple Network Time Protocol) - บริการเวลา สามารถใช้เชื่อมต่อกับบริการเวลาใดก็ได้เพื่อกำหนดวันที่และเวลาปัจจุบัน

TIdSimpleServer

ส่วนประกอบเซิร์ฟเวอร์ที่ให้เซิร์ฟเวอร์ TCP แบบน้ำหนักเบา ช่วยให้คุณสามารถจัดระเบียบการเชื่อมต่อแบบจุดต่อจุด ใช้เพื่อสร้างเซิร์ฟเวอร์ที่มีผู้ใช้รายเดียว กล่าวคือ สามารถให้บริการได้ครั้งละหนึ่งการเชื่อมต่อเท่านั้น ต่างจากคอมโพเนนต์ TIdTCPServer ตรงที่จะไม่เกิดกระบวนการรองเมื่อรอคำขอจากไคลเอ็นต์และเมื่อประมวลผลคำขอเหล่านี้ กล่าวอีกนัยหนึ่ง หากเซิร์ฟเวอร์ให้บริการคำขอจากไคลเอนต์ และในขณะนั้นไคลเอนต์อื่นกำลังติดต่อเซิร์ฟเวอร์เพื่อเชื่อมต่อ เซิร์ฟเวอร์นั้นจะถูกบล็อกจนกระทั่งสิ้นสุดการประมวลผลคำขอแรก

TIdTelnet และ TIdTelnetServer

ส่วนประกอบไคลเอ็นต์ใช้เพื่อจัดระเบียบเซสชันระยะไกลบนคอมพิวเตอร์เครื่องอื่น รวมถึงการเจรจาคอนโซลและการรับรองความถูกต้อง โปรโตคอลการสื่อสารถือว่ามีบุคคลที่โต้ตอบแบบโต้ตอบกับเซิร์ฟเวอร์ ส่วนประกอบไคลเอนต์ไม่มีการรองรับการแสดงผลหรือการจำลองเทอร์มินัล แต่เพียงให้การเชื่อมต่อกับส่วนของเซิร์ฟเวอร์ โดยทั่วไปแล้ว โปรโตคอลเซิร์ฟเวอร์ TIdTelnetServer ใช้เพื่อจัดระเบียบฐานข้อมูลระยะไกลด้วยอินเทอร์เฟซข้อความสำหรับการโต้ตอบแบบโต้ตอบกับไคลเอนต์

TIdTime และ TIdTimeServer

คอมโพเนนต์ไคลเอ็นต์เป็นทางเลือกแทนคอมโพเนนต์ TIdSNTP ในการกำหนดเวลา สิ่งสำคัญคือต้องทราบว่ารูปแบบของโปรโตคอลทั้งสองนั้นแตกต่างกัน TIdTime ขึ้นอยู่กับรูปแบบ RFC 868 (ส่งคืนเวลาในมาตรฐาน UNIX OS ภายใน โดยดำเนินการแปลงที่จำเป็นทั้งหมด) ส่วนประกอบเซิร์ฟเวอร์มีความคล้ายคลึงในการทำงานกับเซิร์ฟเวอร์ DayTime สามารถใช้เพื่อใช้บริการเวลาได้ คอมพิวเตอร์ท้องถิ่น- ไม่จำเป็นต้องมีรหัสเพิ่มเติม เพียงสร้างอินสแตนซ์ของ TIdTimeServer ที่จะส่งคืนเวลาของนาฬิกาภายในของคอมพิวเตอร์เซิร์ฟเวอร์

TIdTrivialFTP และ TIdTrivialFTPServer

ส่วนประกอบเหล่านี้จำเป็นต่อการจัดระเบียบโปรโตคอลการถ่ายโอนไฟล์อย่างง่าย ส่วนประกอบไคลเอ็นต์ของโปรโตคอลนี้ใช้เพื่อเชื่อมต่อกับอินสแตนซ์ของส่วนประกอบเซิร์ฟเวอร์ที่เกี่ยวข้อง โปรโตคอลนี้มีไว้สำหรับการถ่ายโอนไฟล์แบบส่วนตัวและน้ำหนักเบา เช่น ในเครือข่ายท้องถิ่นหรือสำหรับการโหลด (อัปโหลด) ตารางเส้นทางไปยังเราเตอร์ เนื่องจากคุณลักษณะที่อ่อนแอของโปรโตคอลนี้ จึงไม่แนะนำให้ใช้เมื่อใช้อัลกอริธึมการรับรองความถูกต้องหรือกลไกความปลอดภัยอื่น ๆ วัตถุประสงค์หลักของโปรโตคอลนี้คือเพื่อถ่ายโอนไฟล์ไปยังอุปกรณ์ฮาร์ดแวร์เพื่อวัตถุประสงค์ในการแก้ไข

TIdTunnelMaster และ TIdTunnelSlave

ส่วนประกอบช่องสัญญาณเซิร์ฟเวอร์ใช้ในพร็อกซีเซิร์ฟเวอร์เพื่อจัดระเบียบการเชื่อมต่อแบบลอจิคัลหลายรายการบนฟิสิคัลเดียว (ช่องสัญญาณ) คลาสเหล่านี้สามารถใช้เพื่อวัตถุประสงค์ต่างๆ เช่น เพื่อจัดระเบียบการเชื่อมต่อที่เป็นความลับผ่านช่องทางที่ไม่เป็นความลับ

TIdWhois และ TIdWhoIsServer

ส่วนประกอบไคลเอนต์นี้เชื่อมต่อกับเซิร์ฟเวอร์ Whois มาตรฐานใด ๆ ทำให้คุณได้รับข้อมูลเกี่ยวกับโดเมน ส่วนประกอบเซิร์ฟเวอร์มีฟังก์ชันพื้นฐานของเซิร์ฟเวอร์ NIC

อินดี้ อื่นๆ

หน้าจานสี Indy Miscellaneous Components ประกอบด้วย BASE64, UUE, Quoted Printable และรูปแบบการสื่อสารทางอีเมลทั่วไปอื่นๆ ตัวเข้ารหัส (MD2, MD4 และ MD5) สำหรับมาตรฐานการเข้ารหัสที่ใช้ในการจัดเก็บรหัสผ่านและ ลายเซ็นอิเล็กทรอนิกส์ในรูปแบบที่ไม่สามารถย้อนกลับได้ (ถอดรหัสยาก) รวมถึงส่วนประกอบและยูทิลิตี้ที่มีประโยชน์อื่น ๆ อีกมากมายที่มักใช้ในการพัฒนาแอปพลิเคชันอินเทอร์เน็ต

TIdAntiFreeze

เนื่องจากอัลกอริธึมแบบบล็อกของส่วนประกอบ Indy จึงมักปรากฏว่าแอปพลิเคชันค้างในขณะที่การเชื่อมต่อกำลังทำงาน เพื่อลดการใช้กระบวนการรอง (เธรด) เมื่อจัดระเบียบการสื่อสารเพื่อป้องกันไม่ให้แอปพลิเคชันค้างก็เพียงพอที่จะวางส่วนประกอบที่ระบุลงในแบบฟอร์ม

ส่วนประกอบทำงานโดยแยกวิเคราะห์คำขอจากสแต็กโปรโตคอล TCP/IP และส่งข้อความไปยังแอปพลิเคชันในระหว่างความล่าช้าเมื่อการเชื่อมต่อภายนอกถูกบล็อก ซึ่งสร้างภาพลวงตาของการเรียกใช้โค้ด เนื่องจากส่วนประกอบส่งผลต่อการเชื่อมต่อที่ถูกบล็อกสำหรับกระบวนการหลักเท่านั้น จึงไม่จำเป็นต้องใช้ TIdAntiFreeze ในกระบวนการรองของแอปพลิเคชัน โปรดทราบว่าคอมโพเนนต์ TIdAntiFreeze ทำให้การเชื่อมต่อช้าลงเนื่องจากกระบวนการหลักถูกขัดจังหวะเป็นระยะๆ ในการประมวลผลข้อความ เป็นไปตามนั้นจะต้องได้รับการดูแลเพื่อให้แน่ใจว่าแอปพลิเคชันที่กำลังพัฒนาไม่ได้ใช้เวลาประมวลผลข้อความมากเกินไป รวมถึง OnClick, OnPaint, OnResize ฯลฯ สามารถควบคุมได้ผ่านคุณสมบัติของคลาส TIdAntiFreeze ในระดับหนึ่ง การใช้ส่วนประกอบนี้ไม่จำเป็น แต่ช่วยให้คุณสามารถแก้ปัญหาการซิงโครไนซ์การเชื่อมต่อกับส่วนต่อประสานภาพของแอปพลิเคชัน

TIdDateTimeStamp

คลาสสำหรับการคำนวณวันที่และเวลาที่เกี่ยวข้องกับข้อเท็จจริงที่ว่าอินเทอร์เน็ตโปรโตคอลใช้รูปแบบวันที่และเวลาที่แตกต่างกัน นอกจากนี้ ไคลเอนต์และเซิร์ฟเวอร์อาจอยู่ในโซนเวลาที่แตกต่างกัน

TIdIPWatch

เป็นส่วนประกอบแบบจับเวลาซึ่งจะคอยติดตามการเปลี่ยนแปลงที่อยู่ IP ของคอมพิวเตอร์อย่างต่อเนื่อง เหตุการณ์คอมโพเนนต์เกิดขึ้นเมื่อตรวจพบการเปลี่ยนแปลง โดยปกติส่วนประกอบนี้ใช้เพื่อตรวจสอบว่าคอมพิวเตอร์เชื่อมต่อกับอินเทอร์เน็ตหรือเครือข่ายอื่นหรือไม่ การเปลี่ยนแปลงที่อยู่ IP ในสถานการณ์นี้อาจเกิดขึ้นเนื่องจากที่อยู่ IP ถูกกำหนดโดยเซิร์ฟเวอร์ DHCP (Dynamic Host Configuration Protocol) เมื่อเชื่อมต่อกับเครือข่ายใหม่

TIdLogDebug

วัตถุประสงค์ของส่วนประกอบนี้คือเพื่อสกัดกั้นเหตุการณ์ของส่วนประกอบไคลเอนต์หรือเซิร์ฟเวอร์ใด ๆ และวางบันทึกของเหตุการณ์ไว้ ไฟล์ที่ระบุ- ส่วนประกอบนี้มีประโยชน์มากสำหรับการดีบักส่วนประกอบ Indy

TIdMessage

ส่วนประกอบนี้จะใช้ร่วมกับส่วนประกอบอื่นๆ เพื่อถอดรหัสหรือเข้ารหัสข้อความอย่างเหมาะสม สิ่งเหล่านี้อาจเป็นส่วนประกอบ POP, SMTP และ NNTP คลาสรองรับการเข้ารหัสและถอดรหัส MIME อักขระหลายไบต์ และการเข้ารหัส ISO

TIdNetworkCalculator

หนึ่งในส่วนประกอบ Indy ไม่กี่ชิ้นที่สามารถใช้ในการสร้างแอปพลิเคชันได้ เครื่องคำนวณเครือข่ายสามารถใช้เพื่อคำนวณที่อยู่ IP รวมถึงเน็ตมาสก์ ซับเน็ต คลาสเครือข่าย ฯลฯ

TIdThreadMgrDefault

ส่วนประกอบให้การควบคุมกระบวนการรองตามค่าเริ่มต้น สร้างขึ้นเมื่อองค์ประกอบ Indy ใดๆ ที่สนับสนุนการจัดการกระบวนการไม่มีอินสแตนซ์ของคลาส TIdThreadManager ที่กำหนดไว้ ส่วนประกอบมีความสามารถพื้นฐานสำหรับการจัดการกระบวนการรองเท่านั้น: การสร้างและทำลายกระบวนการเหล่านี้ตามความต้องการ

TIdThreadMgrPool

ส่วนประกอบการจัดการกระบวนการขั้นสูงกว่า TIdThreadMgrDefault เนื่องจากจะผสานกระบวนการต่างๆ แทนที่จะสร้างหรือทำลายกระบวนการเหล่านั้นตามความต้องการ

TIdVCard

VCard เทียบเท่ากับนามบัตรทางอิเล็กทรอนิกส์ และอาจมีข้อมูลส่วนบุคคลและข้อมูลกราฟิกของเจ้าของ

TIdIMFDecoder

ออกแบบมาเพื่อถอดรหัสข้อความอินเทอร์เน็ต มันเป็นลูกหลานของคลาส TIdCoder เช่นเดียวกับส่วนประกอบตัวเข้ารหัสอื่นๆ ทั้งหมด คลาส TIdCoder ถอดรหัสตามมาตรฐานรูปแบบข้อความอินเทอร์เน็ต ARPA RFS-822 ที่เสนอในเดือนสิงหาคม พ.ศ. 2525 และมาตรฐานการส่งข้อความ USENET RFC 1036 ที่เสนอในเดือนธันวาคม พ.ศ. 2530

ส่วนประกอบจะขยายคลาส TIdCoder เพื่อให้สามารถตรวจจับรูปแบบ RFS-822 ตามบริบทของส่วนหัว โดยมีโหมดถอดรหัสเมื่อรับและการเข้ารหัสและการถอดรหัส MIME คอมโพเนนต์ TIdIMFDecoder ใช้ในคลาส TIdMessageClient เพื่อถอดรหัสข้อความที่ได้รับและส่งข้อความ

TIdQuotedPrintableEncoder

QuotedPrintableEncoder ช่วยให้คุณสามารถถอดรหัสข้อความในรูปแบบที่ระบุ สามารถทำหน้าที่เป็นองค์ประกอบแบบสแตนด์อโลนที่มีประเภทการเข้ารหัสที่ระบุ ทำให้สามารถส่งข้อความที่มีประเภทการเข้ารหัสใหม่ได้

TIdBase64ตัวเข้ารหัส

ใช้อัลกอริธึมการเข้ารหัสอื่นที่ทำให้สามารถส่งอักขระที่ไม่สามารถพิมพ์ได้

TIdUUตัวเข้ารหัส

ใช้หนึ่งในอัลกอริธึมการเข้ารหัสแรกๆ การเข้ารหัส UU บางครั้งใช้เมื่อส่งบทความไปยังบริการข่าว

TIdXXEncoder

วิธีการเข้ารหัสนี้ไม่น่าจะถูกนำมาใช้เลย โดยพื้นฐานแล้ว นี่คือการเข้ารหัส UU เดียวกัน แต่มีตารางการเข้ารหัสที่แตกต่างกัน

TIdCoderMD2

ส่วนประกอบที่มีอัลกอริธึมการเข้ารหัส MD (Message Digest) ประเภทต่างๆ ทั้งหมดเป็นแบบสับเปลี่ยนทางเดียว และไม่มีอัลกอริธึมการถอดรหัส

ส่วนประกอบของไคลเอ็นต์โปรโตคอลและเซิร์ฟเวอร์สามารถใช้ในการพัฒนาเซิร์ฟเวอร์และแอปพลิเคชันอินเทอร์เน็ตไคลเอ็นต์ ร่วมกับหรือแทนแอปพลิเคชันพื้นฐาน (ClientSocket, ServerSocket) และส่วนประกอบอื่นๆ จากอินเทอร์เน็ตและจานสี Fastnet ส่วนประกอบ Indy ไม่ได้ใช้สถาปัตยกรรม WebBroker ซึ่งใช้การสนับสนุนระดับต่ำสำหรับอินเทอร์เน็ตโปรโตคอลและบริการโดยตรงในซอร์สโค้ด ( ซอร์สโค้ดแนบมาด้วย)

TIdConnectionInterceptOpenSSL และ TIdServerInterceptOpenSSL

โปรโตคอล SSL - Secure Sockets Layer ซึ่งรับประกันความลับและความน่าเชื่อถือของการสื่อสารระหว่างสองแอปพลิเคชันนั้นมีสองชั้น ที่ระดับต่ำของโปรโตคอลการขนส่งหลายชั้น (เช่น TCP) SSL เป็นโปรโตคอลการบันทึกและใช้เพื่อห่อหุ้มโปรโตคอลระดับสูงกว่าต่างๆ ข้อดีของ SSL ก็คือเป็นโปรโตคอลแอปพลิเคชันอิสระ แต่สามารถใช้โปรโตคอลระดับสูงกว่าบน SSL ได้

SSL ให้ความปลอดภัยในการสื่อสารซึ่งมีสามหน้าที่หลัก: ให้การเชื่อมต่อที่เป็นความลับ; การเข้ารหัสด้วย กุญแจสาธารณะ(ใช้เพื่อยืนยันความถูกต้องของผู้รับ) รองรับความน่าเชื่อถือในการส่งข้อมูล

  • การเข้ารหัสแบบสมมาตรใช้ในการเข้ารหัสข้อมูล (เช่น DES, RC4 เป็นต้น)
  • ลายเซ็นดิจิทัลมีให้โดยใช้การเข้ารหัสคีย์สาธารณะแบบอสมมาตร (เช่น RSA, DSS เป็นต้น)
  • ความน่าเชื่อถือของการสื่อสาร การส่งข้อความรวมถึงการตรวจสอบความสมบูรณ์ของข้อความผ่านรหัสแก้ไข MAC ฟังก์ชันแฮชที่ปลอดภัย (เช่น SHA, MD5 ฯลฯ) โดยใช้การคำนวณ MAC

เมื่อใช้ร่วมกับ HTTP และการรับรองความถูกต้องของเซิร์ฟเวอร์ SSL จะมอบฟังก์ชันการเข้ารหัสที่จำเป็นและรักษาการเชื่อมต่อที่สร้างขึ้นเพิ่มเติมโดยการตรวจสอบข้อมูลประจำตัวของเว็บเซิร์ฟเวอร์ ฯลฯ สิ่งสำคัญคือต้องเข้าใจว่า SSL ปกป้องการสื่อสารระหว่างการถ่ายโอนข้อมูลเท่านั้น และไม่ได้แทนที่กลไกความปลอดภัยอื่นๆ

คอมโพเนนต์ TIdConnectionInterceptOpenSSL และ TIdServerInterceptOpenSSL ให้การเชื่อมต่อทั้งฝั่งไคลเอ็นต์และฝั่งเซิร์ฟเวอร์โดยใช้โปรโตคอล SSL ควรสังเกตว่าส่วนประกอบ TIdConnectionInterceptOpenSSL และ TIdServerInterceptOpenSSL มีเฉพาะใน Delphi 6 เท่านั้นและไม่มีใน Kylix นี่เป็นเพราะความซับซ้อนของโปรโตคอลซึ่งในกรณีของการใช้งาน Windows นั้นจะขึ้นอยู่กับฟังก์ชั่นของระบบปฏิบัติการ

ตัวอย่างของการใช้ส่วนประกอบ Indy สามารถพบได้ในไดเร็กทอรี /Delphi6/Demos/Indy โดยรวมแล้วไลบรารี Indy ในเวอร์ชัน 8.0 มีส่วนประกอบ 69 รายการ มีการระบุว่าในเวอร์ชัน 9.0 ไลบรารีที่ระบุจะมีส่วนประกอบ 86 รายการ ส่วนประกอบทั้งหมดได้รับการรวมเป็นหนึ่งเดียวและรวมอยู่ในทั้ง Delphi 6 และ Kylix ซึ่งช่วยให้สามารถใช้ในการพัฒนาแอปพลิเคชันข้ามแพลตฟอร์มได้ ส่วนประกอบ Indy ทั้งหมดรองรับมัลติเธรด

ส่วนประกอบ Indy ใช้ฟังก์ชันการทำงานเกือบทั้งหมดที่พบในอินเทอร์เน็ตและส่วนประกอบ Fastnet ดังที่แสดงไว้อย่างชัดเจนในตาราง

Fastn และส่วนประกอบ ส่วนประกอบอินดี้ วัตถุประสงค์ของส่วนประกอบ
1 TserverSocket, TClientSocket TIdTCPserverSocket, TIdTCPClientSocket ปฏิสัมพันธ์ระหว่างคอมพิวเตอร์สองเครื่อง (ไคลเอนต์และเซิร์ฟเวอร์) โดยใช้โปรโตคอล TCP/IP
2 TNMDayTime TIdDayTime, TIdDayTimeServer สอบถามเซิร์ฟเวอร์สำหรับเวลาปัจจุบัน
3 TNMEcho TIdEcho, TIdEchoServer ใช้เพื่อสื่อสารกับเซิร์ฟเวอร์ตอบกลับ
4 TNMFinger TIdFinger, TIdFingerServer ใช้เพื่อรับข้อมูลเกี่ยวกับผู้ใช้จากเซิร์ฟเวอร์การค้นหาทางอินเทอร์เน็ต
5 TNMFTP TIdFTP, TIdTrivialFTP, TIdTrivialFTPServer ให้การถ่ายโอนไฟล์โดยใช้โปรโตคอล FTP
6 TNMHTTP TIdHTTP, TIdHTTPเซิร์ฟเวอร์ ใช้โปรโตคอล HTTP สำหรับการแลกเปลี่ยนข้อมูล
7 TNMMsgServ, TNMMsg ใช้ในการถ่ายทอดอย่างเรียบง่าย ข้อความจากไคลเอนต์ไปยังเซิร์ฟเวอร์
8 TNMNNTP TIdNNTP, TIdNNTPเซิร์ฟเวอร์ รองรับการแลกเปลี่ยนข้อมูลกับเซิร์ฟเวอร์ข่าว
9 TNMPOP3 TIdPOP3 ใช้เพื่อรับอีเมลจากเมลเซิร์ฟเวอร์โดยใช้โปรโตคอล POP3
10 TNMSMTP TIdSMTP ใช้ในการส่งอีเมล์ผ่านทาง เมลเซิร์ฟเวอร์อินเทอร์เน็ต
11 TNMStrm, TNMStrmServ ส่งข้อมูลไบนารี่ที่เขียนไปยังสตรีมโดยใช้โปรโตคอล TCP/IP
12 TNMUDP TIdUDP, TIdUDPเซิร์ฟเวอร์ ถ่ายโอนข้อมูลโดยใช้โปรโตคอล UDP
13 TpowerSock, TNMเซิร์ฟเวอร์ทั่วไป คลาสที่ห่อหุ้มส่วนประกอบที่เป็นพื้นฐานสำหรับการเขียนไคลเอนต์ของคุณเอง (Powersock) และเซิร์ฟเวอร์ (NMGeneralServer)
14 TNMUUตัวประมวลผล TIdUUEncoder, TIdUUDecoder ดำเนินการบันทึก ไฟล์ไบนารีเป็นรูปแบบ MIME หรือ UUENCODE
15 TNMURL แปลงสตริงเป็นรูปแบบ HTML และทำการแปลงแบบย้อนกลับ

ข้อยกเว้นคือคลาสต่างๆ เช่น TNMMsgServ, TNMMsg, TNMStrm, TNMStrmServ, TpowerSock, TNMGeneralServer, TNMURL ซึ่งใช้โปรโตคอลที่ล้าสมัยหรือมีการใช้งานฟังก์ชันในกลุ่มคลาสทางเลือกขนาดใหญ่

อย่างไรก็ตาม แตกต่างจากรุ่นก่อนๆ นั่นคือส่วนประกอบอินเทอร์เน็ตและ Fastnet Indy มีส่วนประกอบเซิร์ฟเวอร์ที่สมบูรณ์ยิ่งขึ้นและส่วนประกอบสำหรับการแปลงรหัสและการเข้ารหัสข้อมูล รวมถึงการสนับสนุนการตรวจสอบสิทธิ์ (Indy Misc palette) ดังที่เห็นได้จากตารางด้านบน โปรโตคอลและบริการหลักไม่ได้จัดทำโดยไคลเอนต์เท่านั้น แต่ยังรวมถึงส่วนประกอบของเซิร์ฟเวอร์ด้วย บริการเหล่านี้คือบริการเวลา บริการตอบสนอง การรับข้อมูลผู้ใช้ รวมถึงโปรโตคอล HTTP, NNTP, UDP และแม้แต่ FTP เวอร์ชันที่ง่ายที่สุด

ตัวอย่างการใช้ส่วนประกอบ Indy

ในส่วนประกอบ Indy ที่มีอยู่ใน Delphi ที่อยู่ IP จะถูกกำหนดไว้ในคุณสมบัติ Host ซึ่งโดยทั่วไปจะมีเฉพาะในแอปพลิเคชันไคลเอนต์เท่านั้น ส่วนประกอบที่โฮสต์บนเซิร์ฟเวอร์มีวิธีการที่ช่วยให้คุณสามารถเริ่มหรือหยุดการสำรวจพอร์ตที่เกี่ยวข้องได้ ตัวอย่างเช่น การเปลี่ยนคุณสมบัติ Active ของส่วนประกอบ IdTCPServer จะเริ่มต้นหรือหยุดการสำรวจพอร์ตที่เกี่ยวข้อง เมื่อสร้างการเชื่อมต่อระหว่างไคลเอนต์และเซิร์ฟเวอร์แล้ว การถ่ายโอนข้อมูลจึงสามารถเริ่มต้นได้

ส่วนประกอบ Indy ให้ความสำคัญกับความปลอดภัยและความน่าเชื่อถือเป็นอย่างมากเมื่อทำงานกับข้อมูล ตัวอย่างเช่น ส่วนประกอบ IdTCPClient มีวิธีการเชื่อมต่อและตัดการเชื่อมต่อ การใช้เทคนิคการเขียนโปรแกรมเช่นโค้ดด้านล่างจากฝั่งไคลเอ็นต์:

ด้วย TCPClient จะเริ่มต้นการเชื่อมต่อ; ลอง lstMain.Items.Add(ReadLn); ในที่สุดก็ตัดการเชื่อมต่อ; จบ; จบ;

และใช้คุณสมบัติการเชื่อมต่อที่ส่งผ่านเป็นพารามิเตอร์ไปยังอินสแตนซ์ AThread ของคลาส TIdPeerThread จากฝั่งเซิร์ฟเวอร์:

ด้วย AThread.Connection ให้เริ่ม WriteLn ("สวัสดีจากเซิร์ฟเวอร์ Basic Indy Server"); ตัดการเชื่อมต่อ; จบ;

คุณสามารถวางใจได้ในการดำเนินการเชื่อมต่อตามปกติหรือการจัดการข้อผิดพลาดที่ถูกต้อง

สังเกตเมธอด ReadLn และ WriteLn ของคลาสที่เกี่ยวข้อง ซึ่งคล้ายกับคำสั่ง Pascal I/O มาตรฐาน นี่เป็นการยกย่องเทคนิคการเขียนโปรแกรม UNIX ซึ่งการทำงานของระบบส่วนใหญ่ดำเนินการโดยการอ่านและเขียนลงในไฟล์ที่เกี่ยวข้อง

เช่นเดียวกับส่วนประกอบ Fastnet คลาสองค์ประกอบ Indy มีเหตุการณ์ที่สามารถใช้เพื่อจัดเตรียมการจัดการเหตุการณ์ได้ ตัวอย่างเช่น คุณสามารถจัดเรียงข้อความให้แสดงบนแบบฟอร์มเมื่อเชื่อมต่อกับไคลเอนต์:

ขั้นตอน TForm1.IdECHOServer1Connect (AThread: TIdPeerThread); start lblStatus.caption:= "[ ให้บริการลูกค้า ]"; จบ;

Indy จัดเตรียมส่วนประกอบที่ใช้โปรโตคอลกับส่วนของไคลเอนต์และเซิร์ฟเวอร์ที่เป็นเอกลักษณ์ของไลบรารีนี้ ส่วนประกอบ TIdGopherServer และ TIdGopher ต้องขอบคุณเมธอด GetExtensedMenu, GetFile, GetMenu, GetTextFile บนฝั่งไคลเอ็นต์และ ReturnGopherItem, SendDirectoryEntry บนฝั่งเซิร์ฟเวอร์ ช่วยในการดูไฟล์ หลากหลายชนิดรวมถึงรายการที่ถูกทำเครื่องหมายว่าซ่อนอยู่ รวมถึงไดเร็กทอรีบน คอมพิวเตอร์ระยะไกล(คล้ายกับคำสั่ง dir *.* ในระบบปฏิบัติการ MS-DOS)

การใช้คอมโพเนนต์ IdSMTP และ IdMessage คุณสามารถสร้างเว็บแอปพลิเคชันของคุณเองที่สามารถส่งอีเมลโดยใช้โปรโตคอล SMTP ได้อย่างง่ายดาย

ในกรณีนี้ คลาส IdMessage (หนึ่งใน 23 คอมโพเนนต์จากหน้า Indy Misc) มีหน้าที่สร้างข้อความ ซึ่งตามมาจากชื่อ และ IdSMTP ใช้สำหรับจัดระเบียบการเชื่อมต่อกับเซิร์ฟเวอร์อีเมล

เทคโนโลยีที่ใช้ใน Indy ใช้การล็อกการอ่านและเขียน การดำเนินการเชื่อมต่อใดๆ ที่ใช้ใน Indy จะรอให้การเชื่อมต่อเสร็จสมบูรณ์ เมื่อทำงานกับส่วนประกอบไคลเอนต์ Indy โดยทั่วไปคุณจะต้องทำสิ่งต่อไปนี้:

  • ขอเชื่อมต่อกับเซิร์ฟเวอร์
  • ส่งคำขออ่านและเขียนไปยังเซิร์ฟเวอร์ (ขึ้นอยู่กับประเภทของเซิร์ฟเวอร์ ขั้นตอนจะดำเนินการครั้งเดียวหรือทำซ้ำหลายครั้ง)
  • ยุติการเชื่อมต่อกับเซิร์ฟเวอร์และตัดการเชื่อมต่อ

ส่วนประกอบอินดี้ได้รับการออกแบบเพื่อให้มีนามธรรมในระดับสูงเป็นพิเศษ รายละเอียดปลีกย่อยและรายละเอียดของสแต็ก TCP/IP ถูกซ่อนไม่ให้โปรแกรมเมอร์ เพื่อให้เขาสามารถมุ่งความสนใจไปที่งานที่ทำอยู่ได้

ตัวอย่างเล็กๆ ต่อไปนี้แสดงเซสชัน bean ไคลเอนต์ทั่วไป:

ด้วย IndyClient ให้เริ่มต้น Host:= "zip.pbe.com"; // โฮสต์เรียกพอร์ต:= 6000; // พอร์ตเพื่อเรียกเซิร์ฟเวอร์บน Connect; ลอง // รหัสของคุณอยู่ที่นี่ในที่สุด ตัดการเชื่อมต่อ; จบ; จบ;

ในตัวอย่างนี้ แม้ว่าการเชื่อมต่อกับเซิร์ฟเวอร์จะไม่ได้ถูกสร้างขึ้น การเชื่อมต่อจะสิ้นสุดลงอย่างสวยงามเนื่องจากการใช้คำสั่ง try-finally

ส่วนประกอบเซิร์ฟเวอร์ของ Indy อธิบายเซิร์ฟเวอร์รุ่นต่างๆ มากมายที่สามารถใช้ได้ ขึ้นอยู่กับความต้องการและโปรโตคอลที่คุณใช้

TIdTCPServer เป็นส่วนประกอบเซิร์ฟเวอร์ที่ใช้บ่อยที่สุด ซึ่งสร้างกระบวนการรองที่ไม่ขึ้นกับกระบวนการแอปพลิเคชันหลัก กระบวนการที่สร้างขึ้นรอการร้องขอที่เข้ามาจาก ผู้มีโอกาสเป็นลูกค้า- กระบวนการรองแต่ละกระบวนการถูกสร้างขึ้นสำหรับลูกค้าแต่ละรายที่มีการร้องขอที่ตอบสนอง เหตุการณ์ที่เกิดขึ้นในระหว่างกระบวนการบำรุงรักษาเกี่ยวข้องกับบริบทของกระบวนการที่เกี่ยวข้อง

กล่าวอีกนัยหนึ่ง สำหรับการเชื่อมต่อไคลเอ็นต์แต่ละครั้ง คลาส TIdTCPServer ใช้เธรดรองที่ไม่ซ้ำกันโดยการเรียกตัวจัดการเหตุการณ์ OnExecute ของเธรดนั้น พารามิเตอร์อย่างเป็นทางการของเมธอด OnExecute คือการอ้างอิงถึงอินสแตนซ์ของคลาส Athread ที่สอดคล้องกับเธรดที่สร้างขึ้น คุณสมบัติการเชื่อมต่อของคลาสนี้คือการอ้างอิงถึงคลาส TIdTCPConnection ซึ่งเป็นอินสแตนซ์ที่ถูกสร้างขึ้นเพื่อประมวลผลคำขอของไคลเอ็นต์ TIdTCPConnection รองรับการอ่านและเขียนผ่านการเชื่อมต่อ รวมถึงการสร้างและยุติเซสชันการสื่อสาร

โปรโตคอล UDP ทำงานโดยไม่ต้องสร้างการเชื่อมต่อกับเซิร์ฟเวอร์ก่อน (แต่ละแพ็กเก็ตที่ส่งเป็นชุดข้อมูลอิสระ และไม่ได้เป็นส่วนหนึ่งของเซสชันหรือการเชื่อมต่อที่ใหญ่กว่า) ในขณะที่ TIdTCPServer จะสร้างเธรดแยกกันสำหรับแต่ละการเชื่อมต่อ TIdUDPServer จะใช้เธรดหลักหรือเธรดรองเดี่ยวที่จัดการคำขอโปรโตคอล UDP ทั้งหมด เมื่อ TIdUDPServer ทำงานอยู่ เธรดจะถูกสร้างขึ้นเพื่อฟังแพ็กเก็ต UDP ที่เข้ามา สำหรับแต่ละแพ็กเก็ตที่ได้รับ เหตุการณ์ OnUDPRead จะถูกยกขึ้นบนเธรดหลักหรือในบริบทของเธรดการฟัง ขึ้นอยู่กับค่าของคุณสมบัติ ThreadedEvent เมื่อ ThreadedEvent ประเมินเป็น False เหตุการณ์จะเกิดขึ้นบนเธรดหลัก ไม่เช่นนั้นจะเกิดขึ้นบนเธรดที่กำลังฟัง ในขณะที่กำลังประมวลผลเหตุการณ์ การทำงานของเซิร์ฟเวอร์อื่นๆ จะถูกบล็อก ดังนั้นจึงเป็นสิ่งสำคัญเพื่อให้แน่ใจว่าขั้นตอน OnUDPRead ทำงานโดยเร็วที่สุด

หากคุณต้องการสร้างแอปพลิเคชันไคลเอนต์ใหม่สำหรับเซิร์ฟเวอร์ที่มีอยู่โดยใช้โปรโตคอลที่มีอยู่ งานของคุณคือการพัฒนาและแก้ไขข้อบกพร่องแอปพลิเคชันไคลเอนต์เท่านั้น แต่เมื่อคุณต้องพัฒนาทั้งลูกค้าและ แอปพลิเคชันเซิร์ฟเวอร์ไม่ว่าจะใช้โปรโตคอลที่มีอยู่หรือใหม่ เรากำลังเผชิญกับปัญหา "ไก่กับไข่" แบบคลาสสิก จะเริ่มเขียนโปรแกรมได้ที่ไหน - จากไคลเอนต์หรือจากเซิร์ฟเวอร์?

แน่นอนว่าทั้งไคลเอนต์และเซิร์ฟเวอร์จะต้องถูกสร้างขึ้นในที่สุด สำหรับแอปพลิเคชันจำนวนมาก โดยเฉพาะอย่างยิ่งที่ใช้โปรโตคอลแบบข้อความ (เช่น HTTP) การเริ่มสร้างแอปพลิเคชันโดยการออกแบบเซิร์ฟเวอร์จะง่ายกว่า และสำหรับการดีบักก็มีไคลเอนต์ที่สะดวกอยู่แล้ว นี่คือแอปพลิเคชันคอนโซล Telnet ที่พร้อมใช้งานทั้งบน Windows และ UNIX

หากคุณพิมพ์คอนโซล คำสั่งเทลเน็ต 127.0.0.1 80 ด้วยที่อยู่ IP ของคอมพิวเตอร์ในระบบและหมายเลขพอร์ต 80 ซึ่งใช้เป็นค่าเริ่มต้นโดยเว็บเซิร์ฟเวอร์ จากนั้นแอปพลิเคชันจะตอบสนองด้วยข้อความที่แสดงในรูปที่ 1 6 ในกรณีของระบบปฏิบัติการ Windows 2000 และ IIS 5.0

ในการสร้างเซิร์ฟเวอร์ที่ง่ายที่สุดโดยใช้ส่วนประกอบ Indy คุณต้องมี:

หากคุณต้องการออกแบบเซิร์ฟเวอร์ที่ไม่เพียงแต่จะแจ้งไคลเอ็นต์อย่างถูกต้องเมื่อการเชื่อมต่อขาดหายไป แต่ยังให้ข้อมูลเกี่ยวกับสถานการณ์ข้อผิดพลาดที่เกิดขึ้นด้วย ให้ใช้คำสั่ง try-ยกเว้น แทน try-finally - ตัวอย่างเช่น แสดงในตัวอย่างต่อไปนี้:

ขั้นตอน TDataModule1.IdTCPServer1Execute (ATThread: IdPeerThread); var s: สตริง; เริ่มต้นด้วย AThread.Connection ลองลอง s:= ReadLn; // ดำเนินงานของเซิร์ฟเวอร์ที่นี่ // หากไม่มีข้อยกเว้น // เขียนการตอบสนองของเซิร์ฟเวอร์ WriteLn ยกเว้นใน e: ข้อยกเว้นจะเริ่มต้น WriteLn (e.Message); //ลองยกเว้นในที่สุดก็ตัดการเชื่อมต่อ;

ตัวอย่างเล็กๆ นี้สาธิตขั้นตอนในการสร้างเซิร์ฟเวอร์ข้อความแบบง่าย รวมถึงวิธีการแก้ไขข้อบกพร่อง

เซิร์ฟเวอร์ที่อธิบายไว้ข้างต้นเป็นตัวอย่างทั่วไปขององค์กรของการคำนวณแบบกระจายสมัยใหม่

คุณสมบัติของการสร้างแอปพลิเคชั่นหลายชั้น

เมื่อเร็ว ๆ นี้ มีการใช้งานเซิร์ฟเวอร์หลายเครื่องมากขึ้นเพื่อตอบสนองคำขอของลูกค้า เซิร์ฟเวอร์ประเภทนี้ เมื่อได้รับคำขอของลูกค้าและเตรียมบางส่วนสำหรับการประมวลผลเพิ่มเติม จะติดต่อกับเซิร์ฟเวอร์อื่นและส่งคำขอหรือคำขอที่แปลงแล้วไป เซิร์ฟเวอร์ชั้นสองสามารถสื่อสารกับเซิร์ฟเวอร์อื่นได้ ดังนั้นเราจึงสามารถพูดคุยเกี่ยวกับสถาปัตยกรรมเซิร์ฟเวอร์แบบหลายชั้นได้

ต่อไปเราจะสร้างเซิร์ฟเวอร์การเข้าถึงข้อมูลที่มีวัตถุประสงค์เพื่อส่งคืนข้อมูลจากฐานข้อมูล อย่างไรก็ตาม เซิร์ฟเวอร์นี้ไม่ได้อ่านหรือเขียนลงในไฟล์ฐานข้อมูลโดยตรง แต่จะสื่อสารกับเซิร์ฟเวอร์ฐานข้อมูลเพื่อค้นหาข้อมูลที่ลูกค้าต้องการแทน

ดังนั้นเราจึงเริ่มพัฒนาแอปพลิเคชันด้วยสถาปัตยกรรมสามระดับ ในการสร้างเซิร์ฟเวอร์ฐานข้อมูลโดยใช้ส่วนประกอบ Indy คุณต้องมี:

  1. สร้างโครงการใหม่
  2. วางอินสแตนซ์ของคอมโพเนนต์ TIdTCPServer จากจานสี Indy Servers บนรูปแบบหลักของโปรเจ็กต์
  3. ตั้งค่าคุณสมบัติ DefaultPort ของอินสแตนซ์คลาส TIdTCPServer1 เป็น 6001 (ขอแนะนำให้กำหนดค่าขนาดใหญ่เพื่อหลีกเลี่ยงการทำซ้ำหมายเลขพอร์ตในแอปพลิเคชันต่างๆ) และตั้งค่าคุณสมบัติ Active เป็นจริง
  4. เพิ่มโมดูลใหม่ให้กับโปรเจ็กต์โดยเลือกไฟล์ | ใหม่ | โมดูลข้อมูล และวางอินสแตนซ์ของส่วนประกอบ SQLConnection และ SQLDataSet จากแท็บ dbExpress บนแผงส่วนประกอบ
  5. ตั้งค่าคุณสมบัติ ConnectionName ของคลาส SQLConnection เป็น IBLocal และ LoginPrompt เป็น False หากคุณไม่ได้กำหนดค่า IBLocal บนฐานข้อมูล Employee.gdb ให้ทำตามขั้นตอนนี้ก่อน
  6. ตั้งค่าคุณสมบัติ SQLConnection ของคลาส SQLDataSet เป็น SQLConnection1 และกำหนดคุณสมบัติให้กับ CommandText คำสั่ง SQL: เลือกลูกค้า CONTACT_FIRST, CONTACT_LAST จากลูกค้าโดยที่ CUST_NO = :cust

แซร์จ โดซูคอฟ ไมค์ ฟาม

บทความนี้จะแสดงวิธีสร้างบริการบนเว็บแบบสแตนด์อโลนโดยใช้ Indy kit และ Delphi 7 และวิธีใช้ Indy kit เพื่อรองรับบริการบนเว็บที่ใช้ SOAP ของ Delphi 7 ด้านหลัง ข้อมูลเพิ่มเติมสำหรับข้อมูลเกี่ยวกับการสร้างบริการบนเว็บ โปรดดูบทความที่ยอดเยี่ยมของ Nick Hodges บนไซต์ชุมชน Borland: Shakespeare on the Web

ไม่ช้าก็เร็ว คุณอาจต้องสร้างเซิร์ฟเวอร์ที่เป็นเซิร์ฟเวอร์ HTTP แบบสแตนด์อโลนและรองรับบริการบนเว็บ ตัวอย่างเช่น คุณอาจต้องการสร้างแอปพลิเคชันเซิร์ฟเวอร์ที่ใช้ SOAP สำหรับแอปพลิเคชันระดับ n ที่สร้างโดยใช้ Delphi

การแนะนำ

ความช่วยเหลือออนไลน์ของ Delphi นั้นยอดเยี่ยมมาก การเรียนการสอนตามลำดับเกี่ยวกับวิธีสร้างบริการเว็บเซิร์ฟเวอร์ MIDAS (รุ่น COM, DCOM) แต่ในทางปฏิบัติแล้วไม่มีข้อมูลเกี่ยวกับการสร้างแอปพลิเคชัน MIDAS n-tier แบบสแตนด์อโลนที่ใช้โปรโตคอล SOAP

เผยแพร่ก่อนหน้านี้โดย Dave Nottage บทความนี้อธิบายแนวคิดของวิธีสร้างบริการเว็บใน Delphi 6 ด้วยการสนับสนุน SOAP และความสามารถในการเผยแพร่อินเทอร์เฟซ SOAP ของ Datamodule นั่นคือบทความนี้อนุญาตให้คุณเรียนรู้วิธีสร้าง n-tier ของคุณเอง ระบบไมดาส

Delphi 7 ของ Borland และชุด Indy ใหม่รองรับฟังก์ชันนี้ในตัว

อย่างไรก็ตาม แม้จะรองรับในตัวแล้ว แต่ฟีเจอร์นี้ก็ไม่ได้รับการบันทึกไว้

โพสต์ล่าสุดในการประชุมทางเว็บของ Borland และการค้นหาเว็บโดยใช้เซิร์ฟเวอร์ของ Google ทำให้ผู้เขียนสามารถพัฒนาวิธีการแปลงโค้ดที่มีอยู่จาก Delphi 6 เป็น Delphi 7 ได้ แต่ทุกอย่างมีเวลาของมัน

แนวคิดหลัก

บทความนี้เป็นส่วนแรกของซีรี่ส์สามส่วน มันอธิบายบทบัญญัติหลัก ส่วนที่สองและสามจะกล่าวถึงปัญหาและวิธีแก้ปัญหาบางประการ เรามาเริ่มอธิบายแนวคิดหลักกันดีกว่า

  • เป็นเซิร์ฟเวอร์ HTTP แบบสแตนด์อโลน
  • ใช้ Indy เป็นแพลตฟอร์ม
  • รองรับการเผยแพร่ผ่านโปรโตคอล SOAP
  • สามารถเผยแพร่ SOAP DataModules ได้ ซึ่งจะช่วยให้คุณสร้างเซิร์ฟเวอร์ n-tier ของคุณเองโดยใช้ SOAP/HTML

เซิร์ฟเวอร์ HTTP และ SOAP

หลายๆ คนรู้จัก Indy และเคยใช้ส่วนประกอบของ THTTPServer มาก่อน เป็นเรื่องง่ายที่จะใส่ส่วนประกอบนี้ลงในแบบฟอร์มใบสมัคร แต่คุณจะทำให้ส่วนประกอบนี้รองรับ SOAP ได้อย่างไร ในไดเร็กทอรี "C:Program FilesBorlandDelphi7SourceIndy" คุณจะพบไฟล์ IdHTTPWebBrokerBridge.pas นี่คือสิ่งที่คุณต้องการ

ไฟล์นี้ไม่ได้เป็นส่วนหนึ่งของไฟล์ปฏิบัติการ Indy ดังนั้นคุณต้องรวมไว้ในโปรเจ็กต์ปัจจุบันของคุณเป็นไฟล์โปรเจ็กต์มาตรฐาน (ในการคอมไพล์โปรเจ็กต์ คุณจะต้องมีไฟล์ IdCompilerDefines.inc ด้วย) ไฟล์เหล่านี้จะต้องถูกคัดลอกไปยังไดเร็กทอรีโปรเจ็กต์ปัจจุบัน อาจจำเป็นต้องเปลี่ยนแปลงโค้ดเพื่อเพิ่มความเร็ว ดังนั้นจึงควรแยกไฟล์เหล่านี้ออกจาก Indy Distribution

ข้อมูลต่อไปนี้จะอธิบายการใช้งานส่วนประกอบทดแทนจาก THTTPServer ซึ่งขยายเพื่อรองรับแพ็กเก็ต SOAP ที่เรียกว่า TIdHTTPWebBrokerBridge โครงสร้างนี้เป็นคลาสที่สืบทอดมาจาก TCustomHTTPServer และรองรับการผูกคำขอพื้นฐาน

เนื่องจากคลาสนี้ไม่สามารถเข้าถึงได้จากพาเล็ต คุณจะต้องกำหนดคลาสนี้เป็นออบเจ็กต์ปกติเมื่อรันโค้ดของคุณ

ออบเจ็กต์นี้สามารถใช้ได้ในลักษณะเดียวกับ THTTPServer ทั่วไปทุกประการ ยกเว้นคุณสมบัติเพิ่มเติมที่เปิดใช้งานการดำเนินการกับ SOAP
อย่างไรก็ตาม มาดูการเตรียมโค้ดที่จำเป็นกันก่อน

เว็บโบรคเกอร์และอินดี้

สำหรับผู้ที่เคยสร้างเว็บเซอร์วิสมาก่อนก็รู้ว่าใช้งาน เว็บโบรคเกอร์- Delphi 7 เช่นเดียวกับ Delphi 6 ใช้สถาปัตยกรรม WebBroker เพื่อรองรับ SOAP

ดังนั้นคุณต้องสร้างโมดูลขึ้นมา TWebModuleและวางคอมโพเนนต์สามรายการต่อไปนี้ลงไป: THHTTPSoapDispatcher, THHTTPSoapPascalInviver และ TWSDLHTMLPublish ทั้งหมดนี้มีอยู่ในแท็บ WebServices ของพาเล็ตส่วนประกอบ หลังจากเชื่อมโยง SOAPDispatcher กับ SOAPPascalInvacer แล้ว แบบฟอร์มใบสมัครก็พร้อมแล้ว ผลลัพธ์ที่ได้ควรเป็นสิ่งที่แสดงในรูปต่อไปนี้:

(โมดูล uWebModule.pas)

ทางที่ดีควรปล่อยให้ทุกอย่างเหมือนเดิม เนื่องจากไม่จำเป็นต้องเปลี่ยนแปลงหรือรันโค้ดที่กำหนดเองใดๆ สำหรับแบบฟอร์มนี้

เว็บโมดูลและอินดี้

มาดูส่วนอื่นๆ ของโค้ดที่จำเป็นในการใช้งานเซิร์ฟเวอร์ HTTP กัน

อย่างที่คุณเห็น TIdHTTPWebBrokerBridge มีเมธอด RegisterWebModuleClass ซึ่งช่วยให้คุณสามารถลงทะเบียน WebModule ของคุณเองและทำให้พร้อมใช้งานบนเซิร์ฟเวอร์

ดังนั้น หลังจากสร้างอ็อบเจ็กต์เซิร์ฟเวอร์ fServer คุณเพียงแค่ต้องเรียกคลาส fServer.RegisterWebModuleClass (TwmSOAPIndy)

บันทึก.ในการใช้งาน TIdHTTPWebBrokerBridge ตามปกติ ออบเจ็กต์ TwmSOAPIndy จะถูกสร้างขึ้นทุกครั้งที่ได้รับการร้องขอ แน่นอนว่านี่ไม่จำเป็น ดังนั้นจึงสามารถแก้ไขคลาสเพื่อสร้างการสร้างถาวรได้ ของวัตถุชิ้นนี้ตราบใดที่วัตถุเซิร์ฟเวอร์มีอยู่ ขอแนะนำให้คุณดูเอกสารประกอบการใช้งานคลาสสำหรับข้อมูลเพิ่มเติม

เซิร์ฟเวอร์พร้อมหรือยัง?

ความรู้เบื้องต้นเกี่ยวกับอินดี้

ความรู้เบื้องต้นเกี่ยวกับอินดี้
โพสต์โดย Chad Z. Hower
หน้าแรก: http://www.atozedsoftware.com
การแปล: อนาโตลี พอดโกเรตสกี้
การแนะนำ
ฉันเขียนบทความนี้เมื่อ รุ่นปัจจุบันคือ Indy 8.0 บทความนี้ส่วนใหญ่นำไปใช้ได้และมีประโยชน์มากใน Indy เวอร์ชันต่อๆ ไป หากคุณชอบบทความนี้และต้องการอ่านบทความเชิงลึกเพิ่มเติม ลองอ่านหนังสือ Indy in Depth
อินดี้กำลังทำงานในโหมดบล็อก
อินดี้ใช้เต้ารับปิดกั้น โหมดการบล็อกจะคล้ายกับการอ่าน-เขียนไฟล์ เมื่ออ่านหรือเขียนข้อมูล ฟังก์ชันจะไม่ส่งคืนการควบคุมจนกว่าการดำเนินการจะเสร็จสิ้น ความแตกต่างจากการทำงานกับไฟล์คือการโทรอาจใช้เวลานานกว่า เนื่องจากยังไม่มีข้อมูลที่ร้องขอ ขึ้นอยู่กับความเร็วที่เครือข่ายหรือโมเด็มของคุณทำงาน
ตัวอย่างเช่น เรียกเมธอดง่ายๆ และรอจนกว่าการควบคุมจะถูกส่งกลับไปยังจุดเรียก หากการโทรสำเร็จ การควบคุมจะถูกส่งกลับจากเมธอด หากเกิดข้อผิดพลาด ข้อยกเว้นจะเกิดขึ้น
ล็อคดาวน์ไม่ทำให้เสียชีวิต
เนื่องจากโหมดการบล็อค เราจึงถูกคู่ต่อสู้ของเราพ่ายแพ้หลายครั้ง แต่โหมดการบล็อคไม่ใช่ปีศาจ
ปัญหาปรากฏขึ้นหลังจากย้าย Winsock ไปยัง Windows ในระบบปฏิบัติการ Unix โดยทั่วไปปัญหาจะได้รับการแก้ไขโดยการฟอร์ก (คล้ายกับมัลติเธรด แต่มีกระบวนการแยกกันแทนที่จะเป็นเธรด) ไคลเอนต์ Unix และ daemons ต้องแยกกระบวนการที่ควรทำงานและใช้โหมดการบล็อก Windows 3.x ไม่สามารถขนานได้และไม่รองรับเธรดมากนัก การใช้อินเทอร์เฟซการบล็อกจะทำให้อินเทอร์เฟซผู้ใช้ค้างและทำให้โปรแกรมไม่ตอบสนอง ดังนั้นจึงมีการเพิ่มโหมดไม่บล็อกลงใน WinSock ทำให้ Windows 3.x มีข้อจำกัดในการใช้ Winsock โดยไม่บล็อกเธรดหลักและเธรดเดียวของโปรแกรม สิ่งนี้จำเป็นต้องมีการเขียนโปรแกรมที่แตกต่างกัน และ Microsoft และโหมดการบล็อกอื่น ๆ ก็ใส่ร้ายป้ายสีอย่างกระตือรือร้นเพื่อปกปิดข้อบกพร่องของ Windows 3.x
จากนั้นก็มาถึง Win32 ซึ่งสามารถรองรับการทำงานแบบมัลติเธรดได้ แต่เมื่อถึงเวลานี้ สมองของพวกเขาสับสนไปหมดแล้ว (นั่นคือ นักพัฒนาถือว่าการบล็อกซ็อกเก็ตเป็นการสร้างปีศาจ) และเป็นการยากที่จะเปลี่ยนแปลงสิ่งที่พวกเขาทำไปแล้ว ดังนั้นการใส่ร้ายระบอบการปิดกั้นจึงยังคงดำเนินต่อไป
ในความเป็นจริง Unix มีเพียงซ็อกเก็ตที่บล็อกเท่านั้น การบล็อกซ็อกเก็ตยังมีข้อดีและดีกว่ามากสำหรับการทำงานแบบมัลติเธรด การรักษาความปลอดภัย และด้านอื่นๆ มีการเพิ่มส่วนขยายบางส่วนลงใน Unix สำหรับซ็อกเก็ตที่ไม่ปิดกั้น อย่างไรก็ตาม มันทำงานแตกต่างไปจากบน Windows มาก สิ่งเหล่านี้ไม่ได้มาตรฐานและไม่ธรรมดามาก การบล็อกซ็อกเก็ตใน Unix ใช้ในเกือบทุกกรณี และจะยังคงใช้ต่อไป
ข้อดีของโหมดการบล็อก·ตั้งโปรแกรมง่ายกว่า - โหมดการบล็อกตั้งโปรแกรมได้ง่ายกว่า รหัสผู้ใช้ทั้งหมดสามารถอยู่ในที่เดียวและดำเนินการตามลำดับที่เป็นธรรมชาติ ·พอร์ตไปยัง Unix ง่ายกว่า - เนื่องจาก Unix ใช้ซ็อกเก็ตที่ปิดกั้น โค้ดแบบพกพาจึงเขียนได้ง่ายกว่าในกรณีนี้ Indy ใช้ข้อเท็จจริงนี้ในการเขียนโค้ดแบบเดียวกัน ·สะดวกกว่าในการทำงานกับเธรด - เนื่องจากซ็อกเก็ตการปิดกั้นมีลำดับที่ได้มาจากพันธุกรรม ดังนั้นจึงง่ายต่อการใช้งานในเธรด
ข้อเสียของโหมดการบล็อก · อินเทอร์เฟซผู้ใช้ค้างในไคลเอนต์ - การเรียกซ็อกเก็ตการบล็อกจะไม่ส่งคืนการควบคุมจนกว่าจะทำงานเสร็จสิ้น เมื่อมีการเรียกดังกล่าวในเธรดหลักของแอปพลิเคชัน แอปพลิเคชันจะไม่สามารถประมวลผลข้อความของผู้ใช้ได้ ซึ่งทำให้อินเทอร์เฟซผู้ใช้หยุดทำงาน หน้าต่างไม่รีเฟรช และไม่มีข้อความอื่นใดที่จะถูกประมวลผลจนกว่าจะส่งคืนการควบคุมจากซ็อกเก็ตการบล็อก
ส่วนประกอบ TIdAntiFreeze
Indy มีส่วนประกอบพิเศษที่ช่วยแก้ปัญหาการแช่แข็งส่วนต่อประสานกับผู้ใช้ เพียงเพิ่มองค์ประกอบ TIdAntiFreeze หนึ่งรายการในแอปพลิเคชันของคุณ และคุณสามารถบล็อกการโทรได้โดยไม่ต้องหยุดการทำงานของ UI
TIdAntiFreeze ทำงานบนตัวจับเวลาภายในภายนอก call stack และเรียก Application.ProcessMessages เมื่อหมดเวลาใช้งาน การเรียกจากภายนอกไปยัง Indy ยังคงถูกบล็อกอยู่ ดังนั้นจึงทำงานเหมือนกับการไม่ใช้คอมโพเนนต์ TIdAntiFreeze การใช้ TIdAntiFreeze ช่วยให้คุณได้รับข้อดีทั้งหมดของการบล็อกซ็อกเก็ต โดยไม่มีข้อเสียใดๆ
โค้ดเธรด (เธรด)
ด้วยการบล็อกซ็อกเก็ต โค้ดสตรีมจึงมักถูกใช้เกือบทุกครั้ง ซ็อกเก็ตที่ไม่ปิดกั้นสามารถใช้เธรดได้เช่นกัน แต่ต้องมีบางส่วน การประมวลผลเพิ่มเติมและข้อดีในกรณีนี้จะสูญหายไปเมื่อเปรียบเทียบกับการปิดกั้นซ็อกเก็ต
ข้อดีของเธรด·การตั้งค่าลำดับความสำคัญ - สามารถกำหนดค่าลำดับความสำคัญของแต่ละเธรดได้ ซึ่งช่วยให้แต่ละงานได้รับการจัดสรรเวลา CPU มากขึ้นหรือน้อยลง ·การห่อหุ้ม - แต่ละการเชื่อมต่อสามารถมีรูปร่างหน้าตาของอินเทอร์เฟซกับการเชื่อมต่ออื่นได้ ·ความปลอดภัย - แต่ละเธรดสามารถมีคุณลักษณะด้านความปลอดภัยที่แตกต่างกันได้ ·โปรเซสเซอร์หลายตัว - ให้ข้อได้เปรียบบนระบบที่มีโปรเซสเซอร์หลายตัว ·ไม่จำเป็นต้องซีเรียลไลซ์ - ให้การทำงานพร้อมกันเต็มรูปแบบ คำขอทั้งหมดจะต้องได้รับการประมวลผลในเธรดเดียวโดยไม่ต้องมีเธรดมากนัก ดังนั้นงานแต่ละงานจึงต้องแบ่งออกเป็นชิ้นเล็ก ๆ เพื่อให้สามารถทำงานได้อย่างรวดเร็ว ในขณะที่บล็อกหนึ่งกำลังทำงานอยู่ ทุกคนถูกบังคับให้รอให้บล็อกนั้นเสร็จสิ้น เมื่อสิ้นสุดบล็อกหนึ่ง บล็อกถัดไปจะถูกดำเนินการและต่อๆ ไป เมื่อใช้มัลติเธรด แต่ละงานสามารถตั้งโปรแกรมเป็นหน่วยเดียวและได้ ระบบปฏิบัติการกระจายเวลาระหว่างงานทั้งหมด
กระทู้สำรวจความคิดเห็น
การสร้างและทำลายเธรดต้องใช้ทรัพยากรมาก นี่เป็นงานที่ยากเป็นพิเศษสำหรับเซิร์ฟเวอร์ที่มีการเชื่อมต่อระยะสั้น เซิร์ฟเวอร์แต่ละเครื่องจะสร้างเธรด ใช้งานในช่วงเวลาสั้นๆ จากนั้นจึงทำลายเธรดนั้น ส่งผลให้มีการสร้างและลบเธรดบ่อยครั้งมาก ตัวอย่างนี้คือเว็บเซิร์ฟเวอร์ คำขอเดียวถูกส่งไปและการตอบกลับแบบธรรมดาจะถูกส่งกลับ เมื่อใช้เบราว์เซอร์ การเชื่อมต่อและการตัดการเชื่อมต่อนับร้อยสามารถเกิดขึ้นได้เมื่อดูเว็บไซต์ใดๆ
เธรดการโพลสามารถแก้ไขสถานการณ์นี้ได้ แทนที่จะสร้างและทำลายเธรดตามความต้องการ เธรดจะถูกเลือกจากรายการเธรดที่ไม่ได้ใช้แต่สร้างไว้แล้วจากพูล เมื่อเธรดไม่จำเป็นอีกต่อไป เธรดนั้นจะถูกส่งกลับไปยังพูลแทนที่จะถูกทำลาย เธรดในพูลถูกทำเครื่องหมายว่าไม่ได้ใช้ ดังนั้นจึงไม่ต้องใช้เวลา CPU เพื่อการปรับปรุงที่ดียิ่งขึ้น เธรดสามารถปรับให้เข้ากับความต้องการปัจจุบันของระบบได้แบบไดนามิก
Indy รองรับการโพลเธรด เธรดพูลใน Indy สามารถเข้าถึงได้ผ่านคอมโพเนนต์ TIdThreadMgrPool
กระทู้เยอะมาก
เซิร์ฟเวอร์ที่มีการโหลดจำนวนมากอาจต้องใช้เธรดนับร้อยหรือหลายพันเธรด มีความเชื่อกันโดยทั่วไปว่าเธรดนับร้อยสามารถทำลายระบบของคุณได้ นี่เป็นความเชื่อที่ผิด
ในเซิร์ฟเวอร์ส่วนใหญ่ เธรดจะรอข้อมูล ขณะรอสายที่บล็อก เธรดจะไม่ทำงาน ในเซิร์ฟเวอร์ที่มี 500 เธรด สามารถใช้งานได้เพียง 50 เธรดในเวลาเดียวกัน
จำนวนเธรดที่ทำงานบนระบบของคุณอาจทำให้คุณประหลาดใจ ด้วยจำนวนเซิร์ฟเวอร์ที่ทำงานขั้นต่ำและระบุ แอปพลิเคชันที่ทำงานอยู่ระบบของฉันสร้าง 333 เธรด แม้ว่าจะมี 333 เธรด แต่ CPU ก็โหลดเพียง 1% เท่านั้น บรรทุกหนักมาก เซิร์ฟเวอร์ไอไอเอส(Microsoft Internet Information Server) สามารถสร้างเธรดได้นับร้อยนับพันเธรด
หัวข้อและส่วนทั่วโลก
เมื่อใช้หลายเธรด คุณต้องมั่นใจในความสมบูรณ์ของข้อมูลเมื่อเข้าถึง นี่อาจเป็นเรื่องยากสำหรับโปรแกรมเมอร์ที่ไม่ได้ทำงานกับเธรด แต่โดยทั่วไปแล้ว เซิร์ฟเวอร์ส่วนใหญ่ไม่จำเป็นต้องใช้ข้อมูลทั่วโลก เซิร์ฟเวอร์ส่วนใหญ่ทำหน้าที่แยกกัน แต่ละเธรดดำเนินงานแยกของตัวเอง ส่วนการอ่าน/เขียนส่วนกลางเป็นคุณลักษณะหนึ่งของแอปพลิเคชันแบบมัลติเธรดจำนวนมาก แต่ไม่ใช่เรื่องปกติสำหรับเซิร์ฟเวอร์
ระเบียบวิธีอินดี้
Indy แตกต่างจากส่วนประกอบ Winsock อื่นๆ ที่คุณคุ้นเคย หากคุณได้ทำงานร่วมกับส่วนประกอบอื่นแล้ว ทางออกที่ดีที่สุดจะลืมไปว่ามันทำงานอย่างไร ส่วนประกอบอื่นๆ จำนวนมากใช้การโทรแบบไม่บล็อก (อะซิงโครนัส) และทำงานแบบอะซิงโครนัส พวกเขาจำเป็นต้องตอบสนองต่อเหตุการณ์ สร้างเครื่องสถานะ และดำเนินการวนรอบการรอบ่อยครั้ง
ตัวอย่างเช่น สำหรับส่วนประกอบอื่นๆ เมื่อคุณเรียกใช้การเชื่อมต่อ คุณต้องรอให้เหตุการณ์การเชื่อมต่อเกิดขึ้น หรือรอในลักษณะวนซ้ำเพื่อให้คุณสมบัติระบุว่ามีการเชื่อมต่อเกิดขึ้น ด้วย Indy คุณสามารถเรียกใช้วิธี Connect และรอให้มันกลับมา จะมีการคืนเงินหากการเชื่อมต่อสำเร็จหรือมีข้อยกเว้นหากเกิดปัญหา ดังนั้นการทำงานกับ Indy จึงคล้ายกับการทำงานกับไฟล์มาก Indy ช่วยให้คุณสามารถใส่โค้ดทั้งหมดของคุณไว้ในที่เดียว แทนที่จะกระจายโค้ดไปยังกิจกรรมต่างๆ นอกจากนี้ Indy ยังง่ายและสะดวกที่สุดเมื่อทำงานกับเธรด
อินดี้ต่างกันยังไง?
ภาพรวมโดยย่อ ·ใช้การบล็อกการโทร ·ไม่เน้นเหตุการณ์ - มีเหตุการณ์ต่างๆ แต่ใช้สำหรับความต้องการด้านข้อมูลและไม่จำเป็นจริงๆ · ออกแบบมาสำหรับเธรด - Indy ได้รับการออกแบบมาสำหรับเธรด แต่สามารถใช้ได้โดยไม่มีเธรด การเขียนโปรแกรมตามลำดับ
รีวิวแบบละเอียด
Indy ไม่เพียงแต่ใช้การบล็อคการโทร (ซิงโครนัส) แต่ยังทำงานในลักษณะนี้อีกด้วย เซสชันอินดี้ทั่วไปมีลักษณะดังนี้:
ด้วย IndyClient จะเริ่มต้น
เชื่อมต่อ; พยายาม
//ทำธุระที่นี่.
ในที่สุดก็ตัดการเชื่อมต่อ; จบ;
จบ;
ด้วยส่วนประกอบอื่น ๆ มีลักษณะดังนี้:
ขั้นตอน TFormMain.TestOnClick (ผู้ส่ง: TComponent);
เริ่ม
ด้วย SocketComponent จะเริ่มต้น
เชื่อมต่อ; พยายาม
ในขณะที่ไม่ได้เชื่อมต่อให้เริ่มต้น
ถ้า IsError ให้เริ่มต้น
ยกเลิก;
จบ;

OutData:= "ข้อมูลที่จะส่ง";
ในขณะที่ length(OutData) > 0 จะเริ่มต้น
แอปพลิเคชัน กระบวนการข้อความ;
จบ;
ในที่สุดก็ตัดการเชื่อมต่อ; จบ;
จบ;
จบ;
ขั้นตอน TFormMain.OnConnectError;
เริ่ม
IsError:= จริง;
จบ;
ขั้นตอน TFormMain.OnRead;
var
ฉัน: จำนวนเต็ม;
เริ่ม
i:= SocketComponent.Send (OutData);
OutData:= คัดลอก (OutData, i + 1, MaxInt);
จบ;
ส่วนประกอบจำนวนมากทำงานได้ไม่ดีนักในการแยกโปรแกรมเมอร์ออกจากสแต็ก คอมโพเนนต์จำนวนมาก แทนที่จะแยกผู้ใช้ออกจากความซับซ้อนของสแต็ก เพียงแค่ปล่อยผู้ใช้ไว้กับองค์ประกอบนั้นหรือจัดเตรียมเสื้อคลุมไว้เหนือสแต็ก
อินดี้แบบพิเศษ
Indy ได้รับการออกแบบตั้งแต่พื้นฐานจนถึงแบบมัลติเธรด การสร้างเซิร์ฟเวอร์และไคลเอนต์ใน Indy นั้นคล้ายคลึงกับการสร้างเซิร์ฟเวอร์และไคลเอนต์ใน Unix โดยทั่วไปแอปพลิเคชัน Unix จะเรียกสแต็กโดยตรงโดยมีเลเยอร์นามธรรมเพียงเล็กน้อยหรือไม่มีเลย
โดยทั่วไปแล้ว เซิร์ฟเวอร์ Unix มีกระบวนการรับฟังตั้งแต่หนึ่งกระบวนการขึ้นไปที่ตรวจสอบคำขอของไคลเอ็นต์ขาเข้า สำหรับลูกค้าแต่ละรายที่ต้องให้บริการ ก กระบวนการใหม่- ทำให้การเขียนโปรแกรมเป็นเรื่องง่าย แต่ละกระบวนการสำหรับไคลเอนต์เพียงรายเดียวเท่านั้น แต่ละกระบวนการทำงานในบริบทด้านความปลอดภัยของตัวเอง ซึ่งกำหนดโดยกระบวนการรับฟังหรือกระบวนการตามสิทธิ์ ตัวตน หรือสิ่งอื่นๆ ที่มีอยู่
เซิร์ฟเวอร์ Indy ทำงานในลักษณะเดียวกันมาก Windows ต่างจาก Unix คือไม่สามารถคูณกระบวนการได้ดี แต่ทำงานได้ดีกับเธรด เซิร์ฟเวอร์ Indy สร้างเธรดแยกต่างหากสำหรับการเชื่อมต่อไคลเอนต์แต่ละรายการ
เซิร์ฟเวอร์ Indy กำหนดเธรดการฟังที่แยกจากเธรดโค้ดหลักของโปรแกรม เธรดการรอฟังคำขอที่เข้ามาจากไคลเอ็นต์ สำหรับไคลเอนต์แต่ละรายที่ตอบกลับ เธรดใหม่จะถูกสร้างขึ้นเพื่อรองรับไคลเอนต์ เหตุการณ์ที่เกี่ยวข้องจะถูกให้บริการในบริบท ของกระแสนี้.
รีวิวลูกค้าอินดี้
อินดี้ได้รับการออกแบบมาเพื่อให้มีความเป็นนามธรรมในระดับที่สูงมาก ความซับซ้อนและรายละเอียดของสแต็ก TCP/IP จะถูกซ่อนจากโปรแกรมเมอร์ โดยทั่วไปแล้ว เซสชันไคลเอนต์ทั่วไปใน Indy จะมีลักษณะดังนี้:
ด้วย IndyClient จะเริ่มต้น
โฮสต์:= "zip.pbe.com"; // โฮสต์ที่จะโทร
พอร์ต:= 6000; // พอร์ตสำหรับเรียกเซิร์ฟเวอร์
เชื่อมต่อ; พยายาม
//ทำธุระที่นี่.
ในที่สุดก็ตัดการเชื่อมต่อ; จบ;
จบ;
ภาพรวมเซิร์ฟเวอร์อินดี้
ส่วนประกอบเซิร์ฟเวอร์ Indy สร้างเธรดการฟังที่แยกจากเธรดโค้ดโปรแกรมหลัก เธรดการรอฟังคำขอที่เข้ามาจากไคลเอ็นต์ สำหรับไคลเอนต์แต่ละรายที่ตอบกลับ เธรดใหม่จะถูกสร้างขึ้นเพื่อรองรับไคลเอนต์ เหตุการณ์ที่เกี่ยวข้องจะได้รับการบริการในบริบทของเธรดนั้น

ตัวอย่างการปฏิบัติ
ตัวอย่างต่อไปนี้จะช่วยให้คุณเริ่มต้นใช้งานส่วนประกอบต่างๆ ได้ ง่ายต่อการใช้แต่เพื่อที่จะสาธิตตัวอย่างที่ทำเป็น แอปพลิเคชั่นที่เรียบง่าย- บางโครงการจัดทำขึ้นเพื่อแสดงสถานการณ์ที่แตกต่างกัน ตัวอย่างเหล่านี้พร้อมให้ดาวน์โหลดเป็นไฟล์ zip ด้วยเช่นกัน
หมายเหตุจากนักแปล: ลิงก์บนเว็บไซต์ใช้งานไม่ได้
ตัวอย่างที่ 1 - การยืนยันรหัสไปรษณีย์
โครงการแรกทำง่ายที่สุด ค้นหาด้วยรหัสไปรษณีย์ ลูกค้าจะถามเซิร์ฟเวอร์ว่าเมืองใดและระบุรหัสไปรษณีย์ที่ระบุ
สำหรับผู้ที่อาศัยอยู่นอกสหรัฐอเมริกาและไม่ทราบว่ารหัสไปรษณีย์คืออะไร เป็นรหัสไปรษณีย์ที่ระบุสถานที่จัดส่ง รหัสไปรษณีย์ประกอบด้วยตัวเลข 5 หลัก
มาตรการ
ขั้นตอนแรกในการสร้างเซิร์ฟเวอร์และไคลเอนต์คือการพัฒนาโปรโตคอล สำหรับโปรโตคอลมาตรฐาน สิ่งนี้ถูกกำหนดโดย RFC ที่เกี่ยวข้อง สำหรับรหัสไปรษณีย์ มีการกำหนดโปรโตคอลไว้ด้านล่าง
โปรโตคอลการสื่อสารส่วนใหญ่ทำงานใน โหมดข้อความ- การแลกเปลี่ยนหมายความว่าคำสั่งถูกส่งและตอบสนองต่อสถานะและข้อมูลที่เป็นไปได้ โปรโตคอลไม่ได้จำกัดอยู่เพียงการแลกเปลี่ยน แต่ยังคงใช้ข้อความธรรมดา โปรโตคอลในการกำหนดรหัสไปรษณีย์ก็เป็นแบบข้อความเช่นกัน ข้อความธรรมดาทำให้โปรโตคอลง่ายต่อการดีบัก และช่วยให้ภาษาการเขียนโปรแกรมและระบบปฏิบัติการต่างๆ สามารถสื่อสารได้
หลังจากเชื่อมต่อแล้ว เซิร์ฟเวอร์จะส่งข้อความสวัสดี จากนั้นจึงยอมรับคำสั่ง คำสั่งนี้อาจเป็น "ZipCode x" (โดยที่ x คือรหัสไปรษณีย์) หรือ "Quit" ในการตอบสนองต่อคำสั่ง ZipCode การตอบกลับจะถูกส่งในรูปแบบบรรทัดเดียวพร้อมคำตอบหรือ บรรทัดว่างหากไม่พบรหัส คำสั่ง Quit ทำให้เซิร์ฟเวอร์ปิดการเชื่อมต่อ เซิร์ฟเวอร์อาจยอมรับคำสั่งหลายคำสั่งก่อนที่จะส่งคำสั่ง Quit
ซอร์สโค้ดเซิร์ฟเวอร์

หน่วย ServerMain;

อินเตอร์เฟซ

การใช้งาน

พิมพ์

TformMain = คลาส (TForm)

IdTCPServer1: TIdTCPServer;

ขั้นตอน FormCreate (ผู้ส่ง: TObject ) ;

ขั้นตอน FormDestroy (ผู้ส่ง: TObject ) ;

ขั้นตอน IdTCPServer1Connect (AThread: TIdPeerThread);

ส่วนตัว

ZipCodeList: TStrings;

สาธารณะ

จบ ;

FormMain: TformMain;

การดำเนินการ

(R*.DFM)

ขั้นตอน TformMain.IdTCPServer1Connect (AThread: TIdPeerThread);

เริ่ม

AThread.Connection .WriteLn ( "เซิร์ฟเวอร์รหัสไปรษณีย์อินดี้พร้อมแล้ว" );

จบ ;

คำสั่ง S: สตริง ;

เริ่ม

SCommand:= ReadLn ;

จบ ;

จบ ;

จบ ;

ขั้นตอน TformMain.FormCreate (ผู้ส่ง: TObject ) ;

เริ่ม

ZipCodeList:= TStringList.Create ;

ZipCodeList.LoadFromFile(ExtractFilePath(Application.EXEName) + "ZipCodes.dat");

จบ ;

ขั้นตอน TformMain.FormDestroy (ผู้ส่ง: TObject ) ;

เริ่ม

ZipCodeList.Free ;

จบ ;

จบ.

ส่วนเดียวในโปรเจ็กต์ที่เฉพาะเจาะจงของ Indy คือคอมโพเนนต์ IdTCPServer1, วิธี IdTCPServer1Connect และ IdTCPServer1Execute
แบบฟอร์มประกอบด้วยส่วนประกอบ IdTCPServer1 ประเภท TIdTCPServer คุณสมบัติต่อไปนี้มีการเปลี่ยนแปลง: ·Active = True - หลังจากแอปพลิเคชันเริ่มทำงาน เซิร์ฟเวอร์จะรับฟัง ·DefaultPort = 6000 - ค่าพอร์ตสำหรับโปรเจ็กต์นี้ เซิร์ฟเวอร์รับฟังคำขอของไคลเอ็นต์บนพอร์ตนี้
วิธีการ IdTCPServer1Execute เชื่อมโยงกับเหตุการณ์ OnExecute ของเซิร์ฟเวอร์ เหตุการณ์ OnExecute เกิดขึ้นหลังจากยอมรับการเชื่อมต่อไคลเอ็นต์แล้ว เหตุการณ์ OnExecute แตกต่างจากเหตุการณ์อื่นๆ ที่คุณรู้จัก OnExecute ทำงานในบริบทของเธรด เหตุการณ์เธรดถูกยกขึ้นและได้รับอาร์กิวเมนต์ AThread ที่ส่งผ่านไปยังเมธอด นี่เป็นสิ่งสำคัญเนื่องจากสามารถดำเนินการเหตุการณ์ OnExecute หลายเหตุการณ์พร้อมกันได้ ทำเช่นนี้เพื่อให้เซิร์ฟเวอร์สามารถทำงานได้โดยไม่ต้องสร้างส่วนประกอบใหม่ นอกจากนี้ยังมีวิธีการที่สามารถแทนที่ได้เมื่อสร้างทายาท
เหตุการณ์ OnConnect เริ่มทำงานหลังจากยอมรับการเชื่อมต่อและสร้างเธรดแล้ว ในเซิร์ฟเวอร์นี้ ใช้เพื่อส่งข้อความต้อนรับไปยังไคลเอนต์ หากต้องการ ก็สามารถทำได้ในเหตุการณ์ OnExecute
เหตุการณ์ OnExecute สามารถดำเนินการได้หลายครั้งจนกว่าการเชื่อมต่อจะถูกตัดการเชื่อมต่อหรือสูญหาย ซึ่งช่วยลดความจำเป็นในการตรวจสอบการเชื่อมต่อว่าขาดการเชื่อมต่อหรือสูญเสียในลูปภายในเหตุการณ์หรือไม่
IdTCPServer1Execute ใช้ฟังก์ชันพื้นฐานสองฟังก์ชัน ได้แก่ ReadLn และ WriteLn ReadLn อ่านสตริงจากการเชื่อมต่อ และ WriteLn ส่งสตริงไปยังการเชื่อมต่อ
sCommand:= ReadLn;
โค้ดด้านบนรับสตริงจากไคลเอ็นต์และวางลงในตัวแปรสตริง sCommand ในเครื่อง

ถ้า SameText (sCommand, "QUIT" ) ให้เริ่มต้น

สิ้นสุดอย่างอื่นถ้า SameText (Copy (sCommand, 1 , 8 ) , "ZipCode " ) จากนั้นเริ่มต้น

WriteLn(ZipCodeList.Values[คัดลอก(sCommand, 9, MaxInt)]);

จบ ;


ถัดไป sCommand จะถูกตรวจสอบเพื่อหาคำสั่งที่ถูกต้อง
หากคำสั่งคือ "Quit" แสดงว่าการตัดการเชื่อมต่อจะดำเนินการ ไม่อนุญาตให้อ่านหรือเขียนหลังจากขาดการเชื่อมต่อ หลังจากกิจกรรมสิ้นสุดลง เธรดที่กำลังฟังจะไม่เรียกอีกต่อไป แต่จะล้างเธรดและยุติการเชื่อมต่อ
หากคำสั่งคือ "ZipCode" พารามิเตอร์หลังจากแตกคำสั่งและตารางจะถูกสแกนหาเมืองและรัฐ เมืองและรัฐจะถูกส่งต่อไปยังไคลเอนต์ หรือส่งสตริงว่างหากไม่มีค่าที่ตรงกัน
ต่อไปจะออกจากวิธีการนี้ เซิร์ฟเวอร์จะเพิ่มเหตุการณ์อีกครั้งทันทีที่มีคำสั่งใหม่มาถึง ทำให้ไคลเอนต์สามารถส่งคำสั่งหลายคำสั่งได้
ซอร์สโค้ดไคลเอ็นต์

หน่วย ClientMain;

อินเตอร์เฟซ

การใช้งาน

Windows, ข้อความ, SysUtils, คลาส, กราฟิก, การควบคุม, แบบฟอร์ม, กล่องโต้ตอบ,

StdCtrls, ExtCtrls, IdAntiFreezeBase,

IdAntiFreeze, IdBaseComponent, IdComponent, IdTCPConnection, IdTCPClient;

พิมพ์

TformMain = คลาส (TForm)

ลูกค้า: TIdTCPClient;

IdAntiFreeze1: TIdAntiFreeze;

แผง 1: TPanel;

แผง2: TPanel;

บันทึกอินพุต: TMemo;

ผลลัพธ์ Lbox: TListBox;

แผง 3: TPanel;

Button1: T ปุ่ม;

Button2: T ปุ่ม;

Label1: TLabel;

ขั้นตอน Button2Click (ผู้ส่ง: TObject ) ;

ขั้นตอน Button1Click (ผู้ส่ง: TObject ) ;

ส่วนตัว

สาธารณะ

จบ ;

FormMain: TformMain;

การดำเนินการ

(R*.DFM)

ขั้นตอน TformMain.Button2Click (ผู้ส่ง: TObject ) ;

เริ่ม

MemoInput.เคลียร์ ;

LboxResults.เคลียร์ ;

จบ ;

ขั้นตอน TformMain.Button1Click (ผู้ส่ง: TObject ) ;

ฉัน: จำนวนเต็ม ;

ส: สตริง ;

เริ่ม

ButnLookup.Enabled := จริง ; พยายาม

LboxResults.เคลียร์ ;

กับลูกค้าจะเริ่มต้น

เชื่อมต่อ; พยายาม

LboxResults.Items.Add(ReadLn);

สำหรับ i:= 0 ถึง memoInput.Lines .Count - 1 จะเริ่มต้น

WriteLn("รหัสไปรษณีย์" + memoInput.Lines[i]);

LboxResults.Items.Add(memoInput.Lines[i]);

ส:= ReadLn ;

ถ้า s = "" ให้เริ่มเลย

ส:= "-- ไม่พบรายการสำหรับรหัสไปรษณีย์นี้";

จบ ;

LboxResults.Items.Add(s);

LboxResults.Items.Add("");

จบ ;

WriteLn("ออก");

ในที่สุดก็ตัดการเชื่อมต่อ; จบ ;

จบ ;

ในที่สุด butnLookup.Enabled := true ; จบ ;

จบ ;

จบ.


ส่วนเฉพาะสำหรับคอมโพเนนต์ไคลเอนต์คือเมธอด Button1Click
ส่วนประกอบไคลเอ็นต์เป็นประเภท TIdTCPClient และวางไว้บนแบบฟอร์ม คุณสมบัติต่อไปนี้มีการเปลี่ยนแปลง: ·Host = 127.0.0.1 - เซิร์ฟเวอร์อยู่บนเครื่องเดียวกันกับไคลเอนต์ ·พอร์ต = 6000 - พอร์ตเซิร์ฟเวอร์
เมธอด Button1Click เชื่อมโยงกับเหตุการณ์ OnClick ของคอมโพเนนต์ Button1 เมื่อคลิกปุ่ม จะเรียกวิธีนี้ ส่วน Indy ของวิธีนี้สามารถลดได้ดังนี้ 1.เชื่อมต่อกับเซิร์ฟเวอร์ (Connect;) 1.อ่านคำทักทายจากเซิร์ฟเวอร์ 1. สำหรับแต่ละบรรทัดที่ผู้ใช้ป้อนใน TMemo: 1. การส่งคำขอไปยังเซิร์ฟเวอร์ (WriteLn("ZipCode " + memoInput.Lines[i]);) 1. การอ่านการตอบกลับจากเซิร์ฟเวอร์ (s:= ReadLn; ) 1. การส่งคำสั่ง Quit (WriteLn("Quit");) 1.Disconnect (Disconnect;)
การทดสอบ
ตัวอย่างนี้ได้รับการทดสอบและใช้งานได้กับ TCP/IP ที่ติดตั้งไว้ คุณสามารถเปลี่ยนให้ทำงานผ่านเครือข่ายจากคอมพิวเตอร์เครื่องหนึ่งไปยังอีกเครื่องหนึ่งได้ โดยการเริ่มต้นเซิร์ฟเวอร์บนคอมพิวเตอร์เครื่องอื่นและเปลี่ยนชื่อหรือ IP ของเซิร์ฟเวอร์บนไคลเอนต์
เพื่อทดสอบโปรเจ็กต์ ให้คอมไพล์และรันเซิร์ฟเวอร์ จากนั้นคอมไพล์และรันไคลเอนต์ ป้อนรหัสไปรษณีย์ของคุณในช่องบันทึกและกดปุ่มค้นหา
การดีบัก
โปรโตคอลข้อความนั้นแก้ไขได้ง่ายมากเพราะสามารถทดสอบได้โดยใช้ Telnet เมื่อต้องการทำเช่นนี้ ก็เพียงพอที่จะทราบพอร์ตเซิร์ฟเวอร์แล้ว เซิร์ฟเวอร์การค้นหารหัสไปรษณีย์ฟังบนพอร์ต 6000
เริ่มเซิร์ฟเวอร์การค้นหารหัสไปรษณีย์อีกครั้ง จากนั้นเปิดคอนโซล (เช่น หน้าต่าง Dos) ตอนนี้ป้อน:
เทลเน็ต 127.0.0.1 6000
ขณะนี้คุณเชื่อมต่อกับเซิร์ฟเวอร์แล้ว เซิร์ฟเวอร์บางแห่งยังส่งข้อความต้อนรับด้วย บางคนทำไม่ได้ คุณจะไม่เห็นบรรทัดที่คุณป้อน เซิร์ฟเวอร์ส่วนใหญ่ไม่สะท้อนเพื่อประหยัดการรับส่งข้อมูล อย่างไรก็ตาม คุณสามารถเปลี่ยนการตั้งค่าเทลเน็ตได้โดยตั้งค่าตัวเลือก "Echo On" ซึ่งทำได้แตกต่างออกไปในไคลเอ็นต์ telnet ที่แตกต่างกัน และบางไคลเอ็นต์ไม่มีคุณลักษณะนี้เลย ตอนนี้ป้อน:
รหัสไปรษณีย์ 37642
คุณจะเห็นการตอบกลับของเซิร์ฟเวอร์:
เชิร์ชฮิลล์, เทนเนสซี
หากต้องการยกเลิกการเชื่อมต่อจากเซิร์ฟเวอร์ ให้ป้อน:
ล้มเลิก
ตัวอย่างที่ 2 - การเข้าถึงฐานข้อมูล
ตัวอย่างนี้จำลองเซิร์ฟเวอร์ที่ต้องดำเนินการบล็อกงานอื่นนอกเหนือจากการเรียกซ็อกเก็ต เซิร์ฟเวอร์จำนวนมากถูกบังคับให้ทำงานในสภาวะดังกล่าว เซิร์ฟเวอร์ที่ต้องการเข้าถึงฐานข้อมูล การเรียกใช้ขั้นตอนภายนอก หรือการคำนวณ มักจะไม่สามารถขัดจังหวะการโทรเหล่านี้ได้ เนื่องจากเป็นการเรียกภายนอกหรือเนื่องจากความซับซ้อนของสิ่งนี้ การเข้าถึงฐานข้อมูลไม่สามารถแบ่งออกเป็นส่วนเล็กๆ ได้ และผู้พัฒนาต้องรอให้การดำเนินการกับฐานข้อมูลสิ้นสุดลง นี่เป็นคุณสมบัติที่ไม่เพียงแต่การเรียกฐานข้อมูลเท่านั้น แต่ยังรวมไปถึงการดำเนินการอื่นๆ เช่น การบีบอัด การคำนวณ และการประมวลผลอื่นๆ ที่เป็นประเภทเดียวกัน
เพื่อวัตถุประสงค์ในการสาธิต สมมติว่าเซิร์ฟเวอร์ทำการเรียกฐานข้อมูลที่ใช้เวลา 5 วินาทีจึงจะเสร็จสิ้น เพื่อให้ง่ายขึ้น เรามาหยุดชั่วคราวโดยใช้ฟังก์ชัน Sleep(5000) แทนการโทรจริงๆ
ตัวอย่างนี้ยังต้องการรายละเอียดน้อยกว่าตัวอย่างก่อนหน้านี้ เนื่องจากแนวคิดหลายประการยังไม่เป็นที่เข้าใจ
แหล่งที่มา

หน่วยหลัก;

อินเตอร์เฟซ

การใช้งาน

Windows, ข้อความ, SysUtils, คลาส, กราฟิก, การควบคุม, แบบฟอร์ม, กล่องโต้ตอบ,

IdBaseComponent, IdComponent, IdTCPServer;

พิมพ์

TformMain = คลาส (TForm)

IdTCPServer1: TIdTCPServer;

ขั้นตอน IdTCPServer1Execute (AThread: TIdPeerThread);

ส่วนตัว

สาธารณะ

จบ ;

FormMain: TformMain;

การดำเนินการ

(R*.DFM)

ขั้นตอน TformMain.IdTCPServer1Execute (AThread: TIdPeerThread);

ฉัน: จำนวนเต็ม ;

เริ่ม

ด้วย AThread.Connection จะเริ่มต้นขึ้น

WriteLn("สวัสดี เซิร์ฟเวอร์ DB พร้อมแล้ว");

ฉัน:= StrToIntDef(ReadLn, 0);

// Sleep ถูกแทนที่ด้วย DB แบบยาวหรือการโทรอื่น

นอนหลับ(5,000);

WriteLn(IntToStr(i * 7));

จบ ;

จบ ;

จบ.

เนื่องจากเหตุการณ์ Execute เกิดขึ้นในบริบทของเธรด รหัสการประมวลผลจึงสามารถมีความยาวเท่าใดก็ได้ ไคลเอนต์แต่ละรายมีเธรดของตัวเองและไม่ปิดกั้นไคลเอนต์อื่น
การทดสอบ
หากต้องการทดสอบเซิร์ฟเวอร์ DB ให้คอมไพล์และรัน เชื่อมต่อโดยใช้ Telnet กับพอร์ต 6001 เซิร์ฟเวอร์จะตอบกลับด้วยข้อความต้อนรับ ใส่หมายเลข เซิร์ฟเวอร์จะ "ประมวลผล" คำขอของคุณและตอบกลับภายใน 5 วินาที

โปรโตคอล UDP ค่อนข้างดีสำหรับการส่งข้อความนั่นคือคุณสามารถจัดระเบียบการแชทในพื้นที่และสิ่งที่คล้ายกันได้ ฉันตัดสินใจยกตัวอย่างงานที่ง่ายที่สุดกับ UDP ใน Delphi

คำแนะนำทีละขั้นตอน:

ผมยกตัวอย่างแต่ขออภัยที่ผมเขียนไม่ครบทุกบรรทัดเพราะ... ฉันไม่เห็นอะไรซับซ้อนและใครๆ ก็สามารถเข้าใจได้

ที่จริงแล้วหากมีอะไรไม่ชัดเจนคุณสามารถถามคำถามฉันได้ และนี่คือรหัสจริง:

การใช้งาน
Windows, ข้อความ, SysUtils, ตัวแปร, คลาส, กราฟิก, การควบคุม, แบบฟอร์ม,
กล่องโต้ตอบ, StdCtrls, IdUDPServer, IdBaseComponent, IdComponent, IdUDPBase,
IdUDPClient, IdSocketHandle;

พิมพ์
TForm1 = คลาส (TForm)
IdUDPClient1: TIdUDPClient;
IdUDPServer1: TIdUDPServer;
Button1: T ปุ่ม;
Label1: TLabel;
ขั้นตอน FormCreate (ผู้ส่ง: TObject);
ขั้นตอน FormClose (ผู้ส่ง: TObject; var Action: TCloseAction);
ขั้นตอน Button1Click (ผู้ส่ง: TObject);
ขั้นตอน IdUDPServer1UDPRead (AThread: TIdUDPListenerThread; AData: TBytes;
การเชื่อมโยง: TIdSocketHandle);
ส่วนตัว
(ประกาศส่วนตัว)
สาธารณะ
(ประกาศสาธารณะ)
จบ;

var
แบบฟอร์ม 1: TForm1;

($R *.dfm)
[b]//ขั้นตอนการส่งข้อความ
ขั้นตอน TForm1.Button1Click (ผู้ส่ง: TObject);
เริ่ม
พยายาม
IdUDPClient1.Active:= จริง;
IdUDPClient1.Host:= "localhost";
IdUDPClient1.เชื่อมต่อ;
ถ้า IdUDPClient1.Connected แล้ว
เริ่ม
IdUDPClient1.Send (TimeToStr (เวลา));
Label1.Caption:= "ตกลง";
จบ;
IdUDPClient1.Active:= เท็จ;
บี๊บบี๊บบี๊บ;
ยกเว้น
MessageDlg("มีบางอย่างผิดพลาด =(", mtError, , 0);
จบ;
จบ;
[ข]
//เปิดปิด. เซิร์ฟเวอร์ UDP เมื่อเริ่มและปิดแบบฟอร์ม
ขั้นตอน TForm1.FormClose (ผู้ส่ง: TObject; var Action: TCloseAction);
เริ่ม
IdUDPServer1.Active:= เท็จ;
จบ;

ขั้นตอน TForm1.FormCreate (ผู้ส่ง: TObject);
เริ่ม
IdUDPServer1.Active:= จริง;
จบ;

[b]//ขั้นตอนการตอบสนองของเซิร์ฟเวอร์เมื่อรับข้อมูล
ขั้นตอน TForm1.IdUDPServer1UDPRead (ATThread: TIdUDPListenerThread;
ข้อมูล: TBytes; การเชื่อมโยง: TIdSocketHandle);
วาร์
ฉัน:จำนวนเต็ม;
s:สตริง;
เริ่ม
ส:= "";
พยายาม
ฉัน:= 0;
ในขณะที่ (AData[i] 0) ทำ
เริ่ม
s:= s + chr(AData[i]);
ฉัน:= ฉัน + 1;
จบ;
ในที่สุด
Label1.Caption:= s;
จบ;
จบ;