Bagaimana cara keluar pengguna dari situs web menggunakan otentikasi BASIC?

279

Apakah mungkin untuk logout pengguna dari situs web jika dia menggunakan otentikasi dasar?

Sesi pembunuhan tidak cukup, karena, setelah pengguna diautentikasi, setiap permintaan berisi info masuk, sehingga pengguna secara otomatis login di lain waktu ia mengakses situs menggunakan kredensial yang sama.

Satu-satunya solusi sejauh ini adalah menutup browser, tetapi itu tidak dapat diterima dari sudut pandang kegunaan.

Marko
sumber
1
Hanya penasaran. Mengapa Anda ingin melakukan ini?
DOK
17
Untuk dapat masuk sebagai pengguna yang berbeda.
Marko
16
@DOK - Ini adalah hal peretasan sosial standar: pengguna harus dapat keluar sambil membiarkan peramban terbuka. Misalkan salah satu pengguna Anda mengakses situs di mesin publik? Mereka harus log-off secara eksplisit sehingga pengguna berikutnya tidak dapat mengakses situs seperti mereka.
Keith
@DOK Ada juga masalah yang membuatnya tidak mungkin bagi pengguna untuk keluar dari situs. Server dapat menghapus cookie otorisasi, dan bahkan cookie sesi. Tetapi ketika browser masuk untuk memuat /halaman, mereka akan secara otomatis login lagi.
Ian Boyd
Saya menggunakan metode yang mengirim permintaan palsu untuk keluar, tetapi mengunci pengguna di pelanggan karena ada batasan ketat yang gagal login 3 kali dalam AD. Jadi, sarankan menggunakan metode ini (mengirim permintaan palsu) dengan hati-hati.
Qianchao Pan

Jawaban:

170

Otentikasi dasar tidak dirancang untuk mengelola keluar. Anda dapat melakukannya, tetapi tidak sepenuhnya secara otomatis.

Yang harus Anda lakukan adalah meminta pengguna mengklik tautan logout, dan mengirim tanggapan '401 Tidak Sah', menggunakan ranah yang sama dan pada tingkat folder URL yang sama seperti 401 normal yang Anda kirim meminta login.

Mereka harus diarahkan untuk memasukkan kredensial yang salah selanjutnya, mis. nama pengguna dan kata sandi kosong, dan sebagai tanggapan Anda mengirim kembali halaman "Anda telah berhasil keluar". Kredensial yang salah / kosong kemudian akan menimpa kredensial yang benar sebelumnya.

Singkatnya, skrip logout membalikkan logika skrip login, hanya mengembalikan halaman sukses jika pengguna tidak melewati kredensial yang tepat.

Pertanyaannya adalah apakah kotak kata sandi “jangan masukkan kata sandi” yang agak aneh akan memenuhi penerimaan pengguna. Pengelola kata sandi yang mencoba mengisi kata sandi secara otomatis juga dapat menghalangi di sini.

Sunting untuk menambahkan sebagai tanggapan terhadap komentar: masuk kembali adalah masalah yang sedikit berbeda (kecuali Anda memerlukan logout / login dua langkah jelas). Anda harus menolak (401) upaya pertama untuk mengakses tautan relogin, daripada menerima yang kedua (yang mungkin memiliki nama pengguna / kata sandi lain). Ada beberapa cara Anda bisa melakukan ini. Salah satunya adalah memasukkan nama pengguna saat ini di tautan logout (mis. / Relogin? Nama pengguna), dan menolak ketika kredensial cocok dengan nama pengguna.

