Click here to Skip to main content
15,893,644 members
Articles / Programming Languages / C#

IMAP and POP3 Clients in C#

Rate me:
Please Sign up or sign in to vote.
4.67/5 (21 votes)
28 Sep 2012CPOL1 min read 258.8K   16.6K   48  
IMAP & POP3 Clients C#. A library for intuitive ease of use of these two protocols.
using System;
using System.Collections.Generic;
using System.Text;
using System.Net;

namespace LumiSoft.Net.RTP
{
    /// <summary>
    /// This class represents RTP single-media and multimedia session.
    /// </summary>
    public class RTP_MultimediaSession : IDisposable
    {
        private bool                                      m_IsDisposed        = false;
        private RTP_Participant_Local                     m_pLocalParticipant = null;
        private List<RTP_Session>                         m_pSessions         = null;
        private Dictionary<string,RTP_Participant_Remote> m_pParticipants     = null;

        /// <summary>
        /// Default constructor.
        /// </summary>
        /// <param name="cname">Canonical name of participant. <seealso cref="LumiSoft.Net.RTP.RTP_Utils.GenerateCNAME"/>RTP_Utils.GenerateCNAME 
        /// can be used to create this value.</param>
        /// <exception cref="ArgumentNullException">Is raised when <b>cname</b> is null reference.</exception>
        /// <exception cref="ArgumentException">Is raised when any of the arguments has invalid value.</exception>
        public RTP_MultimediaSession(string cname)
        {
            if(cname == null){
                throw new ArgumentNullException("cname");
            }
            if(cname == string.Empty){
                throw new ArgumentException("Argument 'cname' value must be specified.");
            }

            m_pLocalParticipant = new RTP_Participant_Local(cname);
            m_pSessions = new List<RTP_Session>();
            m_pParticipants = new Dictionary<string,RTP_Participant_Remote>();
        }

        #region method Dispose

        /// <summary>
        /// Cleans up any resources being used.
        /// </summary>
        public void Dispose()
        {
            if(m_IsDisposed){
                return;
            }
            foreach(RTP_Session session in m_pSessions.ToArray()){
                session.Dispose();
            }
            m_IsDisposed = true;

            m_pLocalParticipant = null;
            m_pSessions         = null;
            m_pParticipants     = null;            

            this.NewParticipant = null;
            this.Error = null;
        }

        #endregion


        #region method Close

        /// <summary>
        /// Closes RTP multimedia session, sends BYE with optional reason text to remote targets.
        /// </summary>
        /// <param name="closeReason">Close reason. Value null means not specified.</param>
        /// <exception cref="ObjectDisposedException">Is raised when this class is Disposed and this method is accessed.</exception>
        public void Close(string closeReason)
        {
            if(m_IsDisposed){
                throw new ObjectDisposedException(this.GetType().Name);
            }

            foreach(RTP_Session session in m_pSessions.ToArray()){
                session.Close(closeReason);
            }

            Dispose();
        }

        #endregion

        #region method Start

        /// <summary>
        /// Starts session.
        /// </summary>
        /// <exception cref="ObjectDisposedException">Is raised when this class is Disposed and this method is accessed.</exception>
        public void Start()
        {
            if(m_IsDisposed){
                throw new ObjectDisposedException(this.GetType().Name);
            }

            // TODO:
        }

        #endregion

        #region method Stop

        /// <summary>
        /// Stops session.
        /// </summary>
        /// <exception cref="ObjectDisposedException">Is raised when this class is Disposed and this method is accessed.</exception>
        public void Stop()
        {
            if(m_IsDisposed){
                throw new ObjectDisposedException(this.GetType().Name);
            }

            // TODO:
        }

        #endregion

        #region method CreateSession

        /// <summary>
        /// Creates new RTP session.
        /// </summary>
        /// <param name="localEP">Local RTP end point.</param>
        /// <param name="clock">RTP media clock.</param>
        /// <returns>Returns created session.</returns>
        /// <exception cref="ObjectDisposedException">Is raised when this class is Disposed and this method is accessed.</exception>
        /// <exception cref="ArgumentNullException">Is raised when <b>localEP</b> or <b>clock</b> is null reference.</exception>
        public RTP_Session CreateSession(RTP_Address localEP,RTP_Clock clock)
        {
            if(m_IsDisposed){
                throw new ObjectDisposedException(this.GetType().Name);
            }
            if(localEP == null){
                throw new ArgumentNullException("localEP");
            }
            if(clock == null){
                throw new ArgumentNullException("clock");
            }

            RTP_Session session = new RTP_Session(this,localEP,clock);
            session.Disposed += new EventHandler(delegate(object s,EventArgs e){
                m_pSessions.Remove((RTP_Session)s);
            });
            m_pSessions.Add(session);

            OnSessionCreated(session);

            return session;
        }

