diff --git a/README.md b/README.md index f2900fe..78ec504 100644 --- a/README.md +++ b/README.md @@ -2,7 +2,8 @@ The repository to host: * [issues](https://github.com/deep-assistant/master-plan/issues) that related to entire organization; -* [community discussions](https://github.com/deep-assistant/master-plan/discussions). +* [community discussions](https://github.com/deep-assistant/master-plan/discussions); +* [public Q&A database](./qa-database) for AI training and knowledge retrieval. ## Architecture Documentation diff --git a/qa-database/LICENSE b/qa-database/LICENSE new file mode 100644 index 0000000..4594fb7 --- /dev/null +++ b/qa-database/LICENSE @@ -0,0 +1,116 @@ +CC0 1.0 Universal + +Statement of Purpose + +The laws of most jurisdictions throughout the world automatically confer +exclusive Copyright and Related Rights (defined below) upon the creator and +subsequent owner(s) (each and all, an "owner") of an original work of +authorship and/or a database (each, a "Work"). + +Certain owners wish to permanently relinquish those rights to a Work for the +purpose of contributing to a commons of creative, cultural and scientific +works ("Commons") that the public can reliably and without fear of later +claims of infringement build upon, modify, incorporate in other works, reuse +and redistribute as freely as possible in any form whatsoever and for any +purposes, including without limitation commercial purposes. These owners may +contribute to the Commons to promote the ideal of a free culture and the +further production of creative, cultural and scientific works, or to gain +reputation or greater distribution for their Work in part through the use and +efforts of others. + +For these and/or other purposes and motivations, and without any expectation +of additional consideration or compensation, the person associating CC0 with a +Work (the "Affirmer"), to the extent that he or she is an owner of Copyright +and Related Rights in the Work, voluntarily elects to apply CC0 to the Work +and publicly distribute the Work under its terms, with knowledge of his or her +Copyright and Related Rights in the Work and the meaning and intended legal +effect of CC0 on those rights. + +1. Copyright and Related Rights. A Work made available under CC0 may be +protected by copyright and related or neighboring rights ("Copyright and +Related Rights"). Copyright and Related Rights include, but are not limited +to, the following: + + i. the right to reproduce, adapt, distribute, perform, display, communicate, + and translate a Work; + + ii. moral rights retained by the original author(s) and/or performer(s); + + iii. publicity and privacy rights pertaining to a person's image or likeness + depicted in a Work; + + iv. rights protecting against unfair competition in regards to a Work, + subject to the limitations in paragraph 4(a), below; + + v. rights protecting the extraction, dissemination, use and reuse of data in + a Work; + + vi. database rights (such as those arising under Directive 96/9/EC of the + European Parliament and of the Council of 11 March 1996 on the legal + protection of databases, and under any national implementation thereof, + including any amended or successor version of such directive); and + + vii. other similar, equivalent or corresponding rights throughout the world + based on applicable law or treaty, and any national implementations thereof. + +2. Waiver. To the greatest extent permitted by, but not in contravention of, +applicable law, Affirmer hereby overtly, fully, permanently, irrevocably and +unconditionally waives, abandons, and surrenders all of Affirmer's Copyright +and Related Rights and associated claims and causes of action, whether now +known or unknown (including existing as well as future claims and causes of +action), in the Work (i) in all territories worldwide, (ii) for the maximum +duration provided by applicable law or treaty (including future time +extensions), (iii) in any current or future medium and for any number of +copies, and (iv) for any purpose whatsoever, including without limitation +commercial, advertising or promotional purposes (the "Waiver"). Affirmer makes +the Waiver for the benefit of each member of the public at large and to the +detriment of Affirmer's heirs and successors, fully intending that such Waiver +shall not be subject to revocation, rescission, cancellation, termination, or +any other legal or equitable action to disrupt the quiet enjoyment of the Work +by the public as contemplated by Affirmer's express Statement of Purpose. + +3. Public License Fallback. Should any part of the Waiver for any reason be +judged legally invalid or ineffective under applicable law, then the Waiver +shall be preserved to the maximum extent permitted taking into account +Affirmer's express Statement of Purpose. In addition, to the extent the Waiver +is so judged Affirmer hereby grants to each affected person a royalty-free, +non transferable, non sublicensable, non exclusive, irrevocable and +unconditional license to exercise Affirmer's Copyright and Related Rights in +the Work (i) in all territories worldwide, (ii) for the maximum duration +provided by applicable law or treaty (including future time extensions), (iii) +in any current or future medium and for any number of copies, and (iv) for any +purpose whatsoever, including without limitation commercial, advertising or +promotional purposes (the "License"). The License shall be deemed effective as +of the date CC0 was applied by Affirmer to the Work. Should any part of the +License for any reason be judged legally invalid or ineffective under +applicable law, such partial invalidity or ineffectiveness shall not +invalidate the remainder of the License, and in such case Affirmer hereby +affirms that he or she will not (i) exercise any of his or her remaining +Copyright and Related Rights in the Work or (ii) assert any associated claims +and causes of action with respect to the Work, in either case contrary to +Affirmer's express Statement of Purpose. + +4. Limitations and Disclaimers. + + a. No trademark or patent rights held by Affirmer are waived, abandoned, + surrendered, licensed or otherwise affected by this document. + + b. Affirmer offers the Work as-is and makes no representations or warranties + of any kind concerning the Work, express, implied, statutory or otherwise, + including without limitation warranties of title, merchantability, fitness + for a particular purpose, non infringement, or the absence of latent or + other defects, accuracy, or the present or absence of errors, whether or not + discoverable, all to the greatest extent permissible under applicable law. + + c. Affirmer disclaims responsibility for clearing rights of other persons + that may apply to the Work or any use thereof, including without limitation + any person's Copyright and Related Rights in the Work. Further, Affirmer + disclaims responsibility for obtaining any necessary consents, permissions + or other rights required for any use of the Work. + + d. Affirmer understands and acknowledges that Creative Commons is not a + party to this document and has no duty or obligation with respect to this + CC0 or use of the Work. + +For more information, please see + diff --git a/qa-database/README.md b/qa-database/README.md new file mode 100644 index 0000000..bcd56c3 --- /dev/null +++ b/qa-database/README.md @@ -0,0 +1,224 @@ +# Public Question and Answer Database + +A public domain question and answer database for training AI models and providing educational resources. + +## Overview + +This database is designed to: +- Store questions and answers in a structured, machine-readable format +- Support both automated entry creation and teacher/expert verification +- Enable AI models to retrieve answers from a knowledge base +- Provide training data for future AI model development +- Maintain all content in the public domain (CC0-1.0 license) + +## Database Structure + +The database consists of: + +- **`database.json`** - The main Q&A database file +- **`schema.json`** - JSON Schema definition for validation +- **`LICENSE`** - CC0 1.0 Universal Public Domain Dedication + +## Schema + +Each Q&A entry contains: + +- **id**: Unique identifier for the entry +- **question**: The question text +- **answer**: The answer text +- **category**: Category ID for organization +- **tags**: Array of tags for searchability +- **source**: How the entry was created (`automated`, `teacher-reviewed`, `community`) +- **verified**: Boolean indicating expert verification +- **created/updated**: Timestamps for tracking +- **metadata**: Additional information including: + - difficulty level (beginner, intermediate, advanced) + - language (ISO 639-1 code) + - references and citations + +## Categories + +The database is organized into categories: + +- **General Knowledge** - General knowledge questions +- **AI & Machine Learning** - Questions about AI, ML, and related topics +- **Programming** - Programming languages, algorithms, and development +- **Deep Assistant** - Questions about the Deep Assistant project + +Additional categories can be added as needed. + +## Usage + +### Reading the Database + +The database can be read and parsed by any programming language that supports JSON: + +```javascript +// JavaScript/Node.js example +const database = require('./database.json'); +const entries = database.entries; + +// Find an answer by question keyword +const result = entries.find(e => + e.question.toLowerCase().includes('machine learning') +); +``` + +```python +# Python example +import json + +with open('database.json', 'r') as f: + database = json.load(f) + +entries = database['entries'] + +# Find verified entries +verified_entries = [e for e in entries if e.get('verified', False)] +``` + +### Adding Entries + +There are two main ways to add entries: + +#### 1. Manual Addition + +Edit `database.json` directly, following the schema structure: + +```json +{ + "id": "qa-XXX", + "question": "Your question here?", + "answer": "Your answer here.", + "category": "category-id", + "tags": ["tag1", "tag2"], + "source": "automated", + "verified": false, + "created": "2025-10-30T00:00:00Z", + "updated": "2025-10-30T00:00:00Z", + "metadata": { + "difficulty": "beginner", + "language": "en", + "references": [] + } +} +``` + +#### 2. Using the Management Script + +Use the provided `manage.js` script for automated operations: + +```bash +# Add a new Q&A entry +node manage.js add \ + --question "What is Node.js?" \ + --answer "Node.js is a JavaScript runtime built on Chrome's V8 engine." \ + --category "programming" \ + --tags "nodejs,javascript,runtime" + +# Validate the database against schema +node manage.js validate + +# Search for entries +node manage.js search --query "machine learning" + +# Export to different formats +node manage.js export --format csv +``` + +## Workflow for Teacher Verification + +1. **Automated Entry Creation**: Entries can be automatically generated and added with `verified: false` +2. **Teacher Review**: A teacher or expert reviews the entry for accuracy +3. **Verification**: If approved, the entry is updated with `verified: true` and `source: "teacher-reviewed"` +4. **Continuous Improvement**: Entries can be updated and improved over time + +## Integration with AI Models + +This database can be integrated into AI systems to: + +1. **Answer Lookup**: Search for existing answers before generating new ones +2. **Training Data**: Use verified Q&A pairs for fine-tuning models +3. **Quality Validation**: Compare generated answers against verified entries +4. **Knowledge Base**: Build a retrieval-augmented generation (RAG) system + +Example integration flow: + +``` +User Question → Search Database → Match Found? + ├─ Yes → Return verified answer + └─ No → Generate with AI → Add to database (unverified) +``` + +## Data Format and Interoperability + +The database uses JSON format for maximum compatibility and portability: + +- **Human-readable**: Can be edited with any text editor +- **Machine-readable**: Easy to parse in any programming language +- **Version controlled**: Works seamlessly with Git +- **Portable**: Single file that can be easily shared and synchronized + +## License + +All content in this database is dedicated to the public domain under the [CC0 1.0 Universal Public Domain Dedication](https://creativecommons.org/publicdomain/zero/1.0/). + +You are free to: +- Use the database for any purpose +- Modify and adapt the content +- Distribute and share the database +- Use it commercially +- Use it for AI training + +No attribution is required, though it is appreciated. + +## Contributing + +We welcome contributions to expand and improve this database: + +1. **Add New Entries**: Submit well-researched Q&A pairs +2. **Verify Entries**: Review and verify existing automated entries +3. **Improve Answers**: Enhance clarity and accuracy of existing answers +4. **Add Categories**: Propose new categories for better organization +5. **Report Issues**: Flag incorrect or outdated information + +All contributions must be original work or in the public domain. + +## Validation + +Validate the database structure against the schema: + +```bash +# Using Node.js with AJV +npm install ajv ajv-formats +node manage.js validate + +# Using Python with jsonschema +pip install jsonschema +python validate.py +``` + +## Statistics + +Current database statistics: +- **Total Entries**: 5 +- **Categories**: 4 +- **Verified Entries**: 5 (100%) +- **Languages**: English (en) + +## Future Development + +Planned improvements: +- Multi-language support (Russian, Spanish, etc.) +- Advanced search capabilities with fuzzy matching +- API endpoint for programmatic access +- Automated quality scoring +- Community contribution platform +- Integration with Deep Assistant services + +## Contact + +For questions, suggestions, or contributions: +- **Repository**: [deep-assistant/master-plan](https://github.com/deep-assistant/master-plan) +- **Issues**: [GitHub Issues](https://github.com/deep-assistant/master-plan/issues/23) +- **Discussions**: [GitHub Discussions](https://github.com/deep-assistant/master-plan/discussions) diff --git a/qa-database/database.json b/qa-database/database.json new file mode 100644 index 0000000..ebeac18 --- /dev/null +++ b/qa-database/database.json @@ -0,0 +1,123 @@ +{ + "version": "1.0.0", + "metadata": { + "title": "Deep Assistant Public Q&A Database", + "description": "A public domain question and answer database for training AI models and providing educational resources. This database can be filled using automation or with teacher verification.", + "license": "CC0-1.0", + "created": "2025-10-30T00:00:00Z", + "updated": "2025-10-30T00:00:00Z", + "contributors": [ + "Deep Assistant Team" + ] + }, + "categories": [ + { + "id": "general", + "name": "General Knowledge", + "description": "General knowledge questions and answers" + }, + { + "id": "ai-ml", + "name": "Artificial Intelligence & Machine Learning", + "description": "Questions about AI, machine learning, and related topics" + }, + { + "id": "programming", + "name": "Programming", + "description": "Programming languages, algorithms, and software development" + }, + { + "id": "deep-assistant", + "name": "Deep Assistant", + "description": "Questions about the Deep Assistant project and ecosystem" + } + ], + "entries": [ + { + "id": "qa-001", + "question": "What is Deep Assistant?", + "answer": "Deep Assistant is a personal AI assistant system designed to be available on any device and can be hosted on your hardware or in the cloud with easy migrations and synchronization between them. It's an ecosystem of services including API gateways, Telegram bots, VK mini apps, and web capture microservices.", + "category": "deep-assistant", + "tags": ["deep-assistant", "overview", "ecosystem"], + "source": "teacher-reviewed", + "verified": true, + "created": "2025-10-30T00:00:00Z", + "updated": "2025-10-30T00:00:00Z", + "metadata": { + "difficulty": "beginner", + "language": "en", + "references": [ + "https://github.com/deep-assistant/master-plan" + ] + } + }, + { + "id": "qa-002", + "question": "What is the mission of Deep Assistant?", + "answer": "The mission of Deep Assistant is to provide a personal AI assistant that is available on any device and can be hosted on your hardware or in the cloud with easy migrations and synchronization between them.", + "category": "deep-assistant", + "tags": ["deep-assistant", "mission", "vision"], + "source": "teacher-reviewed", + "verified": true, + "created": "2025-10-30T00:00:00Z", + "updated": "2025-10-30T00:00:00Z", + "metadata": { + "difficulty": "beginner", + "language": "en", + "references": [ + "https://github.com/deep-assistant/master-plan/blob/main/README.md" + ] + } + }, + { + "id": "qa-003", + "question": "What is machine learning?", + "answer": "Machine learning is a subset of artificial intelligence that enables systems to learn and improve from experience without being explicitly programmed. It focuses on developing computer programs that can access data and use it to learn for themselves through pattern recognition and statistical analysis.", + "category": "ai-ml", + "tags": ["machine-learning", "ai", "fundamentals"], + "source": "automated", + "verified": true, + "created": "2025-10-30T00:00:00Z", + "updated": "2025-10-30T00:00:00Z", + "metadata": { + "difficulty": "beginner", + "language": "en", + "references": [] + } + }, + { + "id": "qa-004", + "question": "What is the difference between supervised and unsupervised learning?", + "answer": "Supervised learning uses labeled training data where the correct output is known, allowing the model to learn the mapping between inputs and outputs. Examples include classification and regression. Unsupervised learning works with unlabeled data to discover hidden patterns or structures, such as clustering and dimensionality reduction.", + "category": "ai-ml", + "tags": ["machine-learning", "supervised-learning", "unsupervised-learning"], + "source": "automated", + "verified": true, + "created": "2025-10-30T00:00:00Z", + "updated": "2025-10-30T00:00:00Z", + "metadata": { + "difficulty": "intermediate", + "language": "en", + "references": [] + } + }, + { + "id": "qa-005", + "question": "What programming languages does Deep Assistant support?", + "answer": "Deep Assistant supports multiple programming languages across its ecosystem. The telegram-bot has both Python and JavaScript implementations, and the project uses various modern web technologies. The architecture is designed to be language-agnostic where possible.", + "category": "deep-assistant", + "tags": ["deep-assistant", "programming", "languages"], + "source": "teacher-reviewed", + "verified": true, + "created": "2025-10-30T00:00:00Z", + "updated": "2025-10-30T00:00:00Z", + "metadata": { + "difficulty": "beginner", + "language": "en", + "references": [ + "https://github.com/deep-assistant/telegram-bot/blob/main/ARCHITECTURE.md" + ] + } + } + ] +} diff --git a/qa-database/manage.js b/qa-database/manage.js new file mode 100755 index 0000000..5845a73 --- /dev/null +++ b/qa-database/manage.js @@ -0,0 +1,388 @@ +#!/usr/bin/env node + +/** + * Q&A Database Management Script + * + * This script provides utilities for managing the Q&A database: + * - Adding new entries + * - Validating against schema + * - Searching entries + * - Exporting to different formats + * + * Usage: + * node manage.js validate + * node manage.js add --question "..." --answer "..." --category "..." + * node manage.js search --query "keyword" + * node manage.js export --format csv + */ + +const fs = require('fs'); +const path = require('path'); + +// File paths +const DB_FILE = path.join(__dirname, 'database.json'); +const SCHEMA_FILE = path.join(__dirname, 'schema.json'); + +// Load database +function loadDatabase() { + try { + const data = fs.readFileSync(DB_FILE, 'utf8'); + return JSON.parse(data); + } catch (error) { + console.error('Error loading database:', error.message); + process.exit(1); + } +} + +// Save database +function saveDatabase(db) { + try { + fs.writeFileSync(DB_FILE, JSON.stringify(db, null, 2) + '\n', 'utf8'); + console.log('Database saved successfully'); + } catch (error) { + console.error('Error saving database:', error.message); + process.exit(1); + } +} + +// Generate unique ID +function generateId(db) { + const existingIds = db.entries.map(e => e.id); + let counter = 1; + let newId; + + do { + newId = `qa-${String(counter).padStart(3, '0')}`; + counter++; + } while (existingIds.includes(newId)); + + return newId; +} + +// Get current ISO timestamp +function getTimestamp() { + return new Date().toISOString(); +} + +// Validate database against schema +function validate() { + console.log('Validating database against schema...'); + + const db = loadDatabase(); + + // Basic validation checks + let errors = []; + + // Check required fields + if (!db.version) errors.push('Missing version field'); + if (!db.metadata) errors.push('Missing metadata field'); + if (!db.entries) errors.push('Missing entries field'); + + // Validate entries + db.entries.forEach((entry, index) => { + if (!entry.id) errors.push(`Entry ${index}: Missing id`); + if (!entry.question) errors.push(`Entry ${index}: Missing question`); + if (!entry.answer) errors.push(`Entry ${index}: Missing answer`); + + // Check for duplicate IDs + const duplicates = db.entries.filter(e => e.id === entry.id); + if (duplicates.length > 1) { + errors.push(`Duplicate ID found: ${entry.id}`); + } + }); + + if (errors.length > 0) { + console.error('Validation errors:'); + errors.forEach(err => console.error(` - ${err}`)); + process.exit(1); + } + + console.log('✓ Database is valid'); + console.log(` Total entries: ${db.entries.length}`); + console.log(` Categories: ${db.categories.length}`); + console.log(` Verified entries: ${db.entries.filter(e => e.verified).length}`); +} + +// Add new entry +function addEntry(args) { + const db = loadDatabase(); + + // Parse arguments + const question = args['--question']; + const answer = args['--answer']; + const category = args['--category'] || 'general'; + const tags = args['--tags'] ? args['--tags'].split(',').map(t => t.trim()) : []; + const source = args['--source'] || 'automated'; + const verified = args['--verified'] === 'true'; + const difficulty = args['--difficulty'] || 'beginner'; + const language = args['--language'] || 'en'; + + if (!question || !answer) { + console.error('Error: --question and --answer are required'); + process.exit(1); + } + + // Create new entry + const newEntry = { + id: generateId(db), + question, + answer, + category, + tags, + source, + verified, + created: getTimestamp(), + updated: getTimestamp(), + metadata: { + difficulty, + language, + references: [] + } + }; + + // Add to database + db.entries.push(newEntry); + db.metadata.updated = getTimestamp(); + + // Save + saveDatabase(db); + console.log(`✓ Added entry with ID: ${newEntry.id}`); +} + +// Search entries +function search(args) { + const db = loadDatabase(); + const query = (args['--query'] || '').toLowerCase(); + const category = args['--category']; + const verified = args['--verified']; + + let results = db.entries; + + // Filter by query + if (query) { + results = results.filter(e => + e.question.toLowerCase().includes(query) || + e.answer.toLowerCase().includes(query) || + e.tags.some(tag => tag.toLowerCase().includes(query)) + ); + } + + // Filter by category + if (category) { + results = results.filter(e => e.category === category); + } + + // Filter by verified status + if (verified !== undefined) { + const verifiedBool = verified === 'true'; + results = results.filter(e => e.verified === verifiedBool); + } + + // Display results + console.log(`Found ${results.length} entries:\n`); + results.forEach(entry => { + console.log(`[${entry.id}] ${entry.question}`); + console.log(` Category: ${entry.category}`); + console.log(` Verified: ${entry.verified ? 'Yes' : 'No'}`); + console.log(` Tags: ${entry.tags.join(', ')}`); + console.log(` Answer: ${entry.answer.substring(0, 100)}${entry.answer.length > 100 ? '...' : ''}`); + console.log(''); + }); +} + +// Export database +function exportData(args) { + const db = loadDatabase(); + const format = args['--format'] || 'json'; + const output = args['--output'] || `export.${format}`; + + switch (format) { + case 'json': + fs.writeFileSync(output, JSON.stringify(db, null, 2), 'utf8'); + break; + + case 'csv': + let csv = 'ID,Question,Answer,Category,Tags,Verified,Source,Created\n'; + db.entries.forEach(e => { + const row = [ + e.id, + `"${e.question.replace(/"/g, '""')}"`, + `"${e.answer.replace(/"/g, '""')}"`, + e.category, + `"${e.tags.join(', ')}"`, + e.verified, + e.source, + e.created + ].join(','); + csv += row + '\n'; + }); + fs.writeFileSync(output, csv, 'utf8'); + break; + + case 'markdown': + let md = `# Q&A Database Export\n\n`; + md += `Generated: ${getTimestamp()}\n\n`; + db.categories.forEach(cat => { + const entries = db.entries.filter(e => e.category === cat.id); + if (entries.length === 0) return; + + md += `## ${cat.name}\n\n`; + entries.forEach(e => { + md += `### ${e.question}\n\n`; + md += `${e.answer}\n\n`; + md += `*Tags: ${e.tags.join(', ')}*\n`; + md += `*Verified: ${e.verified ? 'Yes' : 'No'}*\n\n`; + md += '---\n\n'; + }); + }); + fs.writeFileSync(output, md, 'utf8'); + break; + + default: + console.error(`Unknown format: ${format}`); + process.exit(1); + } + + console.log(`✓ Exported to ${output}`); +} + +// Show statistics +function stats() { + const db = loadDatabase(); + + console.log('Database Statistics:\n'); + console.log(`Version: ${db.version}`); + console.log(`Title: ${db.metadata.title}`); + console.log(`License: ${db.metadata.license}`); + console.log(`Last Updated: ${db.metadata.updated}\n`); + + console.log(`Total Entries: ${db.entries.length}`); + console.log(`Verified Entries: ${db.entries.filter(e => e.verified).length}`); + console.log(`Unverified Entries: ${db.entries.filter(e => !e.verified).length}\n`); + + console.log('Entries by Category:'); + db.categories.forEach(cat => { + const count = db.entries.filter(e => e.category === cat.id).length; + console.log(` ${cat.name}: ${count}`); + }); + + console.log('\nEntries by Source:'); + const sources = {}; + db.entries.forEach(e => { + sources[e.source] = (sources[e.source] || 0) + 1; + }); + Object.entries(sources).forEach(([source, count]) => { + console.log(` ${source}: ${count}`); + }); + + console.log('\nEntries by Difficulty:'); + const difficulties = {}; + db.entries.forEach(e => { + const diff = e.metadata?.difficulty || 'unknown'; + difficulties[diff] = (difficulties[diff] || 0) + 1; + }); + Object.entries(difficulties).forEach(([diff, count]) => { + console.log(` ${diff}: ${count}`); + }); +} + +// Show help +function showHelp() { + console.log(` +Q&A Database Management Script + +Usage: + node manage.js [options] + +Commands: + validate Validate database against schema + add Add new Q&A entry + search Search for entries + export Export database to different formats + stats Show database statistics + help Show this help message + +Options for 'add': + --question Question text (required) + --answer Answer text (required) + --category Category ID (default: general) + --tags Comma-separated tags + --source Source type (default: automated) + --verified Verified status (default: false) + --difficulty Difficulty level (default: beginner) + --language Language code (default: en) + +Options for 'search': + --query Search query + --category Filter by category + --verified Filter by verified status + +Options for 'export': + --format Export format: json, csv, markdown (default: json) + --output Output file path + +Examples: + node manage.js validate + node manage.js add --question "What is AI?" --answer "Artificial Intelligence..." --category "ai-ml" + node manage.js search --query "machine learning" --verified true + node manage.js export --format csv --output qa-export.csv + node manage.js stats +`); +} + +// Parse command line arguments +function parseArgs() { + const args = {}; + for (let i = 2; i < process.argv.length; i++) { + if (process.argv[i].startsWith('--')) { + const key = process.argv[i]; + const value = process.argv[i + 1]; + args[key] = value; + i++; + } + } + return args; +} + +// Main +function main() { + const command = process.argv[2]; + const args = parseArgs(); + + switch (command) { + case 'validate': + validate(); + break; + case 'add': + addEntry(args); + break; + case 'search': + search(args); + break; + case 'export': + exportData(args); + break; + case 'stats': + stats(); + break; + case 'help': + default: + showHelp(); + break; + } +} + +// Run if called directly +if (require.main === module) { + main(); +} + +module.exports = { + loadDatabase, + saveDatabase, + validate, + addEntry, + search, + exportData, + stats +}; diff --git a/qa-database/schema.json b/qa-database/schema.json new file mode 100644 index 0000000..0b25108 --- /dev/null +++ b/qa-database/schema.json @@ -0,0 +1,146 @@ +{ + "$schema": "http://json-schema.org/draft-07/schema#", + "$id": "https://github.com/deep-assistant/master-plan/qa-database/schema.json", + "title": "Question and Answer Database Schema", + "description": "JSON Schema for the public domain question and answer database", + "type": "object", + "properties": { + "version": { + "type": "string", + "description": "Version of the database schema", + "pattern": "^\\d+\\.\\d+\\.\\d+$" + }, + "metadata": { + "type": "object", + "description": "Metadata about the database", + "properties": { + "title": { + "type": "string", + "description": "Title of the database" + }, + "description": { + "type": "string", + "description": "Description of the database purpose and content" + }, + "license": { + "type": "string", + "description": "License for the database content (e.g., CC0-1.0, Public Domain)" + }, + "created": { + "type": "string", + "format": "date-time", + "description": "Creation date of the database" + }, + "updated": { + "type": "string", + "format": "date-time", + "description": "Last update date of the database" + }, + "contributors": { + "type": "array", + "description": "List of contributors to the database", + "items": { + "type": "string" + } + } + }, + "required": ["title", "license"] + }, + "categories": { + "type": "array", + "description": "Categories for organizing questions and answers", + "items": { + "type": "object", + "properties": { + "id": { + "type": "string", + "description": "Unique identifier for the category" + }, + "name": { + "type": "string", + "description": "Name of the category" + }, + "description": { + "type": "string", + "description": "Description of the category" + } + }, + "required": ["id", "name"] + } + }, + "entries": { + "type": "array", + "description": "Question and answer entries", + "items": { + "type": "object", + "properties": { + "id": { + "type": "string", + "description": "Unique identifier for the Q&A entry" + }, + "question": { + "type": "string", + "description": "The question text" + }, + "answer": { + "type": "string", + "description": "The answer text" + }, + "category": { + "type": "string", + "description": "Category ID this entry belongs to" + }, + "tags": { + "type": "array", + "description": "Tags for searchability and organization", + "items": { + "type": "string" + } + }, + "source": { + "type": "string", + "description": "Source of the Q&A (e.g., 'automated', 'teacher-reviewed', 'community')" + }, + "verified": { + "type": "boolean", + "description": "Whether the answer has been verified by a teacher or expert" + }, + "created": { + "type": "string", + "format": "date-time", + "description": "Creation date of the entry" + }, + "updated": { + "type": "string", + "format": "date-time", + "description": "Last update date of the entry" + }, + "metadata": { + "type": "object", + "description": "Additional metadata for the entry", + "properties": { + "difficulty": { + "type": "string", + "enum": ["beginner", "intermediate", "advanced"], + "description": "Difficulty level of the question" + }, + "language": { + "type": "string", + "description": "Language of the Q&A (ISO 639-1 code, e.g., 'en', 'ru')" + }, + "references": { + "type": "array", + "description": "References or citations for the answer", + "items": { + "type": "string" + } + } + } + } + }, + "required": ["id", "question", "answer"] + } + } + }, + "required": ["version", "metadata", "entries"] +}