mirror of
https://github.com/Mahdi-zarei/nekoray.git
synced 2026-01-08 06:19:13 +08:00
feat: Add routing profiles for bypassing Iran and Chinese traffic
This commit is contained in:
parent
8527fdde5f
commit
07fffcae19
@ -88,6 +88,10 @@ namespace NekoGui {
|
||||
routes[id] = route;
|
||||
}
|
||||
|
||||
// Add default route chains
|
||||
routes[IranBypassChainID] = RoutingChain::GetIranDefaultChain();
|
||||
routes[ChinaBypassChainID] = RoutingChain::GetChinaDefaultChain();
|
||||
|
||||
// First setup
|
||||
if (groups.empty()) {
|
||||
auto defaultGroup = NekoGui::ProfileManager::NewGroup();
|
||||
|
||||
@ -297,16 +297,76 @@ namespace NekoGui {
|
||||
return res;
|
||||
}
|
||||
|
||||
bool RoutingChain::isViewOnly() const {
|
||||
return id == IranBypassChainID ||
|
||||
id == ChinaBypassChainID;
|
||||
}
|
||||
|
||||
std::shared_ptr<RoutingChain> RoutingChain::GetDefaultChain() {
|
||||
auto defaultChain = std::make_shared<RoutingChain>();
|
||||
defaultChain->name = "Default";
|
||||
auto defaultRule = std::make_shared<RouteRule>();
|
||||
defaultRule->name = "Route DNS";
|
||||
defaultRule->protocol = "dns";
|
||||
defaultRule->outboundID = -4;
|
||||
defaultChain->Rules << defaultRule;
|
||||
return defaultChain;
|
||||
}
|
||||
|
||||
std::shared_ptr<RoutingChain> RoutingChain::GetIranDefaultChain() {
|
||||
auto chain = std::make_shared<RoutingChain>();
|
||||
chain->name = "Bypass Iran";
|
||||
chain->id = IranBypassChainID;
|
||||
chain->save_control_no_save = true;
|
||||
|
||||
auto rule0 = std::make_shared<RouteRule>();
|
||||
rule0->name = "Route DNS";
|
||||
rule0->protocol = "dns";
|
||||
rule0->outboundID = -4;
|
||||
chain->Rules << rule0;
|
||||
|
||||
auto rule1 = std::make_shared<RouteRule>();
|
||||
rule1->rule_set << QString("ir_IP") << QString("category-ir_SITE");
|
||||
rule1->name = "Bypass Iran IPs and Domains";
|
||||
rule1->outboundID = -2;
|
||||
chain->Rules << rule1;
|
||||
|
||||
auto rule2 = std::make_shared<RouteRule>();
|
||||
rule2->name = "Bypass Private IPs";
|
||||
rule2->ip_is_private = true;
|
||||
rule1->outboundID = -2;
|
||||
chain->Rules << rule2;
|
||||
|
||||
return chain;
|
||||
}
|
||||
|
||||
std::shared_ptr<RoutingChain> RoutingChain::GetChinaDefaultChain() {
|
||||
auto chain = std::make_shared<RoutingChain>();
|
||||
chain->name = "Bypass China";
|
||||
chain->id = ChinaBypassChainID;
|
||||
chain->save_control_no_save = true;
|
||||
|
||||
auto rule0 = std::make_shared<RouteRule>();
|
||||
rule0->name = "Route DNS";
|
||||
rule0->protocol = "dns";
|
||||
rule0->outboundID = -4;
|
||||
chain->Rules << rule0;
|
||||
|
||||
auto rule1 = std::make_shared<RouteRule>();
|
||||
rule1->name = "Bypass Chinese IPs and Domains";
|
||||
rule1->rule_set << QString("cn_IP") << QString("geolocation-cn_SITE");
|
||||
rule1->outboundID = -2;
|
||||
chain->Rules << rule1;
|
||||
|
||||
auto rule2 = std::make_shared<RouteRule>();
|
||||
rule2->name = "Bypass Private IPs";
|
||||
rule2->ip_is_private = true;
|
||||
rule1->outboundID = -2;
|
||||
chain->Rules << rule2;
|
||||
|
||||
return chain;
|
||||
}
|
||||
|
||||
std::shared_ptr<QList<int>> RoutingChain::get_used_outbounds() {
|
||||
auto res = std::make_shared<QList<int>>();
|
||||
for (const auto& item: Rules) {
|
||||
|
||||
@ -4,6 +4,8 @@
|
||||
|
||||
namespace NekoGui {
|
||||
enum inputType {trufalse, select, text};
|
||||
const int IranBypassChainID = 111111111;
|
||||
const int ChinaBypassChainID = 222222222;
|
||||
|
||||
class RouteRule : public JsonStore {
|
||||
public:
|
||||
@ -60,8 +62,14 @@ namespace NekoGui {
|
||||
|
||||
QJsonArray get_route_rules(bool forView = false, std::map<int, QString> outboundMap = {});
|
||||
|
||||
bool isViewOnly() const;
|
||||
|
||||
static std::shared_ptr<RoutingChain> GetDefaultChain();
|
||||
|
||||
static std::shared_ptr<RoutingChain> GetIranDefaultChain();
|
||||
|
||||
static std::shared_ptr<RoutingChain> GetChinaDefaultChain();
|
||||
|
||||
std::shared_ptr<QList<int>> get_used_outbounds();
|
||||
|
||||
std::shared_ptr<QStringList> get_used_rule_sets();
|
||||
|
||||
@ -166,6 +166,7 @@ void DialogManageRoutes::on_edit_route_clicked() {
|
||||
routeChainWidget->setWindowModality(Qt::ApplicationModal);
|
||||
routeChainWidget->show();
|
||||
connect(routeChainWidget, &RouteItem::settingsChanged, this, [=](const std::shared_ptr<NekoGui::RoutingChain>& chain) {
|
||||
if (chain->isViewOnly()) return;
|
||||
chainList[idx] = chain;
|
||||
reloadProfileItems();
|
||||
});
|
||||
@ -181,6 +182,7 @@ void DialogManageRoutes::on_delete_route_clicked() {
|
||||
}
|
||||
|
||||
auto profileToDel = chainList[idx];
|
||||
if (profileToDel->isViewOnly()) return;
|
||||
chainList.removeAt(idx);
|
||||
if (profileToDel->id == currentRouteProfileID) {
|
||||
currentRouteProfileID = chainList[0]->id;
|
||||
|
||||
@ -185,6 +185,16 @@ RouteItem::RouteItem(QWidget *parent, const std::shared_ptr<NekoGui::RoutingChai
|
||||
connect(deleteShortcut, &QShortcut::activated, this, [=]{
|
||||
on_delete_route_item_clicked();
|
||||
});
|
||||
|
||||
if (chain->isViewOnly()) {
|
||||
ui->route_name->setText(chain->name + " (View only)");
|
||||
ui->route_name->setEnabled(false);
|
||||
ui->rule_attr_box->setEnabled(false);
|
||||
ui->new_route_item->setEnabled(false);
|
||||
ui->moveup_route_item->setEnabled(false);
|
||||
ui->movedown_route_item->setEnabled(false);
|
||||
ui->delete_route_item->setEnabled(false);
|
||||
}
|
||||
}
|
||||
|
||||
RouteItem::~RouteItem() {
|
||||
@ -255,7 +265,7 @@ void RouteItem::updateRuleSection() {
|
||||
}
|
||||
}
|
||||
ui->rule_name->setText(ruleItem->name);
|
||||
ui->rule_attr_box->setEnabled(true);
|
||||
ui->rule_attr_box->setDisabled(chain->isViewOnly());
|
||||
ui->rule_out->setCurrentText(get_outbound_name(ruleItem->outboundID));
|
||||
if (currentAttr == "rule_set") ui->rule_set_helper->show();
|
||||
else ui->rule_set_helper->hide();
|
||||
@ -311,6 +321,7 @@ void RouteItem::applyRuleHelperSelect(const QModelIndex& index) {
|
||||
}
|
||||
|
||||
void RouteItem::on_new_route_item_clicked() {
|
||||
if (chain->isViewOnly()) return;
|
||||
auto routeItem = std::make_shared<NekoGui::RouteRule>();
|
||||
routeItem->name = "rule_" + Int2String(++lastNum);
|
||||
chain->Rules << routeItem;
|
||||
@ -323,6 +334,7 @@ void RouteItem::on_new_route_item_clicked() {
|
||||
}
|
||||
|
||||
void RouteItem::on_moveup_route_item_clicked() {
|
||||
if (chain->isViewOnly()) return;
|
||||
if (currentIndex == -1 || currentIndex == 0) return;
|
||||
auto curr = chain->Rules[currentIndex];
|
||||
chain->Rules[currentIndex] = chain->Rules[currentIndex-1];
|
||||
@ -332,6 +344,7 @@ void RouteItem::on_moveup_route_item_clicked() {
|
||||
}
|
||||
|
||||
void RouteItem::on_movedown_route_item_clicked() {
|
||||
if (chain->isViewOnly()) return;
|
||||
if (currentIndex == -1 || currentIndex == chain->Rules.size() - 1) return;
|
||||
auto curr = chain->Rules[currentIndex];
|
||||
chain->Rules[currentIndex] = chain->Rules[currentIndex+1];
|
||||
@ -341,6 +354,7 @@ void RouteItem::on_movedown_route_item_clicked() {
|
||||
}
|
||||
|
||||
void RouteItem::on_delete_route_item_clicked() {
|
||||
if (chain->isViewOnly()) return;
|
||||
if (currentIndex == -1) return;
|
||||
chain->Rules.removeAt(currentIndex);
|
||||
if (chain->Rules.empty()) currentIndex = -1;
|
||||
|
||||
Loading…
Reference in New Issue
Block a user