Изменение пользовательского агента элемента управления WebBrowser
Я пытаюсь изменить UserAgent элемента управления WebBrowser в приложении Winforms.
Я успешно достиг этого, используя следующий код:
[DllImport("urlmon.dll", CharSet = CharSet.Ansi)]
private static extern int UrlMkSetSessionOption(
int dwOption, string pBuffer, int dwBufferLength, int dwReserved);
const int URLMON_OPTION_USERAGENT = 0x10000001;
public void ChangeUserAgent()
{
List<string> userAgent = new List<string>();
string ua = "Googlebot/2.1 (+http://www.google.com/bot.html)";
UrlMkSetSessionOption(URLMON_OPTION_USERAGENT, ua, ua.Length, 0);
}
Единственная проблема заключается в том, что это работает только один раз. Когда я пытаюсь запустить метод ChangeUserAgent() во второй раз, он не работает. Он остается установленным для первого измененного значения. Это довольно раздражает, и я пробовал все, но он просто не изменится более одного раза.
Кто-нибудь знает о другом, более гибком подходе?
Спасибо
Ответы
Ответ 1
Я не уверен, следует ли мне просто скопировать/вставить с веб-сайт, но я предпочел бы оставить здесь ответ вместо ссылка. Если кто-то может прояснить в комментариях, я буду очень благодарен.
В принципе, вам нужно расширить класс WebBrowser.
public class ExtendedWebBrowser : WebBrowser
{
bool renavigating = false;
public string UserAgent { get; set; }
public ExtendedWebBrowser()
{
DocumentCompleted += SetupBrowser;
//this will cause SetupBrowser to run (we need a document object)
Navigate("about:blank");
}
void SetupBrowser(object sender, WebBrowserDocumentCompletedEventArgs e)
{
DocumentCompleted -= SetupBrowser;
SHDocVw.WebBrowser xBrowser = (SHDocVw.WebBrowser)ActiveXInstance;
xBrowser.BeforeNavigate2 += BeforeNavigate;
DocumentCompleted += PageLoaded;
}
void PageLoaded(object sender, WebBrowserDocumentCompletedEventArgs e)
{
}
void BeforeNavigate(object pDisp, ref object url, ref object flags, ref object targetFrameName,
ref object postData, ref object headers, ref bool cancel)
{
if (!string.IsNullOrEmpty(UserAgent))
{
if (!renavigating)
{
headers += string.Format("User-Agent: {0}\r\n", UserAgent);
renavigating = true;
cancel = true;
Navigate((string)url, (string)targetFrameName, (byte[])postData, (string)headers);
}
else
{
renavigating = false;
}
}
}
}
Примечание. Чтобы использовать вышеописанный метод, вам необходимо добавить ссылку COM на "Microsoft Internet Controls".
Он также упоминает ваш подход и заявляет, что элемент управления WebBrowser, похоже, кэширует эту строку пользовательского агента, поэтому он не будет изменять агент пользователя без перезапуска процесса.
Ответ 2
Самый простой способ:
webBrowser.Navigate("http://localhost/run.php", null, null,
"User-Agent: Here Put The User Agent");
Ответ 3
Кроме того, в функции есть опция обновления (согласно MSDN). Он работал хорошо для меня (вы должны установить его перед изменением любого пользовательского агента). Тогда код вопроса можно было бы изменить следующим образом:
[DllImport("urlmon.dll", CharSet = CharSet.Ansi)]
private static extern int UrlMkSetSessionOption(
int dwOption, string pBuffer, int dwBufferLength, int dwReserved);
const int URLMON_OPTION_USERAGENT = 0x10000001;
const int URLMON_OPTION_USERAGENT_REFRESH = 0x10000002;
public void ChangeUserAgent()
{
string ua = "Googlebot/2.1 (+http://www.google.com/bot.html)";
UrlMkSetSessionOption(URLMON_OPTION_USERAGENT_REFRESH, null, 0, 0);
UrlMkSetSessionOption(URLMON_OPTION_USERAGENT, ua, ua.Length, 0);
}
Ответ 4
Я хотел бы добавить к ответу @Jean Azzopardi.
void BeforeNavigate(object pDisp, ref object url, ref object flags, ref object targetFrameName,
ref object postData, ref object headers, ref bool cancel)
{
// This alone is sufficient, because headers is a "Ref" parameters, and the browser seems to pick this back up.
headers += string.Format("User-Agent: {0}\r\n", UserAgent);
}
Это решение работало лучше всего для меня. Использование renavigating вызвало другие странные проблемы для меня, такие как содержимое браузера, внезапно исчезающее, а иногда и получение Unsupported Browser. С помощью этой техники все запросы в Fiddler имели правильный User Agent.