@sonicjs-cms/core 2.3.0 → 2.3.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/{chunk-HBJU3I2Y.cjs → chunk-23VPL6VI.cjs} +278 -2
- package/dist/chunk-23VPL6VI.cjs.map +1 -0
- package/dist/{chunk-CAMM3MJV.js → chunk-3MPQII4R.js} +278 -2
- package/dist/chunk-3MPQII4R.js.map +1 -0
- package/dist/{chunk-TT266RYM.cjs → chunk-44LBCF3B.cjs} +3 -3
- package/dist/{chunk-TT266RYM.cjs.map → chunk-44LBCF3B.cjs.map} +1 -1
- package/dist/{chunk-MPFSSBIY.cjs → chunk-5QJX2VMP.cjs} +90 -90
- package/dist/{chunk-MPFSSBIY.cjs.map → chunk-5QJX2VMP.cjs.map} +1 -1
- package/dist/{chunk-KP4DVEX5.cjs → chunk-5UUYHAZT.cjs} +4 -4
- package/dist/{chunk-KP4DVEX5.cjs.map → chunk-5UUYHAZT.cjs.map} +1 -1
- package/dist/{chunk-4C433FET.js → chunk-6RJU7HL5.js} +3 -3
- package/dist/{chunk-4C433FET.js.map → chunk-6RJU7HL5.js.map} +1 -1
- package/dist/{chunk-5TRX2JHU.js → chunk-WK5EUGBO.js} +3 -3
- package/dist/{chunk-5TRX2JHU.js.map → chunk-WK5EUGBO.js.map} +1 -1
- package/dist/{chunk-3ZLCMOCM.js → chunk-ZPERJATF.js} +8 -8
- package/dist/{chunk-3ZLCMOCM.js.map → chunk-ZPERJATF.js.map} +1 -1
- package/dist/index.cjs +74 -74
- package/dist/index.js +7 -7
- package/dist/middleware.cjs +23 -23
- package/dist/middleware.js +2 -2
- package/dist/migrations-CCLAGJGP.js +4 -0
- package/dist/{migrations-B2CDNN76.js.map → migrations-CCLAGJGP.js.map} +1 -1
- package/dist/migrations-O6INOHRD.cjs +13 -0
- package/dist/{migrations-IBKKBIKR.cjs.map → migrations-O6INOHRD.cjs.map} +1 -1
- package/dist/routes.cjs +24 -24
- package/dist/routes.js +4 -4
- package/dist/services.cjs +2 -2
- package/dist/services.js +1 -1
- package/dist/utils.cjs +11 -11
- package/dist/utils.js +1 -1
- package/migrations/002_faq_plugin.sql +86 -0
- package/migrations/013_code_examples_plugin.sql +177 -0
- package/package.json +1 -1
- package/dist/chunk-CAMM3MJV.js.map +0 -1
- package/dist/chunk-HBJU3I2Y.cjs.map +0 -1
- package/dist/migrations-B2CDNN76.js +0 -4
- package/dist/migrations-IBKKBIKR.cjs +0 -13
package/dist/routes.cjs
CHANGED
|
@@ -1,12 +1,12 @@
|
|
|
1
1
|
'use strict';
|
|
2
2
|
|
|
3
|
-
var
|
|
3
|
+
var chunk5QJX2VMP_cjs = require('./chunk-5QJX2VMP.cjs');
|
|
4
4
|
require('./chunk-ES3BRZQJ.cjs');
|
|
5
|
-
require('./chunk-
|
|
5
|
+
require('./chunk-5UUYHAZT.cjs');
|
|
6
6
|
require('./chunk-NAYD76QF.cjs');
|
|
7
|
-
require('./chunk-
|
|
7
|
+
require('./chunk-23VPL6VI.cjs');
|
|
8
8
|
require('./chunk-YU6QFFI4.cjs');
|
|
9
|
-
require('./chunk-
|
|
9
|
+
require('./chunk-44LBCF3B.cjs');
|
|
10
10
|
require('./chunk-7KCDFDRI.cjs');
|
|
11
11
|
require('./chunk-RCQ2HIQD.cjs');
|
|
12
12
|
require('./chunk-IGJUBJBW.cjs');
|
|
@@ -15,83 +15,83 @@ require('./chunk-IGJUBJBW.cjs');
|
|
|
15
15
|
|
|
16
16
|
Object.defineProperty(exports, "ROUTES_INFO", {
|
|
17
17
|
enumerable: true,
|
|
18
|
-
get: function () { return
|
|
18
|
+
get: function () { return chunk5QJX2VMP_cjs.ROUTES_INFO; }
|
|
19
19
|
});
|
|
20
20
|
Object.defineProperty(exports, "adminApiRoutes", {
|
|
21
21
|
enumerable: true,
|
|
22
|
-
get: function () { return
|
|
22
|
+
get: function () { return chunk5QJX2VMP_cjs.admin_api_default; }
|
|
23
23
|
});
|
|
24
24
|
Object.defineProperty(exports, "adminCheckboxRoutes", {
|
|
25
25
|
enumerable: true,
|
|
26
|
-
get: function () { return
|
|
26
|
+
get: function () { return chunk5QJX2VMP_cjs.adminCheckboxRoutes; }
|
|
27
27
|
});
|
|
28
28
|
Object.defineProperty(exports, "adminCodeExamplesRoutes", {
|
|
29
29
|
enumerable: true,
|
|
30
|
-
get: function () { return
|
|
30
|
+
get: function () { return chunk5QJX2VMP_cjs.admin_code_examples_default; }
|
|
31
31
|
});
|
|
32
32
|
Object.defineProperty(exports, "adminCollectionsRoutes", {
|
|
33
33
|
enumerable: true,
|
|
34
|
-
get: function () { return
|
|
34
|
+
get: function () { return chunk5QJX2VMP_cjs.adminCollectionsRoutes; }
|
|
35
35
|
});
|
|
36
36
|
Object.defineProperty(exports, "adminContentRoutes", {
|
|
37
37
|
enumerable: true,
|
|
38
|
-
get: function () { return
|
|
38
|
+
get: function () { return chunk5QJX2VMP_cjs.admin_content_default; }
|
|
39
39
|
});
|
|
40
40
|
Object.defineProperty(exports, "adminDashboardRoutes", {
|
|
41
41
|
enumerable: true,
|
|
42
|
-
get: function () { return
|
|
42
|
+
get: function () { return chunk5QJX2VMP_cjs.router; }
|
|
43
43
|
});
|
|
44
44
|
Object.defineProperty(exports, "adminDesignRoutes", {
|
|
45
45
|
enumerable: true,
|
|
46
|
-
get: function () { return
|
|
46
|
+
get: function () { return chunk5QJX2VMP_cjs.adminDesignRoutes; }
|
|
47
47
|
});
|
|
48
48
|
Object.defineProperty(exports, "adminLogsRoutes", {
|
|
49
49
|
enumerable: true,
|
|
50
|
-
get: function () { return
|
|
50
|
+
get: function () { return chunk5QJX2VMP_cjs.adminLogsRoutes; }
|
|
51
51
|
});
|
|
52
52
|
Object.defineProperty(exports, "adminMediaRoutes", {
|
|
53
53
|
enumerable: true,
|
|
54
|
-
get: function () { return
|
|
54
|
+
get: function () { return chunk5QJX2VMP_cjs.adminMediaRoutes; }
|
|
55
55
|
});
|
|
56
56
|
Object.defineProperty(exports, "adminPluginRoutes", {
|
|
57
57
|
enumerable: true,
|
|
58
|
-
get: function () { return
|
|
58
|
+
get: function () { return chunk5QJX2VMP_cjs.adminPluginRoutes; }
|
|
59
59
|
});
|
|
60
60
|
Object.defineProperty(exports, "adminSettingsRoutes", {
|
|
61
61
|
enumerable: true,
|
|
62
|
-
get: function () { return
|
|
62
|
+
get: function () { return chunk5QJX2VMP_cjs.adminSettingsRoutes; }
|
|
63
63
|
});
|
|
64
64
|
Object.defineProperty(exports, "adminTestimonialsRoutes", {
|
|
65
65
|
enumerable: true,
|
|
66
|
-
get: function () { return
|
|
66
|
+
get: function () { return chunk5QJX2VMP_cjs.admin_testimonials_default; }
|
|
67
67
|
});
|
|
68
68
|
Object.defineProperty(exports, "adminUsersRoutes", {
|
|
69
69
|
enumerable: true,
|
|
70
|
-
get: function () { return
|
|
70
|
+
get: function () { return chunk5QJX2VMP_cjs.userRoutes; }
|
|
71
71
|
});
|
|
72
72
|
Object.defineProperty(exports, "apiContentCrudRoutes", {
|
|
73
73
|
enumerable: true,
|
|
74
|
-
get: function () { return
|
|
74
|
+
get: function () { return chunk5QJX2VMP_cjs.api_content_crud_default; }
|
|
75
75
|
});
|
|
76
76
|
Object.defineProperty(exports, "apiMediaRoutes", {
|
|
77
77
|
enumerable: true,
|
|
78
|
-
get: function () { return
|
|
78
|
+
get: function () { return chunk5QJX2VMP_cjs.api_media_default; }
|
|
79
79
|
});
|
|
80
80
|
Object.defineProperty(exports, "apiRoutes", {
|
|
81
81
|
enumerable: true,
|
|
82
|
-
get: function () { return
|
|
82
|
+
get: function () { return chunk5QJX2VMP_cjs.api_default; }
|
|
83
83
|
});
|
|
84
84
|
Object.defineProperty(exports, "apiSystemRoutes", {
|
|
85
85
|
enumerable: true,
|
|
86
|
-
get: function () { return
|
|
86
|
+
get: function () { return chunk5QJX2VMP_cjs.api_system_default; }
|
|
87
87
|
});
|
|
88
88
|
Object.defineProperty(exports, "authRoutes", {
|
|
89
89
|
enumerable: true,
|
|
90
|
-
get: function () { return
|
|
90
|
+
get: function () { return chunk5QJX2VMP_cjs.auth_default; }
|
|
91
91
|
});
|
|
92
92
|
Object.defineProperty(exports, "testCleanupRoutes", {
|
|
93
93
|
enumerable: true,
|
|
94
|
-
get: function () { return
|
|
94
|
+
get: function () { return chunk5QJX2VMP_cjs.test_cleanup_default; }
|
|
95
95
|
});
|
|
96
96
|
//# sourceMappingURL=routes.cjs.map
|
|
97
97
|
//# sourceMappingURL=routes.cjs.map
|
package/dist/routes.js
CHANGED
|
@@ -1,10 +1,10 @@
|
|
|
1
|
-
export { ROUTES_INFO, admin_api_default as adminApiRoutes, adminCheckboxRoutes, admin_code_examples_default as adminCodeExamplesRoutes, adminCollectionsRoutes, admin_content_default as adminContentRoutes, router as adminDashboardRoutes, adminDesignRoutes, adminLogsRoutes, adminMediaRoutes, adminPluginRoutes, adminSettingsRoutes, admin_testimonials_default as adminTestimonialsRoutes, userRoutes as adminUsersRoutes, api_content_crud_default as apiContentCrudRoutes, api_media_default as apiMediaRoutes, api_default as apiRoutes, api_system_default as apiSystemRoutes, auth_default as authRoutes, test_cleanup_default as testCleanupRoutes } from './chunk-
|
|
1
|
+
export { ROUTES_INFO, admin_api_default as adminApiRoutes, adminCheckboxRoutes, admin_code_examples_default as adminCodeExamplesRoutes, adminCollectionsRoutes, admin_content_default as adminContentRoutes, router as adminDashboardRoutes, adminDesignRoutes, adminLogsRoutes, adminMediaRoutes, adminPluginRoutes, adminSettingsRoutes, admin_testimonials_default as adminTestimonialsRoutes, userRoutes as adminUsersRoutes, api_content_crud_default as apiContentCrudRoutes, api_media_default as apiMediaRoutes, api_default as apiRoutes, api_system_default as apiSystemRoutes, auth_default as authRoutes, test_cleanup_default as testCleanupRoutes } from './chunk-ZPERJATF.js';
|
|
2
2
|
import './chunk-Q52ZQFMB.js';
|
|
3
|
-
import './chunk-
|
|
3
|
+
import './chunk-WK5EUGBO.js';
|
|
4
4
|
import './chunk-7CXL5K7N.js';
|
|
5
|
-
import './chunk-
|
|
5
|
+
import './chunk-3MPQII4R.js';
|
|
6
6
|
import './chunk-5RKQB2JG.js';
|
|
7
|
-
import './chunk-
|
|
7
|
+
import './chunk-6RJU7HL5.js';
|
|
8
8
|
import './chunk-RRKXFGIO.js';
|
|
9
9
|
import './chunk-FICTAGD4.js';
|
|
10
10
|
import './chunk-V4OQ3NZ2.js';
|
package/dist/services.cjs
CHANGED
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
|
|
3
3
|
var chunkES3BRZQJ_cjs = require('./chunk-ES3BRZQJ.cjs');
|
|
4
4
|
var chunkNAYD76QF_cjs = require('./chunk-NAYD76QF.cjs');
|
|
5
|
-
var
|
|
5
|
+
var chunk23VPL6VI_cjs = require('./chunk-23VPL6VI.cjs');
|
|
6
6
|
require('./chunk-7KCDFDRI.cjs');
|
|
7
7
|
require('./chunk-IGJUBJBW.cjs');
|
|
8
8
|
|
|
@@ -106,7 +106,7 @@ Object.defineProperty(exports, "validateCollectionConfig", {
|
|
|
106
106
|
});
|
|
107
107
|
Object.defineProperty(exports, "MigrationService", {
|
|
108
108
|
enumerable: true,
|
|
109
|
-
get: function () { return
|
|
109
|
+
get: function () { return chunk23VPL6VI_cjs.MigrationService; }
|
|
110
110
|
});
|
|
111
111
|
//# sourceMappingURL=services.cjs.map
|
|
112
112
|
//# sourceMappingURL=services.cjs.map
|
package/dist/services.js
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
export { CACHE_CONFIGS, CacheService, Logger, SettingsService, TelemetryService, createInstallationIdentity, getCacheService, getLogger, getTelemetryService, initLogger, initTelemetry } from './chunk-Q52ZQFMB.js';
|
|
2
2
|
export { PluginBootstrapService, PluginService, cleanupRemovedCollections, fullCollectionSync, getAvailableCollectionNames, getManagedCollections, isCollectionManaged, loadCollectionConfig, loadCollectionConfigs, registerCollections, syncCollection, syncCollections, validateCollectionConfig } from './chunk-7CXL5K7N.js';
|
|
3
|
-
export { MigrationService } from './chunk-
|
|
3
|
+
export { MigrationService } from './chunk-3MPQII4R.js';
|
|
4
4
|
import './chunk-RRKXFGIO.js';
|
|
5
5
|
import './chunk-V4OQ3NZ2.js';
|
|
6
6
|
//# sourceMappingURL=services.js.map
|
package/dist/utils.cjs
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
'use strict';
|
|
2
2
|
|
|
3
|
-
var
|
|
3
|
+
var chunk44LBCF3B_cjs = require('./chunk-44LBCF3B.cjs');
|
|
4
4
|
var chunk7KCDFDRI_cjs = require('./chunk-7KCDFDRI.cjs');
|
|
5
5
|
var chunkRCQ2HIQD_cjs = require('./chunk-RCQ2HIQD.cjs');
|
|
6
6
|
require('./chunk-IGJUBJBW.cjs');
|
|
@@ -9,43 +9,43 @@ require('./chunk-IGJUBJBW.cjs');
|
|
|
9
9
|
|
|
10
10
|
Object.defineProperty(exports, "QueryFilterBuilder", {
|
|
11
11
|
enumerable: true,
|
|
12
|
-
get: function () { return
|
|
12
|
+
get: function () { return chunk44LBCF3B_cjs.QueryFilterBuilder; }
|
|
13
13
|
});
|
|
14
14
|
Object.defineProperty(exports, "SONICJS_VERSION", {
|
|
15
15
|
enumerable: true,
|
|
16
|
-
get: function () { return
|
|
16
|
+
get: function () { return chunk44LBCF3B_cjs.SONICJS_VERSION; }
|
|
17
17
|
});
|
|
18
18
|
Object.defineProperty(exports, "TemplateRenderer", {
|
|
19
19
|
enumerable: true,
|
|
20
|
-
get: function () { return
|
|
20
|
+
get: function () { return chunk44LBCF3B_cjs.TemplateRenderer; }
|
|
21
21
|
});
|
|
22
22
|
Object.defineProperty(exports, "buildQuery", {
|
|
23
23
|
enumerable: true,
|
|
24
|
-
get: function () { return
|
|
24
|
+
get: function () { return chunk44LBCF3B_cjs.buildQuery; }
|
|
25
25
|
});
|
|
26
26
|
Object.defineProperty(exports, "escapeHtml", {
|
|
27
27
|
enumerable: true,
|
|
28
|
-
get: function () { return
|
|
28
|
+
get: function () { return chunk44LBCF3B_cjs.escapeHtml; }
|
|
29
29
|
});
|
|
30
30
|
Object.defineProperty(exports, "getCoreVersion", {
|
|
31
31
|
enumerable: true,
|
|
32
|
-
get: function () { return
|
|
32
|
+
get: function () { return chunk44LBCF3B_cjs.getCoreVersion; }
|
|
33
33
|
});
|
|
34
34
|
Object.defineProperty(exports, "renderTemplate", {
|
|
35
35
|
enumerable: true,
|
|
36
|
-
get: function () { return
|
|
36
|
+
get: function () { return chunk44LBCF3B_cjs.renderTemplate; }
|
|
37
37
|
});
|
|
38
38
|
Object.defineProperty(exports, "sanitizeInput", {
|
|
39
39
|
enumerable: true,
|
|
40
|
-
get: function () { return
|
|
40
|
+
get: function () { return chunk44LBCF3B_cjs.sanitizeInput; }
|
|
41
41
|
});
|
|
42
42
|
Object.defineProperty(exports, "sanitizeObject", {
|
|
43
43
|
enumerable: true,
|
|
44
|
-
get: function () { return
|
|
44
|
+
get: function () { return chunk44LBCF3B_cjs.sanitizeObject; }
|
|
45
45
|
});
|
|
46
46
|
Object.defineProperty(exports, "templateRenderer", {
|
|
47
47
|
enumerable: true,
|
|
48
|
-
get: function () { return
|
|
48
|
+
get: function () { return chunk44LBCF3B_cjs.templateRenderer; }
|
|
49
49
|
});
|
|
50
50
|
Object.defineProperty(exports, "generateInstallationId", {
|
|
51
51
|
enumerable: true,
|
package/dist/utils.js
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
export { QueryFilterBuilder, SONICJS_VERSION, TemplateRenderer, buildQuery, escapeHtml, getCoreVersion, renderTemplate, sanitizeInput, sanitizeObject, templateRenderer } from './chunk-
|
|
1
|
+
export { QueryFilterBuilder, SONICJS_VERSION, TemplateRenderer, buildQuery, escapeHtml, getCoreVersion, renderTemplate, sanitizeInput, sanitizeObject, templateRenderer } from './chunk-6RJU7HL5.js';
|
|
2
2
|
export { generateInstallationId, generateProjectId, getDefaultTelemetryConfig, getTelemetryConfig, isTelemetryEnabled, sanitizeErrorMessage, sanitizeRoute, shouldSkipEvent } from './chunk-RRKXFGIO.js';
|
|
3
3
|
export { metricsTracker } from './chunk-FICTAGD4.js';
|
|
4
4
|
import './chunk-V4OQ3NZ2.js';
|
|
@@ -0,0 +1,86 @@
|
|
|
1
|
+
-- FAQ Plugin Migration (DEPRECATED - Now managed by third-party plugin)
|
|
2
|
+
-- Creates FAQ table for the FAQ plugin
|
|
3
|
+
-- NOTE: This migration is kept for historical purposes.
|
|
4
|
+
-- The FAQ functionality is now provided by the faq-plugin third-party plugin.
|
|
5
|
+
|
|
6
|
+
CREATE TABLE IF NOT EXISTS faqs (
|
|
7
|
+
id INTEGER PRIMARY KEY AUTOINCREMENT,
|
|
8
|
+
question TEXT NOT NULL,
|
|
9
|
+
answer TEXT NOT NULL,
|
|
10
|
+
category TEXT,
|
|
11
|
+
tags TEXT,
|
|
12
|
+
isPublished INTEGER NOT NULL DEFAULT 1,
|
|
13
|
+
sortOrder INTEGER NOT NULL DEFAULT 0,
|
|
14
|
+
created_at INTEGER NOT NULL DEFAULT (strftime('%s', 'now')),
|
|
15
|
+
updated_at INTEGER NOT NULL DEFAULT (strftime('%s', 'now'))
|
|
16
|
+
);
|
|
17
|
+
|
|
18
|
+
-- Create indexes for better performance
|
|
19
|
+
CREATE INDEX IF NOT EXISTS idx_faqs_category ON faqs(category);
|
|
20
|
+
CREATE INDEX IF NOT EXISTS idx_faqs_published ON faqs(isPublished);
|
|
21
|
+
CREATE INDEX IF NOT EXISTS idx_faqs_sort_order ON faqs(sortOrder);
|
|
22
|
+
|
|
23
|
+
-- Create trigger to update updated_at timestamp
|
|
24
|
+
CREATE TRIGGER IF NOT EXISTS faqs_updated_at
|
|
25
|
+
AFTER UPDATE ON faqs
|
|
26
|
+
BEGIN
|
|
27
|
+
UPDATE faqs SET updated_at = strftime('%s', 'now') WHERE id = NEW.id;
|
|
28
|
+
END;
|
|
29
|
+
|
|
30
|
+
-- Insert sample FAQ data
|
|
31
|
+
INSERT OR IGNORE INTO faqs (question, answer, category, tags, isPublished, sortOrder) VALUES
|
|
32
|
+
('What is SonicJS AI?',
|
|
33
|
+
'SonicJS AI is a modern, TypeScript-first headless CMS built for Cloudflare''s edge platform. It provides a complete content management system with admin interface, API endpoints, and plugin architecture.',
|
|
34
|
+
'general',
|
|
35
|
+
'sonicjs, cms, cloudflare',
|
|
36
|
+
1,
|
|
37
|
+
1),
|
|
38
|
+
|
|
39
|
+
('How do I get started with SonicJS AI?',
|
|
40
|
+
'To get started: 1) Clone the repository, 2) Install dependencies with npm install, 3) Set up your Cloudflare account and services, 4) Run the development server with npm run dev, 5) Access the admin interface at /admin.',
|
|
41
|
+
'general',
|
|
42
|
+
'getting-started, setup',
|
|
43
|
+
1,
|
|
44
|
+
2),
|
|
45
|
+
|
|
46
|
+
('What technologies does SonicJS AI use?',
|
|
47
|
+
'SonicJS AI is built with: TypeScript for type safety, Hono.js as the web framework, Cloudflare D1 for the database, Cloudflare R2 for media storage, Cloudflare Workers for serverless execution, and Tailwind CSS for styling.',
|
|
48
|
+
'technical',
|
|
49
|
+
'technology-stack, typescript, cloudflare',
|
|
50
|
+
1,
|
|
51
|
+
3),
|
|
52
|
+
|
|
53
|
+
('How do I create content in SonicJS AI?',
|
|
54
|
+
'Content creation is done through the admin interface. Navigate to /admin, log in with your credentials, go to Content section, select a collection, and click "New Content" to create articles, pages, or other content types.',
|
|
55
|
+
'general',
|
|
56
|
+
'content-creation, admin',
|
|
57
|
+
1,
|
|
58
|
+
4),
|
|
59
|
+
|
|
60
|
+
('Is SonicJS AI free to use?',
|
|
61
|
+
'SonicJS AI is open source and free to use. You only pay for the Cloudflare services you consume (D1 database, R2 storage, Workers execution time). Cloudflare offers generous free tiers for development and small projects.',
|
|
62
|
+
'billing',
|
|
63
|
+
'pricing, open-source, cloudflare',
|
|
64
|
+
1,
|
|
65
|
+
5),
|
|
66
|
+
|
|
67
|
+
('How do I add custom functionality?',
|
|
68
|
+
'SonicJS AI features a plugin system that allows you to extend functionality. You can create plugins using the PluginBuilder API, add custom routes, models, admin pages, and integrate with external services.',
|
|
69
|
+
'technical',
|
|
70
|
+
'plugins, customization, development',
|
|
71
|
+
1,
|
|
72
|
+
6),
|
|
73
|
+
|
|
74
|
+
('Can I customize the admin interface?',
|
|
75
|
+
'Yes! The admin interface is built with TypeScript templates and can be customized. You can modify existing templates, create new components, add custom pages, and integrate your own styling while maintaining the dark theme.',
|
|
76
|
+
'technical',
|
|
77
|
+
'admin-interface, customization, templates',
|
|
78
|
+
1,
|
|
79
|
+
7),
|
|
80
|
+
|
|
81
|
+
('How does authentication work?',
|
|
82
|
+
'SonicJS AI includes a built-in authentication system with JWT tokens, role-based access control (admin, editor, viewer), secure password hashing, and session management. Users can be managed through the admin interface.',
|
|
83
|
+
'technical',
|
|
84
|
+
'authentication, security, users',
|
|
85
|
+
1,
|
|
86
|
+
8);
|
|
@@ -0,0 +1,177 @@
|
|
|
1
|
+
-- Code Examples Plugin Migration
|
|
2
|
+
-- Creates code_examples table for the code examples plugin
|
|
3
|
+
-- This demonstrates a code-based collection for storing and managing code snippets
|
|
4
|
+
|
|
5
|
+
CREATE TABLE IF NOT EXISTS code_examples (
|
|
6
|
+
id INTEGER PRIMARY KEY AUTOINCREMENT,
|
|
7
|
+
title TEXT NOT NULL,
|
|
8
|
+
description TEXT,
|
|
9
|
+
code TEXT NOT NULL,
|
|
10
|
+
language TEXT NOT NULL,
|
|
11
|
+
category TEXT,
|
|
12
|
+
tags TEXT,
|
|
13
|
+
isPublished INTEGER NOT NULL DEFAULT 1,
|
|
14
|
+
sortOrder INTEGER NOT NULL DEFAULT 0,
|
|
15
|
+
created_at INTEGER NOT NULL DEFAULT (strftime('%s', 'now')),
|
|
16
|
+
updated_at INTEGER NOT NULL DEFAULT (strftime('%s', 'now'))
|
|
17
|
+
);
|
|
18
|
+
|
|
19
|
+
-- Create indexes for better performance
|
|
20
|
+
CREATE INDEX IF NOT EXISTS idx_code_examples_published ON code_examples(isPublished);
|
|
21
|
+
CREATE INDEX IF NOT EXISTS idx_code_examples_sort_order ON code_examples(sortOrder);
|
|
22
|
+
CREATE INDEX IF NOT EXISTS idx_code_examples_language ON code_examples(language);
|
|
23
|
+
CREATE INDEX IF NOT EXISTS idx_code_examples_category ON code_examples(category);
|
|
24
|
+
|
|
25
|
+
-- Create trigger to update updated_at timestamp
|
|
26
|
+
CREATE TRIGGER IF NOT EXISTS code_examples_updated_at
|
|
27
|
+
AFTER UPDATE ON code_examples
|
|
28
|
+
BEGIN
|
|
29
|
+
UPDATE code_examples SET updated_at = strftime('%s', 'now') WHERE id = NEW.id;
|
|
30
|
+
END;
|
|
31
|
+
|
|
32
|
+
-- Insert plugin record
|
|
33
|
+
INSERT OR IGNORE INTO plugins (name, display_name, description, version, status, category, settings) VALUES
|
|
34
|
+
('code-examples',
|
|
35
|
+
'Code Examples',
|
|
36
|
+
'Manage code snippets and examples with syntax highlighting support. Perfect for documentation and tutorials.',
|
|
37
|
+
'1.0.0',
|
|
38
|
+
'active',
|
|
39
|
+
'content',
|
|
40
|
+
'{"defaultPublished": true, "supportedLanguages": ["javascript", "typescript", "python", "go", "rust", "java", "php", "ruby", "sql"]}');
|
|
41
|
+
|
|
42
|
+
-- Insert sample code examples
|
|
43
|
+
INSERT OR IGNORE INTO code_examples (title, description, code, language, category, tags, isPublished, sortOrder) VALUES
|
|
44
|
+
('React useState Hook',
|
|
45
|
+
'Basic example of using the useState hook in React for managing component state.',
|
|
46
|
+
'import { useState } from ''react'';
|
|
47
|
+
|
|
48
|
+
function Counter() {
|
|
49
|
+
const [count, setCount] = useState(0);
|
|
50
|
+
|
|
51
|
+
return (
|
|
52
|
+
<div>
|
|
53
|
+
<p>Count: {count}</p>
|
|
54
|
+
<button onClick={() => setCount(count + 1)}>
|
|
55
|
+
Increment
|
|
56
|
+
</button>
|
|
57
|
+
</div>
|
|
58
|
+
);
|
|
59
|
+
}
|
|
60
|
+
|
|
61
|
+
export default Counter;',
|
|
62
|
+
'javascript',
|
|
63
|
+
'frontend',
|
|
64
|
+
'react,hooks,state',
|
|
65
|
+
1,
|
|
66
|
+
1),
|
|
67
|
+
|
|
68
|
+
('TypeScript Interface Example',
|
|
69
|
+
'Defining a TypeScript interface for type-safe objects.',
|
|
70
|
+
'interface User {
|
|
71
|
+
id: string;
|
|
72
|
+
email: string;
|
|
73
|
+
name: string;
|
|
74
|
+
role: ''admin'' | ''editor'' | ''viewer'';
|
|
75
|
+
createdAt: Date;
|
|
76
|
+
}
|
|
77
|
+
|
|
78
|
+
function greetUser(user: User): string {
|
|
79
|
+
return `Hello, ${user.name}!`;
|
|
80
|
+
}
|
|
81
|
+
|
|
82
|
+
const user: User = {
|
|
83
|
+
id: ''123'',
|
|
84
|
+
email: ''user@example.com'',
|
|
85
|
+
name: ''John Doe'',
|
|
86
|
+
role: ''admin'',
|
|
87
|
+
createdAt: new Date()
|
|
88
|
+
};
|
|
89
|
+
|
|
90
|
+
console.log(greetUser(user));',
|
|
91
|
+
'typescript',
|
|
92
|
+
'backend',
|
|
93
|
+
'typescript,types,interface',
|
|
94
|
+
1,
|
|
95
|
+
2),
|
|
96
|
+
|
|
97
|
+
('Python List Comprehension',
|
|
98
|
+
'Elegant way to create lists in Python using list comprehensions.',
|
|
99
|
+
'# Basic list comprehension
|
|
100
|
+
squares = [x**2 for x in range(10)]
|
|
101
|
+
print(squares) # [0, 1, 4, 9, 16, 25, 36, 49, 64, 81]
|
|
102
|
+
|
|
103
|
+
# With condition
|
|
104
|
+
even_squares = [x**2 for x in range(10) if x % 2 == 0]
|
|
105
|
+
print(even_squares) # [0, 4, 16, 36, 64]
|
|
106
|
+
|
|
107
|
+
# Nested list comprehension
|
|
108
|
+
matrix = [[i+j for j in range(3)] for i in range(3)]
|
|
109
|
+
print(matrix) # [[0, 1, 2], [1, 2, 3], [2, 3, 4]]',
|
|
110
|
+
'python',
|
|
111
|
+
'general',
|
|
112
|
+
'python,lists,comprehension',
|
|
113
|
+
1,
|
|
114
|
+
3),
|
|
115
|
+
|
|
116
|
+
('SQL Join Example',
|
|
117
|
+
'Common SQL JOIN patterns for combining data from multiple tables.',
|
|
118
|
+
'-- INNER JOIN: Returns only matching rows
|
|
119
|
+
SELECT users.name, orders.total
|
|
120
|
+
FROM users
|
|
121
|
+
INNER JOIN orders ON users.id = orders.user_id;
|
|
122
|
+
|
|
123
|
+
-- LEFT JOIN: Returns all users, even without orders
|
|
124
|
+
SELECT users.name, orders.total
|
|
125
|
+
FROM users
|
|
126
|
+
LEFT JOIN orders ON users.id = orders.user_id;
|
|
127
|
+
|
|
128
|
+
-- Multiple JOINs
|
|
129
|
+
SELECT
|
|
130
|
+
users.name,
|
|
131
|
+
orders.order_date,
|
|
132
|
+
products.name AS product_name
|
|
133
|
+
FROM users
|
|
134
|
+
INNER JOIN orders ON users.id = orders.user_id
|
|
135
|
+
INNER JOIN order_items ON orders.id = order_items.order_id
|
|
136
|
+
INNER JOIN products ON order_items.product_id = products.id;',
|
|
137
|
+
'sql',
|
|
138
|
+
'database',
|
|
139
|
+
'sql,joins,queries',
|
|
140
|
+
1,
|
|
141
|
+
4),
|
|
142
|
+
|
|
143
|
+
('Go Error Handling',
|
|
144
|
+
'Idiomatic error handling pattern in Go.',
|
|
145
|
+
'package main
|
|
146
|
+
|
|
147
|
+
import (
|
|
148
|
+
"errors"
|
|
149
|
+
"fmt"
|
|
150
|
+
)
|
|
151
|
+
|
|
152
|
+
func divide(a, b float64) (float64, error) {
|
|
153
|
+
if b == 0 {
|
|
154
|
+
return 0, errors.New("division by zero")
|
|
155
|
+
}
|
|
156
|
+
return a / b, nil
|
|
157
|
+
}
|
|
158
|
+
|
|
159
|
+
func main() {
|
|
160
|
+
result, err := divide(10, 2)
|
|
161
|
+
if err != nil {
|
|
162
|
+
fmt.Println("Error:", err)
|
|
163
|
+
return
|
|
164
|
+
}
|
|
165
|
+
fmt.Printf("Result: %.2f\n", result)
|
|
166
|
+
|
|
167
|
+
// This will error
|
|
168
|
+
_, err = divide(10, 0)
|
|
169
|
+
if err != nil {
|
|
170
|
+
fmt.Println("Error:", err)
|
|
171
|
+
}
|
|
172
|
+
}',
|
|
173
|
+
'go',
|
|
174
|
+
'backend',
|
|
175
|
+
'go,error-handling,functions',
|
|
176
|
+
1,
|
|
177
|
+
5);
|
package/package.json
CHANGED