Skip to content

Commit

Permalink
feat: support i18n in frontend
Browse files Browse the repository at this point in the history
  • Loading branch information
7Sageer committed Feb 18, 2025
1 parent 84acdec commit 8d056e9
Show file tree
Hide file tree
Showing 11 changed files with 394 additions and 152 deletions.
5 changes: 3 additions & 2 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -46,6 +46,7 @@
- 支持固定/随机短链接生成(基于 KV)
- 浅色/深色主题切换
- 灵活的 API,支持脚本化操作
- 中文,英语,阿拉伯三语言支持

### 客户端支持
- Sing-Box
Expand All @@ -69,9 +70,9 @@

## 📝 最近更新

### 2025-01-11
### 2025-02-18

- 使用代理获取规则集
- 添加前端i18n支持,后续会完善订阅逻辑

## 🔧 项目结构

Expand Down
4 changes: 4 additions & 0 deletions docs/update-log.md
Original file line number Diff line number Diff line change
@@ -1,5 +1,9 @@
# 更新日志

## 2025-02-18

- 添加前端i18n支持,后续会完善订阅逻辑

## 2025-01-11

- 使用代理获取规则集
Expand Down
Empty file added index.js
Empty file.
5 changes: 2 additions & 3 deletions src/ClashConfigBuilder.js
Original file line number Diff line number Diff line change
Expand Up @@ -4,14 +4,13 @@ import { BaseConfigBuilder } from './BaseConfigBuilder.js';
import { DeepCopy } from './utils.js';

