Penso che la dimensione del messaggio in uscita in realtà non è il problema. Ho lo stesso identico problema e impostare "max_payload_size" su un valore più grande non lo risolve. Se questo fosse il problema, vedresti il messaggio di errore da Frame.pm "to_bytes" sub "Il payload è troppo grande, invia messaggi più brevi o aumenta max_payload_size". Quando invio un messaggio dal server a Chrome su 16k non vedo questo errore (o qualsiasi altro) sul server, sì, ho ancora il messaggio "Impossibile decodificare una cornice di testo come UTF-8" con un "(Opcode - 1) "come il corpo del messaggio frame evidenziato in rosso nella scheda Rete dell'ispettore Chrome.
Penso che sia molto più probabile che si tratti di un problema IO :: Socket :: SSL, poiché lo sto utilizzando come prescritto nei documenti di Net :: WebSocket :: Server. Sono curioso di sapere se stai bene o se vedi questo problema in normali prese non crittografate.
Dal IO :: Socket :: SSL Documenti:
syswrite (BUF, [LEN, [Offset]]) Questa funzione si comporta da al di fuori della stessa syswrite in altri IO :: Socket oggetti, ad es sarà scrivere nella maggior parte dei byte LEN al socket, ma non è garantito che sia scritto tutti i byte LEN. Restituirà il numero di byte scritti. syswrite scriverà tutti i dati all'interno di un singolo frame SSL, che significa , che non può essere scritto più di 16.384 byte, che è la dimensione massima di un frame SSL in una sola volta.
Net :: WebSocket :: Server :: Connection sta chiamando syswrite dopo che il telaio è costruito:
syswrite($self->{socket}, $bytes);
Delle idee come affrontare questo mi incuriosisce. Forse il modulo Frame dovrebbe frammentare i messaggi sotto 16k quando si utilizza SSL, ma questo dovrebbe essere gestito in Connection.pm, penserei.
AGGIORNATO con la soluzione:
si scopre questo è una correzione abbastanza facile se si è disposti a modificare il Connection.pm e mettere lo syswrite in un ciclo 16k. Ricordando che i frame SSL e i frame WebSocket non sono la stessa cosa, non è necessario che la dimensione del frame SSL sia eccessiva. Vedere soluzione di lavoro:
sub send {
my ($self, $type, $data) = @_;
if ($self->{handshake}) {
carp "tried to send data before finishing handshake";
return 0;
}
my $frame = new Protocol::WebSocket::Frame(type => $type, max_payload_size => $self->{max_send_size});
$frame->append($data) if defined $data;
my $bytes = eval { $frame->to_bytes };
if (!defined $bytes) {
carp "error while building message: [email protected]" if [email protected];
return;
}
# modified to not overflow the 16k SSL frame size
while(16384 < length $bytes) {
syswrite($self->{socket}, $bytes, 16384);
substr($bytes, 0, 16384, '');
}
syswrite($self->{socket}, $bytes);
}
Sono stato in grado di inviare una stringa json 27k a Chrome che non aveva precedentemente funzionato su SSL.
Ho inviato un'email all'autore della libreria e ha scritto: "Il limite imposto dal protocollo Protocol :: WebSocket :: Frame sottostante sembra essere 65535 byte". Penso che questo sia correlato e il limite di ~ 16.000 caratteri che sto colpendo potrebbe essere dovuto al fatto che send_utf8 considera ogni carattere come 4 byte. Spero comunque una risposta più precisa e una possibile soluzione alternativa. –