Поиск:

Ответ в темуСоздание новой темы Создание опроса
> Убрать кеширование запросов в интернет, Убрать кеширование запросов в интернет 
V
    Опции темы
Bima
Дата 18.12.2006, 08:57 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


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

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



Делаю программу, которая проверяет размер файла из интернета, но заметил странную особенность. Если запустить программу и сразу запросить размер файла, то мне программа ВСЕГДА выдает размер 2379, но стоит хоть раз скачать этот файл, то программа выдает истинный размер файла. Пробовал на многих файлах из интернета, всегда одно и тоже. Такое ощущение, что запрос где то кешируется и если в кеше нет информации о файле, то запрос возвращает любое число.

Код программы:
Код

//---------------------------------------------------------------------------
#include <memory>
#include <vcl.h>
#include <urlmon.h>
#pragma comment(lib,"urlmon.lib")
#include <wininet.h>
#pragma comment(lib,"wininet.lib")

#include "Kod.h"
//---------------------------------------------------------------------------
#pragma package(smart_init)
#pragma resource "*.dfm"
TForm1 *Form1;
__int64 GetInetFileSize(char *url);
AnsiString myUrl;
AnsiString MyFile;
//---------------------------------------------------------------------------
__fastcall TForm1::TForm1(TComponent* Owner):TForm(Owner){}
//---------------------------------------------------------------------------
void __fastcall TForm1::Button1Click(TObject *Sender)
{
int retcode;
retcode = URLDownloadToFile( NULL, myUrl.c_str(), MyFile.c_str(), 0, 0 );
Label1->Caption=IntToStr(retcode);
}
//---------------------------------------------------------------------------
void __fastcall TForm1::Button2Click(TObject *Sender)
{
myUrl="http://www.biminc.narod.ru/Test.zip";
MyFile="c:\\Test.zip";
__int64 a;
a=GetInetFileSize(myUrl.c_str() );
Label1->Caption=IntToStr(a);
}
//---------------------------------------------------------------------------
void __fastcall TForm1::Button3Click(TObject *Sender)
{
myUrl="http://www.drweb.ru/bases/dwrtoday.zip";
MyFile="c:\\dwrtoday.zip";
__int64 a;
a=GetInetFileSize(myUrl.c_str());
Label1->Caption=IntToStr(a);
}
//---------------------------------------------------------------------------
__int64 GetInetFileSize(char *url)
{
HINTERNET hInet, hUrl;
char nSize[32];
__int64 Size;
DWORD nBuffLen;

hInet = InternetOpen("YOUR_AGENT",//"Microsoft Internet Explorer",
                     NULL,
                     NULL,
                     NULL,
                     NULL);
if (hInet != NULL)
   {
   Form1->Label3->Caption=IntToStr(Integer(hInet));  //ShowMessage("hInet="+IntToStr(Integer(hInet)));
   hUrl = InternetOpenUrl(hInet,
                          url,
                          NULL,
                          NULL,
                          NULL,
                          NULL);
   Form1->Label5->Caption=IntToStr(Integer(hUrl));//ShowMessage("hUrl="+IntToStr(Integer(hUrl)));
   if (hUrl != NULL)
      {
      nBuffLen = sizeof(nSize);
      if (HttpQueryInfo(hUrl,
                        HTTP_QUERY_CONTENT_LENGTH,
                        &nSize,
                        &nBuffLen,
                        0))
         Size=StrToInt(AnsiString(nSize));//ShowMessage("File size: "+AnsiString(nSize));
      else
         {
         MessageBoxA(Application->Handle , SysErrorMessage(GetLastError()).c_str(), "Error", 16);
         }
      InternetCloseHandle(hUrl);
      }
   InternetCloseHandle(hInet);
   }
return Size;
}
//---------------------------------------------------------------------------


P.S. дома пробовал эту программу на DialUp все проходит нормально, все запросы нормально обрабатываются и программы выдает реальный размер файла сразу, а на работе стоит выделенка через корпоративный прокси.

