@pixelated-tech/components 3.5.12 → 3.5.14

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.
Files changed (37) hide show
  1. package/dist/components/admin/site-health/seo-metrics.config.json +38 -18
  2. package/dist/components/admin/site-health/site-health-accessibility.js +2 -94
  3. package/dist/components/admin/site-health/site-health-axe-core.js +2 -2
  4. package/dist/components/admin/site-health/site-health-cloudwatch.js +2 -2
  5. package/dist/components/admin/site-health/site-health-dependency-vulnerabilities.js +1 -1
  6. package/dist/components/admin/site-health/site-health-github.js +3 -3
  7. package/dist/components/admin/site-health/site-health-google-analytics.js +1 -1
  8. package/dist/components/admin/site-health/site-health-google-search-console.js +1 -1
  9. package/dist/components/admin/site-health/site-health-on-site-seo.integration.js +275 -3
  10. package/dist/components/admin/site-health/site-health-on-site-seo.js +5 -56
  11. package/dist/components/admin/site-health/site-health-overview.js +1 -9
  12. package/dist/components/admin/site-health/site-health-performance.js +2 -158
  13. package/dist/components/admin/site-health/site-health-security.js +2 -139
  14. package/dist/components/admin/site-health/site-health-seo.js +2 -94
  15. package/dist/components/admin/site-health/site-health-utils.js +170 -0
  16. package/dist/components/admin/site-health/site-health.css +33 -3
  17. package/dist/components/cms/smartimage.js +28 -8
  18. package/dist/components/general/table.js +2 -2
  19. package/dist/components/sitebuilder/config/ConfigBuilder.js +12 -3
  20. package/dist/index.adminclient.js +1 -0
  21. package/dist/index.adminserver.js +1 -0
  22. package/dist/types/components/admin/site-health/site-health-accessibility.d.ts.map +1 -1
  23. package/dist/types/components/admin/site-health/site-health-on-site-seo.d.ts.map +1 -1
  24. package/dist/types/components/admin/site-health/site-health-on-site-seo.integration.d.ts.map +1 -1
  25. package/dist/types/components/admin/site-health/site-health-overview.d.ts.map +1 -1
  26. package/dist/types/components/admin/site-health/site-health-performance.d.ts.map +1 -1
  27. package/dist/types/components/admin/site-health/site-health-security.d.ts.map +1 -1
  28. package/dist/types/components/admin/site-health/site-health-seo.d.ts.map +1 -1
  29. package/dist/types/components/admin/site-health/site-health-utils.d.ts +17 -0
  30. package/dist/types/components/admin/site-health/site-health-utils.d.ts.map +1 -0
  31. package/dist/types/components/cms/smartimage.d.ts.map +1 -1
  32. package/dist/types/components/sitebuilder/config/ConfigBuilder.d.ts.map +1 -1
  33. package/dist/types/index.adminclient.d.ts +1 -0
  34. package/dist/types/index.adminserver.d.ts +1 -0
  35. package/dist/types/tests/test-seo-logic.d.ts +2 -0
  36. package/dist/types/tests/test-seo-logic.d.ts.map +1 -0
  37. package/package.json +4 -4
@@ -148,16 +148,6 @@
148
148
  "scoreLogic": "present",
149
149
  "displayTemplate": "{{count}} manifest link(s) found"
150
150
  },
151
- "schema-markup": {
152
- "id": "schema-markup",
153
- "title": "Schema Markup",
154
- "description": "Checks for structured data markup",
155
- "scoreDisplayMode": "binary",
156
- "pattern": "(<script[^>]*type=[\"']application/ld\\+json[\"'][^>]*>[^<]*</script>)|(<[^>]*itemtype=[\"'][^\"']*[\"'][^>]*>)",
157
- "countLogic": "count",
158
- "scoreLogic": "present",
159
- "displayTemplate": "{{count}} schema markup element(s) found"
160
- },
161
151
  "twitter-cards": {
162
152
  "id": "twitter-cards",
163
153
  "title": "Twitter Cards",
@@ -239,15 +229,45 @@
239
229
  "scoreLogic": "present",
240
230
  "displayTemplate": "{{count}} pagination link(s) found"
241
231
  },
