عميل HTTP بلغة Go: إجراء الطلبات بشكل صحيح

مدرب بايثون أونلاين للمبتدئين

تعلم Python بسهولة دون إرهاق نظري. حل مهام عملية مع التحقق التلقائي واكتب الكود مباشرة في المتصفح.

ابدأ الدورة

مقدمة: لماذا يستحق عميل HTTP في Go الاهتمام

تطبيقات الويب الحديثة نادراً ما تعمل بمعزل عن الآخرين. تقريباً أي خدمة تتفاعل مع واجهات برمجة التطبيقات الخارجية أو الخدمات المصغرة أو الموارد الخارجية عبر HTTP. توفر لغة Go (Golang) مكتبة مدمجة وقوية net/http تتيح إنشاء عملاء HTTP فعالين وعاليي الأداء دون الحاجة إلى تبعيات خارجية.

في هذه المقالة، سنشرح كيفية العمل بشكل صحيح مع عميل HTTP في Go: من طلبات GET البسيطة إلى معالجة الأخطاء وإدارة المهلات الزمنية. ستتعلم كيفية تجنب الأخطاء الشائعة وكتابة كود موثوق.



أساسيات العمل مع عميل HTTP في Go

تم تصميم مكتبة net/http في Go مع مراعاة الأداء. على عكس العديد من اللغات الأخرى حيث ينشئ كل طلب اتصالاً جديداً، يستخدم Go مجموعة اتصالات (connection pool) افتراضياً. هذا يعني أن اتصالات TCP يُعاد استخدامها، مما يسرع العمل بشكل كبير.



أبسط طلب GET

لنبدأ بأبسط مثال — إرسال طلب GET باستخدام الدالة http.Get():



package main

import ( "fmt" "io" "net/http" "os")

func main() { // طلب GET بسيط resp, err := http.Get("https://api.github.com") if err != nil { fmt.Printf("خطأ أثناء تنفيذ الطلب: %v", err) os.Exit(1) } defer resp.Body.Close()

// قراءة نص الرد body, err := io.ReadAll(resp.Body) if err != nil { fmt.Printf("خطأ أثناء قراءة الرد: %v", err) os.Exit(1) }

fmt.Printf("الحالة: %s", resp.Status) fmt.Printf("نص الرد: %s", string(body))}


هام: أغلق دائماً نص الرد (resp.Body.Close()). استخدم defer للإغلاق المضمون، حتى في حالة حدوث خطأ.



طلب GET مع معاملات ورؤوس

للطلبات الأكثر تعقيداً، من الأفضل استخدام الصيغة الكاملة مع إنشاء كائن http.Request:



package main

import ( "fmt" "io" "net/http" "time")

func main() { // إنشاء عميل جديد client := &http.Client{ Timeout: 10 * time.Second, }

// إنشاء طلب req, err := http.NewRequest("GET", "https://api.example.com/users", nil) if err != nil { fmt.Printf("خطأ في إنشاء الطلب: %v", err) return }

// إضافة رؤوس req.Header.Set("Authorization", "Bearer your-token-here") req.Header.Set("Accept", "application/json") req.Header.Set("User-Agent", "Go-http-client/1.0")

// إضافة معاملات الاستعلام q := req.URL.Query() q.Add("limit", "10") q.Add("offset", "0") req.URL.RawQuery = q.Encode()

// تنفيذ الطلب resp, err := client.Do(req) if err != nil { fmt.Printf("خطأ في تنفيذ الطلب: %v", err) return } defer resp.Body.Close()

body, _ := io.ReadAll(resp.Body) fmt.Printf("الرد: %s", string(body))}


العمل مع طلبات POST و JSON

طلبات POST مع نص JSON هي مهمة قياسية عند العمل مع REST API. توفر Go أدوات مناسبة لتسلسل البيانات.



إرسال JSON باستخدام POST

package main

import ( "bytes" "encoding/json" "fmt" "net/http" "time")

type User struct { Name string `json:"name"` Email string `json:"email"` Age int `json:"age"`}

func main() { user := User{ Name: "إيفان بيتروف", Email: "ivan@example.com", Age: 30, }

// تسلسل الهيكل إلى JSON jsonData, err := json.Marshal(user) if err != nil { fmt.Printf("خطأ في تسلسل JSON: %v", err) return }

client := &http.Client{Timeout: 5 * time.Second}

المدونات

توصيات الكتب