bobince
sumber
2
Saya akan mencoba pendekatan ini. Maksud dari logout (dalam hal ini) adalah untuk memungkinkan pengguna untuk masuk sebagai pengguna yang berbeda, jadi itu adalah solusi yang dapat diterima. Adapun kata sandi pengisian otomatis, terserah pengguna apakah ia akan menggunakannya atau tidak. Terima kasih
Marko
Apakah ini masih satu-satunya jalan? Saya telah melakukan implementasi ASP.Net MVC dan jQuery yang berfungsi, tetapi saya masih tidak senang dengannya: stackoverflow.com/questions/6277919
Keith
@Keith: Masih hanya ini dan jawaban systemPAUSE (yang tidak bekerja di semua browser, tetapi lebih halus daripada pendekatan manual ketika itu bekerja).
bobince
16
W3C sangat aktif pada spesifikasi HTML. Tetapi spec HTTP sedang mendekam. W3C seharusnya memperbaiki masalah ini sekitar dua dekade lalu. Dengan meningkatnya penggunaan layanan REST, metode otentikasi asli yang kuat sangat dibutuhkan saat ini.
Dojo
9
Tampaknya ini tidak berfungsi dengan baik di Chrome 46 menjelajah di localhost. Chrome muncul untuk menjaga kata sandi lama (benar) dan kata sandi baru yang Anda tentukan. Setelah menavigasi ke halaman logout, chrome dengan benar menggunakan kata sandi yang baru SAMPAI SAATNYA MENDAPATKAN A 401 TIDAK DIHORMATI HALAMAN DI SITUS ANDA. Setelah 401 pertama, Chrome kembali ke kata sandi lama (benar). Jadi itu benar-benar tidak menghapus kata sandi sejak awal.
vancan1ty
196

Tambahan untuk jawaban oleh bobince ...

Dengan Ajax Anda dapat memiliki tautan / tombol 'Logout' Anda terhubung ke fungsi Javascript. Minta fungsi ini mengirim XMLHttpRequest dengan nama pengguna dan kata sandi yang buruk. Ini akan mendapatkan 401. Kemudian atur document.location kembali ke halaman pra-login. Dengan cara ini, pengguna tidak akan pernah melihat dialog login tambahan selama logout, atau harus ingat untuk memasukkan kredensial yang buruk.

sistem PAUSE
sumber
12
Peretasan bagus, meminta pengguna secara manual memasukkan kredensial buruk mungkin tidak dapat diterima untuk sebagian besar aplikasi web.
BillMan
1
Pastikan saja XMLHttpRequest tidak disetel sebagai tidak sinkron atau Anda mungkin menemukan bahwa pengalihan via akan dilakukan sebelum permintaan logout selesai.
davidjb
5
Anda dapat menggunakan trik yang sama untuk login juga. Dengan begitu Anda dapat menyesuaikan dialog login tanpa harus mengubah metode otentikasi server. Artikel ini memberikan beberapa ide bagus: http://www.peej.co.uk/articles/http-auth-with-html-forms.html
Stijn de Witt
1
@davidjb Karena permintaan sinkron dianggap usang sekarang, solusi alternatif mungkin untuk mengarahkan ulang pengguna dalam panggilan balik permintaan async.
Hayden Schiff
1
David: chrome sekarang mengizinkan ini untuk XHRs, dan saya dapat mengonfirmasi bahwa itu masih berfungsi di kenari chrome. bugs.chromium.org/p/chromium/issues/detail?id=435547
CpnCrunch
192

Minta pengguna mengklik tautan ke https: // log: [email protected]/ . Itu akan menimpa kredensial yang ada dengan yang tidak valid; logout mereka.

Matthew Welborn
sumber
19
Mengapa yang ini tidak mendapatkan lebih banyak upvotes? Sepertinya solusi yang sederhana dan berhasil bagi saya. Adakah masalah yang diketahui dengan pendekatan ini?
amoebe
35
Ini tidak lagi berfungsi di Chrome, yang karena alasan keamanan mengabaikan kredensial dalam URL.
Thom
5
Ini Berhasil untuk saya :) Saya menggunakan Versi Chrome 32.0.1700.102
abottoni
6
masalah: menggunakan versi 39.0 chrome, Ketika saya mengklik tautan logout melalui metode ini, Chrome mengingat kredensial login yang buruk, dan meminta kredensial login baru pada setiap pemuatan halaman, sampai saya pergi ke example.com tanpa kredensial login yang ditentukan, untuk hapus memori chrome.
Scott
4
Hai, saya tidak bisa menggunakannya untuk https di Chrome.
thienkhoi tran
67

Anda dapat melakukannya seluruhnya dalam JavaScript:

IE memiliki (untuk waktu yang lama) API standar untuk membersihkan cache Otentikasi Dasar:

