/// <summary>
        /// <para>Events:</para>
        /// <para>@emits transportclose</para>
        /// <para>@emits dataproducerclose</para>
        /// <para>@emits message - (message: Buffer, ppid: number)</para>
        /// <para>@emits sctpsendbufferfull</para>
        /// <para>@emits bufferedamountlow - (bufferedAmount: number)</para>
        /// <para>@emits @close</para>
        /// <para>@emits @dataproducerclose</para>
        /// <para>Observer events:</para>
        /// <para>@emits close</para>
        /// </summary>
        /// <param name="loggerFactory"></param>
        /// <param name="dataConsumerInternalData"></param>
        /// <param name="sctpStreamParameters"></param>
        /// <param name="label"></param>
        /// <param name="protocol"></param>
        /// <param name="channel"></param>
        /// <param name="payloadChannel"></param>
        /// <param name="appData"></param>
        public DataConsumer(ILoggerFactory loggerFactory,
                            DataConsumerInternalData dataConsumerInternalData,
                            SctpStreamParameters sctpStreamParameters,
                            string label,
                            string protocol,
                            Channel channel,
                            PayloadChannel payloadChannel,
                            Dictionary <string, object>?appData
                            )
        {
            _logger = loggerFactory.CreateLogger <DataConsumer>();

            // Internal
            _internal = dataConsumerInternalData;

            // Data
            SctpStreamParameters = sctpStreamParameters;
            Label    = label;
            Protocol = protocol;

            _channel        = channel;
            _payloadChannel = payloadChannel;
            AppData         = appData;

            HandleWorkerNotifications();
        }
示例#2
0
        /// <summary>
        /// Create a DataConsumer.
        /// </summary>
        /// <param name="dataConsumerOptions"></param>
        /// <returns></returns>
        public async Task <DataConsumer> ConsumeDataAsync(DataConsumerOptions dataConsumerOptions)
        {
            _logger.LogDebug("ConsumeDataAsync()");

            if (dataConsumerOptions.DataProducerId.IsNullOrWhiteSpace())
            {
                throw new Exception("missing dataProducerId");
            }

            var dataProducer = GetDataProducerById(dataConsumerOptions.DataProducerId);

            if (dataProducer == null)
            {
                throw new Exception($"DataProducer with id {dataConsumerOptions.DataProducerId} not found");
            }

            var sctpStreamParameters = dataProducer.SctpStreamParameters.DeepClone <SctpStreamParameters>();

            // This may throw.
            var sctpStreamId = GetNextSctpStreamId();

            if (_sctpStreamIds == null || sctpStreamId > _sctpStreamIds.Length - 1)
            {
                throw new IndexOutOfRangeException(nameof(_sctpStreamIds));
            }
            _sctpStreamIds[sctpStreamId]  = 1;
            sctpStreamParameters.StreamId = sctpStreamId;

            var @internal = new DataConsumerInternalData
                            (
                Internal.RouterId,
                Internal.TransportId,
                dataConsumerOptions.DataProducerId,
                Guid.NewGuid().ToString()
                            );

            var reqData = new
            {
                SctpStreamParameters = sctpStreamParameters,
                dataProducer.Label,
                dataProducer.Protocol
            };

            var status = await Channel.RequestAsync(MethodId.TRANSPORT_CONSUME_DATA, @internal, reqData);

            var responseData = JsonConvert.DeserializeObject <TransportDataConsumeResponseData>(status);

            var dataConsumer = new DataConsumer(_loggerFactory,
                                                @internal,
                                                responseData.SctpStreamParameters,
                                                responseData.Label,
                                                responseData.Protocol,
                                                Channel,
                                                AppData);

            DataConsumers[dataConsumer.Internal.DataConsumerId] = dataConsumer;

            dataConsumer.On("@close", _ =>
            {
                DataConsumers.Remove(dataConsumer.Internal.DataConsumerId);
                _sctpStreamIds[sctpStreamId] = 0;
            });

            dataConsumer.On("@dataproducerclose", _ =>
            {
                DataConsumers.Remove(dataConsumer.Internal.DataConsumerId);
                _sctpStreamIds[sctpStreamId] = 0;
            });

            // Emit observer event.
            Observer.Emit("newdataconsumer", dataConsumer);

            return(dataConsumer);
        }