242
- "local-seo-elements": {
243
- "id": "local-seo-elements",
244
- "title": "Local SEO Elements",
245
- "description": "Checks for local business schema markup",
232
+ "schema-blogposting": {
233
+ "id": "schema-blogposting",
234
+ "title": "BlogPosting Schema",
235
+ "description": "Checks for BlogPosting structured data markup",
246
236
  "scoreDisplayMode": "binary",
247
- "pattern": "(<script[^>]*type=[\"']application/ld\\+json[\"'][^>]*>[^<]*\"@type\"[^<]*\"LocalBusiness\"[^<]*</script>)|(<[^>]*itemtype=[\"'][^\"']*LocalBusiness[^\"']*[\"'][^>]*>)",
248
- "countLogic": "count",
249
- "scoreLogic": "present",
250
- "displayTemplate": "{{count}} local business schema element(s) found"
237
+ "dataCollector": "collectSchemaBlogPostingData",
238
+ "scorer": "calculateSchemaBlogPostingScore"
239
+ },
240
+ "schema-faq": {
241
+ "id": "schema-faq",
242
+ "title": "FAQ Schema",
243
+ "description": "Checks for FAQPage structured data markup",
244
+ "scoreDisplayMode": "binary",
245
+ "dataCollector": "collectSchemaFAQData",
246
+ "scorer": "calculateSchemaFAQScore"
247
+ },
248
+ "schema-localbusiness": {
249
+ "id": "schema-localbusiness",
250
+ "title": "LocalBusiness Schema",
251
+ "description": "Checks for LocalBusiness structured data markup",
252
+ "scoreDisplayMode": "binary",
253
+ "dataCollector": "collectSchemaLocalBusinessData",
254
+ "scorer": "calculateSchemaLocalBusinessScore"
255
+ },
256
+ "schema-services": {
257
+ "id": "schema-services",
258
+ "title": "Service Schema",
259
+ "description": "Checks for Service structured data markup",
260
+ "scoreDisplayMode": "binary",
261
+ "dataCollector": "collectSchemaServicesData",
262
+ "scorer": "calculateSchemaServicesScore"
263
+ },
264
+ "schema-website": {
265
+ "id": "schema-website",
266
+ "title": "WebSite Schema",
267
+ "description": "Checks for WebSite structured data markup",
268
+ "scoreDisplayMode": "binary",
269
+ "dataCollector": "collectSchemaWebsiteData",
270
+ "scorer": "calculateSchemaWebsiteScore"
251
271
  },
252
272
  "amp-validation": {
253
273
  "id": "amp-validation",
@@ -3,7 +3,7 @@ import { jsx as _jsx, jsxs as _jsxs, Fragment as _Fragment } from "react/jsx-run
3
3
  import { useCallback } from 'react';
4
4
  import PropTypes from 'prop-types';
5
5
  import { SiteHealthTemplate } from './site-health-template';
6
- import { getScoreIndicator } from './site-health-indicators';
6
+ import { formatAuditItem, getAuditScoreIcon, getScoreColor } from './site-health-utils';
7
7
  SiteHealthAccessibility.propTypes = {
8
8
  siteName: PropTypes.string.isRequired,
9
9
  };
@@ -17,98 +17,6 @@ export function SiteHealthAccessibility({ siteName }) {
17
17
  return result;
18
18
  }, []);
19
19
  return (_jsx(SiteHealthTemplate, { siteName: siteName, title: "PageSpeed - Accessibility", fetchData: fetchAccessibilityData, children: (data) => {
20
- const getScoreColor = (score) => {
21
- return getScoreIndicator(score).color;
22
- };
23
- const getAuditScoreIcon = (score) => {
24
- return getScoreIndicator(score).icon;
25
- };
26
- // Helper function to display audit item details
27
- const formatAuditItem = (item, auditTitle) => {
28
- // Handle URLs
29
- if (item.url && typeof item.url === 'string') {
30
- return item.url;
31
- }
32
- // Handle sources (like JavaScript files)
33
- if (item.source && typeof item.source === 'string') {
34
- return item.source;
35
- }
36
- // Handle text descriptions
37
- if (item.text && typeof item.text === 'string') {
38
- return item.text;
39
- }
40
- // Handle entities (like "Google Tag Manager")
41
- if (item.entity && typeof item.entity === 'string') {
42
- return item.entity;
43
- }
44
- // Handle nodes with selectors
45
- if (item.node && typeof item.node === 'object' && 'selector' in item.node) {
46
- return `Element: ${item.node.selector}`;
47
- }
48
- // Handle nodes with snippets
49
- if (item.node && typeof item.node === 'object' && 'snippet' in item.node) {
50
- const snippet = item.node.snippet;
51
- return `Element: ${snippet.length > 50 ? snippet.substring(0, 50) + '...' : snippet}`;
52
- }
53
- // Handle origins (like domains)
54
- if (item.origin && typeof item.origin === 'string') {
55
- return item.origin;
56
- }
57
- // Handle labels
58
- if (item.label && typeof item.label === 'string') {
59
- return item.label;
60
- }
61
- // Handle numeric values with units
62
- if (item.value && typeof item.value === 'object' && 'type' in item.value && item.value.type === 'numeric') {
63
- const value = item.value;
64
- return `${value.value}${item.unit || ''}`;
65
- }
66
- // Handle statistics
67
- if (item.statistic && typeof item.statistic === 'string' && item.value) {
68
- if (typeof item.value === 'object' && 'type' in item.value && item.value.type === 'numeric') {
69
- const value = item.value;
70
- return `${item.statistic}: ${value.value}`;
71
- }
72
- return item.statistic;
73
- }
74
- // Handle timing data with audit context
75
- if (typeof item === 'number') {
76
- let context = '';
77
- if (auditTitle) {
78
- if (auditTitle.toLowerCase().includes('server') || auditTitle.toLowerCase().includes('backend')) {
79
- context = ' server response';
80
- }
81
- else if (auditTitle.toLowerCase().includes('network') || auditTitle.toLowerCase().includes('request')) {
82
- context = ' network request';
83
- }
84
- else if (auditTitle.toLowerCase().includes('render') || auditTitle.toLowerCase().includes('blocking')) {
85
- context = ' render blocking';
86
- }
87
- else if (auditTitle.toLowerCase().includes('javascript') || auditTitle.toLowerCase().includes('js')) {
88
- context = ' JavaScript';
89
- }
90
- else if (auditTitle.toLowerCase().includes('image') || auditTitle.toLowerCase().includes('media')) {
91
- context = ' media resource';
92
- }
93
- }
94
- return `${item.toFixed(2)}ms${context}`;
95
- }
96
- if (item.value && typeof item.value === 'number') {
97
- const unit = item.unit || 'ms';
98
- let context = '';
99
- if (auditTitle && unit === 'ms') {
100
- if (auditTitle.toLowerCase().includes('server')) {
101
- context = ' server time';
102
- }
103
- else if (auditTitle.toLowerCase().includes('network')) {
104
- context = ' network time';
105
- }
106
- }
107
- return `${item.value.toFixed(2)}${unit}${context}`;
108
- }
109
- // If we can't find anything meaningful, show a generic message
110
- return 'Details available';
111
- };
112
20
  if (!data?.data || data.data.length === 0) {
113
21
  return (_jsx("p", { style: { color: '#6b7280' }, children: "No accessibility data available for this site." }));
114
22
  }
@@ -119,7 +27,7 @@ export function SiteHealthAccessibility({ siteName }) {
119
27
  return (_jsxs(_Fragment, { children: [_jsx("h4", { className: "health-site-name", children: siteData.site.replace('-', ' ') }), _jsxs("p", { className: "health-site-url", children: ["URL: ", siteData.url] }), siteData.scores.accessibility !== null && (_jsx("div", { className: "health-score-container", children: _jsxs("div", { className: "health-score-item", children: [_jsx("div", { className: "health-score-label", children: "Accessibility Score" }), _jsxs("div", { className: "health-score-value", style: { color: getScoreColor(siteData.scores.accessibility) }, children: [Math.round((siteData.scores.accessibility || 0) * 100), "%"] }), _jsx("div", { className: "health-score-bar", children: _jsx("div", { className: "health-score-fill", style: {
120
28
  width: `${(siteData.scores.accessibility || 0) * 100}%`,
121
29
  backgroundColor: getScoreColor(siteData.scores.accessibility)
122
- } }) })] }) })), siteData.categories.accessibility && siteData.categories.accessibility.audits.length > 0 && (_jsxs("div", { children: [_jsx("h5", { style: { fontSize: '1rem', fontWeight: '600', marginBottom: '1rem' }, children: "Accessibility Issues & Recommendations" }), _jsx("div", { className: "space-y-2", children: siteData.categories.accessibility.audits
30
+ } }) })] }) })), siteData.categories.accessibility && siteData.categories.accessibility.audits.length > 0 && (_jsxs("div", { children: [_jsx("h5", { style: { fontSize: '1rem', fontWeight: '600', marginBottom: '1rem' }, children: "Accessibility Issues & Recommendations" }), _jsx("div", { className: "health-audit-list", children: siteData.categories.accessibility.audits
123
31
  .filter((audit) => audit.scoreDisplayMode !== 'notApplicable')
124
32
  .sort((a, b) => {
125
33
  // Prioritize specific important accessibility audits
@@ -43,13 +43,13 @@ export function SiteHealthAxeCore({ siteName }) {
43
43
  return (_jsxs("p", { style: { color: '#ef4444', fontSize: '0.875rem' }, children: ["Error: ", siteData.error] }));
44
44
  }
45
45
  const { result, summary } = siteData;
46
- return (_jsxs(_Fragment, { children: [_jsx("h4", { className: "health-site-name", children: siteData.site.replace('-', ' ') }), _jsxs("p", { className: "health-site-url", children: ["URL: ", siteData.url] }), _jsx("div", { className: "health-score-container", children: _jsxs("div", { className: "health-score-item", children: [_jsx("div", { className: "health-score-label", children: "Accessibility Summary" }), _jsxs("div", { className: "health-score-grid", children: [_jsxs("div", { className: "health-stat-item", children: [_jsx("span", { className: "health-stat-label", children: "Violations : " }), _jsx("span", { className: "health-stat-value", style: { color: summary.violations > 0 ? '#ef4444' : '#10b981' }, children: summary.violations })] }), _jsxs("div", { className: "health-stat-item", children: [_jsx("span", { className: "health-stat-label", children: "Passes : " }), _jsx("span", { className: "health-stat-value", style: { color: '#10b981' }, children: summary.passes })] }), _jsxs("div", { className: "health-stat-item", children: [_jsx("span", { className: "health-stat-label", children: "Incomplete : " }), _jsx("span", { className: "health-stat-value", style: { color: '#f59e0b' }, children: summary.incomplete })] })] })] }) }), summary.violations > 0 && (_jsx("div", { className: "health-score-container", children: _jsxs("div", { className: "health-score-item", children: [_jsx("div", { className: "health-score-label", children: "Violation Impact Levels" }), _jsxs("div", { className: "health-score-grid", children: [_jsxs("div", { className: "health-stat-item", children: [_jsx("span", { className: "health-stat-label", children: "Critical : " }), _jsx("span", { className: "health-stat-value", style: { color: getImpactColor('critical') }, children: summary.critical })] }), _jsxs("div", { className: "health-stat-item", children: [_jsx("span", { className: "health-stat-label", children: "Serious : " }), _jsx("span", { className: "health-stat-value", style: { color: getImpactColor('serious') }, children: summary.serious })] }), _jsxs("div", { className: "health-stat-item", children: [_jsx("span", { className: "health-stat-label", children: "Moderate : " }), _jsx("span", { className: "health-stat-value", style: { color: getImpactColor('moderate') }, children: summary.moderate })] }), _jsxs("div", { className: "health-stat-item", children: [_jsx("span", { className: "health-stat-label", children: "Minor : " }), _jsx("span", { className: "health-stat-value", style: { color: getImpactColor('minor') }, children: summary.minor })] })] })] }) })), result.violations.length > 0 && (_jsxs("div", { children: [_jsx("h5", { style: { fontSize: '1rem', fontWeight: '600', marginBottom: '1rem' }, children: "Accessibility Violations" }), _jsx("div", { className: "space-y-2", children: result.violations
46
+ return (_jsxs(_Fragment, { children: [_jsx("h4", { className: "health-site-name", children: siteData.site.replace('-', ' ') }), _jsxs("p", { className: "health-site-url", children: ["URL: ", siteData.url] }), _jsx("div", { className: "health-score-container", children: _jsxs("div", { className: "health-score-item", children: [_jsx("div", { className: "health-score-label", children: "Accessibility Summary" }), _jsxs("div", { className: "health-score-grid", children: [_jsxs("div", { className: "health-stat-item", children: [_jsx("span", { className: "health-stat-label", children: "Violations : " }), _jsx("span", { className: "health-stat-value", style: { color: summary.violations > 0 ? '#ef4444' : '#10b981' }, children: summary.violations })] }), _jsxs("div", { className: "health-stat-item", children: [_jsx("span", { className: "health-stat-label", children: "Passes : " }), _jsx("span", { className: "health-stat-value", style: { color: '#10b981' }, children: summary.passes })] }), _jsxs("div", { className: "health-stat-item", children: [_jsx("span", { className: "health-stat-label", children: "Incomplete : " }), _jsx("span", { className: "health-stat-value", style: { color: '#f59e0b' }, children: summary.incomplete })] })] })] }) }), summary.violations > 0 && (_jsx("div", { className: "health-score-container", children: _jsxs("div", { className: "health-score-item", children: [_jsx("div", { className: "health-score-label", children: "Violation Impact Levels" }), _jsxs("div", { className: "health-score-grid", children: [_jsxs("div", { className: "health-stat-item", children: [_jsx("span", { className: "health-stat-label", children: "Critical : " }), _jsx("span", { className: "health-stat-value", style: { color: getImpactColor('critical') }, children: summary.critical })] }), _jsxs("div", { className: "health-stat-item", children: [_jsx("span", { className: "health-stat-label", children: "Serious : " }), _jsx("span", { className: "health-stat-value", style: { color: getImpactColor('serious') }, children: summary.serious })] }), _jsxs("div", { className: "health-stat-item", children: [_jsx("span", { className: "health-stat-label", children: "Moderate : " }), _jsx("span", { className: "health-stat-value", style: { color: getImpactColor('moderate') }, children: summary.moderate })] }), _jsxs("div", { className: "health-stat-item", children: [_jsx("span", { className: "health-stat-label", children: "Minor : " }), _jsx("span", { className: "health-stat-value", style: { color: getImpactColor('minor') }, children: summary.minor })] })] })] }) })), result.violations.length > 0 && (_jsxs("div", { children: [_jsx("h5", { style: { fontSize: '1rem', fontWeight: '600', marginBottom: '1rem' }, children: "Accessibility Violations" }), _jsx("div", { className: "health-audit-list", children: result.violations
47
47
  .sort((a, b) => {
48
48
  const impactOrder = { critical: 4, serious: 3, moderate: 2, minor: 1 };
49
49
  return impactOrder[b.impact] - impactOrder[a.impact];
50
50
  })
51
51
  .slice(0, 20)
52
- .map((violation) => (_jsxs("div", { className: "health-audit-item", children: [_jsx("span", { className: "health-audit-icon", children: getImpactIcon(violation.impact) }), _jsxs("div", { className: "health-audit-content", children: [_jsxs("span", { className: "health-audit-title", children: [violation.help, " (", violation.impact, ")"] }), _jsx("p", { className: "health-audit-description", children: violation.description }), violation.nodes && violation.nodes.length > 0 && (_jsx("div", { className: "health-audit-details", children: _jsxs("div", { style: { fontSize: '0.75rem', color: '#6b7280', marginTop: '0.25rem' }, children: ["Affected elements (", violation.nodes.length, "):", violation.nodes.map((node, idx) => (_jsx("div", { style: { marginBottom: '0.125rem' }, children: formatNodeInfo(node) }, idx)))] }) })), _jsx("div", { style: { fontSize: '0.75rem', color: '#6b7280', marginTop: '0.25rem' }, children: _jsx("a", { href: violation.helpUrl, target: "_blank", rel: "noopener noreferrer", style: { color: '#3b82f6', textDecoration: 'underline' }, children: "Learn more about this rule" }) })] })] }, violation.id))) })] })), result.passes.length > 0 && result.violations.length === 0 && (_jsxs("div", { children: [_jsxs("h5", { style: { fontSize: '1rem', fontWeight: '600', marginBottom: '1rem', color: '#10b981' }, children: [getPassingIndicator().icon, " All Accessibility Checks Passed"] }), _jsxs("p", { style: { color: '#6b7280', fontSize: '0.875rem' }, children: [result.passes.length, " accessibility rules were successfully validated."] })] })), result.incomplete.length > 0 && (_jsxs("div", { style: { marginTop: '15px' }, children: [_jsxs("h5", { style: { fontSize: '1rem', fontWeight: '600', marginBottom: '1rem', color: '#f59e0b' }, children: ["Incomplete Tests (", result.incomplete.length, ")"] }), _jsx("div", { className: "space-y-2", children: result.incomplete
52
+ .map((violation) => (_jsxs("div", { className: "health-audit-item", children: [_jsx("span", { className: "health-audit-icon", children: getImpactIcon(violation.impact) }), _jsxs("div", { className: "health-audit-content", children: [_jsxs("span", { className: "health-audit-title", children: [violation.help, " (", violation.impact, ")"] }), _jsx("p", { className: "health-audit-description", children: violation.description }), violation.nodes && violation.nodes.length > 0 && (_jsx("div", { className: "health-audit-details", children: _jsxs("div", { style: { fontSize: '0.75rem', color: '#6b7280', marginTop: '0.25rem' }, children: ["Affected elements (", violation.nodes.length, "):", violation.nodes.map((node, idx) => (_jsx("div", { style: { marginBottom: '0.125rem' }, children: formatNodeInfo(node) }, idx)))] }) })), _jsx("div", { style: { fontSize: '0.75rem', color: '#6b7280', marginTop: '0.25rem' }, children: _jsx("a", { href: violation.helpUrl, target: "_blank", rel: "noopener noreferrer", style: { color: '#3b82f6', textDecoration: 'underline' }, children: "Learn more about this rule" }) })] })] }, violation.id))) })] })), result.passes.length > 0 && result.violations.length === 0 && (_jsxs("div", { children: [_jsxs("h5", { style: { fontSize: '1rem', fontWeight: '600', marginBottom: '1rem', color: '#10b981' }, children: [getPassingIndicator().icon, " All Accessibility Checks Passed"] }), _jsxs("p", { style: { color: '#6b7280', fontSize: '0.875rem' }, children: [result.passes.length, " accessibility rules were successfully validated."] })] })), result.incomplete.length > 0 && (_jsxs("div", { style: { marginTop: '15px' }, children: [_jsxs("h5", { style: { fontSize: '1rem', fontWeight: '600', marginBottom: '1rem', color: '#f59e0b' }, children: ["Incomplete Tests (", result.incomplete.length, ")"] }), _jsx("div", { className: "health-audit-list", children: result.incomplete
53
53
  .sort((a, b) => a.id.localeCompare(b.id))
54
54
  .slice(0, 10)
55
55
  .map((incomplete) => (_jsxs("div", { className: "health-audit-item", children: [_jsx("span", { className: "health-audit-icon", children: getIncompleteIndicator().icon }), _jsxs("div", { className: "health-audit-content", children: [_jsx("span", { className: "health-audit-title", children: incomplete.help }), _jsx("p", { className: "health-audit-description", children: incomplete.description }), incomplete.nodes && incomplete.nodes.length > 0 && (_jsx("div", { className: "health-audit-details", children: _jsxs("div", { style: { fontSize: '0.75rem', color: '#6b7280', marginTop: '0.25rem' }, children: ["Elements tested (", incomplete.nodes.length, "):", incomplete.nodes.slice(0, 3).map((node, idx) => (_jsx("div", { style: { marginBottom: '0.125rem' }, children: formatNodeInfo(node) }, idx))), incomplete.nodes.length > 3 && (_jsxs("div", { style: { marginTop: '0.25rem', fontStyle: 'italic' }, children: ["... and ", incomplete.nodes.length - 3, " more elements"] }))] }) })), _jsx("div", { style: { fontSize: '0.75rem', color: '#6b7280', marginTop: '0.25rem' }, children: _jsx("a", { href: incomplete.helpUrl, target: "_blank", rel: "noopener noreferrer", style: { color: '#3b82f6', textDecoration: 'underline' }, children: "Learn more about this rule" }) })] })] }, incomplete.id))) })] })), _jsxs("div", { className: "health-timestamp", children: [_jsxs("div", { children: ["Tested with axe-core ", result.testEngine?.version || 'unknown'] }), _jsxs("div", { children: ["Last checked: ", new Date(siteData.timestamp).toLocaleString()] })] })] }));
@@ -32,12 +32,12 @@ export function SiteHealthCloudwatch({ siteName, startDate, endDate }) {
32
32
  };
33
33
  return (_jsx(SiteHealthTemplate, { siteName: siteName, title: "CloudWatch Uptime", columnSpan: 2, fetchData: fetchCloudwatchData, children: (data) => {
34
34
  if (!data || data.length === 0) {
35
- return (_jsx("div", { className: "flex items-center justify-center h-64", children: _jsx("div", { className: "text-gray-500", children: "No uptime data available. Route53 health checks may not be configured to send metrics to CloudWatch." }) }));
35
+ return (_jsx("div", { className: "health-visualization-placeholder", children: _jsx("div", { className: "health-text-secondary", children: "No uptime data available. Route53 health checks may not be configured to send metrics to CloudWatch." }) }));
36
36
  }
37
37
  // Check if all data points have zero checks (no actual data)
38
38
  const hasActualData = data.some((point) => point.totalChecks > 0);
39
39
  if (!hasActualData) {
40
- return (_jsx("div", { className: "flex items-center justify-center h-64", children: _jsxs("div", { className: "text-gray-500", children: ["Health check exists but has no metric data in CloudWatch for the selected period.", _jsx("br", {}), "Route53 health checks must be configured to send metrics to CloudWatch for historical data."] }) }));
40
+ return (_jsx("div", { className: "health-visualization-placeholder", children: _jsxs("div", { className: "health-text-secondary", children: ["Health check exists but has no metric data in CloudWatch for the selected period.", _jsx("br", {}), "Route53 health checks must be configured to send metrics to CloudWatch for historical data."] }) }));
41
41
  }
42
42
  return (_jsx("div", { children: _jsx("div", { style: { width: '100%', height: '400px', border: '1px solid #ddd' }, children: _jsx(ResponsiveContainer, { width: "100%", height: "100%", children: _jsxs(ComposedChart, { data: data, margin: { top: 40, right: 30, left: 20, bottom: 5 }, children: [_jsx("text", { x: "50%", y: 20, textAnchor: "middle", fontSize: "16", fontWeight: "bold", fill: "#374151", children: "CloudWatch Health Check Availability Over Time" }), _jsx(CartesianGrid, { strokeDasharray: "3 3" }), _jsx(XAxis, { dataKey: "date", tick: { fontSize: 12 }, angle: -45, textAnchor: "end", height: 60 }), _jsx(YAxis, { tick: { fontSize: 12 }, label: { value: 'Check Count', angle: -90, position: 'insideLeft' } }), _jsx(Tooltip, { formatter: (value, name) => [
43
43
  value?.toLocaleString() || '0',
@@ -37,6 +37,6 @@ export function SiteHealthDependencyVulnerabilities({ siteName }) {
37
37
  data.status === 'Moderate Risk' ? '#f59e0b' :
38
38
  data.status === 'High Risk' ? '#ef4444' :
39
39
  data.status === 'Critical' ? '#ef4444' : '#6b7280'
40
- } }) })] }) }), _jsxs("div", { className: "health-audit-item", children: [_jsx("span", { className: "health-audit-icon", style: { color: '#10b981' }, children: "\u2713" }), _jsx("div", { className: "health-audit-content", children: _jsxs("span", { className: "health-audit-title", children: ["Dependencies: ", data.totalDependencies || data.dependencies || 0] }) })] }), data.vulnerabilities && data.vulnerabilities.length > 0 && (_jsxs("div", { children: [_jsxs("h5", { style: { fontSize: '1rem', fontWeight: '600', marginBottom: '1rem' }, children: ["Vulnerabilities (", data.summary.total, ")"] }), _jsx("div", { className: "space-y-2", children: data.vulnerabilities.map((vuln, index) => (_jsx("div", { className: `health-vulnerability-item health-vulnerability-${vuln.severity}`, children: _jsxs("div", { className: "health-vulnerability-header", children: [_jsx("span", { className: "health-vulnerability-severity", children: vuln.severity }), _jsxs("div", { children: [_jsx("span", { className: "health-vulnerability-name", children: vuln.name }), vuln.title && (_jsx("p", { className: "health-vulnerability-details", children: vuln.title })), _jsxs("div", { className: "health-vulnerability-meta", children: [_jsxs("span", { className: "health-vulnerability-range", children: ["Range: ", vuln.range] }), vuln.fixAvailable && (_jsx("span", { className: "health-vulnerability-fix", children: "\u2713 Fix available" }))] }), vuln.url && (_jsx("a", { href: vuln.url, target: "_blank", rel: "noopener noreferrer", className: "health-vulnerability-link", children: "View details \u2192" }))] })] }) }, index))) })] })), (!data.vulnerabilities || data.vulnerabilities.length === 0) && data.status === 'Secure' && (_jsxs("div", { className: "health-audit-item", children: [_jsx("span", { className: "health-audit-icon", style: { color: '#10b981' }, children: "\u2713" }), _jsx("div", { className: "health-audit-content", children: _jsx("span", { className: "health-audit-title", children: "No vulnerabilities found" }) })] })), _jsxs("p", { className: "health-timestamp", children: ["Last checked: ", new Date(data.timestamp).toLocaleString()] })] }));
40
+ } }) })] }) }), _jsxs("div", { className: "health-audit-item", children: [_jsx("span", { className: "health-audit-icon", style: { color: '#10b981' }, children: "\u2713" }), _jsx("div", { className: "health-audit-content", children: _jsxs("span", { className: "health-audit-title", children: ["Dependencies: ", data.totalDependencies || data.dependencies || 0] }) })] }), data.vulnerabilities && data.vulnerabilities.length > 0 && (_jsxs("div", { children: [_jsxs("h5", { style: { fontSize: '1rem', fontWeight: '600', marginBottom: '1rem' }, children: ["Vulnerabilities (", data.summary.total, ")"] }), _jsx("div", { className: "health-audit-list", children: data.vulnerabilities.map((vuln, index) => (_jsx("div", { className: `health-vulnerability-item health-vulnerability-${vuln.severity}`, children: _jsxs("div", { className: "health-vulnerability-header", children: [_jsx("span", { className: "health-vulnerability-severity", children: vuln.severity }), _jsxs("div", { children: [_jsx("span", { className: "health-vulnerability-name", children: vuln.name }), vuln.title && (_jsx("p", { className: "health-vulnerability-details", children: vuln.title })), _jsxs("div", { className: "health-vulnerability-meta", children: [_jsxs("span", { className: "health-vulnerability-range", children: ["Range: ", vuln.range] }), vuln.fixAvailable && (_jsx("span", { className: "health-vulnerability-fix", children: "\u2713 Fix available" }))] }), vuln.url && (_jsx("a", { href: vuln.url, target: "_blank", rel: "noopener noreferrer", className: "health-vulnerability-link", children: "View details \u2192" }))] })] }) }, index))) })] })), (!data.vulnerabilities || data.vulnerabilities.length === 0) && data.status === 'Secure' && (_jsxs("div", { className: "health-audit-item", children: [_jsx("span", { className: "health-audit-icon", style: { color: '#10b981' }, children: "\u2713" }), _jsx("div", { className: "health-audit-content", children: _jsx("span", { className: "health-audit-title", children: "No vulnerabilities found" }) })] })), _jsxs("p", { className: "health-timestamp", children: ["Last checked: ", new Date(data.timestamp).toLocaleString()] })] }));
41
41
  } }));
42
42
  }
@@ -32,9 +32,9 @@ export function SiteHealthGit({ siteName, startDate, endDate }) {
32
32
  // Prepare table data
33
33
  const tableData = (data.commits || []).map((commit) => ({
34
34
  Date: new Date(commit.date).toLocaleDateString(),
35
- Message: _jsx("span", { className: "max-w-xs truncate inline-block", title: commit.message, children: commit.message }),
36
- Version: commit.version ? (_jsx("span", { className: "px-2 py-1 text-xs bg-green-100 text-green-800 rounded", children: commit.version.split('~')[0] })) : (_jsx("span", { className: "text-gray-400", children: "-" }))
35
+ Message: _jsx("span", { title: commit.message, children: commit.message }),
36
+ Version: commit.version ? (_jsx("span", { className: "health-version-tag", children: commit.version.split('~')[0] })) : (_jsx("span", { className: "health-text-muted", children: "-" }))
37
37
  }));
38
- return (_jsxs(_Fragment, { children: [_jsx("h4", { className: "health-site-name", children: siteName.replace('-', ' ') }), _jsx("div", { className: "space-y-4", children: tableData.length === 0 ? (_jsx("p", { className: "text-gray-500 text-center py-4", children: "No recent commits found" })) : (_jsx(Table, { id: "git-table", data: tableData, altRowColor: "#DDD" })) }), _jsxs("p", { className: "health-timestamp", children: ["Last checked: ", new Date(data.timestamp).toLocaleString()] })] }));
38
+ return (_jsxs(_Fragment, { children: [_jsx("h4", { className: "health-site-name", children: siteName.replace('-', ' ') }), _jsx("div", { className: "health-section-list", children: tableData.length === 0 ? (_jsx("p", { className: "health-empty-state", children: "No recent commits found" })) : (_jsx(Table, { id: "git-table", data: tableData, altRowColor: "#DDD" })) }), _jsxs("p", { className: "health-timestamp", children: ["Last checked: ", new Date(data.timestamp).toLocaleString()] })] }));
39
39
  } }));
40
40
  }
@@ -36,7 +36,7 @@ export function SiteHealthGoogleAnalytics({ siteName, startDate, endDate }) {
36
36
  };
37
37
  return (_jsx(SiteHealthTemplate, { siteName: siteName, title: "Google Analytics", columnSpan: 2, fetchData: fetchAnalyticsData, children: (data) => {
38
38
  if (!data || data.length === 0) {
39
- return (_jsx("div", { className: "flex items-center justify-center h-64", children: _jsx("div", { className: "text-gray-500", children: "No data available for the selected date range" }) }));
39
+ return (_jsx("div", { className: "health-visualization-placeholder", children: _jsx("div", { className: "health-text-secondary", children: "No data available for the selected date range" }) }));
40
40
  }
41
41
  return (_jsx("div", { children: _jsx("div", { style: { width: '100%', height: '400px', border: '1px solid #ddd' }, children: _jsx(ResponsiveContainer, { width: "100%", height: "100%", children: _jsxs(ComposedChart, { data: data, margin: { top: 40, right: 30, left: 20, bottom: 5 }, children: [_jsx("text", { x: "50%", y: 20, textAnchor: "middle", fontSize: "16", fontWeight: "bold", fill: "#374151", children: "Page Views (Current vs Previous Period)" }), _jsx(CartesianGrid, { strokeDasharray: "3 3" }), _jsx(XAxis, { dataKey: "date", tick: { fontSize: 12 }, angle: -45, textAnchor: "end", height: 60 }), _jsx(YAxis, { tick: { fontSize: 12 } }), _jsx(Tooltip, { formatter: (value, name) => [
42
42
  value?.toLocaleString() || '0',
@@ -36,7 +36,7 @@ export function SiteHealthGoogleSearchConsole({ siteName, startDate, endDate })
36
36
  };
37
37
  return (_jsx(SiteHealthTemplate, { siteName: siteName, title: "Google Search Console", columnSpan: 2, fetchData: fetchSearchConsoleData, children: (data) => {
38
38
  if (!data || data.length === 0) {
39
- return (_jsx("div", { className: "flex items-center justify-center h-64", children: _jsx("div", { className: "text-gray-500", children: "No indexing data available for the selected date range" }) }));
39
+ return (_jsx("div", { className: "health-visualization-placeholder", children: _jsx("div", { className: "health-text-secondary", children: "No indexing data available for the selected date range" }) }));
40
40
  }
41
41
  return (_jsx("div", { children: _jsx("div", { style: { width: '100%', height: '400px', border: '1px solid #ddd' }, children: _jsx(ResponsiveContainer, { width: "100%", height: "100%", children: _jsxs(ComposedChart, { data: data, margin: { top: 40, right: 30, left: 20, bottom: 5 }, children: [_jsx("text", { x: "50%", y: 20, textAnchor: "middle", fontSize: "16", fontWeight: "bold", fill: "#374151", children: "Impressions vs Clicks (Current vs Previous Period)" }), _jsx(CartesianGrid, { strokeDasharray: "3 3" }), _jsx(XAxis, { dataKey: "date", tick: { fontSize: 12 }, angle: -45, textAnchor: "end", height: 60 }), _jsx(YAxis, { tick: { fontSize: 12 } }), _jsx(Tooltip, { formatter: (value, name) => [
42
42
  value?.toLocaleString() || '0',