document.execCommand("ClearAuthenticationCache")

Harus mengembalikan true ketika berfungsi. Mengembalikan salah, tidak terdefinisi atau meledak di browser lain.

Peramban baru (per Des 2012: Chrome, FireFox, Safari) memiliki perilaku "ajaib". Jika mereka melihat permintaan autentik dasar yang berhasil dengan sembarang nama pengguna palsu lainnya (katakanlah logout) mereka menghapus cache kredensial dan mungkin menyetelnya untuk nama pengguna palsu baru itu, yang perlu Anda pastikan bukan nama pengguna yang valid untuk melihat konten.

Contoh dasar dari itu adalah:

var p = window.location.protocol + '//'
// current location must return 200 OK for this GET
window.location = window.location.href.replace(p, p + 'logout:password@')

Cara "asinkron" untuk melakukan hal di atas adalah dengan melakukan panggilan AJAX menggunakan logoutnama pengguna. Contoh:

(function(safeLocation){
    var outcome, u, m = "You should be logged out now.";
    // IE has a simple solution for it - API:
    try { outcome = document.execCommand("ClearAuthenticationCache") }catch(e){}
    // Other browsers need a larger solution - AJAX call with special user name - 'logout'.
    if (!outcome) {
        // Let's create an xmlhttp object
        outcome = (function(x){
            if (x) {
                // the reason we use "random" value for password is 
                // that browsers cache requests. changing
                // password effectively behaves like cache-busing.
                x.open("HEAD", safeLocation || location.href, true, "logout", (new Date()).getTime().toString())
                x.send("")
                // x.abort()
                return 1 // this is **speculative** "We are done." 
            } else {
                return
            }
        })(window.XMLHttpRequest ? new window.XMLHttpRequest() : ( window.ActiveXObject ? new ActiveXObject("Microsoft.XMLHTTP") : u ))
    }
    if (!outcome) {
        m = "Your browser is too old or too weird to support log out functionality. Close all windows and restart the browser."
    }
    alert(m)
    // return !!outcome
})(/*if present URI does not return 200 OK for GET, set some other 200 OK location here*/)

Anda juga dapat menjadikannya bookmarklet:

javascript:(function(c){var a,b="You should be logged out now.";try{a=document.execCommand("ClearAuthenticationCache")}catch(d){}a||((a=window.XMLHttpRequest?new window.XMLHttpRequest:window.ActiveXObject?new ActiveXObject("Microsoft.XMLHTTP"):void 0)?(a.open("HEAD",c||location.href,!0,"logout",(new Date).getTime().toString()),a.send(""),a=1):a=void 0);a||(b="Your browser is too old or too weird to support log out functionality. Close all windows and restart the browser.");alert(b)})(/*pass safeLocation here if you need*/);

ddotsenko
sumber
1
Apakah ini memerlukan penanganan sisi- logoutpengguna khusus untuk nama pengguna dan / atau URL logout?
ulidtko
1
@ Dulidko Tidak, seharusnya tidak - semua penanganan adalah sisi klien. Satu-satunya situasi yang memerlukan penanganan khusus adalah jika pengguna yang dipanggil logoutkebetulan ada dan kebetulan memiliki kata sandi yang dihasilkan. Dalam kasus yang jarang terjadi, ubah ID pengguna menjadi yang tidak ada di sistem Anda.
davidjb
2
Saya menggunakan bookmarklet di atas hari ini dan saya bekerja dengan baik.
David Gleba
Saya menggunakan ini dan itu berhasil untuk Chrome dan FF. Saya hanya perlu melakukan "GET" tambahan pada halaman logout.php saya untuk menghapus $ _SESSION.
urban
2
Bookmarklet juga berfungsi di Edge. Cukup gunakan dengan<a href='javascript:......need*/);'>Logout</a>
Eric
21

Fungsi berikut ini dikonfirmasikan berfungsi untuk Firefox 40, Chrome 44, Opera 31 dan IE 11.
Bowser digunakan untuk deteksi browser, jQuery juga digunakan.