Как решить данную проблему???


--------------------
Чтобы дойти до цели, надо идти.

Клавиатура и мышь - это главные инструменты прогресса.
PM MAIL WWW   Вверх
Bima
Дата 18.12.2006, 13:50 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


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

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



Я сам разобрался.
Для того, что бы ответы от запросов нормально отображались, нужно использовать соответствующие флаги:
Код

__int64 GetInetFileSize(char *url)
{
HINTERNET hInet, hUrl;
char nSize[32];
__int64 Size;
DWORD nBuffLen;
Size=0; // сброс (можно использовать -1, тогда легче отследить, как сработала функция)

hInet = InternetOpen("Microsoft Internet Explorer",
                     INTERNET_OPEN_TYPE_PRECONFIG, // <- использовать этот флаг
                     NULL,
                     NULL,
                     NULL);
if (hInet != NULL)
   {
   Form1->Label3->Caption=IntToStr(Integer(hInet));
   hUrl = InternetOpenUrl(hInet,
                          url,
                          NULL,
                          NULL,
                          INTERNET_FLAG_EXISTING_CONNECT,  // <- использовать при текущем соединении
                          NULL);
   Form1->Label5->Caption=IntToStr(Integer(hUrl));
   if (hUrl != NULL)
      {
      nBuffLen = sizeof(nSize);
      if (HttpQueryInfo(hUrl,
                        HTTP_QUERY_CONTENT_LENGTH ,
                        &nSize,
                        &nBuffLen,
                        0))
         Size=StrToInt(AnsiString(nSize));//ShowMessage("File size: "+AnsiString(nSize));
      else
         {
         MessageBoxA(Application->Handle , SysErrorMessage(GetLastError()).c_str(), "Error", 16);
         }
      InternetCloseHandle(hUrl);
      }
   InternetCloseHandle(hInet);
   }
return Size;
}



--------------------
Чтобы дойти до цели, надо идти.

Клавиатура и мышь - это главные инструменты прогресса.
PM MAIL WWW   Вверх
Bima
Дата 2.2.2007, 07:09 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


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

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



Опять столкнулся с этой проблемой.
Задача такая: через определенные промежутки времени проверять на сервере размер файла и если он изменился, то закачать его.

код такой:
Код

NewSize=GetInetFileSize (MyURL.c_str()); //код этой подпрограммы смотрите выше
if (NewSize!=OldSize)
   {
   URLDownloadToFile(NULL, MyURL.c_str(), MyFile.c_str(), 0, 0 ); //Закачиваем файл
   OldSize=NewSize;
   }

Если запустить программу, то она хорошо работает, пока не закачает новый файл, а потом всегда показывает один и тот же размер, даже если размер файла изменился на сервере. После долгих поисков, я нашел, что программа кеширует файлы в папку:
c:\Documents and Settings\<имя пользователя>\Local Settings\Temporary Internet Files\Content.IE5\<произвольная папка>\файл

Если во время работы программы удалять файл, то программа начинает работать, как только что ее запустили. Я бы может быть обошел это ограничение (удалял бы эти файлы), но система сама создает <произвольная папки> с неизвестным названием.. ну типа QH8O6I5R

я попробовал другой код:
Код

NewSize=GetInetFileSize (MyURL.c_str()); //код этой подпрограммы смотрите выше
if (NewSize!=OldSize)
   {
   HINTERNET hInet, hUrl;
   hInet = InternetOpen("Microsoft Internet Explorer",
                     INTERNET_OPEN_TYPE_PRECONFIG,
                     NULL,
                     NULL,
                     NULL);
   if (hInet != NULL)
      {
      hUrl = InternetOpenUrl(hInet,
                          MyURL.c_str(),
                          NULL,
                          NULL,
                          INTERNET_FLAG_NO_CACHE_WRITE,//INTERNET_FLAG_RELOAD
                          NULL);
      if (hUrl != NULL)
         {
         URLDownloadToFile(NULL, MyURL.c_str(), MyFile.c_str(), 0, 0 ); //Закачиваем файл
         OldSize=NewSize;
         }
      else
         FDownExtr->SaveLog("Error URLDownloadToFile: "+SysErrorMessage(GetLastError()),2);   // Log-файл
      InternetCloseHandle(hUrl);
      }
   }

