From de9de473434e6faf95792553db53c4e42a20011d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=98=D0=BD=D1=8E=D1=82=D0=B8=D0=BD=20=D0=9C=D0=B0=D0=BA?= =?UTF-8?q?=D1=81=D0=B8=D0=BC=20=D0=9D=D0=B8=D0=BA=D0=BE=D0=BB=D0=B0=D0=B5?= =?UTF-8?q?=D0=B2=D0=B8=D1=87?= Date: Sun, 10 Mar 2019 02:12:26 +0300 Subject: [PATCH] #625 AuthorizationFormHtmlParser.cs --- .../AuthorizationFormHtmlParserTests.cs | 109 ++++ .../Infrastructure/ImplicitFlowTests.cs | 41 +- .../TestData/Authorization/captcha.html | 302 +++++++++ .../TestData/Authorization/consent.html | 301 +++++++++ VkNet.Tests/TestData/Authorization/error.html | 15 + VkNet.Tests/TestData/Authorization/login.html | 290 +++++++++ .../TestData/Authorization/success.html | 15 + VkNet.Tests/TestData/Authorization/twofa.html | 612 ++++++++++++++++++ .../TestData/Authorization/twofa_error.html | 280 ++++++++ .../Utils/ImplicitFlowVkAuthorizationTests.cs | 14 +- .../ImplicitFlow/AbstractAuthorizationForm.cs | 2 +- .../AuthorizationFormHtmlParser.cs | 42 +- .../Authorization/ImplicitFlow/ConsentForm.cs | 5 +- .../IAuthorizationFormHtmlParser.cs | 3 +- .../ImplicitFlowCaptchaLoginForm.cs | 4 +- .../ImplicitFlow/ImplicitFlowLoginForm.cs | 4 +- .../ImplicitFlow/TwoFactorForm.cs | 4 +- VkNet/VkApi.cs | 2 +- 18 files changed, 2010 insertions(+), 35 deletions(-) create mode 100644 VkNet.Tests/Infrastructure/AuthorizationFormHtmlParserTests.cs create mode 100644 VkNet.Tests/TestData/Authorization/captcha.html create mode 100644 VkNet.Tests/TestData/Authorization/consent.html create mode 100644 VkNet.Tests/TestData/Authorization/error.html create mode 100644 VkNet.Tests/TestData/Authorization/login.html create mode 100644 VkNet.Tests/TestData/Authorization/success.html create mode 100644 VkNet.Tests/TestData/Authorization/twofa.html create mode 100644 VkNet.Tests/TestData/Authorization/twofa_error.html diff --git a/VkNet.Tests/Infrastructure/AuthorizationFormHtmlParserTests.cs b/VkNet.Tests/Infrastructure/AuthorizationFormHtmlParserTests.cs new file mode 100644 index 000000000..4feece3f5 --- /dev/null +++ b/VkNet.Tests/Infrastructure/AuthorizationFormHtmlParserTests.cs @@ -0,0 +1,109 @@ +using System; +using System.Collections.Generic; +using System.IO; +using System.Text; +using System.Threading.Tasks; +using Flurl; +using Flurl.Http.Testing; +using Moq.AutoMock; +using NUnit.Framework; +using VkNet.Infrastructure.Authorization.ImplicitFlow; + +namespace VkNet.Tests.Infrastructure +{ + [TestFixture] + public class AuthorizationFormHtmlParserTests + { + [Test] + public async Task LoginForm() + { + using (var httpTest = new HttpTest()) + { + httpTest.RespondWith(ReadHtmlFile("login")); + var mocker = new AutoMocker(); + + var parser = mocker.CreateInstance(); + var result = await parser.GetFormAsync(new Url("https://m.vk.com/login?act=authcheck&m=442")); + + Assert.NotNull(result); + Assert.AreEqual("post", result.Method); + Assert.AreEqual("https://login.vk.com/?act=login&soft=1&utf8=1", result.Action); + Assert.IsNotEmpty(result.Fields); + } + } + + [Test] + public async Task CaptchaForm() + { + using (var httpTest = new HttpTest()) + { + httpTest.RespondWith(ReadHtmlFile("captcha")); + var mocker = new AutoMocker(); + + var parser = mocker.CreateInstance(); + var result = await parser.GetFormAsync(new Url("https://m.vk.com/login?act=authcheck&m=442")); + + Assert.NotNull(result); + Assert.AreEqual("post", result.Method); + Assert.AreEqual("https://login.vk.com/?act=login&soft=1&utf8=1", result.Action); + Assert.IsNotEmpty(result.Fields); + } + } + + [Test] + public async Task TwoFaForm() + { + using (var httpTest = new HttpTest()) + { + httpTest.RespondWith(ReadHtmlFile("twofa")); + var mocker = new AutoMocker(); + + var parser = mocker.CreateInstance(); + var result = await parser.GetFormAsync(new Url("https://m.vk.com/login?act=authcheck&m=442")); + + Assert.NotNull(result); + Assert.AreEqual("post", result.Method); + Assert.AreEqual("https://m.vk.com/login?act=authcheck_code&hash=1552162040_c98f31a6e83d3c91c1", result.Action); + Assert.IsNotEmpty(result.Fields); + } + } + + [Test] + public async Task ConsentForm() + { + using (var httpTest = new HttpTest()) + { + httpTest.RespondWith(ReadHtmlFile("consent")); + var mocker = new AutoMocker(); + + var parser = mocker.CreateInstance(); + var result = await parser.GetFormAsync(new Url("https://m.vk.com/login?act=authcheck&m=442")); + + Assert.NotNull(result); + Assert.AreEqual("post", result.Method); + Assert.AreEqual("https://login.vk.com/?act=grant_access&client_id=4268118&settings=140492255&redirect_uri=https%3A%2F%2Foauth.vk.com%2Fblank.html&response_type=token&group_ids=&token_type=0&v=&state=123&display=mobile&ip_h=5a4524d95f3521be68&hash=1552162134_98614f6fce5d86d252&https=1", result.Action); + Assert.IsNotEmpty(result.Fields); + } + } + + private string ReadHtmlFile(string fileNameWithoutExtension) + { + var folders = new List + { + AppContext.BaseDirectory, + "TestData", + "Authorization", + fileNameWithoutExtension + }; + + var path = Path.Combine(folders.ToArray()) + ".html"; + + if (!File.Exists(path)) + { + throw new FileNotFoundException(path); + } + + return File.ReadAllText(path, Encoding.UTF8); + } + } +} \ No newline at end of file diff --git a/VkNet.Tests/Infrastructure/ImplicitFlowTests.cs b/VkNet.Tests/Infrastructure/ImplicitFlowTests.cs index 61d65af26..edb02cfe6 100644 --- a/VkNet.Tests/Infrastructure/ImplicitFlowTests.cs +++ b/VkNet.Tests/Infrastructure/ImplicitFlowTests.cs @@ -1,12 +1,17 @@ +using System; using System.Text; using System.Threading.Tasks; using Flurl; +using Moq; using Moq.AutoMock; using NUnit.Framework; using VkNet.Abstractions.Core; +using VkNet.Enums; using VkNet.Enums.Filters; using VkNet.Enums.SafetyEnums; using VkNet.Exception; +using VkNet.Infrastructure.Authorization; +using VkNet.Infrastructure.Authorization.ImplicitFlow; using VkNet.Model; using VkNet.Utils; @@ -18,8 +23,8 @@ public class ImplicitFlowTests [Test] public void CreateAuthorizeUrl() { - const int clientId = 1; - var scope = Settings.Notify.ToUInt64(); + const int clientId = 4268118; + var scope = Settings.All|Settings.Offline; const string state = "123"; var display = Display.Mobile; var builder = new StringBuilder("https://oauth.vk.com/authorize?"); @@ -28,7 +33,7 @@ public void CreateAuthorizeUrl() builder.Append("redirect_uri=https://oauth.vk.com/blank.html&"); builder.Append($"display={display}&"); - builder.Append($"scope={scope}&"); + builder.Append($"scope={scope.ToUInt64()}&"); builder.Append("response_type=token&"); builder.Append("v=5.92&"); @@ -41,7 +46,7 @@ public void CreateAuthorizeUrl() var implicitFlow = mocker.CreateInstance(); - var authorizeUrl = implicitFlow.CreateAuthorizeUrl(clientId, scope, display, state); + var authorizeUrl = implicitFlow.CreateAuthorizeUrl(clientId, scope.ToUInt64(), display, state); Assert.AreEqual(new Url(expected), authorizeUrl); } @@ -58,6 +63,34 @@ public async Task Authorize() mocker.Setup(x => x.Version).Returns("5.92"); + mocker.Setup>(x => x.ExecuteAsync(It.IsAny())) + .ReturnsAsync(new AuthorizationFormResult + { + ResponseUrl = "https://m.vk.com/login?act=authcheck&m=442", + RequestUrl = "https://m.vk.com/login?act=authcheck&m=442", + Cookies = new Cookies() + }); + + mocker.Setup(x => x.Create(It.IsAny())) + .Returns(mocker.Get()); + + mocker.GetMock>() + .SetupSequence(x => x.GetPageType(It.IsAny())) + .Returns(ImplicitFlowPageType.LoginPassword) + .Returns(ImplicitFlowPageType.TwoFactor) + .Returns(ImplicitFlowPageType.Consent) + .Returns(ImplicitFlowPageType.Result); + + mocker.GetMock>() + .Setup(x => x.GetAuthorizationResult(It.IsAny())) + .Returns(new AuthorizationResult + { + AccessToken = "access_token", + UserId = 123, + ExpiresIn = 0, + State = "123" + }); + var implicitFlow = mocker.CreateInstance(); var result = await implicitFlow.AuthorizeAsync().ConfigureAwait(false); diff --git a/VkNet.Tests/TestData/Authorization/captcha.html b/VkNet.Tests/TestData/Authorization/captcha.html new file mode 100644 index 000000000..451209140 --- /dev/null +++ b/VkNet.Tests/TestData/Authorization/captcha.html @@ -0,0 +1,302 @@ + + + + + + + + + + + + + + + + + + + Получение доступа к ВКонтакте + + + + + + + + + + + + +
+ + +
+
+
+ +
+
+
+
+ +
+
+ +
+
+
+
+ +
+
raventestapp
+
Для продолжения Вам необходимо войти ВКонтакте.
+
+
+
+ +
+ + + + +
+
Телефон или email:
+
+
+
+
+
+
Пароль:
+
+
+
+
+
+
+
+
+ +
+ Код с картинки: +
+
+ +
+
+
+
+
+ + +
+
+
+
Ещё не зарегистрированы?
+
+ +
+
+
+
+
+ + + +
+
+
+
+Регистрация + + +
+
+
+
+ + + + \ No newline at end of file diff --git a/VkNet.Tests/TestData/Authorization/consent.html b/VkNet.Tests/TestData/Authorization/consent.html new file mode 100644 index 000000000..840dfe4d6 --- /dev/null +++ b/VkNet.Tests/TestData/Authorization/consent.html @@ -0,0 +1,301 @@ + + + + + + + + + + + + + + + + + + + Получение доступа к ВКонтакте + + + + + + + + + + + + + +
+ + +
+
+
+ +
+
+
+
+
+
+
+
+ +
+ выйти +
+
+ +
+
+
+ +
+
+
+
+ +
+
raventestapp
+
запрашивает доступ к Вашему аккаунту
+
+
+
+
+
+ Приложению будут доступны: +
+
+ сообщения, информация страницы, обновление статуса, список друзей, фотографии, + товары, истории, + публикация записей, аудиозаписи, видеозаписи, + Приложению будут доступны Ваши рекламные кабинеты, + доступ в любое время, заметки, вики-страницы, + документы, группы, уведомления об ответах, + статистика, Ваш email in***@mail.ru + + +
+
+
+ +
+ + +
+
+
+
+
+
+ + + +
+
+
+
+ + + +
+
+
+
+ + + + \ No newline at end of file diff --git a/VkNet.Tests/TestData/Authorization/error.html b/VkNet.Tests/TestData/Authorization/error.html new file mode 100644 index 000000000..7a31af698 --- /dev/null +++ b/VkNet.Tests/TestData/Authorization/error.html @@ -0,0 +1,15 @@ + + + + + + + OAuth Blank + + +, . + . + + + + \ No newline at end of file diff --git a/VkNet.Tests/TestData/Authorization/login.html b/VkNet.Tests/TestData/Authorization/login.html new file mode 100644 index 000000000..d888c5780 --- /dev/null +++ b/VkNet.Tests/TestData/Authorization/login.html @@ -0,0 +1,290 @@ + + + + + + + + + + + + + + + + + + + Получение доступа к ВКонтакте + + + + + + + + + + + + + +
+ + +
+
+
+ +
+
+
+
+ +
+
+ +
+
+
+
+ +
+
raventestapp
+
Для продолжения Вам необходимо войти ВКонтакте.
+
+
+
+ +
+ + + + +
+
Телефон или email:
+
+
+
+
+
+
Пароль:
+
+
+
+
+
+ +
+
+ + +
+
+
+
Ещё не зарегистрированы?
+
+ +
+
+
+
+
+ + + +
+
+
+
+Регистрация + + +
+
+
+
+ + + + \ No newline at end of file diff --git a/VkNet.Tests/TestData/Authorization/success.html b/VkNet.Tests/TestData/Authorization/success.html new file mode 100644 index 000000000..e04aa19a2 --- /dev/null +++ b/VkNet.Tests/TestData/Authorization/success.html @@ -0,0 +1,15 @@ + + + + + + + OAuth Blank + + +, . + . + + + + \ No newline at end of file diff --git a/VkNet.Tests/TestData/Authorization/twofa.html b/VkNet.Tests/TestData/Authorization/twofa.html new file mode 100644 index 000000000..86791b26c --- /dev/null +++ b/VkNet.Tests/TestData/Authorization/twofa.html @@ -0,0 +1,612 @@ + + + + + + + + + + + + + + + + + + + Вход | ВКонтакте + + + + + + + + + + + + + + + +
+ + +
+
+
+ +
+
+
+
+ + +
+ выйти +
+
+
+ +
+
+
+