- secUrl adalah url ke area yang dilindungi kata sandi tempat untuk keluar.
- redirUrl adalah url ke area yang tidak dilindungi kata sandi (halaman kesuksesan logout).
- Anda mungkin ingin menambah pengalihan waktu (saat ini 200 ms).

function logout(secUrl, redirUrl) {
    if (bowser.msie) {
        document.execCommand('ClearAuthenticationCache', 'false');
    } else if (bowser.gecko) {
        $.ajax({
            async: false,
            url: secUrl,
            type: 'GET',
            username: 'logout'
        });
    } else if (bowser.webkit) {
        var xmlhttp = new XMLHttpRequest();
        xmlhttp.open("GET", secUrl, true);
        xmlhttp.setRequestHeader("Authorization", "Basic logout");
        xmlhttp.send();
    } else {
        alert("Logging out automatically is unsupported for " + bowser.name
            + "\nYou must close the browser to log out.");
    }
    setTimeout(function () {
        window.location.href = redirUrl;
    }, 200);
}

mthoring
sumber
ini adalah jawaban paling komprehensif
belidzs
Apakah ada alasan untuk $.ajaxvarian sinkron ( async: false) dan xmlhttpvarian asinkron ( truedalam open())?
Bowi
1
Chrome sekarang menggunakan mesin rendering Blink, sehingga Anda harus mengubah (bowser.gecko)ke (bowser.gecko || bowser.blink).
Bowi
1
Mengapa gecko / blink menggunakan $.ajaxdan menggunakan webkit new XMLHttpRequest? Tidakkah tokek / blink dapat melakukannya XMLHttpRequestdan webkit juga bisa melakukannya $.ajax? Saya bingung.
RemyNL
11

Berikut ini adalah contoh Javascript yang sangat sederhana menggunakan jQuery:

