Laravel background jobs

teroristd

Registered
Здравейте, възможно ли е да се стартира задача в бекграунд в Ларавел без да се стартира ръчно? Например юзър достъпва някаква страница, натиска бутон и задачата се стартира, да кажем ъпдейтва някакво поле в базата данни през определен период от време.
 
Може да го направиш с https://laravel.com/docs/5.6/queues

Въпроса е че трябва да го настроиш през командния прозорец или ssh ако си на vps. На споделен хостинг не става или поне преди време аз като търсих нямаше начин. :?:
 
Четох за това но ако съм разбрал правилно трябва да подам команда в артисан за да стартирам задачата, а аз искам да се стартира без моята намеса.
 
Да точно така.

Затова аз ползвам друго. Използвам команди. Но не знам до колко ще ти свърши работа това ако ти трябва да се изпълни точно на клик на бутон от потребител, но все пак .. Те вървят навсякъде и могат да се разграфят както си поискаш. https://laravel.com/docs/5.6/scheduling

Идеята е че работят с cron и трябва да нагласиш един единствен крон който да изпълнява :
Код:
* * * * * php /path-to-your-project/artisan schedule:run >> /dev/null 2>&1

И вече ти в кода си правиш командите и им казваш колко пъти на ден да се изпълняват или всяка минута или както си поискаш. :) :?:

Пример:
PHP:
$schedule->command('foo')
                ->hourly();


като това се пише в App/Console/Kernel.php, а командите се създават с артисан команда и си ги търсиш в App/Console/Commands/(тук) :idea: :?:

Другия вариант е просто ajax call и така :)
 
Мисля че и schedule няма да ми свърши работа, защото пак трябва аз да го стартирам, а целта е да се стартира от юзърите.

А какво имаш предвид с ajax call?
 
ами както би го напрвил попринцип ако не беше във фреймуорк. При цъкане на бутона js функция прави post заявка до някакъв route и кода ти се изпълнява.

Или разбира се може и без ajax и просто при субмит в контролера да си изпълниш кода. Може би ако кажеш какво точно искаш ще е по-лесно иначе варианти колкото иска - както виждаш. :!: :?:
 
Да ще обясня подробно, но ще е след около един час, че сега ми се налага да изляза.
 
joTunkiq каза:
Може да го направиш с https://laravel.com/docs/5.6/queues

Въпроса е че трябва да го настроиш през командния прозорец или ssh ако си на vps. На споделен хостинг не става или поне преди време аз като търсих нямаше начин. :?:

Не му трябва конзола въобще. Всичко може ръчно да си го направи.
Създава си класа в папка app/Jobs, имплементира нужните зависимости(които са описани в сайта), настройва си какво иска да прави(като насторйки от рода на колко опита да направи, за да се изпълни могат да се опишат чрез публични свойства в класа) и воаля. След това го изпълнява с YouJobClass::dispatch().

@teroristd относно примера ти. Искаш като веднъж натисне бутона, задачата да си се стартира като цяло и през определен период да си ъпдейтва? Без да е нужно второ кликане?
 
Revelation каза:
@teroristd относно примера ти. Искаш като веднъж натисне бутона, задачата да си се стартира като цяло и през определен период да си ъпдейтва? Без да е нужно второ кликане?

Да.

Но нека обясня по детайлно. Искам да си направя игра, като я правя изцяло с учебна цел. Смятам че така ще ми е по интересно и ще науча различни неща :) . Ще я правя с Laravel и някакви други технологии ако са необходими, като Vue, Angular и т.н. Да минем на това което искам да направя в момента. Нека си представим че някакъв юзър се регистрира. В момента на регистрацията в базата се попълват освен обичайните неща и някаква таблица с ресурси, например жълтици, камъни и желязо. Да кажем в началото има 100 жълтици, 0 камъни и 0 желязо. Първоначалната опция е да построи мина за камъни, за която като се натисне бутон трябва да се стартира таймер, например за 10мин. и като изтече времето да се стартира задачата в бекграунд която да ъпдейтва базата през някакъв интервал например 1мин. и да добавя по 1 камък на играча.
 
Така вече като знаем какво искаш по-лесно ще ти хелпнем. Не че искам да се поватарям, ноо ..
При цъкане на бутона js функция прави post заявка до някакъв route и кода ти се изпълнява.
Или разбира се може и без ajax и просто при субмит в контролера да си изпълниш кода.

По скоро тука проблема е, че не може да си го представиш как ще изглежда в базата данни ми се струва :D
 
joTunkiq каза:
Така вече като знаем какво искаш по-лесно ще ти хелпнем. Не че искам да се поватарям, ноо ..
При цъкане на бутона js функция прави post заявка до някакъв route и кода ти се изпълнява.
Или разбира се може и без ajax и просто при субмит в контролера да си изпълниш кода.

