build-sgmodule-always-realip.ts 2.4 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677
  1. import path from 'node:path';
  2. import { task } from './trace';
  3. import { compareAndWriteFile } from './lib/create-file';
  4. import { DIRECTS, LANS } from '../Source/non_ip/direct';
  5. import * as yaml from 'yaml';
  6. import { writeFile } from './lib/misc';
  7. import { OUTPUT_INTERNAL_DIR, OUTPUT_MODULES_DIR } from './constants/dir';
  8. const HOSTNAMES = [
  9. // Network Detection, Captive Portal
  10. 'msftncsi.com',
  11. 'msftconnecttest.com',
  12. '*.msftncsi.com',
  13. '*.msftconnecttest.com',
  14. 'network-test.debian.org',
  15. 'detectportal.firefox.com',
  16. 'resolver1.opendns.com',
  17. '*.ipv6.microsoft.com',
  18. // Handle SNAT conversation properly
  19. '*.srv.nintendo.net',
  20. '*.stun.playstation.net',
  21. 'xbox.*.microsoft.com',
  22. '*.xboxlive.com',
  23. 'turn.twilio.com',
  24. '*.turn.twilio.com',
  25. 'stun.twilio.com',
  26. '*.stun.twilio.com',
  27. 'stun.syncthing.net',
  28. 'stun.*',
  29. 'controlplane.tailscale.com',
  30. // NTP
  31. 'time.*.com', 'time.*.gov, time.*.edu.cn, time.*.apple.com', 'time?.*.com', 'ntp.*.com', 'ntp?.*.com', '*.time.edu.cn', '*.ntp.org.cn', '*.pool.ntp.org', 'time*.cloud.tencent.com',
  32. // QQ Login
  33. 'localhost.ptlogin2.qq.com',
  34. 'localhost.sec.qq.com',
  35. 'localhost.work.weixin.qq.com',
  36. // Microsoft Auto Discovery
  37. 'PDC._msDCS.*.*',
  38. 'DC._msDCS.*.*',
  39. 'GC._msDCS.*.*',
  40. // Misc,
  41. '*.battlenet.com.cn',
  42. '*.blzstatic.cn',
  43. '*.battlenet.com'
  44. ];
  45. export const buildAlwaysRealIPModule = task(require.main === module, __filename)(async (span) => {
  46. // Intranet, Router Setup, and mant more
  47. const dataset = [Object.entries(DIRECTS), Object.entries(LANS)];
  48. const surge = dataset.flatMap(data => data.flatMap(([, { domains }]) => domains.flatMap((domain) => [`*.${domain}`, domain])));
  49. const clash = dataset.flatMap(data => data.flatMap(([, { domains }]) => domains.map((domain) => `+.${domain}`)));
  50. return Promise.all([
  51. compareAndWriteFile(
  52. span,
  53. [
  54. '#!name=[Sukka] Always Real IP Plus',
  55. `#!desc=Last Updated: ${new Date().toISOString()}`,
  56. '',
  57. '[General]',
  58. `always-real-ip = %APPEND% ${HOSTNAMES.concat(surge).join(', ')}`
  59. ],
  60. path.resolve(OUTPUT_MODULES_DIR, 'sukka_common_always_realip.sgmodule')
  61. ),
  62. writeFile(
  63. path.join(OUTPUT_INTERNAL_DIR, 'clash_fake_ip_filter.yaml'),
  64. yaml.stringify(
  65. {
  66. dns: {
  67. 'fake-ip-filter': HOSTNAMES.concat(clash)
  68. }
  69. },
  70. { version: '1.1' }
  71. )
  72. )
  73. ]);
  74. });