function logout(to_url) {
    var out = window.location.href.replace(/:\/\//, '://log:out@');

    jQuery.get(out).error(function() {
        window.location = to_url;
    });
}

Pengguna log ini keluar tanpa menunjukkan kotak log-in browser lagi, lalu mengarahkannya ke halaman yang sudah keluar

Romuald Brunet
sumber
1
window.location = window.location.href.replace (/: \ / \ //, ': // log: out @');
sebhaase
10

Ini tidak mungkin secara langsung dengan Otentikasi-Dasar.

Tidak ada mekanisme dalam spesifikasi HTTP untuk server untuk memberitahu browser untuk berhenti mengirim kredensial yang sudah disajikan pengguna.

Ada "retasan" (lihat jawaban lain) yang biasanya melibatkan penggunaan XMLHttpRequest untuk mengirim permintaan HTTP dengan kredensial yang salah untuk menimpa yang semula disediakan.

Alnitak
sumber
12
Dalam teori. Latihan membuktikan sebaliknya sebagaimana dapat dilihat dari jawaban lain.
Stijn de Witt
2
Dan seperti yang Anda juga dapat melihat dari jawaban lain, tidak dengan cara yang dapat diandalkan, konsisten dan gagal-aman!
jplandrain
5

Ini berfungsi untuk IE / Netscape / Chrome:

      function ClearAuthentication(LogOffPage) 
  {
     var IsInternetExplorer = false;    

     try
     {
         var agt=navigator.userAgent.toLowerCase();
         if (agt.indexOf("msie") != -1) { IsInternetExplorer = true; }
     }
     catch(e)
     {
         IsInternetExplorer = false;    
     };

     if (IsInternetExplorer) 
     {
        // Logoff Internet Explorer
        document.execCommand("ClearAuthenticationCache");
        window.location = LogOffPage;
     }
     else 
     {
        // Logoff every other browsers
    $.ajax({
         username: 'unknown',
         password: 'WrongPassword',
             url: './cgi-bin/PrimoCgi',
         type: 'GET',
         beforeSend: function(xhr)
                 {
            xhr.setRequestHeader("Authorization", "Basic AAAAAAAAAAAAAAAAAAA=");
         },

                 error: function(err)
                 {
                    window.location = LogOffPage;
             }
    });
     }
  }


  $(document).ready(function () 
  {
      $('#Btn1').click(function () 
      {
         // Call Clear Authentication 
         ClearAuthentication("force_logout.html"); 
      });
  });          
Claudio
sumber
5

Ini sebenarnya cukup sederhana.

Cukup kunjungi yang berikut ini di browser Anda dan gunakan kredensial yang salah: http: // username: [email protected]

Itu harus "mengeluarkan Anda".

Chiedo
sumber
1
Tetapi pengguna harus menjadi pengguna NYATA, selain itu saya mendapat "401 Tidak Sah", tetapi dengan menggunakan tombol BACK saya dapat terus bekerja sebagai pengguna yang sebelumnya dicatat. Diuji pada server web Abyss X1 (2.11.1)
user2956477
1
Jawaban rangkap (lihat Matthew Welborn di atas).
Skippy le Grand Gourou
3

Yang Anda butuhkan hanyalah mengarahkan pengguna pada beberapa URL logout dan mengembalikan 401 Unauthorizedkesalahan padanya. Pada halaman kesalahan (yang harus dapat diakses tanpa auth dasar) Anda perlu memberikan tautan lengkap ke halaman rumah Anda (termasuk skema dan nama host). Pengguna akan mengklik tautan ini dan browser akan meminta kredensial lagi.

Contoh untuk Nginx:

location /logout {
    return 401;
}

error_page 401 /errors/401.html;

location /errors {
    auth_basic off;
    ssi        on;
    ssi_types  text/html;
    alias /home/user/errors;
}

Halaman kesalahan /home/user/errors/401.html:

<!DOCTYPE html>
<p>You're not authorised. <a href="<!--# echo var="scheme" -->://<!--# echo var="host" -->/">Login</a>.</p>
Envek
sumber
Saya akan lebih menyarankan menggunakan http_hostdi 401.htmlbukan hanya host, sebagai mantan juga menambahkan nomor port (dalam kasus port non-standar yang digunakan)
Emil Koutanov
2
function logout() {
  var userAgent = navigator.userAgent.toLowerCase();

  if (userAgent.indexOf("msie") != -1) {
    document.execCommand("ClearAuthenticationCache", false);
  }

  xhr_objectCarte = null;

  if(window.XMLHttpRequest)
    xhr_object = new XMLHttpRequest();
  else if(window.ActiveXObject)
    xhr_object = new ActiveXObject("Microsoft.XMLHTTP");
  else
    alert ("Your browser doesn't support XMLHTTPREQUEST");

  xhr_object.open ('GET', 'http://yourserver.com/rep/index.php', false, 'username', 'password');
  xhr_object.send ("");
  xhr_object = null;

  document.location = 'http://yourserver.com'; 
  return false;
}
Charlie
sumber
2
 function logout(url){
    var str = url.replace("http://", "http://" + new Date().getTime() + "@");
    var xmlhttp;
    if (window.XMLHttpRequest) xmlhttp=new XMLHttpRequest();
    else xmlhttp=new ActiveXObject("Microsoft.XMLHTTP");
    xmlhttp.onreadystatechange=function()
    {
        if (xmlhttp.readyState==4) location.reload();
    }
    xmlhttp.open("GET",str,true);
    xmlhttp.setRequestHeader("Authorization","Basic xxxxxxxxxx")
    xmlhttp.send();
    return false;
}
Sushovan Mukherjee
sumber
2

Berdasarkan apa yang saya baca di atas, saya mendapat solusi sederhana yang berfungsi di browser apa pun:

1) pada halaman logout Anda, Anda memanggil ajax ke bagian login Anda Bagian belakang login Anda harus menerima pengguna logout. Setelah bagian belakang menerima, browser menghapus pengguna saat ini dan mengasumsikan pengguna "logout".

$.ajax({
    async: false,
    url: 'http://your_login_backend',
    type: 'GET',
    username: 'logout'
});      

setTimeout(function () {
    window.location.href = 'http://normal_index';
}, 200);

2) Sekarang ketika pengguna kembali ke file indeks normal itu akan mencoba untuk masuk secara otomatis dalam sistem dengan pengguna "logout", pada kali kedua ini Anda harus memblokirnya dengan membalas dengan 401 untuk memunculkan dialog login / kata sandi.

