mirror of
https://github.com/2dust/v2rayN.git
synced 2025-05-03 13:48:52 +00:00
Custom config pre-service uses sing-box instead of v2ray
This commit is contained in:
parent
419f5458b4
commit
b06540f2ec
9 changed files with 125 additions and 102 deletions
|
@ -27,6 +27,7 @@
|
||||||
public const string ConfigFileName = "guiNConfig.json";
|
public const string ConfigFileName = "guiNConfig.json";
|
||||||
public const string ConfigDB = "guiNDB.db";
|
public const string ConfigDB = "guiNDB.db";
|
||||||
public const string coreConfigFileName = "config.json";
|
public const string coreConfigFileName = "config.json";
|
||||||
|
public const string corePreConfigFileName = "configPre.json";
|
||||||
|
|
||||||
public const string v2raySampleClient = "v2rayN.Sample.SampleClientConfig";
|
public const string v2raySampleClient = "v2rayN.Sample.SampleClientConfig";
|
||||||
public const string SingboxSampleClient = "v2rayN.Sample.SingboxSampleClientConfig";
|
public const string SingboxSampleClient = "v2rayN.Sample.SingboxSampleClientConfig";
|
||||||
|
|
|
@ -11,10 +11,9 @@ namespace v2rayN.Handler
|
||||||
/// </summary>
|
/// </summary>
|
||||||
internal class CoreHandler
|
internal class CoreHandler
|
||||||
{
|
{
|
||||||
private static string _coreCConfigRes = Global.coreConfigFileName;
|
|
||||||
private CoreInfo? _coreInfo;
|
private CoreInfo? _coreInfo;
|
||||||
private int _processId = 0;
|
|
||||||
private Process? _process;
|
private Process? _process;
|
||||||
|
private Process? _processPre;
|
||||||
private Action<bool, string> _updateFunc;
|
private Action<bool, string> _updateFunc;
|
||||||
|
|
||||||
public CoreHandler(Action<bool, string> update)
|
public CoreHandler(Action<bool, string> update)
|
||||||
|
@ -39,7 +38,7 @@ namespace v2rayN.Handler
|
||||||
ShowMsg(false, ResUI.CheckServerSettings);
|
ShowMsg(false, ResUI.CheckServerSettings);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
string fileName = Utils.GetConfigPath(_coreCConfigRes);
|
string fileName = Utils.GetConfigPath(Global.coreConfigFileName);
|
||||||
if (CoreConfigHandler.GenerateClientConfig(node, fileName, out string msg, out string content) != 0)
|
if (CoreConfigHandler.GenerateClientConfig(node, fileName, out string msg, out string content) != 0)
|
||||||
{
|
{
|
||||||
ShowMsg(false, msg);
|
ShowMsg(false, msg);
|
||||||
|
@ -51,21 +50,6 @@ namespace v2rayN.Handler
|
||||||
CoreStop();
|
CoreStop();
|
||||||
CoreStart(node);
|
CoreStart(node);
|
||||||
}
|
}
|
||||||
|
|
||||||
//start a socks service
|
|
||||||
if (_process != null && !_process.HasExited && node.configType == EConfigType.Custom && node.preSocksPort > 0)
|
|
||||||
{
|
|
||||||
var itemSocks = new ProfileItem()
|
|
||||||
{
|
|
||||||
configType = EConfigType.Socks,
|
|
||||||
address = Global.Loopback,
|
|
||||||
port = node.preSocksPort
|
|
||||||
};
|
|
||||||
if (CoreConfigHandler.GenerateClientConfig(itemSocks, null, out string msg2, out string configStr) == 0)
|
|
||||||
{
|
|
||||||
_processId = CoreStartViaString(configStr);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public int LoadCoreConfigString(Config config, List<ServerTestItem> _selecteds)
|
public int LoadCoreConfigString(Config config, List<ServerTestItem> _selecteds)
|
||||||
|
@ -114,10 +98,11 @@ namespace v2rayN.Handler
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (_processId > 0)
|
if (_processPre != null)
|
||||||
{
|
{
|
||||||
CoreStopPid(_processId);
|
KillProcess(_processPre);
|
||||||
_processId = 0;
|
_processPre.Dispose();
|
||||||
|
_processPre = null;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
catch (Exception ex)
|
catch (Exception ex)
|
||||||
|
@ -165,67 +150,33 @@ namespace v2rayN.Handler
|
||||||
{
|
{
|
||||||
ShowMsg(false, string.Format(ResUI.StartService, DateTime.Now.ToString()));
|
ShowMsg(false, string.Format(ResUI.StartService, DateTime.Now.ToString()));
|
||||||
|
|
||||||
try
|
var proc = RunProcess(node, _coreInfo, "", ShowMsg);
|
||||||
|
if (proc is null)
|
||||||
{
|
{
|
||||||
string fileName = CoreFindexe(_coreInfo);
|
return;
|
||||||
if (fileName == "") return;
|
|
||||||
|
|
||||||
var displayLog = node.configType != EConfigType.Custom || node.displayLog;
|
|
||||||
Process p = new()
|
|
||||||
{
|
|
||||||
StartInfo = new ProcessStartInfo
|
|
||||||
{
|
|
||||||
FileName = fileName,
|
|
||||||
Arguments = _coreInfo.arguments,
|
|
||||||
WorkingDirectory = Utils.GetConfigPath(),
|
|
||||||
UseShellExecute = false,
|
|
||||||
RedirectStandardOutput = displayLog,
|
|
||||||
RedirectStandardError = displayLog,
|
|
||||||
CreateNoWindow = true,
|
|
||||||
StandardOutputEncoding = displayLog ? Encoding.UTF8 : null,
|
|
||||||
StandardErrorEncoding = displayLog ? Encoding.UTF8 : null,
|
|
||||||
}
|
|
||||||
};
|
|
||||||
if (displayLog)
|
|
||||||
{
|
|
||||||
p.OutputDataReceived += (sender, e) =>
|
|
||||||
{
|
|
||||||
if (!string.IsNullOrEmpty(e.Data))
|
|
||||||
{
|
|
||||||
string msg = e.Data + Environment.NewLine;
|
|
||||||
ShowMsg(false, msg);
|
|
||||||
}
|
|
||||||
};
|
|
||||||
p.ErrorDataReceived += (sender, e) =>
|
|
||||||
{
|
|
||||||
if (!string.IsNullOrEmpty(e.Data))
|
|
||||||
{
|
|
||||||
string msg = e.Data + Environment.NewLine;
|
|
||||||
ShowMsg(false, msg);
|
|
||||||
}
|
|
||||||
};
|
|
||||||
}
|
|
||||||
p.Start();
|
|
||||||
if (displayLog)
|
|
||||||
{
|
|
||||||
p.BeginOutputReadLine();
|
|
||||||
p.BeginErrorReadLine();
|
|
||||||
}
|
|
||||||
_process = p;
|
|
||||||
|
|
||||||
if (p.WaitForExit(1000))
|
|
||||||
{
|
|
||||||
throw new Exception(displayLog ? p.StandardError.ReadToEnd() : "启动进程失败并退出 (Failed to start the process and exited)");
|
|
||||||
}
|
|
||||||
|
|
||||||
Global.processJob.AddProcess(p.Handle);
|
|
||||||
}
|
}
|
||||||
catch (Exception ex)
|
_process = proc;
|
||||||
|
|
||||||
|
//start a socks service
|
||||||
|
if (_process != null && !_process.HasExited && node.configType == EConfigType.Custom && node.preSocksPort > 0)
|
||||||
{
|
{
|
||||||
//Utils.SaveLog(Utils.ToJson(node));
|
var itemSocks = new ProfileItem()
|
||||||
Utils.SaveLog(ex.Message, ex);
|
{
|
||||||
string msg = ex.Message;
|
coreType = ECoreType.sing_box,
|
||||||
ShowMsg(true, msg);
|
configType = EConfigType.Socks,
|
||||||
|
address = Global.Loopback,
|
||||||
|
port = node.preSocksPort
|
||||||
|
};
|
||||||
|
string fileName2 = Utils.GetConfigPath(Global.corePreConfigFileName);
|
||||||
|
if (CoreConfigHandler.GenerateClientConfig(itemSocks, fileName2, out string msg2, out string configStr) == 0)
|
||||||
|
{
|
||||||
|
var coreInfo = LazyConfig.Instance.GetCoreInfo(ECoreType.sing_box);
|
||||||
|
var proc2 = RunProcess(node, coreInfo, $" -c {Global.corePreConfigFileName}", ShowMsg);
|
||||||
|
if (proc2 is not null)
|
||||||
|
{
|
||||||
|
_processPre = proc2;
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -300,6 +251,93 @@ namespace v2rayN.Handler
|
||||||
_updateFunc(updateToTrayTooltip, msg);
|
_updateFunc(updateToTrayTooltip, msg);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private int SetCore(Config config, ProfileItem node)
|
||||||
|
{
|
||||||
|
if (node == null)
|
||||||
|
{
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
var coreType = LazyConfig.Instance.GetCoreType(node, node.configType);
|
||||||
|
|
||||||
|
_coreInfo = LazyConfig.Instance.GetCoreInfo(coreType);
|
||||||
|
|
||||||
|
if (_coreInfo == null)
|
||||||
|
{
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
#region Process
|
||||||
|
|
||||||
|
private Process? RunProcess(ProfileItem node, CoreInfo coreInfo, string configPath, Action<bool, string> update)
|
||||||
|
{
|
||||||
|
try
|
||||||
|
{
|
||||||
|
string fileName = CoreFindexe(coreInfo);
|
||||||
|
if (Utils.IsNullOrEmpty(fileName))
|
||||||
|
{
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
var displayLog = node.configType != EConfigType.Custom || node.displayLog;
|
||||||
|
Process proc = new()
|
||||||
|
{
|
||||||
|
StartInfo = new ProcessStartInfo
|
||||||
|
{
|
||||||
|
FileName = fileName,
|
||||||
|
Arguments = string.Format(coreInfo.arguments, configPath),
|
||||||
|
WorkingDirectory = Utils.GetConfigPath(),
|
||||||
|
UseShellExecute = false,
|
||||||
|
RedirectStandardOutput = displayLog,
|
||||||
|
RedirectStandardError = displayLog,
|
||||||
|
CreateNoWindow = true,
|
||||||
|
StandardOutputEncoding = displayLog ? Encoding.UTF8 : null,
|
||||||
|
StandardErrorEncoding = displayLog ? Encoding.UTF8 : null,
|
||||||
|
}
|
||||||
|
};
|
||||||
|
if (displayLog)
|
||||||
|
{
|
||||||
|
proc.OutputDataReceived += (sender, e) =>
|
||||||
|
{
|
||||||
|
if (!string.IsNullOrEmpty(e.Data))
|
||||||
|
{
|
||||||
|
string msg = e.Data + Environment.NewLine;
|
||||||
|
update(false, msg);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
proc.ErrorDataReceived += (sender, e) =>
|
||||||
|
{
|
||||||
|
if (!string.IsNullOrEmpty(e.Data))
|
||||||
|
{
|
||||||
|
string msg = e.Data + Environment.NewLine;
|
||||||
|
update(false, msg);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
}
|
||||||
|
proc.Start();
|
||||||
|
if (displayLog)
|
||||||
|
{
|
||||||
|
proc.BeginOutputReadLine();
|
||||||
|
proc.BeginErrorReadLine();
|
||||||
|
}
|
||||||
|
|
||||||
|
if (proc.WaitForExit(1000))
|
||||||
|
{
|
||||||
|
throw new Exception(displayLog ? proc.StandardError.ReadToEnd() : "启动进程失败并退出 (Failed to start the process and exited)");
|
||||||
|
}
|
||||||
|
|
||||||
|
Global.processJob.AddProcess(proc.Handle);
|
||||||
|
return proc;
|
||||||
|
}
|
||||||
|
catch (Exception ex)
|
||||||
|
{
|
||||||
|
Utils.SaveLog(ex.Message, ex);
|
||||||
|
string msg = ex.Message;
|
||||||
|
update(true, msg);
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
private void KillProcess(Process p)
|
private void KillProcess(Process p)
|
||||||
{
|
{
|
||||||
try
|
try
|
||||||
|
@ -318,21 +356,6 @@ namespace v2rayN.Handler
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private int SetCore(Config config, ProfileItem node)
|
#endregion Process
|
||||||
{
|
|
||||||
if (node == null)
|
|
||||||
{
|
|
||||||
return -1;
|
|
||||||
}
|
|
||||||
var coreType = LazyConfig.Instance.GetCoreType(node, node.configType);
|
|
||||||
|
|
||||||
_coreInfo = LazyConfig.Instance.GetCoreInfo(coreType);
|
|
||||||
|
|
||||||
if (_coreInfo == null)
|
|
||||||
{
|
|
||||||
return -1;
|
|
||||||
}
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
|
@ -343,7 +343,7 @@ namespace v2rayN.Handler
|
||||||
{
|
{
|
||||||
coreType = ECoreType.sing_box,
|
coreType = ECoreType.sing_box,
|
||||||
coreExes = new List<string> { "sing-box-client", "sing-box" },
|
coreExes = new List<string> { "sing-box-client", "sing-box" },
|
||||||
arguments = "run",
|
arguments = "run{0}",
|
||||||
coreUrl = Global.singboxCoreUrl,
|
coreUrl = Global.singboxCoreUrl,
|
||||||
redirectInfo = true,
|
redirectInfo = true,
|
||||||
coreReleaseApiUrl = Global.singboxCoreUrl.Replace(Global.githubUrl, Global.githubApiUrl),
|
coreReleaseApiUrl = Global.singboxCoreUrl.Replace(Global.githubUrl, Global.githubApiUrl),
|
||||||
|
|
|
@ -186,7 +186,6 @@ namespace v2rayN.Base
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
private void routingDirectExe(out List<string> lstDnsExe, out List<string> lstDirectExe)
|
private void routingDirectExe(out List<string> lstDnsExe, out List<string> lstDirectExe)
|
||||||
{
|
{
|
||||||
lstDnsExe = new();
|
lstDnsExe = new();
|
||||||
|
|
2
v2rayN/v2rayN/Resx/ResUI.Designer.cs
generated
2
v2rayN/v2rayN/Resx/ResUI.Designer.cs
generated
|
@ -2951,7 +2951,7 @@ namespace v2rayN.Resx {
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// 查找类似 * After setting this value, an socks service will be started using V2ray to provide functions such as speed display 的本地化字符串。
|
/// 查找类似 * After setting this value, an socks service will be started using Sing-box to provide functions such as speed display 的本地化字符串。
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public static string TipPreSocksPort {
|
public static string TipPreSocksPort {
|
||||||
get {
|
get {
|
||||||
|
|
|
@ -701,7 +701,7 @@
|
||||||
<value>txtPreSocksPort</value>
|
<value>txtPreSocksPort</value>
|
||||||
</data>
|
</data>
|
||||||
<data name="TipPreSocksPort" xml:space="preserve">
|
<data name="TipPreSocksPort" xml:space="preserve">
|
||||||
<value>* After setting this value, an socks service will be started using V2ray to provide functions such as speed display</value>
|
<value>* After setting this value, an socks service will be started using Sing-box to provide functions such as speed display</value>
|
||||||
</data>
|
</data>
|
||||||
<data name="TbBrowse" xml:space="preserve">
|
<data name="TbBrowse" xml:space="preserve">
|
||||||
<value>Browse</value>
|
<value>Browse</value>
|
||||||
|
|
|
@ -701,7 +701,7 @@
|
||||||
<value>txtPreSocksPort</value>
|
<value>txtPreSocksPort</value>
|
||||||
</data>
|
</data>
|
||||||
<data name="TipPreSocksPort" xml:space="preserve">
|
<data name="TipPreSocksPort" xml:space="preserve">
|
||||||
<value>* After setting this value, an socks service will be started using V2ray to provide functions such as speed display</value>
|
<value>* After setting this value, an socks service will be started using Sing-box to provide functions such as speed display</value>
|
||||||
</data>
|
</data>
|
||||||
<data name="TbBrowse" xml:space="preserve">
|
<data name="TbBrowse" xml:space="preserve">
|
||||||
<value>Browse</value>
|
<value>Browse</value>
|
||||||
|
|
|
@ -701,7 +701,7 @@
|
||||||
<value>txtPreSocksPort</value>
|
<value>txtPreSocksPort</value>
|
||||||
</data>
|
</data>
|
||||||
<data name="TipPreSocksPort" xml:space="preserve">
|
<data name="TipPreSocksPort" xml:space="preserve">
|
||||||
<value>* После установки этого значения служба socks будет запущена с использованием V2ray для обеспечения таких функций, как отображение скорости</value>
|
<value>* После установки этого значения служба socks будет запущена с использованием Sing-box для обеспечения таких функций, как отображение скорости</value>
|
||||||
</data>
|
</data>
|
||||||
<data name="TbBrowse" xml:space="preserve">
|
<data name="TbBrowse" xml:space="preserve">
|
||||||
<value>Просмотр</value>
|
<value>Просмотр</value>
|
||||||
|
|
|
@ -701,7 +701,7 @@
|
||||||
<value>Socks端口</value>
|
<value>Socks端口</value>
|
||||||
</data>
|
</data>
|
||||||
<data name="TipPreSocksPort" xml:space="preserve">
|
<data name="TipPreSocksPort" xml:space="preserve">
|
||||||
<value>* 自定义配置的Socks端口值,可不设置;当设置此值后,将使用V2ray-core额外启动一个前置Socks服务,提供分流和速度显示等功能</value>
|
<value>* 自定义配置的Socks端口值,可不设置;当设置此值后,将使用Sing-box额外启动一个前置Socks服务,提供分流和速度显示等功能</value>
|
||||||
</data>
|
</data>
|
||||||
<data name="TbBrowse" xml:space="preserve">
|
<data name="TbBrowse" xml:space="preserve">
|
||||||
<value>浏览</value>
|
<value>浏览</value>
|
||||||
|
|
Loading…
Reference in a new issue