شروع دوره معماری نرم افزار پنجشنبه 20 اذر شروع دوره معماری نرم افزار پنجشنبه 20 اذر
ثبت نام

برنامه نویسی CGI در پایتون (نوشتن برنامه های تولید محتوای پویا در سرویس دهنده بر اساس استاندارد های CGI با پایتون)

CGI چیست؟

Common Gateway Interface یک قسمتی از سرویس دهنده (web server) است که امکانی را فراهم می کند تا برنامه ای در سمت سرویس دهنده اجرا شود و خروجی آن از طریق صفحه ی اپلیکیشن تحت وب برای کاربری که به سرویس دهنده متصل شده به نمایش در آید. CGI در زمره ی اولین روش هایی است که برای تولید و ارائه ی محتوای پویا در صفحات وب بکار گرفته شد.

CGI یک متد استاندارد است که برای ایجاد محتوای پویا در صفحات وب و برنامه‌های کاربردی تحت وب استفاده می‌شود. CGI هنگامی که روی سرور یک وب‌سرور اجرا می‌شود، یک واسطه میان وب‌سرور و برنامه‌هایی که محتوای وب را ایجاد می‌کنند به وجود می‌آورد. این برنامه‌ها را CGI Script یا به‌طور خلاصه CGI می‌نامند که اغلب با زبان‌های اسکریپت نویسی نوشته می‌شوند، اما امکان نوشتن آن‌ها با زبان‌های برنامه‌نویسی نیز وجود دارد.

وبگردی

به منظور درک مفهوم CGI، یک لینک را درنظر بگیرید که کاربر با کلیک آن می خواهد صفحه ی وب یا آدرس اینترنتی را مشاهده کند.

  • • مرورگر به سرور HTTP متصل شده و درخواست URL، به طور مثال، filename را می دهد. سرویس دهنده ی وب URL را parse (تحلیل) کرده و به دنبال filename می گردد. پس از یافتن فایل، آن را به مرورگر ارسال می کند. در صورت عدم وجود فایل، یک پیغام خطا به کاربر ارسال و اعلان می کند که چنین فایلی وجود ندارد.
  • • مرورگر پاسخ را از سرویس دهنده گرفته و سپس یا فایل مدنظر را تحویل می دهد و یا پیغام خطا را برای کاربر به نمایش می گذارد.

حال این سناریو را درنظر بگیرید. سرویس دهنده ی HTTP را طوری تنظیم کنید که هرگاه یک فایل معین در پوشه ی خاصی فراخوانی شد، سرویس دهنده فایل را به مرورگر ارسال نکند بلکه آن را به صورت یک برنامه اجرا نماید. سپس هر آنچه خروجی برنامه بود به مرورگر جهت نمایش برای کاربر ارسال کند. این تابع Common Gateway Interface یا CGI خوانده شده و برنامه هایی که تابع جزئی از آن می باشد، اسکریپت های CGI می گویند. برنامه های CGI می توانند یک اسکریپت Python، PERL، Shell ، برنامه ی نوشته شده با C یا C++ باشد.

نمودار معماری CGI

CGI

تنظیمات سرویس دهنده و پشتیبانی آن از CGI (Web Server Configuration)

پیش از اقدام به برنامه نویسی CGI، لازم است اطمینان حاصل کنید که سرویس دهنده ی وب قابلیت پشتیبانی از CGI را داشته و طوری تنظیم شده که توانایی مدیریت برنامه های CGI را داشته باشد. تمامی برنامه های CGI که قرار است بر روی سرور HTTP اجرا شود، داخل پوشه ای از پیش تعریف شده (pre-configured directory) نگهداری می شود. این پوشه به CGI Directory معروف بوده و طبق قرارداد var/www/cgi-bin نامیده می شود. به طور پیش فرض فایل های CGI دارای پسوند .cgi می باشند، اما شما می توانید پسوند .py فایل های پایتون را برای آن ها استفاده کنید.

به طور پیش فرض، سرویس دهنده ی لینوکس طوری تنظیم شده که فقط اسکریپت های داخل پوشه ی cgi-bin، تحت آدرس /var/www را اجرا کند. اگر می خواهید پوشه ی دیگری را جهت میزبانی و اجرای اسکریپت های CGI مشخص نمایید، خط های زیر را در داخل فایل httpd.conf به Comment تبدیل نمایید:


   AllowOverride None
   Options ExecCGI
   Order allow,deny
   Allow from all


Options All