Проверка безопасности

+
+
Пожалуйста, введите код из личного сообщения от Администрации + или из приложения для генерации кодов, чтобы подтвердить, что Вы — владелец + страницы. +
+
+
+
Код подтверждения:
+
+
+
+
+
+
+
+ +
+ + +
+
+
+
+
+ + +
+ + + +
+
+
+
+
+Регистрация + + +
+
+
+
+ + + + \ No newline at end of file diff --git a/VkNet.Tests/TestData/Authorization/twofa_error.html b/VkNet.Tests/TestData/Authorization/twofa_error.html new file mode 100644 index 000000000..1d5b72547 --- /dev/null +++ b/VkNet.Tests/TestData/Authorization/twofa_error.html @@ -0,0 +1,280 @@ + + + + + + + + + + + + + + + + + + + Вход | ВКонтакте + + + + + + + + + + + + + + + +
+ + +
+
+
+ +
+
+
+
+ + +
+ выйти +
+
+
+ +
+
+
+

Проверка безопасности

+
+
Пожалуйста, введите код из личного сообщения от Администрации + или из приложения для генерации кодов, чтобы подтвердить, что Вы — владелец + страницы. +
+
+
+
Неверный код.
Пожалуйста, + введите код, который Вы только что получили. +
+
+
+
+
+
Код подтверждения:
+
+
+
+
+
+
+
+ +
+ + +
+
+
+
+
+ + +
+ + + +
+
+
+ +
+
+Регистрация + + +
+
+
+
+ + + + \ No newline at end of file diff --git a/VkNet.Tests/Utils/ImplicitFlowVkAuthorizationTests.cs b/VkNet.Tests/Utils/ImplicitFlowVkAuthorizationTests.cs index 5c95de432..c2a26299d 100644 --- a/VkNet.Tests/Utils/ImplicitFlowVkAuthorizationTests.cs +++ b/VkNet.Tests/Utils/ImplicitFlowVkAuthorizationTests.cs @@ -39,7 +39,7 @@ public void GetAuthorizationResult_VkAuthorizationException() public void GetPageType_LoginPassword() { var url = new Uri( - "http://oauth.vk.com/oauth/authorize?client_id=1&redirect_uri=http%3A%2F%2Foauth.vk.com%2Fblank.html&response_type=token&scope=140488159&v=&state=&display=wap&m=4&email=mail"); + "https://oauth.vk.com/authorize?client_id=4268118&redirect_uri=https://oauth.vk.com/blank.html&display=mobile&scope=140492255&response_type=token&v=5.92&state=123&revoke=1"); var auth = new ImplicitFlowVkAuthorization(); var result = auth.GetPageType(url); @@ -51,7 +51,7 @@ public void GetPageType_LoginPassword() public void GetPageType_LoginPassword_AfterIncorrectEnter() { var url = new Uri( - "https://oauth.vk.com/authorize?client_id=1&redirect_uri=http%3A%2F%2Foauth.vk.com%2Fblank.html&response_type=token&scope=140488159&v=&state=&display=wap&m=4&email=mail"); + "https://oauth.vk.com/authorize?client_id=4268118&redirect_uri=https%3A%2F%2Foauth.vk.com%2Fblank.html&response_type=token&scope=140492255&v=5.92&state=123&revoke=1&display=mobile&m=4&email="); var auth = new ImplicitFlowVkAuthorization(); var result = auth.GetPageType(url); @@ -63,7 +63,7 @@ public void GetPageType_LoginPassword_AfterIncorrectEnter() public void GetPageType_Captcha() { var url = new Uri( - "https://oauth.vk.com/authorize?client_id=1&redirect_uri=http%3A%2F%2Foauth.vk.com%2Fblank.html&response_type=token&scope=140488159&v=&state=&display=wap&sid=462572155651&dif=1&email=inyutin_maxim%40mail.ru"); + "https://oauth.vk.com/authorize?client_id=4268118&redirect_uri=https%3A%2F%2Foauth.vk.com%2Fblank.html&response_type=token&scope=140492255&v=5.92&state=123&revoke=1&display=mobile&sid=644558728730&dif=1&email=inyutin_maxim%40mail.ru"); var auth = new ImplicitFlowVkAuthorization(); var result = auth.GetPageType(url); @@ -75,7 +75,7 @@ public void GetPageType_Captcha() public void GetPageType_Captcha_AfterIncorrectEnter() { var url = new Uri( - "https://oauth.vk.com/authorize?client_id=1&redirect_uri=http%3A%2F%2Foauth.vk.com%2Fblank.html&response_type=token&scope=140488159&v=&state=&display=wap&sid=856703151954&dif=1&email=inyutin_maxim%40mail.ru&m=5"); + "https://oauth.vk.com/authorize?client_id=4268118&redirect_uri=https%3A%2F%2Foauth.vk.com%2Fblank.html&response_type=token&scope=140492255&v=5.92&state=123&revoke=1&display=mobile&sid=955166290951&dif=1&email=inyutin_maxim%40mail.ru&m=5"); var auth = new ImplicitFlowVkAuthorization(); var result = auth.GetPageType(url); @@ -108,7 +108,7 @@ public void GetPageType_TwoFactor_AfterIncorrectEnter() [Test] public void GetPageType_Result() { - var url = new Uri("https://oauth.vk.com/blank.html#access_token=access_token&expires_in=86400&user_id=32190123"); + var url = new Uri("https://oauth.vk.com/blank.html#access_token=access_token&expires_in=0&user_id=32190123&email=inyutin_maxim@mail.ru&state=123"); var auth = new ImplicitFlowVkAuthorization(); var result = auth.GetPageType(url); @@ -120,7 +120,7 @@ public void GetPageType_Result() public void GetPageType_Consent() { var url = new Uri( - "https://oauth.vk.com/authorize?client_id=4268118&redirect_uri=http%3A%2F%2Foauth.vk.com%2Fblank.html&response_type=token&scope=140426399&v=&state=&display=wap&__q_hash=30b8b543bbe64e35a9f740ca24f57f12"); + "https://oauth.vk.com/authorize?client_id=4268118&scope=140492255&redirect_uri=https%3A%2F%2Foauth.vk.com%2Fblank.html&response_type=token&token_type=0&state=123&display=mobile&__q_hash=d358748186f6c31d9f249769b7b4d619"); var auth = new ImplicitFlowVkAuthorization(); var result = auth.GetPageType(url); @@ -132,7 +132,7 @@ public void GetPageType_Consent() public void GetPageType_Error() { var url = new Uri( - "https://oauth.vk.com/blank.html#error=access_denied&error_reason=user_denied&error_description=User%20denied%20your%20request"); + "https://oauth.vk.com/blank.html#error=access_denied&error_reason=user_denied&error_description=User%20denied%20your%20request&state=123"); var auth = new ImplicitFlowVkAuthorization(); var result = auth.GetPageType(url); diff --git a/VkNet/Infrastructure/Authorization/ImplicitFlow/AbstractAuthorizationForm.cs b/VkNet/Infrastructure/Authorization/ImplicitFlow/AbstractAuthorizationForm.cs index 11199fdd3..ab27b2d3d 100644 --- a/VkNet/Infrastructure/Authorization/ImplicitFlow/AbstractAuthorizationForm.cs +++ b/VkNet/Infrastructure/Authorization/ImplicitFlow/AbstractAuthorizationForm.cs @@ -29,7 +29,7 @@ protected AbstractAuthorizationForm(IAuthorizationFormHtmlParser htmlParser, Def /// public async Task ExecuteAsync(Url url) { - var form = _htmlParser.GetForm(url); + var form = await _htmlParser.GetFormAsync(url).ConfigureAwait(false); FillFormFields(form); diff --git a/VkNet/Infrastructure/Authorization/ImplicitFlow/AuthorizationFormHtmlParser.cs b/VkNet/Infrastructure/Authorization/ImplicitFlow/AuthorizationFormHtmlParser.cs index 1e4712645..42a3c3a69 100644 --- a/VkNet/Infrastructure/Authorization/ImplicitFlow/AuthorizationFormHtmlParser.cs +++ b/VkNet/Infrastructure/Authorization/ImplicitFlow/AuthorizationFormHtmlParser.cs @@ -1,32 +1,34 @@ using System; using System.Collections.Generic; +using System.Threading.Tasks; using Flurl; +using Flurl.Http; using HtmlAgilityPack; +using JetBrains.Annotations; using VkNet.Exception; namespace VkNet.Infrastructure.Authorization.ImplicitFlow { /// - public class AuthorizationFormHtmlParser : IAuthorizationFormHtmlParser + [UsedImplicitly] + public sealed class AuthorizationFormHtmlParser : IAuthorizationFormHtmlParser { /// - public VkHtmlFormResult GetForm(Url url) + public async Task GetFormAsync(Url url) { - var uri = url.ToUri(); - var responseBaseUrl = uri.Scheme + "://" + uri.Host + ":" + uri.Port; - - var web = new HtmlWeb(); - var doc = web.Load(url); + var html = await url.GetStringAsync().ConfigureAwait(false); + var doc = new HtmlDocument(); + doc.LoadHtml(html); var formNode = GetFormNode(doc); var inputs = ParseInputs(formNode); - var actionUrl = GetActionUrl(formNode, responseBaseUrl); + var actionUrl = GetActionUrl(formNode, url); var method = GetMethod(formNode); return new VkHtmlFormResult { Fields = inputs, - Action = string.IsNullOrWhiteSpace(actionUrl) ? url.ToString() : actionUrl, + Action = actionUrl, Method = method }; } @@ -36,7 +38,7 @@ public VkHtmlFormResult GetForm(Url url) /// /// HTML элемент /// Элемент не найден на форме. - private HtmlNode GetFormNode(HtmlDocument html) + private static HtmlNode GetFormNode(HtmlDocument html) { HtmlNode.ElementsFlags.Remove("form"); var form = html.DocumentNode.SelectSingleNode("//form"); @@ -53,7 +55,7 @@ private HtmlNode GetFormNode(HtmlDocument html) /// Разобрать поля ввода. /// /// Коллекция полей ввода - private Dictionary ParseInputs(HtmlNode formNode) + private static Dictionary ParseInputs(HtmlNode formNode) { var inputs = new Dictionary(); @@ -79,7 +81,7 @@ private Dictionary ParseInputs(HtmlNode formNode) /// /// URL действия. /// - private string GetActionUrl(HtmlNode formNode, string responseBaseUrl) + private static string GetActionUrl(HtmlNode formNode, Url url) { var action = formNode.Attributes["action"]; @@ -90,23 +92,29 @@ private string GetActionUrl(HtmlNode formNode, string responseBaseUrl) var link = action.Value; - if (!string.IsNullOrEmpty(link) && !link.StartsWith("http", StringComparison.Ordinal) - ) // относительный URL + if (!string.IsNullOrWhiteSpace(link) && !link.StartsWith("http", StringComparison.Ordinal)) // относительный URL { - link = Url.Combine(responseBaseUrl, link); + link = Url.Combine(GetResponseBaseUrl(url), link); } - return link; // абсолютный путь + return string.IsNullOrWhiteSpace(link) ? url.ToString() : link; // абсолютный путь } /// /// URL действия. /// - private string GetMethod(HtmlNode formNode) + private static string GetMethod(HtmlNode formNode) { var method = formNode.Attributes["method"]; return method?.Value; } + + private static string GetResponseBaseUrl(Url url) + { + var uri = url.ToUri(); + + return uri.Scheme + "://" + uri.Host + ":" + uri.Port; + } } } \ No newline at end of file diff --git a/VkNet/Infrastructure/Authorization/ImplicitFlow/ConsentForm.cs b/VkNet/Infrastructure/Authorization/ImplicitFlow/ConsentForm.cs index f64251499..5b0bc3c35 100644 --- a/VkNet/Infrastructure/Authorization/ImplicitFlow/ConsentForm.cs +++ b/VkNet/Infrastructure/Authorization/ImplicitFlow/ConsentForm.cs @@ -1,11 +1,14 @@ using Flurl.Http.Configuration; +using JetBrains.Annotations; using VkNet.Enums; namespace VkNet.Infrastructure.Authorization.ImplicitFlow { /// - public class ConsentForm : AbstractAuthorizationForm + [UsedImplicitly] + public sealed class ConsentForm : AbstractAuthorizationForm { + /// public ConsentForm(IAuthorizationFormHtmlParser htmlParser, DefaultHttpClientFactory httpClientFactory) : base(htmlParser, httpClientFactory) { diff --git a/VkNet/Infrastructure/Authorization/ImplicitFlow/IAuthorizationFormHtmlParser.cs b/VkNet/Infrastructure/Authorization/ImplicitFlow/IAuthorizationFormHtmlParser.cs index 9fb13e738..a31f149a5 100644 --- a/VkNet/Infrastructure/Authorization/ImplicitFlow/IAuthorizationFormHtmlParser.cs +++ b/VkNet/Infrastructure/Authorization/ImplicitFlow/IAuthorizationFormHtmlParser.cs @@ -1,3 +1,4 @@ +using System.Threading.Tasks; using Flurl; namespace VkNet.Infrastructure.Authorization.ImplicitFlow @@ -12,6 +13,6 @@ public interface IAuthorizationFormHtmlParser /// /// URL /// Результат с данными формы - VkHtmlFormResult GetForm(Url url); + Task GetFormAsync(Url url); } } \ No newline at end of file diff --git a/VkNet/Infrastructure/Authorization/ImplicitFlow/ImplicitFlowCaptchaLoginForm.cs b/VkNet/Infrastructure/Authorization/ImplicitFlow/ImplicitFlowCaptchaLoginForm.cs index 40891906e..2dc7a5c4c 100644 --- a/VkNet/Infrastructure/Authorization/ImplicitFlow/ImplicitFlowCaptchaLoginForm.cs +++ b/VkNet/Infrastructure/Authorization/ImplicitFlow/ImplicitFlowCaptchaLoginForm.cs @@ -1,4 +1,5 @@ using Flurl.Http.Configuration; +using JetBrains.Annotations; using VkNet.Enums; using VkNet.Exception; using VkNet.Model; @@ -7,7 +8,8 @@ namespace VkNet.Infrastructure.Authorization.ImplicitFlow { /// - public class ImplicitFlowCaptchaLoginForm : AbstractAuthorizationForm + [UsedImplicitly] + public sealed class ImplicitFlowCaptchaLoginForm : AbstractAuthorizationForm { private readonly IApiAuthParams _authorizationParameters; diff --git a/VkNet/Infrastructure/Authorization/ImplicitFlow/ImplicitFlowLoginForm.cs b/VkNet/Infrastructure/Authorization/ImplicitFlow/ImplicitFlowLoginForm.cs index 393ea4685..7a19bbd76 100644 --- a/VkNet/Infrastructure/Authorization/ImplicitFlow/ImplicitFlowLoginForm.cs +++ b/VkNet/Infrastructure/Authorization/ImplicitFlow/ImplicitFlowLoginForm.cs @@ -1,11 +1,13 @@ using Flurl.Http.Configuration; +using JetBrains.Annotations; using VkNet.Enums; using VkNet.Model; namespace VkNet.Infrastructure.Authorization.ImplicitFlow { /// - public class ImplicitFlowLoginForm : AbstractAuthorizationForm + [UsedImplicitly] + public sealed class ImplicitFlowLoginForm : AbstractAuthorizationForm { private readonly IApiAuthParams _authorizationParameters; diff --git a/VkNet/Infrastructure/Authorization/ImplicitFlow/TwoFactorForm.cs b/VkNet/Infrastructure/Authorization/ImplicitFlow/TwoFactorForm.cs index a1806ffd0..306261529 100644 --- a/VkNet/Infrastructure/Authorization/ImplicitFlow/TwoFactorForm.cs +++ b/VkNet/Infrastructure/Authorization/ImplicitFlow/TwoFactorForm.cs @@ -1,4 +1,5 @@ using Flurl.Http.Configuration; +using JetBrains.Annotations; using VkNet.Enums; using VkNet.Exception; using VkNet.Model; @@ -6,7 +7,8 @@ namespace VkNet.Infrastructure.Authorization.ImplicitFlow { /// - public class TwoFactorForm : AbstractAuthorizationForm + [UsedImplicitly] + public sealed class TwoFactorForm : AbstractAuthorizationForm { private readonly IApiAuthParams _authorizationParameters; diff --git a/VkNet/VkApi.cs b/VkNet/VkApi.cs index 2498238b1..4cb3f3a02 100644 --- a/VkNet/VkApi.cs +++ b/VkNet/VkApi.cs @@ -807,7 +807,7 @@ private void Initialization(IServiceProvider serviceProvider) _language = serviceProvider.GetRequiredService(); _rateLimiter = serviceProvider.GetRequiredService(); - Browser = serviceProvider.GetRequiredService(); +// Browser = serviceProvider.GetRequiredService(); NeedValidationHandler = serviceProvider.GetRequiredService(); AuthorizationFlow = serviceProvider.GetRequiredService(); CaptchaSolver = serviceProvider.GetService();