работает также (то есть до первого скачивания), только для внешних сайтов. Я для экспериментов использовал на соседнем компьютере web-сервер apache и туда поместил тестовый файл. Так вот, с этого сервера все нормально скачивается и определяется, а вот если я задаю внешний сервер (на narod.ru или какой другой), то программа работает до первого скачивания.
я пробовал разные флаги в функции InternetOpenUrl (INTERNET_FLAG_NO_CACHE_WRITE, INTERNET_FLAG_RELOAD и их комбинацию), но ничего не помогает.
Я предпологаю, что при больших задержках эта функция начинает кешировать. Может как нибудь убрать таймауты, что кеширования не было?
Как мне убрать кеширование??? 

Это сообщение отредактировал(а) Bima - 2.2.2007, 13:57


--------------------
Чтобы дойти до цели, надо идти.

Клавиатура и мышь - это главные инструменты прогресса.
PM MAIL WWW   Вверх
_hunter
Дата 2.2.2007, 12:11 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
****


Профиль
Группа: Участник Клуба
Сообщений: 8564
Регистрация: 24.6.2003
Где: Europe::Ukraine:: Kiev

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



поробуй еще и INTERNET_FLAG_RESYNCHRONIZE с INTERNET_FLAG_PRAGMA_NOCACHE к тем двум добавить...


--------------------
Tempora mutantur, et nos mutamur in illis...
PM ICQ   Вверх
Bima
Дата 2.2.2007, 13:55 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


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

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



Попробовал. Не помогает smile
 делал так:
Код

// код подпрограммы (см. выше)

      hUrl = InternetOpenUrl(hInet,
                          MyURL.c_str(),
                          NULL,
                          NULL,
                          INTERNET_FLAG_RELOAD & INTERNET_FLAG_NO_CACHE_WRITE & INTERNET_FLAG_RESYNCHRONIZE & INTERNET_FLAG_PRAGMA_NOCACHE,
                          NULL);
      if (hUrl != NULL)
         {
         URLDownloadToFile(NULL, MyURL.c_str(), MyFile.c_str(), 0, 0 ); //Закачиваем файл
         OldSize=NewSize;
         }

// код подпрограммы (см. выше)

Заметил еще одну закономерность. Иногда если не трогать кеш, программа начинает работать через 4 часа. То есть такое ощущение, что данные в кеше становятся не актуальны через 4 часа.
Может быть то соединение, которое я создаю до команды URLDownloadToFile, не действуют на эту команду???
Посмотрел в MSDN, вроде привязок к текущему соединению нет.
Может какой другой командой можно файл скачать???

Добавлено @ 14:01 
P.S. забыл добавить, с локальным сервером Apache все работает нормально


--------------------
Чтобы дойти до цели, надо идти.

Клавиатура и мышь - это главные инструменты прогресса.
PM MAIL WWW   Вверх
Romikgy
Дата 2.2.2007, 14:02 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Любитель-программер
****


Профиль
Группа: Участник Клуба
Сообщений: 7326
Регистрация: 11.5.2005
Где: Porto Franco Odes sa

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



Цитата(Bima @  2.2.2007,  12:55 Найти цитируемый пост)
INTERNET_FLAG_RELOAD & INTERNET_FLAG_NO_CACHE_WRITE & INTERNET_FLAG_RESYNCHRONIZE & INTERNET_FLAG_PRAGMA_NOCACHE,
                          

а разве не через | эту вещь надо объединять?


--------------------
Владение русской орфографией это как владение кунг-фу — истинные мастера не применяют его без надобности. 
smile

PM   Вверх
Bima
Дата 2.2.2007, 14:09 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


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

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



Цитата

а разве не через | эту вещь надо объединять? 