در آموزش حاضر فرض را بر این می گذاریم که شما سرویس دهنده (web server) را تنظیم و آن را برای اجرای تمامی برنامه های CGI که با اسکریپت های Perl یا Shell نوشته شده، آماده کرده اید.

اولین برنامه ی CGI

در زیر لینک ساده ای مشاهده می کنید که شما را به یک برنامه ی CGI به نام hello.py هدایت می کند. این فایل تحت پوشه ی /var/www/cgi-bin نگهداری شده و دربردارنده ی محتوای زیر می باشد. پیش از اجرای برنامه ی CGI، لازم است با فراخوانی دستور chmod 755 hello.py یونیکس وضعیت یا مد فایل را به executable و قابل اجرا، تغییر داده باشید.

                        
#!/usr/bin/python
print "Content-type:text/html\r\n\r\n"
print ''
print ''
print 'Hello Word - First CGI Program'
print ''
print ''
print '

Hello Word! This is my first CGI program

' print '' print ''

پس از کلیک بر روی hello.py، خروجی زیر به نمایش در می آید:

Hello Word! This is my first CGI program

hello.py یک اسکریپت ساده ی Python است که خروجی خود را در فایل STDOUT یا همان نمایشگر چاپ می کند. در اینجا لازم است به نکته ی دیگری اشاره کنیم و آن اولین خطی از کد است (Content-type:text/html\r\n\r\n) که با دستور print چاپ می شود. این خط کد به مرورگر ارسال شده و نوع محتوایی که نهایتا در نمایشگر (پنجره ی مرورگر) چاپ می شود را اعلان می کند.

تا به اینجای آموزش قطعا با مفاهیم ساده ی CGI آشنا شده و می توانید با استفاده از زبان پایتون برنامه های قدرتمند CGI بنویسید. اسکریپتی که با پایتون نوشته می شود قادر است با سایر سیستم های خارجی نظیر سیستم های مدیریت دیتابیس رابطه ای یا RDBMS تعامل برقرار کرده و اطلاعات لازم را رد و بدل نماید.

HTTP Header (اطلاعاتی درباره ی بسته ی ارسال شده به مرورگر)

دستور Content-type:text/html\r\n\r\n که در بالا به آن اشاره شد، در واقع بخشی از http header است که به مرورگر ارسال شده و آن را از محتوای فایل آگاه می سازد. کل http header به صورت زیر خواهد بود:

HTTP Field Name: Field Content
For Example
Content-type: text/html\r\n\r\n

در زیر تعدادی HTTP header پرکاربرد که در برنامه نویسی CGI به طور گسترده مورد استفاده قرار می گیرد را همراه با شرح کاربرد مشاهده می کنید:

Header
شرح
Content-type:
نوع رشته ای (MIME string) که فرمت فایل بازگشتی را مشخص می کند. به طور مثال می توان به Content-type:text/html اشاره کرد.
Expires: Date
تاریخی که پس از آن اطلاعات مربوطه اعتبار خود را از دست می دهد. مرورگر بر اساس مقدار این header صفحات وب را بروز رسانی می کند. یک رشته ی مجاز و معتبر با فرمت 01 Jan 1998 12:00:00 GMT نگاشته می شود.
Location: URL
URL ای که بجای URL درخواستی بازگردانده می شود. می توانید با استفاده از این فیلد درخواست را به هر فایلی بازگشت یا هدایت (redirect) نمایید.
Last-modified: Date
تاریخ آخرین بروز رسانی منبع و محتوای مورد نظر.
Content-length: N
طول داده و حجم اطلاعات بازگشتی بر حسب بایت. مرورگر با استفاده از این مقدار مدت زمانی که طول می کشد تا فایل کاملا بارگیری شود را تخمین می زند.
Set-Cookie: String
کوکی را بر اساس رشته ی ارسال شده مقداردهی و تنظیم می کند.

متغیرهای CGI

تمامی برنامه های CGI به مقادیر متغیرهای زیر دسترسی دارند. این متغیرها در برنامه نویسی CGI بسیار نقش مهمی را ایفا کرده و کاربرد زیادی دارند.