示例#3
0
        /// <summary>
        /// Create a DataConsumer.
        /// </summary>
        /// <param name="dataConsumerOptions"></param>
        /// <returns></returns>
        public async Task <DataConsumer> ConsumeDataAsync(DataConsumerOptions dataConsumerOptions)
        {
            _logger.LogDebug("ConsumeDataAsync()");

            if (dataConsumerOptions.DataProducerId.IsNullOrWhiteSpace())
            {
                throw new Exception("missing dataProducerId");
            }

            var dataProducer = GetDataProducerById(dataConsumerOptions.DataProducerId);

            if (dataProducer == null)
            {
                throw new Exception($"DataProducer with id {dataConsumerOptions.DataProducerId} not found");
            }


            DataProducerType     type;
            SctpStreamParameters?sctpStreamParameters = null;
            int sctpStreamId = -1;

            // If this is not a DirectTransport, use sctpStreamParameters from the
            // DataProducer (if type 'sctp') unless they are given in method parameters.
            if (GetType() != typeof(DirectTransport))
            {
                type = DataProducerType.Sctp;

                sctpStreamParameters = dataProducer.SctpStreamParameters.DeepClone <SctpStreamParameters>();
                // This may throw.
                sctpStreamId = GetNextSctpStreamId();

                if (_sctpStreamIds == null || sctpStreamId > _sctpStreamIds.Length - 1)
                {
                    throw new IndexOutOfRangeException(nameof(_sctpStreamIds));
                }
                _sctpStreamIds[sctpStreamId]  = 1;
                sctpStreamParameters.StreamId = sctpStreamId;
            }
            // If this is a DirectTransport, sctpStreamParameters must not be used.
            else
            {
                type = DataProducerType.Direct;

                if (dataConsumerOptions.Ordered.HasValue ||
                    dataConsumerOptions.MaxPacketLifeTime.HasValue ||
                    dataConsumerOptions.MaxRetransmits.HasValue
                    )
                {
                    _logger.LogWarning("ConsumeDataAsync() | ordered, maxPacketLifeTime and maxRetransmits are ignored when consuming data on a DirectTransport");
                }
            }

            var @internal = new DataConsumerInternalData
                            (
                Internal.RouterId,
                Internal.TransportId,
                dataConsumerOptions.DataProducerId,
                Guid.NewGuid().ToString()
                            );

            var reqData = new
            {
                Type = type.GetEnumStringValue(),
                SctpStreamParameters = sctpStreamParameters,
                dataProducer.Label,
                dataProducer.Protocol
            };

            var status = await Channel.RequestAsync(MethodId.TRANSPORT_CONSUME_DATA, @internal, reqData);

            var responseData = JsonConvert.DeserializeObject <TransportDataConsumeResponseData>(status !);

            var dataConsumer = new DataConsumer(_loggerFactory,
                                                @internal,
                                                responseData.SctpStreamParameters,
                                                responseData.Label,
                                                responseData.Protocol,
                                                Channel,
                                                PayloadChannel,
                                                AppData);

            DataConsumers[dataConsumer.DataConsumerId] = dataConsumer;

            dataConsumer.On("@close", _ =>
            {
                DataConsumers.Remove(dataConsumer.DataConsumerId);
                if (_sctpStreamIds != null && sctpStreamId >= 0)
                {
                    _sctpStreamIds[sctpStreamId] = 0;
                }
            });

            dataConsumer.On("@dataproducerclose", _ =>
            {
                DataConsumers.Remove(dataConsumer.DataConsumerId);
                if (_sctpStreamIds != null && sctpStreamId >= 0)
                {
                    _sctpStreamIds[sctpStreamId] = 0;
                }
            });

            // Emit observer event.
            Observer.Emit("newdataconsumer", dataConsumer);

            return(dataConsumer);
        }