Cronjob in Laravel 5 - laravel

I have the job table contains post_at,day_open,block properties
The post_at property is the day when user post the job (Ex:2015-11-24)
The day_open property is the day that job is open (Ex:10)
The block property can contain 2 values 0 or 1. If post_at + day_open > right now the block value will change from 0 to 1
So how can I do that using cronjob?

First check wheather the post_at,day_open are edit in current date
$date = date('Y-m-d');
$job= DB::table('job') ->select('post_at','day_open','block')->where('updated_at',$date) -first();
$id=$job->id;
if(isset($job) && !empty($job))
{
$finding=CronJobCotroller::pushNotify($id);
}
if it's true it go to function pushNotify under the CronJobCotroller,here we write the coding for changing block field value 0 to 1.
public function pushNotify($id) {
$job= DB::table('job') ->select('block')->where('id',$id) ->get();
if(isset($job) && !empty($job))
{
foreach ($job as $cb)
{
$job= DB::table('job')->update('block',1)->where('block',0);
}
}
}

Related

Getting non overlapping between two dates with Carbon

UseCase: Admin assigns tasks to People. Before we assign them we can see their tasks in a gantt chart. According to the task assign date and deadline, conflict days (overlap days) are generated between tasks.
I wrote this function to get overlapping dates between two dates. But now I need to get non overlapping days between two dates, below is the function I wrote.
$tasks = Assign_review_tasks::where('assigned_to', $employee)
->where('is_active', \Constants::$REVIEW_ACTIVE)
->whereNotNull('permit_id')->get();
$obj['task'] = count($tasks);
// count($tasks));
if (count($tasks) > 0) {
if (count($tasks) > 1) {
$start_one = $tasks[count($tasks) - 1]->start_date;
$end_one = $tasks[count($tasks) - 1]->end_date;
$end_two = $tasks[count($tasks) - 2]->end_date;
$start_two = $tasks[count($tasks) - 2]->start_date;
if ($start_one <= $end_two && $end_one >= $start_two) { //If the dates overlap
$obj['day'] = Carbon::parse(min($end_one, $end_two))->diff(Carbon::parse(max($start_two, $start_one)))->days + 1; //return how many days overlap
} else {
$obj['day'] = 0;
}
// $arr[] = $obj;
} else {
$obj['day'] = 0;
}
} else {
$obj['day'] = 0;
}
$arr[] = $obj;
start_date and end_date are taken from database,
I tried modifying it to,
(Carbon::parse((min($end_one, $end_two))->add(Carbon::parse(max($start_two, $start_one))))->days)->diff(Carbon::parse(min($end_one, $end_two))->diff(Carbon::parse(max($start_two, $start_one)))->days + 1);
But it didn't work, in simple terms this is what I want,
Non conflicting days = (end1-start1 + end2-start2)- Current overlapping days
I'm having trouble translate this expression . Could you help me? Thanks in advance
before trying to reimplement complex stuff I recommend you take a look at enhanced-period for Carbon
composer require cmixin/enhanced-period
CarbonPeriod::diff macro method is what I think you're looking for:
use Carbon\CarbonPeriod;
use Cmixin\EnhancedPeriod;
CarbonPeriod::mixin(EnhancedPeriod::class);
$a = CarbonPeriod::create('2018-01-01', '2018-01-31');
$b = CarbonPeriod::create('2018-02-10', '2018-02-20');
$c = CarbonPeriod::create('2018-02-11', '2018-03-31');
$current = CarbonPeriod::create('2018-01-20', '2018-03-15');
foreach ($current->diff($a, $b, $c) as $period) {
foreach ($period as $day) {
echo $day . "\n";
}
}
This will output all the days that are in $current but not in any of the other periods. (E.g. non-conflicting days)

Queue notifications delay in Laravel

I tried delaying each notification (or job) using Laravel queues. Still, instead of the notifications being delayed one after the other, the delay is applied to all the notifications at once. However, the delay is only applied to the first notification, and the rest are sent out simultaneously as the first message. Please, can anyone in this community help me?
This is part of the method that gets only the applicants whose admissions are accepted or rejected and then notify them individually. Unfortunately, the mail server we are using only allows sending a maximum of 30 emails per 1 minute; therefore, I need to use queuing to limit sending only (not more than) 1 email per 2 seconds.
foreach ($applications as $application)
{
$application_id = $application->id;
$admission = Admission::where('application_id', $application_id)->first();
if (empty($admission->admission_no) & $application->status === 5) {
$this->generateAdmissionNumber($application->id, $application->course_id);
$application->update(['done' => 1]);
$admissions = Admission::where('course_id', '=', $id)->get();
foreach ($admissions as $admission) {
$admission->update(['done' => 1]);
}
}
$application->done = 1;
$application->update();
$user = $application->users;
if ($user->notify_if_decision_is_made === 1)
{
$user->notify((new DecisionNotification($user))
->delay(Carbon::now()->addSeconds(2)));
}
}
I followed the guides but still have no solution. I looked at many solutions here but did not see any issues like this one.
I set QUEUE_CONNECTION=database in my .env file, added shouldQueue in the DecisionNotification file, and run php artisan queue:work from the terminal to execute the jobs. I appreciate any help.
The ->delay() only gives a delay to the running job. As your loop is running almost instantly, it won't delay put a delay of 2 seconds between each job.
One way to achieve what you want is:
foreach ($applications as $i => $application) {
// your code chunk
$user->notify((new DecisionNotification($user))->delay($i * 2)));
}
This results in delays as:
Job 1: 0s
Job 2: 2s
Job 3: 4s
Job 4: 6s
Job 5: 8s
...
By the way, ->delay() also accepts integer as second.
You can use sleep() function, which holds the loop for defined period, for example if you want to hold loop for 2 seconds, use sleep(2).
Your code should be:
foreach ($applications as $application) {
$application_id = $application->id;
$admission = Admission::where('application_id', $application_id)->first();
if (empty($admission->admission_no) & $application->status === 5) {
$this->generateAdmissionNumber($application->id, $application->course_id);
$application->update(['done' => 1]);
$admissions = Admission::where('course_id', '=', $id)->get();
foreach ($admissions as $admission) {
$admission->update(['done' => 1]);
}
}
$application->done = 1;
$application->update();
$user = $application->users;
if ($user->notify_if_decision_is_made === 1) {
$user->notify((new DecisionNotification($user))->delay(Carbon::now()->addSeconds(2)));
}
sleep(2);
}
Hope this will be useful.
Read More about sleep()

