1
بسم االله الرحمان الرحيم الفھرس: مقدمة. برمجة سكریبت الخادم. برمجة سكریبت الزبون. تطبیق البرنامج في شبكة محلیة استعمال تقنیة threading - - - - - 2
-1 المقدمة : لابد انك في یوم احتجت لربط بین برامجك وربما استعملت ملف خارجي لعمل اتصال مثلا ملف نصي او ملف قواعد بیانات خارجي لاستقبال نص اخر من برنامج اخر لكن ھل فكرت في طریقة اخرى نعم توجد طریقة اخرى وھي باستخدامsocket لكن ما معنى socket ھي التقنیة والوسیلة الفعالة التي تمكننا من عمل شبكة بین تطبیقات سواء شبكة محلیة او على الانترنت وھي تستعمل كثیرا في الالعاب ligner) jeux )و en كل ما ھو متعلق بالربط بین تطبیقات برمجة socketمتوفرة في الكثیر من لغات البرمجة سي جافا... 3
فكما تعلم تعتبر لغة البایثون من اقوى اللغات في التعامل مع الشبكات وبرمجتھا بحیث انھا توفر العدید من المكتبات التي المتخصصة في ذالك من ھاتھ المكتبات مكتبة socket سنتمكن من خلالھا من كتابة برامج تستطیع الا تصال عبر الشبكة "low socket programming". ارید ان اوضح في البدایة برامترین مھمین في socket address_family: AF_INET :العناوین الخاصة ببرتوكول IP الا صدارة الرابعة IP : AF_INET6 العناوین الخاصة ببرتوكول الا صدارة.السادسة. AF_UNIX : ھذه العناوین خاصة با نظمة لینكس 4
protocol: البرتوكول الذي سیتم أستخدامھ في الا تصال : SOCK_STREAM برتوكول TCPھذا الذي سنعمل بھ UDP SOCK_DGRAM :برتوكول توجد فرق بینھم لكن لا یمكن الخوض فیھم لكي لا نخرج من موضعنا 5
المھم و مھما اختلفت اللغات و تعقدت یبقى المبدأ واحد كما سیوضحھ المخطط الا تي 6
2- برمجة سكریبت الخادم : ملاحظات: -قمت باستخدام البرمجة الموجھة (كلاس میتود = طریقة) لكن یمكن استخدام برمجة الا جراي یة في برمجتھ المھم ھو فھم المبدأ. -استعملت في السكریبت 127.0.0.1 : ip ھو للجھاز المحلي یعني لجھازك الخاص و ھو اي بي المرافق للعنوان التالي.localhost Python ھنا نقوم باستدعاء المكتبة// import socket نقوم بتعریف كلاس جدید// sof1ane_serveur(object): class ھنا المشید والبرامترات الخاصة// port=8080): def init (self, host='', ارجاع قیم الھوست و بورت// self._host, self._port=host, port self.address=(host, port) متغیر من نوع قاي مة وارجاع قیم الھوست وبورت فیھ // self.sock=socket.socket(socket.af_inet, socket.sock_stream) ھا نقوم بتحدید كل من// socket types et address (and protocol) families self.sock.setsockopt(socket.sol_socket, socket.so_reuseaddr, 1) ھنا یجب تفعیل SO_REUSEADDR لیتم غلق البورت بعد غلق السیرفر// عدم استخدام ھذا المر یو دي الى حدوث خطا في تشغیل السكریبت مرة اخرى تحت عنوان البورت مشغول تعریف میتود جدید // demarrer(self): def 7
self.sock.bind(self.address) ربط العنوان الخاص بالخادم الذي یتم تنفیذ البرنامج علیھ // self.sock.listen(1) تجھیز الخادم لاستقبال الاتصالات منالشبكة مع تحدید عدد معین للاتصالات لاستقبالھا// print "Server s'executant sur: ", self._port self.gerer_con() نستدعي الطریقة تسییر الاتصال الذي سنتطرق الیھا // def handle_request(self): تعریف الطریقة تسییر الاتصال // while True: حلقة غیر منتھیة لانتظار الاتصال// clientsock, addr=self.sock.accept() لحضة قبول الا تصال نستقبل عنوان الا ي بي الخاص بالعمیل و مع توفیر منفذ محلي // ملاحظة للطریقة accept() اھمیة كبیرة نضرا لانھا ترجع لنا كاي ن العمیل مع عنوانھ print "Connexion à partir de: ", addr clientsock.sendall(str(addr)+" vous etes connecte au serveur...") ارسال رسالة نجاح الاتصال // while True: msg=clientsock.recv(100) تستخدم send et recv الطریقة مع الكاي ن الذي انشا تھ// accept() و 100 تمثل عدد الاحرف القصوى في كل رسالة ارسال رمز << // if msg: print ">> ", msg clientsock.sendall(msg) الذي یبین جاھزیة استقبال الرساي ل للعمیل 8
clientsock.close() if name ==" main ": try: serveur=sof1ane_serveur() serveur.start() except KeyboardInterrupt: exit() تنفیذ البرنامج الري یسي مع التعامل مع الاخطاء في حال حدوثھا // 3 -برمجة سكریبت : العمیل Python ھنا نقوم باستدعاء المكتبة// import socket نقوم بتعریف كلاس جدید//:( SimpleClient(object class def init (self, endpoint=('127.0.0.1', 8080)): ھنا المشید والبرامترات الخاصة// self._endpoint=endpoint ارجاع قیم الھوست و بورت// self.sock=socket.socket(socket.af_inet, socket.sock_stream) ھا نقوم بتحدید كل من// socket types et address (and protocol) families المشروحة في المقدمة في الموضوع الا ول self.sock.connect(self._endpoint) نقوم بعمل الاتصال مع السیرفر عن طرق المنھج //connect def start(self): while True: نقوم بفتح حلقة اتصال مع السیرفر // data=self.sock.recv(8096) ارسال و استقبال البیانات// if not data: break print data msg=raw_input("> ") if not msg: 9
break self.sock.send(msg) غلق الاتصال // self.sock.close() if name ==" main ": تنفیذ البرنامج الري یسي مع التعامل مع الاخطاء في حال حدوثھا // try: sc=simpleclient() sc.start() except KeyboardInterrupt: exit() 4 -تطبیق البرنامج في شبكة محلیة : ھنا لا نحتاج سوى تحدید عنوان اي بي والبورت الصور 10
5 -استعمال تقنیة :Threading 5.1- برمجة سكریبت الخادم : نلاحظ حین القیام بفتح حلقة اتصال مع السیرفر یكون البرنامج في حالة انتظار لایمكن لا ارسال لھ ولا عمل أي عمل اخر بحیث یقوم المعالج بفتح الحلقة اتصال وبس. لتوضیح اكثر مثلا اذا طلبت من المستعمل كتابة اسمھ عن طریق inputیبقى السكریبت متوقف الى غایة ادخال اسمھ لا یمكنھ عمل اي عملیة اخرى وھذا یعد عیب في البرنامج. سنحاول في تطبیقنا باستعمال تقنیة threadلكي ینفذ كل عملیھ في (process) منفصل نخبر المعالج ان أي یمكن فتح أكثر من حلقة في نفس الوقت او مثلا فتح حلقة و في نفس الوقت اظھار نص مثلا. 11
1. import socket,threading 2. class sof1ane_serveur(object): 3. def init (self, host, port): 4. self._host, self._port=host, port 5. self.address=(host, port) 6. self.sock=socket.socket(socket.af_inet, socket.sock_stream) 7. self.sock.setsockopt(socket.sol_socket, socket.so_reuseaddr, 1) 8. def start(self): 9. self.sock.bind(self.address) 10. self.sock.listen(5) 11. print "Server s'executant sur: ", self._port 12. self.gerer_con() 13. def gerer_con(self): 14. try: 15. while True: 16. clientsock, addr=self.sock.accept() 17. print "Connexion? partir de: ", addr 18. clientsock.sendall(str(addr)+" vous etes connecte au serveur...") 19. self.th1 = threading.thread(target=self.thread1, args=[clientsock]) 20. self.th2 = threading.thread(target=self.thread2, args=[clientsock]) 21. self.th1.start() 22. self.th2.start() 23. except: 24. exit() 25. def thread1(self,clientsock): 26. try: 27. while True: 28. msg=clientsock.recv(2048) 29. if not msg: 30. break 31. print ">", msg 32. self.sock.close() 33. except: 34. exit() 35. def thread2(self,clientsock): 36. try: 37. while True: 38. mesg = raw_input(">") 39. if not mesg: 40. break 41. clientsock.send('serveur dit :'+mesg) 42. self.sock.close() 43. except: 44. exit() 45. if name ==" main ": 46. try: 47. serveur=sof1ane_serveur('',23456) 48. serveur.start() 49. except: 50. exit() 5.2 12
برمجة سكریبت : الزبون -5.2 1. import socket,threading 2. class project(object): 3. def init (self,ip_port): 4. def recev(self): while 1: self.ip_port = ip_port self.sock = socket.socket(socket.af_inet,socket.sock_stream) self.sock.connect(self.ip_port) msg_rec = self.sock.recv(8096) if not msg_rec: break print msg_rec 5. self.sock.close() 6. def env(self): while 1: msg_env = raw_input("==>") if not msg_env: break self.sock.send(msg_env) self.sock.close() 7. if name ==" main ": 8. print("saisie l'adress IP et le port") 9. ip_port_saisie=input() 10. object_projet = project(ip_port_saisie) 11. thread1 = threading.thread(target=object_projet.env, args=[]) 12. thread2 = threading.thread(target=object_projet.recev, args=[]) 13. thread1.start() 14. thread2.start() 13
الصور لمعالجة اكثر من اربعة اتصالات بعض 14