3) Ada banyak cara untuk melakukan itu, saya membuat dua ujung belakang login, satu menerima pengguna logout dan satu lagi tidak. Halaman login normal saya menggunakan yang tidak menerima, halaman logout saya menggunakan yang menerimanya.

Isi
sumber
2

Saya baru saja menguji yang berikut di Chrome (79), Firefox (71) dan Edge (44) dan berfungsi dengan baik. Itu berlaku solusi skrip seperti yang disebutkan di atas.

Cukup tambahkan tautan "Logout" dan ketika diklik kembalikan html berikut

    <div>You have been logged out. Redirecting to home...</div>    

<script>
    var XHR = new XMLHttpRequest();
    XHR.open("GET", "/Home/MyProtectedPage", true, "no user", "no password");
    XHR.send();

    setTimeout(function () {
        window.location.href = "/";
    }, 3000);
</script>
Teo Bebekis
sumber
1

JavaScript ini harus berfungsi untuk semua browser versi terbaru:

//Detect Browser
var isOpera = !!window.opera || navigator.userAgent.indexOf(' OPR/') >= 0;
    // Opera 8.0+ (UA detection to detect Blink/v8-powered Opera)
var isFirefox = typeof InstallTrigger !== 'undefined';   // Firefox 1.0+
var isSafari = Object.prototype.toString.call(window.HTMLElement).indexOf('Constructor') > 0;
    // At least Safari 3+: "[object HTMLElementConstructor]"
var isChrome = !!window.chrome && !isOpera;              // Chrome 1+
var isIE = /*@cc_on!@*/false || !!document.documentMode; // At least IE6
var Host = window.location.host;


//Clear Basic Realm Authentication
if(isIE){
//IE
    document.execCommand("ClearAuthenticationCache");
    window.location = '/';
}
else if(isSafari)
{//Safari. but this works mostly on all browser except chrome
    (function(safeLocation){
        var outcome, u, m = "You should be logged out now.";
        // IE has a simple solution for it - API:
        try { outcome = document.execCommand("ClearAuthenticationCache") }catch(e){}
        // Other browsers need a larger solution - AJAX call with special user name - 'logout'.
        if (!outcome) {
            // Let's create an xmlhttp object
            outcome = (function(x){
                if (x) {
                    // the reason we use "random" value for password is 
                    // that browsers cache requests. changing
                    // password effectively behaves like cache-busing.
                    x.open("HEAD", safeLocation || location.href, true, "logout", (new Date()).getTime().toString())
                    x.send("");
                    // x.abort()
                    return 1 // this is **speculative** "We are done." 
                } else {
                    return
                }
            })(window.XMLHttpRequest ? new window.XMLHttpRequest() : ( window.ActiveXObject ? new ActiveXObject("Microsoft.XMLHTTP") : u )) 
        }
        if (!outcome) {
            m = "Your browser is too old or too weird to support log out functionality. Close all windows and restart the browser."
        }
        alert(m);
        window.location = '/';
        // return !!outcome
    })(/*if present URI does not return 200 OK for GET, set some other 200 OK location here*/)
}
else{
//Firefox,Chrome
    window.location = 'http://log:out@'+Host+'/';
}
Amit Shah
sumber
1

tambahkan ini ke aplikasi Anda:

@app.route('/logout')
def logout():
    return ('Logout', 401, {'WWW-Authenticate': 'Basic realm="Login required"'})
Amir Mofakhar
sumber
lebih baik menggunakan pengembalian ini: kembali ('Logout', 401)
Amir Mofakhar
1

ketik chrome://restartbilah alamat dan chrome, dengan semua aplikasi yang berjalan di latar belakang, akan dimulai ulang dan cache kata sandi Auth akan dibersihkan.

Ali
sumber
1

Sebagai catatan, ada Header HTTP Response baru yang disebut Clear-Site-Data. Jika balasan server Anda menyertakan Clear-Site-Data: "cookies"tajuk, maka kredensial otentikasi (tidak hanya cookie) harus dihapus. Saya mengujinya di Chrome 77 tetapi peringatan ini muncul di konsol:

Clear-Site-Data header on 'https://localhost:9443/clear': Cleared data types:
"cookies". Clearing channel IDs and HTTP authentication cache is currently not
supported, as it breaks active network connections.

