public MediaChannelState(MediaChannelState src)
 {
     ChannelName = src.ChannelName;
     AddressInfo = src.AddressInfo;
     ServerInfo  = src.ServerInfo;
     MediaInfo   = src.MediaInfo;
     ClientCount = src.ClientCount;
     SourceCount = src.SourceCount;
 }
        public List <MediaChannelState> GetChannelStates()
        {
            List <MediaChannelState> states = new List <MediaChannelState>();

            lock (m_States)
            {
                foreach (var item in m_States)
                {
                    MediaChannelState state = new MediaChannelState(item.Value);
                    states.Add(state);
                }
            }
            return(states);
        }
 public void UpdateState(string channelName, MediaChannelState state)
 {
     // update state
     lock (m_States)
     {
         int streams = 1;
         if (m_States.ContainsKey(channelName))
         {
             streams += m_States[channelName].SourceCount;
             m_States.Remove(channelName); // refresh it
         }
         state.ServerInfo  = ServerName + "(" + InputIp + ":" + InputPort + "/" + OutputIp + ":" + OutputPort + ")";
         state.SourceCount = streams;
         m_States.Add(channelName, state);
     }
 }
        protected virtual void ProcessInputData(object obj)
        {
            HttpListenerContext ctx = obj as HttpListenerContext;

            if (ctx == null)
            {
                return;
            }

            IMediaHandler       handler  = null;
            List <MediaChannel> channels = new List <MediaChannel>();

            var urlSegments = ctx.Request.Url.Segments;

            string channelNames = "";

            if (urlSegments.Length > 1)
            {
                channelNames = urlSegments[1].Replace("/", "");
            }

            if (channelNames.Length > 0)
            {
                var names = channelNames.Split(',');
                foreach (var channelName in names)
                {
                    var channel = GetChannel(channelName.Trim());
                    if (channel != null && channel.IsWorking() == false)
                    {
                        channel.Start();
                    }
                    if (channel != null)
                    {
                        channels.Add(channel);
                    }
                }
            }

            if (channels.Count > 0)
            {
                string typeinfo = "";
                if (urlSegments.Length > 2)
                {
                    typeinfo = urlSegments[2].Replace("/", "");
                }
                if (typeinfo.Length > 0)
                {
                    handler = m_ResourceManager.GetHandler(typeinfo);
                }
            }

            if (channels.Count > 0 && handler != null)
            {
                string mediainfo = "";
                if (urlSegments.Length > 3)
                {
                    mediainfo = urlSegments[3].Replace("/", "");
                }
                if (mediainfo.Length > 0)
                {
                    mediainfo = handler.GetMediaType() + "(" + mediainfo + ")";
                }
                else
                {
                    mediainfo = handler.GetMediaType();
                }

                foreach (var channel in channels)
                {
                    MediaChannelState state = new MediaChannelState();
                    state.ChannelName = channel.ChannelName;
                    state.AddressInfo = ctx.Request.RemoteEndPoint.ToString();
                    state.MediaInfo   = mediainfo;
                    state.ClientCount = 0;

                    UpdateState(channel.ChannelName, state);
                }

                handler.HandleInput(this, channels, ctx.Request.InputStream, mediainfo);

                foreach (var channel in channels)
                {
                    //channel.SetWelcomeText("");
                    channel.RemoveWelcomeText(mediainfo);
                    channel.SetWelcomeData(new byte[0]);
                    RemoveState(channel.ChannelName);
                }
            }

            try
            {
                ctx.Response.Abort(); // make sure the connection is closed
            }
            catch (Exception ex)
            {
                Logger.Error("HTTP context error: " + ex.Message);
            }
        }
        public virtual void ValidateClient(object client)
        {
            Session session = client as Session;

            if (session == null)
            {
                return;
            }

            Task.Factory.StartNew(() =>
            {
                try
                {
                    string target  = "";
                    string reqpath = WebMessage.GetSessionData(session, "Path").ToString();

                    if (m_ClientValidator != null)
                    {
                        target = m_ClientValidator.Validate(session.GetRemoteIp(), reqpath);
                    }
                    else
                    {
                        List <string> paramList = new List <string>();
                        string[] parts          = reqpath.Split('/');
                        foreach (var part in parts)
                        {
                            if (part.Trim().Length > 0)
                            {
                                paramList.Add(part.Trim());
                            }
                        }
                        if (paramList.Count > 0)
                        {
                            target = paramList.First();
                        }
                    }

                    if (target != null && target.Length > 0)
                    {
                        bool isOK = true;
                        try
                        {
                            byte[] welcomeData = null;
                            string welcomeText = "";

                            var channel = m_ResourceManager.GetChannel(target, false);
                            if (channel != null)
                            {
                                welcomeData = channel.GetWelcomeData();
                                welcomeText = channel.GetWelcomeText();
                            }
                            if (welcomeData != null && welcomeData.Length > 0)
                            {
                                session.Send(new WebMessage(welcomeData));
                            }
                            if (welcomeText != null && welcomeText.Length > 0)
                            {
                                session.Send(new WebMessage(welcomeText));
                            }
                        }
                        catch { isOK = false; }

                        if (isOK)
                        {
                            List <object> clients  = null;
                            int channelClientCount = 0;
                            lock (m_WebClients)
                            {
                                if (m_WebClients.ContainsKey(target))
                                {
                                    clients = m_WebClients[target];
                                }
                            }
                            if (clients != null)
                            {
                                lock (clients)
                                {
                                    clients.Add(session);
                                    channelClientCount = clients.Count;
                                }
                            }

                            if (m_InputPort <= 0)
                            {
                                // update state
                                lock (m_States)
                                {
                                    if (!m_States.ContainsKey(target))
                                    {
                                        var channelState         = new MediaChannelState();
                                        channelState.ChannelName = target;
                                        channelState.ClientCount = channelClientCount;
                                        channelState.ServerInfo  = m_ServerName + "(" + m_InputIp + ":" + m_InputPort + "/" + m_OutputIp + ":" + m_OutputPort + ")";
                                        m_States.Add(target, channelState);
                                    }
                                }
                            }
                        }
                    }
                    else
                    {
                        session.Close(); // just close it if failed to validate
                    }
                }
                catch (Exception ex)
                {
                    Logger.Error("Validation error: " + ex.Message);
                }
            });
        }
        protected virtual void ProcessInputData(object obj)
        {
            HttpListenerContext ctx = obj as HttpListenerContext;

            if (ctx == null)
            {
                return;
            }

            string remoteIp  = "";
            string sourceUrl = "";

            try
            {
                remoteIp  = ctx.Request.RemoteEndPoint.Address.ToString();
                sourceUrl = "[" + remoteIp + "] - " + ctx.Request.Url.ToString();
            }
            catch (Exception ex)
            {
                Logger.Error("HTTP context error: " + ex.Message);
            }

            IMediaHandler       handler  = null;
            List <MediaChannel> channels = new List <MediaChannel>();

            var urlSegments = ctx.Request.Url.Segments;

            string channelNames = "";

            if (urlSegments.Length > 1)
            {
                channelNames = urlSegments[1].Replace("/", "");
            }

            if (channelNames.Length > 0)
            {
                var names = channelNames.Split(',');
                foreach (var channelName in names)
                {
                    var channel = GetChannel(channelName.Trim());

                    if (channel != null)
                    {
                        channel.AddInputUrl(sourceUrl);
                    }
                    if (channel != null)
                    {
                        var srcUrls = channel.GetInputUrls();
                        Logger.Info("Channel #" + channelName + "# input source updated >> ");
                        foreach (var srcUrl in srcUrls)
                        {
                            Logger.Info("#" + channelName + "# - " + srcUrl);
                        }
                    }

                    if (channel != null && channel.IsWorking() == false)
                    {
                        channel.Start();
                    }
                    if (channel != null)
                    {
                        channels.Add(channel);
                    }

                    Thread.Sleep(50);
                }
            }

            if (channels.Count > 0)
            {
                string typeinfo = "";
                if (urlSegments.Length > 2)
                {
                    typeinfo = urlSegments[2].Replace("/", "");
                }
                if (typeinfo.Length > 0)
                {
                    handler = m_ResourceManager.GetHandler(typeinfo);
                }
            }

            if (channels.Count > 0 && handler != null)
            {
                string mediainfo = "";
                if (urlSegments.Length > 3)
                {
                    mediainfo = urlSegments[3].Replace("/", "");
                }
                if (mediainfo.Length > 0)
                {
                    mediainfo = handler.GetMediaType() + "(" + mediainfo + ")";
                }
                else
                {
                    mediainfo = handler.GetMediaType();
                }

                foreach (var channel in channels)
                {
                    MediaChannelState state = new MediaChannelState();
                    state.ChannelName = channel.ChannelName;
                    state.AddressInfo = ctx.Request.RemoteEndPoint.ToString();
                    state.MediaInfo   = mediainfo;
                    state.ClientCount = 0;

                    UpdateState(channel.ChannelName, state);
                }

                // should ensure there is at least a try-catch block inside the process function
                handler.HandleInput(this, channels, ctx.Request.InputStream, mediainfo);

                foreach (var channel in channels)
                {
                    //channel.SetWelcomeText("");
                    channel.RemoveWelcomeText(mediainfo);
                    channel.SetWelcomeData(new byte[0]);

                    channel.RemoveInputUrl(sourceUrl);
                    if (channel != null)
                    {
                        var srcUrls = channel.GetInputUrls();
                        if (srcUrls.Count > 0)
                        {
                            Logger.Info("Channel #" + channel.ChannelName + "# input source updated >> ");
                            foreach (var srcUrl in srcUrls)
                            {
                                Logger.Info("#" + channel.ChannelName + "# - " + srcUrl);
                            }
                        }
                        else
                        {
                            Logger.Info("Channel #" + channel.ChannelName + "# input source dropped.");
                        }
                    }

                    RemoveState(channel.ChannelName);

                    Thread.Sleep(50);
                }
            }

            try
            {
                ctx.Response.Abort(); // make sure the connection is closed
            }
            catch (Exception ex)
            {
                Logger.Error("HTTP context error: " + ex.Message);
            }
        }