Подтвердить что ты не робот

Повторять событие в назначенный день каждую неделю до определенной даты

При создании события мне нужно установить начало события и конец события в формате даты и времени (0000-00-00 00:00:00) Затем у меня есть возможность установить еженедельное повторение этого события до определенной даты (0000-00-00) Но я не могу правильно вставлять повторяющиеся события в базу данных. Вот что я имею:

$startDateTime = '2015-04-30 10:30:00';
$endDateTime = '2015-04-30 11:30:00';
$repeatEndDate = '2015-06-01';
$timestamp = strtotime($startDateTime);
$day_of_week = date('l', $timestamp);
$step  = 1;
$unit  = 'W';
$repeatStart = new DateTime($startDateTime);
$repeatEnd   = new DateTime($repeatEndDate);
$repeatStart->modify($day_of_week);  
$interval = new DateInterval("P{$step}{$unit}");
$period   = new DatePeriod($repeatStart, $interval, $repeatEnd);

foreach ($period as $key => $date ) {
    $repeatQuery = 'INSERT INTO event(start,end,status,repeats) VALUES ("'.$startDateTime.'","'.$endDateTime.'","'.$status.'","'.$repeatEndDate.'")';
    $repeatResult = mysqli_query($db, $repeatQuery) or die (mysqli_error($db));
}

Когда я делаю print_r($date);, это выглядит так: никакого фактического времени просто 00:00:00

DateTime Object
(
    [date] => 2015-04-30 00:00:00
    [timezone_type] => 3
    [timezone] => Europe/Berlin
)

Я знаю, что я не могу вставлять такие значения, но я не знаю, как получить правильные значения от объектов. Поэтому в этом примере мне нужно вставить события, которые начинаются в 10:30:00 и заканчиваются в 11:30:00 (события всегда заканчиваются в тот же день) каждый четверг, начиная с 2015-04-30 и заканчивая в 2015-06-01. Как это можно достичь?

Спасибо

4b9b3361

Ответ 1

Проблема заключается в том, что вы вызываете DateTime::modify с именем дня (в настоящее время "четверг" ). Это значение рассчитывается из переменной $startDateTime, а затем используется для изменения этой переменной, поэтому единственный эффект, который он имеет, - это сброс части времени этого экземпляра DateTime обратно в 0:00:00.

Ниже приводятся результаты, которые я ожидал бы: (Я прокомментировал части, которые вам нужно удалить с вашего, чтобы было легче увидеть разницу)

date_default_timezone_set('Etc/UTC');

$startDateTime = '2015-04-30 10:30:00';
$endDateTime = '2015-04-30 11:30:00';
$repeatEndDate = '2015-06-01';
#$timestamp = strtotime($startDateTime);
#$day_of_week = date('l', $timestamp);
$step  = 1;
$unit  = 'W';
$repeatStart = new DateTime($startDateTime);
$repeatEnd   = new DateTime($repeatEndDate);
#$repeatStart->modify($day_of_week);  
$interval = new DateInterval("P{$step}{$unit}");
$period   = new DatePeriod($repeatStart, $interval, $repeatEnd);



foreach ($period as $key => $date ) {
    echo($date->format('Y-m-d H:i:s')) . PHP_EOL;
}

Результатом выполнения вышеперечисленного является:

2015-04-30 10:30:00
2015-05-07 10:30:00
2015-05-14 10:30:00
2015-05-21 10:30:00
2015-05-28 10:30:00

Ответ 2

Когда вы изменяете свой $repeatStart с помощью метода modify(), вы используете символ формата l, который, согласно docs, возвращает

Полнотекстовое представление дня недели

изменив строку формата $day_of_week на

$day_of_week = date('Y-m-d H:i:s', $timestamp);

Я получаю следующий вывод

DateTime Object
(
   [date] => 2015-04-30 10:30:00
   [timezone_type] => 3
   [timezone] => Europe/London
)
DateTime Object
(
    [date] => 2015-05-07 10:30:00
    [timezone_type] => 3
    [timezone] => Europe/London
)
DateTime Object
(
    [date] => 2015-05-14 10:30:00
    [timezone_type] => 3
    [timezone] => Europe/London
) 
DateTime Object
(
    [date] => 2015-05-21 10:30:00
    [timezone_type] => 3
    [timezone] => Europe/London
)
DateTime Object
(
    [date] => 2015-05-28 10:30:00
    [timezone_type] => 3
    [timezone] => Europe/London
)

Хотя, модификация на самом деле не нужна, и следующий код должен достичь того, что вы ищете.

 <?php

$startDateTime = '2015-04-30 10:30:00';
$endDateTime = '2015-04-30 11:30:00';
$repeatEndDate = '2015-06-01';

$step  = 1;
$unit  = 'W';
$repeatStart = new DateTime($startDateTime);

$repeatEnd   = new DateTime($repeatEndDate);

$interval = new DateInterval("P{$step}{$unit}");
$period   = new DatePeriod($repeatStart, $interval, $repeatEnd);
foreach ($period as $key => $date ) {
    $repeatQuery = 'INSERT INTO event(start,end,status,repeats) VALUES ("'.$startDateTime.'","'.$endDateTime.'","'.$status.'","'.$repeatEndDate.'")';
    $repeatResult = mysqli_query($db, $repeatQuery) or die (mysqli_error($db));
    print_r($date);
}