як видалити всі куки мого веб-сайту в php


92

Мені цікаво, чи можу я видалити всі файли cookie свого веб-сайту, коли користувач натискає кнопку виходу, оскільки я використовував цю функцію для видалення файлів cookie, але це не працює належним чином:

setcookie("user",false);

Чи є спосіб видалити куки одного домену в PHP?


У більшості випадків кращою ідеєю буде використовувати файли cookie більш розумно вибірково. Якщо ви використовуєте сеанси, буде достатньо одного файлу cookie. У будь-якому випадку, відстежуйте, які файли cookie ви встановили, тоді вам не знадобиться якийсь динамічний спосіб їх перегляду та видалення.
caw

Відповіді:


172

PHP setcookie ()

Взято з цієї сторінки, це призведе до скасування всіх файлів cookie для вашого домену:

// unset cookies
if (isset($_SERVER['HTTP_COOKIE'])) {
    $cookies = explode(';', $_SERVER['HTTP_COOKIE']);
    foreach($cookies as $cookie) {
        $parts = explode('=', $cookie);
        $name = trim($parts[0]);
        setcookie($name, '', time()-1000);
        setcookie($name, '', time()-1000, '/');
    }
}

http://www.php.net/manual/en/function.setcookie.php#73484


9
Я прочитав цей коментар, але насправді не розумію, чому використання HTTP_COOKIEзначення було б кращим, ніж перегляд $_COOKIEмасиву. У вас є якась причина для цього? Для мене це виглядає лише як більша (подвійна) робота на парсер.
тикати

Наскільки я можу зрозуміти, різниці немає (крім додаткової роботи).
jasonbar

11
@poke: Якщо імена файлів cookie містяться в нотації Array, наприклад: user [ім'я користувача] Тоді PHP автоматично створить відповідний масив у $ _COOKIE. Натомість використовуйте $ _SERVER ['HTTP_COOKIE'], оскільки він відображає фактичні заголовки HTTP-запиту.
Фархаді,

Як би ви видалили всі файли cookie, крім файлів cookie або файлів cookie з заданими значеннями?
Chill Web Designs

2
Я бачив ситуації, коли є 2 файли cookie з однаковим іменем, але з різними налаштуваннями домену. Один з них потрапить у масив $ _COOKIE, а інший - ні. Але вони обидва будуть видимі в HTTP_COOKIE. Якщо ви хочете виправити цю ситуацію, це спосіб зробити це.
dlo

42
$past = time() - 3600;
foreach ( $_COOKIE as $key => $value )
{
    setcookie( $key, $value, $past, '/' );
}

Ще краще, однак, пам’ятати (або десь зберігати), які файли cookie встановлюються разом із вашим додатком у домені, і видаляти всі безпосередньо.
Таким чином ви можете бути впевнені, що правильно видалите всі значення.


2
чудовий код, але його не потрібно використовувати setcookie( $key, FALSE );?! (див. примітки щодо оформлення на php.net/manual/en/function.setcookie.php )
Марко Демайо

@Marco Demaio: Має бути, але я вже бачив, що це не вдалося на деяких серверах. Але звичайно, якщо це працює для вас, просто робіть це так :)
тикай

це не повинно бути питанням сервера, це PHP, який робить це внутрішньо. І для чого потрібен фінал, в якому /ти розмістився setcookie?
Марко Демайо

@Marco Demaio: Так, під сервером я мав на увазі php-сервер. Це /шлях до файлів cookie. Вам потрібно встановити його так, щоб ви могли видалити файли cookie з домену, інакше він встановлюється на поточний шлях і впливає лише на ті, які встановлені для поточного шляху.
тикати

@trante Га !? $ key - це не масив, це ключ.
тикати

16

Я погоджуюсь з деякими з наведених вище відповідей. Я б просто рекомендував замінити "time () - 1000" на "1". Значення "1" означає 1 січня 1970 року, що забезпечує 100% термін дії. Тому:

setcookie($name, '', 1);
setcookie($name, '', 1, '/');

1
Я завжди дивувався, чому ніхто не каже просто робити це, і це свого роду відповідь, яку я шукав.
Anther

Можливо, наразі це не проблема, але в один момент деякі браузери проігнорували давно стару дату разом, і значення не відкидатимуться як слід. Я вважаю, що IE 7 - один із прикладів, який це зробив.
conrad10781

3

переконайтеся, що ви викликали свою функцію setcookie, перш ніж на вашому сайті відбуватиметься будь-який вихід.

також, якщо ваші користувачі виходять із системи, вам слід також видалити / анулювати їх змінні сеансу.


2

Коли ви змінюєте назву своїх файлів cookie, ви також можете видалити всі файли cookie, але зберегти один:

if (isset($_COOKIE)) {
    foreach($_COOKIE as $name => $value) {
        if ($name != "preservecookie") // Name of the cookie you want to preserve 
        {
            setcookie($name, '', 1); // Better use 1 to avoid time problems, like timezones
            setcookie($name, '', 1, '/');
        }
    }
}