По скоро тука проблема е, че не може да си го представиш как ще изглежда в базата данни ми се струва :D

Не ми е проблема базата, нито рутовете, за сега :D, ами това че ако играча излезне от играта кода ще спре да се изпълнява. Целта е мината да почне да си трупа ресурси дори играча да не е на линия.
 
Не ми е проблема базата, нито рутовете, за сега Very Happy, ами това че ако играча излезне от играта кода ще спре да се изпълнява. Целта е мината да почне да си трупа ресурси дори играча да не е на линия.

Можеш да ги смяташ стойностите, когато ти потрябват.

Примерно при следващото влизане умножаваш изминалото време по някакъв коефициент и ъпдейтваш. Няма нужда от кронове и такива работи.

(Щом не правиш игра, която 60 пъти в секунда ъпдейтва)
 
anonimen каза:
Не ми е проблема базата, нито рутовете, за сега Very Happy, ами това че ако играча излезне от играта кода ще спре да се изпълнява. Целта е мината да почне да си трупа ресурси дори играча да не е на линия.

Можеш да ги смяташ стойностите, когато ти потрябват.

Примерно при следващото влизане умножаваш изминалото време по някакъв коефициент и ъпдейтваш. Няма нужда от кронове и такива работи.

(Щом не правиш игра, която 60 пъти в секунда ъпдейтва)

Да виж това е идейно. Не се бях сетил за този начин, обаче тук изниква един проблем. Какво правим ако играча не излезне и не рефрешне през времето което ще е необходимо да се натрупа един камък?
 
Kолегата това ти каза, като сметнеш всичко, ще ъпдейтнеш тогава когато е изминало времето.

Примерно ако трябва да приключи копаенето в 23:59 днес - тогава ще му добавиш всичките изкопани ресурси.

Или процентно спрямо времето на започване и приключване може да му добавяш някакви стойности (там колкото % е разликата), но тука трудно би станало без ajax :)
 
Объркана ти е логиката.

Нещата не се стартират след като кликнеш някъде.
В такава ситуация си правиш една таблица, където регистрираш всеки потребител, който трябва да участва в "работата"(queue job). Това queue работата му е да взима данните от базата данни и да ъпдейтва ресурсите на записаните потребители.

От там си правиш Schedule примерно на всеки 5 минути да изпълнява този queue job и който се стартира от самото пускане на играта.

Самата таблица трябва да съдържа например:

resources_per_min - измисли си име
[sql]
user_id
gold
stone
iron
[/sql]

Това трябва да съдържа по колко ресурси на 5 минути трябва да се увеличават. Отделно си имай таблица resources да речем, която де факто ще се обновява.

Тази таблица(resources_per_min) трябва да се ъпдейтва от друго queue, което се стартира при кликане бутона за построяване на сграда и му се слага delay, който е времето за построяване на сграда + подаваш user_id да знаеш на кой потребител трябва да обновиш данните.

И след като искаш да учиш Laravel, към всичко това можеш да използваш Broadcasting, за да направиш нещата малко real-time.

Надявам се, че съм го описал добре. Ако не, ще се опитам да ти направя някоя графика.
 
Благодаря Revelation. Ако не те притеснява ще се радвам да направиш някоя графика :) . Също така няма да се разсърдя и на малко код.
 
https://drive.google.com/open?id=1W1OEo8s60xaqrrifGY9kJHrmUDuxdojA

Не ми е сила да правя диаграми. Надявам се да е по-ясно какво се случва.

А код не мога да ти предоставя, защото сега нямам достатъчно време да правя имплементации.
 
Имам един малък проблем. Когато стартирам php artisan schedule:run се изпълнява само един път, а съм казал да е на всяка минута.

PHP:
protected function schedule(Schedule $schedule)
    {
        $schedule->command('update:resources')->everyMinute();
    }

Всъщност това не е проблем на сегашната апликация, ами и преди като съм експериментирал с командите е било същото. Аз съм с xampp ако има значение.
 
Ами да защото изпълняваш командата само 1 път :D

Затова ти бях споменал че трябва да създадеш крон задача, която да изпълнява тази команда и вече от кода ще си контролираш точно коя задача колко пъти да се изпълнява.

Идеята е че работят с cron и трябва да нагласиш един единствен крон който да изпълнява :
Код:
* * * * * php /path-to-your-project/artisan schedule:run >> /dev/null 2>&1
И вече ти в кода си правиш командите и им казваш колко пъти на ден да се изпълняват или всяка минута или както си поискаш. Smile Question
:?:
 

Горе