dsh-metaphysics 0.22.0 → 0.38.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +650 -413
- package/README.md +81 -18
- package/client.js +2975 -100
- package/docs/assets/dsh-metaphysics-group.png +0 -0
- package/engine/bazi.js +79 -2
- package/engine/classics.js +380 -0
- package/engine/followup.js +58 -0
- package/engine/geo.js +1 -1
- package/engine/index.js +168 -8
- package/engine/interpret-knowledge.js +448 -277
- package/engine/interpret-plain.js +131 -6
- package/engine/interpret.js +208 -7
- package/engine/liuyao.js +847 -237
- package/engine/mbti.js +417 -0
- package/engine/qimen-interpret.js +37 -2
- package/engine/qimen.js +128 -1
- package/engine/ziwei.js +198 -13
- package/index.js +21 -16
- package/locale/en.json +1 -1
- package/locale/zh.json +1 -1
- package/package.json +19 -15
- package//345/221/275/347/220/206/346/216/222/347/233/230.html +18737 -0
|
Binary file
|
package/engine/bazi.js
CHANGED
|
@@ -6,7 +6,7 @@ import {
|
|
|
6
6
|
} from './calendar.js';
|
|
7
7
|
import { resolveAddress } from './geo.js';
|
|
8
8
|
import { computeBaziShensha } from './shensha.js';
|
|
9
|
-
import { assertCivil } from './validate.js';
|
|
9
|
+
import { assertCivil, daysInMonth } from './validate.js';
|
|
10
10
|
import { applyDst } from './dst.js';
|
|
11
11
|
import { nayinOf } from './nayin.js';
|
|
12
12
|
import { SANHE } from './sanhe.js';
|
|
@@ -277,10 +277,29 @@ export function buildBazi(input) {
|
|
|
277
277
|
// 四舍五入到 12 个月时必须进位,否则显示「X 岁 12 个月起运」
|
|
278
278
|
if (startAgeMonths >= 12) { startAgeMonths -= 12; startAgeYears += 1; }
|
|
279
279
|
|
|
280
|
+
// 交运:三日折一年。
|
|
281
|
+
// 古法三条换算是同一比例的三种说法——3 日折 1 年、1 日折 4 个月、1 时辰折 10 日:
|
|
282
|
+
// 把「出生 → 起运那一侧的节令」的真实间隔按 365.2422/3(≈121.7474)倍放大,
|
|
283
|
+
// 就是起运那一刻;放大后的 1/12 恰好 121.7474/12 ≈ 10.15 天,即「一时辰十日」。
|
|
284
|
+
// 一年取回归年 365.2422 日(交运日细算各家不一,这里固定这一个口径并写明)。
|
|
285
|
+
const JIAO_YEAR_DAYS = 365.2422;
|
|
286
|
+
const JIAO_SCALE = JIAO_YEAR_DAYS / 3;
|
|
287
|
+
const jiaoFromTerm = forward ? nextJieTerm : prevJieTerm;
|
|
288
|
+
const jiaoJd = jd + spanDays * JIAO_SCALE;
|
|
289
|
+
const jiaoParts = jdToParts(jiaoJd);
|
|
290
|
+
// 每步大运在「同月同日同时刻」换;公历闰日(2 月 29 日生)退到 2 月 28 日
|
|
291
|
+
const addYearsClamped = (p, n) => {
|
|
292
|
+
const y = p.year + n;
|
|
293
|
+
return { year: y, month: p.month, day: Math.min(p.day, daysInMonth(y, p.month)), hour: p.hour, minute: p.minute };
|
|
294
|
+
};
|
|
295
|
+
|
|
280
296
|
const dayun = [];
|
|
297
|
+
const dayunWindows = [];
|
|
281
298
|
for (let i = 1; i <= 8; i++) {
|
|
282
299
|
const idx = (((monthIdx + (forward ? i : -i)) % 60) + 60) % 60;
|
|
283
300
|
const g = ganzhiName(idx);
|
|
301
|
+
const fromJd = partsToJd(addYearsClamped(jiaoParts, (i - 1) * 10));
|
|
302
|
+
const toJd = partsToJd(addYearsClamped(jiaoParts, i * 10));
|
|
284
303
|
dayun.push({
|
|
285
304
|
step: i,
|
|
286
305
|
startAge: startAgeYears + (i - 1) * 10,
|
|
@@ -289,7 +308,11 @@ export function buildBazi(input) {
|
|
|
289
308
|
branch: g.branch,
|
|
290
309
|
stemTenGod: tenGod(dayStem, g.stem),
|
|
291
310
|
nayin: nayin(idx),
|
|
311
|
+
// 这一步大运的起止交运时刻(与摘要/面板同源,可直接拿来对年表)
|
|
312
|
+
fromDate: formatJd(fromJd),
|
|
313
|
+
toDate: formatJd(toJd),
|
|
292
314
|
});
|
|
315
|
+
dayunWindows.push({ step: i, ganzhi: g.name, fromJd, toJd });
|
|
293
316
|
}
|
|
294
317
|
|
|
295
318
|
// 流年(默认从「今年」起排 10 年;传 input.nowYear 可钉死基准年,用于复现历史结论)
|
|
@@ -442,6 +465,48 @@ export function buildBazi(input) {
|
|
|
442
465
|
l.luck = scoreLuck(l.ganzhi, frame);
|
|
443
466
|
}
|
|
444
467
|
|
|
468
|
+
// ── 岁运并临 / 伏吟反吟:只标干支层面的「变动信号」,不判吉凶 ──
|
|
469
|
+
// 流年按立春起算(该年立春到次年立春),当值大运取与这一区间相交的步;
|
|
470
|
+
// 交运落在这一年里时,前后两步都在本年当过值,两条都列出。
|
|
471
|
+
const NATAL_LABEL = { year: '年柱', month: '月柱', day: '日柱', hour: '时柱' };
|
|
472
|
+
const stemOvercomes = (a, b) => OVERCOMES[STEM_ELEMENT[a]] === STEM_ELEMENT[b];
|
|
473
|
+
const tianKeDiChong = (a, b) => {
|
|
474
|
+
if (typeof a !== 'string' || typeof b !== 'string' || a.length < 2 || b.length < 2) return false;
|
|
475
|
+
if (!(a[0] in STEM_ELEMENT) || !(b[0] in STEM_ELEMENT)) return false;
|
|
476
|
+
return (stemOvercomes(a[0], b[0]) || stemOvercomes(b[0], a[0])) && hasPair(BRANCH_CHONG, a[1], b[1]);
|
|
477
|
+
};
|
|
478
|
+
const lichunJd = (y) => {
|
|
479
|
+
const t = termWindow(y, { jieOnly: true }).find((x) => x.index === 2 && jdToParts(x.jd).year === y);
|
|
480
|
+
return t ? t.jd : partsToJd({ year: y, month: 2, day: 4 });
|
|
481
|
+
};
|
|
482
|
+
for (const l of liunian) {
|
|
483
|
+
const yStart = lichunJd(l.year);
|
|
484
|
+
const yEnd = lichunJd(l.year + 1);
|
|
485
|
+
const active = dayunWindows.filter((w) => w.fromJd < yEnd && w.toJd > yStart);
|
|
486
|
+
const signals = [];
|
|
487
|
+
for (const w of active) {
|
|
488
|
+
if (w.ganzhi === l.ganzhi) {
|
|
489
|
+
signals.push({ type: '岁运并临', target: `第${w.step}步大运`, detail: `大运与流年同为${l.ganzhi}` });
|
|
490
|
+
} else if (tianKeDiChong(w.ganzhi, l.ganzhi)) {
|
|
491
|
+
signals.push({ type: '运年反吟', target: `第${w.step}步大运`, detail: `大运${w.ganzhi}与流年${l.ganzhi}天克地冲` });
|
|
492
|
+
}
|
|
493
|
+
}
|
|
494
|
+
for (const key of ['year', 'month', 'day', 'hour']) {
|
|
495
|
+
const g = pillars[key].ganzhi;
|
|
496
|
+
if (!g) continue;
|
|
497
|
+
if (l.ganzhi === g) {
|
|
498
|
+
signals.push({ type: '流年伏吟', target: NATAL_LABEL[key], detail: `流年${l.ganzhi}与${NATAL_LABEL[key]}同干支` });
|
|
499
|
+
} else if (tianKeDiChong(l.ganzhi, g)) {
|
|
500
|
+
signals.push({ type: '流年反吟', target: NATAL_LABEL[key], detail: `流年${l.ganzhi}与${NATAL_LABEL[key]}${g}天克地冲` });
|
|
501
|
+
}
|
|
502
|
+
}
|
|
503
|
+
l.suiyun = {
|
|
504
|
+
dayun: active.map((w) => ({ step: w.step, ganzhi: w.ganzhi })),
|
|
505
|
+
signals,
|
|
506
|
+
note: '只标干支重复与天克地冲这类变动信号,不判吉凶;大运按该年立春到次年立春的区间取,交运落在年内时前后两步并列',
|
|
507
|
+
};
|
|
508
|
+
}
|
|
509
|
+
|
|
445
510
|
const p = jdToParts(jd);
|
|
446
511
|
|
|
447
512
|
// ── 胎元 / 命宫 / 身宫 ──
|
|
@@ -503,10 +568,22 @@ export function buildBazi(input) {
|
|
|
503
568
|
rule: `${isYangYear ? '阳' : '阴'}年${gender === 'male' ? '男' : '女'}${forward ? '顺排' : '逆排'}`,
|
|
504
569
|
startAge: { years: startAgeYears, months: startAgeMonths },
|
|
505
570
|
toNextJieDays: Math.round(spanDays * 100) / 100,
|
|
571
|
+
// 交运时刻(日/时辰级):上方 startAge 是四舍五入到月的旧字段,两者同源、不互相覆盖
|
|
572
|
+
jiao: {
|
|
573
|
+
at: formatJd(jiaoJd),
|
|
574
|
+
jd: Math.round(jiaoJd * 1e6) / 1e6,
|
|
575
|
+
scaleDaysPerDay: JIAO_SCALE,
|
|
576
|
+
yearDays: JIAO_YEAR_DAYS,
|
|
577
|
+
spanDays: Math.round(spanDays * 1e4) / 1e4,
|
|
578
|
+
from: { name: jiaoFromTerm.name, time: formatJd(jiaoFromTerm.jd) },
|
|
579
|
+
frame: solar.offsetMinutes ? '真太阳时' : '平太阳时',
|
|
580
|
+
offsetMinutes: solar.offsetMinutes,
|
|
581
|
+
note: '三日折一年:出生到节令的真实间隔按 365.2422/3 放大后加到出生时刻;同一比例即「一日折四月、一时辰折十日」,每步大运在同月同日同时刻换',
|
|
582
|
+
},
|
|
506
583
|
list: dayun,
|
|
507
584
|
},
|
|
508
585
|
strength,
|
|
509
|
-
frame,
|
|
586
|
+
frame,
|
|
510
587
|
climate: frame.yongshen.climate || frame.yongshen.tiaohou || null,
|
|
511
588
|
liunian,
|
|
512
589
|
liunianFrom: thisYear,
|
|
@@ -0,0 +1,380 @@
|
|
|
1
|
+
// 古籍原文库:《子平真诠》《滴天髓》《三命通会》里与「格局取用」「十神喜忌」「寒暖燥湿」直接相关的条目。
|
|
2
|
+
// 原文照录(公共版权:清·沈孝瞻《子平真诠》、明·京图《滴天髓》、明·万民英《三命通会》通行本),仅供文化研究与参考。
|
|
3
|
+
// 出处以中华典藏网在线本为准(逐条给 url),异文处不合并、不改写;plain 是本站自撰白话,不是原文。
|
|
4
|
+
|
|
5
|
+
export const CLASSIC_BOOKS = {
|
|
6
|
+
ziping: { name: '子平真诠', author: '清·沈孝瞻', base: 'https://www.diancang.xyz/xuanxuewushu/zipingzhenquan/' },
|
|
7
|
+
ditian: { name: '滴天髓', author: '明·京图(通行本)', base: 'https://www.diancang.xyz/xuanxuewushu/ditiansui/' },
|
|
8
|
+
sanming: { name: '三命通会', author: '明·万民英', base: 'https://www.diancang.xyz/xuanxuewushu/sanmingtonghui/' },
|
|
9
|
+
};
|
|
10
|
+
|
|
11
|
+
export const CLASSICS = [
|
|
12
|
+
{
|
|
13
|
+
id: 'zp-yongshen',
|
|
14
|
+
book: 'ziping',
|
|
15
|
+
chapter: '八、论用神',
|
|
16
|
+
scene: '用神',
|
|
17
|
+
tags: [],
|
|
18
|
+
quote: '八字用神,专求月令,以日干配月令地支,而生克不同,格局分焉。财官印食,此用神之善而顺用之者也;煞伤劫刃,用神之不善而逆用之者也。',
|
|
19
|
+
plain: '用神从月令里找:财、官、印、食四吉神顺用(生之护之),煞、伤、劫、刃四凶神逆用(制之化之)。',
|
|
20
|
+
url: 'https://www.diancang.xyz/xuanxuewushu/zipingzhenquan/53628.html',
|
|
21
|
+
},
|
|
22
|
+
{
|
|
23
|
+
id: 'zp-zhenguan',
|
|
24
|
+
book: 'ziping',
|
|
25
|
+
chapter: '三十一、论正官',
|
|
26
|
+
scene: '格局',
|
|
27
|
+
tags: ['正官'],
|
|
28
|
+
quote: '以刑冲破害为忌,则以生之护之为喜矣。存其喜而去其忌则贵,而贵之中又有高低者,何也?',
|
|
29
|
+
plain: '正官格最忌刑冲破害,喜财生官、印护官;去忌存喜才谈得上贵,贵的层次还要看财印是否并透、有无伤官七煞混杂。',
|
|
30
|
+
url: 'https://www.diancang.xyz/xuanxuewushu/zipingzhenquan/53651.html',
|
|
31
|
+
},
|
|
32
|
+
{
|
|
33
|
+
id: 'zp-cai',
|
|
34
|
+
book: 'ziping',
|
|
35
|
+
chapter: '三十三、论财',
|
|
36
|
+
scene: '格局',
|
|
37
|
+
tags: ['财'],
|
|
38
|
+
quote: '财为我克,使用之物也,以能生官,所以为美。为财帛,为妻妾,为才能,为驿马,皆财类也。',
|
|
39
|
+
plain: '财是我所克、能为我用之物,因能生官而美;它同时代表钱财、配偶、才能、走动,不只「钱」一项。',
|
|
40
|
+
url: 'https://www.diancang.xyz/xuanxuewushu/zipingzhenquan/53653.html',
|
|
41
|
+
},
|
|
42
|
+
{
|
|
43
|
+
id: 'zp-yin',
|
|
44
|
+
book: 'ziping',
|
|
45
|
+
chapter: '三十五、论印绶',
|
|
46
|
+
scene: '格局',
|
|
47
|
+
tags: ['印'],
|
|
48
|
+
quote: '印绶喜其生身,正偏同为美格,故财与印不分偏正,同为一格而论之。',
|
|
49
|
+
plain: '印能生身,正印偏印都算美格,不分偏正而论;印格的关键在身印强弱与官杀、食伤、财的配合。',
|
|
50
|
+
url: 'https://www.diancang.xyz/xuanxuewushu/zipingzhenquan/53655.html',
|
|
51
|
+
},
|
|
52
|
+
{
|
|
53
|
+
id: 'zp-shishen',
|
|
54
|
+
book: 'ziping',
|
|
55
|
+
chapter: '三十七、论食神',
|
|
56
|
+
scene: '格局',
|
|
57
|
+
tags: ['食神'],
|
|
58
|
+
quote: '食神本属泄气,以其能生正财,所以喜之。故食神生财,美格也。财要有根,不必偏正叠出,如身强食旺而财透,大贵之格。',
|
|
59
|
+
plain: '食神本是泄气,可贵在能生财;食神生财要财有根,身强、食旺、财透三者齐,格局才大。',
|
|
60
|
+
url: 'https://www.diancang.xyz/xuanxuewushu/zipingzhenquan/53657.html',
|
|
61
|
+
},
|
|
62
|
+
{
|
|
63
|
+
id: 'zp-pianguan',
|
|
64
|
+
book: 'ziping',
|
|
65
|
+
chapter: '三十九、论偏官',
|
|
66
|
+
scene: '格局',
|
|
67
|
+
tags: ['七杀', '偏官'],
|
|
68
|
+
quote: '煞以攻身,似非美物,百大贵之格,多存七煞。盖控制得宜,煞为我用,如大英雄大豪杰,似难驾驭,而处之有方,则惊天动地之功,忽焉而就。',
|
|
69
|
+
plain: '七煞攻身,看着不美,但大贵之格多有七煞——能控制住就为我所用,像驾驭豪杰,处之有方就能成大事。',
|
|
70
|
+
url: 'https://www.diancang.xyz/xuanxuewushu/zipingzhenquan/53659.html',
|
|
71
|
+
},
|
|
72
|
+
{
|
|
73
|
+
id: 'zp-shangguan',
|
|
74
|
+
book: 'ziping',
|
|
75
|
+
chapter: '四十一、论伤官',
|
|
76
|
+
scene: '格局',
|
|
77
|
+
tags: ['伤官'],
|
|
78
|
+
quote: '伤官虽非吉神,实为秀气,故文人学士,多于伤官格内得之。而夏木见水,冬金见火,则又为秀之尤秀者也。',
|
|
79
|
+
plain: '伤官不是吉神,却是秀气所在,文人多出伤官格;夏木得水、冬金得火,是秀气里更秀的两种。',
|
|
80
|
+
url: 'https://www.diancang.xyz/xuanxuewushu/zipingzhenquan/53661.html',
|
|
81
|
+
},
|
|
82
|
+
{
|
|
83
|
+
id: 'zp-yangren',
|
|
84
|
+
book: 'ziping',
|
|
85
|
+
chapter: '四十三、论阳刃',
|
|
86
|
+
scene: '格局',
|
|
87
|
+
tags: ['劫财', '阳刃'],
|
|
88
|
+
quote: '阳刃者,劫我正财之神,乃正财之七煞也。禄前一位,惟五阳有之,故为阳刃。不曰劫而曰刃,劫之甚也。刃宜伏制,官煞皆宜,财印相随,尤为贵显。',
|
|
89
|
+
plain: '阳刃是劫财之极(只有五阳干有),宜用官煞制伏;财印相随而不相碍,格局更显。',
|
|
90
|
+
url: 'https://www.diancang.xyz/xuanxuewushu/zipingzhenquan/53663.html',
|
|
91
|
+
},
|
|
92
|
+
{
|
|
93
|
+
id: 'zp-lujie',
|
|
94
|
+
book: 'ziping',
|
|
95
|
+
chapter: '四十五、论建禄月劫',
|
|
96
|
+
scene: '格局',
|
|
97
|
+
tags: ['比肩', '建禄', '月劫'],
|
|
98
|
+
quote: '故建禄与月劫,可同一格,不必加分,皆以透干支,别取财官煞食为用。',
|
|
99
|
+
plain: '建禄、月劫同看一格,月令本身不算用神,要另看透出的财官煞食取用。',
|
|
100
|
+
url: 'https://www.diancang.xyz/xuanxuewushu/zipingzhenquan/53665.html',
|
|
101
|
+
},
|
|
102
|
+
{
|
|
103
|
+
id: 'zp-qihou',
|
|
104
|
+
book: 'ziping',
|
|
105
|
+
chapter: '十四、论用神配气候得失',
|
|
106
|
+
scene: '调候',
|
|
107
|
+
tags: [],
|
|
108
|
+
quote: '论命惟以月令用神为主,然亦须配气候而互参之。譬如英雄豪杰,生得其时,自然事半功倍;遭时不顺,虽有奇才,成功不易。',
|
|
109
|
+
plain: '月令用神为主,但必须配气候参看;同样的格局,生在得时的气候里事半功倍,逆着气候就费劲。',
|
|
110
|
+
url: 'https://www.diancang.xyz/xuanxuewushu/zipingzhenquan/53634.html',
|
|
111
|
+
},
|
|
112
|
+
{
|
|
113
|
+
id: 'zp-chengbai',
|
|
114
|
+
book: 'ziping',
|
|
115
|
+
chapter: '九、论用神成败救应',
|
|
116
|
+
scene: '格局',
|
|
117
|
+
tags: [],
|
|
118
|
+
quote: '成中有败,必是带忌;败中有成,全凭救应。',
|
|
119
|
+
plain: '成格不等于一路顺:成中带忌(官逢财又逢伤、官被合之类)就打了折;败格也未必无救——印来解伤、合来清煞,败中还能转成。',
|
|
120
|
+
url: 'https://www.diancang.xyz/xuanxuewushu/zipingzhenquan/53629.html',
|
|
121
|
+
},
|
|
122
|
+
{
|
|
123
|
+
id: 'zp-bianhua',
|
|
124
|
+
book: 'ziping',
|
|
125
|
+
chapter: '十、论用神变化',
|
|
126
|
+
scene: '格局',
|
|
127
|
+
tags: [],
|
|
128
|
+
quote: '故若丁生亥月,本为正官,支全卯未,则化为印。己生申月,本属伤官。藏庚透壬,则化为财。凡此之类皆用神之变化也。',
|
|
129
|
+
plain: '用神本从月令取,但月令藏干不一:丁生亥月本为正官,支会卯未就化为印;己生申月本属伤官,庚藏壬透就化为财。起点相同,合化一变,取用也跟着变(原文只说变化之由,不断定某盘必化)。',
|
|
130
|
+
url: 'https://www.diancang.xyz/xuanxuewushu/zipingzhenquan/53630.html',
|
|
131
|
+
},
|
|
132
|
+
{
|
|
133
|
+
id: 'dt-hannuan',
|
|
134
|
+
book: 'ditian',
|
|
135
|
+
chapter: '通神论·寒暖',
|
|
136
|
+
scene: '调候',
|
|
137
|
+
tags: [],
|
|
138
|
+
quote: '天道有寒暖,生育万物,人道行之,不可过也。',
|
|
139
|
+
plain: '天有寒暖才能生养万物,人命里寒暖也不能过——过寒过热都要调。',
|
|
140
|
+
url: 'https://www.diancang.xyz/xuanxuewushu/ditiansui/153091.html',
|
|
141
|
+
},
|
|
142
|
+
{
|
|
143
|
+
id: 'dt-zaoshi',
|
|
144
|
+
book: 'ditian',
|
|
145
|
+
chapter: '通神论·燥湿',
|
|
146
|
+
scene: '调候',
|
|
147
|
+
tags: [],
|
|
148
|
+
quote: '地道有燥湿,生成品汇,人道得之,不可偏也。',
|
|
149
|
+
plain: '地有燥湿才有品类生成,人命得燥湿之气也不能偏。',
|
|
150
|
+
url: 'https://www.diancang.xyz/xuanxuewushu/ditiansui/153091.html',
|
|
151
|
+
},
|
|
152
|
+
{
|
|
153
|
+
id: 'dt-shuaiwang',
|
|
154
|
+
book: 'ditian',
|
|
155
|
+
chapter: '通神论·衰旺',
|
|
156
|
+
scene: '调候',
|
|
157
|
+
tags: [],
|
|
158
|
+
quote: '能知旺衰之真机,其于三命之奥,思过半矣。',
|
|
159
|
+
plain: '真正看懂旺衰的机关,命理之奥就过了一半——旺衰不是数个数,要看真机。',
|
|
160
|
+
url: 'https://www.diancang.xyz/xuanxuewushu/ditiansui/153091.html',
|
|
161
|
+
},
|
|
162
|
+
{
|
|
163
|
+
id: 'dt-zhonghe',
|
|
164
|
+
book: 'ditian',
|
|
165
|
+
chapter: '通神论·中和',
|
|
166
|
+
scene: '调候',
|
|
167
|
+
tags: [],
|
|
168
|
+
quote: '既识中和之正理,而于五行之妙,有全能焉。',
|
|
169
|
+
plain: '懂得中和的道理,五行的妙处就都在其中了。',
|
|
170
|
+
url: 'https://www.diancang.xyz/xuanxuewushu/ditiansui/153091.html',
|
|
171
|
+
},
|
|
172
|
+
{
|
|
173
|
+
id: 'dt-guansha',
|
|
174
|
+
book: 'ditian',
|
|
175
|
+
chapter: '通神论·官杀',
|
|
176
|
+
scene: '十神',
|
|
177
|
+
tags: ['正官', '七杀'],
|
|
178
|
+
quote: '官杀混杂来问我,有可有不可。',
|
|
179
|
+
plain: '官杀混杂不是一律不好,要看能不能去留取清。',
|
|
180
|
+
url: 'https://www.diancang.xyz/xuanxuewushu/ditiansui/153091.html',
|
|
181
|
+
},
|
|
182
|
+
{
|
|
183
|
+
id: 'dt-shangguan',
|
|
184
|
+
book: 'ditian',
|
|
185
|
+
chapter: '通神论·伤官',
|
|
186
|
+
scene: '十神',
|
|
187
|
+
tags: ['伤官'],
|
|
188
|
+
quote: '伤官见官最难辨,可见不可见。',
|
|
189
|
+
plain: '伤官见官是最难分辨的一条:有的能见,有的不能见,不能一句「伤官见官为祸百端」了事。',
|
|
190
|
+
url: 'https://www.diancang.xyz/xuanxuewushu/ditiansui/153091.html',
|
|
191
|
+
},
|
|
192
|
+
{
|
|
193
|
+
id: 'dt-yueling',
|
|
194
|
+
book: 'ditian',
|
|
195
|
+
chapter: '通神论·月令',
|
|
196
|
+
scene: '用神',
|
|
197
|
+
tags: [],
|
|
198
|
+
quote: '月令乃提纲之府,譬之宅也,人元为用事之神,宅之定向也,不可以不卜。',
|
|
199
|
+
plain: '月令像宅子,藏干是用事之神,像宅子的朝向,必须细看。',
|
|
200
|
+
url: 'https://www.diancang.xyz/xuanxuewushu/ditiansui/153091.html',
|
|
201
|
+
},
|
|
202
|
+
{
|
|
203
|
+
id: 'dt-tiyong',
|
|
204
|
+
book: 'ditian',
|
|
205
|
+
chapter: '通神论·体用',
|
|
206
|
+
scene: '用神',
|
|
207
|
+
tags: [],
|
|
208
|
+
quote: '道有体用,不可以一端论也,要在扶之抑之得其宜。',
|
|
209
|
+
plain: '体用不能只看一头,关键是扶抑得宜。',
|
|
210
|
+
url: 'https://www.diancang.xyz/xuanxuewushu/ditiansui/153091.html',
|
|
211
|
+
},
|
|
212
|
+
{
|
|
213
|
+
id: 'dt-jingshen',
|
|
214
|
+
book: 'ditian',
|
|
215
|
+
chapter: '通神论·精神',
|
|
216
|
+
scene: '用神',
|
|
217
|
+
tags: [],
|
|
218
|
+
quote: '人有精神,不可以一偏求也,要在损之益之得其中。',
|
|
219
|
+
plain: '看精神不能偏执一端,要在损益之间求其中。',
|
|
220
|
+
url: 'https://www.diancang.xyz/xuanxuewushu/ditiansui/153091.html',
|
|
221
|
+
},
|
|
222
|
+
// —— 三命通会(明·万民英):同一组十神,子平真诠说「怎么用」,三命通会说「怎么取、怕什么」。
|
|
223
|
+
// 两书并列取用,按同一 tag 各取一条对照读,不合并、不裁定谁对。
|
|
224
|
+
{
|
|
225
|
+
id: 'smt-zhenguan',
|
|
226
|
+
book: 'sanming',
|
|
227
|
+
chapter: '卷五·论正官',
|
|
228
|
+
scene: '格局',
|
|
229
|
+
tags: ['正官'],
|
|
230
|
+
quote: '正官者,乃甲见辛、乙见庚之例。阴阳配合,相制有用,成其道也。故正官为六格之首,止许一位,多则不宜。',
|
|
231
|
+
plain: '正官取「克我而阴阳相配」,有制而能成用;六格以正官居首,只宜一位,多见就杂。',
|
|
232
|
+
url: 'https://www.diancang.xyz/xuanxuewushu/sanmingtonghui/7582.html',
|
|
233
|
+
},
|
|
234
|
+
{
|
|
235
|
+
id: 'smt-zhengcai',
|
|
236
|
+
book: 'sanming',
|
|
237
|
+
chapter: '卷六·论正财',
|
|
238
|
+
scene: '格局',
|
|
239
|
+
tags: ['财'],
|
|
240
|
+
quote: '正财者,乃甲见己、乙见戊之例。受我克制,为我之妻,譬人娶妻,妻赍财嫁我,我必精神康强,而后可享用,若衰微不振,虽妻财丰厚,但能目视,终不得用。',
|
|
241
|
+
plain: '正财是我克制之物,古人以「娶妻带财」作比:自身精神康强才受用得起,身弱不振,财再厚也只是看着。',
|
|
242
|
+
url: 'https://www.diancang.xyz/xuanxuewushu/sanmingtonghui/7645.html',
|
|
243
|
+
},
|
|
244
|
+
{
|
|
245
|
+
id: 'smt-yinshou',
|
|
246
|
+
book: 'sanming',
|
|
247
|
+
chapter: '卷六·论印绶',
|
|
248
|
+
scene: '格局',
|
|
249
|
+
tags: ['印'],
|
|
250
|
+
quote: '印绶者,乃五行生我之名。如甲乙在亥子月,丙丁在寅卯月之类,乃我气之源,为生气,为父母,能护我官星,使无伤克',
|
|
251
|
+
plain: '印是生我之气,像源头与父母:它能护住官星,使官不受伤克;反过来说,印重就怕财来破。',
|
|
252
|
+
url: 'https://www.diancang.xyz/xuanxuewushu/sanmingtonghui/7655.html',
|
|
253
|
+
},
|
|
254
|
+
{
|
|
255
|
+
id: 'smt-shishen',
|
|
256
|
+
book: 'sanming',
|
|
257
|
+
chapter: '卷六·论食神',
|
|
258
|
+
scene: '格局',
|
|
259
|
+
tags: ['食神'],
|
|
260
|
+
quote: '凡命遇财煞之地,食神旺相,煞被食制,不敢为祸,财被食生,充裕不竭,故食神一名寿星,一名爵星,良有以也。',
|
|
261
|
+
plain: '食神旺,一头制煞、一头生财:煞被制住不敢为祸,财被生起不至枯竭;所以食神又叫寿星、爵星。',
|
|
262
|
+
url: 'https://www.diancang.xyz/xuanxuewushu/sanmingtonghui/7663.html',
|
|
263
|
+
},
|
|
264
|
+
{
|
|
265
|
+
id: 'smt-shangguan',
|
|
266
|
+
book: 'sanming',
|
|
267
|
+
chapter: '卷六·论伤官',
|
|
268
|
+
scene: '格局',
|
|
269
|
+
tags: ['伤官'],
|
|
270
|
+
quote: '伤官虽凶,乃我所生,自家之物,伤尽则能生财,财旺则能生官,造化展转有情。',
|
|
271
|
+
plain: '伤官虽称凶,却是我自己生出来的:伤尽(柱中不见官星)反能生财,财旺再生官,辗转还是有情。',
|
|
272
|
+
url: 'https://www.diancang.xyz/xuanxuewushu/sanmingtonghui/7662.html',
|
|
273
|
+
},
|
|
274
|
+
{
|
|
275
|
+
id: 'smt-yangren',
|
|
276
|
+
book: 'sanming',
|
|
277
|
+
chapter: '卷六·论阳刃',
|
|
278
|
+
scene: '格局',
|
|
279
|
+
tags: ['阳刃', '劫财'],
|
|
280
|
+
quote: '阳者,阴阳之阳,刃者,刀刃之刃,即禄前一位,言旺越其分,故险。',
|
|
281
|
+
plain: '阳刃指禄前一位,旺过了本分,所以险;甲丙戊庚壬五阳干才有刃,阴干见伤官同论。',
|
|
282
|
+
url: 'https://www.diancang.xyz/xuanxuewushu/sanmingtonghui/7671.html',
|
|
283
|
+
},
|
|
284
|
+
{
|
|
285
|
+
id: 'smt-jianlu',
|
|
286
|
+
book: 'sanming',
|
|
287
|
+
chapter: '卷六·论建禄',
|
|
288
|
+
scene: '格局',
|
|
289
|
+
tags: ['建禄', '比肩', '月劫'],
|
|
290
|
+
quote: '凡命月令建禄,难招祖业,必主平生见财不聚,却病少寿长,行运再见比肩,克妻妨父损子',
|
|
291
|
+
plain: '月令建禄是日主临官之地,身旺而财官难取:古说难承祖业、见财不聚,但病少寿长;再走比肩运,古书说克妻妨父损子(属于旧说的重话,本插件只记原文、不作断语)。',
|
|
292
|
+
url: 'https://www.diancang.xyz/xuanxuewushu/sanmingtonghui/7672.html',
|
|
293
|
+
},
|
|
294
|
+
];
|
|
295
|
+
|
|
296
|
+
const BY_ID = CLASSICS.reduce((m, e) => { m[e.id] = e; return m; }, {});
|
|
297
|
+
|
|
298
|
+
// 格局名 → tags 键(本引擎的格局名都带「格」)
|
|
299
|
+
const GEJU_KEY = {
|
|
300
|
+
正官格: '正官',
|
|
301
|
+
七杀格: '七杀',
|
|
302
|
+
偏官格: '偏官',
|
|
303
|
+
正财格: '财',
|
|
304
|
+
偏财格: '财',
|
|
305
|
+
正印格: '印',
|
|
306
|
+
偏印格: '印',
|
|
307
|
+
食神格: '食神',
|
|
308
|
+
伤官格: '伤官',
|
|
309
|
+
阳刃格: '阳刃',
|
|
310
|
+
月劫格: '月劫',
|
|
311
|
+
建禄格: '建禄',
|
|
312
|
+
};
|
|
313
|
+
|
|
314
|
+
export function classicOf(id) {
|
|
315
|
+
return BY_ID[id] || null;
|
|
316
|
+
}
|
|
317
|
+
|
|
318
|
+
function tagOf(gejuName) {
|
|
319
|
+
const name = String(gejuName || '');
|
|
320
|
+
if (GEJU_KEY[name]) return GEJU_KEY[name];
|
|
321
|
+
const bare = name.replace(/格$/, '');
|
|
322
|
+
return GEJU_KEY[bare + '格'] || bare;
|
|
323
|
+
}
|
|
324
|
+
|
|
325
|
+
// 同一 tag 各书取一条:子平真诠在前(讲怎么用),三命通会紧随作对照(讲怎么取、怕什么)
|
|
326
|
+
function pick(tag, book) {
|
|
327
|
+
return CLASSICS.find((e) => e.scene === '格局' && e.tags.includes(tag) && (!book || e.book === book)) || null;
|
|
328
|
+
}
|
|
329
|
+
|
|
330
|
+
// 章节名去掉卷次/序号与开头的「论」,避免 why 里拼成「论论财」
|
|
331
|
+
function chapterTitle(e) {
|
|
332
|
+
return e.chapter.replace(/^.*[、·]/, '').replace(/^论/, '');
|
|
333
|
+
}
|
|
334
|
+
|
|
335
|
+
// 根据一张八字结果挑原文:先格局(子平真诠 + 三命通会对照),再调候(寒暖/燥湿),
|
|
336
|
+
// 最后「用神总纲」一位按盘取:有化气格取论用神变化、见组合取论用神成败救应、其余取通用总纲;去重、限量。
|
|
337
|
+
export function classicsFor(r, limit = 5) {
|
|
338
|
+
if (!r) return [];
|
|
339
|
+
const out = [];
|
|
340
|
+
const seen = new Set();
|
|
341
|
+
const push = (entry, why) => {
|
|
342
|
+
if (!entry || seen.has(entry.id) || out.length >= limit) return;
|
|
343
|
+
seen.add(entry.id);
|
|
344
|
+
out.push({ ...entry, why });
|
|
345
|
+
};
|
|
346
|
+
const gejuList = Array.isArray(r.geju) ? r.geju : (r.frame && Array.isArray(r.frame.geju) ? r.frame.geju : []);
|
|
347
|
+
for (const g of gejuList) {
|
|
348
|
+
if (!g || (g.kind && g.kind !== '月令格')) continue;
|
|
349
|
+
const tag = tagOf(g.name);
|
|
350
|
+
const primary = pick(tag, 'ziping') || pick(tag);
|
|
351
|
+
if (primary) push(primary, `你的月令格局是「${g.name}」,故取${CLASSIC_BOOKS[primary.book].name}「${chapterTitle(primary)}」一条`);
|
|
352
|
+
const alt = CLASSICS.find((e) => e.scene === '格局' && e.tags.includes(tag) && (!primary || e.book !== primary.book));
|
|
353
|
+
if (alt) push(alt, `同是「${g.name}」,${CLASSIC_BOOKS[alt.book].name}「${chapterTitle(alt)}」另有取法,可对照读`);
|
|
354
|
+
}
|
|
355
|
+
const cli = r.climate || (r.frame && r.frame.yongshen && (r.frame.yongshen.climate || r.frame.yongshen.tiaohou));
|
|
356
|
+
if (cli && cli.kind && cli.kind !== '平和') {
|
|
357
|
+
const cold = !!(cli.cold || cli.kind.indexOf('寒') >= 0);
|
|
358
|
+
const hot = !!(cli.hot || cli.kind.indexOf('热') >= 0);
|
|
359
|
+
push(classicOf(cold ? 'dt-hannuan' : 'dt-zaoshi'), `本盘气候判为「${cli.kind}」,故取${CLASSIC_BOOKS.ditian.name}寒暖燥湿一条`);
|
|
360
|
+
push(classicOf('zp-qihou'), '气候与月令用神要互参,故取子平真诠「用神配气候」一条');
|
|
361
|
+
if (hot) push(classicOf('dt-hannuan'), '本盘偏热,寒暖一条正对');
|
|
362
|
+
}
|
|
363
|
+
// 用神总纲位只放一条:同一个格,化气看「变化」、有组合看「成败救应」,都没有才回到四吉四凶总纲。
|
|
364
|
+
// 不另加位次,是因为格局两条 + 气候两条正好占满 5 条上限;总纲与具体结构二选一,避免泛论挤掉针对这张盘的话。
|
|
365
|
+
const huagi = gejuList.find((g) => g && g.kind === '化气格');
|
|
366
|
+
const combo = gejuList.find((g) => g && g.kind === '组合');
|
|
367
|
+
if (huagi) {
|
|
368
|
+
push(classicOf('zp-bianhua'), `本盘列有「${huagi.name}」:用神由月令合化而变,总纲一位改取${CLASSIC_BOOKS.ziping.name}论用神变化`);
|
|
369
|
+
} else if (combo) {
|
|
370
|
+
push(classicOf('zp-chengbai'), `本盘另有「${combo.name}」组合:成格还要看带忌与救应,总纲一位改取${CLASSIC_BOOKS.ziping.name}论用神成败救应`);
|
|
371
|
+
} else {
|
|
372
|
+
push(classicOf('zp-yongshen'), '用神从月令取、四吉顺用四凶逆用,是通用总纲');
|
|
373
|
+
}
|
|
374
|
+
return out;
|
|
375
|
+
}
|
|
376
|
+
|
|
377
|
+
export function classicsText(rows) {
|
|
378
|
+
if (!rows || !rows.length) return '';
|
|
379
|
+
return rows.map((e) => `《${CLASSIC_BOOKS[e.book].name}·${e.chapter}》「${e.quote}」`).join('\n');
|
|
380
|
+
}
|
package/engine/followup.js
CHANGED
|
@@ -170,4 +170,62 @@ export function followup(r, question) {
|
|
|
170
170
|
return { question: q, ...result };
|
|
171
171
|
}
|
|
172
172
|
|
|
173
|
+
/** 体系显示名:追问提示里用,避免把 bazi 这类内部键直接给用户看。 */
|
|
174
|
+
const SYSTEM_LABEL = {
|
|
175
|
+
bazi: '八字(四柱)',
|
|
176
|
+
ziwei: '紫微斗数',
|
|
177
|
+
liuyao: '六爻',
|
|
178
|
+
meihua: '梅花易数',
|
|
179
|
+
daliuren: '大六壬',
|
|
180
|
+
qimen: '奇门遁甲',
|
|
181
|
+
tarot: '塔罗',
|
|
182
|
+
hepan: '合盘',
|
|
183
|
+
chenggu: '称骨',
|
|
184
|
+
almanac: '黄历',
|
|
185
|
+
zeri: '择日',
|
|
186
|
+
star: '星座',
|
|
187
|
+
numerology: '生命数字',
|
|
188
|
+
mbti: '十六型人格',
|
|
189
|
+
trend: '人生 K 线',
|
|
190
|
+
fengshui: '风水',
|
|
191
|
+
name: '起名',
|
|
192
|
+
convert: '公农历互转',
|
|
193
|
+
};
|
|
194
|
+
|
|
195
|
+
/**
|
|
196
|
+
* 把「就这一盘继续问」整理成一段可以发到对话窗口的提问。
|
|
197
|
+
*
|
|
198
|
+
* 这里只做文本组装,不调用模型、不改盘:面板里点「问进对话」时,
|
|
199
|
+
* 客户端把这段文字写进对话输入框并提交,由对话里的模型基于盘面回答。
|
|
200
|
+
*
|
|
201
|
+
* @param {object} r compute 的结果(至少要带 system 与 summary)
|
|
202
|
+
* @param {{question?:string, maxChars?:number}} [opts]
|
|
203
|
+
* @returns {{text:string, question:string, system:string, label:string, chars:number, truncated:boolean}}
|
|
204
|
+
*/
|
|
205
|
+
export function askPrompt(r, opts = {}) {
|
|
206
|
+
const label = SYSTEM_LABEL[r && r.system] || (r && r.system) || '未知体系';
|
|
207
|
+
const asked = String((opts && opts.question) || '').trim();
|
|
208
|
+
const question = asked || '请先总览这张盘,指出最值得注意的一两处,并说明各自的依据。';
|
|
209
|
+
const limit = Number.isFinite(opts && opts.maxChars) && opts.maxChars >= 400 ? opts.maxChars : 3000;
|
|
210
|
+
const raw = String((r && r.summary) || '').trim();
|
|
211
|
+
const truncated = raw.length > limit;
|
|
212
|
+
const summary = truncated ? `${raw.slice(0, limit)}…(摘要已截断)` : raw;
|
|
213
|
+
|
|
214
|
+
const lines = [
|
|
215
|
+
'【命理追问】下面这张盘是命理插件刚排好的,请就着它回答我的问题;不用重新排盘,盘面字段已经够用。',
|
|
216
|
+
`体系:${label}`,
|
|
217
|
+
`所问:${question}`,
|
|
218
|
+
'',
|
|
219
|
+
'——盘面摘要——',
|
|
220
|
+
summary || '(这张盘没有摘要字段,请先让我重新排一次。)',
|
|
221
|
+
'',
|
|
222
|
+
'——回答要求——',
|
|
223
|
+
'1) 尽量引用到具体的柱、宫或爻,再说判断,别只给结论;',
|
|
224
|
+
'2) 盘面里没有依据的地方直接说「这盘里看不出来」,不要补外部假设;',
|
|
225
|
+
'3) 用概率和倾向的说法,别给绝对化的断言,也别把传统说法当成事实。',
|
|
226
|
+
];
|
|
227
|
+
const text = lines.join('\n');
|
|
228
|
+
return { text, question, system: (r && r.system) || '', label, chars: text.length, truncated };
|
|
229
|
+
}
|
|
230
|
+
|
|
173
231
|
export default followup;
|
package/engine/geo.js
CHANGED
|
@@ -143,7 +143,7 @@ const DETAIL = /(区|县|镇|乡|村|小区|街道|路|号|巷|弄|组|队)/;
|
|
|
143
143
|
|
|
144
144
|
/** OpenStreetMap Nominatim:免密钥、支持中文。失败返回 null。
|
|
145
145
|
* UA 按 OSM 使用政策要求写明应用与联系方式(改版本时同步这里)。 */
|
|
146
|
-
const USER_AGENT = 'dsh-metaphysics/0.
|
|
146
|
+
const USER_AGENT = 'dsh-metaphysics/0.23.0 (+https://github.com/xuanfu-web/dsh-metaphysics)';
|
|
147
147
|
|
|
148
148
|
async function onlineLookup(text, { timeoutMs = 2500 } = {}) {
|
|
149
149
|
if (typeof fetch !== 'function') return null;
|