Socket.io: Beberapa soket terbuka setelah tersambung kembali

Dibuat pada 28 Jul 2011  ·  54Komentar  ·  Sumber: socketio/socket.io

Saya telah memperhatikan ini baik di aplikasi socket.io saya dan orang lain. Saat koneksi ulang terjadi, biasanya lebih dari satu soket dalam klien terbuka, yang seharusnya tidak pernah terjadi.

Berikut adalah log yang saya dapatkan dari aplikasi pengujian saya sendiri ketika saya memutus / menyambungkan kembali.

** Putuskan hubungan* * Berhubungan kembali dengan penundaan 1000 Upaya: 1
** Berhubungan kembali dengan penundaan 2000 Percobaan: 2* * Menghubungkan dengan xhr-polling
** Menghubungkan dengan xhr-polling* * Berhubungan kembali dengan jenis transportasi xhr-polling Upaya: 2
** Terhubung* * Terhubung

Ketika ini terjadi, saya mendapatkan pesan duplikat yang dikirim, satu untuk setiap soket yang terhubung, meskipun seharusnya hanya ada satu. Dikonfirmasi oleh Firebug bahwa pada kenyataannya ada dua soket dari klien yang terhubung. Tebakan terbaik saya adalah bahwa ini ada dalam kode klien, mungkin tidak menutup upaya penyambungan kembali yang pertama.

Tentu saja, pertanyaan sebenarnya mungkin adalah mengapa ada keterputusan di tempat pertama?

Socket.IO client bug

Komentar yang paling membantu

Menyelidiki ini sedikit lebih jauh, sepertinya saya menemukan apa yang menyebabkan masalah saya. Ini bukan bug , tetapi implementasi yang salah dari kode sisi klien dari bagian saya. facepalm Inilah yang awalnya saya miliki:

MASALAH:

var socket = io.connect();

socket.on('connect', function () {

  console.log('User connected!');

  socket.on('message', function(message) {

    console.log(message);

  });

});

JavaScript sisi klien di atas menyebabkan beberapa panggilan ke console.log () saat klien tersambung kembali. Inilah yang saya ganti dengan yang di atas:

LARUTAN:

var socket = io.connect();

socket.on('connect', function () {

  console.log('User connected!');

});

socket.on('message', function(message) {

  console.log(message);

});

Sekarang, beberapa pesan tidak dikirim bolak-balik saat klien tersambung kembali ke server. Adakah yang bisa memastikan bahwa perubahan kode sisi klien mereka memperbaiki masalah?

Semua 54 komentar

Putus sambungan dipicu karena secara teknis, klien telah terputus dari server. Dan terputus hingga acara menyambungkan kembali diaktifkan lagi.

Tapi sisanya adalah bug.

Saya rasa ini juga merupakan penyebab bug di aplikasi saya -

Di sisi server, saya telah membuat kursor berekor pada mongodb untuk diaktifkan setiap kali ada sisipan baru. Pesan ini kemudian dikirim melalui io.sockets.emit () ke semua orang yang terhubung.

Tetapi alih-alih hanya menerima satu pesan per acara, saya mendapatkan beberapa pesan berulang di sisi klien.

Saya menggunakan koneksi internet yang sangat tidak dapat diandalkan, jadi tebakan saya adalah bug ini juga memengaruhi kode saya.

Apakah kalian menggunakan expressjs? Saya memiliki masalah ini dengan mengungkapkan, menulis ulang tanpa dan bekerja dengan baik.

Express sama sekali tidak ada hubungannya dengan @mfkp ini, pasti melakukan sesuatu yang aneh

Setuju dengan @visionmedia , ini bug di socket.io bukan dengan Express. Karena penerapan hubungkan ulang saat ini masih dirancang untuk 0,6, sehingga beberapa pemeriksaan dan pembersihan hilang.

Ah, begitu. Tidak apa-apa, lanjutkan ;-)

