@geekron/hono 0.1.0 → 0.1.1
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/dist/contract.d.ts +9 -1
- package/dist/contract.d.ts.map +1 -1
- package/dist/contract.js +14 -3
- package/dist/core/api/common.d.ts +2 -0
- package/dist/core/api/common.d.ts.map +1 -0
- package/dist/core/api/common.js +38 -0
- package/dist/core/api/inquiries.d.ts +2 -0
- package/dist/core/api/inquiries.d.ts.map +1 -0
- package/dist/core/api/inquiries.js +116 -0
- package/dist/core/api/inquiry.d.ts +2 -0
- package/dist/core/api/inquiry.d.ts.map +1 -0
- package/dist/core/api/inquiry.js +33 -0
- package/dist/core/api/visitor.d.ts +2 -0
- package/dist/core/api/visitor.d.ts.map +1 -0
- package/dist/core/api/visitor.js +152 -0
- package/dist/core/components/InquiryEmailTemplate.d.ts +30 -0
- package/dist/core/components/InquiryEmailTemplate.d.ts.map +1 -0
- package/dist/core/components/InquiryEmailTemplate.js +13 -0
- package/dist/core/components/Seo.d.ts +97 -0
- package/dist/core/components/Seo.d.ts.map +1 -0
- package/dist/core/components/Seo.js +365 -0
- package/dist/core/components/index.d.ts +3 -0
- package/dist/core/components/index.d.ts.map +1 -0
- package/dist/core/components/index.js +2 -0
- package/dist/core/index.d.ts +4 -0
- package/dist/core/index.d.ts.map +1 -0
- package/dist/core/index.js +3 -0
- package/dist/core/lib/constants/inquiry.d.ts +52 -0
- package/dist/core/lib/constants/inquiry.d.ts.map +1 -0
- package/dist/core/lib/constants/inquiry.js +51 -0
- package/dist/core/lib/constants/visitor.d.ts +29 -0
- package/dist/core/lib/constants/visitor.d.ts.map +1 -0
- package/dist/core/lib/constants/visitor.js +28 -0
- package/dist/core/lib/database/constants/database.d.ts +15 -0
- package/dist/core/lib/database/constants/database.d.ts.map +1 -0
- package/dist/core/lib/database/constants/database.js +14 -0
- package/dist/core/lib/database/database.service.d.ts +63 -0
- package/dist/core/lib/database/database.service.d.ts.map +1 -0
- package/dist/core/lib/database/database.service.js +108 -0
- package/dist/core/lib/database/index.d.ts +8 -0
- package/dist/core/lib/database/index.d.ts.map +1 -0
- package/dist/core/lib/database/index.js +7 -0
- package/dist/core/lib/database/managers/sqlite.d.ts +29 -0
- package/dist/core/lib/database/managers/sqlite.d.ts.map +1 -0
- package/dist/core/lib/database/managers/sqlite.js +55 -0
- package/dist/core/lib/database/managers/visitor-shard.d.ts +29 -0
- package/dist/core/lib/database/managers/visitor-shard.d.ts.map +1 -0
- package/dist/core/lib/database/managers/visitor-shard.js +83 -0
- package/dist/core/lib/database/repositories/inquiry.repository.d.ts +33 -0
- package/dist/core/lib/database/repositories/inquiry.repository.d.ts.map +1 -0
- package/dist/core/lib/database/repositories/inquiry.repository.js +173 -0
- package/dist/core/lib/database/repositories/visitor.repository.d.ts +51 -0
- package/dist/core/lib/database/repositories/visitor.repository.d.ts.map +1 -0
- package/dist/core/lib/database/repositories/visitor.repository.js +559 -0
- package/dist/core/lib/database/schemas/inquiry.schema.d.ts +323 -0
- package/dist/core/lib/database/schemas/inquiry.schema.d.ts.map +1 -0
- package/dist/core/lib/database/schemas/inquiry.schema.js +52 -0
- package/dist/core/lib/database/schemas/visitor.schema.d.ts +623 -0
- package/dist/core/lib/database/schemas/visitor.schema.d.ts.map +1 -0
- package/dist/core/lib/database/schemas/visitor.schema.js +162 -0
- package/dist/core/lib/services/captcha.service.d.ts +13 -0
- package/dist/core/lib/services/captcha.service.d.ts.map +1 -0
- package/dist/core/lib/services/captcha.service.js +40 -0
- package/dist/core/lib/services/geoip.service.d.ts +79 -0
- package/dist/core/lib/services/geoip.service.d.ts.map +1 -0
- package/dist/core/lib/services/geoip.service.js +144 -0
- package/dist/core/lib/services/index.d.ts +9 -0
- package/dist/core/lib/services/index.d.ts.map +1 -0
- package/dist/core/lib/services/index.js +8 -0
- package/dist/core/lib/services/inquiry.service.d.ts +56 -0
- package/dist/core/lib/services/inquiry.service.d.ts.map +1 -0
- package/dist/core/lib/services/inquiry.service.js +129 -0
- package/dist/core/lib/services/mailer.service.d.ts +23 -0
- package/dist/core/lib/services/mailer.service.d.ts.map +1 -0
- package/dist/core/lib/services/mailer.service.js +96 -0
- package/dist/core/lib/types/inquiry.d.ts +95 -0
- package/dist/core/lib/types/inquiry.d.ts.map +1 -0
- package/dist/core/lib/types/inquiry.js +1 -0
- package/dist/core/lib/types/visitor.d.ts +135 -0
- package/dist/core/lib/types/visitor.d.ts.map +1 -0
- package/dist/core/lib/types/visitor.js +1 -0
- package/dist/core/lib/utils/api.d.ts +25 -0
- package/dist/core/lib/utils/api.d.ts.map +1 -0
- package/dist/core/lib/utils/api.js +48 -0
- package/dist/core/lib/utils/request.d.ts +18 -0
- package/dist/core/lib/utils/request.d.ts.map +1 -0
- package/dist/core/lib/utils/request.js +25 -0
- package/dist/core/middlewares/api-guard.d.ts +39 -0
- package/dist/core/middlewares/api-guard.d.ts.map +1 -0
- package/dist/core/middlewares/api-guard.js +154 -0
- package/dist/core/middlewares/html-minifier.d.ts +55 -0
- package/dist/core/middlewares/html-minifier.d.ts.map +1 -0
- package/dist/core/middlewares/html-minifier.js +140 -0
- package/dist/core/middlewares/index.d.ts +5 -0
- package/dist/core/middlewares/index.d.ts.map +1 -0
- package/dist/core/middlewares/index.js +4 -0
- package/dist/core/middlewares/initializer.d.ts +11 -0
- package/dist/core/middlewares/initializer.d.ts.map +1 -0
- package/dist/core/middlewares/initializer.js +13 -0
- package/dist/core/middlewares/visitor-tracker.d.ts +85 -0
- package/dist/core/middlewares/visitor-tracker.d.ts.map +1 -0
- package/dist/core/middlewares/visitor-tracker.js +253 -0
- package/dist/core/template.d.ts +4 -0
- package/dist/core/template.d.ts.map +1 -0
- package/dist/core/template.js +7 -0
- package/dist/core/utils/formatDate.d.ts +3 -0
- package/dist/core/utils/formatDate.d.ts.map +1 -0
- package/dist/core/utils/formatDate.js +2 -0
- package/dist/core/utils/fullUrl.d.ts +2 -0
- package/dist/core/utils/fullUrl.d.ts.map +1 -0
- package/dist/core/utils/fullUrl.js +9 -0
- package/dist/core/utils/index.d.ts +6 -0
- package/dist/core/utils/index.d.ts.map +1 -0
- package/dist/core/utils/index.js +5 -0
- package/dist/core/utils/markdownify.d.ts +2 -0
- package/dist/core/utils/markdownify.d.ts.map +1 -0
- package/dist/core/utils/markdownify.js +4 -0
- package/dist/core/utils/params.d.ts +5 -0
- package/dist/core/utils/params.d.ts.map +1 -0
- package/dist/core/utils/params.js +14 -0
- package/dist/core/utils/routeUrl.d.ts +20 -0
- package/dist/core/utils/routeUrl.d.ts.map +1 -0
- package/dist/core/utils/routeUrl.js +111 -0
- package/dist/route/methods.d.ts +15 -0
- package/dist/route/methods.d.ts.map +1 -1
- package/dist/route/methods.js +45 -18
- package/dist/route/setup.d.ts +11 -12
- package/dist/route/setup.d.ts.map +1 -1
- package/dist/route/setup.js +26 -16
- package/dist/strapi/api/site.d.ts +2 -0
- package/dist/strapi/api/site.d.ts.map +1 -0
- package/dist/strapi/api/site.js +153 -0
- package/dist/strapi/cms/cms.js +1 -1
- package/dist/strapi/cms/common.d.ts.map +1 -1
- package/dist/strapi/cms/common.js +3 -1
- package/dist/strapi/cms/menu.d.ts +0 -9
- package/dist/strapi/cms/menu.d.ts.map +1 -1
- package/dist/strapi/cms/menu.js +3 -62
- package/dist/strapi/cms/setup.d.ts +2 -1
- package/dist/strapi/cms/setup.d.ts.map +1 -1
- package/dist/strapi/cms/setup.js +5 -0
- package/dist/strapi/cms/site.d.ts.map +1 -1
- package/dist/strapi/cms/site.js +3 -1
- package/dist/strapi/cms/translations.d.ts.map +1 -1
- package/dist/strapi/cms/translations.js +6 -2
- package/dist/strapi/i18n.d.ts +3 -0
- package/dist/strapi/i18n.d.ts.map +1 -0
- package/dist/strapi/i18n.js +27 -0
- package/dist/strapi/index.d.ts +1 -0
- package/dist/strapi/index.d.ts.map +1 -1
- package/dist/strapi/index.js +1 -0
- package/dist/strapi/interfaces/index.d.ts +1 -0
- package/dist/strapi/interfaces/index.d.ts.map +1 -1
- package/dist/strapi/interfaces/index.js +1 -0
- package/dist/strapi/interfaces/sitemap.d.ts +19 -0
- package/dist/strapi/interfaces/sitemap.d.ts.map +1 -0
- package/dist/strapi/interfaces/sitemap.js +1 -0
- package/dist/strapi/pages/sitemap/index.d.ts +2 -0
- package/dist/strapi/pages/sitemap/index.d.ts.map +1 -0
- package/dist/strapi/pages/sitemap/index.js +50 -0
- package/dist/strapi/pages/sitemap/index.xml +11 -0
- package/dist/strapi/pages/sitemap/list.d.ts +2 -0
- package/dist/strapi/pages/sitemap/list.d.ts.map +1 -0
- package/dist/strapi/pages/sitemap/list.js +123 -0
- package/dist/strapi/pages/sitemap/list.xml +28 -0
- package/dist/strapi/pages/sitemap/robots.d.ts +2 -0
- package/dist/strapi/pages/sitemap/robots.d.ts.map +1 -0
- package/dist/strapi/pages/sitemap/robots.js +19 -0
- package/dist/strapi/pages/sitemap/robots.txt +7 -0
- package/dist/strapi/pages/sitemap/style.d.ts +2 -0
- package/dist/strapi/pages/sitemap/style.d.ts.map +1 -0
- package/dist/strapi/pages/sitemap/style.js +17 -0
- package/dist/strapi/pages/sitemap/style.xsl +602 -0
- package/dist/strapi/utils/index.d.ts +1 -0
- package/dist/strapi/utils/index.d.ts.map +1 -1
- package/dist/strapi/utils/index.js +1 -0
- package/dist/strapi/utils/trans.d.ts +5 -0
- package/dist/strapi/utils/trans.d.ts.map +1 -0
- package/dist/strapi/utils/trans.js +7 -0
- package/package.json +20 -2
package/dist/contract.d.ts
CHANGED
|
@@ -1,5 +1,13 @@
|
|
|
1
1
|
export declare const CMS_URL: string;
|
|
2
|
-
export declare const MEDIA_URL: string;
|
|
3
2
|
export declare const CMS_TOKEN: string;
|
|
3
|
+
export declare const MEDIA_URL: string;
|
|
4
4
|
export declare const URL_SUFFIX: string;
|
|
5
|
+
export declare const WEBSITE_DATA_DIR: string;
|
|
6
|
+
export declare const MAIL_HOST: string;
|
|
7
|
+
export declare const MAIL_PORT: number;
|
|
8
|
+
export declare const MAIL_SECURE: boolean;
|
|
9
|
+
export declare const MAIL_USER: string | undefined;
|
|
10
|
+
export declare const MAIL_PASS: string | undefined;
|
|
11
|
+
export declare const MAIL_FROM: string | undefined;
|
|
12
|
+
export declare const MAIL_TO: string | undefined;
|
|
5
13
|
//# sourceMappingURL=contract.d.ts.map
|
package/dist/contract.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"contract.d.ts","sourceRoot":"","sources":["../src/contract.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"contract.d.ts","sourceRoot":"","sources":["../src/contract.ts"],"names":[],"mappings":"AAcA,eAAO,MAAM,OAAO,QAAsB,CAAA;AAC1C,eAAO,MAAM,SAAS,QAAwB,CAAA;AAG9C,eAAO,MAAM,SAAS,QAAmC,CAAA;AACzD,eAAO,MAAM,UAAU,QAAoC,CAAA;AAG3D,eAAO,MAAM,gBAAgB,QAA0C,CAAA;AAGvE,eAAO,MAAM,SAAS,QAA+C,CAAA;AACrE,eAAO,MAAM,SAAS,QAAuC,CAAA;AAC7D,eAAO,MAAM,WAAW,SAAsC,CAAA;AAC9D,eAAO,MAAM,SAAS,oBAAwB,CAAA;AAC9C,eAAO,MAAM,SAAS,oBAAwB,CAAA;AAC9C,eAAO,MAAM,SAAS,oBAAwB,CAAA;AAC9C,eAAO,MAAM,OAAO,oBAAsB,CAAA"}
|
package/dist/contract.js
CHANGED
|
@@ -2,12 +2,23 @@
|
|
|
2
2
|
if (!process.env.CMS_URL) {
|
|
3
3
|
throw new Error('CMS_URL is required but not provided in environment variables');
|
|
4
4
|
}
|
|
5
|
-
export const CMS_URL = process.env.CMS_URL;
|
|
6
|
-
// MEDIA_URL 可选,如果未提供则使用 CMS_URL
|
|
7
|
-
export const MEDIA_URL = process.env.MEDIA_URL || CMS_URL;
|
|
8
5
|
// 检查 CMS_TOKEN 是否存在
|
|
9
6
|
if (!process.env.CMS_TOKEN) {
|
|
10
7
|
throw new Error('CMS_TOKEN is required but not provided in environment variables');
|
|
11
8
|
}
|
|
9
|
+
// CMS URL 和 TOKEN
|
|
10
|
+
export const CMS_URL = process.env.CMS_URL;
|
|
12
11
|
export const CMS_TOKEN = process.env.CMS_TOKEN;
|
|
12
|
+
// MEDIA_URL 可选,如果未提供则使用 CMS_URL
|
|
13
|
+
export const MEDIA_URL = process.env.MEDIA_URL || CMS_URL;
|
|
13
14
|
export const URL_SUFFIX = process.env.URL_SUFFIX || '.html';
|
|
15
|
+
// 数据文件根目录
|
|
16
|
+
export const WEBSITE_DATA_DIR = process.env.WEBSITE_DATA_DIR || '.data';
|
|
17
|
+
// 邮件服务配置
|
|
18
|
+
export const MAIL_HOST = process.env.MAIL_HOST || 'smtpdm.aliyun.com';
|
|
19
|
+
export const MAIL_PORT = Number(process.env.MAIL_PORT || 465);
|
|
20
|
+
export const MAIL_SECURE = process.env.MAIL_SECURE !== 'false'; // 默认 true
|
|
21
|
+
export const MAIL_USER = process.env.MAIL_USER;
|
|
22
|
+
export const MAIL_PASS = process.env.MAIL_PASS;
|
|
23
|
+
export const MAIL_FROM = process.env.MAIL_FROM;
|
|
24
|
+
export const MAIL_TO = process.env.MAIL_TO;
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"common.d.ts","sourceRoot":"","sources":["../../../src/core/api/common.ts"],"names":[],"mappings":""}
|
|
@@ -0,0 +1,38 @@
|
|
|
1
|
+
import { getDatabase } from '../../core/lib/database';
|
|
2
|
+
import { errorResponse } from '../../core/lib/utils/api';
|
|
3
|
+
import { formatDate } from '../../core/utils';
|
|
4
|
+
import { route } from '../../route';
|
|
5
|
+
route.get('/api/common/dashboard', {
|
|
6
|
+
suffix: '',
|
|
7
|
+
async handler(c) {
|
|
8
|
+
try {
|
|
9
|
+
const today = formatDate().startOf('day').toDate();
|
|
10
|
+
const tomorrow = formatDate().add(1, 'day').startOf('day').toDate();
|
|
11
|
+
// 获取数据库服务实例
|
|
12
|
+
const db = await getDatabase();
|
|
13
|
+
// 并行查询所有统计数据
|
|
14
|
+
const [totalVisitor, todayVisitor, totalInquiry, unreadInquiry] = await Promise.all([
|
|
15
|
+
db.countVisitors(), // 总访问量
|
|
16
|
+
db.countVisitors({ start: today, end: tomorrow }), // 今日访客
|
|
17
|
+
db.countInquiries(), // 总询盘数
|
|
18
|
+
db.countUnreadInquiries(), // 未读询盘数
|
|
19
|
+
]);
|
|
20
|
+
return c.json({
|
|
21
|
+
totalVisitor,
|
|
22
|
+
todayVisitor,
|
|
23
|
+
totalInquiry,
|
|
24
|
+
unreadInquiry,
|
|
25
|
+
});
|
|
26
|
+
}
|
|
27
|
+
catch (error) {
|
|
28
|
+
console.error('Failed to fetch dashboard stats:', error);
|
|
29
|
+
return c.json(errorResponse(400, 'Failed to fetch dashboard stats'), 400);
|
|
30
|
+
}
|
|
31
|
+
},
|
|
32
|
+
});
|
|
33
|
+
route.get('/api/common/hello', {
|
|
34
|
+
suffix: '',
|
|
35
|
+
async handler(c) {
|
|
36
|
+
return c.json({ msg: 'ok' });
|
|
37
|
+
},
|
|
38
|
+
});
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"inquiries.d.ts","sourceRoot":"","sources":["../../../src/core/api/inquiries.ts"],"names":[],"mappings":""}
|
|
@@ -0,0 +1,116 @@
|
|
|
1
|
+
import { ERROR_CODES } from '../../core/lib/constants/inquiry';
|
|
2
|
+
import { getDatabase } from '../../core/lib/database';
|
|
3
|
+
import { errorResponse, successResponse, validateId, } from '../../core/lib/utils/api';
|
|
4
|
+
import { route } from '../../route';
|
|
5
|
+
route.put('/api/inquiries/:id/read', {
|
|
6
|
+
suffix: '',
|
|
7
|
+
async handler(c) {
|
|
8
|
+
try {
|
|
9
|
+
// 解析 ID
|
|
10
|
+
const id = parseInt(c.req.param('id') || '0', 10);
|
|
11
|
+
// 验证 ID
|
|
12
|
+
const validation = validateId(id);
|
|
13
|
+
if (!validation.valid) {
|
|
14
|
+
return c.json({
|
|
15
|
+
code: ERROR_CODES.INVALID_ID,
|
|
16
|
+
message: validation.error || 'Invalid ID',
|
|
17
|
+
data: null,
|
|
18
|
+
timestamp: new Date().toISOString(),
|
|
19
|
+
}, 400);
|
|
20
|
+
}
|
|
21
|
+
// 解析请求体
|
|
22
|
+
const body = await c.req.json();
|
|
23
|
+
const operatorId = parseInt(body.operatorId || '0', 10);
|
|
24
|
+
// 验证 operatorId
|
|
25
|
+
const operatorValidation = validateId(operatorId);
|
|
26
|
+
if (!operatorValidation.valid) {
|
|
27
|
+
return c.json(errorResponse(ERROR_CODES.INVALID_ID, operatorValidation.error || 'Invalid operator ID'), 400);
|
|
28
|
+
}
|
|
29
|
+
// 获取数据库服务
|
|
30
|
+
const db = await getDatabase();
|
|
31
|
+
// 标记已读
|
|
32
|
+
const success = await db.markInquiryAsRead(id, operatorId);
|
|
33
|
+
// 判断是否成功
|
|
34
|
+
if (!success) {
|
|
35
|
+
return c.json(errorResponse(ERROR_CODES.NOT_FOUND, 'Inquiry not found'), 404);
|
|
36
|
+
}
|
|
37
|
+
return c.json(successResponse({ success: true }));
|
|
38
|
+
}
|
|
39
|
+
catch (error) {
|
|
40
|
+
console.error('Failed to mark inquiry as read:', error);
|
|
41
|
+
return c.json(errorResponse(ERROR_CODES.INTERNAL_ERROR, 'Failed to mark inquiry as read'), 500);
|
|
42
|
+
}
|
|
43
|
+
},
|
|
44
|
+
});
|
|
45
|
+
route.get('/api/inquiries/:id', {
|
|
46
|
+
suffix: '',
|
|
47
|
+
async handler(c) {
|
|
48
|
+
try {
|
|
49
|
+
// 解析 ID
|
|
50
|
+
const id = parseInt(c.req.param('id') || '0', 10);
|
|
51
|
+
// 验证 ID
|
|
52
|
+
const validation = validateId(id);
|
|
53
|
+
if (!validation.valid) {
|
|
54
|
+
return c.json(errorResponse(ERROR_CODES.INVALID_ID, validation.error || 'Invalid ID'), 400);
|
|
55
|
+
}
|
|
56
|
+
// 获取数据库服务
|
|
57
|
+
const db = await getDatabase();
|
|
58
|
+
// 获取询盘详情
|
|
59
|
+
const inquiry = await db.getInquiryById(id);
|
|
60
|
+
// 判断是否存在
|
|
61
|
+
if (!inquiry) {
|
|
62
|
+
return c.json(errorResponse(ERROR_CODES.NOT_FOUND, 'Inquiry not found'), 404);
|
|
63
|
+
}
|
|
64
|
+
return c.json(successResponse(inquiry));
|
|
65
|
+
}
|
|
66
|
+
catch (error) {
|
|
67
|
+
console.error('Failed to fetch inquiry detail:', error);
|
|
68
|
+
return c.json(errorResponse(ERROR_CODES.INTERNAL_ERROR, 'Failed to fetch inquiry detail'), 500);
|
|
69
|
+
}
|
|
70
|
+
},
|
|
71
|
+
});
|
|
72
|
+
route.get('/api/inquiries', {
|
|
73
|
+
suffix: '',
|
|
74
|
+
async handler(c) {
|
|
75
|
+
const req = c.req;
|
|
76
|
+
const query = req.query();
|
|
77
|
+
try {
|
|
78
|
+
// 获取查询参数
|
|
79
|
+
const page = parseInt(query.page || '1', 10);
|
|
80
|
+
const pageSize = parseInt(query.pageSize || '15', 10);
|
|
81
|
+
const keyword = query.keyword || undefined;
|
|
82
|
+
const start = query.start ? new Date(query.start) : undefined;
|
|
83
|
+
const end = query.end ? new Date(query.end) : undefined;
|
|
84
|
+
const sortBy = query.sortBy || 'createdAt';
|
|
85
|
+
const order = query.order || 'desc';
|
|
86
|
+
// 获取数据库服务
|
|
87
|
+
const db = await getDatabase();
|
|
88
|
+
// 查询列表
|
|
89
|
+
const offset = (page - 1) * pageSize;
|
|
90
|
+
const items = await db.listInquiries({
|
|
91
|
+
start,
|
|
92
|
+
end,
|
|
93
|
+
keyword,
|
|
94
|
+
limit: pageSize,
|
|
95
|
+
offset,
|
|
96
|
+
sortBy,
|
|
97
|
+
order,
|
|
98
|
+
});
|
|
99
|
+
// 查询总数
|
|
100
|
+
const total = await db.countInquiries({ start, end, keyword });
|
|
101
|
+
// 返回结果 (符合 NestJS ApiResponse<PagedListData> 格式)
|
|
102
|
+
return c.json(successResponse({
|
|
103
|
+
items,
|
|
104
|
+
pagination: {
|
|
105
|
+
page,
|
|
106
|
+
pageSize,
|
|
107
|
+
total,
|
|
108
|
+
},
|
|
109
|
+
}));
|
|
110
|
+
}
|
|
111
|
+
catch (error) {
|
|
112
|
+
console.error('Failed to fetch inquiry list:', error);
|
|
113
|
+
return c.json(errorResponse(ERROR_CODES.INTERNAL_ERROR, 'Failed to fetch inquiry list'), 500);
|
|
114
|
+
}
|
|
115
|
+
},
|
|
116
|
+
});
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"inquiry.d.ts","sourceRoot":"","sources":["../../../src/core/api/inquiry.ts"],"names":[],"mappings":""}
|
|
@@ -0,0 +1,33 @@
|
|
|
1
|
+
import { ERROR_CODES } from '../../core/lib/constants/inquiry';
|
|
2
|
+
import { submitInquiry } from '../../core/lib/services';
|
|
3
|
+
import { errorResponse, successResponse } from '../../core/lib/utils/api';
|
|
4
|
+
import { requestInfo } from '../../core/lib/utils/request';
|
|
5
|
+
import { route } from '../../route';
|
|
6
|
+
route.post('/api/inquiry/post', {
|
|
7
|
+
suffix: '',
|
|
8
|
+
async handler(c) {
|
|
9
|
+
console.log('[Inquiry API] Received request');
|
|
10
|
+
try {
|
|
11
|
+
// 解析请求体 (支持 JSON 格式)
|
|
12
|
+
const body = await c.req.json();
|
|
13
|
+
console.log('[Inquiry API] Parsed data:', Object.keys(body));
|
|
14
|
+
// 提取请求上下文
|
|
15
|
+
const context = requestInfo(c);
|
|
16
|
+
console.log('[Inquiry API] Request context:', {
|
|
17
|
+
ip: context.clientIp,
|
|
18
|
+
userAgent: context.userAgent,
|
|
19
|
+
});
|
|
20
|
+
// 调用统一的业务服务
|
|
21
|
+
console.log('[Inquiry API] Submitting inquiry...');
|
|
22
|
+
const id = await submitInquiry(body, context);
|
|
23
|
+
console.log('[Inquiry API] Inquiry saved successfully, ID:', id);
|
|
24
|
+
// 返回结果 (符合 NestJS 格式)
|
|
25
|
+
return c.json(successResponse({ id }));
|
|
26
|
+
}
|
|
27
|
+
catch (error) {
|
|
28
|
+
console.error('[Inquiry API] Error submitting inquiry:', error);
|
|
29
|
+
console.error('[Inquiry API] Error stack:', error instanceof Error ? error.stack : 'No stack trace');
|
|
30
|
+
return c.json(errorResponse(ERROR_CODES.INTERNAL_ERROR, 'Failed to submit inquiry'), 500);
|
|
31
|
+
}
|
|
32
|
+
},
|
|
33
|
+
});
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"visitor.d.ts","sourceRoot":"","sources":["../../../src/core/api/visitor.ts"],"names":[],"mappings":""}
|
|
@@ -0,0 +1,152 @@
|
|
|
1
|
+
import { getDatabase } from '../../core/lib/database';
|
|
2
|
+
import { errorResponse } from '../../core/lib/utils/api';
|
|
3
|
+
import { route } from '../../route';
|
|
4
|
+
route.get('/api/visitor/sessions', {
|
|
5
|
+
suffix: '',
|
|
6
|
+
async handler(c) {
|
|
7
|
+
try {
|
|
8
|
+
// 获取查询参数
|
|
9
|
+
const query = c.req.query();
|
|
10
|
+
const start = query.start ? new Date(query.start) : undefined;
|
|
11
|
+
const end = query.end ? new Date(query.end) : undefined;
|
|
12
|
+
const ip = query.ip || undefined;
|
|
13
|
+
const limit = query.limit ? parseInt(query.limit, 10) : undefined;
|
|
14
|
+
const offset = query.offset ? parseInt(query.offset, 10) : undefined;
|
|
15
|
+
// 获取数据库服务
|
|
16
|
+
const db = await getDatabase();
|
|
17
|
+
// 查询会话
|
|
18
|
+
const result = await db.queryVisitorSessions({
|
|
19
|
+
start,
|
|
20
|
+
end,
|
|
21
|
+
ip,
|
|
22
|
+
limit,
|
|
23
|
+
offset,
|
|
24
|
+
});
|
|
25
|
+
return c.json(result);
|
|
26
|
+
}
|
|
27
|
+
catch (error) {
|
|
28
|
+
console.error('Failed to query visitor sessions:', error);
|
|
29
|
+
return c.json(errorResponse(400, 'Failed to query visitor sessions'), 400);
|
|
30
|
+
}
|
|
31
|
+
},
|
|
32
|
+
});
|
|
33
|
+
route.get('/api/visitor/page-views', {
|
|
34
|
+
suffix: '',
|
|
35
|
+
async handler(c) {
|
|
36
|
+
try {
|
|
37
|
+
// 获取查询参数
|
|
38
|
+
const query = c.req.query();
|
|
39
|
+
const start = query.start ? new Date(query.start) : undefined;
|
|
40
|
+
const end = query.end ? new Date(query.end) : undefined;
|
|
41
|
+
const ip = query.ip || undefined;
|
|
42
|
+
const page = query.page || undefined;
|
|
43
|
+
const limit = query.limit ? parseInt(query.limit, 10) : undefined;
|
|
44
|
+
const offset = query.offset ? parseInt(query.offset, 10) : undefined;
|
|
45
|
+
// 获取数据库服务
|
|
46
|
+
const db = await getDatabase();
|
|
47
|
+
// 查询记录
|
|
48
|
+
const result = await db.queryPageViews({
|
|
49
|
+
start,
|
|
50
|
+
end,
|
|
51
|
+
ip,
|
|
52
|
+
page,
|
|
53
|
+
limit,
|
|
54
|
+
offset,
|
|
55
|
+
});
|
|
56
|
+
return c.json(result);
|
|
57
|
+
}
|
|
58
|
+
catch (error) {
|
|
59
|
+
console.error('Failed to query page views:', error);
|
|
60
|
+
return c.json(errorResponse(400, 'Failed to query page views'), 400);
|
|
61
|
+
}
|
|
62
|
+
},
|
|
63
|
+
});
|
|
64
|
+
route.get('/api/visitor/stats/uv', {
|
|
65
|
+
suffix: '',
|
|
66
|
+
async handler(c) {
|
|
67
|
+
try {
|
|
68
|
+
// 获取查询参数
|
|
69
|
+
const query = c.req.query();
|
|
70
|
+
const start = query.start ? new Date(query.start) : undefined;
|
|
71
|
+
const end = query.end ? new Date(query.end) : undefined;
|
|
72
|
+
const byDate = query.byDate === 'true';
|
|
73
|
+
// 获取数据库服务
|
|
74
|
+
const db = await getDatabase();
|
|
75
|
+
// 获取统计
|
|
76
|
+
const result = await db.getUVStats({ start, end }, byDate);
|
|
77
|
+
return c.json(result);
|
|
78
|
+
}
|
|
79
|
+
catch (error) {
|
|
80
|
+
console.error('Failed to fetch dashboard stats:', error);
|
|
81
|
+
return c.json(errorResponse(400, 'Failed to fetch dashboard stats'), 400);
|
|
82
|
+
}
|
|
83
|
+
},
|
|
84
|
+
});
|
|
85
|
+
route.get('/api/visitor/stats/pv', {
|
|
86
|
+
suffix: '',
|
|
87
|
+
async handler(c) {
|
|
88
|
+
try {
|
|
89
|
+
// 获取查询参数
|
|
90
|
+
const query = c.req.query();
|
|
91
|
+
const start = query.start ? new Date(query.start) : undefined;
|
|
92
|
+
const end = query.end ? new Date(query.end) : undefined;
|
|
93
|
+
const groupBy = query.groupBy || undefined;
|
|
94
|
+
const page = query.page || undefined;
|
|
95
|
+
const ip = query.ip || undefined;
|
|
96
|
+
// 获取数据库服务
|
|
97
|
+
const db = await getDatabase();
|
|
98
|
+
// 获取统计
|
|
99
|
+
const result = await db.getPVStats({ start, end, page, ip }, groupBy);
|
|
100
|
+
return c.json(result);
|
|
101
|
+
}
|
|
102
|
+
catch (error) {
|
|
103
|
+
console.error('Failed to fetch PV stats:', error);
|
|
104
|
+
return c.json(errorResponse(400, 'Failed to fetch PV stats'), 400);
|
|
105
|
+
}
|
|
106
|
+
},
|
|
107
|
+
});
|
|
108
|
+
route.get('/api/visitor/stats/ip-page', {
|
|
109
|
+
suffix: '',
|
|
110
|
+
async handler(c) {
|
|
111
|
+
try {
|
|
112
|
+
// 获取查询参数
|
|
113
|
+
const query = c.req.query();
|
|
114
|
+
const ip = query.ip || undefined;
|
|
115
|
+
const page = query.page || undefined;
|
|
116
|
+
// 获取数据库服务
|
|
117
|
+
const db = await getDatabase();
|
|
118
|
+
// 获取统计
|
|
119
|
+
const result = await db.getIpPageViewStats({ ip, page });
|
|
120
|
+
return c.json(result);
|
|
121
|
+
}
|
|
122
|
+
catch (error) {
|
|
123
|
+
console.error('Failed to fetch daily page stats:', error);
|
|
124
|
+
return c.json(errorResponse(400, 'Failed to fetch daily page stats'), 400);
|
|
125
|
+
}
|
|
126
|
+
},
|
|
127
|
+
});
|
|
128
|
+
route.get('/api/visitor/stats/daily-page', {
|
|
129
|
+
suffix: '',
|
|
130
|
+
async handler(c) {
|
|
131
|
+
try {
|
|
132
|
+
// 获取查询参数
|
|
133
|
+
const query = c.req.query();
|
|
134
|
+
const start = query.start ? new Date(query.start) : undefined;
|
|
135
|
+
const end = query.end ? new Date(query.end) : undefined;
|
|
136
|
+
const page = query.page || undefined;
|
|
137
|
+
// 获取数据库服务
|
|
138
|
+
const db = await getDatabase();
|
|
139
|
+
// 获取统计
|
|
140
|
+
const result = await db.getDailyPageViewStats({
|
|
141
|
+
start,
|
|
142
|
+
end,
|
|
143
|
+
page,
|
|
144
|
+
});
|
|
145
|
+
return c.json(result);
|
|
146
|
+
}
|
|
147
|
+
catch (error) {
|
|
148
|
+
console.error('Failed to fetch daily page stats:', error);
|
|
149
|
+
return c.json(errorResponse(400, 'Failed to fetch daily page stats'), 400);
|
|
150
|
+
}
|
|
151
|
+
},
|
|
152
|
+
});
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* 询盘邮件模板组件
|
|
3
|
+
* 用于发送邮件时展示询盘信息
|
|
4
|
+
*/
|
|
5
|
+
import type { FC } from 'hono/jsx';
|
|
6
|
+
/**
|
|
7
|
+
* 询盘邮件模板数据接口
|
|
8
|
+
*/
|
|
9
|
+
export interface InquiryEmailValues {
|
|
10
|
+
id: number;
|
|
11
|
+
firstName: string;
|
|
12
|
+
lastName: string;
|
|
13
|
+
email: string;
|
|
14
|
+
phone: string;
|
|
15
|
+
message: string;
|
|
16
|
+
referer: string;
|
|
17
|
+
ip: string;
|
|
18
|
+
userAgent: string;
|
|
19
|
+
geo: string;
|
|
20
|
+
data: object;
|
|
21
|
+
createdAt: string;
|
|
22
|
+
}
|
|
23
|
+
export interface InquiryEmailTemplateProps {
|
|
24
|
+
values: InquiryEmailValues;
|
|
25
|
+
}
|
|
26
|
+
/**
|
|
27
|
+
* 询盘邮件模板组件
|
|
28
|
+
*/
|
|
29
|
+
export declare const InquiryEmailTemplate: FC<InquiryEmailTemplateProps>;
|
|
30
|
+
//# sourceMappingURL=InquiryEmailTemplate.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"InquiryEmailTemplate.d.ts","sourceRoot":"","sources":["../../../src/core/components/InquiryEmailTemplate.tsx"],"names":[],"mappings":"AAAA;;;GAGG;AAEH,OAAO,KAAK,EAAE,EAAE,EAAE,MAAM,UAAU,CAAA;AAIlC;;GAEG;AACH,MAAM,WAAW,kBAAkB;IAClC,EAAE,EAAE,MAAM,CAAA;IACV,SAAS,EAAE,MAAM,CAAA;IACjB,QAAQ,EAAE,MAAM,CAAA;IAChB,KAAK,EAAE,MAAM,CAAA;IACb,KAAK,EAAE,MAAM,CAAA;IACb,OAAO,EAAE,MAAM,CAAA;IACf,OAAO,EAAE,MAAM,CAAA;IACf,EAAE,EAAE,MAAM,CAAA;IACV,SAAS,EAAE,MAAM,CAAA;IACjB,GAAG,EAAE,MAAM,CAAA;IACX,IAAI,EAAE,MAAM,CAAA;IACZ,SAAS,EAAE,MAAM,CAAA;CACjB;AAED,MAAM,WAAW,yBAAyB;IACzC,MAAM,EAAE,kBAAkB,CAAA;CAC1B;AAED;;GAEG;AACH,eAAO,MAAM,oBAAoB,EAAE,EAAE,CAAC,yBAAyB,CA6J9D,CAAA"}
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
import { jsx as _jsx, jsxs as _jsxs } from "hono/jsx/jsx-runtime";
|
|
2
|
+
import { getSite } from '../../strapi/cms';
|
|
3
|
+
import { trans } from '../../strapi/utils';
|
|
4
|
+
/**
|
|
5
|
+
* 询盘邮件模板组件
|
|
6
|
+
*/
|
|
7
|
+
export const InquiryEmailTemplate = ({ values, }) => {
|
|
8
|
+
const { id, firstName, lastName, email, phone, message, referer, ip, userAgent, geo, data, createdAt, } = values;
|
|
9
|
+
const site = getSite();
|
|
10
|
+
const website = site.title;
|
|
11
|
+
const dataItems = Object.entries(data || {}).map(([key, value]) => (_jsxs("tr", { children: [_jsx("th", { style: "padding: 8px 10px; text-align: left; background-color: #f6f6f9; color: #32324d; font-weight: 600; font-size: 13px; width: 100px; vertical-align: top; border: 1px solid #eaeaea;", children: trans(key) }), _jsx("td", { style: "padding: 8px 10px; text-align: left; background-color: #ffffff; color: #666687; font-size: 13px; word-break: break-word; border: 1px solid #eaeaea;", children: value })] }, key)));
|
|
12
|
+
return (_jsx("div", { style: "padding: 8px;", children: _jsxs("div", { style: "max-width: 600px; margin: 0 auto; background-color: #ffffff; border-radius: 6px; box-shadow: 0 2px 6px rgba(0, 0, 0, 0.1); overflow: hidden;", children: [_jsxs("div", { style: "background: linear-gradient(135deg, #667eea 0%, #764ba2 100%); padding: 16px 12px; text-align: center;", children: [_jsxs("h1", { style: "margin: 0; color: #ffffff; font-size: 18px; font-weight: 600;", children: [website, " - \u8BE2\u76D8\u901A\u77E5"] }), _jsxs("p", { style: "margin: 6px 0 0 0; color: rgba(255, 255, 255, 0.9); font-size: 12px;", children: ["\u8BE2\u76D8 ID: #", id] })] }), _jsx("div", { style: "padding: 12px;", children: _jsx("table", { style: "width: 100%; border-collapse: collapse; margin-bottom: 0;", children: _jsxs("tbody", { children: [_jsx("tr", { children: _jsx("th", { colSpan: "2", style: "padding: 8px 10px; text-align: center; background-color: #f6f6f9; color: #32324d; font-weight: 600; font-size: 14px; border: 1px solid #eaeaea;", children: "\u57FA\u672C\u4FE1\u606F" }) }), _jsxs("tr", { children: [_jsx("th", { style: "padding: 8px 10px; text-align: left; background-color: #f6f6f9; color: #32324d; font-weight: 600; font-size: 13px; width: 100px; vertical-align: top; border: 1px solid #eaeaea;", children: "\u59D3\u540D" }), _jsxs("td", { style: "padding: 8px 10px; text-align: left; background-color: #ffffff; color: #666687; font-size: 13px; word-break: break-word; border: 1px solid #eaeaea;", children: [firstName, " ", lastName] })] }), _jsxs("tr", { children: [_jsx("th", { style: "padding: 8px 10px; text-align: left; background-color: #f6f6f9; color: #32324d; font-weight: 600; font-size: 13px; width: 100px; vertical-align: top; border: 1px solid #eaeaea;", children: "\u90AE\u7BB1" }), _jsx("td", { style: "padding: 8px 10px; text-align: left; background-color: #ffffff; color: #666687; font-size: 13px; word-break: break-word; border: 1px solid #eaeaea;", children: email })] }), _jsxs("tr", { children: [_jsx("th", { style: "padding: 8px 10px; text-align: left; background-color: #f6f6f9; color: #32324d; font-weight: 600; font-size: 13px; width: 100px; vertical-align: top; border: 1px solid #eaeaea;", children: "\u7535\u8BDD" }), _jsx("td", { style: "padding: 8px 10px; text-align: left; background-color: #ffffff; color: #666687; font-size: 13px; word-break: break-word; border: 1px solid #eaeaea;", children: phone })] }), _jsxs("tr", { children: [_jsx("th", { style: "padding: 8px 10px; text-align: left; background-color: #f6f6f9; color: #32324d; font-weight: 600; font-size: 13px; width: 100px; vertical-align: top; border: 1px solid #eaeaea;", children: "\u63A5\u6536\u65F6\u95F4" }), _jsx("td", { style: "padding: 8px 10px; text-align: left; background-color: #ffffff; color: #666687; font-size: 13px; word-break: break-word; border: 1px solid #eaeaea;", children: createdAt })] }), _jsxs("tr", { children: [_jsx("th", { style: "padding: 8px 10px; text-align: left; background-color: #f6f6f9; color: #32324d; font-weight: 600; font-size: 13px; width: 100px; vertical-align: top; border: 1px solid #eaeaea;", children: "\u8BE2\u76D8\u9875\u9762" }), _jsx("td", { style: "padding: 8px 10px; text-align: left; background-color: #ffffff; color: #666687; font-size: 13px; word-break: break-word; border: 1px solid #eaeaea;", children: referer })] }), _jsxs("tr", { children: [_jsx("th", { style: "padding: 8px 10px; text-align: left; background-color: #f6f6f9; color: #32324d; font-weight: 600; font-size: 13px; width: 100px; vertical-align: top; border: 1px solid #eaeaea;", children: "\u8BE2\u76D8\u5185\u5BB9" }), _jsx("td", { style: "padding: 8px 10px; text-align: left; background-color: #ffffff; color: #666687; font-size: 13px; word-break: break-word; border: 1px solid #eaeaea; min-height: 80px; white-space: pre-wrap; vertical-align: top;", children: message })] }), _jsx("tr", { children: _jsx("th", { colSpan: "2", style: "padding: 8px 10px; text-align: center; background-color: #f6f6f9; color: #32324d; font-weight: 600; font-size: 14px; border: 1px solid #eaeaea;", children: "\u6269\u5C55\u4FE1\u606F" }) }), dataItems, _jsx("tr", { children: _jsx("th", { colSpan: "2", style: "padding: 8px 10px; text-align: center; background-color: #f6f6f9; color: #32324d; font-weight: 600; font-size: 14px; border: 1px solid #eaeaea;", children: "\u5BA2\u6237\u7AEF\u4FE1\u606F" }) }), _jsxs("tr", { children: [_jsx("th", { style: "padding: 8px 10px; text-align: left; background-color: #f6f6f9; color: #32324d; font-weight: 600; font-size: 13px; width: 100px; vertical-align: top; border: 1px solid #eaeaea;", children: "\u5BA2\u6237 IP" }), _jsx("td", { style: "padding: 8px 10px; text-align: left; background-color: #ffffff; color: #666687; font-size: 13px; word-break: break-word; border: 1px solid #eaeaea;", children: ip })] }), _jsxs("tr", { children: [_jsx("th", { style: "padding: 8px 10px; text-align: left; background-color: #f6f6f9; color: #32324d; font-weight: 600; font-size: 13px; width: 100px; vertical-align: top; border: 1px solid #eaeaea;", children: "\u7CFB\u7EDF\u6807\u8BC6" }), _jsx("td", { style: "padding: 8px 10px; text-align: left; background-color: #ffffff; color: #666687; word-break: break-word; border: 1px solid #eaeaea; font-size: 11px; font-family: monospace;", children: userAgent })] }), _jsxs("tr", { children: [_jsx("th", { style: "padding: 8px 10px; text-align: left; background-color: #f6f6f9; color: #32324d; font-weight: 600; font-size: 13px; width: 100px; vertical-align: top; border: 1px solid #eaeaea;", children: "\u5730\u7406\u4F4D\u7F6E" }), _jsx("td", { style: "padding: 8px 10px; text-align: left; background-color: #ffffff; color: #666687; font-size: 13px; word-break: break-word; border: 1px solid #eaeaea;", children: geo })] })] }) }) }), _jsxs("div", { style: "padding: 10px 12px; background-color: #f8f9fa; border-top: 1px solid #eaeaea; text-align: center;", children: [_jsxs("p", { style: "margin: 6px 0; font-size: 11px; color: #999;", children: ["\u6B64\u90AE\u4EF6\u7531", _jsx("b", { children: "\u6781\u5BA2\u9886\u822A" }), "CMS\u7CFB\u7EDF\u81EA\u52A8\u53D1\u9001,\u8BF7\u52FF\u76F4\u63A5\u56DE\u590D"] }), _jsx("p", { style: "margin: 6px 0; font-size: 11px; color: #999;", children: "\u66F4\u591A\u8BE6\u7EC6\u4FE1\u606F\u8BF7\u524D\u5F80\u7F51\u7AD9\u540E\u53F0\u67E5\u770B" })] })] }) }));
|
|
13
|
+
};
|
|
@@ -0,0 +1,97 @@
|
|
|
1
|
+
import type { FC } from 'hono/jsx';
|
|
2
|
+
export interface SeoProps {
|
|
3
|
+
url: string;
|
|
4
|
+
title: string;
|
|
5
|
+
description: string;
|
|
6
|
+
keywords?: string | string[];
|
|
7
|
+
type: 'website' | 'article' | 'product' | 'organization' | 'local-business';
|
|
8
|
+
published?: Date;
|
|
9
|
+
modified?: Date;
|
|
10
|
+
author?: {
|
|
11
|
+
name: string;
|
|
12
|
+
url?: string;
|
|
13
|
+
email?: string;
|
|
14
|
+
};
|
|
15
|
+
site: {
|
|
16
|
+
name: string;
|
|
17
|
+
logo: string;
|
|
18
|
+
icon: string;
|
|
19
|
+
appleTouchIcon?: string;
|
|
20
|
+
manifest?: string;
|
|
21
|
+
safariPinnedTab?: string;
|
|
22
|
+
msApplicationTileColor?: string;
|
|
23
|
+
msApplicationTileImage?: string;
|
|
24
|
+
themeColor?: string;
|
|
25
|
+
locale: string;
|
|
26
|
+
url: string;
|
|
27
|
+
contactPoint?: {
|
|
28
|
+
telephone: string;
|
|
29
|
+
contactType: string;
|
|
30
|
+
areaServed?: string;
|
|
31
|
+
availableLanguage?: string | string[];
|
|
32
|
+
};
|
|
33
|
+
};
|
|
34
|
+
breadcrumbs: Array<{
|
|
35
|
+
title: string;
|
|
36
|
+
url: string;
|
|
37
|
+
}>;
|
|
38
|
+
image: {
|
|
39
|
+
src: string;
|
|
40
|
+
alt: string;
|
|
41
|
+
width: number;
|
|
42
|
+
height: number;
|
|
43
|
+
caption?: string;
|
|
44
|
+
};
|
|
45
|
+
twitter?: {
|
|
46
|
+
card?: string;
|
|
47
|
+
site?: string;
|
|
48
|
+
creator?: string;
|
|
49
|
+
};
|
|
50
|
+
product?: {
|
|
51
|
+
price: number;
|
|
52
|
+
priceCurrency: string;
|
|
53
|
+
availability: 'InStock' | 'OutOfStock' | 'PreOrder' | 'LimitedAvailability';
|
|
54
|
+
brand?: string;
|
|
55
|
+
category?: string;
|
|
56
|
+
reviews?: Array<{
|
|
57
|
+
author: string;
|
|
58
|
+
ratingValue: number;
|
|
59
|
+
reviewBody?: string;
|
|
60
|
+
datePublished?: Date;
|
|
61
|
+
}>;
|
|
62
|
+
};
|
|
63
|
+
localBusiness?: {
|
|
64
|
+
name: string;
|
|
65
|
+
address: {
|
|
66
|
+
streetAddress: string;
|
|
67
|
+
addressLocality: string;
|
|
68
|
+
addressRegion?: string;
|
|
69
|
+
postalCode: string;
|
|
70
|
+
addressCountry: string;
|
|
71
|
+
};
|
|
72
|
+
geo?: {
|
|
73
|
+
latitude: number;
|
|
74
|
+
longitude: number;
|
|
75
|
+
};
|
|
76
|
+
telephone?: string;
|
|
77
|
+
openingHours?: Array<{
|
|
78
|
+
dayOfWeek: string[];
|
|
79
|
+
hours: string;
|
|
80
|
+
}>;
|
|
81
|
+
};
|
|
82
|
+
organization?: {
|
|
83
|
+
foundingDate?: Date;
|
|
84
|
+
memberOf?: string;
|
|
85
|
+
numberOfEmployees?: number;
|
|
86
|
+
};
|
|
87
|
+
article?: {
|
|
88
|
+
wordCount?: number;
|
|
89
|
+
headline?: string;
|
|
90
|
+
section?: string;
|
|
91
|
+
tag?: string[];
|
|
92
|
+
};
|
|
93
|
+
metaHandler?: (meta: Record<string, string>) => Record<string, string>;
|
|
94
|
+
indexing?: boolean;
|
|
95
|
+
}
|
|
96
|
+
export declare const Seo: FC<SeoProps>;
|
|
97
|
+
//# sourceMappingURL=Seo.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"Seo.d.ts","sourceRoot":"","sources":["../../../src/core/components/Seo.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,EAAE,EAAE,MAAM,UAAU,CAAA;AAGlC,MAAM,WAAW,QAAQ;IACxB,GAAG,EAAE,MAAM,CAAA;IACX,KAAK,EAAE,MAAM,CAAA;IACb,WAAW,EAAE,MAAM,CAAA;IACnB,QAAQ,CAAC,EAAE,MAAM,GAAG,MAAM,EAAE,CAAA;IAC5B,IAAI,EAAE,SAAS,GAAG,SAAS,GAAG,SAAS,GAAG,cAAc,GAAG,gBAAgB,CAAA;IAC3E,SAAS,CAAC,EAAE,IAAI,CAAA;IAChB,QAAQ,CAAC,EAAE,IAAI,CAAA;IACf,MAAM,CAAC,EAAE;QACR,IAAI,EAAE,MAAM,CAAA;QACZ,GAAG,CAAC,EAAE,MAAM,CAAA;QACZ,KAAK,CAAC,EAAE,MAAM,CAAA;KACd,CAAA;IACD,IAAI,EAAE;QACL,IAAI,EAAE,MAAM,CAAA;QACZ,IAAI,EAAE,MAAM,CAAA;QACZ,IAAI,EAAE,MAAM,CAAA;QACZ,cAAc,CAAC,EAAE,MAAM,CAAA;QACvB,QAAQ,CAAC,EAAE,MAAM,CAAA;QACjB,eAAe,CAAC,EAAE,MAAM,CAAA;QACxB,sBAAsB,CAAC,EAAE,MAAM,CAAA;QAC/B,sBAAsB,CAAC,EAAE,MAAM,CAAA;QAC/B,UAAU,CAAC,EAAE,MAAM,CAAA;QACnB,MAAM,EAAE,MAAM,CAAA;QACd,GAAG,EAAE,MAAM,CAAA;QACX,YAAY,CAAC,EAAE;YACd,SAAS,EAAE,MAAM,CAAA;YACjB,WAAW,EAAE,MAAM,CAAA;YACnB,UAAU,CAAC,EAAE,MAAM,CAAA;YACnB,iBAAiB,CAAC,EAAE,MAAM,GAAG,MAAM,EAAE,CAAA;SACrC,CAAA;KACD,CAAA;IACD,WAAW,EAAE,KAAK,CAAC;QAClB,KAAK,EAAE,MAAM,CAAA;QACb,GAAG,EAAE,MAAM,CAAA;KACX,CAAC,CAAA;IACF,KAAK,EAAE;QACN,GAAG,EAAE,MAAM,CAAA;QACX,GAAG,EAAE,MAAM,CAAA;QACX,KAAK,EAAE,MAAM,CAAA;QACb,MAAM,EAAE,MAAM,CAAA;QACd,OAAO,CAAC,EAAE,MAAM,CAAA;KAChB,CAAA;IACD,OAAO,CAAC,EAAE;QACT,IAAI,CAAC,EAAE,MAAM,CAAA;QACb,IAAI,CAAC,EAAE,MAAM,CAAA;QACb,OAAO,CAAC,EAAE,MAAM,CAAA;KAChB,CAAA;IAED,OAAO,CAAC,EAAE;QACT,KAAK,EAAE,MAAM,CAAA;QACb,aAAa,EAAE,MAAM,CAAA;QACrB,YAAY,EAAE,SAAS,GAAG,YAAY,GAAG,UAAU,GAAG,qBAAqB,CAAA;QAC3E,KAAK,CAAC,EAAE,MAAM,CAAA;QACd,QAAQ,CAAC,EAAE,MAAM,CAAA;QACjB,OAAO,CAAC,EAAE,KAAK,CAAC;YACf,MAAM,EAAE,MAAM,CAAA;YACd,WAAW,EAAE,MAAM,CAAA;YACnB,UAAU,CAAC,EAAE,MAAM,CAAA;YACnB,aAAa,CAAC,EAAE,IAAI,CAAA;SACpB,CAAC,CAAA;KACF,CAAA;IAED,aAAa,CAAC,EAAE;QACf,IAAI,EAAE,MAAM,CAAA;QACZ,OAAO,EAAE;YACR,aAAa,EAAE,MAAM,CAAA;YACrB,eAAe,EAAE,MAAM,CAAA;YACvB,aAAa,CAAC,EAAE,MAAM,CAAA;YACtB,UAAU,EAAE,MAAM,CAAA;YAClB,cAAc,EAAE,MAAM,CAAA;SACtB,CAAA;QACD,GAAG,CAAC,EAAE;YACL,QAAQ,EAAE,MAAM,CAAA;YAChB,SAAS,EAAE,MAAM,CAAA;SACjB,CAAA;QACD,SAAS,CAAC,EAAE,MAAM,CAAA;QAClB,YAAY,CAAC,EAAE,KAAK,CAAC;YACpB,SAAS,EAAE,MAAM,EAAE,CAAA;YACnB,KAAK,EAAE,MAAM,CAAA;SACb,CAAC,CAAA;KACF,CAAA;IAED,YAAY,CAAC,EAAE;QACd,YAAY,CAAC,EAAE,IAAI,CAAA;QACnB,QAAQ,CAAC,EAAE,MAAM,CAAA;QACjB,iBAAiB,CAAC,EAAE,MAAM,CAAA;KAC1B,CAAA;IAED,OAAO,CAAC,EAAE;QACT,SAAS,CAAC,EAAE,MAAM,CAAA;QAClB,QAAQ,CAAC,EAAE,MAAM,CAAA;QACjB,OAAO,CAAC,EAAE,MAAM,CAAA;QAChB,GAAG,CAAC,EAAE,MAAM,EAAE,CAAA;KACd,CAAA;IACD,WAAW,CAAC,EAAE,CAAC,IAAI,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,KAAK,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAA;IACtE,QAAQ,CAAC,EAAE,OAAO,CAAA;CAClB;AAED,eAAO,MAAM,GAAG,EAAE,EAAE,CAAC,QAAQ,CA4Z5B,CAAA"}
|