PDA

View Full Version : سوال: نوشتن برنامه ای که همیشه در حال اجرا باشد !



sara66
جمعه 29 اردیبهشت 1391, 12:36 عصر
سلام
من روی یک سرور مجازی با دلفی برنامه ای نوشتم که با استارت شدن ویندوز شروع به کار می کند و هر 30 ثانیه یک کد را اجرا می کند
اما هزینه سرور مجازی بالا هست
الان یک هاست گرفتم و می خوام برنامه را با php بنویسم
باید چکار کنم که برنامه همیشه در حال اجرا باشه و هر 30 ثانیه بتونه یک کد را اجرا کنه ؟
مرسی

djsaeedkhan
جمعه 29 اردیبهشت 1391, 12:40 عصر
سلام
می تونید از خاصیتی به نام cron Jobs استفاده کنید. البته یاهو هم یه امکانی داره که بشه باهاش کاری مثل Cron Jobs رو درست کرد.
با سپاس

sara66
جمعه 29 اردیبهشت 1391, 12:52 عصر
cron رو توی لینوکس دیدم ، اما اینجا چی هست ؟ دستوری از php یا امکانی از سروری که ازش هاست گرفتم ؟

djsaeedkhan
جمعه 29 اردیبهشت 1391, 12:58 عصر
این یه چیزی توی سی پنل هست. مثل بقیه امکانات سی پنل

sara66
جمعه 29 اردیبهشت 1391, 13:12 عصر
یعنی یک فایل php را توی cpanel بردم بهcron ؟
توی برنامه php نمیشه تایمر گذاشت ؟

djsaeedkhan
جمعه 29 اردیبهشت 1391, 13:26 عصر
یعنی یک فایل php را توی cpanel بردم بهcron ؟
توی برنامه php نمیشه تایمر گذاشت ؟

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

sara66
جمعه 29 اردیبهشت 1391, 13:29 عصر
مرسی
پس کران را میشه مثلا روی هر 30 ثانیه تنظیم کرد و بعد فقط کد هام را توی صفحه php بنویسم ؟
برای multithreading توی php مقاله ای هست ؟

colors
جمعه 29 اردیبهشت 1391, 14:00 عصر
درود

البته باید قبل از استفاده از کران جابز باید با مدیریت هاست هماهنگی کنید, معمولا اجازه نمیدن از کران جابز برای اجرای دستورات هر 30 ثانیه یک بار استفاده کنید

sara66
جمعه 29 اردیبهشت 1391, 14:11 عصر
پس باید چکار کرد ؟

djsaeedkhan
شنبه 30 اردیبهشت 1391, 00:34 صبح
این سایت رو ببینید
مجانی هست
http://cronless.com/register.php

sara66
شنبه 30 اردیبهشت 1391, 08:44 صبح
مرسی اما چی هست این ؟!
ببینید کل برنامه ای که قراره نوشته بشه اینه :
یک برنامه که هر 30 یا 60 ثانیه شرطی را چک می کنه و اگر اون شرط برقرار بود ، برای صد نفر ایمیل بزنه ! این صد تا ایمیل هم باید همزمان ارسال بشه ، نه اینکه ایمیل نفر صدم ، نیم ساعت بعد برسه !

میشه اصلا همچین برنامه ای را با php نوشت ؟ روی هاست میشه یا بهتره سرور مجازی بگیرم ؟
مرسی

Unique
شنبه 30 اردیبهشت 1391, 19:10 عصر
شما اگه هر 30 ثانیه یکبار با درست بودن شرطت به تعداد زیاد برای هر نفر روی سرویس دهنده Shared در هر مرتبه 100 ایمیل بفرستی قطعا یکی دو روزه دسترسیتون را میبندن یک سنت هم بهتون پس نمیدن !
برای ارسال به این تعداد بالا حتما باید Mail Server روی یک سرور مجازی ایجاد کنین و تنظیماتش را حتما درست انجام بدین تا بتونین ایمیل های زیاد بفرستین ولی block نشین ! اگه هم ایمیل هاتون جنبه تبلیغاتی داره . دریافت کنندگان ممکنه نخوان ایمیل شما را بگیرند یعنی دارین spam میفرستین که در هر حالتی block میشین و spam folder نتیجه خواهد بود !

اما از نظر فنی شما میتونی 10 تا ایمیل را توی CC یا BCC بگذاری و سرویس دهنده ایمیل شما ASAP (در اولین فرصت) ایمیل ها را میفرسته و نیازی به thread ندارین. در مورد هز 30 ثانیه یکبار هم میتونی Cron Job ست کنی که اگه سرور مجازی بگیری محدودیتی نداری و بعضی از هاستینگ های Shared هم اجاز میدن !

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