اسم متغیر
شرح
CONTENT_TYPE
نوع داده ای در این متغیر نگه داری می شود. زمانی مورد استفاده قرار می گیرد که سرویس گیرنده یا کلاینت محتوای الصاق شده را به سرویس دهنده یا سرور ارسال می کند. برای مثال می توان به بارگذاری فایل در سرور و file upload اشاره کرد.
CONTENT_LENGTH
طول و حجم اطلاعات کوئری یا درخواست شده در این متغیر ذخیره می شود. متغیر جاری تنها برای درخواست هایی که با POST ارسال می شوند، قابل بهره برداری می باشد.
HTTP_COOKIE
کوکی های تنظیم شده (مقداردهی شده) را در قالب جفت های کلید و مقدار بازگردانی می کند.
HTTP_USER_AGENT
اسم مرورگری که درخواست را به سرویس دهنده ارسال می کند. این متغیر اطلاعات مربوط به user agent که همان فرستنده ی درخواست محتوا از سرور می باشد را در خود ذخیره می کند.
PATH_INFO
اطلاعات مربوط به path و محل قرارگیری اسکریپت (برنامه ی CGI) در قالب این متغیر نگهداری می شود.
QUERY_STRING
اطلاعات کدگذاری شده در قالب URL که همراه با متد GET به سرویس دهنده ارسال می شود، داخل این متغیر جای می گیرد.
REMOTE_ADDR
آدرس IP میزبان یا سرور راه دور (remote server) که درخواست اطلاعات را می کند داخل متغیر جاری نگه داری می شود. مورد کاربرد این متغیر غالبا در گزارش گیری (logging) یا احرازهویت (authentication) خلاصه می شود.
REMOTE_HOST
اسم کامل و دقیق میزبان (host) که درخواست را ارسال می کند. چنانچه این اطلاعات دردسترس نبود، می توان با استفاده از REMOTE_ADDR آدرس IR را بازیابی کرد.
REQUEST_METHOD
متد مورد استفاده برای ایجاد و ارسال درخواست. پرکاربردترین این متدها عبارتند از GET و POST.
SCRIPT_FILENAME
آدرس کامل و دقیق که اسکریپت یا برنامه ی CGI در آن مستقر می باشد.
SCRIPT_NAME
اسم اسکریپت یا برنامه ی CGI.
SERVER_NAME
اسم سرور یا آدرس IP
SERVER_SOFTWARE
اسم و ورژن نرم افزار که بر روی سرویس دهنده در حال اجرا می باشد.

در زیر یک برنامه ی ساده ی CGI را می بینید که تمامی متغیرهای CGI را لیست می کند.

#!/usr/bin/python
import os
print "Content-type: text/html\r\n\r\n";
print "Environment<\br>";
for param in os.environ.keys():
  print "%20s: %s<\br>" % (param, os.environ[param])

در زیر خروجی کد را مشاهده می کنید:

