Redux-сага и сокет подписки вызывают Uncaught TypeError: Преобразование круговой структуры в JSON

У меня возникают проблемы при подписке на канал socketcluster ( http://socketcluster.io/) при использовании генератора redux-saga в моем приложении чата. Серверная часть socketcluster настраивается таким образом, что любые сообщения сохраняются в базе данных, а затем публикуются в личном канале принимающего пользователя, который назван в честь идентификатора пользователя. Например, пользователь A имеет идентификатор "123abc" и будет подписываться на канал с именем "123abc" для своих сообщений в реальном времени.

Приведенный ниже код получает новые сообщения, которые публикуются в канале, но он выдает "TypeError: Преобразование циклической структуры в JSON" и отключает все мои другие генераторы redux-saga в приложении. Я закончил копаться в Chrome Devtools, и моя теория состоит в том, что это как-то связано с очередью, созданной в функции createChannel. Кроме того, я попытался вернуть отложенное обещание в функции subscribeToChannel, но это также вызвало ошибку циклического преобразования, я могу опубликовать этот код по запросу.

Сначала я сослался на этот ответ: /questions/1142231/kak-svyazat-sobyitiya-generiruemyie-sobyitiyami-v-redx-sagu/1142249#1142249 и это помогло мне получить приведенный ниже код, но я не могу найти аналогичные проблемы в Интернете. Также кое-что стоит отметить, я использую кластер сокета redux-сокета ( https://github.com/mattkrick/redux-socket-cluster) для синхронизации сокета и состояния, но я не думаю, что это корень проблема

sagas.js

export default function* root() {
    yield [
        fork(startSubscription),
    ]
}


function* startSubscription(getState) {
    while (true) {
        const {
            userId
        } = yield take(actions.SUBSCRIBE_TO_MY_CHANNEL);
        yield call(monitorChangeEvents, subscribeToChannel(userId))
    }
}

function* monitorChangeEvents(channel) {
    while (true) {
        const info = yield call(channel.take) // Blocks until the promise resolves
        console.log(info)
    }
}

function subscribeToChannel(channelName) {
    const channel = createChannel();
    const socket = socketCluster.connect(socketConfig);
    const c = socket.subscribe(channelName);
    c.watch(event => {
        channel.put(event)
    })

    return channel;
}

function createChannel() {
    const messageQueue = []
    const resolveQueue = []

    function put(msg) {
        // anyone waiting for a message ?
        if (resolveQueue.length) {
            // deliver the message to the oldest one waiting (First In First Out)
            const nextResolve = resolveQueue.shift()
            nextResolve(msg)
        } else {
            // no one is waiting ? queue the event
            messageQueue.push(msg)
        }
    }

    // returns a Promise resolved with the next message
    function take() {
        // do we have queued messages ?
        if (messageQueue.length) {
            // deliver the oldest queued message
            return Promise.resolve(messageQueue.shift())
        } else {
            // no queued messages ? queue the taker until a message arrives
            return new Promise((resolve) => resolveQueue.push(resolve))
        }
    }

    return {
        take,
        put
    }
}

Спасибо за помощь!

0 ответов

Другие вопросы по тегам