+1 untuk ini. Masalah intermiten di aplikasi obrolan kami di mana socket.io membuka banyak koneksi. Klien kemudian menerima dupes dari semua emisi.

+1. Websockets & chrome. Laptop pergi tidur -> aplikasi terhubung kembali setelah wakup -> acara ganda. Hanya terjadi saat menghubungkan ke server jauh. Tidak dapat mereproduksi ini secara lokal, pasti ada masalah koneksi ulang / jaringan.

apakah ada solusi untuk menghilangkan beberapa koneksi setelah ini ?, misalnya dari sisi klien, jika saya menggunakan socket.disconnect (), apakah akan memutuskan semua koneksi? Karena saya ingin menghindari banyak pembaruan. apakah mengikuti bekerja?
socket = io.connect (url)
socket.on ('hubungkan', function () {
if (multipleConnect) {
socket.disconnect ();
socket.removeAllListeners ('terhubung');
io.sockets = {};
socket = io.connect (url);
socket.on ('terhubung', functionToConnect);
}
})

Harap baca https://github.com/LearnBoost/socket.io/issues/474#issuecomment -2833227 ini.
Ini menjelaskan mengapa bug ini terjadi dan bagaimana itu dapat direproduksi.

@ 3rd-Eden - Adakah ide di mana perbaikan ini termasuk dalam daftar rencana / prioritas Anda? Saya memiliki aplikasi yang sedang saya buat dan saya berencana menggunakannya untuk itu, dan ingin sekali memberi tahu klien saya bahwa aplikasi itu akan tersambung kembali dengan benar dari perangkat iOS. Ini terputus setelah aplikasi diletakkan di latar belakang atau perangkat dalam mode tidur.

Atau apakah Anda tahu tentang bagaimana saya dapat membuat kode solusi? Saya telah mengerjakan beberapa hal selama beberapa hari terakhir, tetapi kasus terbaik sepertinya selalu membiarkan terlalu banyak koneksi terbuka dan menjatuhkan semua soket yang disimpan data. Data bukanlah akhir dunia. Saya dapat menggunakan pemicu menyambungkan kembali dari klien untuk memecahkan masalah itu, tetapi koneksi bersamaan agak jelek.

Terima kasih!

@cris Saya tidak yakin bahwa ini adalah bug yang sama yang Anda sebutkan. Saya memiliki contoh bug yang sangat sederhana tanpa perlambatan di server.

Saya dapat dengan jelas mereproduksi masalah ini dengan:

  1. Menerapkan klien detak jantung sederhana yang mengirimkan detak jantung dalam interval 1 detik.
  2. Hitung jumlah sisi server koneksi baru.
  3. Hitung jumlah pemutusan sisi server.
  4. Mulai server dan buat koneksi dengan klien.
  5. Putuskan koneksi jaringan antara klien dan server.
  6. Tunggu hingga server kehabisan waktu dan mengeluarkan peristiwa pemutusan hubungan.
  7. Hubungkan kembali koneksi jaringan.

Perhatikan bahwa ketika klien menghubungkan kembali itu membuat 2-4 koneksi yang memancarkan acara 'terhubung' untuk masing-masing. Server menerima 2-4 koneksi dari klien dan memancarkan peristiwa 'koneksi' untuk masing-masing koneksi. Klien tidak pernah menutup koneksi yang salah dimulai.

Terima kasih. Menurut saya bug ini harus menjadi prioritas. Banyak perusahaan komersial yang tidak tahu apa-apa mencoba mempekerjakan orang untuk mengembangkan kerangka kerja socket.io, berpikir itu bekerja dengan baik. Memang, socket.io gratis, jadi mungkin perusahaan komersial ini harus mulai melihat produk komersial. Tetapi sekali lagi, saya pikir ini benar-benar perlu diprioritaskan sebagai prioritas yang sangat tinggi. Bug ini sudah ada sejak 0.7.0 dan mudah direproduksi.

@dwi_dwi Saya sudah memperbaiki masalah ini untuk saya sejak lama, dan berfungsi tanpa keributan.