Environment HTTP_COOKIE: __utma=55973678.1477211342.1492087219.1492087219.1492087219.1; __utmb=55973678; __utmc=55973678; __utmz=55973678.1492087219.1.1.utmccn=(referral)|utmcsr=google.de|utmcct=/|utmcmd=referral
HTTP_COOKIE: __utma=55973678.1477211342.1492087219.1492087219.1492087219.1; __utmb=55973678; __utmc=55973678; __utmz=55973678.1492087219.1.1.utmccn=(referral)|utmcsr=google.de|utmcct=/|utmcmd=referral
CONTEXT_DOCUMENT_ROOT: /var/www/cgi-bin/
CONTEXT_DOCUMENT_ROOT: /var/www/cgi-bin/
SERVER_SOFTWARE: Apache/2.4.6 (CentOS)
SERVER_SOFTWARE: Apache/2.4.6 (CentOS)
CONTEXT_PREFIX: /cgi-bin/
CONTEXT_PREFIX: /cgi-bin/
REQUEST_SCHEME: http
REQUEST_SCHEME: http
SERVER_SIGNATURE: 
SERVER_SIGNATURE: 
GEOIP_COUNTRY_CODE: EU
GEOIP_COUNTRY_CODE: EU
SERVER_PROTOCOL: HTTP/1.1
SERVER_PROTOCOL: HTTP/1.1
QUERY_STRING: 
QUERY_STRING: 
PATH: /usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin
PATH: /usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin
HTTP_USER_AGENT: Mozilla/5.0 (Windows NT 6.1; WOW64; rv:52.0) Gecko/20100101 Firefox/52.0
HTTP_USER_AGENT: Mozilla/5.0 (Windows NT 6.1; WOW64; rv:52.0) Gecko/20100101 Firefox/52.0
SERVER_NAME: www.tutorialspoint.com
SERVER_NAME: www.tutorialspoint.com
REMOTE_ADDR: 5.104.65.183
REMOTE_ADDR: 5.104.65.183
GEOIP_COUNTRY_NAME: Europe
GEOIP_COUNTRY_NAME: Europe
HTTP_X_BLUECOAT_VIA: eaefec6a124f3f39
HTTP_X_BLUECOAT_VIA: eaefec6a124f3f39
HTTP_VIA: HTTP/1.1 ECS (fcn/41B7)
HTTP_VIA: HTTP/1.1 ECS (fcn/41B7)
SERVER_PORT: 80
SERVER_PORT: 80
SERVER_ADDR: 10.34.18.35
SERVER_ADDR: 10.34.18.35
DOCUMENT_ROOT: /var/www/tutorialspoint
DOCUMENT_ROOT: /var/www/tutorialspoint
HTTP_X_FORWARDED_PROTO: http
HTTP_X_FORWARDED_PROTO: http
SCRIPT_FILENAME: /var/www/cgi-bin/get_env.py
SCRIPT_FILENAME: /var/www/cgi-bin/get_env.py
SERVER_ADMIN: contact@tutorialspoint.com
SERVER_ADMIN: contact@tutorialspoint.com
SCRIPT_URI: http://www.tutorialspoint.com/cgi-bin/get_env.py
SCRIPT_URI: http://www.tutorialspoint.com/cgi-bin/get_env.py
GEOIP_CONTINENT_CODE: EU
GEOIP_CONTINENT_CODE: EU
HTTP_HOST: www.tutorialspoint.com
HTTP_HOST: www.tutorialspoint.com
SCRIPT_URL: /cgi-bin/get_env.py
SCRIPT_URL: /cgi-bin/get_env.py
HTTP_UPGRADE_INSECURE_REQUESTS: 1
HTTP_UPGRADE_INSECURE_REQUESTS: 1
HTTP_CACHE_CONTROL: max-stale=0
HTTP_CACHE_CONTROL: max-stale=0
REQUEST_URI: /cgi-bin/get_env.py
REQUEST_URI: /cgi-bin/get_env.py
HTTP_ACCEPT: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8
HTTP_ACCEPT: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8
GATEWAY_INTERFACE: CGI/1.1
GATEWAY_INTERFACE: CGI/1.1
HTTP_X_FORWARDED_FOR: 91.212.206.55
HTTP_X_FORWARDED_FOR: 91.212.206.55
SCRIPT_NAME: /cgi-bin/get_env.py
SCRIPT_NAME: /cgi-bin/get_env.py
REMOTE_PORT: 33398
REMOTE_PORT: 33398
HTTP_ACCEPT_LANGUAGE: fr,fr-FR;q=0.8,en-US;q=0.5,en;q=0.3
HTTP_ACCEPT_LANGUAGE: fr,fr-FR;q=0.8,en-US;q=0.5,en;q=0.3
HTTP_X_HOST: www.tutorialspoint.com
HTTP_X_HOST: www.tutorialspoint.com
GEOIP_ADDR: 5.104.65.183
GEOIP_ADDR: 5.104.65.183
REQUEST_METHOD: GET
REQUEST_METHOD: GET
HTTP_ACCEPT_ENCODING: gzip, deflate
HTTP_ACCEPT_ENCODING: gzip, deflate
UNIQUE_ID: WO9x6LegxBEa9DE2Vqkc2AAAAHs
UNIQUE_ID: WO9x6LegxBEa9DE2Vqkc2AAAAHs

متدهای ارسال اطلاعات به سرور (GET و POST)

گاهی لازم می شود که اطلاعاتی را از مرورگر به سرویس دهنده ی وب و در نهایت به برنامه ی CGI ارسال کنید. مرورگرها برای ارسال این اطلاعات به سرویس دهنده از دو متد GET و POST استفاده می کنند.

ارسال اطلاعات با استفاده از متد GET

متد GET اطلاعات کاربری کدگذاری شده که به درخواست صفحه ضمیمه شده را به سرور ارسال می کند. صفحه و اطلاعات کدگذاری شده به وسیله ی کاراکتر ? از یکدیگر جدا می شوند:

http://www.test.com/cgi-bin/hello.py?key1=value1&key2=value2