export class ClashConfigBuilder extends BaseConfigBuilder {
constructor(inputString, selectedRules, customRules, pin, baseConfig) {
constructor(inputString, selectedRules, customRules, baseConfig) {
if (!baseConfig) {
baseConfig = CLASH_CONFIG
}
super(inputString, baseConfig);
this.selectedRules = selectedRules;
this.customRules = customRules;
this.pin = pin;
}

addCustomItems(customItems) {
Expand Down Expand Up @@ -79,7 +78,7 @@ export class ClashConfigBuilder extends BaseConfigBuilder {
});
}
formatConfig() {
const rules = generateRules(this.selectedRules, this.customRules, this.pin);
const rules = generateRules(this.selectedRules, this.customRules);

this.config.rules = rules.flatMap(rule => {
const siteRules = rule.site_rules[0] !== '' ? rule.site_rules.map(site => `GEOSITE,${site},${rule.outbound}`) : [];
Expand Down
7 changes: 3 additions & 4 deletions src/SingboxConfigBuilder.js
Original file line number Diff line number Diff line change
Expand Up @@ -2,15 +2,14 @@ import { SING_BOX_CONFIG, generateRuleSets, generateRules, getOutbounds, PREDEFI
import { BaseConfigBuilder } from './BaseConfigBuilder.js';
import { DeepCopy } from './utils.js';

export class ConfigBuilder extends BaseConfigBuilder {
constructor(inputString, selectedRules, customRules, pin, baseConfig) {
export class SingboxConfigBuilder extends BaseConfigBuilder {
constructor(inputString, selectedRules, customRules, baseConfig) {
if (baseConfig === undefined) {
baseConfig = SING_BOX_CONFIG
}
super(inputString, baseConfig);
this.selectedRules = selectedRules;
this.customRules = customRules;
this.pin = pin;
}

addCustomItems(customItems) {
Expand Down Expand Up @@ -73,7 +72,7 @@ export class ConfigBuilder extends BaseConfigBuilder {
}

formatConfig() {
const rules = generateRules(this.selectedRules, this.customRules, this.pin);
const rules = generateRules(this.selectedRules, this.customRules);
const { site_rule_sets, ip_rule_sets } = generateRuleSets(this.selectedRules,this.customRules);

this.config.route.rule_set = [...site_rule_sets, ...ip_rule_sets];
Expand Down
5 changes: 2 additions & 3 deletions src/SurgeConfigBuilder.js
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ import { BaseConfigBuilder } from './BaseConfigBuilder.js';
import { generateRules, getOutbounds, PREDEFINED_RULE_SETS } from './config.js';

export class SurgeConfigBuilder extends BaseConfigBuilder {
constructor(inputString, selectedRules, customRules, pin, baseConfig) {
constructor(inputString, selectedRules, customRules, baseConfig) {
super(inputString, baseConfig || {
'general': {
'allow-wifi-access': false,
Expand Down Expand Up @@ -36,7 +36,6 @@ export class SurgeConfigBuilder extends BaseConfigBuilder {
});
this.selectedRules = selectedRules;
this.customRules = customRules;
this.pin = pin;
this.subscriptionUrl = null;
}

Expand Down Expand Up @@ -201,7 +200,7 @@ export class SurgeConfigBuilder extends BaseConfigBuilder {
}

formatConfig() {
const rules = generateRules(this.selectedRules, this.customRules, this.pin);
const rules = generateRules(this.selectedRules, this.customRules);

// 构建最终配置
let finalConfig = [];
Expand Down
91 changes: 38 additions & 53 deletions src/config.js
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
import { t } from './i18n';

export const SITE_RULE_SET_BASE_URL = 'https://gh.sageer.me/https://raw.githubusercontent.com/lyc8503/sing-box-rules/refs/heads/rule-set-geosite/';
export const IP_RULE_SET_BASE_URL = 'https://gh.sageer.me/https://raw.githubusercontent.com/lyc8503/sing-box-rules/refs/heads/rule-set-geoip/';
// Custom rules
Expand All @@ -6,114 +8,112 @@ export const CUSTOM_RULES = [];
export const UNIFIED_RULES = [
{
name: 'Ad Block',
outbound: '🛑 广告拦截',
outbound: t('outboundNames.Ad Block'),
site_rules: ['category-ads-all'],
ip_rules: []
},
{
name: 'AI Services',
outbound: '💬 AI 服务',
outbound: t('outboundNames.AI Services'),
site_rules: ['openai', 'anthropic','jetbrains-ai','perplexity'],
ip_rules: []
},
{
name: 'Bilibili',
outbound: '📺 哔哩哔哩',
outbound: t('outboundNames.Bilibili'),
site_rules: ['bilibili'],
ip_rules: []
},
{
name: 'Youtube',
outbound: '📹 油管视频',
outbound: t('outboundNames.Youtube'),
site_rules: ['youtube'],
ip_rules: []
},
{
name: 'Google',
outbound: '🔍 谷歌服务',
outbound: t('outboundNames.Google'),
site_rules: ['google'],
ip_rules: ['google']
},

{
name: 'Private',
outbound: '🏠 私有网络',
outbound: t('outboundNames.Private'),
site_rules: [],
ip_rules: ['private']
},
{
name: 'Location:CN',
outbound: '🔒 国内服务',
outbound: t('outboundNames.Location:CN'),
site_rules: ['geolocation-cn'],
ip_rules: ['cn']
},
{
name: 'Telegram',
outbound: '📲 电报消息',
outbound: t('outboundNames.Telegram'),
site_rules: [],
ip_rules: ['telegram']
},
{
name: 'Github',
outbound: '🐱 Github',
outbound: t('outboundNames.Github'),
site_rules: ['github', 'gitlab'],
ip_rules: []
},
{
name: 'Microsoft',
outbound: 'Ⓜ️ 微软服务',
outbound: t('outboundNames.Microsoft'),
site_rules: ['microsoft'],
ip_rules: []
},
{
name: 'Apple',
outbound: '🍏 苹果服务',
outbound: t('outboundNames.Apple'),
site_rules: ['apple'],
ip_rules: []
},
{
name: 'Social Media',
outbound: '🌐 社交媒体',
outbound: t('outboundNames.Social Media'),
site_rules: ['facebook', 'instagram', 'twitter', 'tiktok', 'linkedin'],
ip_rules: []
},
{
},
{
name: 'Streaming',
outbound: '🎬 流媒体',
outbound: t('outboundNames.Streaming'),
site_rules: ['netflix', 'hulu', 'disney', 'hbo', 'amazon','bahamut'],
ip_rules: []
},
{
},
{
name: 'Gaming',
outbound: '🎮 游戏平台',
outbound: t('outboundNames.Gaming'),
site_rules: ['steam', 'epicgames', 'ea', 'ubisoft', 'blizzard'],
ip_rules: []
},
{
},
{
name: 'Education',
outbound: '📚 教育资源',
outbound: t('outboundNames.Education'),
site_rules: ['coursera', 'edx', 'udemy', 'khanacademy', 'category-scholar-!cn'],
ip_rules: []
},
{
},
{
name: 'Financial',
outbound: '💰 金融服务',
outbound: t('outboundNames.Financial'),
site_rules: ['paypal', 'visa', 'mastercard','stripe','wise'],
ip_rules: []
},
{
},
{
name: 'Cloud Services',
outbound: '☁️ 云服务',
outbound: t('outboundNames.Cloud Services'),
site_rules: ['aws', 'azure', 'digitalocean', 'heroku', 'dropbox'],
ip_rules: []
},
{
},
{
name: 'Non-China',
outbound: '🌐 非中国',
outbound: t('outboundNames.Non-China'),
site_rules: ['geolocation-!cn'],
ip_rules: []
}

}
];

export const PREDEFINED_RULE_SETS = {
Expand Down Expand Up @@ -150,7 +150,7 @@ export function getOutbounds(selectedRuleNames) {
}

// Helper function to generate rules based on selected rule names
export function generateRules(selectedRules = [], customRules = [], pin) {
export function generateRules(selectedRules = [], customRules = []) {
if (typeof selectedRules === 'string' && PREDEFINED_RULE_SETS[selectedRules]) {
selectedRules = PREDEFINED_RULE_SETS[selectedRules];
}
Expand All @@ -173,33 +173,18 @@ export function generateRules(selectedRules = [], customRules = [], pin) {
}
});

if (customRules && customRules.length > 0 && pin !== "true") {
customRules.forEach((rule) => {
rules.push({
customRules.reverse();
customRules.forEach((rule) => {
rules.unshift({
site_rules: rule.site.split(','),
ip_rules: rule.ip.split(','),
domain_suffix: rule.domain_suffix ? rule.domain_suffix.split(',') : [],
domain_keyword: rule.domain_keyword ? rule.domain_keyword.split(',') : [],
ip_cidr: rule.ip_cidr ? rule.ip_cidr.split(',') : [],
protocol: rule.protocol ? rule.protocol.split(',') : [],
outbound: rule.name
});
});
}
else if (customRules && customRules.length > 0 && pin === "true") {
customRules.reverse();
customRules.forEach((rule) => {
rules.unshift({
site_rules: rule.site.split(','),
ip_rules: rule.ip.split(','),
domain_suffix: rule.domain_suffix ? rule.domain_suffix.split(',') : [],
domain_keyword: rule.domain_keyword ? rule.domain_keyword.split(',') : [],
ip_cidr: rule.ip_cidr ? rule.ip_cidr.split(',') : [],
protocol: rule.protocol ? rule.protocol.split(',') : [],
outbound: rule.name
});
});
}
});

return rules;
}
Expand Down
Loading

0 comments on commit 8d056e9

Please sign in to comment.