Untuk memperbaikinya, Anda harus:

  1. Terapkan tambalan ini: https://github.com/LearnBoost/socket.io-client/pull/342
  2. Nonaktifkan AJAX-handshake (dan biarkan handshake menjadi hanya melalui JSONP), seperti yang dijelaskan dalam komentar pull-request.

Bagaimana Anda menonaktifkan jabat tangan AJAX? Saya berasumsi Anda masih dapat menggunakan semua jenis koneksi, ini hanya akan mempengaruhi jabat tangan?

+1 tolong perbaiki ini :)

Saya memiliki beberapa koneksi yang sama pada masalah koneksi ulang. Saya pikir ini adalah masalah yang parah ...
Penyebabnya adalah bahwa metode Socket.connect dipanggil tetapi flag conneting hanya disetel ke true setelah handshake selesai, jika salah satu timer matbeReconnect (timer yang menangani reconnect) bangun selama proses handshake, mereka akan memanggil Socket. terhubung lagi menyebabkan beberapa koneksi ulang.
Saya telah memecahkan masalah ini dengan memanggil self.reconnecting di awal metode Socket.connect.

Ada peluang untuk menggabungkan ini?
Bug ini juga membuat bug buruk di aplikasi saya.

Bug ini masih ada. Mencoba kedua tambalan. Tidak berhasil.

+1 Saya sering mengalami masalah ini saat menggunakan xhr-polling. Saya belum mencoba patchnya

+1, Saya juga mengalami masalah ini dengan sambungan ulang duplikat.

Setiap kali Node.js di-restart (yaitu ketika menjalankan melalui supervisor), klien saya menghubungkan kembali X kali berapa kali Node.js telah dimulai ulang dari titik di mana klien terhubung pada awalnya. Bug menyebabkan acara dipancarkan sekali per sambungan ulang dari sisi klien - ini bukan hanya masalah duplikat.

Saya mencoba socket.on('disconnect', function() { socket.disconnect(); }); di sisi klien, tetapi tidak berhasil. : /

Menyelidiki ini sedikit lebih jauh, sepertinya saya menemukan apa yang menyebabkan masalah saya. Ini bukan bug , tetapi implementasi yang salah dari kode sisi klien dari bagian saya. facepalm Inilah yang awalnya saya miliki:

MASALAH:

var socket = io.connect();

socket.on('connect', function () {

  console.log('User connected!');

  socket.on('message', function(message) {

    console.log(message);

  });

});

JavaScript sisi klien di atas menyebabkan beberapa panggilan ke console.log () saat klien tersambung kembali. Inilah yang saya ganti dengan yang di atas:

LARUTAN:

var socket = io.connect();

socket.on('connect', function () {

  console.log('User connected!');

});

socket.on('message', function(message) {

  console.log(message);

});

Sekarang, beberapa pesan tidak dikirim bolak-balik saat klien tersambung kembali ke server. Adakah yang bisa memastikan bahwa perubahan kode sisi klien mereka memperbaiki masalah?

Hai. Saya memiliki masalah yang sama. Ketika saya me-restart node (atau ketika koneksi time-out) dan klien terhubung kembali, saya menerima pesan yang sama yang dipancarkan oleh server pada waktu n (di mana n adalah jumlah koneksi ulang).
Saya menyelesaikan ini dengan memindahkan semua penangan saya dari dalam socket.on ('connect' function () {...}); berfungsi di luar itu.

Kode di atas melakukan apa yang diperlukan.
Ini jawaban lengkap saya dari milis:
https://groups.google.com/forum/?hl=id&fromgroups#!topic/socket_io/X9FRMjCkPco

@xdanx , luar biasa, terima kasih atas balasannya.

ya, ini tampaknya berfungsi untuk saya juga: meletakkan kode socket.on ('message') terpisah dari kode acara 'menghubungkan'

Tapi bagaimana dengan "Connection"?
Dan bagaimana dengan objek "socket" di callback?