متد پیش فرض برای ارسال اطلاعات از مرورگر به سرویس دهنده، متد GET می باشد. این متد یک رشته ی طولانی تولید می کند که داخل Location:box مرورگر نمایان می شود. لازم به توضیح است که اگر اطلاعات ارسالی شما حساس هستند (به عنوان مثال گذرواژه)، توصیه می شود از متد GET برای فرستادن اطلاعات استفاده نکنید. متد GET در خصوص حجم اطلاعات قابل ارسال، محدودیتی اعمال می کند. بدین معنی که کاراکترهای ارسالی در رشته ی درخواست اطلاعات (request string) نباید از مرز 1024 کاراکتر تجاوز کند. متد GET اطلاعات مورد نظر را به وسیله ی هدر QUERY_STRING به سرویس دهنده ارسال می کند. این اطلاعات سپس از طریق متغیر QUERY_STRING در برنامه ی CGI قابل دسترسی می باشد.

جهت ارسال اطلاعات با متد GET می توانید به دو طریق زیر اقدام نمایید:

  • 1. می توانید جفت های کلید و مقدار را به انتهای URL متصل کنید.
  • 2. می توانید اطلاعات درخواستی را با استفاده از تگ های
    ارسال کنید (برای این منظور کافی است مقدار ویژگی method را داخل این تگ، برابر "get" قرار دهید).

ارسال اطلاعات از طریق URL و Query String

در زیر یک URL ساده مشاهده می کنید که دو مقدار را با استفاده از متد GET به hello_get.py ارسال می کند.

/cgi-bin/hello_get.py?first_name=ZARA&last_name=ALI

برنامه ی hello_get.py مقادیر دریافتی از مرورگر (ورودی) را مدیریت می نماید. حال با بهره گیری از ماژول cgi به داده های ارسالی دسترسی پیدا می کنیم:

#!/usr/bin/python
# Import modules for CGI handling 
import cgi, cgitb 
# Create instance of FieldStorage 
form = cgi.FieldStorage() 
# Get data from fields
first_name = form.getvalue('first_name')
last_name  = form.getvalue('last_name')
print "Content-type:text/html\r\n\r\n"
print ""
print ""
print "Hello - Second CGI Program"
print ""
print ""
print "

Hello %s %s

" % (first_name, last_name) print "" print ""

نتیجه ی زیر حاصل می گردد:

Hello ZARA ALI

مثالی کاربردی از ارسال اطلاعات FORM با استفاده از متد GET

در زیر یک HTML FORM مشاهده می کنید که مقادیری را پس از فشردن دکمه ی submit به سرویس دهنده ارسال می کند. سپس داده های ارسالی به برنامه ی hello_get.py جهت مدیریت تحویل داده می شود.

First Name:
Last Name:

در زیر خروجی form بالا را مشاهده می کنید. پس از وارد کردن مقادیر در دو کادر First Name و Last Name، بر روی دکمه ی Submit کلیک کرده و نتیجه را مشاهده نمایید.

ازسال اطلاعات

خروجی زیر را در صفحه ی مجزا مشاهده خواهید نمود:

Hello zara ali

ارسال اطلاعات از طریق متد POST

متد امن تری که برای ارسال اطلاعات به برنامه ی CGI می توان از آن بهره گرفت، متد POST می باشد. متد مذکور اطلاعات را درست مشابه GET پکیج بندی می کند، اما بجای اینکه داده های مورد نظر را به صورت یک رشته ی متنی پس از ? در URL همراه با فرم ارسال کند، آن را در قالب پیغامی مجزا به سرویس دهنده تحویل می دهد.

در زیر همان اسکریپت ساده ی hello_get.py را مشاهده می کنید که اطلاعات ارسالی از هر دو روش (متد GET و POST) را مدیریت می نماید.

#!/usr/bin/python
# Import modules for CGI handling 
import cgi, cgitb 
# Create instance of FieldStorage 
form = cgi.FieldStorage() 
# Get data from fields
first_name = form.getvalue('first_name')
last_name  = form.getvalue('last_name')
print "Content-type:text/html\r\n\r\n"
print ""
print ""
print "Hello - Second CGI Program"
print ""
print ""
print "

Hello %s %s

" % (first_name, last_name) print "" print ""

بار دیگر همان مثال را مشاهده می کنید که دو مقدار را به واسطه ی HTML FORM و دکمه ی Submit به سرویس دهنده ارسال می کند. برای مدیریت مقادیر ارسالی به سرویس دهنده نیز از همان برنامه hello_get.py استفاده می شود.

First Name:
Last Name:

در زیر خروجی واقعی کد فوق را مشاهده می کنید. مقادیر لازم را در کادرهای مربوطه وارد کرده و پس از فشردن دکمه ی Submit، خروجی را مشاهده نمایید:

متد post

خروجی زیر را دریافت می کنید:

Hello zara ali