хм, это получяется если использовать или для объединения, то по логике вещей нужно читать так:
использовать или INTERNET_FLAG_RELOAD или INTERNET_FLAG_NO_CACHE_WRITE  и т.д.
но если рассуждать с точки зрения математики, то если складывать побитно  через "или" два числа 110 и 011 то получится 111,
а если складывать по "и", то 010.
Romikgy скорее всего ты прав, сейчас попробую проверить.


--------------------
Чтобы дойти до цели, надо идти.

Клавиатура и мышь - это главные инструменты прогресса.
PM MAIL WWW   Вверх
Bima
Дата 2.2.2007, 14:55 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


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

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



попробовал и "|" и "||" не помогает. Все равно в кэше появляются файлы. И программа не определяет правильно размер smile, соответственно и не скачивает уже обновленный файл.


--------------------
Чтобы дойти до цели, надо идти.

Клавиатура и мышь - это главные инструменты прогресса.
PM MAIL WWW   Вверх
dumb
Дата 2.2.2007, 15:19 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


sceloglauxalbifacies
****


Профиль
Группа: Экс. модератор
Сообщений: 2929
Регистрация: 16.6.2006

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



достаточно INTERNET_FLAG_PRAGMA_NOCACHE | INTERNET_FLAG_NO_CACHE_WRITE, причем второй не является необходимым.

файл в кэше, связанный с ресурсом, можно удалить так: DeleteUrlCacheEntry(MyURL.c_str());
PM MAIL   Вверх
Bima
Дата 5.2.2007, 07:00 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


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

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



Цитата

DeleteUrlCacheEntry(MyURL.c_str()); 

Файл в кеше создается под именем не тем, с которым я качаю, а еще с префиксом [1], то есть если я качаю файл test.zip, то в кеше появляется файл test[1].zip или test[2].zip и т.д.


--------------------
Чтобы дойти до цели, надо идти.

Клавиатура и мышь - это главные инструменты прогресса.
PM MAIL WWW   Вверх
dumb
Дата 5.2.2007, 09:26 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


sceloglauxalbifacies
****


Профиль
Группа: Экс. модератор
Сообщений: 2929
Регистрация: 16.6.2006

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



Цитата(Bima @  5.2.2007,  07:00 Найти цитируемый пост)
Файл в кеше создается под именем не тем, с которым я качаю, а еще с префиксом [1], то есть если я качаю файл test.zip, то в кеше появляется файл test[1].zip или test[2].zip и т.д. 

и что? - ты не заметил, что функция называется не DeleteFile, и что на вход функции дается не имя файла, а урл?
PM MAIL   Вверх
Bima
Дата 5.2.2007, 09:31 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


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

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



Цитата

и что? - ты не заметил, что функция называется не DeleteFile, и что на вход функции дается не имя файла, а урл? 

Признаю, свою ошибку!!! smile 
Вставил, эту команду в программу, все заработало.
Думаю, что тему можно считать закрытой.


--------------------
Чтобы дойти до цели, надо идти.

Клавиатура и мышь - это главные инструменты прогресса.
PM MAIL WWW   Вверх
  
Ответ в темуСоздание новой темы Создание опроса
Правила форума "С++ Builder"
Rrader

Запрещается!

1. Публиковать ссылки на вскрытые компоненты

2. Обсуждать взлом компонентов и делиться вскрытыми компонентами

  • Литературу по С++ Builder обсуждаем здесь
  • Действия модераторов можно обсудить здесь
  • С просьбами о написании курсовой, реферата и т.п. обращаться сюда
  • Настоятельно рекомендуем заглянуть в DRKB (Delphi Russian Knowledge Base) - крупнейший в рунете сборник материалов по Дельфи


Если Вам понравилась атмосфера форума, заходите к нам чаще! С уважением, Rrader.

 
0 Пользователей читают эту тему (0 Гостей и 0 Скрытых Пользователей)
0 Пользователей:
« Предыдущая тема | C++ Builder | Следующая тема »


 




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


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

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