/ edit Nevermind, saya mengerti, 'connect' ada di klien. Saya masih mendapatkan masalah dengan menghubungkan kembali spamming ketika saya tidak melakukannya. Tapi itu di 0.9.6

Saya tampaknya memiliki masalah yang sama juga ... Mencoba perbaikan di atas untuk memindahkan kode pesan ke blok terpisah .. tetapi perhatikan bahwa saya tidak pernah memilikinya bersama.

ada berita tentang solusi lain untuk ini di 0.9.8?

Saya memiliki masalah yang sama. Saya menginstal 0.9.10. Ada cara untuk memperbaikinya? :(
btw sudah 1+ tahun dan belum ada perbaikan .. :(

EDIT.

Masalahnya sepertinya hilang ketika saya hanya menggunakan jsonp-polling.
io.set ('transports', ['jsonp-polling']);

Saya memiliki masalah yang sama.
stopkontak. [email protected]
node v0.8.8

@semprom Saya pikir menggunakan jsonp-polling memperbaikinya karena mungkin relevan dengan koneksi websocket saja.

Sayangnya bagi saya, seluruh jenis penerapan saya bergantung pada umpan balik secepat mungkin, jadi websockets sebagai lawan polling berfungsi paling baik, Dan karena saya mengendalikan klien yang terhubung, saya tidak melihat alasan kecuali untuk masalah ini untuk pindah ke apa pun lain.

Perhatikan bahwa beberapa sambungan dari klien yang sama yang menyambungkan kembali memiliki socket.id . Jadi Anda dapat mempertahankan daftar id soket Anda sendiri dan mengabaikan duplikat untuk mengatasi masalah ini.

@KasTann Terima kasih. Ini memecahkan masalah ini.

@esanai Tidak masalah, senang itu berhasil!

Hai, Saya memiliki masalah yang sama dan saya perhatikan bahwa setiap kali sambungan tersambung kembali, ID soket klien baru dibuat. Solusinya adalah menggunakan io.set ('transports', ['jsonp-polling']); atau gunakan solusi KasperTidemann?

@KasTidemann Ya ampun, itulah jawaban dari masalah saya! Lihat komit ini: https://github.com/samuelclay/NewsBlur/commit/76cb E5E5E5d8b2a787985bba724dc3562108492b017#L2L3887

Saya dapat mereproduksi acara koneksi ganda setelah kesalahan koneksi sesuka hati dengan kode klien dan server sederhana ini dalam satu file node.js:

"use strict";

var server = require('socket.io');
var client = require('socket.io-client');

setTimeout(function () {
    var io = server.listen(8888);

    io.of('/chat').on('connection', function (socket) {
        console.log('Server: /chat connection');
        socket.emit('greeting', 'Hello, who are you?');
    });

    io.sockets.on('connection', function (socket) {
        console.log('Server: connection');
    });
}, 2000);

var socketAddress = 'http://localhost:8888/chat';
var socket = client.connect(socketAddress);

socket.on('connect', function () {
    console.log("Client: connect");
});

socket.on('greeting', function (data) {
    console.log("Client: greeting: ", data);
});

socket.on('error', function () {
    console.log("Client: error");
    socket.socket.reconnect();
});

Adakah pekerjaan yang sudah terlihat atau diperbaiki?

Maaf, saya juga memposting ini ke edisi # 474.

Saya dapat mereproduksi kesalahan ini secara konsisten menggunakan iPhone dengan iOS 9.3.2 dan Chrome Versi 50.0.2661.95 dan di Safari untuk iOS dengan Socket.IO versi 1.4.6

Saya hanya dapat mereproduksi ini di ponsel dan halaman saya tergantung pada permintaan ke socket.io.

Saya memiliki .on sederhana ('connect', function (socket) {console.log ('Connected');}); dan log Connected dua kali ketika kesalahan terjadi yang membuat saya percaya itu mencoba membuka beberapa koneksi soket pada saat yang sama.

screenshot 2016-05-27 13 03 44

Apakah ada yang tahu solusi untuk ini?

Mengapa masalah ini ditutup ??

Kode contoh saya tanggal 14 April 2014 di atas tidak lagi menghasilkan peristiwa koneksi ganda. Ada acara koneksi untuk '/ chat' dan satu untuk soket itu sendiri. Yang sepertinya masuk akal.

Juga tidak ada kesalahan bahkan di klien lagi.

Ini dengan socket.io 1.4.8 dan node 6.3.0.

Bug ini mempengaruhi saya atm.

Rupanya, ketika socket_handlers adalah placeD dengan rute, mereka dipanggil beberapa kali. Gunakan koneksi soket dalam app.js dan minta penangan dalam koneksi soket, teruskan soket sebagai parameter. Perhatikan bahwa beberapa properti mungkin tidak dikirimkan bersama dengan contoh soket

@leemlwando tolong buka terbitan baru jika perlu.

Saya memiliki masalah yang sama dengan apa yang saya lakukan adalah membuat fungsi koneksi ulang manual pada klien dan memanggil io.destroy (); di dalam fungsi sambungkan kembali ini memperbaiki masalah.

Terima kasih banyak @leemlwando Komentar terakhir Anda membuat saya memecahkan masalah saya.

Saya masih mendapatkan bug ini, apakah ada pembaruan?

Saya pikir satu-satunya bug di sini adalah bahwa internet penuh dengan kode contoh yang buruk di mana panggilan socket.on () dibungkus di dalam handler socket.on ('connect'). Setiap kali soket terhubung kembali, contoh baru dari penangan ditumpuk di atas yang sudah ada dan ini menghasilkan banyak panggilan pada setiap kejadian. Jangan lakukan ini: melihat balasan @KasperTidemann 's dari 25 Jul 2012.

Mungkin DrLexO, kecuali kode yang saya sajikan di atas menunjukkan masalahnya. Tidak ada socket.on () yang dibungkus di dalam handler socket.on ('connect').

Setelah bertahun-tahun saya terkejut masih diberitahu tentang bug ini. Saya tidak tahu apakah itu masih atau tidak. Apakah saya harus mencobanya lagi?

@KasTidemann terima kasih, itu benar-benar menyelesaikan masalah.

Bagaimana Anda dapat menentukan event listener _outside_ dari connect listener jika Anda tidak memiliki akses ke socket ?

const app = express();
const http = require('http').createServer(app);
const io = require('socket.io')(http);

io.on('connect', function(socket) {

  // only now that we are inside the connect callback do we have access to the socket

  socket.on('join', function(room, user) {
  });

  socket.on('add_message', function(room, user) {
  });

  socket.on('disconnect', function(room, user) {
  });
});

Orang-orang tampaknya menyarankan bahwa pendengar acara ( join , add_message dan disconnect ) harus hidup mandiri, _outside_ pendengar connect , tetapi bagaimana mungkin tanpa socket sedang ditentukan?

io.on('connect', function(socket) {
  // socket is only available here
});

// socket is undefined here

socket.on('join', function(room, user) {
});

socket.on('add_message', function(room, user) {
});

socket.on('disconnect', function(room, user) {
});

Apakah ada cara lain untuk membuat instance socket sehingga ini mungkin?

Mengapa ini ditutup? @ michael-lynch memiliki poin yang valid

Saya juga ingin mengetahui jawaban atas poin @ michael-lynch.

@ DrLex0 pada contoh situs web socket.io itu bahkan menunjukkan untuk melakukan hal berikut:

io.on('connection', function(socket){
  socket.on('chat message', function(msg){
    io.emit('chat message', msg);
  });
});
Apakah halaman ini membantu?
0 / 5 - 0 peringkat

Masalah terkait

dmuth picture dmuth  ·  3Komentar

Aweather picture Aweather  ·  4Komentar

MichaelJCole picture MichaelJCole  ·  3Komentar

doughsay picture doughsay  ·  4Komentar

varHarrie picture varHarrie  ·  3Komentar