ارسال داده های Checkbox به سرویس دهنده و مدیریت آن با برنامه ی CGI

Checkbox ها زمانی کاربرد دارند که کاربر احتیاج داشته باشد تا چندین گزینه را همزمان انتخاب نماید.

در زیر نمونه ای از کد HTML که یک فرم ساده با دو CHECKBOX را تشکیل داده و در پنجره ی مرورگر نمایش می دهد، مشاهده می نمایید:

Maths Physics

خروجی کد فوق، فرم زیر می باشد:

خروجی فرم حاضر را در زیر مشاهده می کنید:

CheckBox Maths is : ON
CheckBox Physics is : ON

در زیر کد اسکریپت یا برنامه ی checkbox.cgi را که ورودی کاربر (داده های ارسالی از مرورگر به سرویس دهنده) را مدیریت می کند، مشاهده می نمایید:

#!/usr/bin/python
# Import modules for CGI handling 
import cgi, cgitb 
# Create instance of FieldStorage 
form = cgi.FieldStorage() 
# Get data from fields
if form.getvalue('maths'):
   math_flag = "ON"
else:
   math_flag = "OFF"
if form.getvalue('physics'):
   physics_flag = "ON"
else:
   physics_flag = "OFF"
print "Content-type:text/html\r\n\r\n"
print ""
print ""
print "Checkbox - Third CGI Program"
print ""
print ""
print "

CheckBox Maths is : %s

" % math_flag print "

CheckBox Physics is : %s

" % physics_flag print "" print ""

ارسال داده های Radio Button به برنامه ی CGI در سرویس دهنده

Radio Button ها، برخلاف المان Checkbox، به کاربر اجازه ی انتخاب تنها یک گزینه را می دهند.

در زیر کد HTML که یک فرم به همراه دو Radio button را تشکیل می دهد، مشاهده می نمایید:

Maths Physics

خروجی کد را در زیر مشاهده می کنید:

Radio Button در CGI

در زیر اسکریپت radiobutton.py را که داده های ورودی از کاربر (مرورگر) را دریافت کرده و مدیریت می کند، مشاهده می نمایید:

#!/usr/bin/python
# Import modules for CGI handling 
import cgi, cgitb 
# Create instance of FieldStorage 
form = cgi.FieldStorage() 
# Get data from fields
if form.getvalue('subject'):
   subject = form.getvalue('subject')
else:
   subject = "Not set"
print "Content-type:text/html\r\n\r\n"
print ""
print ""
print "Radio - Fourth CGI Program"
print ""
print ""
print "

Selected Subject is %s

" % subject print "" print ""

ارسال داده های Text Area از مرورگر به برنامه ی CGI در سرویس دهنده

المان TEXTAREA زمانی استفاده می شود که لازم باشد چندین خط متن همراه با فرم به برنامه ی CGI در سرویس گیرنده فرستاده شود.

در زیر یک نمونه کد HTML که یک فرم با کادر TEXTAREA را ساخته و در صفحه نمایش می دهد، مشاهده می نمایید:

خروجی کد فوق، فرم زیر می باشد:

ارسال به Text Area

خروجی اسکریپت به صورت زیر می باشد:

Entered Text Content is Hello Ali Zara

در زیر کد برنامه ی textarea.cgi که ورودی کاربر و مقدار ارسالی از مرورگر را در سمت سرویس گیرنده دریافت کرده و مدیریت می نماید، مشاهده می کنید:

#!/usr/bin/python
# Import modules for CGI handling 
import cgi, cgitb 
# Create instance of FieldStorage 
form = cgi.FieldStorage() 
# Get data from fields
if form.getvalue('textcontent'):
   text_content = form.getvalue('textcontent')
else:
   text_content = "Not entered"
print "Content-type:text/html\r\n\r\n"
print ""
print "";
print "Text Area - Fifth CGI Program"
print ""
print ""
print "

Entered Text Content is %s

" % text_content print ""

ارسال مقادیر کادر کشویی یا Drop down به برنامه ی CGI در سرویس دهنده

از المان کادر کشویی یا drop-down زمانی استفاده می کنیم که لازم باشد گزینه های متعددی برای کاربر نمایش داده و در عین حال اجازه ی انتخاب تنها یک یا دو گزینه در آن واحد را به وی بدهیم:

در زیر نمونه کد HTML که یک فرم به همراه کادر کشویی (drop-down) را در پنجره ی مرورگر برای کاربر نمایش می دهد، مشاهده می کنید:

خروجی کد فوق به این صورت می باشد:

کادر کشویی یا Drop Down

در زیر کد اسکریپت dropdown.py که داده های ارسالی از مرورگر را در سمت سرویس گیرنده دریافت و مدیریت می کند، مشاهده می نمایید:

#!/usr/bin/python
# Import modules for CGI handling 
import cgi, cgitb 
# Create instance of FieldStorage 
form = cgi.FieldStorage() 
# Get data from fields
if form.getvalue('dropdown'):
   subject = form.getvalue('dropdown')
else:
   subject = "Not entered"
print "Content-type:text/html\r\n\r\n"
print ""
print ""
print "Dropdown Box - Sixth CGI Program"
print ""
print ""
print "

Selected Subject is %s

" % subject print "" print ""

استفاده از کوکی ها در CGI

پروتکل HTTP داده های مربوط به وضعیت جاری را ذخیره نمی کند و به عبارتی stateless می باشد. اما همان طور که می دانید یک وب سایت تجاری می بایست اطلاعات جلسه ی کاری یا session جاری که اطلاعات مربوط به کاربر را دربردارد، بین صفحات مختلف وب نگه دارد. به طور مثال، شرایطی را در نظر بگیرید که در آن ثبت نام کاربر پس از تکمیل چندین صفحه ی وب به پایان می رسد. در چنین سناریویی چگونه می بایست اطلاعات کاربر مقیم در session را در تمامی صفحات وب ذخیره نگه داشت؟

در اغلب شرایط استفاده از کوکی بهترین روش برای ذخیره و یادآوری تنظیمات و اطلاعات کاربر است که منجر به کیفیت بالاتر و تجربه ی کاربری بهتر می شود.

کوکی چگونه مورد استفاده قرار می گیرد؟

سرویس دهنده ای که اپلیکیشن بر روی آن مستقر می باشد، اطلاعاتی را در قالب کوکی به مرورگر ارسال می کند. مرورگر بر اساس تنظیمات کاربر می تواند این داده ها را پذیرفته و متعاقبا بر روی هارد دیسک کامپیوتر کاربر ذخیره نماید. حال، هنگامی که کاربر به صفحه ی دیگری از وب سایت مراجعه می کند، اطلاعات ذخیره شده در کوکی به راحتی از کامپیوتر کاربر بازیابی می شود. پس از واکشی اطلاعات از کوکی، سرویس دهنده به خاطر می آورد که کاربر جاری از چه صفحاتی بازدید کرده و اطلاعات لازم را می خواند.

کوکی ها رکوردی از داده های متنی ساده متشکل از 5 فیلد با طول متغیر هستند:

  • Expires: تاریخی که کوکی پس از آن اعتبار خود را از دست داده و غیرقابل استفاده می شود. چناچه فیلد جاری مقداری نداشته باشد، در آن صورت به مجرد خروج کاربر از مرورگر، داده های ذخیره شده در آن نامعتبر و غیرقابل استفاده می شوند.
  • Domain: اسم دامنه یا آدرس سایت شما در این فیلد ذخیره می شود.
  • Path: آدرس پوشه یا محل قرارگیری صفحه ی وب که کوکی را مقداردهی می کند. در شرایطی که ممکن است کوکی از هر صفحه یا پوشه ای بازیابی شود، این فیلد می تواند مقداری نداشته باشد.
  • Secure: چنانچه فیلد جاری با رشته ی "secure" مقداردهی شده باشد، در آن صورت کوکی مورد نظر منحصرا از یک سرویس دهنده ی ایمن و secure قابل واکشی می باشد. اگر این فیلد مقداری نداشته باشد، چنین محدودیتی هم اعمال نخواهد شد.
  • Name=Value: کوکی ها به صورت جفت های کلید و مقدار مقداردهی و بازیابی می شوند.

تنظیم و استفاده از کوکی

ارسال کوکی به مرورگر بسیار آسان می باشد. کوکی ها در واقع همراه با HTTP Header، در حالی که قبل از فیلد Content-type درج شده، به مرورگر فرستاده می شوند. حال به فرض اینکه می خواهید UserID و Password را به عنوان کوکی انتخاب کنید، می بایست کد آن را به صورت زیر تنظیم نمایید:

#!/usr/bin/python
print "Set-Cookie:UserID=XYZ;\r\n"
print "Set-Cookie:Password=XYZ123;\r\n"
print "Set-Cookie:Expires=Tuesday, 31-Dec-2007 23:12:40 GMT";\r\n"
print "Set-Cookie:Domain=www.tutorialspoint.com;\r\n"
print "Set-Cookie:Path=/perl;\n"
print "Content-type:text/html\r\n\r\n"
...........Rest of the HTML Content....