Dan kredensial auth tidak dihapus, jadi ini tidak berfungsi (untuk saat ini) untuk menerapkan logout auth dasar, tapi mungkin di masa depan akan. Tidak menguji pada browser lain.

Referensi:

https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Clear-Site-Data

https://www.w3.org/TR/clear-site-data/

https://github.com/w3c/webappsec-clear-site-data

https://caniuse.com/#feat=mdn-http_headers_clear-site-data_cookies

Nahuel Greco
sumber
1

Mengirim https://invalid_login@hostnameberfungsi dengan baik di mana saja kecuali Safari di Mac (well, tidak mencentang Edge tetapi juga berfungsi di sana).

Logout tidak berfungsi di Safari ketika pengguna memilih 'ingat kata sandi' di sembulan HTTP Otentikasi Dasar. Dalam hal ini kata sandi disimpan di Akses Keychain (Finder> Aplikasi> Utilitas> Akses Keychain (atau CMD + SPACE dan ketik "Akses Keychain")). Mengirim https://invalid_login@hostnametidak mempengaruhi Akses Keychain, jadi dengan kotak centang ini tidak mungkin untuk logout di Safari pada Mac. Setidaknya itu cara kerjanya untuk saya.

MacOS Mojave (10.14.6), Safari 12.1.2.

Kode di bawah ini berfungsi dengan baik untuk saya di Firefox (73), Chrome (80) dan Safari (12). Ketika pengguna menavigasi ke halaman logout kode dieksekusi dan menjatuhkan kredensial.

    //It should return 401, necessary for Safari only
    const logoutUrl = 'https://example.com/logout'; 
    const xmlHttp = new XMLHttpRequest();
    xmlHttp.open('POST', logoutUrl, true, 'logout');
    xmlHttp.send();

Juga karena suatu alasan Safari tidak menyimpan kredensial dalam sembulan HTTP Otentikasi Dasar bahkan ketika 'ingat kata sandi' dipilih. Browser lain melakukan ini dengan benar.

Fogus
sumber
0
  • gunakan ID sesi (cookie)
  • membatalkan ID sesi di server
  • Jangan terima pengguna dengan ID sesi yang tidak valid
Tomalak
sumber
Juga baik untuk menawarkan Otentikasi Dasar sebagai skema masuk cadangan saat cookie tidak tersedia.
bobince
0

Saya memperbarui solusi mthoring untuk versi Chrome modern:

function logout(secUrl, redirUrl) {
    if (bowser.msie) {
        document.execCommand('ClearAuthenticationCache', 'false');
    } else if (bowser.gecko) {
        $.ajax({
            async: false,
            url: secUrl,
            type: 'GET',
            username: 'logout'
        });
    } else if (bowser.webkit || bowser.chrome) {
        var xmlhttp = new XMLHttpRequest();
        xmlhttp.open(\"GET\", secUrl, true);
        xmlhttp.setRequestHeader(\"Authorization\", \"Basic logout\");\
        xmlhttp.send();
    } else {
// http://stackoverflow.com/questions/5957822/how-to-clear-basic-authentication-details-in-chrome
        redirUrl = url.replace('http://', 'http://' + new Date().getTime() + '@');
    }
    setTimeout(function () {
        window.location.href = redirUrl;
    }, 200);
}
Maks
sumber
-1
    function logout(secUrl, redirUrl) {
        if (bowser.msie) {
            document.execCommand('ClearAuthenticationCache', 'false');
        } else if (bowser.gecko) {
            $.ajax({
                async: false,
                url: secUrl,
                type: 'GET',
                username: 'logout'
            });
        } else if (bowser.webkit) {
            var xmlhttp = new XMLHttpRequest();
            xmlhttp.open("GET", secUrl, true);
            xmlhttp.setRequestHeader("Authorization", "Basic logout");
            xmlhttp.send();
        } else {
            alert("Logging out automatically is unsupported for " + bowser.name
                + "\nYou must close the browser to log out.");
        }
        setTimeout(function () {
            window.location.href = redirUrl;
        }, 200);
    }

sumber