MMSHFE
یک شنبه 31 اردیبهشت 1391, 00:52 صبح
مجدداً تأکید میکنم (دفعه قبلی توی یک تاپیک دیگه گفتم) امکانات وب رو نباید با دسکتاپ یکسان فرض کنید. بخصوص درمورد هاستهای اشتراکی که قراره به چندین کاربر همزمان سرویس دهی کنند. برای کارهای تخصصی بهترین راه VPS یا VDS هست. مثلاً شما میتونید توی سرورهای خصوصی مجازی (VPS) یا سرورهای اختصاصی مجازی (VDS) تعداد 100 اسکریپت PHP بسازید که هرکدوم عمل ارسال ایمیل به یک کاربر رو انجام میدن و هر 30 ثانیه یکبار، هر 100 اسکریپت رو با Cron Jobs فراخوانی کنید. اگه تنظیمات Mail Server هم به درستی انجام شده باشه، به مشکلی بر نمیخورین. موفق باشید.

MostafaEs3
یک شنبه 31 اردیبهشت 1391, 00:57 صبح
کاشکی یک چیزی شبیه به تابع sleep بود که سی پی یو رو از کار نمی انداخت !! خیلی خوب میشد :لبخند:

البته یک چیزایی شنیدم با for میشه انجام داد ولی نمیدونم ایرادی بوجود میاره یا نه :متفکر:

MMSHFE
یک شنبه 31 اردیبهشت 1391, 01:13 صبح
شبیه سازی sleep بدون متوقف شدن CPU :


function mySleep($sec) {
flush();
$time = time();
while(time() < ($time + $sec));
}
//Usage:
mySleep(3);

موفق باشید.

MostafaEs3
یک شنبه 31 اردیبهشت 1391, 02:49 صبح
:لبخند: خیلی خوبه

خب به نظرتون این میتونه برای اجرای یک برنامه به مدت زمان زیاد مناسب باشه ؟ مثلا من بخوام 5 روز یک برنامه درحال اجرا باشه و هرچند ثانیه یک ایمیل بفرسته . با این تابع و تابع set_time_limit و با کمک ignore_user_abort فکر کنم بشه یک همچین چیزی رو ساخت .. درست میگم ؟ :متفکر:

MostafaEs3
یک شنبه 31 اردیبهشت 1391, 04:00 صبح
عجب چیزی شد ! :لبخند: دقت کنید که این زمان رو بر اساس میکرو ثانیه میگیره (micro secend) .. هر 1 میلیون میکرو ثانیه برابر با 1 ثانیه هست

اگه اشتباه نکنم این میتونه مشکل اجرای طولانی مدت اسکریپت رو حل کنه .. البته راه درست تر همون کرون جابز هست که دوستان گفتن :لبخندساده:



ob_start();
set_time_limit(0);
ignore_user_abort(true);
error_reporting(E_ALL);
date_default_timezone_set('Asia/Tehran');
ini_set('memory_limit', '512M');
ini_set('default_charset', 'UTF-8');
ini_set('max_execution_time', '30000');
ini_set('magic_quotes_gpc', 'Off');

function mySleep($m_sec) {
flush();
$time = time();
while(time()*1000000 < ($time*1000000 + $m_sec));
}
echo date('h:i:s:u') . "\n < br />";
mySleep(4000000);
echo date('h:i:s:u') . "\n < br />";
ob_end_flush();

eshpilen
یک شنبه 31 اردیبهشت 1391, 09:50 صبح
کاشکی یک چیزی شبیه به تابع sleep بود که سی پی یو رو از کار نمی انداخت !! خیلی خوب میشد :لبخند:

sleep سی پی یو رو از کار نمیندازه. فقط پردازشی که sleep رو اجرا کنه موقتا از لیست اجرای سیستم عامل خارج میشه و بعد از زمان سپری شده دوباره وارد لیست مالتی تسک سیستم عامل میشه. این باعث میشه چنین برنامه ای در مدتی که میخواد صبر کنه زمان CPU رو هدر نده و سهم زمانی اون به پردازشهای دیگر اختصاص پیدا کنه درصورت نیاز.

حالا شما چه مشکلی با sleep داری مگه؟ میخوای چکار کنی که با sleep نمیشه؟

eshpilen
یک شنبه 31 اردیبهشت 1391, 09:59 صبح
:لبخند: خیلی خوبه

خب به نظرتون این میتونه برای اجرای یک برنامه به مدت زمان زیاد مناسب باشه ؟ مثلا من بخوام 5 روز یک برنامه درحال اجرا باشه و هرچند ثانیه یک ایمیل بفرسته . با این تابع و تابع set_time_limit و با کمک ignore_user_abort فکر کنم بشه یک همچین چیزی رو ساخت .. درست میگم ؟ :متفکر:
باید حواست باشه اینطوری پردازش هر درخواست در حافظه و درحال اجرا باقی میمونه.
هر درخواست جدید یک پردازش جدید ایجاد میکنه.
بنابراین اگر خودت اشتباها چند بار درخواست بفرستی چند نسخه از اون برنامه برای 5 روز بصورت موازی درحال اجرا باقی میمونن (مگر اینکه یک جوری مثلا بوسیلهء شل اونا رو خاتمه بدی) که گذشته از منابعی که هدر میدن میتونن بسته به برنامه و الگوریتم شما در کار همدیگر اختلال ایجاد کرده و مشکل به بار بیارن.

