diff --git a/v2rayN/PacLib/PacHandler.cs b/v2rayN/PacLib/PacHandler.cs index 5806d471..4b2fe2c3 100644 --- a/v2rayN/PacLib/PacHandler.cs +++ b/v2rayN/PacLib/PacHandler.cs @@ -1,5 +1,6 @@ using System; using System.IO; +using System.Linq; using System.Net.Sockets; using System.Text; using System.Threading; @@ -43,6 +44,12 @@ public class PacHandler } _pacText = File.ReadAllText(path).Replace("__PROXY__", $"PROXY 127.0.0.1:{_httpPort};DIRECT;"); + + var userPac = LoadUserPac(_configPath); + if (userPac != "") + { + _pacText = _pacText.Replace(" [],\n []", userPac); + } } private static void RunListener() @@ -100,4 +107,32 @@ public class PacHandler } } } + + public static string LoadUserPac(string configPath) + { + var userPac = ""; + var userPacPath = Path.Combine(_configPath, "pacUser.txt"); + if (File.Exists(userPacPath)) + { + userPac = File.ReadAllText(userPacPath); + } + return userPac; + } + + public static void SaveUserPac(string directDomains, string proxyDomains, string configPath) + { + var directDomainsArray = directDomains.Split('\n', StringSplitOptions.RemoveEmptyEntries | StringSplitOptions.TrimEntries); + var proxyDomainsArray = proxyDomains.Split('\n', StringSplitOptions.RemoveEmptyEntries | StringSplitOptions.TrimEntries); + + var userPac = directDomainsArray.Aggregate("[\n", (current, directDomain) => $"{current} \"{directDomain}\",\n"); + + userPac += " ],\n [\n"; + + userPac = proxyDomainsArray.Aggregate(userPac, (current, proxyDomain) => $"{current} \"{proxyDomain}\",\n"); + + userPac += "]"; + + var path = Path.Combine(configPath, "pacUser.txt"); + File.WriteAllText(path, userPac); + } } \ No newline at end of file diff --git a/v2rayN/v2rayN/Resx/ResUI.Designer.cs b/v2rayN/v2rayN/Resx/ResUI.Designer.cs index b53c01a5..299e84c2 100644 --- a/v2rayN/v2rayN/Resx/ResUI.Designer.cs +++ b/v2rayN/v2rayN/Resx/ResUI.Designer.cs @@ -2869,6 +2869,33 @@ namespace v2rayN.Resx { } } + /// + /// 查找类似 User Pac settings 的本地化字符串。 + /// + public static string TbSettingsUserPac { + get { + return ResourceManager.GetString("TbSettingsUserPac", resourceCulture); + } + } + + /// + /// 查找类似 Direct domains(One at a line): 的本地化字符串。 + /// + public static string TbSettingsUserPacDirectDomains { + get { + return ResourceManager.GetString("TbSettingsUserPacDirectDomains", resourceCulture); + } + } + + /// + /// 查找类似 Proxy domains(One at a line): 的本地化字符串。 + /// + public static string TbSettingsUserPacProxyDomains { + get { + return ResourceManager.GetString("TbSettingsUserPacProxyDomains", resourceCulture); + } + } + /// /// 查找类似 ShortId 的本地化字符串。 /// diff --git a/v2rayN/v2rayN/Resx/ResUI.fa-Ir.resx b/v2rayN/v2rayN/Resx/ResUI.fa-Ir.resx index 39f211d2..5e87e1b6 100644 --- a/v2rayN/v2rayN/Resx/ResUI.fa-Ir.resx +++ b/v2rayN/v2rayN/Resx/ResUI.fa-Ir.resx @@ -1009,4 +1009,13 @@ فعال‌سازی شتاب‌دهنده سخت‌افزاری (نیاز به راه‌اندازی مجدد) + + User Pac settings + + + Proxy domains(One at a line): + + + Direct domains(One at a line): + \ No newline at end of file diff --git a/v2rayN/v2rayN/Resx/ResUI.resx b/v2rayN/v2rayN/Resx/ResUI.resx index 3107ae44..72d50480 100644 --- a/v2rayN/v2rayN/Resx/ResUI.resx +++ b/v2rayN/v2rayN/Resx/ResUI.resx @@ -814,6 +814,15 @@ Auth user + + User Pac settings + + + Direct domains(One at a line): + + + Proxy domains(One at a line): + Clear system proxy diff --git a/v2rayN/v2rayN/Resx/ResUI.ru.resx b/v2rayN/v2rayN/Resx/ResUI.ru.resx index 99be3632..3338c270 100644 --- a/v2rayN/v2rayN/Resx/ResUI.ru.resx +++ b/v2rayN/v2rayN/Resx/ResUI.ru.resx @@ -1051,4 +1051,13 @@ Включить аппаратное ускорение (требуется перезагрузка) + + User Pac settings + + + Proxy domains(One at a line): + + + Direct domains(One at a line): + \ No newline at end of file diff --git a/v2rayN/v2rayN/Resx/ResUI.zh-Hans.resx b/v2rayN/v2rayN/Resx/ResUI.zh-Hans.resx index ae6d0440..f1276b60 100644 --- a/v2rayN/v2rayN/Resx/ResUI.zh-Hans.resx +++ b/v2rayN/v2rayN/Resx/ResUI.zh-Hans.resx @@ -1129,4 +1129,13 @@ sing-box Mux 多路复用协议 + + 用户Pac设置 + + + 直连的域名(每行一个): + + + 需要代理的域名(每行一个): + \ No newline at end of file diff --git a/v2rayN/v2rayN/ViewModels/OptionSettingViewModel.cs b/v2rayN/v2rayN/ViewModels/OptionSettingViewModel.cs index 2607a847..89c350a1 100644 --- a/v2rayN/v2rayN/ViewModels/OptionSettingViewModel.cs +++ b/v2rayN/v2rayN/ViewModels/OptionSettingViewModel.cs @@ -3,6 +3,7 @@ using ReactiveUI.Fody.Helpers; using Splat; using System.Reactive; using System.Windows; +using PacLib; using v2rayN.Handler; using v2rayN.Mode; using v2rayN.Resx; @@ -107,6 +108,13 @@ namespace v2rayN.ViewModels #endregion CoreType + #region User Pac + + [Reactive] public string userPacDirectDomains { get; set; } + [Reactive] public string userPacProxyDomains { get; set; } + + #endregion System proxy + public ReactiveCommand SaveCmd { get; } public OptionSettingViewModel(Window view) @@ -201,6 +209,8 @@ namespace v2rayN.ViewModels InitCoreType(); + InitUserPac(); + SaveCmd = ReactiveCommand.Create(() => { SaveSetting(); @@ -367,6 +377,8 @@ namespace v2rayN.ViewModels { UI.ShowWarning(ResUI.OperationFailed); } + + SaveUserPac(); } private int SaveCoreType() @@ -405,5 +417,25 @@ namespace v2rayN.ViewModels } return 0; } + + private void InitUserPac() + { + var userPac = PacHandler.LoadUserPac(Utils.GetConfigPath()); + if (userPac == "") return; + + userPac = userPac.Replace(" \"", "").Replace("\",", ""); + var arr = userPac.Split(" ],\n [\n", StringSplitOptions.RemoveEmptyEntries); + userPacDirectDomains = arr[0].Replace("[\n", ""); + userPacProxyDomains = arr[1].Replace("]", ""); + } + + private int SaveUserPac() + { + var result = -1; + + PacHandler.SaveUserPac(userPacDirectDomains, userPacProxyDomains, Utils.GetConfigPath()); + + return result; + } } } \ No newline at end of file diff --git a/v2rayN/v2rayN/Views/OptionSettingWindow.xaml b/v2rayN/v2rayN/Views/OptionSettingWindow.xaml index 3b568f8b..2d83d445 100644 --- a/v2rayN/v2rayN/Views/OptionSettingWindow.xaml +++ b/v2rayN/v2rayN/Views/OptionSettingWindow.xaml @@ -1080,6 +1080,51 @@ Style="{StaticResource DefComboBox}" /> + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/v2rayN/v2rayN/Views/OptionSettingWindow.xaml.cs b/v2rayN/v2rayN/Views/OptionSettingWindow.xaml.cs index 95f83e24..53cb34cd 100644 --- a/v2rayN/v2rayN/Views/OptionSettingWindow.xaml.cs +++ b/v2rayN/v2rayN/Views/OptionSettingWindow.xaml.cs @@ -190,6 +190,9 @@ namespace v2rayN.Views this.Bind(ViewModel, vm => vm.CoreType5, v => v.cmbCoreType5.Text).DisposeWith(disposables); this.Bind(ViewModel, vm => vm.CoreType6, v => v.cmbCoreType6.Text).DisposeWith(disposables); + this.Bind(ViewModel, vm => vm.userPacDirectDomains, v => v.txtUserPacDirectDomains.Text).DisposeWith(disposables); + this.Bind(ViewModel, vm => vm.userPacProxyDomains, v => v.txtUserPacProxyDomains.Text).DisposeWith(disposables); + this.BindCommand(ViewModel, vm => vm.SaveCmd, v => v.btnSave).DisposeWith(disposables); }); }