Как получить push-данные сервера в C #? - PullRequest
3 голосов
/ 16 июня 2009

Я пишу программу. моя программа получает данные с сервера по протоколу HTTP. данные будут отправлены сервером в мою программу. Я пытался использовать WebRequest, но получил только один сеанс данных. Как я могу сохранить соединение, чтобы непрерывно получать данные с сервера, Любая помощь приветствуется.

следующий документ SDK:

Под авторизацией GUEST или ADMIN можно получить серию живых изображений (Толчок сервера). Чтобы получить изображения, отправьте запрос на «/liveimg.cgi?serverpush=1», как показано на рисунке. 2-1-1.
Когда камера получает указанный выше запрос от клиента, она отправляет возврат, как показано на рисунке. 2-2.
Каждые данные JPEG отделяются «--myboundary», а «image / jpeg» возвращается как Заголовок «Content-Type», после «--myboundary». Для заголовка «Content-Length» он возвращает количество байтов в данных --myboundary (исключая «--myboundary», каждый заголовок и \ r \ n в качестве разделителя). После заголовка «Content-Length» и «\ r \ n» (разделитель), фактический данные будут отправлены.
Эта передача данных будет продолжаться до тех пор, пока клиент не прекратит соединение (не отключит), или возникает какая-то сетевая ошибка.

int len; строка uri = @ "http://192.168.0.2/liveimg.cgi?serverpush=1";

        HttpWebRequest req = (HttpWebRequest)HttpWebRequest.Create(uri);
        req.Credentials = new NetworkCredential("admin", "admin");
        req.KeepAlive = true;

        string line = "";

        HttpWebResponse reply = (HttpWebResponse)req.GetResponse();
        Stream stream = reply.GetResponseStream();

        System.Diagnostics.Debug.WriteLine(reply.ContentType);

        StreamReader reader = new StreamReader(stream);
        do
        {
            line = reader.ReadLine();
            System.Diagnostics.Debug.WriteLine(line);

            System.Threading.Thread.Sleep(300);

        } while (line.Length>0);

Ответы [ 5 ]

2 голосов
/ 26 сентября 2009

Возможно, вы захотите взглянуть на StreamHub Push Server - это популярный сервер Comet и имеет .NET Client SDK, который позволяет получать в режиме реального времени push-обновления на C # (или VB / C ++ ).

2 голосов
/ 16 июня 2009

Вы можете держать HTTP-соединение открытым в течение длительного периода времени, если сервер поддерживает это. (Как уже упоминалось, это значительно ограничит число одновременных пользователей, которых вы можете поддерживать.)

Для сервера необходимо установить Response.Buffer = false и иметь расширенный ScriptTimeout (я предполагаю, что вы используете ASP.NET на стороне сервера). После того, как вы это сделаете, ваша страница может продолжать отправлять данные Response.Write по мере необходимости, пока все, что она делает, не будет сделано.

Ваш клиент должен будет обработать входящий Ответ до завершения соединения, а не блокировать его для полного ответа.

1 голос
/ 30 мая 2011

Вам необходимо получить cookie с IP-камеры и включить этот файл cookie в заголовок вашего следующего запроса HttpWebRequest. В противном случае он всегда будет пытаться перенаправить вас на «index.html».
Вот как вы можете это сделать ...

BitmapObject - это класс, который служит контейнером для изображения Jpeg, текущей даты и текста возможной ошибки. Как только соединение установлено, оно будет создавать пул каждые 200 мс. То же самое должно быть применимо к непрерывному потоку изображений, получаемых через «serverpush».

public void Connect()
{
    try
    {
        request = (HttpWebRequest)WebRequest.Create("Http://192.168.0.2/index.html");

        request.Credentials = new NetworkCredential(UserName,Password);
        request.Method = "GET";
        response = (HttpWebResponse)request.GetResponse();
        WebHeaderCollection headers = response.Headers;
        Cookie = headers["Set-Cookie"];//get cookie

        GetImage(null);
    }
    catch (Exception ex)
    {
        BitmapObject bitmap = new BitmapObject(Properties.Resources.Off,DateTime.Now);
        bitmap.Error = ex.Message;
        onImageReady(bitmap);
    }
}

private Stream GetStream()
{
    Stream s = null;
    try
    {
        request = (HttpWebRequest)WebRequest.Create("http://192.168.0.2/liveimg.cgi");
        if (!Anonimous)
            request.Credentials = new NetworkCredential(UserName, Password);
        request.Method = "GET";
        request.KeepAlive = KeepAlive;

        request.Headers.Add(HttpRequestHeader.Cookie, Cookie);
        response = (HttpWebResponse)request.GetResponse();
        s = response.GetResponseStream();

    }
    catch (Exception ex)
    {
        BitmapObject bitmap = new BitmapObject(Properties.Resources.Off,DateTime.Now);
        bitmap.Error = ex.Message;
        onImageReady(bitmap);
    }
    return s;
}

public void GetImage(Object o)
{
    BitmapObject bitmap = null;
    stream = GetStream();
    DateTime CurrTime = DateTime.Now;
    try
    {
        bitmap = new BitmapObject(new Bitmap(stream),CurrTime);
        if (timer == null)//System.Threading.Timer
            timer = new Timer(new TimerCallback(GetImage), null, 200, 200);
    }
    catch (Exception ex)
    {
        bitmap = new BitmapObject(Properties.Resources.Off, CurrTime);
        bitmap.Error = ex.Message;
    }
    finally
    {
        stream.Flush();
        stream.Close();
    }
    onImageReady(bitmap);
}
1 голос
/ 16 июня 2009

Если я правильно вас понимаю, ваш сервер собирается ответить на какое-то событие, отправив данные вашему клиенту за пределами клиента, сделав запрос / ответ. Это правильно? Если это так, я бы не рекомендовал пытаться держать соединение открытым, если у вас очень небольшое количество клиентов - доступно ограниченное количество соединений, поэтому их открытие может быстро привести к исключению.

Вероятно, самое простое решение - периодически запрашивать у клиентов новые данные. Это позволит вам использовать простой сервер, и вам потребуется всего лишь кодировать поток на клиенте, чтобы запрашивать какие-либо изменения или новую работу раз в минуту или тридцать секунд или в любое другое время.

Если вы действительно хотите, чтобы сервер уведомлял клиентов заблаговременно, без их опроса, вам нужно будет сделать что-то, кроме простого веб-сервера, - вам также придется кодировать и настраивать клиент для принятия. входящие запросы. Это может быть сложно, если ваши клиенты работают за брандмауэрами и тому подобным. Если вы пойдете по этому пути, WCF, вероятно, ваш лучший выбор, поскольку он позволит вам настроить сервер и клиент соответствующим образом.

0 голосов
/ 16 июня 2009

Если вы пользуетесь стандартным веб-сервером, он никогда ничего вам не подтолкнет - вместо этого вашему клиенту придется периодически вытягивать его.

Чтобы действительно получить данные о проталкивании сервера, вы должны создать такой сервер самостоятельно.

...