Модераторы: feodorv
  

Поиск:

Ответ в темуСоздание новой темы Создание опроса
> Передача структуры через сокеты, Передать запрос от клиента к серверу 
V
    Опции темы
Gwynbleiddd
Дата 19.2.2012, 22:41 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Новичок



Профиль
Группа: Участник
Сообщений: 19
Регистрация: 25.3.2008

Репутация: нет
Всего: нет



Добрый день.

Возник вопрос, решение найти не получается.

Необходимо принять запрос от клиента типа GET, разбить его на составные части (распарсить) (User-Agent, Accept и т.п.), записать все части в структуру, затем при необходимости модифицировать отдельные части этого запроса и, наконец, послать серверу.

C приёмом, разбивкой запроса на части и записью в структуру вроде вопросов нет.

Не понимаю как теперь собрать заново модифицированный запрос и отправить его серверу.

Допустим, вот есть запрос:

Код

GET http://www.test1.ru/ HTTP/1.1
User-Agent: Opera/9.80 (Windows NT 6.1; U; ru) Presto/2.10.229 Version/11.60
Host: www.test1.ru
Accept: text/html, application/xml;q=0.9, application/xhtml+xml, image/png, imag
e/webp, image/jpeg, image/gif, image/x-xbitmap, */*;q=0.1
Accept-Language: ru-RU,ru;q=0.9,en;q=0.8
Accept-Encoding: gzip, deflate
Pragma: no-cache
Cache-Control: no-cache
Proxy-Connection: Keep-Alive



Есть структура, в которую мы по частям записали весь запрос. 
Код

struct Request
{
    char Command [3];
    char Site [50];
    char Protocol [10];
    char User_Agent[128];
    char Host[50];
    char Accept[1024];
    char Accept_Language[512];
    char Accept_Encoding[128];
    char Cookie [1024];
    char Pragma[10];
    char Cache_Control[10];
    char Proxy_Connection[10];
};


Содержание структуры следующее
Код

char Command [] = "GET";
char Site [] = "www.test1.ru";
char Protocol [] = " HTTP/1.1";
char User_Agent[] =  "Opera/9.80 (Windows NT 6.1; U; ru) Presto/2.10.229 Version/11.60";

и т.д.


Как теперь послать её серверу?

Заранее Спасибо smile
PM MAIL   Вверх
feodorv
Дата 20.2.2012, 00:14 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
****


Профиль
Группа: Комодератор
Сообщений: 2214
Регистрация: 30.7.2011

Репутация: 10
Всего: 45



Цитата(Gwynbleiddd @  19.2.2012,  22:41 Найти цитируемый пост)
Как теперь послать её серверу?

А в чём, собственно, проблема?
Например, можно собрать запрос согласно спецификации HTTP/1.1 в один буфер, и этот буфер отослать серверу. Буфер можно заказать (alloc etc), можно и определить фиксированного размера (поля-то в Вашей структуре фиксированы по размеру, нужно будет только учесть размер текста заголовков c ':' и ' ', \r\n на каждый заголовок и \r\n\r\n на самый конец запроса).

Цитата(Gwynbleiddd @  19.2.2012,  22:41 Найти цитируемый пост)
char Command [3];

Маловато для команды, уже простой POST не влезает...

Цитата(Gwynbleiddd @  19.2.2012,  22:41 Найти цитируемый пост)
    char Site [50];

Нужна только главная страница сайта, или что-то ещё внутри него?

Добавлено @ 00:23
Вот кусок моего кода на Си, реализующего формирование запроса (через буфер переменной длины):
Код

Boolean hiHttpStart( struct hi_http_s *hh, Boolean isPost, const char *get)
{
  char hostName[AZ_NET_IP_MAXSIZE];
  struct az_stritem_s *si;
  Boolean success;

  azNetIpPut( hh->device->dev->ip, hostName, sizeof(hostName));

/* GET/POST */
  if( isPost )
    success = azDataBufferAdd( &hh->header, (unsigned char *) "POST", 4, NULL);
  else
    success = azDataBufferAdd( &hh->header, (unsigned char *) "GET", 3, NULL);

  if( success ) success = azDataBufferAddChar( &hh->header, ' ', NULL);
  if( success ) success = azDataBufferAdd( &hh->header, (unsigned char *) get, AZ_STRLEN(get), NULL);
  if( success ) success = azDataBufferAdd( &hh->header, (unsigned char *) " HTTP/1.1\r\n", 11, NULL);

/* Accept & Acccept-Charset & Accept-Language */
  if( success ) success = azDataBufferAdd( &hh->header,  (unsigned char *) "Accept: */*\r\n", 13, NULL);
  if( success ) success = azDataBufferAdd( &hh->header,  (unsigned char *) "Accept-Language: ru\r\n", 21, NULL);
  if( success ) success = azDataBufferAdd( &hh->header,  (unsigned char *) "Accept-Charset: koi8-r\r\n", 24, NULL);

/* Host */
  if( success ) success = azDataBufferAdd( &hh->header, (unsigned char *) "Host: ", 6, NULL);
  if( success ) success = azDataBufferAdd( &hh->header, (unsigned char *) hostName, AZ_STRLEN(hostName), NULL);
  if( success ) success = azDataBufferAdd( &hh->header,  (unsigned char *) "\r\n", 6, NULL);