Compare time using Laravel

In my Laravel application I want to compare times
If time was greater than 23:30 and less than 6:00 returns true
else return false
$time1 = strtotime('23:30:00');
$time2 = strtotime('06:00:00');
$time3 = strtotime('01:30:00');
if ($time3>=$time1 && $time2>$time1 ) {
var_dump('yes');
}
else {
var_dump('no');
}
I would suggest using Carbon to compare date and datetime values:
$time1 = Carbon::createFromTimeString('23:30:00');
$time2 = Carbon::createFromTimeString('06:00:00');
$time3 = Carbon::createFromTimeString('01:30:00');
if ($time3->gte($time1) && $time2->gt($time1)) {
var_dump('yes');
} else {
var_dump('no');
}
Use Carbon, it has functionality to create from a certain format, with the createFromFormat() method.
$time1 = Carbon::createFromFormat('H:i:s', '23:30:00');
$time2 = Carbon::createFromFormat('H:i:s', '06:00:00');
$time3 = Carbon::createFromFormat('H:i:s', '01:30:00');
Carbon has comparisons in built, with gt() being greater than and lt() being less than. Adding an e to the call as lte() would be less than equals. Or you can be more explicit, look through this section in the documentation.
if ($time3->gte($time1) && $time2->gt($time1)) {
//
}
else {
//
}

When is laravel executing the yearly() function

When is laravel executing the yearly() function of it's task scheduling? Is it from the first time it was used or is it each year on 01.01.YYYY?
I checked up the laravel docs and several pages, but I wasn't able to find out the answer to this question.
$schedule->call(function () {
DB::table("invoice_settings")
->where("key", "invoice_number")
->update(["value" => 860001]);
})->yearly();
I expect that it's running on the 01.01.YYYY.
Laravel's yearly coresponds to crontab's yearly event. Described here:
https://crontab.guru/every-year
This is the cron produced:
0 0 1 1 *
Which runs:
At 00:00 on day-of-month 1 in January.
The yearly function is defined in:
vendor/laravel/framework/src/Illuminate/Console/Scheduling/ManagesFrequencies.php
Here you can find the daily, monthly and yearly, and other frequency functions.
public function daily()
{
return $this->spliceIntoPosition(1, 0)
->spliceIntoPosition(2, 0);
}
public function monthly()
{
return $this->spliceIntoPosition(1, 0)
->spliceIntoPosition(2, 0)
->spliceIntoPosition(3, 1);
}
public function yearly()
{
return $this->spliceIntoPosition(1, 0)
->spliceIntoPosition(2, 0)
->spliceIntoPosition(3, 1)
->spliceIntoPosition(4, 1);
}
As in the official Laravel documentation is written that the daily function runs daily at midnight, since the yearly function is defined in the same way it will run at the 1/1/YYYY at midnight.

admin session user edit posts

In database I have a column acc_type as int, and I'm trying to code this if $_SESSION['accountTpye']==1 then allowed this user to edit the other users posts,
And should I use and instead of && ? " or , || ".
Example code:
if(isset($_SESSION['username']) && ($_SESSION['username']==$dnn2['author'] || $_SESSION['accc_type']==1['username'])) {
echo "<a href='edit.php'>Edit</a>";
}
i think this will resolve your problem :
if(isset($_SESSION['username']){
if( ($_SESSION['username']==$dnn2['author']) || ($_SESSION['acc_type']==1) ){
echo "<a href='edit.php'>Edit</a>";
}
}
if((isset($_SESSION['username']) && $_SESSION['username']==$dnn2['author']) || $_SESSION['acc_type']==1){
echo "<a href='edit.php'>Edit</a>";
}
This part doesn't make sense:
$_SESSION['acc_type']==1['username']
If you just remove that last ['username'] and then wrap the session username part to be the first part of the conditional so the acc_type one does not depend on it then things should be ok
UPDATE:
In your login.php file locate this part:
$req = mysql_query('select password,id from users where username="'.$username.'"');
$dn = mysql_fetch_array($req);
if($dn['password']==sha1($password) and mysql_num_rows($req)>0)
{
$form = false;
$_SESSION['username'] = $_POST['username'];
$_SESSION['userid'] = $dn['id'];
You need to also select the acc_type. ASSUMING it's a field in the users table, modify the query to read this:
'select password,id, acc_type from users where username="'.$username.'"'
Then make sure to set the session var:
$form = false;
$_SESSION['username'] = $_POST['username'];
$_SESSION['userid'] = $dn['id'];
$_SESSION['acc_type'] = $dn['acc_type'];
When you test this, make sure you log out then log bacak in again.

Resources