        #endregion


        #region method GetOrCreateParticipant

        /// <summary>
        /// Gets or creates new participant if participant does not exist.
        /// </summary>
        /// <param name="cname">Participant canonical name.</param>
        /// <returns>Returns specified participant.</returns>
        internal RTP_Participant_Remote GetOrCreateParticipant(string cname)
        {
            if(cname == null){
                throw new ArgumentNullException("cname");
            }
            if(cname == string.Empty){
                throw new ArgumentException("Argument 'cname' value must be specified.");
            }

            lock(m_pParticipants){
                RTP_Participant_Remote participant = null;
                if(!m_pParticipants.TryGetValue(cname,out participant)){
                    participant = new RTP_Participant_Remote(cname);
                    participant.Removed += new EventHandler(delegate(object sender,EventArgs e){
                        m_pParticipants.Remove(participant.CNAME);
                    });
                    m_pParticipants.Add(cname,participant);

                    OnNewParticipant(participant);
                }

                return participant;
            }
        }

        #endregion


        #region Properties implementation

        /// <summary>
        /// Gets if this object is disposed.
        /// </summary>
        public bool IsDisposed
        {
            get{ return m_IsDisposed; }
        }

        /// <summary>
        /// Gets media sessions.
        /// </summary>
        /// <exception cref="ObjectDisposedException">Is raised when this class is Disposed and this property is accessed.</exception>
        public RTP_Session[] Sessions
        {
            get{ 
                if(m_IsDisposed){
                    throw new ObjectDisposedException(this.GetType().Name);
                }

                return m_pSessions.ToArray(); 
            }
        }

        /// <summary>
        /// Gets local participant.
        /// </summary>
        /// <exception cref="ObjectDisposedException">Is raised when this class is Disposed and this property is accessed.</exception>
        public RTP_Participant_Local LocalParticipant
        {
            get{ 
                if(m_IsDisposed){
                    throw new ObjectDisposedException(this.GetType().Name);
                }

                return m_pLocalParticipant; 
            }
        }

        /// <summary>
        /// Gets session remote participants.
        /// </summary>
        /// <exception cref="ObjectDisposedException">Is raised when this class is Disposed and this property is accessed.</exception>
        public RTP_Participant_Remote[] RemoteParticipants
        {
            get{ 
                if(m_IsDisposed){
                    throw new ObjectDisposedException(this.GetType().Name);
                }

                lock(m_pParticipants){
                    RTP_Participant_Remote[] retVal = new RTP_Participant_Remote[m_pParticipants.Count];
                    m_pParticipants.Values.CopyTo(retVal,0);

                    return retVal;
                }
            }
        }

        #endregion

        #region Event implementation

        /// <summary>
        /// Is raised when new session has created.
        /// </summary>
        public event EventHandler<EventArgs<RTP_Session>> SessionCreated = null;

        #region method OnSessionCreated

        /// <summary>
        /// Raises <b>SessionCreated</b> event.
        /// </summary>
        /// <param name="session">RTP session.</param>
        private void OnSessionCreated(RTP_Session session)
        {
            if(session == null){
                throw new ArgumentNullException("session");
            }

            if(this.SessionCreated != null){
                this.SessionCreated(this,new EventArgs<RTP_Session>(session));
            }
        }

        #endregion

        /// <summary>
        /// Is raised when new remote participant has joined to session.
        /// </summary>
        public event EventHandler<RTP_ParticipantEventArgs> NewParticipant = null;

        #region method OnNewParticipant

        /// <summary>
        /// Raises <b>NewParticipant</b> event.
        /// </summary>
        /// <param name="participant">New participant.</param>
        private void OnNewParticipant(RTP_Participant_Remote participant)
        {
            if(this.NewParticipant != null){
                this.NewParticipant(this,new RTP_ParticipantEventArgs(participant));
            }
        }

        #endregion

        /// <summary>
        /// Is raised when unknown error has happened.
        /// </summary>
        public event EventHandler<ExceptionEventArgs> Error = null;

        #region method OnError

        /// <summary>
        /// Raises <b>Error</b> event.
        /// </summary>
        /// <param name="exception">Exception.</param>
        internal void OnError(Exception exception)
        {
            if(this.Error != null){
                this.Error(this,new ExceptionEventArgs(exception));
            }
        }

        #endregion

        #endregion
    }
}

By viewing downloads associated with this article you agree to the Terms of Service and the article's licence.

If a file you wish to view isn't highlighted, and is a text file (not binary), please let us know and we'll add colourisation support for it.

License

This article, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)


Written By
Software Developer (Senior) D.Net Solution
Italy Italy
This member has not yet provided a Biography. Assume it's interesting and varied, and probably something to do with programming.

Comments and Discussions