Add custom outbound support (#9817)

* Add custom outbound support

* Add test

* Add inner fmt support

* Full config to outbounds

* Rename to `Outbound`

* AI optimized

* Fix

* Add bind interface placeholder

---------

Co-authored-by: 2dust <31833384+2dust@users.noreply.github.com>
This commit is contained in:
DHR60
2026-08-05 14:25:16 +08:00
committed by GitHub
co-authored by 2dust
parent ccf18ba0fb
commit eff584597f
43 changed files with 1364 additions and 367 deletions
@@ -12,6 +12,9 @@ public partial class AddServer2ViewModel : MyReactiveObject, ICloseable
[Reactive]
public partial string? CoreType { get; set; }
[Reactive]
public partial bool IsSingboxEndpoint { get; set; }
public ReactiveCommand<RxVoid, RxVoid> BrowseServerCmd { get; }
public ReactiveCommand<RxVoid, RxVoid> EditServerCmd { get; }
public ReactiveCommand<RxVoid, RxVoid> SaveServerCmd { get; }
@@ -40,7 +43,10 @@ public partial class AddServer2ViewModel : MyReactiveObject, ICloseable
});
SelectedSource = profileItem.IndexId.IsNullOrEmpty() ? profileItem : JsonUtils.DeepCopy(profileItem);
CoreType = SelectedSource?.CoreType?.ToString();
var coreStr = SelectedSource?.CoreType?.ToString();
coreStr = coreStr.IsNullOrEmpty() ? Global.CoreTypes.FirstOrDefault() : coreStr;
CoreType = coreStr;
IsSingboxEndpoint = SelectedSource?.GetProtocolExtra()?.IsSingboxEndpoint ?? false;
}
private async Task SaveServerAsync()
@@ -58,6 +64,10 @@ public partial class AddServer2ViewModel : MyReactiveObject, ICloseable
return;
}
SelectedSource.CoreType = CoreType.IsNullOrEmpty() ? null : Enum.Parse<ECoreType>(CoreType);
SelectedSource.SetProtocolExtra(SelectedSource?.GetProtocolExtra() with
{
IsSingboxEndpoint = IsSingboxEndpoint ? true : null,
});
if (await ConfigHandler.EditCustomServer(_config, SelectedSource) == 0)
{
@@ -80,7 +90,8 @@ public partial class AddServer2ViewModel : MyReactiveObject, ICloseable
var item = await AppManager.Instance.GetProfileItem(SelectedSource.IndexId);
item ??= SelectedSource;
item.Address = fileName;
if (await ConfigHandler.AddCustomServer(_config, item, false) == 0)
var result = item.ConfigType == EConfigType.Outbound ? await ConfigHandler.AddCustomOutboundServer(_config, item, false) : await ConfigHandler.AddCustomServer(_config, item, false);
if (result == 0)
{
NoticeManager.Instance.Enqueue(ResUI.SuccessfullyImportedCustomServer);
if (item.IndexId.IsNotEmpty())