/* Referer */
  if( success ) success = azDataBufferAdd( &hh->header, (unsigned char *) "Referer: http://", 16, NULL);
  if( success ) success = azDataBufferAdd( &hh->header, (unsigned char *) hostName, AZ_STRLEN(hostName), NULL);
  if( success ) success = azDataBufferAdd( &hh->header, (unsigned char *) DEFAULT_MAINPAGE, sizeof(DEFAULT_MAINPAGE)-1, NULL);
  if( success ) success = azDataBufferAdd( &hh->header, (unsigned char *) "\r\n", 2, NULL);

/* Cookies */
  if( success ) for( si = hh->device->cookies.head; si != NULL; si = si->next)
    if( !azDataBufferAdd( &hh->header, (unsigned char *) "Cookie: ", 8, NULL) ||
        !azDataBufferAdd( &hh->header, (unsigned char *) si->string, si->length, NULL) ||
        !azDataBufferAdd( &hh->header, (unsigned char *) "\r\n", 2, NULL) )
    {
      success = False;
      break;
    }

/* Boundary */
  if( success && hh->isMultiPart && isPost )
  {
    success = azDataBufferAdd( &hh->header,  (unsigned char *) "Content-Type: multipart/form-data; boundary=", 44, NULL);
    if( success ) success = azDataBufferAdd( &hh->header,  (unsigned char *) hh->boundary, AZ_STRLEN(hh->boundary), NULL);
    if( success ) success = azDataBufferAdd( &hh->header, (unsigned char *) "\r\n", 2, NULL);
  }

  if( !success )
  {
     ...
  }

  return success;
}

Boolean hiHttpFinish( struct hi_http_s *hh )
{
  Boolean success = True;

  if( hh->isMultiPart && hh->post.length > 0 )
  {
    success = azDataBufferAdd( &hh->post,  (unsigned char *) "--", 2, NULL);
    if( success ) success = azDataBufferAdd( &hh->post,  (unsigned char *) hh->boundary, AZ_STRLEN(hh->boundary), NULL);
    if( success ) success = azDataBufferAdd( &hh->post,  (unsigned char *) "--", 2, NULL);
    if( success ) success = azDataBufferAdd( &hh->post,  (unsigned char *) "\r\n", 2, NULL);
  }

  if( hh->post.length > 0 )
  {
    char buf[1024];
    wsprintf( buf, "Content-Length: %d\r\n", hh->post.length);
    success = azDataBufferAdd( &hh->header, (unsigned char *) buf, AZ_STRLEN(buf), NULL);
  }

  if( success ) success = azDataBufferAdd( &hh->header,  (unsigned char *) "\r\n", 2, NULL);

  if( !success )
  {
    ...
  }

  return success;
}


Это сообщение отредактировал(а) feodorv - 20.2.2012, 00:25


--------------------
Напильник, велосипед, грабли и костыли - основные инструменты программиста...
PM MAIL   Вверх
Alexeis
Дата 20.2.2012, 09:13 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Амеба
Group Icon


Профиль
Группа: Админ
Сообщений: 11743
Регистрация: 12.10.2005
Где: Зеленоград

Репутация: 1
Всего: 459



Если не важен строго С, то можно сделать так
Код

    std::stringstream buf;
    buf << "GET" << std::endl << "www.test1.ru" << std::endl <<  " HTTP/1.1" << std::endl;
    std::string s = buf.str();



--------------------
Vit вечная память.

Обсуждение действий администрации форума производятся только в этом форуме

гениальность идеи состоит в том, что ее невозможно придумать
PM ICQ Skype   Вверх
Alca
Дата 20.2.2012, 11:21 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
****


Профиль
Группа: Завсегдатай
Сообщений: 3993
Регистрация: 14.6.2006

Репутация: 1
Всего: 50



snprintf


--------------------
PM WWW ICQ Skype Jabber   Вверх
Gwynbleiddd
Дата 20.2.2012, 17:54 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Новичок



Профиль
Группа: Участник
Сообщений: 19
Регистрация: 25.3.2008

Репутация: нет
Всего: нет



Спасибо большое за ответы.

1. Вчера долго соображал как передать запрос, который хранится в структуре. Сегодня утром пришла мысль "Зачем передавать структуру, когда можно функциями strcat "склеить" все поля запроса в один буфер и просто передать этот буфер?" 
Утро вечера мудренее, сегодня именно так попробую smile

2. Размеры полей структуры писал "на глаз", т.к. сейчас работал с определённым запросом и главное было модифицировать и послать его. Так сказать,  пробная версия.

3. Сейчас посмотрю код на формирование запроса, надеюсь поможет )

4. Нужно именно на Си, С++ не подходит
PM MAIL   Вверх
  
Ответ в темуСоздание новой темы Создание опроса
0 Пользователей читают эту тему (0 Гостей и 0 Скрытых Пользователей)
0 Пользователей:
« Предыдущая тема | C/C++: Сети | Следующая тема »


 




[ Время генерации скрипта: 0.0517 ]   [ Использовано запросов: 22 ]   [ GZIP включён ]


Реклама на сайте     Информационное спонсорство

 
По вопросам размещения рекламы пишите на vladimir(sobaka)vingrad.ru
Отказ от ответственности     Powered by Invision Power Board(R) 1.3 © 2003  IPS, Inc.