ضمنا یک هکر اگر این قضیه و آدرس برنامهء شما رو بفهمه میتونه خیلی راحت یک حملهء DOS رو بر این اساس اجرا کنه. یعنی تعدادی درخواست میفرسته تا برنامه های درحال اجرا زیاد بشن و تمام منابع سخت افزاری سیستم (عمدتا RAM و CPU) مصرف بشه، و اونوقت سرور میخوابه یا خیلی کند میشه.
البته برای جلوگیری از این قضیه میشه روشهای مختلفی بکار برد (مثلا برنامه قبل از اجرا و وارد شدن به حلقه، منبع ارسال درخواست رو احراز هویت کنه (مثلا بوسیلهء پسورد)).

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

ضمنا یادت نره وقتی سرور ریستارت میشه برنامه های شما هم از کار میفتن و تا وقتی دوباره درخواست نفرستی استارت نمیشن. بنابراین باید یک فکری هم برای این بکنی. فکر نکن سرورهای لینوکس ریستارت نمیشن.

MostafaEs3
یک شنبه 31 اردیبهشت 1391, 16:54 عصر
sleep سی پی یو رو از کار نمیندازه. فقط پردازشی که sleep رو اجرا کنه موقتا از لیست اجرای سیستم عامل خارج میشه و بعد از زمان سپری شده دوباره وارد لیست مالتی تسک سیستم عامل میشه. این باعث میشه چنین برنامه ای در مدتی که میخواد صبر کنه زمان CPU رو هدر نده و سهم زمانی اون به پردازشهای دیگر اختصاص پیدا کنه درصورت نیاز.

حالا شما چه مشکلی با sleep داری مگه؟ میخوای چکار کنی که با sleep نمیشه؟

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

MostafaEs3
یک شنبه 31 اردیبهشت 1391, 16:56 عصر
باید حواست باشه اینطوری پردازش هر درخواست در حافظه و درحال اجرا باقی میمونه.
هر درخواست جدید یک پردازش جدید ایجاد میکنه.
بنابراین اگر خودت اشتباها چند بار درخواست بفرستی چند نسخه از اون برنامه برای 5 روز بصورت موازی درحال اجرا باقی میمونن (مگر اینکه یک جوری مثلا بوسیلهء شل اونا رو خاتمه بدی) که گذشته از منابعی که هدر میدن میتونن بسته به برنامه و الگوریتم شما در کار همدیگر اختلال ایجاد کرده و مشکل به بار بیارن.

ضمنا یک هکر اگر این قضیه و آدرس برنامهء شما رو بفهمه میتونه خیلی راحت یک حملهء DOS رو بر این اساس اجرا کنه. یعنی تعدادی درخواست میفرسته تا برنامه های درحال اجرا زیاد بشن و تمام منابع سخت افزاری سیستم (عمدتا RAM و CPU) مصرف بشه، و اونوقت سرور میخوابه یا خیلی کند میشه.
البته برای جلوگیری از این قضیه میشه روشهای مختلفی بکار برد (مثلا برنامه قبل از اجرا و وارد شدن به حلقه، منبع ارسال درخواست رو احراز هویت کنه (مثلا بوسیلهء پسورد)).

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

ضمنا یادت نره وقتی سرور ریستارت میشه برنامه های شما هم از کار میفتن و تا وقتی دوباره درخواست نفرستی استارت نمیشن. بنابراین باید یک فکری هم برای این بکنی. فکر نکن سرورهای لینوکس ریستارت نمیشن.

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

eshpilen
یک شنبه 31 اردیبهشت 1391, 17:08 عصر
ولی اگه صفحه بسته بشه دیگه باز نمیشه (درصورتی که فایل ارسال ایمیل با فایل صفحه ی اصلی متفاوت هست) !!!!!
چی دیگه باز نمیشه؟ چرا باز نمیشه؟

MostafaEs3
یک شنبه 31 اردیبهشت 1391, 19:46 عصر
صفحه ی اصلی اون سیستم ایمیل !! چون باید یکسری اطلاعات رو دریافت کنه از سرور و سرور هم Out هستش روی تابع sleep !!!!! :لبخند:

zeinab-es'haghi
دوشنبه 01 خرداد 1391, 15:40 عصر
من توی یکی از صفحات وب سایتم می خوام مثلا هر 3 دقیقه چک کنم که آیا اس ام اس جدید دریافتی داشتم یا نه. این کار رو باید با همین چیزایی که تو این تاپیک گفته شد انجام بدم؟ راه راحت تری نداره؟

MMSHFE
دوشنبه 01 خرداد 1391, 19:03 عصر
میتونید با AJAX هر 180 ثانیه دریافتهای جدید رو از سرور درخواست کنید و نشون بدین. درمورد تابع setTimeout (یا setInterval) تحقیق کنید. فقط کافیه اون صفحه باز باشه.