extractBaiduPan.js 1.8 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465
  1. /**
  2. * 从混合格式文案(含文件名、说明、提取码等)中解析百度网盘标准分享链接。
  3. */
  4. const PAN_S_URL_RE =
  5. /https?:\/\/pan\.baidu\.com\/s\/[A-Za-z0-9_-]+(?:\?(?:[A-Za-z0-9_=&%.-]*))?/i;
  6. const PWD_LABEL_RE = /(?:提取码|密码|提取\s*码)[::\s]*([A-Za-z0-9]{4,8})\b/i;
  7. const FIRST_HTTP_RE =
  8. /https?:\/\/[^\s\u4e00-\u9fff\u3000-\u303f]+/i;
  9. /**
  10. * @param {string|null|undefined} text
  11. * @returns {{ url: string|null, pwd: string|null }}
  12. */
  13. export function parseBaiduPanShare(text) {
  14. if (text == null || text === "") {
  15. return { url: null, pwd: null };
  16. }
  17. const s = String(text);
  18. const urlMatch = s.match(PAN_S_URL_RE);
  19. let url = urlMatch ? urlMatch[0] : null;
  20. let pwd = null;
  21. if (url) {
  22. try {
  23. const u = new URL(url);
  24. pwd = u.searchParams.get("pwd") || u.searchParams.get("PWD");
  25. } catch {
  26. /* ignore */
  27. }
  28. }
  29. const pwdLabel = s.match(PWD_LABEL_RE);
  30. if (!pwd && pwdLabel) {
  31. pwd = pwdLabel[1];
  32. }
  33. if (url && pwd && !/pwd=/i.test(url)) {
  34. url += url.includes("?") ? `&pwd=${encodeURIComponent(pwd)}` : `?pwd=${encodeURIComponent(pwd)}`;
  35. }
  36. return { url, pwd };
  37. }
  38. /**
  39. * 表格/外链打开用:优先解析百度分享;否则取文案中首个 http(s) URL(去掉末尾中英文标点粘连)。
  40. * @param {string|null|undefined} raw
  41. * @returns {string|null}
  42. */
  43. export function resolveExternalShareUrl(raw) {
  44. const { url } = parseBaiduPanShare(raw);
  45. if (url) return url;
  46. if (raw == null || raw === "") return null;
  47. const s = String(raw).trim();
  48. const any = s.match(FIRST_HTTP_RE);
  49. if (any) {
  50. return any[0].replace(/[,.;,。、;]+$/, "");
  51. }
  52. if (/^https?:\/\//i.test(s)) {
  53. return s.replace(/[,.;,。、;]+$/, "");
  54. }
  55. return null;
  56. }