Також базується на цьому PHP-відповіді


1
Неправильний синтаксис: 1) у конструкції AS немає конструкції AS, якщо пункт 2) замінити "$ cookies" на $ _COOKIE
Джефф,

2

Надані відповіді не вирішили мою проблему,

Це не:

  1. Видалити батьківські файли cookie домену (з abc; видалити bc; cookies),
  2. Видаліть файли cookie з вищого шляху, відмінного від root.

Мій сценарій робить, дивіться.

<?php function unset_cookie($name)
{
    $host = $_SERVER['HTTP_HOST'];
    $domain = explode(':', $host)[0];

    $uri = $_SERVER['REQUEST_URI'];
    $uri = rtrim(explode('?', $uri)[0], '/');

    if ($uri && !filter_var('file://' . $uri, FILTER_VALIDATE_URL)) {
        throw new Exception('invalid uri: ' . $uri);
    }

    $parts = explode('/', $uri);

    $cookiePath = '';
    foreach ($parts as $part) {
        $cookiePath = '/'.ltrim($cookiePath.'/'.$part, '//');

        setcookie($name, '', 1, $cookiePath);

        $_domain = $domain;
        do {
            setcookie($name, '', 1, $cookiePath, $_domain);
        } while (strpos($_domain, '.') !== false && $_domain = substr($_domain, 1 + strpos($_domain, '.')));
    }
}

Це не найкраще / безпечне / оптимальне рішення, тому використовуйте це, лише якщо ви не знаєте шлях до файлу cookie та / або домен cookie. Або скористайтеся ідеєю для того, щоб створити свою версію.


Ідеальне рішення,
Shakeel Ahmed

1

Вам слід знати, що різні інструменти відстеження, такі як Google Analytics, також використовують файли cookie у вашому домені, і ви не хочете їх видаляти, якщо ви хочете мати правильні дані в GA.

Єдиним рішенням, яке я міг запрацювати, було встановити для існуючих файлів cookie значення null. Не вдалося видалити файли cookie з клієнта.

Тому для виходу користувача з системи я використовую наступне:

setcookie("username", null, time()+$this->seconds, "/", $this->domain, 0);
setcookie("password", null, time()+$this->seconds, "/", $this->domain, 0);

Звичайно, це не видаляє ВСІ файли cookie.


7
Я не рекомендую зберігати пароль користувача у файлі cookie. Це серйозна діра в безпеці, особливо зважаючи на 0аргумент, що файл cookie навіть не зашифрований під час передачі.
Andrew Ensley

1

Усі попередні відповіді не враховували, що їх setcookieможна було використовувати з явним доменом. Крім того, файл cookie міг бути встановлений для більш високого субдомену, наприклад, якщо ви знаходитесь у foo.bar.tar.comдомені, можливо, файл cookie встановлений tar.com. Отже, ви хочете скасувати файли cookie для всіх доменів, які могли скинути файл cookie:

$host = explode('.', $_SERVER['HTTP_HOST']);

while ($host) {
    $domain = '.' . implode('.', $host);

    foreach ($_COOKIE as $name => $value) {
        setcookie($name, '', 1, '/', $domain);
    }

    array_shift($host);
}

0

Використовуйте функцію для очищення файлів cookie:

function clearCookies($clearSession = false)
{
    $past = time() - 3600;
    if ($clearSession === false)
        $sessionId = session_id();
    foreach ($_COOKIE as $key => $value)
    {
        if ($clearSession !== false || $value !== $sessionId)
            setcookie($key, $value, $past, '/');
    }
}

Якщо ви перейдете, trueце очистить sessionдані, інакше дані сеансу зберігаються.


0

Я знаю, що це питання давнє, але це набагато простіша альтернатива:

header_remove();

Але будьте обережні! Він видалить ВСІ заголовки, включаючи файли cookie, сеанс тощо, як пояснюється в документах .


це насправді не робить нічого, щоб насправді видалити файли cookie або щось подібне до цього поняття, оскільки браузер просто зберігає будь-які збережені файли cookie до їх закінчення. хоча це допомагає, якщо інші речі намагаються породити файли cookie і заважають їм це робити.
My1

0
<?php
      parse_str(http_build_query($_COOKIE),$arr);
      foreach ($arr as $k=>$v) {
        setCookie("$k","",1000,"/");
      }

Дякуємо за цей фрагмент коду, який може надати обмежену негайну допомогу. Правильне пояснення значно покращило б його довгострокове значення, показавши, чому це гарне рішення проблеми, і зробило б його більш корисним для майбутніх читачів з іншими подібними питаннями. Будь ласка, відредагуйте свою відповідь, щоб додати пояснення, включаючи припущення, які ви зробили.
Максиміліан Пітерс
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.