setting.ts 8.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198
  1. import { z } from 'zod';
  2. const port = z.number().int().min(1).max(65535);
  3. const nonNegativeInt = z.number().int().min(0);
  4. const absolutePath = z.string().regex(/^\//, 'pages.settings.validation.pathLeadingSlash');
  5. export const SubProfileModeSchema = z.enum(['none', 'builtin', 'custom']);
  6. export type SubProfileMode = z.infer<typeof SubProfileModeSchema>;
  7. export const AllSettingSchema = z
  8. .object({
  9. webListen: z.string().optional(),
  10. webDomain: z.string().optional(),
  11. webPort: port.optional(),
  12. webCertFile: z.string().optional(),
  13. webKeyFile: z.string().optional(),
  14. webBasePath: absolutePath.optional(),
  15. sessionMaxAge: z.number().int().min(1).max(525600).optional(),
  16. trustedProxyCIDRs: z.string().optional(),
  17. realityScanCandidates: z.string().optional(),
  18. ipLimitAllowlist: z.string().optional(),
  19. panelOutbound: z.string().optional(),
  20. pageSize: z.number().int().min(0).max(1000).optional(),
  21. expireDiff: nonNegativeInt.optional(),
  22. trafficDiff: nonNegativeInt.max(100).optional(),
  23. remarkTemplate: z.string().optional(),
  24. subShowIdentityOnAllLinks: z.boolean().optional(),
  25. subInfoNodeEnable: z.boolean().optional(),
  26. subCalendarExpireInclusive: z.boolean().optional(),
  27. subExpiredTemplate: z.string().optional(),
  28. subTrafficDepletedTemplate: z.string().optional(),
  29. datepicker: z.enum(['gregorian', 'jalalian']).optional(),
  30. tgBotEnable: z.boolean().optional(),
  31. tgBotToken: z.string().optional(),
  32. tgBotProxy: z.string().optional(),
  33. tgBotAPIServer: z.string().optional(),
  34. tgBotChatId: z.string().optional(),
  35. tgRunTime: z.string().optional(),
  36. tgBotBackup: z.boolean().optional(),
  37. tgCpu: z.number().int().min(0).max(100).optional(),
  38. outboundDownThreshold: z.number().int().min(1).max(100).optional(),
  39. tgLang: z.string().optional(),
  40. twoFactorEnable: z.boolean().optional(),
  41. twoFactorToken: z.string().optional(),
  42. xrayTemplateConfig: z.string().optional(),
  43. happLinkEnable: z.boolean().optional(),
  44. subEnable: z.boolean().optional(),
  45. subJsonEnable: z.boolean().optional(),
  46. subJsonAutoDetect: z.boolean().optional(),
  47. subJsonAlwaysArray: z.boolean().optional(),
  48. subJsonUserAgentRegex: z.string().max(2048).optional(),
  49. subClashAutoDetect: z.boolean().optional(),
  50. subClashUserAgentRegex: z.string().max(2048).optional(),
  51. subTitle: z.string().optional(),
  52. subSupportUrl: z.string().optional(),
  53. subProfileMode: SubProfileModeSchema.optional(),
  54. subProfileUrl: z.string().optional(),
  55. subAnnounce: z.string().optional(),
  56. subEnableRouting: z.boolean().optional(),
  57. subRoutingRules: z.string().optional(),
  58. subIncyEnableRouting: z.boolean().optional(),
  59. subIncyRoutingRules: z.string().optional(),
  60. subListen: z.string().optional(),
  61. subPort: port.optional(),
  62. subPath: absolutePath.optional(),
  63. subJsonPath: absolutePath.optional(),
  64. subClashEnable: z.boolean().optional(),
  65. subClashPath: absolutePath.optional(),
  66. subDomain: z.string().optional(),
  67. externalTrafficInformEnable: z.boolean().optional(),
  68. externalTrafficInformURI: z.string().optional(),
  69. restartXrayOnClientDisable: z.boolean().optional(),
  70. subCertFile: z.string().optional(),
  71. subKeyFile: z.string().optional(),
  72. externalSubUserAgent: z.string().max(512).optional(),
  73. subUpdates: z.number().int().min(0).max(525600).optional(),
  74. subEncrypt: z.boolean().optional(),
  75. subURI: z.string().optional(),
  76. subJsonURI: z.string().optional(),
  77. subClashURI: z.string().optional(),
  78. subClashEnableRouting: z.boolean().optional(),
  79. subClashRules: z.string().optional(),
  80. subJsonMux: z.string().optional(),
  81. subJsonRules: z.string().optional(),
  82. subJsonRoutingRules: z.string().optional(),
  83. subJsonDns: z.string().optional(),
  84. subJsonFinalMask: z.string().optional(),
  85. subJsonObservatory: z.string().optional(),
  86. subHideSettings: z.boolean().optional(),
  87. subHappAutoDetect: z.boolean().optional(),
  88. subHappProviderId: z.string().optional(),
  89. subHappNewUrl: z.string().optional(),
  90. subHappFallbackUrl: z.string().optional(),
  91. subHappSubInfoColor: z.string().optional(),
  92. subHappSubInfoText: z.string().optional(),
  93. subHappSubInfoButtonText: z.string().optional(),
  94. subHappSubInfoButtonLink: z.string().optional(),
  95. subHappSubExpire: z.boolean().optional(),
  96. subHappSubExpireButtonLink: z.string().optional(),
  97. subHappNotificationExpire: z.boolean().optional(),
  98. subHappNoLimit: z.boolean().optional(),
  99. subHappAlwaysHwid: z.boolean().optional(),
  100. subHappTunMode: z.string().optional(),
  101. subHappTunType: z.string().optional(),
  102. subHappExcludeRoutes: z.string().optional(),
  103. subHappExcludeApns: z.boolean().optional(),
  104. subHappColorProfile: z.string().optional(),
  105. subHappPingType: z.string().optional(),
  106. subHappAutoConnect: z.boolean().optional(),
  107. subHappAutoConnectType: z.string().optional(),
  108. subHappPerAppMode: z.string().optional(),
  109. subHappPerAppList: z.string().optional(),
  110. subHappLocalProxyAuth: z.string().optional(),
  111. subIncyAppAutoDetect: z.boolean().optional(),
  112. subIncyProfileDescription: z.string().optional(),
  113. subIncySortOrder: z.string().optional(),
  114. subIncySupportEmail: z.string().optional(),
  115. subIncyAnnounceUrl: z.string().optional(),
  116. subIncyPremiumUrl: z.string().optional(),
  117. subIncyBannerText: z.string().optional(),
  118. subIncyBannerButtonText: z.string().optional(),
  119. subIncyBannerButtonUrl: z.string().optional(),
  120. subIncyBannerBgColor: z.string().optional(),
  121. subIncyBannerButtonColor: z.string().optional(),
  122. subIncyHideUrl: z.string().optional(),
  123. subIncyHideCheck: z.string().optional(),
  124. subIncyNoLimitEnabled: z.string().optional(),
  125. subIncyPerAppEnable: z.string().optional(),
  126. subIncyPerAppMode: z.string().optional(),
  127. subIncyPerAppList: z.string().optional(),
  128. subIncyFragmentationEnable: z.string().optional(),
  129. subIncyFragmentLength: z.string().optional(),
  130. subIncyFragmentInterval: z.string().optional(),
  131. subIncyFragmentPackets: z.string().optional(),
  132. subIncyNoisesEnable: z.string().optional(),
  133. subIncyNoisesType: z.string().optional(),
  134. subIncyNoisesPacket: z.string().optional(),
  135. subIncyNoisesDelay: z.string().optional(),
  136. subIncyResolveEnable: z.string().optional(),
  137. subIncyResolveDnsDomain: z.string().optional(),
  138. subIncyResolveDnsIp: z.string().optional(),
  139. timeLocation: z.string().optional(),
  140. ldapEnable: z.boolean().optional(),
  141. ldapHost: z.string().optional(),
  142. ldapPort: port.optional(),
  143. ldapUseTLS: z.boolean().optional(),
  144. ldapInsecureSkipVerify: z.boolean().optional(),
  145. ldapBindDN: z.string().optional(),
  146. ldapPassword: z.string().optional(),
  147. ldapBaseDN: z.string().optional(),
  148. ldapUserFilter: z.string().optional(),
  149. ldapUserAttr: z.string().optional(),
  150. ldapVlessField: z.string().optional(),
  151. ldapSyncCron: z.string().optional(),
  152. ldapFlagField: z.string().optional(),
  153. ldapTruthyValues: z.string().optional(),
  154. ldapInvertFlag: z.boolean().optional(),
  155. ldapInboundTags: z.string().optional(),
  156. ldapAutoCreate: z.boolean().optional(),
  157. ldapAutoDelete: z.boolean().optional(),
  158. ldapDefaultTotalGB: nonNegativeInt.optional(),
  159. ldapDefaultExpiryDays: nonNegativeInt.optional(),
  160. ldapDefaultLimitIP: nonNegativeInt.optional(),
  161. hasTgBotToken: z.boolean().optional(),
  162. hasTwoFactorToken: z.boolean().optional(),
  163. hasLdapPassword: z.boolean().optional(),
  164. hasApiToken: z.boolean().optional(),
  165. hasWarpSecret: z.boolean().optional(),
  166. hasNordSecret: z.boolean().optional(),
  167. hasSmtpPassword: z.boolean().optional(),
  168. hasDiscordBotToken: z.boolean().optional(),
  169. discordBotEnable: z.boolean().optional(),
  170. discordBotToken: z.string().optional(),
  171. discordChannelId: z.string().optional(),
  172. discordAdminIds: z.string().optional(),
  173. discordRunTime: z.string().optional(),
  174. discordBotBackup: z.boolean().optional(),
  175. discordCpu: z.number().int().min(0).max(100).optional(),
  176. discordMemory: z.number().int().min(0).max(100).optional(),
  177. discordLang: z.string().optional(),
  178. discordEnabledEvents: z.string().optional(),
  179. })
  180. .loose();
  181. export type AllSettingInput = z.infer<typeof AllSettingSchema>;
  182. // Existing installations can contain regex values saved before the backend
  183. // enforced its 2,048-character limit. Accept those values when reading so the
  184. // settings page can display and let users correct them, while keeping the
  185. // stricter schema above for outgoing updates.
  186. export const AllSettingResponseSchema = AllSettingSchema.extend({
  187. subJsonUserAgentRegex: z.string().optional(),
  188. subClashUserAgentRegex: z.string().optional(),
  189. });
  190. export const FactoryDefaultsSchema = z.record(z.string(), z.string());
  191. export type FactoryDefaults = z.infer<typeof FactoryDefaultsSchema>;