Hacktoberfest 2026: los issues que los mantenedores marcaron para octubre, abiertos y aptos para principiantes. Explorar issues de Hacktoberfest

partytracks: createAudioSink().attach throws on a synchronous track, and a failed track close is an unhandled rejection

Abierto Apto para principiantes
#425 1 comentario 0 reacciones 0 asignados Ver en GitHub

Nadie ha tomado este issue todavía.

Evaluación

Dificultad
2/5
Tiempo estimado
1-3 horas
Aptitud para principiantes
70/100
Tipo de issue
Error
Claridad
Bien especificado
Estado de actividad
Activo
Stack tecnológico
typescript

Línea de trabajo

Empieza en packages/partytracks/src/client/audioSink.ts, donde attach() se suscribe a track$ y llama a sub.add dentro del callback, y reproduce el problema con una fuente síncrona como of(track). El segundo error está en el método del cliente #closeTrackInBulk, que parsea la respuesta de tracks/close y pasa sessionDescription a setRemoteDescription; localízalo buscando closeTrackInBulk. Se considera terminado cuando attach funciona con un track síncrono y un cierre fallido no lanza una excepción sin manejar ni renegocia una vez que la conexión peer está cerrada.

Escrito por el modelo de indexación a partir del texto del issue.

Descripción

Two bugs in partytracks 0.0.56 (also on main), found while running Cloudflare Realtime calls in production-like tests.

1. createAudioSink().attach throws when the track emits synchronously

attach(track$) calls track$.subscribe(...) and, inside the callback, sub.add(...). When track$ emits synchronously (for example an already-pulled track behind shareReplay), the callback runs before sub is assigned:

ReferenceError: Cannot access 'sub' before initialization

Reproduction:

import { of } from "rxjs";
createAudioSink({ audioElement: new Audio() }).attach(of(track));

Suggested fix (packages/partytracks/src/client/audioSink.ts): create the subscription first and add the inner one to it:

const sub = new Subscription();
sub.add(
  pulledAudioTrack$.subscribe((track) => {
    mediaStream.addTrack(track);
    resetSrcObject();
    sub.add(() => {
      mediaStream.removeTrack(track);
      resetSrcObject();
    });
  }),
);
2. A failed track close is an unhandled rejection

#closeTrackInBulk parses the tracks/close response as JSON and passes response.sessionDescription to setRemoteDescription without checking either. A close that races the end of a session becomes an unhandled rejection in the page: the server refuses it in plain text (so response.json() throws), or the SFU answers 410 because the session has gone (so setRemoteDescription gets undefined). Nothing awaits doBulkRequest there, so the caller cannot catch it.

This happens routinely when one participant leaves just as a call ends: the others stop receiving their tracks while the session is being torn down.

Suggested: check response.ok before parsing, and drop the failure when the peer connection has closed meanwhile (peerConnection.connectionState === "closed"), since there is nothing left to renegotiate.

We carry both fixes as a local patch for now and would be glad to drop it.

Lenguaje dominante
TypeScript
Estrellas
1.3k
Forks
83
Métricas de merge de PR
Sin PR fusionados en 30 d

Preparar el entorno

Primeros pasos

  1. Lee el issue completo y luego la guía de contribución del proyecto.
  2. Comenta en el issue que vas a ocuparte — evita que dos personas hagan lo mismo.
  3. Haz un fork del repositorio y trabaja en una rama.
  4. Abre un pull request que haga referencia al número del issue.

Más de cloudflare/partykit

Todos los issues de cloudflare/partykit

Issues similares

Más issues de TypeScript

Recibe los nuevos issues en tu correo

Un resumen breve de issues de GitHub para principiantes.