با بررسی مثال جاری قطعا با نحوه ی مقداردهی و تنظیم کوکی آشنا شده اید. در واقع کار مقداردهی کوکی را به وسیله ی Set-Cookie از HTTP Header انجام می دهیم.

تنظیم و مقداردهی ویژگی ها (attribute) و فیلدهای کوکی نظیر Expires، Domain و Path اختیاری می باشد. گفتنی است که کوکی ها پیش از ارسال خط "Content-type:text/html\r\n\r\n به مرورگر، تنظیم و مقداردهی می شوند.

بازیابی کوکی ها

به راحتی می توان تمامی کوکی های مقداردهی شده را بازیابی کرد. کوکی ها در متغیر HTTP_COOKIE به صورت زیر ذخیره می شوند:

key1=value1;key2=value2;key3=value3....

مثال زیر نحوه ی بازیابی کوکی ها را به صورت کاربردی به نمایش می گذارد:

#!/usr/bin/python
# Import modules for CGI handling 
from os import environ
import cgi, cgitb
if environ.has_key('HTTP_COOKIE'):
   for cookie in map(strip, split(environ['HTTP_COOKIE'], ';')):
      (key, value ) = split(cookie, '=');
      if key == "UserID":
         user_id = value
      if key == "Password":
         password = value
print "User ID  = %s" % user_id
print "Password = %s" % password

کد بالا خروجی زیر را برمی گرداند:

User ID = XYZ
Password = XYZ123

مثالی از آپلود فایل

به منظور آپلود یک فایل، لازم است ویژگی enctype از فرم HTML را بر روی multipart/form-data تنظیم نمایید. تگ input با ویژگی type آن بر روی file تنظیم شده، یک دکمه ی "Browse" ایجاد می کند.



File:

خروجی کد فوق به صورت زیر می باشد:

آپلود فایل در کوکی

در زیر اسکریپت save_file.py که آپلود فایل را مدیریت می کند، مشاهده می کنید:

#!/usr/bin/python
import cgi, os
import cgitb; cgitb.enable()
form = cgi.FieldStorage()
# Get filename here.
fileitem = form['filename']
# Test if the file was uploaded
if fileitem.filename:
   # strip leading path from file name to avoid 
   # directory traversal attacks
   fn = os.path.basename(fileitem.filename)
   open('/tmp/' + fn, 'wb').write(fileitem.file.read())
   message = 'The file "' + fn + '" was uploaded successfully'
else:
   message = 'No file was uploaded'
print """\
Content-Type: text/html\n


%s

""" % (message,)

چنانچه اسکریپت فوق را بر روی Unix/Linux اجرا کنید، در آن صورت می بایست خود کار جایگزینی file separator (کاراکتر تفکیک گر) را به صورت انجام دهید. بر روی ویندوز نیازی به این کار نیست و صرف استفاده از دستور open() در کد بالا، عملیات لازم را انجام می دهد.

fn = os.path.basename(fileitem.filename.replace("\\", "/" ))

نحوه ی نمایش و پیاده سازی کادر محاوره ای "File Download" جهت بارگیری محتوا از اینترنت

گاهی توسعه دهنده لازم می داند، زمانی که کاربر بر روی لینکی از صفحه کلیک کرد، بجای نمایش محتوای آن لینک در صفحه، یک کادر محاوره ای "File Download" جهت دانلود اطلاعات مورد نظر به صورت فایل، به کاربر نشان داده شود. این کار به راحتی از طریق HTTP header قابل اجرا می باشد. این HTTP header می بایست با header های نام برده در بخش های قبلی متفاوت باشد.

در مثال حاضر، زمانی که کاربر بر روی لینک کلیک می کند، یک کادر محاوره ای نمایان شده که به وی امکان دانلود فایل FileName را می دهد:

#!/usr/bin/python
# HTTP Header
print "Content-Type:application/octet-stream; name=\"FileName\"\r\n";
print "Content-Disposition: attachment; filename=\"FileName\"\r\n\n";
# Actual File Content will go here.
fo = open("foo.txt", "rb")
str = fo.read();
print str
# Close opend file
fo.close()
1396/02/17 5874 2095
رمز عبور : tahlildadeh.com یا www.tahlildadeh.com
نظرات شما

نظرات خود را ثبت کنید...