diff --git a/app/Http/Controllers/Public/DocsController.php b/app/Http/Controllers/Public/DocsController.php new file mode 100644 index 00000000..e8860edc --- /dev/null +++ b/app/Http/Controllers/Public/DocsController.php @@ -0,0 +1,309 @@ + .mdx -> .md -> folder/README -> folder/index + if (File::exists($fullPath) && !File::isDirectory($fullPath)) { + $file = $fullPath; + } else { + $checkPaths = [ + $fullPath . '.mdx', + $fullPath . '.md', + $fullPath . DIRECTORY_SEPARATOR . 'README.md', + $fullPath . DIRECTORY_SEPARATOR . 'index.md', + $fullPath . DIRECTORY_SEPARATOR . 'README.mdx', + ]; + + foreach ($checkPaths as $p) { + if (File::exists($p) && !File::isDirectory($p)) { + $file = $p; + break; + } + } + } + + if (!$file) { + // Final fallback to root README + $file = $docsPath . DIRECTORY_SEPARATOR . 'README.md'; + $path = 'README'; + } + + $content = File::get($file); + $sidebar = $this->getSidebar($docsPath); + + // Add Introduction (Home) to the top of sidebar if not present + $hasIntro = false; + foreach ($sidebar as $item) { + if (($item['path'] ?? '') === 'README') { + $hasIntro = true; + break; + } + } + + if (!$hasIntro && (File::exists($docsPath . DIRECTORY_SEPARATOR . 'README.md') || File::exists($docsPath . DIRECTORY_SEPARATOR . 'README.mdx'))) { + array_unshift($sidebar, [ + 'type' => 'link', + 'label' => 'مدخل', + 'href' => '/docs/README', + 'path' => 'README', + 'position' => -1 + ]); + } + + $title = $this->extractTitle($content) ?? $this->formatLabel(basename($file)); + $metaDescription = $this->extractMetaDescription($content); + + $flatSidebar = $this->flattenSidebar($sidebar); + $currentIndex = -1; + $normalizedPath = str_replace(['\\', DIRECTORY_SEPARATOR], '/', $path); + + foreach ($flatSidebar as $index => $item) { + if ($item['path'] === $normalizedPath || $item['path'] === $path) { + $currentIndex = $index; + break; + } + } + + $prev = $currentIndex > 0 ? $flatSidebar[$currentIndex - 1] : null; + $next = ($currentIndex !== -1 && $currentIndex < count($flatSidebar) - 1) ? $flatSidebar[$currentIndex + 1] : null; + + return Inertia::render('Docs/Show', [ + 'content' => $content, + 'title' => $title, + 'metaTitle' => $title . ' | توثيق قيد', + 'metaDescription' => $metaDescription, + 'sidebar' => $sidebar, + 'currentPath' => $normalizedPath, + 'navigation' => [ + 'prev' => $prev, + 'next' => $next, + ], + ]); + } catch (\Throwable $e) { + return response("Docs Error: " . $e->getMessage() . " in " . $e->getFile() . ":" . $e->getLine(), 200) + ->header('Content-Type', 'text/plain'); + } + } + + private function getSidebar($dir, $baseDir = null) + { + if (!$baseDir) $baseDir = $dir; + $items = []; + if (!File::isDirectory($dir)) return []; + + $files = File::files($dir); + $directories = File::directories($dir); + + foreach ($files as $file) { + $name = $file->getFilename(); + if (in_array($name, ['_category_.json', 'README.md', 'index.md', 'README.mdx', 'index.mdx'])) continue; + + $content = File::get($file->getPathname()); + $position = $this->extractPosition($content, $name); + $label = $this->extractTitle($content) ?? $this->formatLabel($name); + + $relativePath = str_replace($baseDir . DIRECTORY_SEPARATOR, '', $file->getPathname()); + $relativePath = str_replace(['.mdx', '.md'], '', $relativePath); + $relativePath = str_replace(DIRECTORY_SEPARATOR, '/', $relativePath); + + $items[] = [ + 'type' => 'link', + 'label' => $label, + 'href' => '/docs/' . $relativePath, + 'path' => $relativePath, + 'position' => $position + ]; + } + + foreach ($directories as $directory) { + $name = basename($directory); + + // Skip private segments entirely from sidebar + foreach (self::PRIVATE_SEGMENTS as $segment) { + if ($name === $segment) continue 2; + } + + $categoryFile = $directory . DIRECTORY_SEPARATOR . '_category_.json'; + $label = $this->formatLabel($name); + $position = $this->extractPosition('', $name); + + $indexFile = null; + $indexExtensions = ['README.md', 'index.md', 'README.mdx', 'index.mdx']; + foreach ($indexExtensions as $ext) { + if (File::exists($directory . DIRECTORY_SEPARATOR . $ext)) { + $idxContent = File::get($directory . DIRECTORY_SEPARATOR . $ext); + $label = $this->extractTitle($idxContent) ?? $label; + + $relativePath = str_replace($baseDir . DIRECTORY_SEPARATOR, '', $directory . DIRECTORY_SEPARATOR . $ext); + $relativePath = str_replace(['.mdx', '.md'], '', $relativePath); + $indexFile = str_replace(DIRECTORY_SEPARATOR, '/', $relativePath); + break; + } + } + + if (File::exists($categoryFile)) { + $category = json_decode(File::get($categoryFile), true); + $label = $category['label'] ?? $label; + $position = $category['position'] ?? $position; + } + + $items[] = [ + 'type' => 'category', + 'label' => $label, + 'href' => $indexFile ? '/docs/' . $indexFile : null, + 'path' => $indexFile, + 'items' => $this->getSidebar($directory, $baseDir), + 'position' => $position + ]; + } + + usort($items, function ($a, $b) { + if (($a['position'] ?? 999) !== ($b['position'] ?? 999)) { + return ($a['position'] ?? 999) <=> ($b['position'] ?? 999); + } + return strnatcmp($a['label'] ?? '', $b['label'] ?? ''); + }); + + return $items; + } + + private function extractTitle($content) + { + if (preg_match('/^title:\s*(.+)$/m', $content, $matches)) { + return trim($matches[1], "\"' "); + } + if (preg_match('/^#\s+(.+)$/m', $content, $matches)) { + return trim($matches[1]); + } + return null; + } + + private function extractPosition($content, $filename) + { + if (preg_match('/^(\d+)_/', $filename, $matches)) { + return (int)$matches[1]; + } + if (preg_match('/^sidebar_position:\s*(-?\d+)$/m', $content, $matches)) { + return (int)$matches[1]; + } + return 999; + } + + private function flattenSidebar($items) + { + $flat = []; + foreach ($items as $item) { + if ($item['type'] === 'link') { + $flat[] = $item; + } else { + if (isset($item['href']) && $item['href']) { + // Category itself is a link + $flat[] = $item; + } + $flat = array_merge($flat, $this->flattenSidebar($item['items'] ?? [])); + } + } + return $flat; + } + + private function formatLabel($name) + { + $name = str_replace(['.md', '.mdx'], '', $name); + $name = preg_replace('/^\d+_/', '', $name); + $name = str_replace(['_', '-'], ' ', $name); + return Str::title($name); + } + + /** + * Extract the first meaningful prose paragraph as a meta description. + * Strips Markdown headings, code blocks, and frontmatter. + */ + private function extractMetaDescription(string $content): string + { + $lines = explode("\n", $content); + $inCode = false; + $inFront = false; + $firstLine = true; + + foreach ($lines as $line) { + $trimmed = trim($line); + + // Skip frontmatter block + if ($firstLine && $trimmed === '---') { + $inFront = true; + $firstLine = false; + continue; + } + if ($inFront) { + if ($trimmed === '---') $inFront = false; + continue; + } + $firstLine = false; + + // Skip code blocks + if (str_starts_with($trimmed, '```') || str_starts_with($trimmed, '~~~')) { + $inCode = !$inCode; + continue; + } + if ($inCode) continue; + + // Skip headings, tables, HTML, empty lines, and list markers + if (empty($trimmed)) continue; + if (str_starts_with($trimmed, '#')) continue; + if (str_starts_with($trimmed, '|')) continue; + if (str_starts_with($trimmed, '<')) continue; + if (str_starts_with($trimmed, '- ')) continue; + if (str_starts_with($trimmed, '* ')) continue; + if (preg_match('/^\d+\.\s/', $trimmed)) continue; + + // Clean inline markdown and return first paragraph + $plain = preg_replace('/[*_`\[\]()#>]/', '', $trimmed); + $plain = trim(preg_replace('/\s+/', ' ', $plain)); + + if (strlen($plain) > 30) { + return Str::limit($plain, 155, ''); + } + } + + return 'توثيق أكاديمية شفيع — تطبيق محاسبة شخصية بالقيد المزدوج الكامل مع تشفير E2EE.'; + } +} diff --git a/package-lock.json b/package-lock.json index 56c631cd..69f02182 100644 --- a/package-lock.json +++ b/package-lock.json @@ -50,8 +50,10 @@ "@tiptap/pm": "^3.29.2", "@tiptap/react": "^3.29.2", "@tiptap/starter-kit": "^3.29.2", + "@types/github-slugger": "^1.3.0", "@types/react": "^19.0.3", "@types/react-dom": "^19.0.2", + "@types/react-syntax-highlighter": "^15.5.13", "@vitejs/plugin-react": "^4.3.4", "axios": "^1.13.2", "class-variance-authority": "^0.7.1", @@ -59,13 +61,18 @@ "cmdk": "^1.1.1", "concurrently": "^9.0.1", "framer-motion": "^12.43.0", + "github-slugger": "^2.0.0", "globals": "^15.14.0", "laravel-vite-plugin": "^1.3.0", "lucide-react": "^0.475.0", "react": "^19.0.0", "react-dom": "^19.0.0", + "react-markdown": "^10.1.0", "react-router-dom": "^7.18.1", + "react-syntax-highlighter": "^16.1.1", "recharts": "^2.15.4", + "rehype-raw": "^7.0.0", + "remark-gfm": "^4.0.1", "tailwind-merge": "^3.0.1", "tailwindcss": "^4.0.0", "tailwindcss-animate": "^1.0.7", @@ -3674,12 +3681,45 @@ "integrity": "sha512-Ps3T8E8dZDam6fUyNiMkekK3XUsaUEik+idO9/YjPtfj2qruF8tFBXS7XhtE4iIXBLxhmLjP3SXpLhVf21I9Lw==", "license": "MIT" }, + "node_modules/@types/debug": { + "version": "4.1.13", + "resolved": "https://registry.npmjs.org/@types/debug/-/debug-4.1.13.tgz", + "integrity": "sha512-KSVgmQmzMwPlmtljOomayoR89W4FynCAi3E8PPs7vmDVPe84hT+vGPKkJfThkmXs0x0jAaa9U8uW8bbfyS2fWw==", + "license": "MIT", + "dependencies": { + "@types/ms": "*" + } + }, "node_modules/@types/estree": { "version": "1.0.9", "resolved": "https://registry.npmjs.org/@types/estree/-/estree-1.0.9.tgz", "integrity": "sha512-GhdPgy1el4/ImP05X05Uw4cw2/M93BCUmnEvWZNStlCzEKME4Fkk+YpoA5OiHNQmoS7Cafb8Xa3Pya8m1Qrzeg==", "license": "MIT" }, + "node_modules/@types/estree-jsx": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/@types/estree-jsx/-/estree-jsx-1.0.5.tgz", + "integrity": "sha512-52CcUVNFyfb1A2ALocQw/Dd1BQFNmSdkuC3BkZ6iqhdMfQz7JWOFRuJFloOzjk+6WijU56m9oKXFAXc7o3Towg==", + "license": "MIT", + "dependencies": { + "@types/estree": "*" + } + }, + "node_modules/@types/github-slugger": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/@types/github-slugger/-/github-slugger-1.3.0.tgz", + "integrity": "sha512-J/rMZa7RqiH/rT29TEVZO4nBoDP9XJOjnbbIofg7GQKs4JIduEO3WLpte+6WeUz/TcrXKlY+bM7FYrp8yFB+3g==", + "license": "MIT" + }, + "node_modules/@types/hast": { + "version": "3.0.5", + "resolved": "https://registry.npmjs.org/@types/hast/-/hast-3.0.5.tgz", + "integrity": "sha512-rp/ezSWaD1m44dPKICGhiskI13nVr7qTloFwDa/IYkhhf5nzwP+zIQcIJh3WIFSBOy/H1PzB40jPjMDksN4F+g==", + "license": "MIT", + "dependencies": { + "@types/unist": "*" + } + }, "node_modules/@types/json-schema": { "version": "7.0.15", "resolved": "https://registry.npmjs.org/@types/json-schema/-/json-schema-7.0.15.tgz", @@ -3702,6 +3742,21 @@ "@types/lodash": "*" } }, + "node_modules/@types/mdast": { + "version": "4.0.4", + "resolved": "https://registry.npmjs.org/@types/mdast/-/mdast-4.0.4.tgz", + "integrity": "sha512-kGaNbPh1k7AFzgpud/gMdvIm5xuECykRR+JnWKQno9TAXVa6WIVCGTPvYGekIDL4uwCZQSYbUxNBSb1aUo79oA==", + "license": "MIT", + "dependencies": { + "@types/unist": "*" + } + }, + "node_modules/@types/ms": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/@types/ms/-/ms-2.1.0.tgz", + "integrity": "sha512-GsCCIZDE/p3i96vtEqx+7dBUGXrc7zeSK3wwPHIaRThS+9OhWIXRqzs4d6k1SVU8g91DrNRWxWUGhp5KXQb2VA==", + "license": "MIT" + }, "node_modules/@types/node": { "version": "22.20.1", "resolved": "https://registry.npmjs.org/@types/node/-/node-22.20.1.tgz", @@ -3712,6 +3767,12 @@ "undici-types": "~6.21.0" } }, + "node_modules/@types/prismjs": { + "version": "1.26.6", + "resolved": "https://registry.npmjs.org/@types/prismjs/-/prismjs-1.26.6.tgz", + "integrity": "sha512-vqlvI7qlMvcCBbVe0AKAb4f97//Hy0EBTaiW8AalRnG/xAN5zOiWWyrNqNXeq8+KAuvRewjCVY1+IPxk4RdNYw==", + "license": "MIT" + }, "node_modules/@types/react": { "version": "19.2.18", "resolved": "https://registry.npmjs.org/@types/react/-/react-19.2.18.tgz", @@ -3730,6 +3791,15 @@ "@types/react": "^19.2.0" } }, + "node_modules/@types/react-syntax-highlighter": { + "version": "15.5.13", + "resolved": "https://registry.npmjs.org/@types/react-syntax-highlighter/-/react-syntax-highlighter-15.5.13.tgz", + "integrity": "sha512-uLGJ87j6Sz8UaBAooU0T6lWJ0dBmjZgN1PZTrj05TNql2/XpC6+4HhMT5syIdFUUt+FASfCeLLv4kBygNU+8qA==", + "license": "MIT", + "dependencies": { + "@types/react": "*" + } + }, "node_modules/@types/ua-parser-js": { "version": "0.7.39", "resolved": "https://registry.npmjs.org/@types/ua-parser-js/-/ua-parser-js-0.7.39.tgz", @@ -3737,6 +3807,12 @@ "dev": true, "license": "MIT" }, + "node_modules/@types/unist": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/@types/unist/-/unist-3.0.3.tgz", + "integrity": "sha512-ko/gIFJRv177XgZsZcBwnqJN5x/Gien8qNOn0D5bQU/zAzVf9Zt3BlcUiLqhV9y4ARk0GbT3tnUiPNgnTXzc/Q==", + "license": "MIT" + }, "node_modules/@types/use-sync-external-store": { "version": "0.0.6", "resolved": "https://registry.npmjs.org/@types/use-sync-external-store/-/use-sync-external-store-0.0.6.tgz", @@ -4038,6 +4114,12 @@ "url": "https://opencollective.com/eslint" } }, + "node_modules/@ungap/structured-clone": { + "version": "1.3.3", + "resolved": "https://registry.npmjs.org/@ungap/structured-clone/-/structured-clone-1.3.3.tgz", + "integrity": "sha512-60YRaenCQcVjYEKOcG824+DRGGIQ3VKErcBoAEDJZz5bKIs2ZG+X/H9Nk+Q6EVkwJk5QNApxbrc5QtBSwtrXAg==", + "license": "ISC" + }, "node_modules/@vitejs/plugin-react": { "version": "4.7.0", "resolved": "https://registry.npmjs.org/@vitejs/plugin-react/-/plugin-react-4.7.0.tgz", @@ -4335,6 +4417,16 @@ "proxy-from-env": "^2.1.0" } }, + "node_modules/bail": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/bail/-/bail-2.0.2.tgz", + "integrity": "sha512-0xO6mYd7JB2YesxDKplafRpsiOzPt9V02ddPCLbY1xYGPOX24NTyN50qnUxgCPcSoYMhKpAuBTjQoRZCAkUDRw==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, "node_modules/balanced-match": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.2.tgz", @@ -4476,6 +4568,16 @@ ], "license": "CC-BY-4.0" }, + "node_modules/ccount": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/ccount/-/ccount-2.0.1.tgz", + "integrity": "sha512-eyrF0jiFpY+3drT6383f1qhkbGsLSifNAjA61IUjZjmLCWjItY6LB9ft9YhoDgwfmclB2zhu51Lc7+95b8NRAg==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, "node_modules/chalk": { "version": "4.1.2", "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", @@ -4504,6 +4606,46 @@ "node": ">=8" } }, + "node_modules/character-entities": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/character-entities/-/character-entities-2.0.2.tgz", + "integrity": "sha512-shx7oQ0Awen/BRIdkjkvz54PnEEI/EjwXDSIZp86/KKdbafHh1Df/RYGBhn4hbe2+uKC9FnT5UCEdyPz3ai9hQ==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/character-entities-html4": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/character-entities-html4/-/character-entities-html4-2.1.0.tgz", + "integrity": "sha512-1v7fgQRj6hnSwFpq1Eu0ynr/CDEw0rXo2B61qXrLNdHZmPKgb7fqS1a2JwF0rISo9q77jDI8VMEHoApn8qDoZA==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/character-entities-legacy": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/character-entities-legacy/-/character-entities-legacy-3.0.0.tgz", + "integrity": "sha512-RpPp0asT/6ufRm//AJVwpViZbGM/MkjQFxJccQRHmISF/22NBtsHqAWmL+/pmkPWoIUJdWyeVleTl1wydHATVQ==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/character-reference-invalid": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/character-reference-invalid/-/character-reference-invalid-2.0.1.tgz", + "integrity": "sha512-iBZ4F4wRbyORVsu0jPV7gXkOsGYjGHPmAyv+HiHG8gi5PtC9KI2j1+v8/tlibRvjoWX027ypmG/n0HtO5t7unw==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, "node_modules/class-variance-authority": { "version": "0.7.1", "resolved": "https://registry.npmjs.org/class-variance-authority/-/class-variance-authority-0.7.1.tgz", @@ -4585,6 +4727,16 @@ "node": ">= 0.8" } }, + "node_modules/comma-separated-tokens": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/comma-separated-tokens/-/comma-separated-tokens-2.0.3.tgz", + "integrity": "sha512-Fu4hJdvzeylCfQPp9SGWidpzrMs7tTrlu6Vb8XGaRGck8QSNZJJp538Wrb60Lax4fPwR64ViY468OIUTbRlGZg==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, "node_modules/concat-map": { "version": "0.0.1", "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", @@ -4854,6 +5006,19 @@ "integrity": "sha512-qIMFpTMZmny+MMIitAB6D7iVPEorVw6YQRWkvarTkT4tBeSLLiHzcwj6q0MmYSFCiVpiqPJTJEYIrpcPzVEIvg==", "license": "MIT" }, + "node_modules/decode-named-character-reference": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/decode-named-character-reference/-/decode-named-character-reference-1.3.0.tgz", + "integrity": "sha512-GtpQYB283KrPp6nRw50q3U9/VfOutZOe103qlN7BPP6Ad27xYnOIWv4lPzo8HCAL+mMZofJ9KEy30fq6MfaK6Q==", + "license": "MIT", + "dependencies": { + "character-entities": "^2.0.0" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, "node_modules/deep-is": { "version": "0.1.4", "resolved": "https://registry.npmjs.org/deep-is/-/deep-is-0.1.4.tgz", @@ -4906,6 +5071,15 @@ "node": ">=0.4.0" } }, + "node_modules/dequal": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/dequal/-/dequal-2.0.3.tgz", + "integrity": "sha512-0je+qPKHEMohvfRTCEo3CrPG6cAzAYgmzKyxRiYSSDkS6eGJdyVJm7WaYA5ECaAD9wLB2T4EEeymA5aFVcYXCA==", + "license": "MIT", + "engines": { + "node": ">=6" + } + }, "node_modules/detect-europe-js": { "version": "0.1.2", "resolved": "https://registry.npmjs.org/detect-europe-js/-/detect-europe-js-0.1.2.tgz", @@ -4941,6 +5115,19 @@ "integrity": "sha512-ypdmJU/TbBby2Dxibuv7ZLW3Bs1QEmM7nHjEANfohJLvE0XVujisn1qPJcZxg+qDucsr+bP6fLD1rPS3AhJ7EQ==", "license": "MIT" }, + "node_modules/devlop": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/devlop/-/devlop-1.1.0.tgz", + "integrity": "sha512-RWmIqhcFf1lRYBvNmr7qTNuyCt/7/ns2jbpp1+PalgE/rDQcBT0fioSMUpJ93irlUhC5hrg4cYqe6U+0ImW0rA==", + "license": "MIT", + "dependencies": { + "dequal": "^2.0.0" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, "node_modules/doctrine": { "version": "2.1.0", "resolved": "https://registry.npmjs.org/doctrine/-/doctrine-2.1.0.tgz", @@ -5003,6 +5190,18 @@ "node": ">=10.13.0" } }, + "node_modules/entities": { + "version": "6.0.1", + "resolved": "https://registry.npmjs.org/entities/-/entities-6.0.1.tgz", + "integrity": "sha512-aN97NXWF6AWBTahfVOIrB/NShkzi5H7F9r1s9mD3cDj4Ko5f2qhhVoYMibXF7GlLveb/D2ioWay8lxI97Ven3g==", + "license": "BSD-2-Clause", + "engines": { + "node": ">=0.12" + }, + "funding": { + "url": "https://github.com/fb55/entities?sponsor=1" + } + }, "node_modules/es-abstract": { "version": "1.24.2", "resolved": "https://registry.npmjs.org/es-abstract/-/es-abstract-1.24.2.tgz", @@ -5467,6 +5666,16 @@ "node": ">=4.0" } }, + "node_modules/estree-util-is-identifier-name": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/estree-util-is-identifier-name/-/estree-util-is-identifier-name-3.0.0.tgz", + "integrity": "sha512-hFtqIDZTIUZ9BXLb8y4pYGyk6+wekIivNVTcmvk8NoOh+VeRn5y6cEHzbURrWbfp1fIqdVipilzj+lfaadNZmg==", + "license": "MIT", + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, "node_modules/esutils": { "version": "2.0.3", "resolved": "https://registry.npmjs.org/esutils/-/esutils-2.0.3.tgz", @@ -5483,6 +5692,12 @@ "integrity": "sha512-8guHBZCwKnFhYdHr2ysuRWErTwhoN2X8XELRlrRwpmfeY2jjuUN4taQMsULKUVo1K4DvZl+0pgfyoysHxvmvEw==", "license": "MIT" }, + "node_modules/extend": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/extend/-/extend-3.0.2.tgz", + "integrity": "sha512-fjquC59cD7CyW6urNXK0FBufkZcoiGG80wTuPujX590cB5Ttln20E2UB4S/WARVqhXffZl2LNgS+gQdPIIim/g==", + "license": "MIT" + }, "node_modules/fast-deep-equal": { "version": "3.1.3", "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-3.1.3.tgz", @@ -5513,6 +5728,19 @@ "dev": true, "license": "MIT" }, + "node_modules/fault": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/fault/-/fault-1.0.4.tgz", + "integrity": "sha512-CJ0HCB5tL5fYTEA7ToAq5+kTwd++Borf1/bifxd9iT70QcXr4MRrO3Llf8Ifs70q+SJcGHFtnIE/Nw6giCtECA==", + "license": "MIT", + "dependencies": { + "format": "^0.2.0" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, "node_modules/fdir": { "version": "6.5.0", "resolved": "https://registry.npmjs.org/fdir/-/fdir-6.5.0.tgz", @@ -5633,6 +5861,14 @@ "node": ">= 6" } }, + "node_modules/format": { + "version": "0.2.2", + "resolved": "https://registry.npmjs.org/format/-/format-0.2.2.tgz", + "integrity": "sha512-wzsgA6WOq+09wrU1tsJ09udeR/YZRaeArL9e1wPbFg3GG2yDnC2ldKpxs4xunpFF9DgqCqOIra3bc1HWrJ37Ww==", + "engines": { + "node": ">=0.4.x" + } + }, "node_modules/framer-motion": { "version": "12.43.0", "resolved": "https://registry.npmjs.org/framer-motion/-/framer-motion-12.43.0.tgz", @@ -5809,6 +6045,12 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/github-slugger": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/github-slugger/-/github-slugger-2.0.0.tgz", + "integrity": "sha512-IaOQ9puYtjrkq7Y0Ygl9KDZnrf/aiUJYUpVf89y8kyaxbRG7Y1SrX/jaumrv81vc61+kiMempujsM3Yw7w5qcw==", + "license": "ISC" + }, "node_modules/glob-parent": { "version": "6.0.2", "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-6.0.2.tgz", @@ -5959,6 +6201,175 @@ "node": ">= 0.4" } }, + "node_modules/hast-util-from-parse5": { + "version": "8.0.3", + "resolved": "https://registry.npmjs.org/hast-util-from-parse5/-/hast-util-from-parse5-8.0.3.tgz", + "integrity": "sha512-3kxEVkEKt0zvcZ3hCRYI8rqrgwtlIOFMWkbclACvjlDw8Li9S2hk/d51OI0nr/gIpdMHNepwgOKqZ/sy0Clpyg==", + "license": "MIT", + "dependencies": { + "@types/hast": "^3.0.0", + "@types/unist": "^3.0.0", + "devlop": "^1.0.0", + "hastscript": "^9.0.0", + "property-information": "^7.0.0", + "vfile": "^6.0.0", + "vfile-location": "^5.0.0", + "web-namespaces": "^2.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/hast-util-parse-selector": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/hast-util-parse-selector/-/hast-util-parse-selector-4.0.0.tgz", + "integrity": "sha512-wkQCkSYoOGCRKERFWcxMVMOcYE2K1AaNLU8DXS9arxnLOUEWbOXKXiJUNzEpqZ3JOKpnha3jkFrumEjVliDe7A==", + "license": "MIT", + "dependencies": { + "@types/hast": "^3.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/hast-util-raw": { + "version": "9.1.0", + "resolved": "https://registry.npmjs.org/hast-util-raw/-/hast-util-raw-9.1.0.tgz", + "integrity": "sha512-Y8/SBAHkZGoNkpzqqfCldijcuUKh7/su31kEBp67cFY09Wy0mTRgtsLYsiIxMJxlu0f6AA5SUTbDR8K0rxnbUw==", + "license": "MIT", + "dependencies": { + "@types/hast": "^3.0.0", + "@types/unist": "^3.0.0", + "@ungap/structured-clone": "^1.0.0", + "hast-util-from-parse5": "^8.0.0", + "hast-util-to-parse5": "^8.0.0", + "html-void-elements": "^3.0.0", + "mdast-util-to-hast": "^13.0.0", + "parse5": "^7.0.0", + "unist-util-position": "^5.0.0", + "unist-util-visit": "^5.0.0", + "vfile": "^6.0.0", + "web-namespaces": "^2.0.0", + "zwitch": "^2.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/hast-util-to-jsx-runtime": { + "version": "2.3.6", + "resolved": "https://registry.npmjs.org/hast-util-to-jsx-runtime/-/hast-util-to-jsx-runtime-2.3.6.tgz", + "integrity": "sha512-zl6s8LwNyo1P9uw+XJGvZtdFF1GdAkOg8ujOw+4Pyb76874fLps4ueHXDhXWdk6YHQ6OgUtinliG7RsYvCbbBg==", + "license": "MIT", + "dependencies": { + "@types/estree": "^1.0.0", + "@types/hast": "^3.0.0", + "@types/unist": "^3.0.0", + "comma-separated-tokens": "^2.0.0", + "devlop": "^1.0.0", + "estree-util-is-identifier-name": "^3.0.0", + "hast-util-whitespace": "^3.0.0", + "mdast-util-mdx-expression": "^2.0.0", + "mdast-util-mdx-jsx": "^3.0.0", + "mdast-util-mdxjs-esm": "^2.0.0", + "property-information": "^7.0.0", + "space-separated-tokens": "^2.0.0", + "style-to-js": "^1.0.0", + "unist-util-position": "^5.0.0", + "vfile-message": "^4.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/hast-util-to-parse5": { + "version": "8.0.1", + "resolved": "https://registry.npmjs.org/hast-util-to-parse5/-/hast-util-to-parse5-8.0.1.tgz", + "integrity": "sha512-MlWT6Pjt4CG9lFCjiz4BH7l9wmrMkfkJYCxFwKQic8+RTZgWPuWxwAfjJElsXkex7DJjfSJsQIt931ilUgmwdA==", + "license": "MIT", + "dependencies": { + "@types/hast": "^3.0.0", + "comma-separated-tokens": "^2.0.0", + "devlop": "^1.0.0", + "property-information": "^7.0.0", + "space-separated-tokens": "^2.0.0", + "web-namespaces": "^2.0.0", + "zwitch": "^2.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/hast-util-whitespace": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/hast-util-whitespace/-/hast-util-whitespace-3.0.0.tgz", + "integrity": "sha512-88JUN06ipLwsnv+dVn+OIYOvAuvBMy/Qoi6O7mQHxdPXpjy+Cd6xRkWwux7DKO+4sYILtLBRIKgsdpS2gQc7qw==", + "license": "MIT", + "dependencies": { + "@types/hast": "^3.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/hastscript": { + "version": "9.0.1", + "resolved": "https://registry.npmjs.org/hastscript/-/hastscript-9.0.1.tgz", + "integrity": "sha512-g7df9rMFX/SPi34tyGCyUBREQoKkapwdY/T04Qn9TDWfHhAYt4/I0gMVirzK5wEzeUqIjEB+LXC/ypb7Aqno5w==", + "license": "MIT", + "dependencies": { + "@types/hast": "^3.0.0", + "comma-separated-tokens": "^2.0.0", + "hast-util-parse-selector": "^4.0.0", + "property-information": "^7.0.0", + "space-separated-tokens": "^2.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/highlight.js": { + "version": "10.7.3", + "resolved": "https://registry.npmjs.org/highlight.js/-/highlight.js-10.7.3.tgz", + "integrity": "sha512-tzcUFauisWKNHaRkN4Wjl/ZA07gENAjFl3J/c480dprkGTg5EQstgaNFqBfUqCq54kZRIEcreTsAgF/m2quD7A==", + "license": "BSD-3-Clause", + "engines": { + "node": "*" + } + }, + "node_modules/highlightjs-vue": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/highlightjs-vue/-/highlightjs-vue-1.0.0.tgz", + "integrity": "sha512-PDEfEF102G23vHmPhLyPboFCD+BkMGu+GuJe2d9/eH4FsCwvgBpnc9n0pGE+ffKdph38s6foEZiEjdgHdzp+IA==", + "license": "CC0-1.0" + }, + "node_modules/html-url-attributes": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/html-url-attributes/-/html-url-attributes-3.0.1.tgz", + "integrity": "sha512-ol6UPyBWqsrO6EJySPz2O7ZSr856WDrEzM5zMqp+FJJLGMW35cLYmmZnl0vztAZxRUoNZJFTCohfjuIJ8I4QBQ==", + "license": "MIT", + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/html-void-elements": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/html-void-elements/-/html-void-elements-3.0.0.tgz", + "integrity": "sha512-bEqo66MRXsUGxWHV5IP0PUiAWwoEjba4VCzg0LjFJBpchPaTfyfCKTG6bc5F8ucKec3q5y6qOdGyYTSBEvhCrg==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, "node_modules/https-proxy-agent": { "version": "5.0.1", "resolved": "https://registry.npmjs.org/https-proxy-agent/-/https-proxy-agent-5.0.1.tgz", @@ -6009,6 +6420,12 @@ "node": ">=0.8.19" } }, + "node_modules/inline-style-parser": { + "version": "0.2.7", + "resolved": "https://registry.npmjs.org/inline-style-parser/-/inline-style-parser-0.2.7.tgz", + "integrity": "sha512-Nb2ctOyNR8DqQoR0OwRG95uNWIC0C1lCgf5Naz5H6Ji72KZ8OcFZLz2P5sNgwlyoJ8Yif11oMuYs5pBQa86csA==", + "license": "MIT" + }, "node_modules/internal-slot": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/internal-slot/-/internal-slot-1.1.0.tgz", @@ -6033,6 +6450,30 @@ "node": ">=12" } }, + "node_modules/is-alphabetical": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/is-alphabetical/-/is-alphabetical-2.0.1.tgz", + "integrity": "sha512-FWyyY60MeTNyeSRpkM2Iry0G9hpr7/9kD40mD/cGQEuilcZYS4okz8SN2Q6rLCJ8gbCt6fN+rC+6tMGS99LaxQ==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/is-alphanumerical": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/is-alphanumerical/-/is-alphanumerical-2.0.1.tgz", + "integrity": "sha512-hmbYhX/9MUMF5uh7tOXyK/n0ZvWpad5caBA17GsC6vyuCqaWliRG5K1qS9inmUhEMaOBIW7/whAnSwveW/LtZw==", + "license": "MIT", + "dependencies": { + "is-alphabetical": "^2.0.0", + "is-decimal": "^2.0.0" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, "node_modules/is-array-buffer": { "version": "3.0.5", "resolved": "https://registry.npmjs.org/is-array-buffer/-/is-array-buffer-3.0.5.tgz", @@ -6168,6 +6609,16 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/is-decimal": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/is-decimal/-/is-decimal-2.0.1.tgz", + "integrity": "sha512-AAB9hiomQs5DXWcRB1rqsxGUstbRroFOPPVAomNk/3XHR5JyEZChOyTWe2oayKnsSsr/kcGqF+z6yuH6HHpN0A==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, "node_modules/is-document.all": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/is-document.all/-/is-document.all-1.0.0.tgz", @@ -6252,6 +6703,16 @@ "node": ">=0.10.0" } }, + "node_modules/is-hexadecimal": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/is-hexadecimal/-/is-hexadecimal-2.0.1.tgz", + "integrity": "sha512-DgZQp241c8oO6cA1SbTEWiXeoxV42vlcJxgH+B3hi1AiqqKruZR3ZGF8In3fj4+/y/7rHvlOZLZtgJ/4ttYGZg==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, "node_modules/is-map": { "version": "2.0.3", "resolved": "https://registry.npmjs.org/is-map/-/is-map-2.0.3.tgz", @@ -6295,6 +6756,18 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/is-plain-obj": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/is-plain-obj/-/is-plain-obj-4.1.0.tgz", + "integrity": "sha512-+Pgi+vMuUNkJyExiMBt5IlFoMyKnr5zhJ4Uspz58WOhBF5QoIZkFyNHIbBAtHwzVAgk5RtndVNsDRN61/mmDqg==", + "license": "MIT", + "engines": { + "node": ">=12" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, "node_modules/is-regex": { "version": "1.2.1", "resolved": "https://registry.npmjs.org/is-regex/-/is-regex-1.2.1.tgz", @@ -6954,6 +7427,16 @@ "dev": true, "license": "MIT" }, + "node_modules/longest-streak": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/longest-streak/-/longest-streak-3.1.0.tgz", + "integrity": "sha512-9Ri+o0JYgehTaVBBDoMqIl8GXtbWg711O3srftcHhZ0dqnETqLaoIK0x17fUw9rFSlK/0NlsKe0Ahhyl5pXE2g==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, "node_modules/loose-envify": { "version": "1.4.0", "resolved": "https://registry.npmjs.org/loose-envify/-/loose-envify-1.4.0.tgz", @@ -6966,6 +7449,20 @@ "loose-envify": "cli.js" } }, + "node_modules/lowlight": { + "version": "1.20.0", + "resolved": "https://registry.npmjs.org/lowlight/-/lowlight-1.20.0.tgz", + "integrity": "sha512-8Ktj+prEb1RoCPkEOrPMYUN/nCggB7qAWe3a7OpMjWQkh3l2RD5wKRQ+o8Q8YuI9RG/xs95waaI/E6ym/7NsTw==", + "license": "MIT", + "dependencies": { + "fault": "^1.0.0", + "highlight.js": "~10.7.0" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, "node_modules/lru-cache": { "version": "5.1.1", "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-5.1.1.tgz", @@ -6993,6 +7490,16 @@ "@jridgewell/sourcemap-codec": "^1.5.5" } }, + "node_modules/markdown-table": { + "version": "3.0.4", + "resolved": "https://registry.npmjs.org/markdown-table/-/markdown-table-3.0.4.tgz", + "integrity": "sha512-wiYz4+JrLyb/DqW2hkFJxP7Vd7JuTDm77fvbM8VfEQdmSMqcImWeeRbHwZjBjIFki/VaMK2BhFi7oUUZeM5bqw==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, "node_modules/math-intrinsics": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/math-intrinsics/-/math-intrinsics-1.1.0.tgz", @@ -7002,6 +7509,851 @@ "node": ">= 0.4" } }, + "node_modules/mdast-util-find-and-replace": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/mdast-util-find-and-replace/-/mdast-util-find-and-replace-3.0.2.tgz", + "integrity": "sha512-Tmd1Vg/m3Xz43afeNxDIhWRtFZgM2VLyaf4vSTYwudTyeuTneoL3qtWMA5jeLyz/O1vDJmmV4QuScFCA2tBPwg==", + "license": "MIT", + "dependencies": { + "@types/mdast": "^4.0.0", + "escape-string-regexp": "^5.0.0", + "unist-util-is": "^6.0.0", + "unist-util-visit-parents": "^6.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/mdast-util-find-and-replace/node_modules/escape-string-regexp": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-5.0.0.tgz", + "integrity": "sha512-/veY75JbMK4j1yjvuUxuVsiS/hr/4iHs9FTT6cgTexxdE0Ly/glccBAkloH/DofkjRbZU3bnoj38mOmhkZ0lHw==", + "license": "MIT", + "engines": { + "node": ">=12" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/mdast-util-from-markdown": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/mdast-util-from-markdown/-/mdast-util-from-markdown-2.0.3.tgz", + "integrity": "sha512-W4mAWTvSlKvf8L6J+VN9yLSqQ9AOAAvHuoDAmPkz4dHf553m5gVj2ejadHJhoJmcmxEnOv6Pa8XJhpxE93kb8Q==", + "license": "MIT", + "dependencies": { + "@types/mdast": "^4.0.0", + "@types/unist": "^3.0.0", + "decode-named-character-reference": "^1.0.0", + "devlop": "^1.0.0", + "mdast-util-to-string": "^4.0.0", + "micromark": "^4.0.0", + "micromark-util-decode-numeric-character-reference": "^2.0.0", + "micromark-util-decode-string": "^2.0.0", + "micromark-util-normalize-identifier": "^2.0.0", + "micromark-util-symbol": "^2.0.0", + "micromark-util-types": "^2.0.0", + "unist-util-stringify-position": "^4.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/mdast-util-gfm": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/mdast-util-gfm/-/mdast-util-gfm-3.1.0.tgz", + "integrity": "sha512-0ulfdQOM3ysHhCJ1p06l0b0VKlhU0wuQs3thxZQagjcjPrlFRqY215uZGHHJan9GEAXd9MbfPjFJz+qMkVR6zQ==", + "license": "MIT", + "dependencies": { + "mdast-util-from-markdown": "^2.0.0", + "mdast-util-gfm-autolink-literal": "^2.0.0", + "mdast-util-gfm-footnote": "^2.0.0", + "mdast-util-gfm-strikethrough": "^2.0.0", + "mdast-util-gfm-table": "^2.0.0", + "mdast-util-gfm-task-list-item": "^2.0.0", + "mdast-util-to-markdown": "^2.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/mdast-util-gfm-autolink-literal": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/mdast-util-gfm-autolink-literal/-/mdast-util-gfm-autolink-literal-2.0.1.tgz", + "integrity": "sha512-5HVP2MKaP6L+G6YaxPNjuL0BPrq9orG3TsrZ9YXbA3vDw/ACI4MEsnoDpn6ZNm7GnZgtAcONJyPhOP8tNJQavQ==", + "license": "MIT", + "dependencies": { + "@types/mdast": "^4.0.0", + "ccount": "^2.0.0", + "devlop": "^1.0.0", + "mdast-util-find-and-replace": "^3.0.0", + "micromark-util-character": "^2.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/mdast-util-gfm-footnote": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/mdast-util-gfm-footnote/-/mdast-util-gfm-footnote-2.1.0.tgz", + "integrity": "sha512-sqpDWlsHn7Ac9GNZQMeUzPQSMzR6Wv0WKRNvQRg0KqHh02fpTz69Qc1QSseNX29bhz1ROIyNyxExfawVKTm1GQ==", + "license": "MIT", + "dependencies": { + "@types/mdast": "^4.0.0", + "devlop": "^1.1.0", + "mdast-util-from-markdown": "^2.0.0", + "mdast-util-to-markdown": "^2.0.0", + "micromark-util-normalize-identifier": "^2.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/mdast-util-gfm-strikethrough": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/mdast-util-gfm-strikethrough/-/mdast-util-gfm-strikethrough-2.0.0.tgz", + "integrity": "sha512-mKKb915TF+OC5ptj5bJ7WFRPdYtuHv0yTRxK2tJvi+BDqbkiG7h7u/9SI89nRAYcmap2xHQL9D+QG/6wSrTtXg==", + "license": "MIT", + "dependencies": { + "@types/mdast": "^4.0.0", + "mdast-util-from-markdown": "^2.0.0", + "mdast-util-to-markdown": "^2.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/mdast-util-gfm-table": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/mdast-util-gfm-table/-/mdast-util-gfm-table-2.0.0.tgz", + "integrity": "sha512-78UEvebzz/rJIxLvE7ZtDd/vIQ0RHv+3Mh5DR96p7cS7HsBhYIICDBCu8csTNWNO6tBWfqXPWekRuj2FNOGOZg==", + "license": "MIT", + "dependencies": { + "@types/mdast": "^4.0.0", + "devlop": "^1.0.0", + "markdown-table": "^3.0.0", + "mdast-util-from-markdown": "^2.0.0", + "mdast-util-to-markdown": "^2.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/mdast-util-gfm-task-list-item": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/mdast-util-gfm-task-list-item/-/mdast-util-gfm-task-list-item-2.0.0.tgz", + "integrity": "sha512-IrtvNvjxC1o06taBAVJznEnkiHxLFTzgonUdy8hzFVeDun0uTjxxrRGVaNFqkU1wJR3RBPEfsxmU6jDWPofrTQ==", + "license": "MIT", + "dependencies": { + "@types/mdast": "^4.0.0", + "devlop": "^1.0.0", + "mdast-util-from-markdown": "^2.0.0", + "mdast-util-to-markdown": "^2.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/mdast-util-mdx-expression": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/mdast-util-mdx-expression/-/mdast-util-mdx-expression-2.0.1.tgz", + "integrity": "sha512-J6f+9hUp+ldTZqKRSg7Vw5V6MqjATc+3E4gf3CFNcuZNWD8XdyI6zQ8GqH7f8169MM6P7hMBRDVGnn7oHB9kXQ==", + "license": "MIT", + "dependencies": { + "@types/estree-jsx": "^1.0.0", + "@types/hast": "^3.0.0", + "@types/mdast": "^4.0.0", + "devlop": "^1.0.0", + "mdast-util-from-markdown": "^2.0.0", + "mdast-util-to-markdown": "^2.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/mdast-util-mdx-jsx": { + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/mdast-util-mdx-jsx/-/mdast-util-mdx-jsx-3.2.0.tgz", + "integrity": "sha512-lj/z8v0r6ZtsN/cGNNtemmmfoLAFZnjMbNyLzBafjzikOM+glrjNHPlf6lQDOTccj9n5b0PPihEBbhneMyGs1Q==", + "license": "MIT", + "dependencies": { + "@types/estree-jsx": "^1.0.0", + "@types/hast": "^3.0.0", + "@types/mdast": "^4.0.0", + "@types/unist": "^3.0.0", + "ccount": "^2.0.0", + "devlop": "^1.1.0", + "mdast-util-from-markdown": "^2.0.0", + "mdast-util-to-markdown": "^2.0.0", + "parse-entities": "^4.0.0", + "stringify-entities": "^4.0.0", + "unist-util-stringify-position": "^4.0.0", + "vfile-message": "^4.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/mdast-util-mdxjs-esm": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/mdast-util-mdxjs-esm/-/mdast-util-mdxjs-esm-2.0.1.tgz", + "integrity": "sha512-EcmOpxsZ96CvlP03NghtH1EsLtr0n9Tm4lPUJUBccV9RwUOneqSycg19n5HGzCf+10LozMRSObtVr3ee1WoHtg==", + "license": "MIT", + "dependencies": { + "@types/estree-jsx": "^1.0.0", + "@types/hast": "^3.0.0", + "@types/mdast": "^4.0.0", + "devlop": "^1.0.0", + "mdast-util-from-markdown": "^2.0.0", + "mdast-util-to-markdown": "^2.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/mdast-util-phrasing": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/mdast-util-phrasing/-/mdast-util-phrasing-4.1.0.tgz", + "integrity": "sha512-TqICwyvJJpBwvGAMZjj4J2n0X8QWp21b9l0o7eXyVJ25YNWYbJDVIyD1bZXE6WtV6RmKJVYmQAKWa0zWOABz2w==", + "license": "MIT", + "dependencies": { + "@types/mdast": "^4.0.0", + "unist-util-is": "^6.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/mdast-util-to-hast": { + "version": "13.2.1", + "resolved": "https://registry.npmjs.org/mdast-util-to-hast/-/mdast-util-to-hast-13.2.1.tgz", + "integrity": "sha512-cctsq2wp5vTsLIcaymblUriiTcZd0CwWtCbLvrOzYCDZoWyMNV8sZ7krj09FSnsiJi3WVsHLM4k6Dq/yaPyCXA==", + "license": "MIT", + "dependencies": { + "@types/hast": "^3.0.0", + "@types/mdast": "^4.0.0", + "@ungap/structured-clone": "^1.0.0", + "devlop": "^1.0.0", + "micromark-util-sanitize-uri": "^2.0.0", + "trim-lines": "^3.0.0", + "unist-util-position": "^5.0.0", + "unist-util-visit": "^5.0.0", + "vfile": "^6.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/mdast-util-to-markdown": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/mdast-util-to-markdown/-/mdast-util-to-markdown-2.1.2.tgz", + "integrity": "sha512-xj68wMTvGXVOKonmog6LwyJKrYXZPvlwabaryTjLh9LuvovB/KAH+kvi8Gjj+7rJjsFi23nkUxRQv1KqSroMqA==", + "license": "MIT", + "dependencies": { + "@types/mdast": "^4.0.0", + "@types/unist": "^3.0.0", + "longest-streak": "^3.0.0", + "mdast-util-phrasing": "^4.0.0", + "mdast-util-to-string": "^4.0.0", + "micromark-util-classify-character": "^2.0.0", + "micromark-util-decode-string": "^2.0.0", + "unist-util-visit": "^5.0.0", + "zwitch": "^2.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/mdast-util-to-string": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/mdast-util-to-string/-/mdast-util-to-string-4.0.0.tgz", + "integrity": "sha512-0H44vDimn51F0YwvxSJSm0eCDOJTRlmN0R1yBh4HLj9wiV1Dn0QoXGbvFAWj2hSItVTlCmBF1hqKlIyUBVFLPg==", + "license": "MIT", + "dependencies": { + "@types/mdast": "^4.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/micromark": { + "version": "4.0.2", + "resolved": "https://registry.npmjs.org/micromark/-/micromark-4.0.2.tgz", + "integrity": "sha512-zpe98Q6kvavpCr1NPVSCMebCKfD7CA2NqZ+rykeNhONIJBpc1tFKt9hucLGwha3jNTNI8lHpctWJWoimVF4PfA==", + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "license": "MIT", + "dependencies": { + "@types/debug": "^4.0.0", + "debug": "^4.0.0", + "decode-named-character-reference": "^1.0.0", + "devlop": "^1.0.0", + "micromark-core-commonmark": "^2.0.0", + "micromark-factory-space": "^2.0.0", + "micromark-util-character": "^2.0.0", + "micromark-util-chunked": "^2.0.0", + "micromark-util-combine-extensions": "^2.0.0", + "micromark-util-decode-numeric-character-reference": "^2.0.0", + "micromark-util-encode": "^2.0.0", + "micromark-util-normalize-identifier": "^2.0.0", + "micromark-util-resolve-all": "^2.0.0", + "micromark-util-sanitize-uri": "^2.0.0", + "micromark-util-subtokenize": "^2.0.0", + "micromark-util-symbol": "^2.0.0", + "micromark-util-types": "^2.0.0" + } + }, + "node_modules/micromark-core-commonmark": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/micromark-core-commonmark/-/micromark-core-commonmark-2.0.3.tgz", + "integrity": "sha512-RDBrHEMSxVFLg6xvnXmb1Ayr2WzLAWjeSATAoxwKYJV94TeNavgoIdA0a9ytzDSVzBy2YKFK+emCPOEibLeCrg==", + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "license": "MIT", + "dependencies": { + "decode-named-character-reference": "^1.0.0", + "devlop": "^1.0.0", + "micromark-factory-destination": "^2.0.0", + "micromark-factory-label": "^2.0.0", + "micromark-factory-space": "^2.0.0", + "micromark-factory-title": "^2.0.0", + "micromark-factory-whitespace": "^2.0.0", + "micromark-util-character": "^2.0.0", + "micromark-util-chunked": "^2.0.0", + "micromark-util-classify-character": "^2.0.0", + "micromark-util-html-tag-name": "^2.0.0", + "micromark-util-normalize-identifier": "^2.0.0", + "micromark-util-resolve-all": "^2.0.0", + "micromark-util-subtokenize": "^2.0.0", + "micromark-util-symbol": "^2.0.0", + "micromark-util-types": "^2.0.0" + } + }, + "node_modules/micromark-extension-gfm": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/micromark-extension-gfm/-/micromark-extension-gfm-3.0.0.tgz", + "integrity": "sha512-vsKArQsicm7t0z2GugkCKtZehqUm31oeGBV/KVSorWSy8ZlNAv7ytjFhvaryUiCUJYqs+NoE6AFhpQvBTM6Q4w==", + "license": "MIT", + "dependencies": { + "micromark-extension-gfm-autolink-literal": "^2.0.0", + "micromark-extension-gfm-footnote": "^2.0.0", + "micromark-extension-gfm-strikethrough": "^2.0.0", + "micromark-extension-gfm-table": "^2.0.0", + "micromark-extension-gfm-tagfilter": "^2.0.0", + "micromark-extension-gfm-task-list-item": "^2.0.0", + "micromark-util-combine-extensions": "^2.0.0", + "micromark-util-types": "^2.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/micromark-extension-gfm-autolink-literal": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/micromark-extension-gfm-autolink-literal/-/micromark-extension-gfm-autolink-literal-2.1.0.tgz", + "integrity": "sha512-oOg7knzhicgQ3t4QCjCWgTmfNhvQbDDnJeVu9v81r7NltNCVmhPy1fJRX27pISafdjL+SVc4d3l48Gb6pbRypw==", + "license": "MIT", + "dependencies": { + "micromark-util-character": "^2.0.0", + "micromark-util-sanitize-uri": "^2.0.0", + "micromark-util-symbol": "^2.0.0", + "micromark-util-types": "^2.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/micromark-extension-gfm-footnote": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/micromark-extension-gfm-footnote/-/micromark-extension-gfm-footnote-2.1.0.tgz", + "integrity": "sha512-/yPhxI1ntnDNsiHtzLKYnE3vf9JZ6cAisqVDauhp4CEHxlb4uoOTxOCJ+9s51bIB8U1N1FJ1RXOKTIlD5B/gqw==", + "license": "MIT", + "dependencies": { + "devlop": "^1.0.0", + "micromark-core-commonmark": "^2.0.0", + "micromark-factory-space": "^2.0.0", + "micromark-util-character": "^2.0.0", + "micromark-util-normalize-identifier": "^2.0.0", + "micromark-util-sanitize-uri": "^2.0.0", + "micromark-util-symbol": "^2.0.0", + "micromark-util-types": "^2.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/micromark-extension-gfm-strikethrough": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/micromark-extension-gfm-strikethrough/-/micromark-extension-gfm-strikethrough-2.1.0.tgz", + "integrity": "sha512-ADVjpOOkjz1hhkZLlBiYA9cR2Anf8F4HqZUO6e5eDcPQd0Txw5fxLzzxnEkSkfnD0wziSGiv7sYhk/ktvbf1uw==", + "license": "MIT", + "dependencies": { + "devlop": "^1.0.0", + "micromark-util-chunked": "^2.0.0", + "micromark-util-classify-character": "^2.0.0", + "micromark-util-resolve-all": "^2.0.0", + "micromark-util-symbol": "^2.0.0", + "micromark-util-types": "^2.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/micromark-extension-gfm-table": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/micromark-extension-gfm-table/-/micromark-extension-gfm-table-2.1.1.tgz", + "integrity": "sha512-t2OU/dXXioARrC6yWfJ4hqB7rct14e8f7m0cbI5hUmDyyIlwv5vEtooptH8INkbLzOatzKuVbQmAYcbWoyz6Dg==", + "license": "MIT", + "dependencies": { + "devlop": "^1.0.0", + "micromark-factory-space": "^2.0.0", + "micromark-util-character": "^2.0.0", + "micromark-util-symbol": "^2.0.0", + "micromark-util-types": "^2.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/micromark-extension-gfm-tagfilter": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/micromark-extension-gfm-tagfilter/-/micromark-extension-gfm-tagfilter-2.0.0.tgz", + "integrity": "sha512-xHlTOmuCSotIA8TW1mDIM6X2O1SiX5P9IuDtqGonFhEK0qgRI4yeC6vMxEV2dgyr2TiD+2PQ10o+cOhdVAcwfg==", + "license": "MIT", + "dependencies": { + "micromark-util-types": "^2.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/micromark-extension-gfm-task-list-item": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/micromark-extension-gfm-task-list-item/-/micromark-extension-gfm-task-list-item-2.1.0.tgz", + "integrity": "sha512-qIBZhqxqI6fjLDYFTBIa4eivDMnP+OZqsNwmQ3xNLE4Cxwc+zfQEfbs6tzAo2Hjq+bh6q5F+Z8/cksrLFYWQQw==", + "license": "MIT", + "dependencies": { + "devlop": "^1.0.0", + "micromark-factory-space": "^2.0.0", + "micromark-util-character": "^2.0.0", + "micromark-util-symbol": "^2.0.0", + "micromark-util-types": "^2.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/micromark-factory-destination": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/micromark-factory-destination/-/micromark-factory-destination-2.0.1.tgz", + "integrity": "sha512-Xe6rDdJlkmbFRExpTOmRj9N3MaWmbAgdpSrBQvCFqhezUn4AHqJHbaEnfbVYYiexVSs//tqOdY/DxhjdCiJnIA==", + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "license": "MIT", + "dependencies": { + "micromark-util-character": "^2.0.0", + "micromark-util-symbol": "^2.0.0", + "micromark-util-types": "^2.0.0" + } + }, + "node_modules/micromark-factory-label": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/micromark-factory-label/-/micromark-factory-label-2.0.1.tgz", + "integrity": "sha512-VFMekyQExqIW7xIChcXn4ok29YE3rnuyveW3wZQWWqF4Nv9Wk5rgJ99KzPvHjkmPXF93FXIbBp6YdW3t71/7Vg==", + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "license": "MIT", + "dependencies": { + "devlop": "^1.0.0", + "micromark-util-character": "^2.0.0", + "micromark-util-symbol": "^2.0.0", + "micromark-util-types": "^2.0.0" + } + }, + "node_modules/micromark-factory-space": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/micromark-factory-space/-/micromark-factory-space-2.0.1.tgz", + "integrity": "sha512-zRkxjtBxxLd2Sc0d+fbnEunsTj46SWXgXciZmHq0kDYGnck/ZSGj9/wULTV95uoeYiK5hRXP2mJ98Uo4cq/LQg==", + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "license": "MIT", + "dependencies": { + "micromark-util-character": "^2.0.0", + "micromark-util-types": "^2.0.0" + } + }, + "node_modules/micromark-factory-title": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/micromark-factory-title/-/micromark-factory-title-2.0.1.tgz", + "integrity": "sha512-5bZ+3CjhAd9eChYTHsjy6TGxpOFSKgKKJPJxr293jTbfry2KDoWkhBb6TcPVB4NmzaPhMs1Frm9AZH7OD4Cjzw==", + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "license": "MIT", + "dependencies": { + "micromark-factory-space": "^2.0.0", + "micromark-util-character": "^2.0.0", + "micromark-util-symbol": "^2.0.0", + "micromark-util-types": "^2.0.0" + } + }, + "node_modules/micromark-factory-whitespace": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/micromark-factory-whitespace/-/micromark-factory-whitespace-2.0.1.tgz", + "integrity": "sha512-Ob0nuZ3PKt/n0hORHyvoD9uZhr+Za8sFoP+OnMcnWK5lngSzALgQYKMr9RJVOWLqQYuyn6ulqGWSXdwf6F80lQ==", + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "license": "MIT", + "dependencies": { + "micromark-factory-space": "^2.0.0", + "micromark-util-character": "^2.0.0", + "micromark-util-symbol": "^2.0.0", + "micromark-util-types": "^2.0.0" + } + }, + "node_modules/micromark-util-character": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/micromark-util-character/-/micromark-util-character-2.1.1.tgz", + "integrity": "sha512-wv8tdUTJ3thSFFFJKtpYKOYiGP2+v96Hvk4Tu8KpCAsTMs6yi+nVmGh1syvSCsaxz45J6Jbw+9DD6g97+NV67Q==", + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "license": "MIT", + "dependencies": { + "micromark-util-symbol": "^2.0.0", + "micromark-util-types": "^2.0.0" + } + }, + "node_modules/micromark-util-chunked": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/micromark-util-chunked/-/micromark-util-chunked-2.0.1.tgz", + "integrity": "sha512-QUNFEOPELfmvv+4xiNg2sRYeS/P84pTW0TCgP5zc9FpXetHY0ab7SxKyAQCNCc1eK0459uoLI1y5oO5Vc1dbhA==", + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "license": "MIT", + "dependencies": { + "micromark-util-symbol": "^2.0.0" + } + }, + "node_modules/micromark-util-classify-character": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/micromark-util-classify-character/-/micromark-util-classify-character-2.0.1.tgz", + "integrity": "sha512-K0kHzM6afW/MbeWYWLjoHQv1sgg2Q9EccHEDzSkxiP/EaagNzCm7T/WMKZ3rjMbvIpvBiZgwR3dKMygtA4mG1Q==", + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "license": "MIT", + "dependencies": { + "micromark-util-character": "^2.0.0", + "micromark-util-symbol": "^2.0.0", + "micromark-util-types": "^2.0.0" + } + }, + "node_modules/micromark-util-combine-extensions": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/micromark-util-combine-extensions/-/micromark-util-combine-extensions-2.0.1.tgz", + "integrity": "sha512-OnAnH8Ujmy59JcyZw8JSbK9cGpdVY44NKgSM7E9Eh7DiLS2E9RNQf0dONaGDzEG9yjEl5hcqeIsj4hfRkLH/Bg==", + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "license": "MIT", + "dependencies": { + "micromark-util-chunked": "^2.0.0", + "micromark-util-types": "^2.0.0" + } + }, + "node_modules/micromark-util-decode-numeric-character-reference": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/micromark-util-decode-numeric-character-reference/-/micromark-util-decode-numeric-character-reference-2.0.2.tgz", + "integrity": "sha512-ccUbYk6CwVdkmCQMyr64dXz42EfHGkPQlBj5p7YVGzq8I7CtjXZJrubAYezf7Rp+bjPseiROqe7G6foFd+lEuw==", + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "license": "MIT", + "dependencies": { + "micromark-util-symbol": "^2.0.0" + } + }, + "node_modules/micromark-util-decode-string": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/micromark-util-decode-string/-/micromark-util-decode-string-2.0.1.tgz", + "integrity": "sha512-nDV/77Fj6eH1ynwscYTOsbK7rR//Uj0bZXBwJZRfaLEJ1iGBR6kIfNmlNqaqJf649EP0F3NWNdeJi03elllNUQ==", + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "license": "MIT", + "dependencies": { + "decode-named-character-reference": "^1.0.0", + "micromark-util-character": "^2.0.0", + "micromark-util-decode-numeric-character-reference": "^2.0.0", + "micromark-util-symbol": "^2.0.0" + } + }, + "node_modules/micromark-util-encode": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/micromark-util-encode/-/micromark-util-encode-2.0.1.tgz", + "integrity": "sha512-c3cVx2y4KqUnwopcO9b/SCdo2O67LwJJ/UyqGfbigahfegL9myoEFoDYZgkT7f36T0bLrM9hZTAaAyH+PCAXjw==", + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "license": "MIT" + }, + "node_modules/micromark-util-html-tag-name": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/micromark-util-html-tag-name/-/micromark-util-html-tag-name-2.0.1.tgz", + "integrity": "sha512-2cNEiYDhCWKI+Gs9T0Tiysk136SnR13hhO8yW6BGNyhOC4qYFnwF1nKfD3HFAIXA5c45RrIG1ub11GiXeYd1xA==", + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "license": "MIT" + }, + "node_modules/micromark-util-normalize-identifier": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/micromark-util-normalize-identifier/-/micromark-util-normalize-identifier-2.0.1.tgz", + "integrity": "sha512-sxPqmo70LyARJs0w2UclACPUUEqltCkJ6PhKdMIDuJ3gSf/Q+/GIe3WKl0Ijb/GyH9lOpUkRAO2wp0GVkLvS9Q==", + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "license": "MIT", + "dependencies": { + "micromark-util-symbol": "^2.0.0" + } + }, + "node_modules/micromark-util-resolve-all": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/micromark-util-resolve-all/-/micromark-util-resolve-all-2.0.1.tgz", + "integrity": "sha512-VdQyxFWFT2/FGJgwQnJYbe1jjQoNTS4RjglmSjTUlpUMa95Htx9NHeYW4rGDJzbjvCsl9eLjMQwGeElsqmzcHg==", + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "license": "MIT", + "dependencies": { + "micromark-util-types": "^2.0.0" + } + }, + "node_modules/micromark-util-sanitize-uri": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/micromark-util-sanitize-uri/-/micromark-util-sanitize-uri-2.0.1.tgz", + "integrity": "sha512-9N9IomZ/YuGGZZmQec1MbgxtlgougxTodVwDzzEouPKo3qFWvymFHWcnDi2vzV1ff6kas9ucW+o3yzJK9YB1AQ==", + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "license": "MIT", + "dependencies": { + "micromark-util-character": "^2.0.0", + "micromark-util-encode": "^2.0.0", + "micromark-util-symbol": "^2.0.0" + } + }, + "node_modules/micromark-util-subtokenize": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/micromark-util-subtokenize/-/micromark-util-subtokenize-2.1.0.tgz", + "integrity": "sha512-XQLu552iSctvnEcgXw6+Sx75GflAPNED1qx7eBJ+wydBb2KCbRZe+NwvIEEMM83uml1+2WSXpBAcp9IUCgCYWA==", + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "license": "MIT", + "dependencies": { + "devlop": "^1.0.0", + "micromark-util-chunked": "^2.0.0", + "micromark-util-symbol": "^2.0.0", + "micromark-util-types": "^2.0.0" + } + }, + "node_modules/micromark-util-symbol": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/micromark-util-symbol/-/micromark-util-symbol-2.0.1.tgz", + "integrity": "sha512-vs5t8Apaud9N28kgCrRUdEed4UJ+wWNvicHLPxCa9ENlYuAY31M0ETy5y1vA33YoNPDFTghEbnh6efaE8h4x0Q==", + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "license": "MIT" + }, + "node_modules/micromark-util-types": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/micromark-util-types/-/micromark-util-types-2.0.2.tgz", + "integrity": "sha512-Yw0ECSpJoViF1qTU4DC6NwtC4aWGt1EkzaQB8KPPyCRR8z9TWeV0HbEFGTO+ZY1wB22zmxnJqhPyTpOVCpeHTA==", + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "license": "MIT" + }, "node_modules/mime-db": { "version": "1.52.0", "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.52.0.tgz", @@ -7304,6 +8656,43 @@ "node": ">=6" } }, + "node_modules/parse-entities": { + "version": "4.0.2", + "resolved": "https://registry.npmjs.org/parse-entities/-/parse-entities-4.0.2.tgz", + "integrity": "sha512-GG2AQYWoLgL877gQIKeRPGO1xF9+eG1ujIb5soS5gPvLQ1y2o8FL90w2QWNdf9I361Mpp7726c+lj3U0qK1uGw==", + "license": "MIT", + "dependencies": { + "@types/unist": "^2.0.0", + "character-entities-legacy": "^3.0.0", + "character-reference-invalid": "^2.0.0", + "decode-named-character-reference": "^1.0.0", + "is-alphanumerical": "^2.0.0", + "is-decimal": "^2.0.0", + "is-hexadecimal": "^2.0.0" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/parse-entities/node_modules/@types/unist": { + "version": "2.0.11", + "resolved": "https://registry.npmjs.org/@types/unist/-/unist-2.0.11.tgz", + "integrity": "sha512-CmBKiL6NNo/OqgmMn95Fk9Whlp2mtvIv+KNpQKN2F4SjvrEesubTRWGYSg+BnWZOnlCaSTU1sMpsBOzgbYhnsA==", + "license": "MIT" + }, + "node_modules/parse5": { + "version": "7.3.0", + "resolved": "https://registry.npmjs.org/parse5/-/parse5-7.3.0.tgz", + "integrity": "sha512-IInvU7fabl34qmi9gY8XOVxhYyMyuH2xUNpb2q8/Y+7552KlejkRvqvD19nMoUW/uQGGbqNpA6Tufu5FL5BZgw==", + "license": "MIT", + "dependencies": { + "entities": "^6.0.0" + }, + "funding": { + "url": "https://github.com/inikulin/parse5?sponsor=1" + } + }, "node_modules/path-exists": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-4.0.0.tgz", @@ -7517,6 +8906,15 @@ } } }, + "node_modules/prismjs": { + "version": "1.30.0", + "resolved": "https://registry.npmjs.org/prismjs/-/prismjs-1.30.0.tgz", + "integrity": "sha512-DEvV2ZF2r2/63V+tK8hQvrR2ZGn10srHbXviTlcv7Kpzw8jWiNTqbVgjO3IY8RxrrOUF8VPMQQFysYYYv0YZxw==", + "license": "MIT", + "engines": { + "node": ">=6" + } + }, "node_modules/prop-types": { "version": "15.8.1", "resolved": "https://registry.npmjs.org/prop-types/-/prop-types-15.8.1.tgz", @@ -7528,6 +8926,16 @@ "react-is": "^16.13.1" } }, + "node_modules/property-information": { + "version": "7.2.0", + "resolved": "https://registry.npmjs.org/property-information/-/property-information-7.2.0.tgz", + "integrity": "sha512-IAtzIB6sUiWaJYrX9smp3V46pBGbBeLFRGdh25kg1334VcBlD8HzhPeNIWQH9zhGmo2itIe25EHt9dQP7G5hmg==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, "node_modules/prosemirror-changeset": { "version": "2.4.1", "resolved": "https://registry.npmjs.org/prosemirror-changeset/-/prosemirror-changeset-2.4.1.tgz", @@ -7750,6 +9158,33 @@ "integrity": "sha512-24e6ynE2H+OKt4kqsOvNd8kBpV65zoxbA4BVsEOB3ARVWQki/DHzaUoC5KuON/BiccDaCCTZBuOcfZs70kR8bQ==", "license": "MIT" }, + "node_modules/react-markdown": { + "version": "10.1.0", + "resolved": "https://registry.npmjs.org/react-markdown/-/react-markdown-10.1.0.tgz", + "integrity": "sha512-qKxVopLT/TyA6BX3Ue5NwabOsAzm0Q7kAPwq6L+wWDwisYs7R8vZ0nRXqq6rkueboxpkjvLGU9fWifiX/ZZFxQ==", + "license": "MIT", + "dependencies": { + "@types/hast": "^3.0.0", + "@types/mdast": "^4.0.0", + "devlop": "^1.0.0", + "hast-util-to-jsx-runtime": "^2.0.0", + "html-url-attributes": "^3.0.0", + "mdast-util-to-hast": "^13.0.0", + "remark-parse": "^11.0.0", + "remark-rehype": "^11.0.0", + "unified": "^11.0.0", + "unist-util-visit": "^5.0.0", + "vfile": "^6.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + }, + "peerDependencies": { + "@types/react": ">=18", + "react": ">=18" + } + }, "node_modules/react-refresh": { "version": "0.17.0", "resolved": "https://registry.npmjs.org/react-refresh/-/react-refresh-0.17.0.tgz", @@ -7898,6 +9333,26 @@ } } }, + "node_modules/react-syntax-highlighter": { + "version": "16.1.1", + "resolved": "https://registry.npmjs.org/react-syntax-highlighter/-/react-syntax-highlighter-16.1.1.tgz", + "integrity": "sha512-PjVawBGy80C6YbC5DDZJeUjBmC7skaoEUdvfFQediQHgCL7aKyVHe57SaJGfQsloGDac+gCpTfRdtxzWWKmCXA==", + "license": "MIT", + "dependencies": { + "@babel/runtime": "^7.28.4", + "highlight.js": "^10.4.1", + "highlightjs-vue": "^1.0.0", + "lowlight": "^1.17.0", + "prismjs": "^1.30.0", + "refractor": "^5.0.0" + }, + "engines": { + "node": ">= 16.20.2" + }, + "peerDependencies": { + "react": ">= 0.14.0" + } + }, "node_modules/react-transition-group": { "version": "4.4.5", "resolved": "https://registry.npmjs.org/react-transition-group/-/react-transition-group-4.4.5.tgz", @@ -7976,6 +9431,22 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/refractor": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/refractor/-/refractor-5.0.0.tgz", + "integrity": "sha512-QXOrHQF5jOpjjLfiNk5GFnWhRXvxjUVnlFxkeDmewR5sXkr3iM46Zo+CnRR8B+MDVqkULW4EcLVcRBNOPXHosw==", + "license": "MIT", + "dependencies": { + "@types/hast": "^3.0.0", + "@types/prismjs": "^1.0.0", + "hastscript": "^9.0.0", + "parse-entities": "^4.0.0" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, "node_modules/regexp.prototype.flags": { "version": "1.5.4", "resolved": "https://registry.npmjs.org/regexp.prototype.flags/-/regexp.prototype.flags-1.5.4.tgz", @@ -7997,6 +9468,87 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/rehype-raw": { + "version": "7.0.0", + "resolved": "https://registry.npmjs.org/rehype-raw/-/rehype-raw-7.0.0.tgz", + "integrity": "sha512-/aE8hCfKlQeA8LmyeyQvQF3eBiLRGNlfBJEvWH7ivp9sBqs7TNqBL5X3v157rM4IFETqDnIOO+z5M/biZbo9Ww==", + "license": "MIT", + "dependencies": { + "@types/hast": "^3.0.0", + "hast-util-raw": "^9.0.0", + "vfile": "^6.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/remark-gfm": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/remark-gfm/-/remark-gfm-4.0.1.tgz", + "integrity": "sha512-1quofZ2RQ9EWdeN34S79+KExV1764+wCUGop5CPL1WGdD0ocPpu91lzPGbwWMECpEpd42kJGQwzRfyov9j4yNg==", + "license": "MIT", + "dependencies": { + "@types/mdast": "^4.0.0", + "mdast-util-gfm": "^3.0.0", + "micromark-extension-gfm": "^3.0.0", + "remark-parse": "^11.0.0", + "remark-stringify": "^11.0.0", + "unified": "^11.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/remark-parse": { + "version": "11.0.0", + "resolved": "https://registry.npmjs.org/remark-parse/-/remark-parse-11.0.0.tgz", + "integrity": "sha512-FCxlKLNGknS5ba/1lmpYijMUzX2esxW5xQqjWxw2eHFfS2MSdaHVINFmhjo+qN1WhZhNimq0dZATN9pH0IDrpA==", + "license": "MIT", + "dependencies": { + "@types/mdast": "^4.0.0", + "mdast-util-from-markdown": "^2.0.0", + "micromark-util-types": "^2.0.0", + "unified": "^11.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/remark-rehype": { + "version": "11.1.2", + "resolved": "https://registry.npmjs.org/remark-rehype/-/remark-rehype-11.1.2.tgz", + "integrity": "sha512-Dh7l57ianaEoIpzbp0PC9UKAdCSVklD8E5Rpw7ETfbTl3FqcOOgq5q2LVDhgGCkaBv7p24JXikPdvhhmHvKMsw==", + "license": "MIT", + "dependencies": { + "@types/hast": "^3.0.0", + "@types/mdast": "^4.0.0", + "mdast-util-to-hast": "^13.0.0", + "unified": "^11.0.0", + "vfile": "^6.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/remark-stringify": { + "version": "11.0.0", + "resolved": "https://registry.npmjs.org/remark-stringify/-/remark-stringify-11.0.0.tgz", + "integrity": "sha512-1OSmLd3awB/t8qdoEOMazZkNsfVTeY4fTsgzcQFdXNq8ToTN4ZGwrMnlda4K6smTFKD+GRV6O48i6Z4iKgPPpw==", + "license": "MIT", + "dependencies": { + "@types/mdast": "^4.0.0", + "mdast-util-to-markdown": "^2.0.0", + "unified": "^11.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, "node_modules/require-directory": { "version": "2.1.1", "resolved": "https://registry.npmjs.org/require-directory/-/require-directory-2.1.1.tgz", @@ -8353,6 +9905,16 @@ "node": ">=0.10.0" } }, + "node_modules/space-separated-tokens": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/space-separated-tokens/-/space-separated-tokens-2.0.2.tgz", + "integrity": "sha512-PEGlAwrG8yXGXRjW32fGbg66JAlOAwbObuqVoJpv/mRgoWDQfgH1wDPvtzWyUSNAXBGSk8h755YDbbcEy3SH2Q==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, "node_modules/stop-iteration-iterator": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/stop-iteration-iterator/-/stop-iteration-iterator-1.1.0.tgz", @@ -8480,6 +10042,20 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/stringify-entities": { + "version": "4.0.4", + "resolved": "https://registry.npmjs.org/stringify-entities/-/stringify-entities-4.0.4.tgz", + "integrity": "sha512-IwfBptatlO+QCJUo19AqvrPNqlVMpW9YEL2LIVY+Rpv2qsjCGxaDLNRgeGsQWJhfItebuJhsGSLjaBbNSQ+ieg==", + "license": "MIT", + "dependencies": { + "character-entities-html4": "^2.0.0", + "character-entities-legacy": "^3.0.0" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, "node_modules/strip-ansi": { "version": "6.0.1", "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-6.0.1.tgz", @@ -8505,6 +10081,24 @@ "url": "https://github.com/sponsors/sindresorhus" } }, + "node_modules/style-to-js": { + "version": "1.1.21", + "resolved": "https://registry.npmjs.org/style-to-js/-/style-to-js-1.1.21.tgz", + "integrity": "sha512-RjQetxJrrUJLQPHbLku6U/ocGtzyjbJMP9lCNK7Ag0CNh690nSH8woqWH9u16nMjYBAok+i7JO1NP2pOy8IsPQ==", + "license": "MIT", + "dependencies": { + "style-to-object": "1.0.14" + } + }, + "node_modules/style-to-object": { + "version": "1.0.14", + "resolved": "https://registry.npmjs.org/style-to-object/-/style-to-object-1.0.14.tgz", + "integrity": "sha512-LIN7rULI0jBscWQYaSswptyderlarFkjQ+t79nzty8tcIAceVomEVlLzH5VP4Cmsv6MtKhs7qaAiwlcp+Mgaxw==", + "license": "MIT", + "dependencies": { + "inline-style-parser": "0.2.7" + } + }, "node_modules/supports-color": { "version": "8.1.1", "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-8.1.1.tgz", @@ -8615,6 +10209,26 @@ "tree-kill": "cli.js" } }, + "node_modules/trim-lines": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/trim-lines/-/trim-lines-3.0.1.tgz", + "integrity": "sha512-kRj8B+YHZCc9kQYdWfJB2/oUl9rA99qbowYYBtr4ui4mZyAQ2JpvVBd/6U2YloATfqBhBTSMhTpgBHtU0Mf3Rg==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/trough": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/trough/-/trough-2.2.0.tgz", + "integrity": "sha512-tmMpK00BjZiUyVyvrBK7knerNgmgvcV/KLVyuma/SC+TQN167GrMRciANTz09+k3zW8L8t60jWO1GpfkZdjTaw==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, "node_modules/ts-api-utils": { "version": "2.5.0", "resolved": "https://registry.npmjs.org/ts-api-utils/-/ts-api-utils-2.5.0.tgz", @@ -8839,6 +10453,93 @@ "devOptional": true, "license": "MIT" }, + "node_modules/unified": { + "version": "11.0.5", + "resolved": "https://registry.npmjs.org/unified/-/unified-11.0.5.tgz", + "integrity": "sha512-xKvGhPWw3k84Qjh8bI3ZeJjqnyadK+GEFtazSfZv/rKeTkTjOJho6mFqh2SM96iIcZokxiOpg78GazTSg8+KHA==", + "license": "MIT", + "dependencies": { + "@types/unist": "^3.0.0", + "bail": "^2.0.0", + "devlop": "^1.0.0", + "extend": "^3.0.0", + "is-plain-obj": "^4.0.0", + "trough": "^2.0.0", + "vfile": "^6.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/unist-util-is": { + "version": "6.0.1", + "resolved": "https://registry.npmjs.org/unist-util-is/-/unist-util-is-6.0.1.tgz", + "integrity": "sha512-LsiILbtBETkDz8I9p1dQ0uyRUWuaQzd/cuEeS1hoRSyW5E5XGmTzlwY1OrNzzakGowI9Dr/I8HVaw4hTtnxy8g==", + "license": "MIT", + "dependencies": { + "@types/unist": "^3.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/unist-util-position": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/unist-util-position/-/unist-util-position-5.0.0.tgz", + "integrity": "sha512-fucsC7HjXvkB5R3kTCO7kUjRdrS0BJt3M/FPxmHMBOm8JQi2BsHAHFsy27E0EolP8rp0NzXsJ+jNPyDWvOJZPA==", + "license": "MIT", + "dependencies": { + "@types/unist": "^3.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/unist-util-stringify-position": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/unist-util-stringify-position/-/unist-util-stringify-position-4.0.0.tgz", + "integrity": "sha512-0ASV06AAoKCDkS2+xw5RXJywruurpbC4JZSm7nr7MOt1ojAzvyyaO+UxZf18j8FCF6kmzCZKcAgN/yu2gm2XgQ==", + "license": "MIT", + "dependencies": { + "@types/unist": "^3.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/unist-util-visit": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/unist-util-visit/-/unist-util-visit-5.1.0.tgz", + "integrity": "sha512-m+vIdyeCOpdr/QeQCu2EzxX/ohgS8KbnPDgFni4dQsfSCtpz8UqDyY5GjRru8PDKuYn7Fq19j1CQ+nJSsGKOzg==", + "license": "MIT", + "dependencies": { + "@types/unist": "^3.0.0", + "unist-util-is": "^6.0.0", + "unist-util-visit-parents": "^6.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/unist-util-visit-parents": { + "version": "6.0.2", + "resolved": "https://registry.npmjs.org/unist-util-visit-parents/-/unist-util-visit-parents-6.0.2.tgz", + "integrity": "sha512-goh1s1TBrqSqukSc8wrjwWhL0hiJxgA8m4kFxGlQ+8FYQ3C/m11FcTs4YYem7V664AhHVvgoQLk890Ssdsr2IQ==", + "license": "MIT", + "dependencies": { + "@types/unist": "^3.0.0", + "unist-util-is": "^6.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, "node_modules/update-browserslist-db": { "version": "1.2.3", "resolved": "https://registry.npmjs.org/update-browserslist-db/-/update-browserslist-db-1.2.3.tgz", @@ -8931,6 +10632,48 @@ "react": "^16.8.0 || ^17.0.0 || ^18.0.0 || ^19.0.0" } }, + "node_modules/vfile": { + "version": "6.0.3", + "resolved": "https://registry.npmjs.org/vfile/-/vfile-6.0.3.tgz", + "integrity": "sha512-KzIbH/9tXat2u30jf+smMwFCsno4wHVdNmzFyL+T/L3UGqqk6JKfVqOFOZEpZSHADH1k40ab6NUIXZq422ov3Q==", + "license": "MIT", + "dependencies": { + "@types/unist": "^3.0.0", + "vfile-message": "^4.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/vfile-location": { + "version": "5.0.3", + "resolved": "https://registry.npmjs.org/vfile-location/-/vfile-location-5.0.3.tgz", + "integrity": "sha512-5yXvWDEgqeiYiBe1lbxYF7UMAIm/IcopxMHrMQDq3nvKcjPKIhZklUKL+AE7J7uApI4kwe2snsK+eI6UTj9EHg==", + "license": "MIT", + "dependencies": { + "@types/unist": "^3.0.0", + "vfile": "^6.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/vfile-message": { + "version": "4.0.3", + "resolved": "https://registry.npmjs.org/vfile-message/-/vfile-message-4.0.3.tgz", + "integrity": "sha512-QTHzsGd1EhbZs4AsQ20JX1rC3cOlt/IWJruk893DfLRr57lcnOeMaWG4K0JrRta4mIJZKth2Au3mM3u03/JWKw==", + "license": "MIT", + "dependencies": { + "@types/unist": "^3.0.0", + "unist-util-stringify-position": "^4.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, "node_modules/victory-vendor": { "version": "36.9.2", "resolved": "https://registry.npmjs.org/victory-vendor/-/victory-vendor-36.9.2.tgz", @@ -9055,6 +10798,16 @@ "integrity": "sha512-dpojBhNsCNN7T82Tm7k26A6G9ML3NkhDsnw9n/eoxSRlVBB4CEtIQ/KTCLI2Fwf3ataSXRhYFkQi3SlnFwPvPQ==", "license": "MIT" }, + "node_modules/web-namespaces": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/web-namespaces/-/web-namespaces-2.0.1.tgz", + "integrity": "sha512-bKr1DkiNa2krS7qxNtdrtHAmzuYGFQLiQ13TsorsdT6ULTkPLKuu5+GsFpDlg6JFjUTwX2DyhMPG2be8uPrqsQ==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, "node_modules/which": { "version": "2.0.2", "resolved": "https://registry.npmjs.org/which/-/which-2.0.2.tgz", @@ -9241,6 +10994,16 @@ "funding": { "url": "https://github.com/sponsors/sindresorhus" } + }, + "node_modules/zwitch": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/zwitch/-/zwitch-2.0.4.tgz", + "integrity": "sha512-bXE4cR/kVZhKZX/RjPEflHaKVhUVl85noU3v6b8apfQEc1x4A+zBxjZ4lN8LqGd6WZ3dl98pY4o717VFmoPp+A==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } } } } diff --git a/package.json b/package.json index 513bd311..d3b87bd4 100644 --- a/package.json +++ b/package.json @@ -72,8 +72,10 @@ "@tiptap/pm": "^3.29.2", "@tiptap/react": "^3.29.2", "@tiptap/starter-kit": "^3.29.2", + "@types/github-slugger": "^1.3.0", "@types/react": "^19.0.3", "@types/react-dom": "^19.0.2", + "@types/react-syntax-highlighter": "^15.5.13", "@vitejs/plugin-react": "^4.3.4", "axios": "^1.13.2", "class-variance-authority": "^0.7.1", @@ -81,13 +83,18 @@ "cmdk": "^1.1.1", "concurrently": "^9.0.1", "framer-motion": "^12.43.0", + "github-slugger": "^2.0.0", "globals": "^15.14.0", "laravel-vite-plugin": "^1.3.0", "lucide-react": "^0.475.0", "react": "^19.0.0", "react-dom": "^19.0.0", + "react-markdown": "^10.1.0", "react-router-dom": "^7.18.1", + "react-syntax-highlighter": "^16.1.1", "recharts": "^2.15.4", + "rehype-raw": "^7.0.0", + "remark-gfm": "^4.0.1", "tailwind-merge": "^3.0.1", "tailwindcss": "^4.0.0", "tailwindcss-animate": "^1.0.7", diff --git a/platform/resources/docs/00_introduction/00_why_this_app.md b/platform/resources/docs/00_introduction/00_why_this_app.md new file mode 100644 index 00000000..4dbcf086 --- /dev/null +++ b/platform/resources/docs/00_introduction/00_why_this_app.md @@ -0,0 +1,72 @@ +# لماذا هذا التطبيق؟ — الفلسفة والغاية + +## 1. السؤال الجوهري: مَن يملك سجلاتك المالية؟ + +معظم تطبيقات المالية الشخصية تجيب على هذا السؤال بطريقة لا تقولها صراحةً، لكنها تُطبّقها عملياً: +**الشركة تملك سجلاتك.** + +بياناتك على خوادمهم. يعالجون معاملاتك. يحتفظون بتاريخك المالي. تستطيع الاطلاع عليه بإذنهم. إذا أغلقت الشركة خدمتها، أو حذفت حسابك، أو تعرضت لاختراق — بياناتك في خطر. + +نظام قيد يجيب على السؤال ذاته بإجابة مختلفة تماماً: **أنتَ تملك سجلاتك.** + +## 2. ما معنى السيادة المالية الحقيقية؟ + +"السيادة المالية" ليست شعاراً تسويقياً في قيد (qayd) — إنها قرار هندسي مُرمَّز في كل طبقة من طبقات النظام: + +**أولاً: قاعدة بياناتك على جهازك** +لا يوجد خادم يحتفظ بسجلاتك المالية. قاعدة البيانات تُخزَّن حصراً على جهازك، مشفرةً بتشفير AES-256 — وهو التشفير ذاته المستخدم في حماية المعلومات العسكرية والمصرفية. + +**ثانياً: مفتاح التشفير بيدك** +مفتاح التشفير لا يُخزَّن على أي خادم ولا يمكن لأي جهة معرفته. يُشتق من ثلاثة عناصر يجب توافرها معاً: عبارتك التذكيرية التي تحتفظ بها، وملح محلي مرتبط بجهازك، وملح صادر من الخادم. غياب أي عنصر واحد يجعل البيانات غير قابلة للاستعادة — لأي طرف، بما في ذلك مطوري النظام أنفسهم. + +**ثالثاً: الخادم عمره أعمى** +عندما تُزامن بياناتك مع طرف آخر عبر الشبكة، تُشفَّر الحزمة بمفتاح الطرف المستلِم قبل مغادرة جهازك. الخادم ينقل الحزمة كـ"بريد مغلق" لا يستطيع فتحه ولا قراءته. يعرف الخادم فقط أن إرسالاً حدث بين مستخدمَيْن — لكنه لا يعرف المبلغ ولا طبيعة المعاملة ولا أي تفاصيل مالية. + +## 3. لماذا هذا مختلف عما اعتدتَ عليه؟ + +معظم الناس اعتادوا على محاسبة "ناعمة": تطبيقات تساهل معك في إدخال أي رقم، لا تفرض منطقاً محاسبياً صارماً، ولا تهتم بالتوازن الرياضي لقيودك. + +قيد يختار المسار الصعب. يُطبّق محاسبة ازدواجية حقيقية — وهي الطريقة الوحيدة المعترف بها عالمياً لضمان دقة السجلات المالية منذ قرون. هذا يعني: + +- كل معاملة لها طرفان: ما يأتي من مكان يذهب إلى مكان. +- لا يمكن تسجيل صرف بدون مصدر واضح للمال. +- لا يمكن تعديل أو حذف قيد محاسبي تم تأكيده. + +هذه القيود ليست عيوباً. إنها **الضمانات الوحيدة** لصحة سجلاتك على المدى الطويل. + +## 4. الثمن الحقيقي للسيادة + +الصدق يقتضي الاعتراف: السيادة المطلقة تأتي مع مسؤولية مطلقة. + +**ما تكسبه:** +- بياناتك لا يصلها أحد بدونك. +- لا يُمكن لأي طرف ثالث قراءة سجلاتك أو التلاعب بها. +- نظامك يعمل حتى بدون اتصال بالإنترنت. +- تاريخك المالي محمي تشفيراً حتى لو سُرق جهازك. + +**ما تتحمله:** +- إذا فقدتَ عبارتك التذكيرية ولم يكن لديك نسخة احتياطية، لا يوجد "استعادة كلمة المرور". البيانات غير قابلة للاسترجاع لأي طرف. +- أنت المسؤول عن دقة ما تُسجله. النظام يُدير الحسابات بدقة رياضية مطلقة، لكنه لا يملك القدرة على منعك من تسجيل معلومة خاطئة. +- المزامنة مع طرف آخر تتطلب أن يكون الطرف الآخر متعاوناً. النظام لا يُلزم أحداً. + +## 5. من يحتاج هذا النظام؟ + +قيد مصمم لمن: + +- يريد تتبعاً دقيقاً وحقيقياً لأمواله، لا مجرد قائمة نفقات. +- يتعامل مع ديون وأمانات وتحويلات بين أشخاص تحتاج توثيقاً موثوقاً. +- يعمل وسيطاً في تحويلات مالية بين أطراف ويريد حماية حقوقه والأطراف الأخرى. +- يؤمن بأن بياناته الشخصية ملكه وليست سلعة لشركة. + +قيد ليس أداة حيادية. إنه موقف واضح: **المحاسبة الحقيقية تستحق الجهد الحقيقي.** + +## 6. ما الذي ستتعلمه في هذا الدليل؟ + +هذا الدليل لن يشرح لك فقط كيف تضغط الأزرار. بل سيشرح لك: + +- **لماذا** يفعل النظام ما يفعله بهذه الطريقة. +- **ما** القاعدة المحاسبية التي تحكم كل شاشة. +- **متى** يُسمح لك بفعل شيء ومتى يُمنع ولماذا. +- **كيف** تتجنب الأخطاء الشائعة قبل أن تُرتكب. + +ابدأ بالقراءة. الفهم يأتي أولاً؛ الاستخدام يأتي بعده. diff --git a/platform/resources/docs/00_introduction/01_accounting_worldview.md b/platform/resources/docs/00_introduction/01_accounting_worldview.md new file mode 100644 index 00000000..ad2e5999 --- /dev/null +++ b/platform/resources/docs/00_introduction/01_accounting_worldview.md @@ -0,0 +1,80 @@ +# نظرة المحاسبة المزدوجة بعيون بسيطة + +## 1. ما الذي يعنيه "القيد المزدوج"؟ + +عندما تدفع مبلغاً من المال، يحدث شيئان في آنٍ واحد: +- **المال يخرج** من مكان ما (محفظتك، حسابك البنكي). +- **المال يدخل** إلى مكان ما (يد صاحب المحل، أو تتحول إلى بضاعة في يدك). + +هذا هو جوهر المحاسبة المزدوجة: **كل حركة مالية لها طرفان**، وكلاهما يُسجَّل في آنٍ واحد. + +هذه الفكرة تبدو بديهية حين تُقال بهذه الطريقة. لكن معظم تطبيقات المالية الشخصية تتجاهلها تماماً وتسجل فقط: "أنفقتَ 100 ﷼". عند ذلك يكون نظفك المالي في الحقيقة غير مكتمل — فلا تعرف من أين جاءت الـ100 ﷼، ولا إلى أين ذهبت بالضبط. + +## 2. القاعدة الذهبية التي لا تُكسر + +في المحاسبة المزدوجة، هناك قاعدة رياضية صارمة: + +> **مجموع المدينات = مجموع الدائنيات** في كل وقت، دائماً. + +"المدين" هو الطرف الذي تُضاف إليه قيمة (يُسجَّل له كزيادة أصل أو خسارة التزام). +"الدائن" هو الطرف الذي تُخصم منه قيمة (يُسجَّل له كنقص أصل أو زيادة التزام). + +إذا كانت مجموع المدينات في دفترك لا تساوي مجموع الدائنيات — فهناك خطأ في مكان ما. هذه القاعدة هي "الكشف التلقائي للأخطاء" في المحاسبة. + +نظام قيد يُطبّق هذه القاعدة رياضياً في كل قيد يُسجَّل. لا يمكن أبداً أن تكون دفاترك غير متوازنة. + +## 3. الحسابات: الخزانات التي يتدفق المال بينها + +تخيل سجلك المالي كمجموعة من الخزانات: +- **خزانة النقدية**: ما تملكه من نقود ورقية وأرصدة بنكية. +- **خزانة المصروفات**: ما أنفقته على المأكل والسكن والنقل وغيرها. +- **خزانة الإيرادات**: ما استقبلته من راتب أو عمل حر أو مصادر أخرى. +- **خزانة الذمم**: ما يديه لك الآخرون، أو ما تديه أنت لهم. + +عندما تشتري طعاماً بـ50 ريالاً نقداً، يحدث: +- خزانة النقدية تنقص بـ50 ريالاً. +- خزانة المصروفات (تحديداً تصنيف الطعام) تزيد بـ50 ريالاً. + +المجموع الكلي لأصولك لم يتغير من المنظور النظري — فقط نقلت قيمة من نوع لآخر. + +## 4. كيف يُطبّق قيد هذا المنطق عملياً؟ + +عندما تُسجّل معاملة في قيد (مثل "اشتريت بقالة بـ50 ريالاً")، يقوم النظام تلقائياً بـ: +1. إنشاء **سند دفع** خارجي: من حسابك النقدي إلى حساب محل البقالة. +2. إنشاء **سند داخلي تلقائي**: من حسابك النقدي إلى حساب مصروفات الطعام. + +المستخدم لا يحتاج لفهم هذا التفصيل. يكفيه أن يُنشئ معاملة واحدة، والنظام يُكمل بقية التسجيل المحاسبي تلقائياً. هذا ما يُسميه الدليل التقني "الجسر الآلي". + +## 5. لماذا أرفض القيد الحسابات العائمة؟ + +الأرقام في الحاسوب عادةً تُخزَّن كـ"أرقام عشرية عائمة" — وهي طريقة لا تستطيع تمثيل بعض القيم بدقة مطلقة. مثلاً: +- `0.1 + 0.2` في معظم لغات البرمجة لا تساوي `0.3` بالضبط، بل تساوي `0.30000000000000004`. + +هذا الخطأ الصغير يتراكم مئات أو آلاف مرة في سجلاتك، ويؤدي إلى فرق غير مبرر في ميزانك. + +قيد يحل هذه المشكلة بطريقة قاطعة: **كل مبلغ يُخزَّن كعدد صحيح** يمثل "الوحدات الصغرى" للعملة. ريالاً واحداً = 100 وحدة في النظام. الحسابات تجري على أعداد صحيحة فقط — ولا توجد أي أخطاء عشرية أبداً. + +## 6. الوثيقة تسبق القيد + +في المحاسبة التقليدية الأصيلة، كان التاجر يُعدّ وثيقة القبض أو الصرف أولاً ويحتفظ بها كدليل، ثم يُسجّل قيوده في الدفتر استناداً إليها. + +نظام قيد يُجسّد هذا المبدأ التاريخي: **السند الوثيقة يأتي أولاً**، والقيود المحاسبية تُنتَج منه، لا العكس. لا يمكن وجود قيد محاسبي بدون سند مرجعي واضح موجود قبله. هذا يعني: + +- كل رقم في تقاريرك قابل للتتبع حتى الوثيقة الأصلية التي أنتجته. +- لا توجد قيود "معلقة" بدون مستند. +- إذا أردتَ تصحيح خطأ، تُنشئ وثيقة تصحيح جديدة — لا تُعدّل الوثيقة الأصلية. + +## 7. المحاسبة المزدوجة ليست معقدة — إنها دقيقة + +خلاصة ما يجب أن تعرفه كمستخدم: + +| ما تعرفه أنت | ما يتولاه النظام تلقائياً | +|------------|--------------------------| +| "أنفقتُ X على Y" | تحديد الحساب المدين والدائن | +| "استلمتُ X من Z" | توليد القيد المزدوج المتوازن | +| "أقرضتُ X لشخص" | تسجيل الذمة المدينة | +| "سددتُ X لجهة" | إغلاق الذمة الدائنة | + +أنت تتحدث بلغة الحياة اليومية. النظام يُترجمها إلى محاسبة مزدوجة دقيقة. + +ما تحتاجه حقاً هو: فهم لماذا بعض الإجراءات مُقيَّدة. وهذا ما يشرحه باقي هذا الدليل. diff --git a/platform/resources/docs/00_introduction/02_how_to_read_this_guide.md b/platform/resources/docs/00_introduction/02_how_to_read_this_guide.md new file mode 100644 index 00000000..15063d54 --- /dev/null +++ b/platform/resources/docs/00_introduction/02_how_to_read_this_guide.md @@ -0,0 +1,77 @@ +# كيف تقرأ هذا الدليل؟ + +## 1. هذا الدليل ليس دليل تشغيل عادياً + +معظم أدلة المستخدمين تشرح: اضغط هنا، اكتب هناك، انتقل إلى القائمة الفلانية. هذا الدليل مختلف. إنه يشرح أولاً **لماذا** النظام يتصرف كما يتصرف، ثم يشرح **كيف** تتفاعل معه. + +السبب بسيط: نظام قيد مبني على مبادئ محاسبية وأمنية صارمة. من يحاول استخدامه دون فهم هذه المبادئ سيجد قيوداً كثيرة تبدو له تعسفية — ولن يستطيع الاستفادة منه بشكل صحيح. + +أما من يفهم المبادئ أولاً، فسيرى أن كل "قيد" في النظام هو في الواقع ضمانة تحميه. + +## 2. طريقة القراءة المثلى + +**للمستخدم الجديد تماماً:** +ابدأ بالترتيب التالي قراءةً كاملةً قبل أن تلمس التطبيق: +1. الفصل 00: المقدمة (الملفات الثلاثة) — لبناء الإطار الذهني. +2. الفصل 01: المفاهيم الأساسية — لفهم وحدات النظام. +3. الفصل 02: هيكل التطبيق — لفهم التنقل. + +ثم انطلق للاستخدام. سيكون لديك فهم كافٍ. + +**للمستخدم الذي يريد تعلم ميزة محددة:** +انتقل مباشرة للفصل المعني. كل ملف مستقل بذاته ومكتفٍ بنفسه. + +**لمن واجهته مشكلة أثناء الاستخدام:** +الفصل 09 هو نقطة البداية. إذا لم تجد إجابتك هناك، ارجع للفصل الذي يتناول الموضوع المتعلق بمشكلتك. + +## 3. الإطار الذهني الذي ستحتاجه + +قبل أن تبدأ، Internalize هذه المبادئ الثلاثة: + +**المبدأ الأول: القيد المزدوج ليس خياراً** +كل معاملة مالية لها طرفان. النظام يُسجّلهما معاً دائماً. لا يوجد طريق للتحايل على هذا. + +**المبدأ الثاني: الوثيقة قبل القيد** +لا يمكن لأي رقم أن يظهر في تقاريرك إلا إذا كان خلفه سند موثق. هذا يعني: كل شيء قابل للتتبع والتدقيق. + +**المبدأ الثالث: الماضي ثابت** +بعد تأكيد سند، لا يمكن تغييره. يمكن تصحيحه بـ"سند تصحيح" جديد يُضاف فوقه. لكن السند الأصلي يبقى في السجل. هذا يعني: دفترك لا يُزوَّر. + +## 4. رموز الدليل ومعانيها + +ستجد في بعض ملفات الدليل هذه الإشارات: + +> **ملاحظة:** معلومة تُوضّح سلوك النظام. + +> **تحذير:** شيء يجب أن تعرفه لتجنب مشكلة. + +> **مثال:** توضيح عملي لمفهوم نظري. + +> **المفهوم الخاطئ الشائع:** توضيح لفهم خاطئ شائع وتصحيحه. + +## 5. ما هذا الدليل لا يفعله + +هذا الدليل **لا يشرح** كيف تضغط كل زر في كل شاشة. البرنامج نفسه يحتوي على نصوص توضيحية وتسميات واضحة للحقول. + +ما يشرحه الدليل هو: **المعنى** وراء ما تفعله. + +## 6. هيئة اليقين والشك في هذا الدليل + +ستجد عبارتين مختلفتين في هذا الدليل: + +- **"النظام يمنع..."** أو **"النظام يُطبّق..."**: هذا يعني أن الكود البرمجي يُنفّذ هذا القيد. لا استثناء. لا طريق للتحايل. +- **"التصميم يستهدف..."** أو **"التوقع المقصود..."**: هذا يعني أن الهدف موثق، لكن التطبيق البرمجي قد يكون جزئياً. يُذكَر هذا التفريق لأنك تستحق أن تعرف ما هو مطبق فعلاً وما هو مخطط. + +## 7. ملاحظة على اللغة المستخدمة + +هذا الدليل مكتوب بالعربية الفصحى الواضحة، بأسلوب مهني ومباشر. تجنّبنا المصطلحات التقنية الصعبة حيث أمكن، وشرحنا كل مصطلح عند وروده لأول مرة. + +المصطلحات الأساسية التي ستتكرر في الدليل: +- **السند**: وثيقة المعاملة المالية. +- **القيد**: الإدخال المحاسبي في دفتر الأستاذ. +- **الحساب**: الفئة أو التصنيف المالي (كالنقدية أو المصروفات). +- **مركز التكلفة**: أداة تحليل الإنفاق بحسب الغرض أو النشاط. +- **الميزان**: قائمة مقارنة بين المدينات والدائنيات. +*** + +ابدأ الآن بقراءة الفصل الأول. ستجد أن الدليل مكتوب بحيث تبني كل فكرة على سابقتها. لا تتخطى. diff --git a/platform/resources/docs/00_introduction/_category_.json b/platform/resources/docs/00_introduction/_category_.json new file mode 100644 index 00000000..ebdc47ff --- /dev/null +++ b/platform/resources/docs/00_introduction/_category_.json @@ -0,0 +1,4 @@ +{ + "label": "مقدمة", + "position": 0 +} diff --git a/platform/resources/docs/01_core_concepts/00_accounts_and_truth.md b/platform/resources/docs/01_core_concepts/00_accounts_and_truth.md new file mode 100644 index 00000000..7c6b0811 --- /dev/null +++ b/platform/resources/docs/01_core_concepts/00_accounts_and_truth.md @@ -0,0 +1,75 @@ +# الحسابات والحقيقة المالية + +## 1. ما هو الحساب في نظام قيد؟ + +الحساب في نظام قيد هو **تصنيف مالي دائم**. إنه ليس مجرد مجلد لتخزين المعاملات — إنه تصريح صريح بالطبيعة الاقتصادية لكل شيء يُسجَّل فيه. + +عندما تُنشئ حساباً باسم "مصروفات الطعام"، فأنت لا تُنشئ ملفاً للبيانات فحسب — بل تُعلن أن كل رقم سيُسجَّل في هذا الحساب هو بطبيعته **إنفاق** وليس دخلاً أو أصلاً. هذا الإعلان يُحدّد كيف يُعالج النظام هذا الرقم في توازناتك وتقاريرك. + +## 2. التصنيفات العشرة الثابتة + +لا يستطيع النظام "اختراع" تصنيفات جديدة من العدم. ثمة عشرة تصنيفات أساسية تُمثّل كل ما تحتاجه الحياة المالية الشخصية: + +| التصنيف | المعنى | النوع المالي | +|---------|--------|-------------| +| نقدية وسائلة | النقد في اليد والبنك والمحافظ الرقمية | أصل | +| ذمم دائنة (عليك) | ما يديه الآخرون لك | أصل | +| أصول ثابتة مولِّدة للربح | استثمارات تدرّ عائداً: عقارات، أسهم | أصل | +| أصول ثابتة قابلة للإهلاك | ممتلكات تتناقص قيمتها: سيارة، أجهزة | أصل | +| ذمم مدينة (لك) | ما تديه أنت للآخرين | التزام | +| تسوية وشخصي | حسابات التسوية والمراسلة الشخصية | التزام | +| مقاصة الحوالات | حساب عبور مؤقت للتحويلات الثلاثية | التزام | +| مصروفات شخصية | كل ما تُنفقه | دخل ومصروف | +| إيرادات شخصية | كل ما تستقبله | دخل وإيراد | +| رسوم الحوالات | العائد من وساطة التحويلات | دخل وإيراد | + +هذه العشرة ليست اختياراً عشوائياً بل إجابة على سؤال: **ما هي الفئات التي تُصوّر الواقع المالي الشخصي كاملاً؟** + +## 3. لماذا طبيعة الحساب لا تتغير؟ + +كل حساب لديه "طبيعة": إما مدينة أو دائنة. وهذه الطبيعة تُحدَّد لحظة إنشاء الحساب وتبقى ثابتة للأبد. + +**مثال توضيحي:** +لنفترض أن لديك حساباً "سيارتي" مصنّفاً كأصل ذو طبيعة مدينة. على مدى ثلاث سنوات، سُجّلت فيه عشرات المعاملات. لو كان بالإمكان تغيير طبيعة هذا الحساب إلى دائنة — كل الأرصدة التاريخية ستُقلَب رأساً على عقب. ما كان "رصيد موجب" صار "رصيداً سالباً". ما كان يُمثّل أصلاً صار يُمثّل التزاماً. + +**هذا تزوير للتاريخ المالي**، وهو ما يرفضه النظام بشكل مطلق. لكن هذا لا يعني أنك محاصر — يمكنك دائماً إنشاء حساب جديد بالتصنيف الصحيح، وأرشفة القديم. + +## 4. الحسابات الجذرية والفرعية + +الحسابات في قيد تتنظم في هرمية واضحة: + +**الحسابات الجذرية**: هي رؤوس التصنيفات الكبرى. مثل "مصروفات شخصية" كمفهوم عام. + +**الحسابات الفرعية**: تندرج تحت الجذر وترث منه التصنيف والطبيعة. مثل "مصروفات الطعام" تندرج تحت "مصروفات شخصية". + +**قاعدة الوراثة المطلقة**: حساب فرعي يرث تصنيف أبيه وطبيعته بشكل تلقائي وكامل. لا يمكن إنشاء حساب فرعي بتصنيف مختلف عن أبيه. ونقل حساب من أب لآخر يشترط تطابق التصنيف والطبيعة — وإلا رفضه النظام. + +هذا يعني: عندما ترى حساباً فرعياً في أي مكان، أنت تعرف على الفور طبيعته الاقتصادية دون الحاجة للتحقق من تفاصيله. + +## 5. الحسابات الافتراضية: الأعمدة التي لا تُزال + +بعض الحسابات تُوجَد بشكل تلقائي عند تهيئة النظام لأنها ضرورية لعمله. هذه الحسابات تُعرَّف برمز "افتراضي" ومن خصائصها: + +- لا يمكن حذفها مهما كان الرصيد. +- لا يمكن إيقافها أو أرشفتها. +- لا يمكن نقلها لأب آخر. + +**مثال على ذلك**: الحساب النقدي الجذري — وهو المحور الذي يمر عبره كل تسجيل مصروف أو إيراد شخصي. حذف هذا الحساب سيُعطّل آليات أساسية في النظام. لذلك، النظام لا يتيح هذا الخيار أصلاً. + +## 6. الحساب المُعطَّل مقابل المُؤرشَف + +حين يتوقف نشاط حساب، لديك خيارا: + +**التعطيل**: الحساب "نائم" ولا يظهر في قوائم الاختيار النشطة. لكنه قابل لإعادة التفعيل في أي وقت. يستخدم للحسابات التي توقف نشاطها مؤقتاً. + +**الأرشفة**: الحساب يُحال للتقاعد الدائم. تاريخه محفوظ بالكامل ومرئي في التقارير. لكنه لا يظهر في الاستخدام اليومي. يستخدم للحسابات المغلقة نهائياً. + +**تنبيه مهم**: لا يمكن أرشفة حساب له رصيد غير صفري — لأن الأرشفة تُوحي بالإغلاق النهائي وحساب متبقٍ يظهر في تقاريرك يتناقض مع هذا. يجب تصفية الرصيد أولاً، ثم الأرشفة. + +## 7. ما تعنيه "الحقيقة المالية" في هذا السياق + +الحسابات في قيد ليست مجرد تصنيفات. إنها **خريطة الحقيقة المالية لحياتك**. كل ما تملكه، كل ما تديه، كل ما تنفقه أو تكتسبه — له مكانه المحدد في هذه الخريطة. + +دقة هذه الخريطة تعتمد عليك: إذا أنشأتَ حساباً بتصنيف خاطئ، فالنظام سيُعالج أرقامه بتصنيفها الخاطئ. الحسابات لا تُوجه البيانات — البيانات تُصنَّف وفق الحسابات التي تختارها. + +لهذا السبب، الوقت الذي تستثمره في إعداد حساباتك بشكل صحيح في البداية هو من أكثر الاستثمارات قيمةً في هذا النظام. diff --git a/platform/resources/docs/01_core_concepts/01_root_cash_account.md b/platform/resources/docs/01_core_concepts/01_root_cash_account.md new file mode 100644 index 00000000..574b7d2d --- /dev/null +++ b/platform/resources/docs/01_core_concepts/01_root_cash_account.md @@ -0,0 +1,79 @@ +# الحساب النقدي الجذري — محور النظام + +## 1. ما الذي يجعل هذا الحساب مختلفاً؟ + +في نظام قيد، يوجد حساب واحد له وضع استثنائي في البنية الكاملة للنظام: **الحساب النقدي الجذري** (Root Liquid Assets Account). + +هذا الحساب ليس مجرد حساب عادي لتسجيل ما في محفظتك. إنه **المحور الهيكلي** الذي تدور حوله كل العمليات المالية الشخصية اليومية. كل مرة تُسجّل فيها مصروفاً أو إيراداً شخصياً، يمر المال "نظرياً" عبر هذا الحساب — حتى لو لم تُلاحظ ذلك. + +## 2. آلية الجسر الآلي — كيف ينقل النظام العمليات تلقائياً + +عندما تُسجّل "اشتريتُ بقالة بـ80 ريالاً"، أنت في الحقيقة تخبر النظام: + +- **المبلغ**: 80 ريالاً. +- **المستلِم**: محل البقالة (حساب الطرف الآخر). +- **التصنيف**: مصروفات غذاء (حساب التصنيف الداخلي). + +يقوم النظام تلقائياً بإنشاء معاملتين مرتبطتين: + +**المعاملة الأولى (الخارجية):** + +- من: حسابك النقدي الجذري. +- إلى: محل البقالة. +- المبلغ: 80 ريالاً. + +**المعاملة الثانية (الداخلية - الجسر):** + +- من: محل البقالة. +- إلى (عبر): حسابك النقدي الجذري. +- إلى (التصنيف): حساب مصروفات الغذاء. +- المبلغ: 80 ريالاً. + +الخلاصة الرياضية: المال خرج من محفظتك، وسُجّل كمصروف تحت تصنيف الغذاء. توازن الحسابات محقق. + +## 3. لماذا يوجد حساب جذري واحد فقط؟ + +قد يبدو هذا التصميم تقييدياً. لماذا لا يسمح النظام بتوزيع المصروفات من حسابات نقدية متعددة؟ + +الإجابة تتعلق بمبدأ البساطة المقصودة: وجود "مصدر مالي واحد افتراضي" للمصروفات اليومية يُلغي سؤالاً يُلهي المستخدم في كل معاملة: "هل أسجّل هذا من حساب الراتب أم حساب المدخرات أم حساب النقد الاحتياطي؟" + +النظام يُجيب: **كل المصروفات تمر عبر الحساب النقدي الجذري**. من أين أتى المال إلى هذا الحساب؟ — هذا ما تُسجّله بشكل منفصل كإيراد. وكيف وُزّع من الحساب على أوجه الإنفاق؟ — هذا ما يرصده الجسر الآلي تلقائياً. + +## 4. ماذا يحدث إذا لم يوجد حساب جذري؟ + +هذا سؤال نظري مهم لفهم أثر هذا الحساب: + +إذا لم يعثر النظام على حساب نقدي جذري عند تسجيل مصروف شخصي، **يتوقف الجسر الآلي عن العمل**. المعاملة لا تُوقَف ولكن تُسجَّل بصورة مختلفة — دون التوجيه الآلي المزدوج. + +هذا يعني: صلاحية الجسر الآلي قائمة على وجود هذا الحساب. الحساب النقدي الجذري ليس حساباً يمكن إهمال وجوده. + +## 5. الحساب النقدي الجذري كأصل افتراضي + +عند إعداد النظام لأول مرة، يُنشئ النظام تلقائياً الحساب النقدي الجذري بصفة "افتراضي". وهذا يعني ثلاثة قيود مطلقة: + +**لا يمكن حذفه** — لأنه معماري بنيوي. +**لا يمكن إيقافه** — لأن الجسر الآلي يعتمد عليه. +**لا يمكن نقله** لاندراجه تحت حساب آخر — لأنه بطبيعته حساب جذري. + +إذا كنت تتساءل "لماذا لا تظهر لي خيارات الحذف أو الإيقاف لهذا الحساب تحديداً؟"، فالإجابة هي ما سبق: النظام يُخفي هذه الخيارات عمداً لحمايتك من اتخاذ إجراء سيُعطّل أجزاء أساسية من آليات العمل. + +## 6. كيف أتفاعل مع الحساب النقدي الجذري؟ + +التفاعل الرئيسي مع هذا الحساب هو: + +**إضافة المال إليه**: عند استلام راتب أو دخل، تُسجّل إيراداً يُضيف المال إلى هذا الحساب. + +**يُخصَم منه تلقائياً**: عند تسجيل أي مصروف شخصي، الجسر الآلي يُسجّل الخصم من هذا الحساب. + +**اطلاع على رصيده**: رصيد هذا الحساب في أي وقت يُمثّل ما لديك فعلياً من سيولة — وهو أهم رقم واحد في متابعة وضعك المالي. + +## 7. مثال واقعي متكامل + +| الحدث | ما يُسجّله المستخدم | ما يُنشئه النظام تلقائياً | +| ------- | --------------------- | -------------------------- | +| استلام راتب 10,000 ﷼ | إيراد من صاحب العمل | رصيد الحساب الجذري يرتفع بـ10,000 | +| شراء بقالة 200 ﷼ | دفع لمتجر + تصنيف: طعام | خصم 200 من الجذري، قيد في حساب الطعام | +| شراء وقود 150 ﷼ | دفع لمحطة + تصنيف: نقل | خصم 150 من الجذري، قيد في حساب النقل | +| الرصيد النقدي المتبقي | — | 10,000 - 200 - 150 = 9,650 ﷼ | + +الحساب النقدي الجذري هو الذاكرة الحية لوضعك النقدي الفوري. احتفظ برصيده دقيقاً ومحدثاً، وستمتلك دائماً صورة صادقة عن وضعك المالي. diff --git a/platform/resources/docs/01_core_concepts/02_cost_centers_overview.md b/platform/resources/docs/01_core_concepts/02_cost_centers_overview.md new file mode 100644 index 00000000..ea208637 --- /dev/null +++ b/platform/resources/docs/01_core_concepts/02_cost_centers_overview.md @@ -0,0 +1,64 @@ +# مراكز التكلفة — نظرة عامة + +## 1. الفرق بين الحساب ومركز التكلفة + +هذا أحد أكثر المفاهيم أهمية في نظام قيد، ويُخطئ كثيرون في فهمه في البداية. + +**الحساب** يُجيب عن: "ما القيمة المالية لهذا النشاط أو الأصل؟" — إنه جزء من نظام المحاسبة المزدوجة، يُؤثّر في التوازن، ويظهر في الميزانية والميزان. + +**مركز التكلفة** يُجيب عن: "لأيّ نشاط أو غرض صرفتُ هذا المال؟" — إنه أداة تحليل إدارية، لا يُؤثّر على أي رصيد حسابي، ولا يظهر في الميزانية. + +الفصل بينهما مقصود ومهم: يمكنك إجراء محاسبة دقيقة بدون مراكز تكلفة. لكنك ستفقد القدرة على تحليل "أين يذهب مالي بالضبط". + +## 2. ماذا تتيح لك مراكز التكلفة؟ + +تخيل أن لديك حساباً واحداً: "مصروفات شخصية". كل مصروفاتك تبدو متشابهة في كشف الحساب. كيف ستعرف مثلاً: +- كم أنفقتَ على السيارة هذا الشهر مقابل الشهر الماضي؟ +- ما نسبة إنفاقك على التعليم من إجمالي مصروفاتك؟ +- ما التصنيف الذي استنزف أكثر ميزانيتك هذا العام؟ + +مراكز التكلفة هي الإجابة. هي "بطاقات التصنيف" التي تُوسِم كل معاملة بالغرض منها. بعد إوسامها، يمكنك استخراج تقارير تحليلية دقيقة بأي مقطع تشاء. + +## 3. طبيعة التسطيح — لماذا مراكز التكلفة ليست هرمية؟ + +في بعض الأنظمة المحاسبية، مراكز التكلفة تكون هرمية كشجرة: قسم → إدارة → فريق. نظام قيد يرفض هذا التعقيد وجميع مراكز التكلفة فيه تقع على مستوى واحد مسطح. + +السبب: للحياة الشخصية، التسلسل الهرمي للمراكز غير ضروري. ما تحتاجه هو "تصنيف سريع بالغرض" لا "هيكل إداري". التعقيد الإضافي سيُرهقك في التصنيف اليومي دون فائدة معنوية. + +**الحل البديل**: إذا احتجت مستويين من التحليل، تستخدم "الأبعاد" — وهي تصنيفات فرعية داخل المركز الواحد. سيشرحها الملف التالي بالتفصيل. + +## 4. نوعا المراكز: تكلفة أو ربح + +كل مركز تكلفة يجب أن يُعرَّف بأحد نوعين: + +**مركز التكلفة (cost):** +يُتابع الإنفاق والاستنزاف. السؤال الذي يُجيب عنه: "كم كلّف هذا النشاط؟" مثل: مركز مصروفات السيارة، مركز فواتير الخدمات. + +**مركز الربح (profit):** +يُتابع الإيرادات والتكاليف معاً، ويُقيّم الجدوى الاقتصادية. السؤال الذي يُجيب عنه: "هل هذا النشاط يُدرّ عائداً كافياً مقابل تكاليفه؟" مثل: مركز الشقة المؤجَّرة، مركز مشروع حر. + +**ملاحظة مهمة**: نوع المركز يُحدَّد لحظة إنشائه ولا يمكن تغييره لاحقاً. إذا بدأت مركزاً كـ"تكلفة" ثم قررتَ تحويله لـ"ربح" — ثمانية أشهر من البيانات الموسومة لن يُعاد حساب معناها الإحصائي. التخطيط المبكر لطبيعة كل مركز ضروري. + +## 5. لماذا لا تُحذَف مراكز التكلفة؟ + +يمكنك تعليق مركز تكلفة (إيقافه مؤقتاً) إذا كان رصيده يساوي صفراً — لكن لا يمكن حذفه نهائياً. + +السبب: إذا وسّمتَ معاملات بهذا المركز، فحذفه سيُكسر الروابط التحليلية لكل هذه المعاملات. التقارير التاريخية ستصبح غير مكتملة وغير موثوقة. + +التعليق هو الحل الصحيح: المركز المعلَّق لا يظهر في القوائم النشطة ولا يمكن الإيساء به في معاملات جديدة، لكن تاريخه محفوظ وتقاريره قابلة للاستعراض. + +## 6. المراكز الافتراضية مقابل المراكز المخصصة + +**المراكز الافتراضية**: نظام قيد يأتي بـ11 مركزاً مُعدّة مسبقاً تُغطي المجالات الحياتية الأساسية. هذه المراكز لا يمكن تعليقها ولا إعادة تسميتها. إنها ثوابت. + +**المراكز المخصصة**: يمكنك إنشاء مراكز إضافية تناسب حياتك المحددة. مثل: "مصروفات الزفاف"، "مشروع الاستثمار العقاري"، "نفقات الدراسة في الخارج". + +## 7. متى تستخدم مركز التكلفة؟ + +ليس شرطاً ربط كل معاملة بمركز تكلفة. لكن التوسيم المنتظم يجعل التقارير التحليلية أكثر قيمة. نصيحة عملية: + +- لأي إنفاق متكرر: دائماً وسّمه بمركز. +- للإنفاق الاستثنائي غير المتكرر: أنشئ مركزاً مخصصاً أو استخدم المركز الأقرب. +- لا تهتم بالتوسيم المثالي في البداية — حتى التوسيم التقريبي أفضل من لا شيء. + +مراكز التكلفة هي "العيون الإضافية" لنظامك المالي. كلما استخدمتها بانتظام، كلما أخبرتك تقاريرك بحقائق أكثر قيمة. diff --git a/platform/resources/docs/01_core_concepts/03_dimensions_philosophy.md b/platform/resources/docs/01_core_concepts/03_dimensions_philosophy.md new file mode 100644 index 00000000..c400987a --- /dev/null +++ b/platform/resources/docs/01_core_concepts/03_dimensions_philosophy.md @@ -0,0 +1,71 @@ +# أبعاد التحليل — فلسفة التصنيف + +## 1. ما هو البُعد وكيف يختلف عن المركز؟ + +إذا كان مركز التكلفة هو "الغرف" في بيتك، فالأبعاد هي "التقسيمات داخل كل غرفة". إنها طبقة تحليلية ثانية مُتداخلة داخل المركز الواحد. + +**مثال**: لديك مركز تكلفة اسمه "مصروفات الأسرة". هذا المركز يُخبرك كم أنفقتَ على الأسرة إجمالاً. لكن ماذا لو أردت أن تعرف: كم أنفقتَ تحديداً على كل فرد من أفراد الأسرة؟ + +هنا تأتي الأبعاد: تُضيف "محمد" و"فاطمة" و"أحمد" كأبعاد داخل مركز "مصروفات الأسرة". كل معاملة تُسجَّل في المركز تُوسَم بعد ذلك بالبُعد المناسب — ومن ثم تستطيع استخراج تقرير: "ما أنفقتُه على كل فرد بالتفصيل". + +## 2. الأبعاد الإحدى عشر الافتراضية + +النظام يأتي بإحدى عشر فئة بُعدية افتراضية تُمثّل هيكلاً سوسيولوجياً متكاملاً للحياة الشخصية، مُرتَّبةً بحسب الأولوية من الضروري إلى الترفيهي: + +| الترتيب | الفئة | ما تُمثّله | +|---------|-------|------------| +| 1 | الدخل والعمل | مصادر الكسب والإيراد | +| 2 | السكن والمعيشة | الإيجار، الصيانة، الفواتير | +| 3 | التغذية والاستهلاك | الطعام والمستلزمات اليومية | +| 4 | النقل والتنقل | البنزين، الصيانة، المواصلات | +| 5 | الصحة والعناية | الطب، الأدوية، العناية الشخصية | +| 6 | التعليم وتنمية القدرات | الدراسة، الدورات، الكتب | +| 7 | الأسرة والمعالون | الأبناء، الوالدان، المعالون | +| 8 | الالتزامات والديون | الأقساط، التعهدات المالية | +| 9 | الاستثمارات والمشاريع | رأس المال، المشاريع | +| 10 | الادخار وبناء الاحتياطي | الصندوق الطارئ، المدخرات | +| 11 | الترفيه ونمط الحياة | الترفيه، السفر، الهوايات | + +هذا الترتيب ليس عشوائياً. إنه يُجسّد منطق الأولويات: البقاء والضرورة أولاً، التطوير والنمو ثانياً، الترفيه والكماليات أخيراً. + +## 3. لماذا هذه الفئات تحديداً؟ + +هذا الترتيب الاحدى عشري يعكس فهماً عميقاً لكيفية توزيع الإنسان لموارده الاقتصادية: + +- **الغذاء والسكن** (فئتا 2 و3): الحاجتان الأوليتان للبقاء. أي شخص يعيش باستقلالية ينفق عليهما أولاً قبل أي شيء آخر. +- **التنقل والصحة** (فئتا 4 و5): ضروريتان للمشاركة الاقتصادية والحفاظ على القدرة الإنتاجية. +- **التعليم والأسرة** (فئتا 6 و7): استثمار في المستقبل وإيفاء واجب اجتماعي — يسبقان تراكم الثروة لأنهما أكثر إلحاحاً. +- **الادخار والاستثمار** (فئتا 9 و10): يُمكِّنان من بناء الثروة بعد تغطية الضروريات. +- **الترفيه** (فئة 11): في نهاية السلم لأنه يأتي بعد تلبية كل الحاجات الأخرى. + +## 4. الفئات الافتراضية ثابتة — والثوابت مقصودة + +الفئات الافتراضية لا يمكن تعديل اسمها أو تعليقها. هذا ليس تقصيراً في التصميم — إنه موقف واضح. + +بيانات سنة كاملة موسومة بفئات افتراضية متسقة تعطيك مقارنات موحّدة عبر الزمن. لو غيّرتَ أسماء الفئات في منتصف العام، ستجد نفسك أمام بيانات لا يمكن مقارنتها لأن التسميات اختلفت. + +الثبات يُمكّن الاتساق. الاتساق يُمكّن التحليل الحقيقي. + +## 5. الأبعاد المخصصة — ما وراء الإحدى عشر + +لأن إحدى عشر فئة لا تُمثّل حياة كل شخص، يُتيح النظام إنشاء فئات أبعاد مخصصة: + +- مستقل يعمل مع عملاء متعددين: فئات تُسمّى باسم كل عميل. +- صاحب عقارات متعددة: فئة لكل عقار. +- عائلة كبيرة: فئة لكل فرد بحسب الإنفاق. + +الفئات المخصصة تُكمّل الافتراضية ولا تُحل محلها. + +## 6. كيف يرتبط البُعد بمركز التكلفة عملياً؟ + +عند توسيم معاملة في النظام: +1. تختار **مركز التكلفة**: مثل "مصروفات الأسرة". +2. ثم تختار من **الأبعاد** للمركز: مثل "الابن الأكبر" أو "مصاريف المدرسة". + +هذا التداخل يُعطيك بُعدَيْن أفقيَّيْن للتحليل في وقت واحد بدلاً من بُعد واحد. + +## 7. قاعدة الاستمرارية في التوسيم + +أهمية الأبعاد تتوقف على الاتساق في استخدامها. إذا وسّمتَ معاملة اليوم بـ"السيارة - صيانة" وغداً بـ"نقل - سيارة" وبعد أسبوع لم توسّم أصلاً — لن تحصل منها على قيمة تحليلية حقيقية. + +النصيحة العملية: حدّد أبعادك مرة واحدة، واجعل تطبيقها آلياً قدر الإمكان من خلال "الأبعاد الافتراضية للحسابات" — وهو موضوع الملف التالي. diff --git a/platform/resources/docs/01_core_concepts/04_vouchers_and_commitments.md b/platform/resources/docs/01_core_concepts/04_vouchers_and_commitments.md new file mode 100644 index 00000000..200d04a0 --- /dev/null +++ b/platform/resources/docs/01_core_concepts/04_vouchers_and_commitments.md @@ -0,0 +1,77 @@ +# السندات والالتزامات — الوثيقة قبل القيد + +## 1. ما هو السند وما وزنه في النظام؟ + +السند في نظام قيد هو "وثيقة الحدث المالي". إنه ليس مجرد إدخال بيانات — إنه الوحدة الأساسية غير القابلة للانقسام في النظام. كل قيد محاسبي ينتج من سند. كل رقم في تقاريرك قابل للتتبع حتى سند محدد. + +**ما الفرق العملي؟** +في أنظمة أخرى، قد توجد أرقام في تقرير لا تعرف من أين أتت. في قيد، هذا مستحيل هيكلياً. القيد المحاسبي في دفتر الأستاذ لا يُوجَد أصلاً إلا إذا جاء من سند مؤكَّد. + +## 2. نوعا السندات الأساسيان + +كل سند في النظام له نوع: إما **قبض** أو **دفع**. + +**سند القبض (Receipt)**: يُمثّل دخول مال إليك من طرف آخر. مثل: استلام راتب، استلام ثمن بضاعة بعتَها، استلام سداد من مدين. + +**سند الدفع (Payment)**: يُمثّل خروج مال منك إلى طرف آخر. مثل: دفع فاتورة، دفع ثمن مشتريات، سداد دين عليك. + +النوع ليس مجرد وصف — إنه ما يُحدّد **اتجاه القيد المحاسبي**: من يُدان ومن يُدان. النظام يُحسب هذا تلقائياً من النوع، فلا تحتاج لإدخال جانب الدين، مدين/دائن يدوياً أبداً. + +## 3. الحقلان الأساسيان لكل سند + +كل سند بالإضافة إلى نوعه يجب أن يُحدّد: + +**الطرف الآخر (counterparty)**: صاحب المتجر الذي اشتريتَ منه، الشخص الذي أقرضتَه، الجهة التي سددتَ لها. هو الحساب على "الجانب الآخر" من المعاملة. + +**الحساب المتأثر (affected account)**: ما أُثّر في حساباتك الداخلية. مثل: حساب مصروفات الطعام، حساب مدخراتك، حساب أصل استثماري. + +من هذين الحقلين + النوع، يُنتج النظام تلقائياً قيداً مزدوجاً متوازناً رياضياً دون أي إدخال إضافي من المستخدم. + +## 4. دورة حياة السند — آلة الحالات المحدودة + +السند يمر بمراحل صارمة لا يمكن تجاوزها أو التراجع فيها: + +```txt +مسودة ──── تأكيد ────► مؤكَّد ──── تسوية ────► مُسوَّى (نهائي) + │ │ + └───────────────────────┘ + سحب + ▼ + مسحوب (نهائي) +``` + +**مسودة**: السند موجود لكن لم تُنشئ منه قيوداً بعد. يمكن تعديله بحرية. + +**مؤكَّد**: تم تأكيد السند وتُنشئت قيوده المحاسبية. لا يمكن تعديل محتواه الجوهري. يمكن سحبه (إذا لم يقبله الطرف الآخر بعد). + +**مُسوَّى**: الالتزام الذي يمثله السند تم تنفيذه كاملاً. هذه حالة نهائية لا رجعة منها. + +**مسحوب**: السند أُلغي قبل اكتمال دورة حياته. أيضاً حالة نهائية. السند مسحوب لا يختفي من السجل — يبقى مرئياً للتاريخ لكن بلا أثر مالي نشط. + +## 5. لماذا لا يمكن تعديل سند مؤكَّد؟ + +هذا هو السؤال الذي يُوقف كثيراً من المستخدمين لأول وهلة: "أخطأتُ في المبلغ بعد التأكيد. لماذا لا أستطيع تصحيحه مباشرة؟" + +التفسير: في المحاسبة الحقيقية، السجلات هي أدلة. السند المؤكَّد ربما أبلغتَ به طرفاً آخر، أو ربما ولّد قيوداً تُؤثّر على أرصدة إجمالية. السماح بتعديله بصمت سيعني: + +- أن طرفاً آخر يرى سنداً مختلفاً عما رآه قبلاً. +- أن القيود المحاسبية التي ولّدها السند لم تعد تُمثّل ما تقوله الوثيقة. +- أن التاريخ المحاسبي يمكن إعادة كتابته — وهذا تزوير. + +**الحل الصحيح**: إذا أخطأتَ، تُنشئ سند تصحيح جديد. السند الخاطئ يُسحَب، والسند الصحيح يُضاف. كلاهما موجود في السجل. المراجِع يرى ماذا حدث بالكامل. + +## 6. الالتزام الثنائي — ما يجعل السند أكثر من مجرد إدخال بيانات + +السند في قيد يمكن أن يكون **اتفاقية ثنائية الأطراف** بين مستخدمَيْن. عندما تُرسل سنداً لطرف آخر: + +- الطرف الآخر يُبدي رأيه: يقبل أو يرفض. +- القبول يُنشئ توقيعاً رقمياً مُشفَّراً غير قابل للإنكار. +- الرفض يُتيح لك إعادة التفاوض وتقديم سند معدَّل. + +هذا يعني: بعد أن يقبل الطرف الآخر سنداً، **لا يستطيع منشئ السند سحبه بشكل منفرد**. لأن القبول يُنشئ التزاماً ثنائياً — ما لا يفسخه طرف واحد بإرادته. + +## 7. السند كمحادثة مالية — الحقيقة التراكمية + +سلسلة السندات بين شخصَيْن ليست قائمة أرقام جافة — إنها رواية مالية: "طلبتُ منك 500 ﷼، رفضتَ لأن المبلغ خاطئ، أرسلتُ سنداً معدَّلاً بـ450 ريالاً، قبلتَه، سُوّي الآن." كل هذه الخطوات موثقة في سجل لا يُحذَف. + +هذا ما يُميّز نظام قيد عن تطبيقات تتبع النفقات البسيطة: إنه يُمثّل الواقع المالي كما يحدث فعلاً — بالتفاوض والتصحيح والتأكيد — لا كإدخالات منعزلة بلا سياق. diff --git a/platform/resources/docs/01_core_concepts/05_conversational_ledger.md b/platform/resources/docs/01_core_concepts/05_conversational_ledger.md new file mode 100644 index 00000000..6f6f765d --- /dev/null +++ b/platform/resources/docs/01_core_concepts/05_conversational_ledger.md @@ -0,0 +1,69 @@ +# دفتر الأستاذ كمحادثة — التفسير الاجتماعي للسجل المالي + +## 1. الأرقام لها سياق: مفهوم المحادثة المالية + +معظم أنظمة المحاسبة تُقدّم علاقتك المالية مع أي طرف على شكل جدول أو قائمة: تاريخ، مبلغ، وصف. هذا مفيد للمحاسب — لكنه يفتقر لشيء مهم: **السياق الاجتماعي للحدث**. + +نظام قيد يُرى العلاقة المالية بين طرفَيْن على هيئة **محادثة** — تماماً كنافذة محادثة نصية في هاتفك. كل معاملة مالية ظاهرة كـ"رسالة": الرسائل الصادرة منك مُحاذاة لليمين، الواردة إليك لليسار، مع توضيح الرصيد التراكمي بعد كل رسالة. + +## 2. المنظور — قراءة الأرقام من زاويتك أنت + +الظاهرة المالية ذاتها تُوصَف بشكل مختلف تماماً بحسب مَن يصفها. + +**المثال**: أقرضتَ لصديقك 1000 ﷼. +- من منظورك: "دفعتُ 1000 ﷼" — المال خرج منك. +- من منظوره: "استلمتُ 1000 ﷼" — المال وصله. + +نفس المبلغ، نفس اليوم، وصفان متعاكسان تماماً — وكلاهما صحيح. + +نظام قيد يحل هذا بمفهوم **المنظور**: كل عرض لكشف الحساب يستند إلى منظور حساب محدد. الرصيد الإيجابي يعني أن المال في صالح هذا المنظور. الرصيد السلبي يعني أن الطرف الآخر له حق عليه. تغيير المنظور يقلب الإشارة ويعيد ترتيب الوصف. + +## 3. اتجاه المعاملة — إلى وعبر وإلى منين + +لكل معاملة في عرض المحادثة اتجاه واضح: + +**صادرة**: المال غادر هذا المنظور — مثل دفع مبلغ أو إرسال قرض. + +**واردة**: المال وصل لهذا المنظور — مثل استلام مبلغ أو استرداد قرض. + +الاتجاه يُقدَّر بحسب المنظور المختار. نفس السند يكون "صادراً" من منظور المُرسِل و"وارداً" من منظور المستلم. النظام يُحسب هذا تلقائياً. + +## 4. الرصيد التراكمي — اللقطة الفورية لوضعك مع أي طرف + +عرض المحادثة لا يُظهر فقط قائمة المعاملات — بل بعد كل معاملة يُظهر **الرصيد التراكمي** بين الطرفَيْن في تلك اللحظة. + +**مثال متسلسل**: +- بدأنا الشهر: رصيدنا = صفر. +- أقرضتُك 500 ﷼: رصيد = 500 ﷼ (أنت تديني 500). +- أرجعتَ لي 200: رصيد = 300 ﷼ (تبقى تديني 300). +- أقرضتُك 100 أخرى: رصيد = 400 ﷼. + +كل معاملة تُظهر الرصيد المتراكم بعدها. في الرسالة الأخيرة في المحادثة دائماً تجد الرصيد الصافي الحالي بيننا. + +## 5. الوضع الثنائي للسند — "رسالتي" أم "رسالته"؟ + +في عرض المحادثة، كل سند له خاصية: هل أنا مَن أنشأه أم الطرف الآخر؟ + +- **"رسالتي"** (السند الذي أنشأتُه): يظهر مُحاذياً لليمين بلون مختلف. +- **"رسالته"** (السند الذي أنشأه الطرف الآخر): يظهر مُحاذياً لليسار. + +هذا التمييز يُجيب على سؤال مهم عند المراجعة: "هذه المعاملة — أنا الذي طلبتُها أم طلبتَها مني؟" + +## 6. السندات المشروطة في المحادثة — ما لا يظهر ولماذا + +في حالات التحويل الثلاثي (حين تتوسط بين طرفَيْن)، قد يوجد سند "مشروط": السند الذي ستدفعه للطرف الثاني، لكنك لم تستلم بعد من الطرف الأول. + +هذا السند المشروط **لا يظهر** في عرض المحادثة حتى يتحقق الشرط (استلام المال من الطرف الأول). سبب هذا ليس إخفاء المعلومات — بل لأن سنداً لا يمكنك التصرف حياله الآن لا معنى لعرضه كما لو كان قابلاً للتصرف. + +حين يُستلَم المال من الطرف الأول ويُؤكَّد السند، يُرفَع القفل عن السند المشروط ويظهر في المحادثة. + +## 7. الخلاصة — لماذا هذا المدخل الاجتماعي أقوى؟ + +عرض السجل المالي كمحادثة يتيح لك: +- قراءة علاقتك المالية مع أي شخص بتسلسل زمني واضح. +- رؤية كيف تطورت هذه العلاقة: "كنا على صفر، ثم أقرضتُه، ثم سدّد جزءاً، ثم أضفتُ آخر..." +- معرفة الرصيد الصافي الحالي دون حسابات يدوية. +- تمييز السندات التي بدأتَها عن تلك التي بدأها الطرف الآخر. +- فهم السياق وراء كل رقم بدلاً من أرقام معزولة. + +المحاسبة الحقيقية ليست أرقاماً باردة — هي أحداث مرتبطة ببشر وقرارات. عرض المحادثة يُذكّرك بهذا الواقع في كل لحظة. diff --git a/platform/resources/docs/01_core_concepts/_category_.json b/platform/resources/docs/01_core_concepts/_category_.json new file mode 100644 index 00000000..85eff211 --- /dev/null +++ b/platform/resources/docs/01_core_concepts/_category_.json @@ -0,0 +1,4 @@ +{ + "label": "المفاهيم الأساسية", + "position": 1 +} diff --git a/platform/resources/docs/02_app_structure/00_navigation_logic.md b/platform/resources/docs/02_app_structure/00_navigation_logic.md new file mode 100644 index 00000000..cd7a2374 --- /dev/null +++ b/platform/resources/docs/02_app_structure/00_navigation_logic.md @@ -0,0 +1,80 @@ +# منطق التنقل بين أقسام التطبيق + +## 1. الواجهة الرئيسية — خمسة تبويبات، خمس طبقات + +بعد تسجيل الدخول، يُقدّم التطبيق شاشة رئيسية بخمسة تبويبات. هذه التبويبات ليست خيارات متساوية — هي طبقات مرتبة تصاعدياً في التجريد المحاسبي: + +| التبويب | الاسم | الطبقة المحاسبية | +|---------|-------|-----------------| +| 1 | الحسابات | تعريف الكيانات المالية | +| 2 | السندات | تسجيل الأحداث المالية | +| 3 | التقارير | استخراج المعرفة | +| 4 | مراكز التكلفة | التحليل الإداري | +| 5 | الإعدادات | إدارة النظام | + +## 2. لماذا هذا الترتيب تحديداً؟ + +الترتيب يُجسّد التبعية المنطقية: + +- **الحسابات أولاً**: لا سند بدون حساب. يجب أن تُنشئ الحسابات قبل أن تستطيع تسجيل أي معاملة. +- **السندات ثانياً**: لا تقارير بدون سندات. السندات تنتج القيود، والقيود تنتج التقارير. +- **التقارير ثالثاً**: تُولَد من السندات المسجّلة. لا معنى لها بدون بيانات. +- **مراكز التكلفة رابعاً**: تُحلّل البيانات الموجودة. أداة تحليل، لا أداة إدخال أساسية. +- **الإعدادات أخيراً**: إدارة النظام — لا أثر على الدورة المحاسبية مباشرة. + +## 3. تبويب الحسابات — رؤية شاملة بنك المعلومات + +يُعرض في هذا التبويب هيكل الحسابات الكامل. تستطيع من هنا: +- رؤية جميع الحسابات مُصنَّفةً حسب طبيعتها (أصول، التزامات، إيرادات، مصروفات). +- إنشاء حسابات جديدة. +- الاطلاع على رصيد كل حساب. +- الوصول لكشف حساب أي جهة. + +هذا التبويب هو **خريطتك المالية الكاملة** — ما تملكه وما تديه وما ينتجه مالك. + +## 4. تبويب السندات — قلب النشاط اليومي + +هنا تُسجَّل المعاملات اليومية. يُعرض في هذا التبويب: +- قائمة السندات الأخيرة مُرتَّبةً زمنياً. +- أدوات البحث والتصفية للوصول لأي سند مسبق. +- زر إنشاء سند جديد. + +يُلاحظ كثيرون أن بعض السندات تظهر بصورة "مزدوجة" — سند رئيسي وسند داخلي مرتبط به. هذا هو الجسر الآلي في عمله: السند الداخلي تلقائي ومرتبط بالرئيسي، ويمكن التمييز بينهما من التسمية التوضيحية. + +## 5. تبويب التقارير — استخراج المعنى من الأرقام + +التقارير تُولَد مباشرة من دفتر الأستاذ في الوقت الفعلي — لا يوجد "تحديث يدوي" أو "حساب دفعي" يجب تشغيله. أحدث سند تُؤكّده يظهر في التقارير فوراً. + +يتضمن هذا التبويب: +- ميزان المراجعة. +- الميزانية العمومية. +- تقارير السندات المفلترة. +- كشوفات الحسابات. + +## 6. تبويب مراكز التكلفة — المنظور التحليلي + +هذا التبويب منفصل عن التبويبات المحاسبية لسبب واضح: مراكز التكلفة ليست جزءاً من المحاسبة الرسمية. إنها أداة تحليلية إدارية. وضعها في تبويب مستقل يُعزّز الفصل المفاهيمي الذي يُقوم عليه النظام. + +من هنا تُنشئ المراكز، تُراجع ميزانياتها، وتستعرض التقارير التحليلية المرتبطة بكل مركز. + +## 7. شريط الحالة العلوي — مرآة المزامنة + +يظهر في أعلى الواجهة شريط مزامنة يُوضّح حالة أي تواصل مع أطراف أخرى: +- **مخفي**: لا مزامنة جارية، التطبيق في وضع محلي. +- **جارٍ الاتصال**: التطبيق يحاول التواصل مع الشبكة. +- **مزامنة جارية**: إرسال أو استلام بيانات. +- **نجاح**: آخر مزامنة اكتملت. +- **فشل**: المزامنة لم تصل — تحتاج للمتابعة. + +حالة الفشل مهمة جداً: إذا أرسلتَ سنداً لطرف آخر ولم تتم المزامنة، ذلك الطرف لم يستلم السند بعد. متابعة هذا الشريط ضرورية. + +## 8. ما يعنيه التصميم البنيوي للتطبيق + +هذا الترتيب الخماسي ليس مجرد قائمة. إنه نموذج متكامل لأي نظام محاسبي في العالم: +- **تعريف الكيانات** (حسابات). +- **تسجيل الأحداث** (سندات). +- **استخراج التقارير** (تقارير). +- **تحليل الأداء** (مراكز تكلفة). +- **إدارة النظام** (إعدادات). + +معرفة أي قسم ينتمي لأي طبقة تُساعدك في اتخاذ القرار الصحيح: "هل مشكلتي في الحسابات؟ في السندات؟ في مراكز التكلفة؟" diff --git a/platform/resources/docs/02_app_structure/01_levels_of_accounting.md b/platform/resources/docs/02_app_structure/01_levels_of_accounting.md new file mode 100644 index 00000000..61046dea --- /dev/null +++ b/platform/resources/docs/02_app_structure/01_levels_of_accounting.md @@ -0,0 +1,70 @@ +# مستويات المحاسبة في النظام + +## 1. نظام قيد (qayd) — طبقتان متكاملتان، لا طبقة واحدة + +نظام قيد لا يُقدّم محاسبةً من نمط واحد. إنه يُقدّم **طبقتَي محاسبة** تعملان جنباً إلى جنب، كل منهما لغرض مختلف: + +**المحاسبة المالية الرسمية**: القيود المزدوجة، دفتر الأستاذ، الميزانية العمومية، ميزان المراجعة. هذه الطبقة مُحكَمة رياضياً ولا تقبل الاستثناء. + +**المحاسبة الإدارية التحليلية**: مراكز التكلفة، الأبعاد، تقارير الإنفاق بحسب الغرض. هذه الطبقة مرنة ومعلوماتية، لا تُؤثّر على الأرصدة. + +الفارق بين الطبقتين: **الأولى تُجيب "كم رصيدي؟"**. **الثانية تُجيب "أين أنفقتُ رصيدي؟"** + +## 2. المحاسبة المالية — الهيكل الصلب + +كل ما يظهر في دفتر الأستاذ وتقارير الميزانية هو جزء من المحاسبة المالية. خصائصها: + +- **إلزامية التوازن**: مجموع المدينات = مجموع الدائنيات دائماً. +- **اللارجعة**: القيد المُسجَّل لا يُحذَف، الخطأ يُصحَّح بقيد جديد. +- **الاستقلالية عن الإنترنت**: هذه البيانات على جهازك، تعمل دون اتصال. +- **الدقة الكاملة**: لا أرقام عشرية عائمة، لا تقريب غير مُعلَن. + +هذه الطبقة هي "الشهادة الرسمية" لوضعك المالي. إذا كان هناك نزاع حول رصيدك، هنا الحقيقة الموثّقة. + +## 3. محاسبة التكلفة — الطبقة التحليلية المرنة + +مراكز التكلفة وأبعادها تعمل فوق الطبقة المالية. خصائصها: + +- **لا أثر على الأرصدة**: إضافة أو إزالة مركز تكلفة لا تُغيّر أي رصيد حساب. +- **اختيارية في المعاملات**: يمكن تسجيل معاملة بدون تصنيف مركز تكلفة. +- **قابلية التحليل المتعدد**: نفس المعاملة يمكن تصنيفها تحت أكثر من بُعد تحليلي. +- **لا توازن مشروط**: لا قاعدة "مجموع = صفر" تحكم هذه الطبقة. + +هذه الطبقة هي "عيونك الإحصائية" على سلوكك المالي. تُجيب على: من أين تأتي مصروفاتي؟ هل أنفق على الضروريات أكثر مما يجب؟ + +## 4. دورة حياة المعاملة عبر الطبقتين + +عندما تُسجّل سنداً وتُؤكّده: + +**الطبقة الأولى تُنشَّط أولاً**: النظام يُنشئ القيد المزدوج فوراً — مدين ودائن متطابقان. يُحدَّث رصيد الحسابات. + +**الطبقة الثانية تُنشَّط مستقلة**: النظام يُسجّل ارتباط هذا السند بمراكز التكلفة المختارة. إذا لم تختر مركزاً، تبقى الطبقة الثانية فارغة لهذه المعاملة — لكن الطبقة الأولى مكتملة. + +هذا التسلسل يُظهر الأولوية: المحاسبة المالية إلزامية، محاسبة التكلفة اختيارية. + +## 5. لماذا الفصل ضروري؟ + +دمج الطبقتين في طبقة واحدة سيُؤدّي لمشاكل خطيرة: + +- إذا كانت مراكز التكلفة تُؤثّر على أرصدة الحسابات، فتعديل مركز تكلفة سيُعيد رسم الأرصدة التاريخية — وهذا تزوير. +- إذا كانت التصنيفات الإدارية تُشارك في التوازن المحاسبي، فكل تغيير تصنيفي يوجب إعادة التوازن. + +الفصل يُبقي الطبقة الصلبة نقية وغير مُلوَّثة بالضبابية التحليلية، ويُبقي الطبقة التحليلية حرة ومرنة بلا قيود المحاسبة الرسمية. + +## 6. ما الذي يُحدّد المستوى الذي تعمل فيه؟ + +**في تبويب السندات**: تعمل في كلتا الطبقتين معاً. تُسجّل السند (طبقة 1) وتُضيف التصنيف التحليلي (طبقة 2). + +**في تبويب التقارير**: تستعرض نتائج الطبقة الأولى (الأرصدة والميزانية) وأحياناً الطبقة الثانية (توزيع الإنفاق). + +**في تبويب مراكز التكلفة**: تعمل حصراً في الطبقة الثانية. + +هذا يعني: خطأ في السند يُؤثّر على الطبقة الأولى ويحتاج "سند تصحيح". خطأ في التصنيف التحليلي يُؤثّر فقط على الطبقة الثانية ويمكن تصحيحه بتعديل أبسط. + +## 7. كيف تُفكر عند الشك؟ + +سؤال مرشد: "هل هذا سيُؤثّر على رصيد حسابي؟" +- إذا **نعم**: أنت في الطبقة الأولى. كن دقيقاً جداً. +- إذا **لا**: أنت في الطبقة الثانية. أنت في أمان من المشاكل المحاسبية الجوهرية. + +هذا التمييز يُريحك نفسياً: الأخطاء في الطبقة الثانية لا تُدمّر ميزانيتك المالية. أخطاء الطبقة الأولى هي ما يستحق التروّي والتثبّت. diff --git a/platform/resources/docs/02_app_structure/02_basic_vs_advanced_accounting.md b/platform/resources/docs/02_app_structure/02_basic_vs_advanced_accounting.md new file mode 100644 index 00000000..fdcaf289 --- /dev/null +++ b/platform/resources/docs/02_app_structure/02_basic_vs_advanced_accounting.md @@ -0,0 +1,70 @@ +# المحاسبة الأساسية مقابل المتقدمة + +## 1. للمستخدم اليومي — المحاسبة الأساسية + +الغالبية العظمى من مستخدمي نظام قيد لن يحتاجوا في حياتهم اليومية إلى أكثر مما تُقدّمه "المحاسبة الأساسية": + +- إنشاء وإدارة الحسابات الشخصية. +- تسجيل السندات (مصروفات وإيرادات). +- تتبع الديون والمستحقات مع الأطراف الآخرين. +- استعراض التقارير الأساسية. +- إنشاء مراكز التكلفة وتصنيف الإنفاق. + +هذه العمليات تُغطي 95% من الاستخدام اليومي وتعمل بسلاسة دون الحاجة لفهم المفاهيم المتقدمة. + +## 2. المحاسبة المتقدمة — للحالات الأعمق + +"المحاسبة المتقدمة" في نظام قيد تُشير لمجموعة من العمليات التي تتطلب فهماً أعمق لمنطق النظام أو تُؤثّر على هيكله الجوهري: + +**تعديل الحسابات الجوهرية**: التعامل مع الحسابات الافتراضية المحمية أو هيكلة حسابات معقدة. + +**إدارة العملات**: التعامل مع حسابات بعملات متعددة مع فهم أن الحسابات المنفصلة لكل عملة هي المنهج المعتمد. + +**تحويلات ثلاثية الأطراف**: الوساطة بين طرفَيْن — وهو نمط متقدم يتطلب فهم منطق الشرطية والتوقيت. + +**إعداد سياسات التحويل**: تحديد شروط استقبال طلبات التحويل والتعامل معها. + +## 3. ما الذي يجعل شيئاً "متقدماً"؟ + +العلامات التي تُشير لأنك في نطاق المتقدم: + +- أنت تُغيّر هيكل النظام لا فقط تُضيف بيانات. +- العملية تُؤثّر على ثبات الحسابات الجوهرية. +- القيد المحاسبي الناتج أكثر تعقيداً من "مدين/دائن" بسيط. +- لديك أطراف متعددون في معاملة واحدة. + +## 4. لماذا لا يُعطَى الجميع وصولاً كاملاً تلقائياً؟ + +المنطق بسيط: الإجراءات المتقدمة يمكن أن تُلحق ضرراً على الهيكل المحاسبي إذا نُفّذت بدون فهم. مثلاً: + +- تعديل تصنيف حساب جوهري قد يُفسد توازن الميزانية. +- إنشاء تحويل ثلاثي بدون فهم القفل المشروط قد يُترك ذمم معلقة. + +التصميم الذي يُفصل "الأساسي" عن "المتقدم" ليس عائقاً — إنه حماية. + +## 5. المسار من الأساسي إلى المتقدم + +لا يوجد "مستوى تقني" مطلوب للانتقال. المطلوب هو **الفهم**. الانتقال يحدث حين: + +1. تفهم تماماً كيف تعمل السندات والحسابات الأساسية. +2. يظهر لك احتياج لا تتيحه الأدوات الأساسية. +3. تقرأ الشرح المخصص للميزة المتقدمة في هذا الدليل. + +بناء الفهم التدريجي هو الطريق الصحيح — لا "تجربة والخطأ" في الأنظمة المحاسبية. + +## 6. ما يبقى ثابتاً بغض النظر عن المستوى + +سواء كنت في "الأساسي" أو "المتقدم"، هذه القواعد لا تتغير: + +- القيد المزدوج المتوازن إلزامي. +- السند يسبق القيد. +- الماضي المؤكَّد لا يُمحى. +- التشفير والأمان يعملان في الخلفية دائماً. + +المستوى "المتقدم" يُوسِّع ما تستطيع فعله — لكنه لا يُخفّف القواعد الجوهرية أبداً. + +## 7. نصيحة للمستخدم الجديد + +إذا كنت تبدأ: **ابقَ في الأساسي لأول ثلاثة أشهر**. أتقن تسجيل السندات اليومية، وبناء مراكز التكلفة، واستعراض التقارير. بعد أن تُصبح هذه الأنشطة طبيعية وتلقائية، سيظهر لك بوضوح متى تحتاج المتقدم — وستكون مؤهلاً لفهمه. + +الانتقال المبكر للمتقدم قبل إتقان الأساسي هو المصدر الأكثر شيوعاً للإحباط وسوء التهيئة. diff --git a/platform/resources/docs/02_app_structure/03_sidebar_authority_model.md b/platform/resources/docs/02_app_structure/03_sidebar_authority_model.md new file mode 100644 index 00000000..b5687176 --- /dev/null +++ b/platform/resources/docs/02_app_structure/03_sidebar_authority_model.md @@ -0,0 +1,70 @@ +# نموذج الصلاحيات والحوكمة + +## 1. ما معنى "الحوكمة" في نظام قيد؟ + +"الحوكمة" في قيد تُشير لآلية التحقق من أن استخدامك للنظام ضمن النطاق المُصرَّح به. كل محاولة تعديل أو إضافة بيانات تمر عبر "بوابة الكتابة" قبل أن يُقبَل أي تغيير. + +هذه البوابة لا يمكن الالتفاف عليها. لا يوجد في الكود مسار يُتيح حفظ بيانات دون المرور بها. إنها بوابة وحيدة لكل عمليات الكتابة. + +## 2. حالات الحوكمة الأربع + +لنظام القيد أربع حالات إدارية ممكنة تُحدّد ما يُسمح به: + +**مُفعَّل (activated)**: +الوضع الطبيعي. كل عمليات القراءة والكتابة مسموحة بلا أي قيد. + +**مُعلَّق (suspended)**: +وضع مؤقت يُفرَض إدارياً. عمليات الكتابة (إنشاء سندات، تعديلات) مُحظورة. لكن عمليات القراءة — استعراض أرصدتك وتقاريرك — تبقى متاحة. يمكن التفكير فيه كـ"حساب مجمَّد تشاهد صاحبه لكن لا تُجري تحويلات". + +**مُلغى (revoked)**: +إلغاء دائم. عمليات الكتابة مُحظورة نهائياً. لا مسار للعودة من هذه الحالة. + +**منتهي (expired)**: +انتهت صلاحية الترخيص. قد تُطبَّق فترة سماح. دون تجديد، يُحوَّل النظام لحالة الإلغاء. + +## 3. لماذا تُحافظ حالة التعليق على إمكانية القراءة؟ + +هذا قرار تصميمي يُجسّد موقفاً أخلاقياً: بياناتك ملكك حتى في حال تعليق الحساب. النظام لا يحجز بياناتك كورقة ضغط. يمكنك دائماً رؤية ما لديك — حتى لو تعذّر إضافة الجديد. + +هذا يُتيح لك في حالة التعليق: تنزيل التقارير، استعراض الأرصدة، الإعداد للخروج من النظام أو حل مشكلة الترخيص — مع الحفاظ على وصولك لبياناتك. + +## 4. الترخيص وحارس الدورة — الحماية من الالتفاف + +يُطبَّق نظام الحوكمة مع **حارس الساعة** لمنع التلاعب بالتواريخ لتمديد فترة التجربة: + +- التطبيق يُسجّل الوقت عند كل إغلاق. +- عند الفتح، يُقارن الوقت الحالي بآخر وقت مُسجَّل. +- إذا تراجعت الساعة أكثر من 60 ثانية: يُكشَف التلاعب. +- النتيجة: تنبيه أو تجميد. + +فترة التسامح (60 ثانية) موجودة لأن تعديلات NTP الشبكية الطبيعية قد تُزيح الساعة ببضع ثوانٍ. لكن تراجعها بساعات أو أيام — هذا تدخل مقصود ويُكشَف. + +## 5. الحوكمة اللامركزية — القرار في السحابة، التنفيذ على الجهاز + +النظام يستخدم نمط "التقييم البعيد والتنفيذ المحلي": + +- **التقييم**: الخادم يُصدر رمز ترخيص (JWT) يُحدّد حالة الحوكمة. +- **التنفيذ**: جهازك يقرأ هذا الرمز ويُطبّق القواعد محلياً، حتى بدون اتصال. + +هذا يعني: إذا كنت مُفعَّلاً وانقطع الإنترنت، تبقى مُفعَّلاً وتعمل بشكل طبيعي. إذا كنت مُعلَّقاً وانقطع الإنترنت، تبقى مُعلَّقاً. الحالة لا تعتمد على الاتصال اللحظي. + +رمز الترخيص مُخزَّن في التخزين الآمن للجهاز — وهو محمي من التعديل بدون وصول على مستوى نظام التشغيل. + +## 6. عملية المسح الطارئ — الزر النووي + +في إعدادات الأمان، يوجد خيار "المسح الطارئ". هذه العملية تُدمّر دفعة واحدة: +- جميع المفاتيح التشفيرية المُخزَّنة. +- قاعدة البيانات المالية كاملة. +- جميع ملفات المرفقات. + +**تحذير مطلق**: هذا التدمير لا رجعة فيه بأي طريقة. لا "استعادة نسخة احتياطية" بعده ما لم تكن قد صدّرت نسخة احتياطية خارجية مسبقاً. + +هذا الخيار موجود لسبب: النظام يُقدّر أن **انعدام البيانات أفضل من اختراقها**. إذا كنت في موقف تشعر فيه أن جهازك سيقع في يد شخص لا يُريد له أن يرى بياناتك — المسح الطارئ هو خيارك الأمثل. + +## 7. خلاصة — الحوكمة كحارس لا كقيد + +نظام الحوكمة ليس موجوداً لتقييدك بل لحمايتك: +- يحميك من الاستخدام غير المُصرَّح به لحسابك. +- يحميك من التلاعب بالساعة لخداع فترات التجربة. +- يُبقي بياناتك قابلة للاطلاع حتى في أصعب الظروف. +- يُتيح لك المسح الكامل إذا أردتَ ذلك بإرادتك. diff --git a/platform/resources/docs/02_app_structure/_category_.json b/platform/resources/docs/02_app_structure/_category_.json new file mode 100644 index 00000000..1aa6470b --- /dev/null +++ b/platform/resources/docs/02_app_structure/_category_.json @@ -0,0 +1,4 @@ +{ + "label": "هيكلية التطبيق", + "position": 2 +} diff --git a/platform/resources/docs/03_daily_operations/00_creating_vouchers.md b/platform/resources/docs/03_daily_operations/00_creating_vouchers.md new file mode 100644 index 00000000..f3f88e39 --- /dev/null +++ b/platform/resources/docs/03_daily_operations/00_creating_vouchers.md @@ -0,0 +1,74 @@ +# إنشاء السندات — من الفكرة إلى القيد المحاسبي + +## 1. قبل إنشاء السند — ما تحتاج معرفته + +إنشاء السند هو العملية الأكثر تكراراً في نظام قيد. لتجنب المشاكل، تأكد من توافر هذه المتطلبات: + +**أولاً: الحسابات موجودة**. قبل إنشاء سند، يجب أن يكون الحساب الذي ستُسند إليه المعاملة موجوداً. لا يمكن إنشاء سند يشير لحساب غير موجود. + +**ثانياً: فهم واضح للطرف الآخر**. كل سند يحتاج "الطرف الآخر" — هو الشخص أو الجهة التي تتعامل معها. إذا لم يكن هذا الطرف موجوداً كحساب، أنشئه أولاً. + +**ثالثاً: البيانات المالية الصحيحة جاهزة**. المبلغ الصحيح، العملة الصحيحة، التاريخ الصحيح (وقد يكون لأمس أو ما قبله). + +## 2. العناصر الأساسية لأي سند + +| العنصر | ما يعنيه | لماذا مطلوب | +|--------|---------|-------------| +| النوع | قبض أم دفع | يُحدّد اتجاه القيد المحاسبي | +| التاريخ | تاريخ الحدث الاقتصادي | يُحدّد متى يُسجَّل القيد في دفتر الأستاذ | +| المبلغ | القيمة المالية | لا معاملة بدون قيمة — الصفر مرفوض | +| العملة | عملة الحدث | منع الخلط بين عملات مختلفة | +| الطرف الآخر | الجهة المقابلة | نصف القيد المزدوج | +| الحساب المتأثر | تصنيفك الداخلي | النصف الآخر من القيد المزدوج | + +## 3. التاريخ الاقتصادي مقابل تاريخ التسجيل + +نقطة مربكة يجب التوضيح حولها: التطبيق يُفرّق بين: + +**تاريخ الحدث (date)**: متى وقعت المعاملة فعلاً في الواقع. هذا هو ما يُحدّد موضع القيد في تقاريرك ودفتر أستاذك. + +**تاريخ الإنشاء (createdAt)**: متى أدخلتَ البيانات في النظام. هذا لأغراض التدقيق فقط. + +**المثال**: اشتريتَ بقالة أمس ونسيتَ التسجيل. تُسجّل اليوم لكن تُدخل تاريخ الأمس كـ"تاريخ الحدث". القيد في دفتر الأستاذ سيظهر في اليوم الصحيح — أمس — لا اليوم. + +هذا مهم: لا تُسجّل اليوم كتاريخ لمعاملات الأمس. السجل المالي يُفترض أن يعكس الزمن الفعلي للأحداث، لا زمن تسجيلها. + +## 4. السند الصادر مني أم الوارد إليّ؟ + +من منظورك: +- **دفع**: مال يخرج منك — سند دفع. +- **قبض**: مال يأتي إليك — سند قبض. + +هذا التعريف يبدو بسيطاً لكنه يُزبك بعض المستخدمين عند التعامل مع الديون: + +- أقرضتَ شخصاً 500 ﷼ → **أنت دفعتَ** (سند دفع). المال خرج منك إليه. +- سددتَ قسطاً لبنك → **أنت دفعتَ** (سند دفع). المال خرج منك للبنك. +- استلمتَ راتبك → **استلمتَ** (سند قبض). المال وصلك. +- استُرجع لك مبلغ → **استلمتَ** (سند قبض). + +## 5. المسودة ثم التأكيد — لا تستعجل + +عند إنشاء سند، يبدأ في حالة "مسودة". هذا يمنحك فرصة المراجعة قبل التأكيد النهائي. + +**في المسودة**: كل شيء قابل للتعديل. لا قيود مُنشأة بعد. + +**بعد التأكيد**: القيود المزدوجة تُنشأ فوراً ولا رجعة فيها. المحتوى الجوهري (المبلغ والأطراف) يصبح ثابتاً. + +نصيحة: إذا كنت تُسجّل سنداً لطرف آخر موجود في النظام، أرسله في مرحلة المسودة واطلب مراجعته قبل تأكيده — خاصة لمبالغ كبيرة أو معقدة. + +## 6. ما يمنعه النظام عند إنشاء السند + +النظام يرفض هذه الحالات برسائل خطأ واضحة: + +- **مبلغ صفر أو سالب**: لا معنى لمعاملة بقيمة صفر. المعاملة لا تحدث. +- **نفس الحساب طرفاً ومتأثراً**: قيد ذاتي يلغي نفسه — لا أثر مالي حقيقي. +- **عملتان مختلفتان في معاملة**: لا تحويل ضمني للعملات. كل عملة لها حسابها المستقل. +- **حالة الحوكمة لا تسمح بالكتابة**: إذا كان حسابك في حالة تعليق. + +هذه الرفضات ليست تعقيدات — هي حماية من تسجيل بيانات لا معنى لها أو مُضلِّلة. + +## 7. إضافة مرفقات وملاحظات — الأدلة الداعمة + +يمكنك إرفاق ملفات (فواتير، إيصالات) بكل سند. المرفق يُخزَّن على جهازك مع حساب بصمته للتحقق من سلامته عند الفتح. + +الملاحظات الخاصة تُضاف للسند كذلك — وهي مرئية لك فقط، لا تُشارَك مع الطرف الآخر في حالة السندات الثنائية. diff --git a/platform/resources/docs/03_daily_operations/01_receipts_and_payments.md b/platform/resources/docs/03_daily_operations/01_receipts_and_payments.md new file mode 100644 index 00000000..405c5c3e --- /dev/null +++ b/platform/resources/docs/03_daily_operations/01_receipts_and_payments.md @@ -0,0 +1,79 @@ +# سندات القبض والدفع — منطق التدفق المالي + +## 1. سند القبض — ماذا يعني فعلاً؟ + +سند القبض (Receipt) يُسجَّل حين يصلك مال من طرف خارجي. "الطرف الخارجي" هنا واسع المعنى: + +- صاحب العمل يدفع لك الراتب. +- عميل يدفع ثمن خدمة قدّمتَها. +- شخص يُسدّد قرضاً أخذه منك. +- استرداد مبلغ دفعتَه سابقاً. +- هبة أو دعم مالي من أحد. + +الشيء المشترك: **المال ينتقل من طرف خارج حساباتك الداخلية إلى داخلها**. + +## 2. سند الدفع — ماذا يعني فعلاً؟ + +سند الدفع (Payment) يُسجَّل حين يخرج مال منك إلى طرف خارجي: + +- دفع فاتورة لخدمة. +- شراء بضاعة أو منتج. +- إقراض شخص مبلغاً. +- سداد قسط لبنك أو جهة. +- دفع أجور. + +الشيء المشترك: **المال ينتقل من داخل حساباتك الداخلية إلى خارجها**. + +## 3. التمييز يُحدّد القيد المحاسبي تلقائياً + +لماذا يهم هذا التمييز؟ لأن النظام يُنتج القيدين المحاسبيين تلقائياً بحسب النوع: + +**سند قبض بمبلغ 1000 ﷼**: +- مدين: الحساب المتأثر (زاد بـ1000). +- دائن: حساب الطرف الآخر (المصدر) بـ1000. + +**سند دفع بمبلغ 1000 ﷼**: +- مدين: حساب الطرف الآخر (المستفيد) بـ1000. +- دائن: الحساب المتأثر (نقص بـ1000). + +أنت لا تُدخل "مدين/دائن" يدوياً أبداً. أنت تُخبر النظام **ما حدث في الواقع** — النظام يُترجمه للقيد الصحيح. + +## 4. الحسابات المتأثرة بحسب نوع المعاملة + +**للمصروف اليومي (سند دفع)**: +- الطرف الآخر: المتجر أو الجهة المُدفوع لها. +- الحساب المتأثر: حساب مصروفات (طعام، نقل، صحة، إلخ). +- النتيجة: رصيد حسابك النقدي ينقص، رصيد المصروف يرتفع. + +**للإيراد الشخصي (سند قبض)**: +- الطرف الآخر: صاحب العمل أو مصدر الدخل. +- الحساب المتأثر: حساب الإيرادات الشخصية. +- النتيجة: رصيد حسابك النقدي يرتفع، رصيد الإيرادات يرتفع. + +**للقرض المُعطى (سند دفع)**: +- الطرف الآخر: حساب المدين (من أقرضته). +- الحساب المتأثر: حسابك النقدي. +- النتيجة: رصيد النقدية ينقص، رصيد الذمة عليه يرتفع. + +## 5. التاريخ الاقتصادي — متى حدث الأمر فعلاً؟ + +تذكّر دائماً: اكتب **تاريخ الحدث الفعلي** لا تاريخ التسجيل. + +إذا اشتريتَ خميساً وسجّلتَ الأحد: اكتب الخميس. + +هذا يُؤثّر على: +- موضع القيد في التقارير الشهرية والسنوية. +- حساب رصيد الميزان في أي تاريخ محدد. +- دقة التحليل بين الفترات. + +## 6. العملة — قاعدة الصرامة التامة + +كل سند يجب أن يكون بعملة واحدة. النظام لا يقبل سنداً يمزج عملتين. إذا أردتَ تحويل عملة، تُنشئ سندات منفصلة لكل طرف من المعاملة. + +لماذا هذه الصرامة؟ لأن سعر الصرف متغير. التحويل الضمني بسعر "افتراضي" سيُؤدّي لأرصدة لا تعكس الواقع على المدى البعيد. الصرامة تُبقيك مسؤولاً عن قرار التحويل. + +## 7. متى يُصبح السند "مُؤثِّراً" في أرصدتك؟ + +السند لا يُؤثّر على أرصدتك حتى يُؤكَّد. في مرحلة المسودة: يوجد في النظام لكن بلا أثر على أي حساب. عند التأكيد: القيدان المزدوجان يُنشآن فوراً وتُحدَّث الأرصدة. + +هذا يعني: إذا أنشأتَ سنداً ثم تركتَه "مسودة" ونسيتَه، رصيدك في التقارير لن يعكسه. المسودات لا أثر لها. التأكيد هو الفعل الذي "يُحيي" السند فعلياً. diff --git a/platform/resources/docs/03_daily_operations/02_transfers_and_mediation.md b/platform/resources/docs/03_daily_operations/02_transfers_and_mediation.md new file mode 100644 index 00000000..4285df5f --- /dev/null +++ b/platform/resources/docs/03_daily_operations/02_transfers_and_mediation.md @@ -0,0 +1,84 @@ +# التحويلات والوساطة — الوسيط المالي في النظام + +## 1. ما هي الوساطة المالية في سياق قيد؟ + +الوساطة المالية تُشير لسيناريو يظهر كثيراً في الحياة الواقعية: شخص يريد إرسال مال لآخر، لكن لا يستطيع مباشرة — فيُوكّل وسيطاً. + +**مثال من الحياة**: خالد في السعودية يريد إرسال مال لعائلته في اليمن، لكن لا يملك قناة مباشرة. محمد في السعودية يعرف شخصاً في اليمن. فيُودع خالد المال عند محمد، ومحمد يُسلّم المبلغ لعائلة خالد هناك. + +في هذا السيناريو: محمد هو الوسيط. النظام المالي في قيد مُصمَّم لتوثيق هذا الدور بدقة وحمايته. + +## 2. التحويل الثلاثي — ثلاثة أطراف وسندان + +عندما تكون وسيطاً، تُنشئ النظام **تحويلاً ثلاثياً** يتكون من: + +**السند الأول (القبض)**: المال الذي استلمتَه من الطرف المُرسِل (خالد في المثال). يُسجَّل كقبض في حسابك. + +**السند الثاني (الدفع المشروط)**: المال الذي ستدفعه للطرف المُستقبِل (عائلة خالد). هذا السند يُنشأ منذ البداية لكنه **مقفل** حتى يتحقق السند الأول. + +الكلمة المفتاحية هنا: **مشروط**. لا يمكنك إرسال السند الثاني أو تأكيده حتى يتأكد السند الأول. + +## 3. لماذا القفل المشروط ضروري؟ + +هذا القفل هو الفارق بين الوساطة الموثوقة والكلام الفارغ. + +**بدون القفل**: ثمة وسيط يُنشئ سندَيْن ويُؤكّدهما في آنٍ واحد — يقول للمرسِل "استلمتُ" وللمستقبِل "أرسلتُ" قبل أن يُستلم المال فعلاً. هذا تزوير أو على الأقل خطأ. + +**مع القفل**: السند الثاني لا يُؤكَّد إلا بعد تأكيد الأول فعلياً. الوسيط لا يملك تقنياً إمكانية "الدفع المزعوم قبل الاستلام". + +القفل يُفرضه النظام برمجياً — الوسيط لا يستطيع الالتفاف عليه. + +## 4. رسوم الوساطة — إذا كان للوسيط أجر + +إذا كنت تعمل وسيطاً بأجر، يُتيح النظام إضافة رسوم: +- تُحدّد الرسوم عند إنشاء التحويل الثلاثي. +- النظام يُنشئ تلقائياً سنداً ثالثاً لتسجيل الرسوم كإيراد في حسابك. +- هذا السند الثالث مرتبط بنفس مجموعة التحويل للتتبع الكامل. + +هذا يعني: حتى الأجر التجاري لعملك كوسيط يُسجَّل بشكل واضح ومُنتج لقيد إيراد في حسابك. + +## 5. معرف المجموعة — ما يربط السندات الثلاثة + +كل التحويل الثلاثي لديه "معرف مجموعة" فريد يُشار إليه في كل سنداته (القبض، الدفع، الرسوم). هذا المعرف يُتيح لك: + +- استعراض التحويل الثلاثي كوحدة واحدة لا كسندات منفصلة. +- التأكد من اكتمال التسلسل (القبض → تحرير القفل → الدفع). +- تتبع أي تحويل من أي سند فيه. + +## 6. الشفافية للأطراف — كل طرف يرى ما يخصه + +التحويل الثلاثي مُصمَّم بشفافية مدروسة: + +- الطرف المُرسِل (خالد) يرى: "أرسلتُ لمحمد وسيطاً والمستفيد النهائي عائلتي في اليمن". +- الطرف المُستقبِل (العائلة) يرى: "استلمنا من محمد والمُرسِل الأصلي خالد". +- الوسيط (محمد) يرى: التدفق الكامل من المُرسِل إليه ومنه للمستقبِل. + +هذه الشفافية تحمي جميع الأطراف وتمنع إنكار أي طرف لدوره. + +## 7. الفرق بين اختيار الوساطة والتحويل المباشر + +| السيناريو | الشكل الصحيح | +|-----------|-------------| +| أنا أُرسِل لشخص مباشرة | سند دفع بسيط | +| أنا أستلم من شخص مباشرة | سند قبض بسيط | +| أنا أُرسِل نيابةً عن شخص لآخر | تحويل ثلاثي أنا فيه الوسيط | +| أنا أُرسِل لشخص مع وجود وسيط | سند قبض للوسيط، الوسيط يُنشئ الثلاثي | + +لا تُحوّل "أنا أُرسِل مباشرة" إلى تحويل ثلاثي — ذلك يُضيف تعقيداً غير ضروري. + +## 8. الوساطة لا تُلوّث أرصدتك الشخصية — ولا محادثاتك + +نقطة يُثيرها كثير من الوسطاء عند أول استخدام: + +> "أنا لدي رصيد شخصي مع خالد من تعاملات سابقة. هل التحويل الثلاثي الذي سأُجريه له سيُغيّر هذا الرصيد؟ وهل سيظهر التحويل في محادثتنا؟" + +**الإجابة المزدوجة:** + +١. **رصيدك معه لم يتغير** — قيود التحويل الثلاثي تمر عبر صندوقك النقدي الوسيط حصراً. + +٢. **التحويل لن يظهر في محادثتك معه** — بل سيظهر في محادثة المُرسِل (خالد) مع المُستقبِل (بديع) مباشرة، مع ذكر اسمك أنت كـ"وسيط". + +هذا هو الفارق الجوهري بين "الوساطة النظيفة" وأي قيدَيْن متتاليَيْن عاديَيْن. + +← تفصيل كامل لهذا المبدأ في الفصل السادس: [عزل القيود المحاسبية](../06_transfers_system/05_accounting_isolation.md) + diff --git a/platform/resources/docs/03_daily_operations/03_editing_and_corrections.md b/platform/resources/docs/03_daily_operations/03_editing_and_corrections.md new file mode 100644 index 00000000..f1a2ce95 --- /dev/null +++ b/platform/resources/docs/03_daily_operations/03_editing_and_corrections.md @@ -0,0 +1,68 @@ +# التعديل والتصحيح — كيف تُصلح خطأً بدون تزوير؟ + +## 1. المبدأ الجوهري: التصحيح إضافة، لا حذف + +في نظام قيد، لا يمكن تعديل سند مؤكَّد مباشرة. هذا ليس عجزاً تقنياً — إنه قرار معماري مقصود يُجسّد مبدأ المحاسبة الأصيل: + +**السجل المالي يُضاف إليه، لا يُمحى منه.** + +"التصحيح" في المحاسبة الحقيقية ليس محو الخطأ — إنه إضافة حدث جديد يعكس الحدث الخاطئ. بعد ذلك يوجد في سجلك: الحدث الخاطئ (موسوم بالسحب) + الحدث الصحيح. المراجِع يرى كليهما ويفهم ما جرى. + +## 2. متى يمكن التعديل بشكل مباشر؟ + +التعديل المباشر ممكن **فقط في مرحلة المسودة**: + +- السند في حالة مسودة: كل حقوله قابلة للتعديل. لا قيد مُنشأ بعد. +- بعد التأكيد: المحتوى الجوهري (المبلغ، الأطراف، النوع، التاريخ) ثابت. + +**نصيحة**: راجع سندك بعناية قبل التأكيد. بعد التأكيد، التصحيح يستلزم خطوات إضافية. + +## 3. السحب — الطريقة الأولى للتصحيح + +**متى يُستخدم**: إذا تنبّهتَ للخطأ بعد تأكيد السند لكن **قبل** أن يقبله الطرف الآخر. + +**آلية العمل**: +1. تسحب السند (withdraw). +2. السند يتحول لحالة "مسحوب" — لا أثر مالي نشط. +3. القيود التي أُنشئت تبقى في السجل لكن بلا تأثير فعلي. +4. تُنشئ سنداً جديداً صحيحاً. + +**القيد الذي تجب معرفته**: لا يمكن سحب سند بعد أن يقبله الطرف الآخر. قبول الطرف الآخر يُغلق باب السحب الأحادي لأنه يُنشئ التزاماً ثنائياً. + +## 4. سند العكس — الطريقة الثانية + +**متى يُستخدم**: إذا أكّد الطرف الآخر السند وأصبح ثنائياً مُلزِماً، والخطأ يجب تصحيحه. + +سند العكس (reversal) هو سند من النوع المعاكس بنفس المبلغ يُبطل أثر الأول: + +**مثال**: سجّلتَ قبضاً بـ500 ﷼ خطأً وكان المبلغ الصحيح 400 ﷼. أنشأتَ سند دفع بـ500 ﷼ كـ"سند عكس". ثم أنشأتَ قبضاً جديداً بـ400 ﷼ صحيح. + +النتيجة: +500 - 500 + 400 = +400 ﷼. السجل يكشف كل الخطوات. + +## 5. السند المُعاد بعد الرفض — التفاوض الموثَّق + +حين يرفض الطرف الآخر سندك (مع ذكر سبب)، يمكنك: + +1. تأخذ علماً بالسبب. +2. تُنشئ سنداً معدَّلاً جديداً مُشيراً إلى السند الأصلي المرفوض. +3. النظام تلقائياً يسحب السند الأصلي ويرتبط الجديد به. + +هذا يُنشئ "خيط محادثة": السند الأصلي ← الرفض مع السبب ← السند المعدَّل. التاريخ موثَّق بالكامل بلا فجوات. + +## 6. تصحيحات مراكز التكلفة — أبسط بكثير + +إذا أخطأتَ في التصنيف التحليلي لسند (اخترتَ مركز تكلفة خاطئاً): + +هذه الحالة **أبسط بكثير** لأن مراكز التكلفة لا تُؤثّر على الأرصدة المحاسبية. في أغلب الحالات يمكن تصحيح ارتباط مركز التكلفة دون التأثير على السند نفسه. + +هذا يُذكّرك بأهمية الفصل بين الطبقتين: خطأ في الطبقة التحليلية أبسط تصحيحاً من خطأ في الطبقة المحاسبية. + +## 7. اسأل نفسك قبل التصحيح + +قبل بدء أي تصحيح: +- هل أنا في مرحلة المسودة؟ → عدّل مباشرة. +- هل أكّدتُ السند لكن الطرف الآخر لم يقبله بعد؟ → اسحبه وأنشئ جديداً. +- هل قبل الطرف الآخر السند؟ → ستحتاج سند عكس. +- هل الخطأ في التصنيف التحليلي فقط؟ → عدّل الارتباط التحليلي مباشرة. + +التمييز بين هذه الحالات يُحدّد الطريق الصحيح ويُجنّبك تعقيد المسارات الخاطئة. diff --git a/platform/resources/docs/03_daily_operations/04_viewing_and_searching.md b/platform/resources/docs/03_daily_operations/04_viewing_and_searching.md new file mode 100644 index 00000000..4a7f87ed --- /dev/null +++ b/platform/resources/docs/03_daily_operations/04_viewing_and_searching.md @@ -0,0 +1,73 @@ +# العرض والبحث — كيف تصل لما تريده؟ + +## 1. قراءة قائمة السندات — الفهرس الزمني + +القائمة الرئيسية للسندات تعرض المعاملات بترتيب زمني عكسي — الأحدث أولاً. هذا هو النمط الأنسب لمراجعة ما سجّلتَه مؤخراً. + +كل سند في القائمة يُظهر: +- التاريخ الاقتصادي للحدث. +- المبلغ والعملة. +- نوع السند (قبض/دفع). +- الطرف الآخر. +- الحالة الراهنة (مسودة، مؤكَّد، مُسوَّى، مسحوب). + +القراءة السريعة للقائمة تُعطيك فهماً فورياً للنشاط المالي الأخير. + +## 2. تصفية السندات — تضييق نطاق العرض + +عندما تبحث عن شيء محدد، أدوات التصفية تُساعدك: + +**تصفية بالتاريخ**: حدّد فترة زمنية (مثل: هذا الشهر، الربع الأخير، سنة بعينها). + +**تصفية بالنوع**: أظهر فقط القبوض أو فقط المدفوعات. + +**تصفية بالحالة**: أظهر المسودات فقط، أو المؤكَّدة فقط، أو جميع غير المُسوَّاة. + +**تصفية بالطرف**: أظهر جميع معاملاتك مع طرف محدد. + +**تصفية بالحساب**: أظهر جميع السندات المرتبطة بحساب معين. + +دمج عدة مرشّحات معاً يُعطيك نتائج أدق: "مدفوعاتي لمتجر البقالة خلال الربع الثالث". + +## 3. عرض تفاصيل السند — الصورة الكاملة + +عند النقر على سند، تُعرض كل تفاصيله: +- جميع الحقول المُدخَلة عند الإنشاء. +- حالة الطرف الآخر (هل وصله السند؟ هل قبله؟). +- ارتباطات مراكز التكلفة إن وجدت. +- المرفقات إن وجدت. +- ارتباط بسندات أصلية أو مرتبطة (للسندات الجزء من خيط تصحيح). +- إذا كان السند جزءاً من تحويل ثلاثي: رابط للتحويل الكامل. + +## 4. كشف الحساب مع طرف محدد — المنظور المحادثاتي + +لاستعراض سجلك مع شخص بعينه، اذهب لحسابه واختر "كشف الحساب". يُقدَّم العرض على شكل محادثة: + +- معاملاتك الصادرة وواردة مُرتَّبة زمنياً. +- رصيد متراكم يتحرك مع كل معاملة. +- تمييز بين ما أرسلتَه وما أرسله هو. + +هذا العرض يُجيب على السؤال الأكثر شيوعاً: "كم يديني هذا الشخص الآن وكيف وصلنا لهذا الرقم؟" + +## 5. البحث النصي — البحث عن كلمة أو وصف + +يمكنك البحث في حقول الوصف والملاحظات بكلمات مفتاحية. مثلاً: "فاتورة الكهرباء" أو "قسط السيارة". + +**تنبيه**: البحث يعمل في النصوص القابلة للبحث فقط — الأوصاف والملاحظات. لا يبحث في الأرقام مباشرة (استخدم التصفية بالمبلغ لذلك). + +## 6. التقارير الإجمالية— أرقام، لا قوائم + +إذا كنت تريد إجماليات لا قوائم تفصيلية، انتقل لتبويب التقارير: + +- الميزانية العمومية: رصيد كل تصنيف حسابي. +- ميزان المراجعة: مجاميع المدينات والدائنيات لكل حساب. +- كشف الحساب لحساب بعينه: تاريخ حساب محدد مع الرصيد التراكمي. + +التقارير تُولَد من بيانات السندات المؤكَّدة فقط — المسودات لا تظهر في أي تقرير. + +## 7. قواعد ذهبية للعرض والبحث + +- دائماً تحقق من "نطاق التاريخ" المُطبَّق — قد يكون التقرير يُظهر شهراً واحداً فقط بشكل افتراضي. +- السندات المسحوبة موجودة لكن غير نشطة — يمكن تصفيتها للإظهار أو الإخفاء. +- عند مراجعة رصيد مع طرف: استخدم كشف الحساب التفصيلي، لا مجرد النظر لقائمة السندات. +- للتحقق من رصيد حساب في تاريخ محدد: التقارير تدعم "التاريخ الافتراضي" الذي تريد. diff --git a/platform/resources/docs/03_daily_operations/_category_.json b/platform/resources/docs/03_daily_operations/_category_.json new file mode 100644 index 00000000..8cf5d1eb --- /dev/null +++ b/platform/resources/docs/03_daily_operations/_category_.json @@ -0,0 +1,4 @@ +{ + "label": "العمليات اليومية", + "position": 3 +} diff --git a/platform/resources/docs/04_cost_centers_and_dimensions/00_cost_center_lifecycle.md b/platform/resources/docs/04_cost_centers_and_dimensions/00_cost_center_lifecycle.md new file mode 100644 index 00000000..2456e69e --- /dev/null +++ b/platform/resources/docs/04_cost_centers_and_dimensions/00_cost_center_lifecycle.md @@ -0,0 +1,67 @@ +# دورة حياة مراكز التكلفة — من الإنشاء إلى التعليق + +## 1. لماذا مراكز التكلفة لها "دورة حياة"؟ + +مراكز التكلفة ليست ثابتة للأبد ولا مُستهلَكة بسرعة. إنها كيانات تحليلية تمر بمراحل: +- تُنشأ حين يبدأ نشاط مالي جديد يستحق التتبع. +- تعمل بنشاط طوال فترة النشاط. +- تُعلَّق حين لا يعود النشاط قائماً. +- ولا تُحذَف أبداً — تاريخها يبقى. + +## 2. إنشاء مركز التكلفة — القرارات الأساسية + +عند إنشاء مركز جديد، تُحدّد: + +**الاسم**: اسم واضح يصف الغرض. مثل: "مشروع الشقة الجديدة"، "مصاريف الدراسة"، "مشروع التجارة". + +**النوع**: تكلفة أم ربح؟ +- تكلفة: إذا كان المركز يتتبع إنفاقاً فقط. +- ربح: إذا كان يتتبع إيرادات وتكاليف لتقييم جدوى. + +**الميزانية (اختيارية)**: حد أقصى للإنفاق. إذا ضُبطت، يمكنك تتبع نسبة استنزاف الميزانية. + +**الأبعاد المرتبطة**: أي فئات تحليلية ستُتيح عند توسيم المعاملات بهذا المركز. + +## 3. النوع لا يتغير — قرار لحظة الإنشاء + +هذه من القرارات التي يجب التروّي فيها: **نوع مركز التكلفة ثابت بعد الإنشاء**. + +إذا أنشأتَ "مشروع العقار" كمركز "تكلفة" وبعد سنة بدأ يُدرّ دخلاً — لا تستطيع تحويله لـ"ربح". ستضطر لإنشاء مركز جديد من نوع ربح والبدء من جديد بالتوسيم المستقبلي، بينما يبقى الماضي في المركز القديم. + +**التوجيه**: عند الشك، اختر "ربح" — هو يدعم تتبع التكاليف أيضاً بالإضافة للإيرادات. + +## 4. الميزانية — سقف إنفاق ليس حاجزاً تقنياً + +الميزانية في مركز التكلفة هي **معلومة للتنبيه**، لا قفل تقني. + +إذا ضبطتَ ميزانية قدرها 5000 ﷼ لمركز "رحلة العطلة"، والإنفاق تجاوزها — لن يرفض النظام تسجيل معاملات جديدة. لكن التقارير ستُظهر أنك تجاوزتَ الميزانية بوضوح. + +هذا قرار تصميمي: المحاسبة تُسجّل ما حدث فعلاً. الميزانية أداة تخطيط ومتابعة، لا قيد تشغيلي. + +## 5. مراكز التكلفة الافتراضية — محمية من التعديل والتعليق + +الإحدى عشر مركزاً الافتراضية (الدخل، السكن، الغذاء، النقل، إلخ) محمية بثلاث قواعد: + +- **لا تعليق**: لا يمكن إيقافها. +- **لا إعادة تسمية**: أسماؤها ثابتة. +- **لا حذف**: يبقى تاريخها دائماً. + +هذا يضمن أن تقاريرك عبر السنوات تستخدم نفس الفئات الثابتة، مما يُتيح المقارنة بين الفترات. + +## 6. تعليق مركز مخصص — الشرط والنتيجة + +للمراكز المخصصة التي تُنشئها، التعليق ممكن إذا تحقق شرط واحد: **رصيد المركز يساوي صفراً**. + +"رصيد المركز" يعني: مجموع ما سُجّل فيه من معاملات. إذا مازالت معاملات نشطة مرتبطة به، لا يمكن تعليقه. يجب أولاً تسوية هذه المعاملات أو نقلها. + +بعد التعليق: المركز يُزال من قوائم الاختيار النشطة. لكن تاريخه مرئي في التقارير. يمكن إعادة تفعيله لاحقاً. + +## 7. ما يجب مراعاته عند إعداد هيكل المراكز + +نصائح عملية لهيكلة مراكز التكلفة: + +- **لا تُنشئ مركزاً لكل معاملة صغيرة** — المراكز للأنشطة الرئيسية المستمرة. +- **لا تُنشئ أكثر مما يمكنك تتبعه يومياً** — التعقيد الزائد يُؤدّي للتخلي عن التوسيم. +- **ابدأ بالافتراضية** — هي تُغطي معظم الاحتياجات الأساسية. +- **أضف مخصصة حين يظهر احتياج واضح** — لا تُنشئ مسبقاً. +- **راجع المراكز كل ستة أشهر** — عطّل ما لا يُستخدم لتنظيف قائمة الاختيار. diff --git a/platform/resources/docs/04_cost_centers_and_dimensions/01_default_dimensions.md b/platform/resources/docs/04_cost_centers_and_dimensions/01_default_dimensions.md new file mode 100644 index 00000000..7358cc66 --- /dev/null +++ b/platform/resources/docs/04_cost_centers_and_dimensions/01_default_dimensions.md @@ -0,0 +1,73 @@ +# الأبعاد الافتراضية للحسابات — التوسيم التلقائي + +## 1. مشكلة وحلها — لماذا الأبعاد الافتراضية؟ + +كل مرة تُسجّل معاملة لمتجر البقالة، تُختار يدوياً مركز التكلفة "التغذية والاستهلاك اليومي" والبُعد "مصروفات الطعام". إذا سجّلتَ 50 معاملة لمتجر البقالة في الشهر، هذا يعني 50 مرة اختيار يدوي. + +مع مرور الوقت، هذا التكرار يُشجع على الإهمال وعدم التصنيف. + +الحل: **الأبعاد الافتراضية للحسابات**. تُضبَط مرة واحدة على مستوى الحساب (حساب متجر البقالة)، وكل معاملة جديدة مع هذا الحساب تُقترح عليها هذه الأبعاد تلقائياً. + +## 2. كيف تعمل الأبعاد الافتراضية؟ + +عند إنشاء حساب (أو تعديله)، يمكنك ضبط "الأبعاد الافتراضية": + +- ربط الحساب بمركز تكلفة محدد. +- وتحديد الأبعاد الأكثر شيوعاً داخل هذا المركز لهذا الحساب. + +عند إنشاء سند جديد مع هذا الحساب: +- النظام يُقترح تلقائياً هذه الأبعاد. +- يمكنك قبولها كما هي أو تعديلها للمعاملة الحالية فقط. +- تعديلك لمعاملة واحدة لا يُغيّر الإعداد الافتراضي للحساب. + +## 3. فرق مهم: الاقتراح لا الإلزام + +الأبعاد الافتراضية **مُقترحة، لا مُلزَمة**. عند إنشاء سند، يمكنك: + +- قبول الاقتراح دون تغيير (الأكثر شيوعاً للمعاملات الروتينية). +- تعديل الاقتراح لهذه المعاملة تحديداً (دون تغيير الافتراضي). +- مسح الاقتراح والتوسيم يدوياً (للمعاملات الاستثنائية). +- ترك الحقل فارغاً (المعاملة بلا تصنيف تحليلي). + +الاقتراح يُوفّر الجهد في الحالة الاعتيادية، ويُتيح المرونة في الاستثناء. + +## 4. متى يجب ضبط الأبعاد الافتراضية؟ + +ليس كل حساب يستحق أبعاداً افتراضية. الأنسب لها: + +- **الحسابات المتكررة**: متاجر، خدمات، أشخاص تتعامل معهم يومياً أو أسبوعياً. +- **الحسابات ذات التصنيف الواضح**: متجر البقالة دائماً = تغذية. محطة الوقود دائماً = نقل. +- **الحسابات بأبعاد ثابتة**: إذا كانت معظم معاملاتك مع هذا الحساب تندرج تحت نفس البُعد. + +لا تُضبط لـ: +- الحسابات النادرة التي تملك معهم معاملة كل أشهر. +- الحسابات التي تتنوع أبعادها كثيراً من معاملة لأخرى. + +## 5. تعديل الأبعاد الافتراضية — متى ولماذا؟ + +إذا تغيّر طابع تعاملاتك مع حساب، عدّل الافتراضي: + +- مثلاً: "متجر الإلكترونيات" كان كل مشترياتك منه شخصية (ترفيه). ثم بدأتَ تشتري منه لأغراض عمل. عدّل بعد الافتراضي أو أزله وصنّف يدوياً. + +التعديل يُؤثّر فقط على المعاملات المستقبلية. الماضي يبقى كما سُجّل. + +## 6. أبعاد افتراضية متعددة لحساب واحد + +يمكن تعريف أكثر من بُعد افتراضي لنفس الحساب: + +مثلاً: موزع "حساب المدرسة": +- البُعد الأول: "التعليم وتنمية القدرات". +- البُعد الثاني: "عبد الله" (الابن الذي يدرس هناك). + +عند التوسيم التلقائي، كلا البُعدَيْن يُقترحان معاً — فيظهر في تقاريرك كل ما دفعتَه على التعليم وكل ما دفعتَه على عبد الله. + +## 7. الأبعاد الافتراضية وعلاقتها بجودة التقارير + +جودة تقاريرك التحليلية تعتمد مباشرة على انتظام التوسيم. الأبعاد الافتراضية هي الأداة الأكثر فاعلية لجعل التوسيم منتظماً دون جهد. + +ستة أشهر من التوسيم المنتظم تُعطيك بيانات كافية لأسئلة مثل: +- ما نسبة إنفاقي على التعليم من إجمالي مصروفاتي؟ +- من أي حساب خرجت أكثر نفقاتي على الصحة؟ +- ما الشهر الذي ارتفعت فيه مصروفات النقل وبمقدار كم ارتفعت؟ + +الحل يبدأ بضبط الأبعاد الافتراضية على الحسابات التي تتفاعل معها يومياً. diff --git a/platform/resources/docs/04_cost_centers_and_dimensions/02_overriding_dimensions.md b/platform/resources/docs/04_cost_centers_and_dimensions/02_overriding_dimensions.md new file mode 100644 index 00000000..1048b214 --- /dev/null +++ b/platform/resources/docs/04_cost_centers_and_dimensions/02_overriding_dimensions.md @@ -0,0 +1,69 @@ +# تجاوز الأبعاد الافتراضية — التصنيف الاستثنائي + +## 1. لماذا تحتاج أحياناً تجاوز الافتراضي؟ + +الأبعاد الافتراضية للحسابات مُصمَّمة للحالة الاعتيادية. لكن الحياة المالية ليست دائماً اعتيادية. قد تجد نفسك: + +- تشتري من متجر البقالة لمناسبة اجتماعية (لا للاستهلاك اليومي). +- تدفع من محطة الوقود مصروفاً لشخص آخر أثناء الرحلة. +- تنفق من ميزانية شخصية لصالح مشروع عملي. + +في كل هذه الحالات، البُعد الافتراضي غير دقيق — والتوسيم الدقيق يُعطيك تقارير أصدق. + +## 2. آلية التجاوز — بسيطة وغير مؤثرة على الإعداد الأصلي + +عند إنشاء سند جديد: + +1. الأبعاد الافتراضية تظهر مُعبّأة مسبقاً. +2. يمكنك مسحها واستبدالها ببُعد آخر. +3. يمكنك إضافة أبعاد إضافية لم تكن في الافتراضي. +4. يمكنك ترك الحقل فارغاً إذا كانت المعاملة استثنائية بلا تصنيف واضح. + +**هام**: تعديلك لهذه المعاملة لا يُغيّر الإعداد الافتراضي للحساب. الإعداد الافتراضي يبقى كما كان للمعاملات المستقبلية. + +## 3. متى تجاوز الافتراضي؟ + +**التجاوز ضروري حين**: +- الغرض الفعلي للمعاملة يختلف عن الغرض المعتاد للحساب. +- المعاملة تخص مشروعاً أو غرضاً استثنائياً. +- تريد تحليلاً دقيقاً لمعاملة ذات طابع خاص. + +**لا حاجة للتجاوز حين**: +- المعاملة اعتيادية وتطابق الغرض المعتاد للحساب. +- الافتراضي دقيق. + +## 4. التجاوز المتعدد — أبعاد متعددة لمعاملة واحدة + +يمكن لمعاملة واحدة أن تُوسَم بأكثر من بُعد تحليلي واحد: + +مثال: دفعتَ 300 ﷼ كهدية عيد ميلاد لصديق — يمكن توسيمها بـ: +- بُعد "الأسرة والمعالون" (لأنه من عائلتك الممتدة). +- بُعد "الترفيه ونمط الحياة" (لأنها مناسبة اجتماعية). + +الاختيار يعكس كيف تُفكّر في تصنيف هذا النوع من الإنفاق. لا إجابة خاطئة — المهم اتساق نهجك. + +## 5. الإزالة الكاملة — معاملة بلا تصنيف تحليلي + +يمكنك دائماً ترك معاملة بلا أبعاد: + +- المعاملة تُسجَّل وتُؤثّر على الأرصدة المحاسبية بشكل طبيعي. +- في التقارير التحليلية، ستظهر في خانة "غير مُصنَّف". + +بعض المستخدمين يُفضّلون ترك المعاملات الاستثنائية بلا تصنيف — أفضل من توسيمها بتصنيف خاطئ يُعكّر التقارير. + +## 6. مراجعة التوسيم — هل يمكن تعديله لاحقاً؟ + +الأبعاد والتوسيم التحليلي أبسط تعديلاً من الحسابات والأرصدة. لأنها لا تُؤثّر على الأرصدة المحاسبية، التعديل لا يُنشئ قيوداً عكسية. + +يمكنك مراجعة توسيم ماضٍ وتصحيحه. الأثر يظهر فوراً في التقارير التحليلية. + +## 7. استراتيجية التوسيم على المدى البعيد + +التوسيم الجيد يتبنّى مبدأ "الاتساق أهم من الكمال": + +- اختر نهجاً وطبّقه باستمرار — حتى لو لم يكن المثالي. +- راجع نهجك مرة كل ربع سنة وعدّل إن لزم. +- استخدم الأبعاد الافتراضية لتقليل الجهد اليدوي. +- تجاوز الافتراضي بوعي حين تختلف الحال. + +ستة أشهر من التوسيم المتسق تُعطيك صورة أصفى من سنة توسيم متقطع وغير منتظم. diff --git a/platform/resources/docs/04_cost_centers_and_dimensions/03_dimension_propagation.md b/platform/resources/docs/04_cost_centers_and_dimensions/03_dimension_propagation.md new file mode 100644 index 00000000..3141a099 --- /dev/null +++ b/platform/resources/docs/04_cost_centers_and_dimensions/03_dimension_propagation.md @@ -0,0 +1,61 @@ +# انتشار الأبعاد تلقائياً — كيف ينقل النظام التصنيف؟ + +## 1. الانتشار التلقائي — ما يحدث خلف الكواليس + +"انتشار الأبعاد" يُشير لآلية يُكمل فيها النظام جانباً من التصنيف التحليلي دون تدخل مُستخدم إضافي. هذه الآلية تظهر في سياقين رئيسيين: + +**السياق الأول**: السندات المرتبطة بالجسر الآلي. +**السياق الثاني**: السندات الداخلية في التحويل الثلاثي. + +## 2. الجسر الآلي وتوسيم الأبعاد + +تذكّر: حين تُسجّل مصروفاً شخصياً (مثل دفع بقالة)، يُنشئ النظام سندَيْن: +- السند الرئيسي الخارجي (أنت → متجر البقالة). +- السند الداخلي للجسر (حساب نقدي → حساب مصروف الطعام). + +عند توسيم السند الرئيسي بأبعاد تحليلية، هل تحتاج لتوسيم السند الداخلي منفصلاً؟ + +النظام يُعالج هذا بشكل ذكي: السند الداخلي للجسر مُرتبط بالسند الرئيسي. تقارير مراكز التكلفة تعمل على مستوى المجموعة — لا تُكرّر التوسيم على السنديْن. + +## 3. انتشار السياق في التحويل الثلاثي + +في التحويلات الثلاثية (الوساطة)، السندات الثلاثة تحمل "معرف المجموعة" المشترك. هذا المعرف يُتيح: + +- ربط الأبعاد التحليلية بالتحويل كاملاً لا بسند واحد فيه. +- استعراض تقارير التحويل الثلاثي كوحدة تحليلية متكاملة. + +لا تحتاج لتوسيم كل سند من سندات الثلاثي بشكل منفصل. توسيم المجموعة يُغني عن ذلك. + +## 4. قاعدة التوسيم عند التأكيد — لا قبله + +التوسيم التحليلي يُطبَّق على السند في لحظة إنشائه أو تعديله. لكن السند لا يُؤثّر في تقارير مراكز التكلفة إلا بعد التأكيد. + +المسودات غير مرئية في التقارير التحليلية تماماً — مثلما هي غير مرئية في التقارير المحاسبية. + +## 5. التوسيم غير الذري — خطر صغير مُعترَف به + +ثمة نقطة مهمة تتعلق بكيفية حفظ التوسيم: + +حفظ السند وحفظ الارتباط بمراكز التكلفة يحدثان في خطوتين منفصلتين. في حالة نادرة (مثل انقطاع في منتصف العملية)، قد يُحفَظ السند دون توسيمه. + +النتيجة: السند موجود في القيود المحاسبية لكن غير موجود في التقارير التحليلية. تظهر هذه المعاملة في خانة "غير مُصنَّف" في التقارير. + +الحل: مراجعة التوسيم يدوياً من وقت لآخر للتأكد من اكتمال الربط. + +## 6. التوسيم على المعاملات التاريخية — إضافة ما فات + +يمكنك توسيم معاملات قديمة لم تُوسَّم عند التسجيل: + +- النظام يتيح إضافة أبعاد للمعاملات السابقة. +- الأثر يظهر فوراً في التقارير التحليلية. +- لا أثر على الأرصدة المحاسبية. + +هذا مفيد إذا بدأتَ باستخدام مراكز التكلفة بعد فترة من بدء النظام. يمكنك "الرجوع وتصنيف" ما فات لتكتمل صورتك التحليلية. + +## 7. الانتشار لا يُساوي النقل التلقائي للأرصدة + +ملاحظة جوهرية: "انتشار الأبعاد" في هذا السياق يُشير لانتشار **المعلومة التحليلية** لا **الرصيد المحاسبي**. + +لا يوجد "نقل تلقائي" للأرقام بين مراكز التكلفة. مراكز التكلفة لا تملك أرصدة محاسبية تتحرك. هي فقط تجمع المعاملات الموسومة بها وتُجمّع قيمها للتقرير. + +الخلط بين "رصيد الحساب" و"إجمالي مركز التكلفة" يُؤدّي لتوقعات خاطئة. الحساب له رصيد حقيقي يُؤثّر في الميزانية. مركز التكلفة له "إجمالي تحليلي" لا يُؤثّر في الميزانية. diff --git a/platform/resources/docs/04_cost_centers_and_dimensions/04_analysis_and_reporting.md b/platform/resources/docs/04_cost_centers_and_dimensions/04_analysis_and_reporting.md new file mode 100644 index 00000000..bf85d21f --- /dev/null +++ b/platform/resources/docs/04_cost_centers_and_dimensions/04_analysis_and_reporting.md @@ -0,0 +1,71 @@ +# التحليل وإعداد التقارير لمراكز التكلفة + +## 1. ما الذي تُقدّمه تقارير مراكز التكلفة؟ + +تقارير مراكز التكلفة تُجيب عن أسئلة لا تجيب عنها التقارير المحاسبية: + +- "كم أنفقتُ على السيارة هذا العام؟" +- "ما نسبة إنفاقي على التعليم مقابل الترفيه؟" +- "هل مشروعي العقاري يُدرّ عائداً يتجاوز تكاليفه؟" +- "في أي شهر يرتفع إنفاقي على الأسرة؟" + +هذه أسئلة إدارية واعية، لا مجرد أرصدة محاسبية. + +## 2. نوعا التقرير لمراكز التكلفة + +**تقرير الحركة (Activity Report)**: +يُظهر قائمة المعاملات الموسومة بمركز تكلفة محدد خلال فترة. يُفيد للمراجعة التفصيلية والتحقق من صحة التوسيم. + +**تقرير الإجمالي (Summary Report)**: +يُظهر مجموع ما صُرف على مركز تكلفة خلال فترة. يُفيد للمقارنة والتخطيط. + +أكثر الاستخدامات قيمةً تجمع بين النوعين: تبدأ بالإجمالي لتحديد المراكز الأكثر إنفاقاً، ثم تغوص في تفاصيل مركز محدد للفهم العميق. + +## 3. التصفية في تقارير مراكز التكلفة + +يمكن تصفية التقارير التحليلية بـ: + +- **الفترة الزمنية**: أسبوع، شهر، ربع، سنة مالية. +- **نوع المركز**: تكلفة أم ربح. +- **مركز بعينه**: تقرير تفصيلي لمركز واحد. +- **بُعد محدد**: ماذا رصد هذا البُعد داخل مركز التكلفة؟ +- **الحالة**: معاملات مؤكّدة فقط (الأكثر شيوعاً في التقارير). + +## 4. مقارنة الفترات — الفهم عبر الزمن + +أكثر قيمة من تقرير فترة واحدة هو مقارنة الفترات: هذا الشهر مقابل الشهر الماضي، هذا الربع مقابل نفس الربع من العام الماضي. + +هذه المقارنة تُجيب: هل سلوكي المالي يتغير؟ هل ارتفعت نفقة معينة دون سبب؟ + +الشرط للحصول على مقارنات ذات معنى: توسيم منتظم ومتسق على مدى الفترتين المقارنتين. + +## 5. مراكز الربح — قياس العائد مقابل التكلفة + +لمراكز الربح (مثل شقة مؤجَّرة أو مشروع تجاري)، التقرير يُظهر: + +- **الإيرادات الموسومة**: ما دخل من هذا المركز. +- **التكاليف الموسومة**: ما صُرف على هذا المركز. +- **صافي الربح التحليلي**: الفرق. + +هذا "صافي الربح التحليلي" ليس "رصيداً محاسبياً". إنه تجميع تحليلي للمعاملات الموسومة. دقته تعتمد على اكتمال التوسيم. + +## 6. الميزانية كمرشد — الفعلي مقابل المخطط + +إذا ضبطتَ ميزانية لمركز تكلفة، يُظهر التقرير: + +- الميزانية القصوى المُحدَّدة. +- المُنفَق فعلياً حتى الآن. +- النسبة المئوية للاستنزاف. +- ما تبقّى من الميزانية. + +هذا يُجيب على: "هل أنا على المسار الصحيح في الإنفاق على هذا البند؟" + +## 7. تحديد جاهزية التقارير للاعتماد + +قبل اعتماد أي قرار مبني على تقارير مراكز التكلفة، اسأل: + +- **هل التوسيم مكتمل؟** معاملات غير موسومة تُشوّه الصورة. +- **هل الفترة صحيحة؟** بعض النفقات موسمية — طبيعي ارتفاع التكلفة في رمضان أو الإجازات. +- **هل قارنتَ بفترة مماثلة؟** لا تقارن شهر رمضان بشهر عادي. + +التقارير التحليلية أداة تفكير، لا إجابات نهائية. هي تُعطيك البيانات لتُقرّر أنت. diff --git a/platform/resources/docs/04_cost_centers_and_dimensions/_category_.json b/platform/resources/docs/04_cost_centers_and_dimensions/_category_.json new file mode 100644 index 00000000..17587a8f --- /dev/null +++ b/platform/resources/docs/04_cost_centers_and_dimensions/_category_.json @@ -0,0 +1,4 @@ +{ + "label": "مراكز التكلفة والأبعاد", + "position": 4 +} diff --git a/platform/resources/docs/05_accounts_management/00_expense_accounts.md b/platform/resources/docs/05_accounts_management/00_expense_accounts.md new file mode 100644 index 00000000..65ce12ed --- /dev/null +++ b/platform/resources/docs/05_accounts_management/00_expense_accounts.md @@ -0,0 +1,71 @@ +# حسابات المصروفات — بناء خريطة إنفاقك + +## 1. وظيفة حسابات المصروفات + +حسابات المصروفات هي السجل الرسمي لكل ما يصدر عنك من إنفاق. كل ﷼ تُنفقه سيُسجَّل في حساب مصروف مناسب. كمية ونوعية هذه الحسابات تُحدّد مدى تفصيل تقاريرك. + +هناك مستويان من التفصيل المتاحان: + +**مستوى واحد (مُجمَّع)**: حساب واحد "مصروفات شخصية" يجمع كل شيء. سريع في التسجيل، فقير في التحليل. + +**مستويات متعددة (مُفصَّل)**: حسابات لكل فئة رئيسية: مأكل، سكن، نقل، صحة. تحتها ربما فروع أكثر تفصيلاً. أبطأ في الإعداد الأولي، غني في التحليل. + +## 2. هيكل الحسابات الموصى به للمبتدئين + +لمن يبدأ، هذا هيكل معتدل يُوازن بين البساطة والتفصيل: + +``` +مصروفات شخصية (جذر) +├── مصروفات السكن +├── مصروفات الطعام والمشتريات +├── مصروفات النقل +├── مصروفات الصحة +├── مصروفات التعليم +├── مصروفات الأسرة والمعالون +└── مصروفات عامة +``` + +كل حساب يرث من "مصروفات شخصية" طبيعتها (مدين). لا تحتاج تعديل الطبيعة يدوياً. + +## 3. إضافة تفاصيل حين يطلبها الواقع + +ابدأ بسيطاً. إذا شعرتَ بعد أشهر أن "مصروفات السيارة" وحيدة لا تكفيك وتريد التمييز بين "وقود" و"صيانة" و"تأمين": + +- اجعل "مصروفات السيارة" حساباً رئيسياً. +- أضف تحتها "وقود السيارة" و"صيانة السيارة" و"تأمين السيارة" كحسابات فرعية. + +التفصيل يأتي بحسب الحاجة الفعلية، لا التخطيط المسبق المفرط. + +## 4. حسابات الجهات مقابل حسابات التصنيف + +تمييز مهم كثيراً ما يُربك المستخدمين الجدد: + +**حساب الجهة (Counterparty)**: "شركة الكهرباء"، "سوبر ماركت نستو"، "محطة أرامكو". هذا حساب يُمثّل الطرف الخارجي الذي تتعامل معه. + +**حساب التصنيف (Affected Account)**: "مصروفات الطاقة"، "مصروفات الطعام"، "مصروفات النقل". هذا حساب يُمثّل طبيعة المعاملة في سجلك الداخلي. + +كل سند دفع يحتاج الاثنين: الجهة التي دفعتَ لها (counterparty) والتصنيف الذي تُريد تحميل هذا المبلغ عليه (affected account). + +## 5. الحسابات الافتراضية للمصروفات — ما يأتي جاهزاً + +النظام يُنشئ مسبقاً حسابات مصروفات جذرية تُغطي التصنيفات الكبرى. هذه الحسابات الافتراضية محمية من الحذف والأرشفة لأنها المدخل الرئيسي للجسر الآلي. + +يمكنك دائماً إضافة فروع تحتها لزيادة التفصيل. لكن لا تحذف الجذر — النظام يرفض ذلك وله سبب. + +## 6. هل يمكن أرشفة حساب مصروف؟ + +نعم، بشرطَيْن: +- الحساب ليس افتراضياً. +- رصيده صفر (لا معاملات نشطة مرتبطة به). + +إذا أردتَ أرشفة حساب له رصيد غير صفري: سوّ المعاملات المفتوحة أولاً ثم أرشفه. + +## 7. مبدأ التسمية الجيدة للحسابات + +اسم الحساب يظهر في كل قائمة اختيار، كل تقرير، كل كشف حساب. التسمية الجيدة: + +- واضحة ومباشرة: "مصروفات الطعام" أفضل من "مصروفات ن.ع.ي." +- متسقة في النمط: إما كلها بصيغة "مصروفات X" أو كلها بصيغة "X — مصروف" +- لا تحتاج شرحاً: لا اختصارات غامضة + +التسمية الجيدة توفّر عليك ثوانٍ في كل اختيار — تتراكم هذه الثواني عبر مئات المعاملات. diff --git a/platform/resources/docs/05_accounts_management/01_income_sources.md b/platform/resources/docs/05_accounts_management/01_income_sources.md new file mode 100644 index 00000000..779c664e --- /dev/null +++ b/platform/resources/docs/05_accounts_management/01_income_sources.md @@ -0,0 +1,81 @@ +# مصادر الإيرادات — تصنيف الدخل وأنواعه + +## 1. لماذا يُصنَّف مصدر الإيراد؟ + +المال الواحد قد يكون دخلاً من عمل، أو عائداً من استثمار، أو من أصل بُعتَه. هذه الأنواع الثلاثة تختلف في طبيعتها الاقتصادية اختلافاً جوهرياً: + +- الدخل من العمل رهين استمراريتك أنت — يتوقف بتوقف جهدك. +- عائد الاستثمار رهين أصلك — يستمر حتى لو لم تعمل. +- ثمن أصل بعتَه حدث واحد غير متكرر — لا يُعتمد عليه كتدفق مستمر. + +فهم مصدر دخلك يُساعدك في تخطيطك المالي: هل دخلك مستدام؟ هل هو مرهون بك شخصياً أم بأصلك؟ + +## 2. أنواع الإيراد الأربعة + +نظام قيد يُصنّف الإيرادات في أربع فئات: + +**المهنة (كسب)**: +إيراد الجهد والعمل المباشر. الراتب، الأجر اليومي، رسوم الاستشارة، العمل الحر. مشترك: يتطلب مشاركتك الشخصية المستمرة لتحقيقه. + +**الاستثمار (استثمار)**: +عائد رأس المال المُستثمَر. إيجار العقار، توزيعات الأسهم، عائد صندوق استثماري. مشترك: يتطلب رأس مال موجود، لا جهد مستمر. + +**المُلكية (بيع)**: +إيراد نقل ملكية أصل. بيع سيارة، بيع عقار، بيع منتج. مشترك: حدث بيع واحد، ليس تدفقاً دورياً. + +**لا ينتمي لفئة (أخرى)**: +إيرادات خارج الفئات الثلاث. الهبة، الإرث، استرداد مبلغ مدفوع، المكافآت غير المرتبطة بعمل. مشترك: لا نمط متكرر يُعرّفها. + +## 3. كيف يُسجَّل نوع الإيراد؟ + +نوع الإيراد يُضبَط كـ"بيانات وصفية" على حساب الإيراد نفسه — لا على السند. عند إنشاء حساب "راتبي من الشركة X": + +- تُحدّد التصنيف: "مهنة". +- تُحدّد النوع: "إيراد شخصي". +- النوع الوصفي يبقى ملصقاً بالحساب. + +في أي تقرير يُسهم فيه هذا الحساب، تُستطاع تصفيته بحسب نوع الإيراد. + +## 4. الحسابات الفرعية للإيرادات — التفصيل الذي يُنير + +كما في المصروفات، يمكن هيكلة الإيرادات: + +``` +إيرادات شخصية (جذر) +├── إيرادات المهنة +│ ├── الراتب الأساسي +│ └── العمل الحر +├── إيرادات الاستثمار +│ ├── إيجار الشقة +│ └── أرباح صندوق +└── إيرادات أخرى +``` + +هذا التفصيل يُتيح لك معرفة: كم يُشكّل راتبي من إجمالي دخلي؟ هل دخلي من الاستثمار يكفي لتغطية مصاريف أساسية؟ + +## 5. الإيراد والجذر النقدي — الدورة المكتملة + +حين تُسجّل إيراداً (مثل استلام الراتب)، إليك ما يحدث: + +- السند نوعه قبض. +- الطرف الآخر: صاحب العمل. +- الحساب المتأثر: حساب "إيرادات المهنة". +- الجسر الآلي يُضيف إلى رصيد حسابك النقدي الجذري. + +النتيجة: رصيد نقديتك يرتفع، رصيد إيراداتك يرتفع، وكل شيء متوازن. + +## 6. الإيراد لا يعني سيولة فورية دائماً + +تمييز مهم: بعض الإيرادات قد تُسجَّل قبل وصول المال فعلاً. + +مثلاً: أنجزتَ عملاً استشارياً وأرسلتَ فاتورة لعميلك، لكنه لم يدفع بعد. يمكنك تسجيل سند القبض المستحق (مسودة أو بدون تأكيد)، مما يُظهر الذمة في حسابك — "المال الذي يديه لي العميل" — دون أن يرتفع رصيدك النقدي بعد. يرتفع الرصيد النقدي فقط حين يصلك الدفع فعلاً. + +## 7. أثر الاتساق في التصنيف على التخطيط المالي + +بعد سنة من تسجيل الإيرادات بتصنيفاتها الصحيحة، ستستطيع الإجابة على: + +- ما نسبة دخلي من العمل مقابل الاستثمار؟ +- هل أنا مُعتمِد أكثر مما ينبغي على دخل الجهد؟ +- هل دخلي من الاستثمار يكفي تاريخياً لتغطية مصاريف محددة؟ + +هذه أسئلة التخطيط المالي الحقيقي — وإجاباتها في سجلاتك المصنّفة. diff --git a/platform/resources/docs/05_accounts_management/02_investment_assets.md b/platform/resources/docs/05_accounts_management/02_investment_assets.md new file mode 100644 index 00000000..d8668f29 --- /dev/null +++ b/platform/resources/docs/05_accounts_management/02_investment_assets.md @@ -0,0 +1,69 @@ +# الأصول الاستثمارية — متابعة رأس المال المُنتِج + +## 1. ما الذي يُعدّ أصلاً استثمارياً في نظام قيد؟ + +الأصل الاستثماري هو أي ملكية تعمل من أجلك — تُولّد دخلاً أو تنمو في قيمتها مع الزمن. في سياق نظام قيد: + +- عقار مؤجَّر → أصل ثابت مُولِّد للربح. +- محفظة أسهم → أصل ثابت مُولِّد للربح. +- معدة تُؤجَّر للآخرين → أصل ثابت مُولِّد للربح. + +في المقابل: +- سيارة تستخدمها للنقل الشخصي → أصل ثابت قابل للإهلاك (ينقص في القيمة). +- حاسوب للعمل الشخصي → أصل ثابت قابل للإهلاك. + +## 2. الفرق بين التصنيفَيْن للأصول الثابتة + +الفرق ليس مجرد تسمية — له أثر في تفسير التقارير: + +**الأصول المُولِّدة للربح**: يُتوقَّع أن يرتفع دخلك بسببها من خلال الاستخدام. رصيدها في الميزانية يُمثّل قيمتها الاستثمارية. + +**الأصول القابلة للإهلاك**: تتناقص قيمتها مع الاستخدام. التقييم الصادق لوضعك المالي يتطلب أخذ تناقص قيمتها بعين الاعتبار — وإن كان نظام قيد لا يُحسب الإهلاك تلقائياً (هذا تقييم يطلبه المحاسبون المحترفون). + +## 3. تسجيل اقتناء أصل استثماري + +حين تشتري عقاراً بـ500,000 ﷼: + +**السند**: دفع (أنت تدفع). +**الطرف الآخر**: البائع. +**الحساب المتأثر**: حساب "عقاري — المدينة" أو ما تختاره من اسم تحت تصنيف "أصول ثابتة مُولِّدة للربح". + +النتيجة: رصيدك النقدي ينقص بـ500,000، رصيد حساب العقار يرتفع بـ500,000. صافي أصولك لم يتغير — تحوّلت من نقد إلى عقار. + +## 4. تسجيل إيراد الأصل الاستثماري + +حين يدفع المستأجر الإيجار شهرياً: + +**السند**: قبض. +**الطرف الآخر**: حساب المستأجر. +**الحساب المتأثر**: حساب "إيرادات إيجار" تحت "إيرادات الاستثمار". + +النتيجة: رصيدك النقدي يرتفع، إيراداتك الاستثمارية ترتفع. الأصل ذاته (العقار) لم يتغير رصيده. + +## 5. تسجيل بيع أصل استثماري + +حين تبيع العقار بـ600,000 ﷼ (أعلى من ثمن الشراء): + +**الخطوة الأولى**: سند قبض بـ600,000 ﷼. الطرف الآخر المشتري. الحساب المتأثر: النقدية. +**الخطوة الثانية**: سند دفع بـ500,000 ﷼ (قيمة العقار في حساباتك). الطرف الآخر: — الحساب المتأثر: حساب العقار (لإغلاقه). + +الفرق 100,000 ﷼: هذا ربح رأس المال. كيف يُسجَّل؟ يحتاج سنداً إضافياً كإيراد رأسمالي. أو استشر محاسباً لأن هذه الحالة تتطلب دقة. + +## 6. الأصول والضمانات — الرابط بالسندات + +يُتيح النظام ربط "ضمان" بأي سند يُمثّل دَيناً مضموناً. مثلاً: "أقرضتُ X مبلغاً ورهن سيارته كضمان". + +الضمان حالاته أربع: نشط، مُفرَج عنه (الدين سُدّد)، منتهي (انتهت فترة الضمان)، مُصادَر (الدين لم يُسدَّد وصُودر الضمان). + +هذا يُمثّل منطق الإقراض المضمون — بسيط في الظاهر لكن دقيق في التوثيق. + +## 7. متى تحتاج إلى محاسب مختص؟ + +نظام قيد أداة قوية للتوثيق والمتابعة. لكن بعض الحالات تستدعي مختصاً: + +- الإهلاك السنوي للأصول وأثره على القيمة الدفترية. +- الضرائب على العوائد الاستثمارية (إن وُجدت). +- المعاملات بعملات متعددة وأثر التقييم الصرفي. +- الشراكات وتوزيع الأرباح. + +النظام يُطبّق محاسبة مزدوجة حقيقية. والمحاسب المختص يُكملها بتفسير الأرقام وتطبيق المعايير المهنية. diff --git a/platform/resources/docs/05_accounts_management/03_parties_and_counterparties.md b/platform/resources/docs/05_accounts_management/03_parties_and_counterparties.md new file mode 100644 index 00000000..e3aa1f3c --- /dev/null +++ b/platform/resources/docs/05_accounts_management/03_parties_and_counterparties.md @@ -0,0 +1,71 @@ +# الأطراف والجهات — بناء شبكة علاقاتك المالية + +## 1. ما هو "الطرف المالي" في نظام قيد؟ + +كل معاملة مالية يجب أن تكون بين طرفَيْن — أنت والطرف الآخر. "الطرف الآخر" هو أي شخص أو جهة تتعامل معها مالياً: + +- صاحب العمل الذي يدفع راتبك. +- المتاجر والجهات التي تشتري منها. +- الأشخاص الذين تُقرضهم أو يُقرضونك. +- الشركاء في أي نشاط مشترك. + +## 2. الطرف الداخلي مقابل الطرف الخارجي + +في قيد، الطرف المالي يوجد كـ"حساب" في نظامك. لكن ثمة فارق مهم: + +**الطرف الخارجي الخالص** (مثل متجر بقالة): حساب في نظامك يُمثّله، لكن هذا الطرف لا يستخدم نظام قيد. المعاملات معه تُسجَّل من طرفك أنت فقط. + +**الطرف المشترك** (شخص يستخدم قيد أيضاً): يمكن إرسال السندات بينكما رقمياً، يؤكّد كلٌّ منكما من طرفه، ويُنشئ توقيعاً رقمياً مشتركاً. + +هذا الفارق حاسم: المعاملات مع الطرف الخارجي الخالص موثّقة من طرفك فقط. المعاملات مع طرف قيد مشترك موثّقة ثنائياً ومُوقَّعة رقمياً — مما يُعطيها حجية أعلى. + +## 3. كيف تُضيف طرفاً جديداً؟ + +الطرف الجديد يُضاف كـ"حساب" بتصنيف مناسب: + +- شخص ستُقرضه أو يُقرضك: تصنيف "ذمم دائنة (عليك)" أو "ذمم مدينة (لك)". +- متجر أو جهة تُدفع لها مصروفات: يمكن أن يكون حساباً تحت "ذمم مدينة (لك)" أو مباشرة حساب طرف خارجي. +- صاحب عمل: حساب تحت "ذمم مدينة (لك)" (هو يدين لك الراتب). +- مستأجر: حساب تحت "ذمم دائنة (عليك)" (يدين لك الإيجار). + +التصنيف الصحيح يُحدّد كيف تظهر الذمة في ميزانيتك. + +## 4. سجل الكشف مع طرف — أهم ميزة في إدارة الأطراف + +لكل طرف في نظامك: يمكن استعراض "كشف الحساب" الكامل معه. هذا الكشف يُظهر: + +- كل المعاملات بينكما زمنياً. +- الرصيد التراكمي بعد كل معاملة. +- حالة أي سند معلق أو مُسوَّى. + +هذا الكشف هو مصدرك للإجابة على: "كم يديني هذا الشخص الآن؟" أو "ما إجمالي ما دفعتُ لهذه الشركة خلال السنة؟" + +## 5. تفاصيل الطرف المالي — المعلومات التكميلية + +كل طرف يمكن إضافة معلومات تكميلية عليه: + +- اسم واضح ووصف. +- رقم تواصل أو معلومات اتصال. +- مفتاح التشفير العام (للمستخدمين الآخرين على قيد) لإتاحة السندات الرقمية المُوقَّعة. +{/*- تاريخ صلاحية المفتاح وسجل مفاتيحه القديمة.*/} + +سجل المفاتيح القديمة مهم: يُتيح التحقق من توقيعات سندات أُبرمت بمفتاح قديم قبل آخر تحديث للطرف الآخر لمفتاحه. + +## 6. الطرف المُعلَّق أو المُؤرشَف + +حين تنتهي علاقتك المالية مع طرف ما: + +- **التعليق**: الطرف لا يظهر في قوائم الاختيار النشطة. يمكن إعادة تفعيله. +- **الأرشفة**: يُحال للتقاعد الدائم. تاريخه محفوظ، تقاريره قابلة للاستعراض، لكنه لا يُتاح لمعاملات جديدة. + +**لا يمكن حذف طرف له تاريخ مالي** — القيود في دفتر الأستاذ مرتبطة بهويته. حذفه سيُكسر هذه الروابط. الأرشفة هي الحل الدائم الصحيح. + +## 7. إدارة الأطراف كاستثمار في وضوح السجل + +الوقت المُنفَق في تسمية الأطراف بشكل واضح وتصنيفهم بشكل دقيق يعود عليك بقيمة كبيرة: + +- كشوفات الحساب ذات معنى فوري. +- التقارير تُميّز بين الأطراف المختلفة. +- الفحص المستقبلي للسجل سهل وواضح. + +حساب اسمه "A" لن يخبرك شيئاً بعد سنة. حساب اسمه "أحمد الشهري — زميل قديم" سيعطيك السياق الكامل. diff --git a/platform/resources/docs/05_accounts_management/04_account_activation_and_suspension.md b/platform/resources/docs/05_accounts_management/04_account_activation_and_suspension.md new file mode 100644 index 00000000..7937e0ae --- /dev/null +++ b/platform/resources/docs/05_accounts_management/04_account_activation_and_suspension.md @@ -0,0 +1,71 @@ +# تفعيل الحسابات وتعليقها — إدارة دورة الحياة + +## 1. الحالات الأربع لأي حساب + +كل حساب في نظام قيد يمر بواحدة من أربع حالات: + +**نشط (active)**: الحالة الطبيعية. الحساب مرئي، قابل للاختيار في السندات، يظهر في التقارير. + +**معطَّل (inactive)**: الحساب موجود لكن مُعلَّق مؤقتاً. لا يظهر في قوائم الاختيار للسندات الجديدة. تاريخه محفوظ. يمكن إعادة تفعيله. + +**مُؤرشَف (archived)**: الحساب مُحال للتقاعد الدائم. لا يُستخدم بعدها. تاريخه محفوظ وقابل للاستعراض في التقارير. + +**محذوف (deleted)**: حالة استثنائية تتطلب شروطاً صارمة. راجع القسم 5. + +## 2. متى تُعطّل حساباً؟ + +التعطيل مناسب حين: +- العلاقة مع طرف ما توقفت مؤقتاً لكن قد تستأنف. +- حساب مصروف لأنشطة موسمية (مثل حساب المصروفات المدرسية — يُعطَّل في الإجازة). +- تريد تنظيف قائمة الاختيار دون فقدان التاريخ. + +التعطيل لا يشترط رصيداً صفرياً. + +## 3. متى تُؤرشف حساباً؟ + +الأرشفة مناسبة حين: +- علاقة مالية انتهت نهائياً (طرف لن تتعامل معه مجدداً). +- نشاط أُغلق تماماً. +- مصروف خاص بمرحلة انتهت. + +**الشرط**: رصيد الحساب يجب أن يكون صفراً قبل الأرشفة. رصيد غير صفري يعني وجود معاملات مفتوحة — وهذه يجب تسويتها أولاً. + +## 4. لماذا الرصيد الصفري شرط للأرشفة؟ + +حساب له رصيد موجب في سجلاتك يُعني: إما أن لك مالاً عند طرف ما، أو أن لطرف ما مالاً عندك. أرشفة مثل هذا الحساب تُوحي بأن الأمر حُسم — وهو لم يُحسم. + +التصحيح: +- إذا كان الرصيد ديناً لك: حصّل الدين، سجّل سند القبض، ثم أرشف. +- إذا كان رصيداً تدين به: سدّد الالتزام، سجّل سند الدفع، ثم أرشف. +- إذا كان رصيداً خاطئاً: أنشئ سند تعديل لمعادلته، ثم أرشف. + +## 5. حالة الحذف — الشروط الثلاثة الصارمة + +الحذف ممكن فقط إذا توافرت **الشروط الثلاثة معاً**: +1. الحساب ليس "افتراضياً" (ليس من الحسابات المحمية). +2. رصيده صفر. +3. لا أبناء له (لا حسابات فرعية تندرج تحته). + +غياب أي شرط واحد يجعل الحذف مستحيلاً، والنظام يرفضه بوضوح. + +**ملاحظة**: الحذف لا يُزيل الحساب من التاريخ المحاسبي — القيود المرتبطة به تبقى. يُزال فقط كـ"كيان نشط". لهذا الحذف نادر الاستخدام. + +## 6. الحسابات الافتراضية — محمية من جميع أشكال الإنهاء + +بعض الحسابات خُصّصت برمجياً بصفة "افتراضي". هذه حصانتها مطلقة: +- لا تعطيل. +- لا أرشفة. +- لا حذف. +- لا نقل لأب آخر (إعادة تصنيف). + +إذا لاحظتَ خيارات مفقودة لحساب بعينه، الأرجح أنه حساب افتراضي. النظام يُخفي الخيارات غير الممكنة تجنباً للإرباك. + +## 7. خلاصة عملية — جدول القرار + +| الحالة | الخيار المناسب | الشرط | +|--------|---------------|-------| +| متوقف مؤقتاً | تعطيل | لا شروط | +| منتهٍ نهائياً + رصيده صفر | أرشفة | رصيد = صفر | +| منتهٍ + له رصيد | سوّ الرصيد أولاً ثم أرشف | — | +| افتراضي | لا إجراء متاح | — | +| يستحق الحذف | أندر من أرشفة | الشروط الثلاثة | diff --git a/platform/resources/docs/05_accounts_management/05_debts_and_receivables.md b/platform/resources/docs/05_accounts_management/05_debts_and_receivables.md new file mode 100644 index 00000000..eccde924 --- /dev/null +++ b/platform/resources/docs/05_accounts_management/05_debts_and_receivables.md @@ -0,0 +1,79 @@ +# الذمم المالية والديون — متابعة ما لك وما عليك + +## 1. ما هي الذمة المالية في قيد؟ + +الذمة المالية هي التزام قائم بين طرفَيْن لم يُسوَّ بعد. نوعان: + +**ذمة لك (ذمم دائنة (عليك))**: شخص ما يديك مالاً. مثل: قرضتَ صديقاً، أو باعتَ خدمة ولم تستلم ثمنها بعد. + +**ذمة عليك (ذمم مدينة (لك))**: أنت تدين لشخص ما بمال. مثل: اقترضتَ مبلغاً، أو أُعطيتَ سلفة. + +## 2. كيف تُسجَّل الذمة في النظام؟ + +الذمة تُسجَّل بطريقتين: + +**الطريقة الأولى — عند قبض أو دفع فعلي**: حين تُقرض شخصاً نقداً، تُنشئ سند دفع. الحساب المتأثر هو صندوقك النقدي، والطرف الآخر هو حساب الشخص (المُقرَض). رصيد حساب المُقرَض يرتفع في خانة "ذمم دائنة (عليك)" — أي يديك. + +**الطريقة الثانية — تسجيل ذمة بدون قبض/دفع فعلي**: إذا اتفقتَ على دين أو حق لك بدون تحريك نقدي فعلي، يمكن تسجيل قيد مباشر في دفتر الأستاذ. هذا أقل شيوعاً لكنه ممكن في حالات كالأجر المستحق غير المدفوع. + +## 3. متابعة الذمم — الحسابات كسجل حي + +في هذا النظام، كل شخص تتعامل معه مالياً يُمثَّل بـ"حساب". رصيد هذا الحساب يُقرأ على النحو: + +| طبيعة الحساب | رصيد موجب يعني | +|-------------|---------------| +| ذمم دائنة (عليك) (receivable) | هذا الطرف يديك | +| ذمم مدينة (لك) (payable) | أنت تدين لهذا الطرف | + +استعراض رصيد حساب شخص محدد يُجيب فوراً: "كم يديني الآن؟" أو "كم أدين له؟" + +## 4. حالات الذمة — الضمان (الكفالة) + +النظام يُتيح ربط "ضمان" بالذمة حين يتطلب الاتفاق كفالة: + +- **نشط**: الدين قائم والضمان مُعلَّق. +- **مُفرَج عنه**: الدين سُدّد والضمان حُرِّر. +- **منتهٍ**: انتهت فترة الضمان بحكم الاتفاق. +- **مُصادَر**: الدين لم يُسدَّد وتم تنفيذ الضمان. + +هذه الحالات مُطبَّقة في النظام لتوثيق المنظومة الكاملة للإقراض المضمون. + +## 5. تسوية الذمة — إغلاق الالتزام + +حين يُسدَّد الدين: + +- تُنشئ سند القبض (إذا كنت الدائن واستلمتَ). +- الطرف الآخر: المدين (الذي كان يدين لك). +- الحساب المتأثر: صندوقك النقدي. + +النتيجة: رصيد حساب المدين ينخفض — الذمة تتناقص بقدر ما دُفع. + +## 6. الذمم الجزئية — الدفع على أقساط + +إذا سدّد المدين على أقساط: + +- كل قسط سند قبض منفصل. +- رصيد حساب المدين ينخفض بعد كل قسط. +- الذمة المتبقية واضحة دائماً = الرصيد الحالي لحساب المدين. + +لا تحتاج تتبع القسط يدوياً — الرصيد التراكمي يُخبرك تلقائياً ما تبقى. + +## 7. الذمم وتقارير الميزانية + +في الميزانية العمومية: + +- الذمم المدينة (ما يدينك به الآخرون) تظهر في **قسم الأصول** — هي مال تستحقه. +- الذمم الدائنة (ما تدين به للآخرين) تظهر في **قسم الالتزامات** — هي التزام عليك. + +صافي الفرق بينهما جزء من حساب ثروتك الصافية الفعلية. + +## 8. الذمة القديمة المنسية — كيف تتعامل معها؟ + +إذا اكتشفتَ ذمةً قديمة في سجلاتك لم تُسوَّ: + +1. تحقق من كشف الحساب مع الطرف — هل هناك سدادات لم تُسجَّل؟ +2. إذا صحّت الذمة ولم تُسدَّد: أبقها مسجّلة وتابع. +3. إذا كانت الذمة قد سُدّدت فعلاً لكن لم تُسجَّل: أنشئ سند القبض بتاريخ السداد الفعلي. +4. إذا تنازلتَ عن الذمة: أنشئ قيد تسوية بالتنازل (هبة أو إسقاط). + +لا تتركها معلّقة — الذمة المعلّقة تُشوّه صورة ثروتك الحقيقية. diff --git a/platform/resources/docs/05_accounts_management/_category_.json b/platform/resources/docs/05_accounts_management/_category_.json new file mode 100644 index 00000000..93084e99 --- /dev/null +++ b/platform/resources/docs/05_accounts_management/_category_.json @@ -0,0 +1,4 @@ +{ + "label": "إدارة الحسابات", + "position": 5 +} diff --git a/platform/resources/docs/06_transfers_system/00_transfer_philosophy.md b/platform/resources/docs/06_transfers_system/00_transfer_philosophy.md new file mode 100644 index 00000000..c9833557 --- /dev/null +++ b/platform/resources/docs/06_transfers_system/00_transfer_philosophy.md @@ -0,0 +1,76 @@ +# فلسفة التحويلات — الوسيط بين الاقتصاد الرسمي والطبيعي + +## 1. الواقع الذي يُعالجه النظام + +في كثير من المجتمعات، التحويلات المالية بين الناس لا تمر دائماً عبر البنوك والقنوات الرسمية. الشبكات الاجتماعية تحل محل المؤسسات: + +- خالد في الرياض يُريد إرسال مال لعائلته في القاهرة، ومحمد صاحبه لديه شريك هناك. +- أب يريد إرسال مصروف لابنه الدارس خارج البلاد، وصديق الأب صاحب شركة صرافة. +- رجال أعمال يُؤدّون دور حلقة الوصل المالية بين عملاء في مناطق مختلفة. + +هذه شبكات التحويل الاجتماعية موجودة في كل الحضارات منذ قرون — السفتجة في التراث العربي الإسلامي، والهوندي في جنوب آسيا، والفي في أفريقيا. نظام قيد لا يُنشئ هذه الشبكات — هو يُوفّر أداة توثيق دقيقة لها. + +## 2. ما يُوثّقه النظام وما لا يُوثّقه + +**يُوثّقه النظام**: +- مَن استلم ماذا ومن مَن ومتى. +- مَن دفع ماذا لمَن ومتى. +- ما الرسوم المتفق عليها. +- هل اكتمل التحويل أم لا. +- من وقّع الاستلام. + +**لا يُوثّقه النظام**: +- الشرعية القانونية للتحويل. +- التزامات العملة في الدول المختلفة. +- الأطر التنظيمية للصرافة. + +النظام أداة توثيق للاقتصاد الاجتماعي، لا مؤسسة مالية مُرخَّصة. + +## 3. لماذا يُشبه النظام مراسلة البنوك؟ + +التحويل الثلاثي في قيد يشترك هيكلياً مع نموذج المراسلة المصرفية (correspondent banking): + +| في المراسلة المصرفية | في قيد الثلاثي | +|---------------------|---------------| +| بنك المُرسِل | الطرف A (المصدر) | +| البنك المراسل | الوسيط C | +| بنك المستلِم | الطرف B (الوجهة) | +| رسالة SWIFT | سند القبض + سند الدفع | +| تاريخ القيمة | تاريخ التحويل | +| عمولة البنك | رسوم السند الثالث | + +الفارق الجوهري: قيد يعمل على المستوى الشخصي الاجتماعي. لا ترخيص مصرفي. لا اشتراطات KYC/AML. لا تنظيم مركزي. هو يُسجّل الاقتصاد الاجتماعي بدقة، والمستخدم مسؤول عن الامتثال القانوني في نطاقه. + +## 4. الضمانات التي يُقدّمها النظام للوسيط + +إذا كنت وسيطاً، النظام يحميك بثلاث آليات: + +**الآلية الأولى — القفل الشرطي**: لا يمكنك تأكيد سند الدفع للطرف الثاني قبل تأكيد سند الاستلام من الطرف الأول. هذا يضمن عدم "الدفع قبل الاستلام" — وهو الموقف الأخطر على الوسيط. + +**الآلية الثانية — التوقيع الرقمي**: كل تأكيد استلام من الطرف الأول يُنشئ توقيعاً رقمياً لا يُنكَر. إذا نكر لاحقاً استلامه، التوقيع دليل قاطع. + +**الآلية الثالثة — الشفافية الكاملة**: كل طرف يرى الصورة الكاملة للتحويل — المرسِل يعرف المستلِم، والمستلِم يعرف المرسِل. لا يستطيع الوسيط إخفاء أي طرف اتصاليّ عن الآخر. يُطبَّق ذلك عبر حقل `linkedPartyId` المُخزَّن في كل سند. + +**الآلية الرابعة — عزل الحسابات الشخصية**: قيود التحويل الثلاثي تُسجَّل في صندوق الوسيط النقدي حصراً. لا تُغيّر رصيد أي حساب شخصي قائم بين الوسيط والمُرسِل أو بينه والمُستقبِل. إذا كان للوسيط رصيد شخصي قديم مع أي من الطرفَيْن، هذا الرصيد يبقى منعزلاً ومصوناً تماماً. + +← تفصيل هذه الآلية: [عزل القيود المحاسبية في التحويل الثلاثي](./05_accounting_isolation.md) + +## 5. فلسفة "المسؤولية المحلية" + +النظام يُجسّد مبدأ: **كل طرف مسؤول عن ما يُؤكّده**. + +حين تُؤكّد استلام مال: أنت تُقرّ باستلامه. +حين تُؤكّد إرسال مال: أنت تُقرّ بإرساله. +التوقيع الرقمي يُجعل هذا الإقرار غير قابل للإنكار لاحقاً. + +هذه المسؤولية المحلية — كل طرف يُوقّع فقط على ما يتعلق به — هي ما يجعل الشبكة اللامركزية ممكنة. لا حاجة لطرف ثالث موثوق يُشهد على كل تحويل. + +## 6. ما يخرج عن نطاق الوساطة في قيد + +هناك حالات لا تُعالجها وساطة قيد: + +- تحويل بعملات مختلفة بين الطرفَيْن (يتطلب حساباً منفصلاً للتحويل الصرفي). +- تحويلات متعددة المراحل (وسيط يُرسل لوسيط آخر) — النظام يُعالج طبقة وساطة واحدة. +- ضمانات تعاقدية خارج النظام (الالتزامات القانونية خارج نطاق السند الرقمي). + +لمن يتعامل بهذه الحالات المعقدة، النظام يُوثّق. الإطار القانوني والتعاقدي يتعامل معه المستخدم. diff --git a/platform/resources/docs/06_transfers_system/01_swift_like_model.md b/platform/resources/docs/06_transfers_system/01_swift_like_model.md new file mode 100644 index 00000000..2000ad68 --- /dev/null +++ b/platform/resources/docs/06_transfers_system/01_swift_like_model.md @@ -0,0 +1,61 @@ +# النموذج المماثل لـ SWIFT — بنية مراسلة الأموال + +## 1. ما هو SWIFT ولماذا نستعير نموذجه؟ + +SWIFT هو نظام الرسائل المالية بين البنوك عالمياً. حين يُرسل بنك في دبي مالاً لبنك في لندن، يستخدمان رسائل SWIFT لتنسيق التحويل عبر بنك وسيط (مراسل). + +هذا النموذج ليس اختراعاً حديثاً — هو تطور تقني لنمط اقتصادي أقدم بكثير: الوساطة في نقل المال عبر المسافات والأنظمة المختلفة. + +نظام قيد يُعيد بناء هذا النمط على المستوى الشخصي. لا تراخيص مصرفية، لا رقابة مركزية — لكن نفس البنية الهيكلية في التسجيل والتوثيق. + +## 2. مقارنة هيكلية بين SWIFT وقيد + +| جانب | SWIFT المصرفي قيد (qayd) | الشخصي | +|------|--------------|------------| +| الأطراف | M بنك + C بنك مراسل + N بنك | A شخص + C وسيط + B شخص | +| الوثيقة | رسالة MT103 | سند القبض + سند الدفع | +| الضمان | التنظيم المصرفي | القفل الشرطي البرمجي | +| التسوية | Clearing house مركزي | تأكيد مزدوج رقمي | +| العمولة | رسوم مقتطعة آلياً | سند رسوم منفصل | +| الإلغاء | محدود وصعب بعد التنفيد | ممكن قبل القبول الثنائي | + +## 3. سند القبض — رسالة MT103 الشخصية + +في SWIFT، رسالة MT103 تُوثّق: أرسلنا مبلغ X من الحساب Y للحساب Z في تاريخ T. + +في قيد، سند القبض يُوثّق: استلمتُ مبلغ X من المرسِل A، وسيُسلَّم للمستفيد B. + +الفارق: سند قيد يُوقَّع بتوقيع رقمي من المستلِم. رسالة SWIFT لا تحتاج توقيع المستلِم للحركة (البنك ينفّذ أوتوماتيكياً). في قيد، التأكيد إنساني وإرادي. + +## 4. حساب المقاصة — التحويل بحسابات عبور + +في SWIFT، البنوك تستخدم حسابات Nostro/Vostro كحسابات عبور مؤقتة. المال "يعبر" هذه الحسابات خلال التسوية. + +في قيد، يوجد تصنيف حساب خاص: "مقاصة الحوالات". هذا هو حساب العبور للوسيط خلال التحويل. حين يستلم الوسيط من A يرتفع الرصيد، وحين يدفع لـB ينخفض. في نهاية التحويل المكتمل يعود رصيده لما كان. + +هذا يُتيح للوسيط تتبع "ما في الطريق": كل تحويل لم يكتمل بعد يُمثَّل برصيد قائم في حساب المقاصة. + +## 5. الفرق الجوهري: الاختيارية مقابل الإلزامية + +SWIFT يُطبَّق في بيئة مُلزِمة: البنوك ملزمة بإتمام التحويل بتاريخ القيمة المتفق عليه وفق الاتفاقيات المصرفية والنظام التنظيمي. + +قيد يعمل في بيئة اختيارية: لا ضامن خارجي، لا إلزام. الضمانة الوحيدة هي الثقة الاجتماعية بين الأطراف + القفل البرمجي + التوقيع الرقمي. + +لهذا السبب، النظام لا يُبدّل الثقة الاجتماعية — بل يُوثّق ويُقوّي الثقة القائمة مسبقاً. + +## 6. تاريخ القيمة — متى يُعدّ التحويل مكتملاً؟ + +في SWIFT، تاريخ القيمة هو اليوم الذي يصبح فيه المال متاحاً للمستفيد. + +في قيد، التحويل يُعدّ "مكتملاً" حين: +1. يُؤكَّد سند القبض من الوسيط (المال وصل الوسيط). +2. يُرفَع القفل عن سند الدفع. +3. يُؤكَّد سند الدفع ويُقبله المستفيد. + +الخطوة الثالثة هي "تاريخ القيمة" الفعلي من منظور النسب المالي. + +## 7. من يجب أن يقرأ هذا الملف؟ + +هذا الملف مُخصَّص لمن يعمل وسيطاً في شبكات تحويل، أو لمن لديه فضول معرفي حول لماذا يُصمَّم التحويل الثلاثي بهذه الطريقة. + +للمستخدم العادي الذي يُحوّل أحياناً بين أصدقائه: يكفيه فهم "آلية القفل الشرطي" والتأكد من إتمام الخطوتين بالترتيب الصحيح. diff --git a/platform/resources/docs/06_transfers_system/02_mediation_vs_presentation.md b/platform/resources/docs/06_transfers_system/02_mediation_vs_presentation.md new file mode 100644 index 00000000..f6ee7dca --- /dev/null +++ b/platform/resources/docs/06_transfers_system/02_mediation_vs_presentation.md @@ -0,0 +1,78 @@ +# الوساطة مقابل التقديم المباشر + +## 1. سؤال التمييز الجوهري + +قبل إنشاء أي تحويل، اسأل نفسك سؤالاً واحداً: + +**"هل أنا أُحوّل من مالي الخاص؟ أم أنا أُحوّل نيابةً عن شخص آخر من ماله؟"** + +الإجابة تُحدّد ما إذا كنت تحتاج "سند دفع بسيط" أو "تحويل ثلاثي". + +## 2. التقديم المباشر — السيناريو الأبسط + +أنت تُحوّل من مالك الخاص لشخص آخر. أمثلة: + +- تُرسل راتباً لموظف. +- تُرسل مالاً لأحد أبنائك. +- تُسدّد ديناً لشخص ما. +- ترسل هدية مالية. + +**الشكل الصحيح**: سند دفع بسيط. +- الطرف الآخر: المستلِم. +- الحساب المتأثر: حسابك النقدي. + +لا تحميل إضافي. لا تحويل ثلاثي. لا قفل شرطي. + +## 3. الوساطة — السيناريو الأعقد + +أنت لا تُحوّل من مالك — بل تتلقى من A وتُوصّل لـB نيابةً عن A. أمثلة: + +- أحد يودع عندك مالاً ليُسلَّم لعائلته في مكان بعيد. +- أنت تُجري التحويل لكن المال سيُفرز لطرف ثالث لا يتعامل مع الطرف الأول. +- أنت صاحب شركة صرافة وتُنفّذ طلب إرسال من عميل لمستفيد. + +**الشكل الصحيح**: تحويل ثلاثي. +- سند قبض (من A إليك) + سند دفع مشروط (منك لـB). + +## 4. ماذا يحدث عند اختيار الشكل الخاطئ؟ + +**استخدام سند بسيط بدل الثلاثي**: +- لا قفل شرطي → يمكنك "الدفع قبل الاستلام" بسهولة. +- لا ارتباط بين السندَيْن → لو نكر A الإرسال، ليس عندك سوى سند ادعاء منفصل. +- لا شفافية للأطراف → B لا يعرف أن المال من A أصلاً. + +**استخدام الثلاثي بدل البسيط**: +- تعقيد غير ضروري. +- أنت ستكون "وسيطاً" في معاملة أنت في الحقيقة طرفها المباشر. +- قد يُربك الطرف الآخر. + +## 5. حالات الحدود — كيف تُقرّر؟ + +**الحالة**: دُفعت لك أموال من شخص Y "لتتصرف بها كيفما تشاء ثم ترد الناتج". + +مالياً، هذا قرض من Y لك. ليس وساطة. السند الصحيح: قبض من Y (قرض دخل لحسابك). إذا وزّعتَه لاحقاً، فسندات دفع منفصلة. + +**الحالة**: أنت تدفع نيابةً عن Z من مالك أنت، وZ سيردّ لك لاحقاً. + +هذا دفع من مالك → ذمة على Z. السند الصحيح: سند دفع مع تسجيل ذمة Z. ليس وساطة. + +**الوساطة الحقيقية**: المال يدخل حسابك من المرسِل خصيصاً لتحويله للمستلِم. أنت لا تملك هذا المال — أنت قناة عبور. + +## 6. الأثر المحاسبي — الوساطة لا تُلوّث حساباتك الشخصية + +هذه نقطة جوهرية كثيراً ما تُثير الاستفسار: + +**في الوساطة الحقيقية**: قيود التحويل الثلاثي تُسجَّل في صندوقك النقدي الوسيط — لا في حساباتك الشخصية مع A أو B. إذا كان لديك رصيد شخصي مع A من تعاملات سابقة، هذا الرصيد يبقى كما هو تماماً بعد الوساطة. + +**في التقديم**: أنت تُقرض فعلياً. ينشأ قيد يرفع رصيد حساب A لديك — "A أصبح يديني المبلغ". هذا أثر شخصي حقيقي يُغيّر علاقتك المالية معه. + +← راجع [عزل القيود المحاسبية في التحويل الثلاثي](./05_accounting_isolation.md) لفهم هذا المبدأ بعمق. + +## 7. التوثيق الذي يحميك في كلتا الحالتين + +سواء كنت في موقف مباشر أو وساطة: +- وثّق كل شيء بسند معنوي. +- اطلب التأكيد من الطرف الآخر. +- لا تعتمد على اتفاقات شفهية لمعاملات مالية ذات قيمة. + +التوثيق الرقمي الموقَّع في قيد هو الحجة التي لا تنكسر. diff --git a/platform/resources/docs/06_transfers_system/03_transfer_fees.md b/platform/resources/docs/06_transfers_system/03_transfer_fees.md new file mode 100644 index 00000000..3cc706e1 --- /dev/null +++ b/platform/resources/docs/06_transfers_system/03_transfer_fees.md @@ -0,0 +1,58 @@ +# رسوم التحويل — توثيق أجر الوساطة + +## 1. هل أجر الوساطة مشروع؟ + +نعم، توثيقه هو الاعتراف بأن الوساطة لها قيمة. الوسيط يبذل جهداً وربما يتحمل مخاطرة في المسافة الزمنية بين استلام المال وإرساله. أجر الوساطة تعويض عادل لهذا الجهد والمخاطرة. + +نظام قيد يُتيح توثيق هذا الأجر بشكل رسمي وشفاف. + +## 2. كيف تُحدَّد الرسوم في التحويل الثلاثي؟ + +عند إنشاء التحويل الثلاثي، يُقدَّم لك حقل اختياري لإدخال "رسوم الوساطة": + +- إذا تركتَه صفراً → لا يُنشأ سند رسوم. تحويل مجاني. +- إذا أدخلتَ مبلغاً → النظام يُنشئ تلقائياً سنداً ثالثاً لتسجيل الرسوم. + +## 3. ماذا يُنشئ سند الرسوم تحديداً؟ + +سند الرسوم هو "قبض" من المرسِل إليك: + +- **نوعه**: قبض. +- **الطرف الآخر**: المرسِل A (من يدفع الرسوم). +- **الحساب المتأثر**: حساب إيرادات الرسوم (أو تصنيف رسوم الحوالات في النظام). +- **يرتبط بنفس مجموعة التحويل**. + +النتيجة: الرسوم تُسجَّل كإيراد لك، وذمة مالية على A تشمل أصل التحويل + الرسوم. + +## 4. من يُدفع الرسوم — المرسِل أم المستلِم؟ + +في نظام قيد، الرسوم تُدفَع من المرسِل A بشكل افتراضي. هذا الأكثر شيوعاً في الواقع (المرسِل يدفع تكلفة الإرسال). + +إذا كان الاتفاق على خصم الرسوم من المبلغ المُستلَم (المستلِم B يدفع)، فالمعالجة ستكون يدوية: +- أرسل لـB المبلغ ناقصاً الرسوم. +- وضّح في الوصف أن الرسوم خُصمت من المبلغ. + +النظام بوضعه الحالي يُسجّل الرسوم كقبض من المرسِل. + +## 5. ربط الرسوم بالتحويل — أهمية معرف المجموعة + +سند الرسوم يحمل نفس معرف مجموعة التحويل (transfer group ID) كالسندَيْن الآخرَيْن (القبض والدفع). هذا يعني: + +- يمكنك استعراض "التحويل كاملاً": القبض من A + الرسوم من A + الدفع لـB. +- في التقارير، يمكن تجميع كل سندات تحويل واحد كوحدة. +- إذا اعترض A على الرسوم لاحقاً، الربط يُثبت أنها جزء من نفس العملية. + +## 6. هل يجب الإعلان عن الرسوم مسبقاً؟ + +من منظور النظام: نعم دائماً. الرسوم تُجعل واضحة في سند الرسوم الذي يظهر لـA عند مراجعة تحويله. + +من منظور الثقة الاجتماعية: من الأفضل دائماً الاتفاق على الرسوم قبل التنفيذ. الإفصاح المسبق يمنع النزاعات اللاحقة. + +## 7. حساب رسوم الحوالات — التصنيف الصحيح + +التصنيف الأنسب لإيراد رسوم الوساطة هو: "رسوم الحوالات" الموجود ضمن تصنيف الإيرادات. هذا التصنيف مُعدّ خصيصاً لهذا النوع من الدخل. + +توثيق رسوم الوساطة بشكل صحيح يُتيح لك: +- تتبع إجمالي دخلك من وساطة التحويلات. +- مقارنة هذا الدخل عبر الفترات. +- شفافية كاملة مع من تُعامله. diff --git a/platform/resources/docs/06_transfers_system/04_tripartite_flows.md b/platform/resources/docs/06_transfers_system/04_tripartite_flows.md new file mode 100644 index 00000000..48c06b1b --- /dev/null +++ b/platform/resources/docs/06_transfers_system/04_tripartite_flows.md @@ -0,0 +1,86 @@ +# التدفقات الثلاثية — التتبع الكامل للتحويل + +## 1. تتبع التحويل الثلاثي من البداية للنهاية + +التحويل الثلاثي الناجح يمر بستة إجراءات منطقية بالترتيب: + +``` +المرحلة ١: إنشاء التحويل +المرحلة ٢: موافقة A على السند الأول +المرحلة ٣: استلام المال من A فعلياً +المرحلة ٤: رفع القفل عن سند الدفع +المرحلة ٥: إرسال المال لـB +المرحلة ٦: تأكيد B الاستلام +``` + +كل مرحلة موثَّقة في النظام. يمكنك دائماً معرفة في أي مرحلة يوجد التحويل. + +## 2. المرحلة الأولى والثانية — الالتزام من الطرفَيْن + +عند إنشاء التحويل الثلاثي: + +- تُنشئ سند القبض (A إليك) في حالة "مسودة" أو "مُؤكَّد" من طرفك. +- تُنشئ سند الدفع (أنت إلى B) مشروطاً مقفولاً. +- A يرى سند القبض ويُؤكّده — هذا إعلان التزامه بالإرسال. + +بعد تأكيد A: الالتزام ثنائي. كلٌّ منكما "وقّع" على دوره. + +## 3. المرحلة الثالثة — الاستلام الفعلي واللحظة الحرجة + +الاستلام الفعلي من A هو اللحظة التي تتحوّل فيها من "طرف بالتزام قانوني" إلى "وسيط بمال في يده". + +حين تستلم المال: +- تُؤكّد سند القبض من طرفك. +- توقيعك الرقمي على هذا السند: "أُقرّ باستلام المبلغ". + +هذه اللحظة هي التي تُرفَع فيها تلقائياً الشرطية عن سند الدفع. + +## 4. المرحلة الرابعة — رفع القفل التلقائي + +حين تُؤكّد سند القبض: +- النظام يكتشف تلقائياً أن لهذا السند "سنداً شرطياً مرتبطاً" في نفس المجموعة. +- يُرفَع القفل الشرطي عن سند الدفع. +- يُصبح سند الدفع قابلاً للمشاركة والتأكيد. + +هذا الرفع تلقائي — لا تحتاج إجراء يدوياً لتفعيل سند الدفع. + +## 5. المرحلة الخامسة والسادسة — إتمام التحويل + +بعد رفع القفل: +- أرسل سند الدفع لـB. +- B يؤكّد استلامه بتوقيعه الرقمي. + +عند تأكيد B: التحويل مكتمل. جميع السندات الثلاثة في حالة "مؤكَّد". معرف المجموعة يربط الصورة الكاملة. + +## 6. كيف تُراجع تحويلاً ثلاثياً في أي مرحلة؟ + +من أي سند في المجموعة، يمكنك: +- الوصول لمعرف المجموعة. +- استعراض "جميع سندات هذه المجموعة". +- رؤية حالة كل سند ومرحلة التحويل الكاملة. + +لا تحتاج تتبع كل سند منفصلاً — المجموعة هي الوحدة. + +## 7. ماذا يحدث إذا رفض B الاستلام؟ + +إذا رفض B سند الدفع: +- B يُبلَّغ يسبب الرفض. +- أنت تعيد النظر: هل هناك خطأ في المبلغ؟ في التاريخ؟ +- يمكنك سحب سند الدفع (إذا لم يُقبَل بعد) وإنشاء سند دفع معدَّل. + +**لكن المال موجود معك**. رفض B لا يُعيد المال لـA تلقائياً. هذا يُشير لمشكلة تحتاج تواصلاً بشرياً بين الأطراف لحلها. + +المال والتوثيق منفصلان — النظام يُوثّق، الأطراف هم من يُحلّون النزاع البشري. + +## 8. أثر التحويل على أرصدة الأطراف — القاعدة الذهبية + +بعد اكتمال التحويل الثلاثي: + +- **رصيد الوسيط مع A** (من حساباتهما الشخصية): **لم يتغير**. +- **رصيد الوسيط مع B** (من حساباتهما الشخصية): **لم يتغير**. +- **صافي صندوق الوسيط النقدي**: دخل مقدار X وخرج مقدار X = **صافي صفر** (إن لم تكن هناك رسوم). + +قيود التحويل الثلاثي تمر عبر صندوق الوسيط النقدي حصراً — لا تلمس أي حساب شخصي بين الأطراف. + +هذا العزل هو الفارق الجوهري بين التحويل الثلاثي وأي سندَيْن متتاليَيْن منفصلَيْن. +← تفصيل كامل: [عزل القيود المحاسبية في التحويل الثلاثي](./05_accounting_isolation.md) diff --git a/platform/resources/docs/06_transfers_system/05_accounting_isolation.md b/platform/resources/docs/06_transfers_system/05_accounting_isolation.md new file mode 100644 index 00000000..b01d2fd8 --- /dev/null +++ b/platform/resources/docs/06_transfers_system/05_accounting_isolation.md @@ -0,0 +1,237 @@ +# عزل القيود المحاسبية — سر الوساطة النظيفة + +## الصورة أولاً + +``` + ═══════════════════════════════════════════════════════════════ + الرسمة الأولى: عزل الحسابات الشخصية + ═══════════════════════════════════════════════════════════════ + + قبل التحويل الثلاثي (1,000 وحدة): + ┌──────────────────────────────────────────────────────────────┐ + │ دفتر محمد (الوسيط C) │ + │ │ + │ ┌──────────────────────────┐ ┌──────────────────────────┐ │ + │ │ حساب علي (شخصي) │ │ حساب بديع (شخصي) │ │ + │ │ الرصيد: 500 ← علي يدين │ │ الرصيد: 0 │ │ + │ └──────────────────────────┘ └──────────────────────────┘ │ + │ │ + │ ┌──────────────────────────────────────────────────────┐ │ + │ │ صندوق محمد النقدي (affectedAccountId) رصيد: س │ │ + │ └──────────────────────────────────────────────────────┘ │ + └──────────────────────────────────────────────────────────────┘ + + أثناء التحويل: EntryGenerator يكتب هنا فقط: + ↓ سند القبض │ ↓ سند الدفع + مدين: صندوق محمد │ مدين: حساب بديع (الطرف المقابل) + دائن: حساب علي │ دائن: صندوق محمد + (counterpartyId) │ (affectedAccountId) + + ✗ حساب علي الشخصي ← لا يُلمس أبداً + ✗ حساب بديع الشخصي ← لا يُلمس أبداً + + بعد التحويل: + ┌──────────────────────────────────────────────────────────────┐ + │ دفتر محمد (الوسيط C) │ + │ │ + │ ┌──────────────────────────┐ ┌──────────────────────────┐ │ + │ │ حساب علي (شخصي) │ │ حساب بديع (شخصي) │ │ + │ │ الرصيد: 500 ← لم يتغير│ │ الرصيد: 0 ← لم يتغير │ │ + │ └──────────────────────────┘ └──────────────────────────┘ │ + │ │ + │ ┌──────────────────────────────────────────────────────┐ │ + │ │ صندوق محمد النقدي رصيد: س+1,000-1,000 = س (صفر) │ │ + │ └──────────────────────────────────────────────────────┘ │ + └──────────────────────────────────────────────────────────────┘ +``` + +``` + ═══════════════════════════════════════════════════════════════ + الرسمة الثانية: في محادثة من يظهر التحويل؟ + ═══════════════════════════════════════════════════════════════ + + ┌─────────────────────────────────────────────────────────────┐ + │ علي (A) محمد (C) بديع (B) │ + │ [مُرسِل] [وسيط] [مُستقبِل] │ + │ │ │ │ │ + │ ══════╪════════════════╪════════════════════╪══════ │ + │ محادثة علي ↔ بديع ║ ║ │ + │ ══════════════════════ ║ ║ │ + │ التحويل يظهر هنا ║ ║ │ + │ ┌────────────────┐ ║ ┌────────────────┐║ │ + │ │ [→ صادر] │══╬══►│ [← وارد] │║ │ + │ │ 1,000 وحدة │ ║ │ 1,000 وحدة │║ │ + │ │ عبر محمد (C) │ ║ │ عبر محمد (C) │║ │ + │ └────────────────┘ ║ └────────────────┘║ │ + │ ║ ║ │ + │ ══════════════════════ ║ ║ │ + │ محادثة علي ↔ محمد ║ ║ │ + │ ══════════════════════ ║ ║ │ + │ ✗ التحويل لا يظهر ───╬► [قاعدة return ║ │ + │ (تعاملات شخصية فقط) ║ false] ║ │ + │ ║ ║ │ + │ ══════════════════════ ║ ║ │ + │ محادثة محمد ↔ بديع ║ ║ │ + │ ══════════════════════ ║ ║ │ + │ ✗ التحويل لا يظهر ─────╬────────────────────╬► [return false│ + │ (تعاملات شخصية فقط) ║ ║ │ + │ ║ ║ │ + │ ══════════════════════════════════════════════ │ + │ محمد يرى التحويل في: كشف الصندوق / مجموعة التحويل │ + │ قبض من علي +1,000 │ دفع لبديع -1,000 │ صافٍ: 0 │ + └─────────────────────────────────────────────────────────────┘ + + ملاحظة مهمة حالة التقديم (لو قدّم محمد المبلغ عن علي): + ┌─────────────────────────────────────────────────────────────┐ + │ محمد ↔ بديع: يظهر سند الدفع │ + │ محمد ↔ علي: تظهر الذمة (علي يدين لمحمد) │ + │ ✗ علي ↔ بديع: لا يظهر شيء (محمد هنا مُقرِض لا وسيط) │ + └─────────────────────────────────────────────────────────────┘ +``` +*** + +## 1. السؤالان اللذان يُربكان كل وسيط + + +**السؤال الأول** (يسأله الوسيط): +> "علي ومحمد يستخدمان قيد. أنا وسيط بينهما. لديّ رصيد شخصي مع علي من تعاملات سابقة. هل التحويل سيُغيّر هذا الرصيد؟" + +**السؤال الثاني** (يسأله المُرسِل أو المُستقبِل): +> "علي طلب من محمد (الوسيط) أن يُرسل مالاً لبديع — كلهم يستخدمون قيد. أين سيظهر هذا التحويل؟ هل في محادثة علي مع محمد؟ أم في محادثة علي مع بديع مباشرة؟" + +الإجابتان مترابطتان وكلتاهما تكشف عن تصميم هندسي عميق. +*** + +## 2. محادثة علي مع بديع — لا محادثة علي مع محمد + +الكود في `ListAccountStatementChatUseCase` يُطبّق **قاعدة الاستبعاد** التالية: + +```dart +// Rule 3: Exclude any voucher where the Mediator is the Counterparty +if (v.isTripartite) { + final mediatorId = v.tripartiteMeta?.mediatorAccountId ?? v.affectedAccountId; + if (myId == mediatorId || cpId == mediatorId) { + return false; // Exclude from Mediator's chat with parties + } +} +``` + +**ماذا تعني هذه القاعدة؟** + +السند الثلاثي **لا يظهر** في محادثة الوسيط مع أي من الطرفَيْن. بدلاً من ذلك، يظهر **في محادثة علي مع بديع مباشرة**، مع إشارة إلى أن محمد هو وسيط هذه المعاملة. + +**الصورة الكاملة لما يرى كل طرف**: + +``` +محادثة علي ↔ بديع: + يظهر التحويل ← "أرسل علي 1,000 ﷼ عبر وسيط محمد" + علي: outgoing ← أنا المصدر + بديع: incoming ← أنا الوجهة + +محادثة علي ↔ محمد: + ✗ لا يظهر التحويل الثلاثي هنا + (يظهر فقط إذا كان بينهما تعاملات شخصية مباشرة أخرى) + +محادثة محمد ↔ بديع: + ✗ لا يظهر التحويل الثلاثي هنا أيضاً +``` +*** + +## 3. كيف "يقرأ" الكود اتجاه المعاملة؟ + +`_directionFromPerspective` يحل إشكالية التوجيه عبر `linkedPartyId`: + +```dart +if (v.isTripartite) { + final isReceipt = v.type == VoucherType.receipt; + // سند القبض: counterpartyId=A، linkedPartyId=B + final sourceId = isReceipt ? v.counterpartyId : v.tripartiteMeta!.linkedPartyId; + // سند الدفع: counterpartyId=B، linkedPartyId=A + final destId = isReceipt ? v.tripartiteMeta!.linkedPartyId : v.counterpartyId; + + if (perspectiveId == sourceId) return 'outgoing'; // يرى نفسه مُرسِلاً + if (perspectiveId == destId) return 'incoming'; // يرى نفسه مُستقبِلاً +} +``` + +بغض النظر عن أي السندَيْن (القبض أو الدفع) يُعرض، `linkedPartyId` يُتيح للنظام تحديد "من هو المصدر الحقيقي" و"من هو الوجهة الحقيقية" — فيُقدّم التحويل في سياقه الصحيح. +*** + +## 4. ما الذي يظهر في كل محادثة؟ — الصورة الكاملة + +**علي يفتح محادثته مع بديع**: +``` +بديع +──────────────────────────────── +[تحويل ثلاثي] 1,000 ﷼ +↑ صادر منك لبديع +عبر الوسيط: محمد +──────────────────────────────── +``` + +**بديع يفتح محادثته مع علي**: +``` +علي +──────────────────────────────── +[تحويل ثلاثي] 1,000 ﷼ +↓ واردٌ إليك من علي +عبر الوسيط: محمد +──────────────────────────────── +``` + +**محمد يفتح محادثته مع علي**: التحويل الثلاثي **لا يظهر هنا**. تظهر فقط تعاملاتهما الشخصية المباشرة. + +**محمد يفتح محادثته مع بديع**: التحويل الثلاثي **لا يظهر هنا أيضاً**. +*** + +## 5. محمد يرى التحويل — لكن في مكان مختلف + +محمد يرى التحويل في **صفحة التحويلات الثلاثية** أو في **كشف صندوقه النقدي**، لا في محادثاته الشخصية مع الطرفَيْن. هناك يرى: + +| السند | الطرف | الاتجاه | المبلغ | +|------|-------|---------|--------| +| القبض | علي | وارد لصندوقه | +1,000 | +| الدفع | بديع | صادر من صندوقه | -1,000 | + +**رصيده مع علي الشخصي**: لم يتغير. +**رصيده مع بديع الشخصي**: لم يتغير. +*** + +## 6. سيناريو التقديم — حين يتغير كل شيء + +إذا اختار محمد "تقديم المبلغ" بدلاً من الوساطة الحقيقية — أي يدفع من ماله لبديع قبل استلام المال من علي: + +هذه **ليست وساطة** — هذا إقراض. والقيود ستكون مختلفة جوهرياً: + +- **سند الدفع**: محمد → بديع (سند عادي، **لا ثلاثي**). +- **ذمة لمحمد على علي**: قيد يُسجّل أن علياً يدين لمحمد بالمبلغ. + +**ما الذي سيظهر في المحادثات؟**: +- محادثة محمد ↔ بديع: يظهر سند الدفع هنا. +- محادثة محمد ↔ علي: هنا تظهر الذمة — "علي يديني 1,000 ﷼". +- محادثة علي ↔ بديع: **لا يظهر فيها شيء** — محمد هنا ليس وسيطاً بل مُقرِضاً. + +هذا هو الفارق الجوهري بين الحالتَيْن من منظور العلاقات الموثَّقة. +*** + +## 7. جدول المقارنة الكامل — الوساطة مقابل التقديم + +| المعيار | الوساطة الحقيقية | التقديم | +|---------|----------------|---------| +| محادثة علي ↔ بديع | التحويل يظهر مباشرة | ✗ لا يظهر شيء | +| محادثة علي ↔ محمد | ✗ التحويل لا يظهر | الذمة تظهر هنا | +| محادثة محمد ↔ بديع | ✗ التحويل لا يظهر | سند الدفع يظهر هنا | +| رصيد محمد مع علي | ✗ لم يتغير | تغيّر — أصبح علي يديني | +| رصيد محمد مع بديع | ✗ لم يتغير | تغيّر — دفعتُ لبديع | +| القفل الشرطي | مُفعَّل | ✗ غير موجود | +*** + +## 8. الخلاصة — أربعة مبادئ مُطبَّقة في الكود + +**مبدأ ١ — الظهور المباشر**: التحويل الثلاثي يظهر في محادثة المُرسِل مع المُستقبِل مباشرة — لا في محادثاتهما مع الوسيط. هذا مُطبَّق عبر قاعدة الاستبعاد في `ListAccountStatementChatUseCase`. + +**مبدأ ٢ — محمد في الهامش**: دور الوسيط يظهر كـ"معلومة إضافية" على التحويل (`mediatorName`) — لا كطرف رئيسي في المحادثة. هو القناة، لا الطرف. + +**مبدأ ٣ — العزل المحاسبي**: حسابات محمد الشخصية مع علي أو بديع لا تتأثر بالوساطة أبداً. القيود تمر عبر صندوقه النقدي حصراً. + +**مبدأ ٤ — التمييز من الاختيار**: الفرق بين الوساطة والتقديم ليس تقنياً فحسب — إنه يُغيّر أين يظهر التوثيق، ومن يرتبط بمن، وكيف تتشكّل العلاقات الموثَّقة في النظام. diff --git a/platform/resources/docs/06_transfers_system/_category_.json b/platform/resources/docs/06_transfers_system/_category_.json new file mode 100644 index 00000000..d937a641 --- /dev/null +++ b/platform/resources/docs/06_transfers_system/_category_.json @@ -0,0 +1,4 @@ +{ + "label": "نظام التحويلات", + "position": 6 +} diff --git a/platform/resources/docs/07_reports_and_outputs/00_trial_balance.md b/platform/resources/docs/07_reports_and_outputs/00_trial_balance.md new file mode 100644 index 00000000..b1a31590 --- /dev/null +++ b/platform/resources/docs/07_reports_and_outputs/00_trial_balance.md @@ -0,0 +1,69 @@ +# ميزان المراجعة — الاختبار الرياضي للدفاتر + +## 1. ما هو ميزان المراجعة؟ + +ميزان المراجعة هو التقرير الذي يُثبت أن دفاترك "متوازنة" رياضياً — مجموع المدينات يساوي مجموع الدائنيات. إنه الاختبار الذي كان المحاسبون يُجرونه تاريخياً قبل إعداد الميزانية للتحقق من سلامة الدفاتر. + +في نظام قيد، ميزان المراجعة لا "يُكتَشَف" فيه خطأ في التوازن — لأن النظام يُطبّق التوازن رياضياً عند كل قيد. ميزان المراجعة هنا وظيفته **عرض** أرصدة كل حساب بشكل مُقارَن ومُجمَّع، لا اكتشاف مشكلة التوازن. + +## 2. ماذا يُظهر ميزان المراجعة؟ + +لكل حساب في النظام، الميزان يُظهر: + +- **الرصيد الافتتاحي**: رصيد الحساب في بداية فترة التقرير. +- **إجمالي المدينات في الفترة**: مجموع ما دُيّن لهذا الحساب خلال الفترة. +- **إجمالي الدائنيات في الفترة**: مجموع ما أُدين على هذا الحساب خلال الفترة. +- **الرصيد الختامي**: الرصيد الافتتاحي + (المدينات - الدائنيات). + +في أسفل الجدول: مجموع كل المدينات الكلي = مجموع كل الدائنيات الكلي. هذه معادلة لا يمكن كسرها إذا كانت الدفاتر سليمة. + +## 3. كيف تقرأ رصيد حساب في الميزان؟ + +قراءة الرصيد تعتمد على طبيعة الحساب: + +**أصل له طبيعة مدينة**: الرصيد المدين موجب يعني "لديّ قيمة هنا". رصيد دائن يعني استثناء يجب التحقق منه. + +**التزام له طبيعة دائنة**: الرصيد الدائن موجب يعني "أدين بهذه القيمة". رصيد مدين يعني استثناء. + +**مصروف له طبيعة مدينة**: الرصيد المدين يُمثّل ما أُنفق. استمراره يعني الإنفاق المتراكم. + +**إيراد له طبيعة دائنة**: الرصيد الدائن يُمثّل ما اكتسبتَ. استمراره يعني الدخل المتراكم. + +## 4. فترة التقرير — الثلاث أوضاع + +يمكن استعراض الميزان في ثلاث أوضاع زمنية: + +**كامل التاريخ**: من أول قيد في النظام حتى الآن — الصورة الإجمالية الكاملة. + +**من التاريخ الأول حتى تاريخ محدد**: لرؤية وضعك المالي في لحظة محددة في الماضي. + +**فترة محددة**: من تاريخ لتاريخ — لرؤية نشاط فترة بعينها. + +## 5. العلاقة بين ميزان المراجعة والميزانية العمومية + +ميزان المراجعة يُدرج كل الحسابات. الميزانية العمومية تُعيد تنظيم هذه الأرصدة في قسمين: + +**الجانب الأيسر (الأصول)**: ما تملكه — نقدية + ذمم دائنة (عليك) + أصول ثابتة. + +**الجانب الأيمن (الخصوم والحقوق)**: ما تدين به + ما تبقى من الثروة الصافية. + +في الميزانية الصحيحة: الأصول = الخصوم + حقوق الملكية. + +## 6. متى تُركّز على ميزان المراجعة؟ + +ميزان المراجعة مفيد بشكل خاص حين: + +- تريد مراجعة تفصيلية حساباً حساباً. +- تبحث عن حساب معين ورصيده. +- تريد مقارنة نشاط فترتين في نفس الحسابات. +- تُعدّ للمراجعة مع محاسب. + +## 7. ما الذي لا يُخبرك به ميزان المراجعة؟ + +ميزان المراجعة لا يُجيب عن: + +- "لماذا ارتفع رصيد حساب معين؟" (للإجابة: اذهب لكشف الحساب التفصيلي). +- "ما ربحي أو خسارتي خلال الفترة؟" (للإجابة: الميزانية العمومية + حساب نتيجة الأعمال). +- "كيف توزّع إنفاقي على الأغراض؟" (للإجابة: تقارير مراكز التكلفة). + +ميزان المراجعة هو نقطة بداية للفهم، يقودك لتقارير أعمق حين تحتاج. diff --git a/platform/resources/docs/07_reports_and_outputs/01_balance_sheet.md b/platform/resources/docs/07_reports_and_outputs/01_balance_sheet.md new file mode 100644 index 00000000..5212248e --- /dev/null +++ b/platform/resources/docs/07_reports_and_outputs/01_balance_sheet.md @@ -0,0 +1,75 @@ +# الميزانية العمومية — صورة وضعك المالي في لحظة + +## 1. الميزانية العمومية — لماذا تُسمى "عامة"؟ + +"عامة" لأنها تُغطي المشهد المالي بكامله في لحظة واحدة: كل ما تملكه، وكل ما تدين به، وكل ما يظل ملكاً صافياً لك. + +في المحاسبة المهنية، الميزانية العمومية (Balance Sheet) هي أم التقارير — المنطلق الذي تُفسَّر في ضوئه بقية التقارير. + +## 2. هيكل الميزانية في قيد + +الميزانية تُحسَب بتصنيف الأرصدة في أقسام بحسب التصنيف الحسابي: + +**قسم الأصول**: + +- نقدية وسائلة: مجموع ما لديك من نقد وحسابات بنكية. +- ذمم دائنة (عليك): مجموع ما يديه الآخرون لك. +- أصول ثابتة مُولِّدة للربح: قيمة استثماراتك. +- أصول ثابتة قابلة للإهلاك: قيمة ممتلكاتك. + +**قسم الالتزامات**: + +- ذمم مدينة (لك): مجموع ما تدين به للآخرين. +- حسابات تسوية: أرصدة حسابات العبور. + +**قسم الدخل الصافي**: + +- إيرادات ناقص مصروفات: هذا هو الفائض أو العجز المالي للفترة. + +## 3. القاعدة التي لا تُكسر: الأصول = الخصوم + الدخل الصافي + +في الميزانية الصحيحة: + +``` +مجموع الأصول = مجموع الالتزامات + صافي الدخل/العجز +``` + +إذا كانت الفجوة بين الجانبَيْن أقل من 10 وحدات مالية صغرى (مثل 10 هللات) — النظام يعتبرها ضمن هامش التقريب المقبول. أي فجوة أكبر يكون مصدرها خطأ في التصنيف. + +## 4. كيف تقرأ ميزانيتك؟ + +**أرصدة الأصول مرتفعة**: تملك قيمة مالية موزعة — نقد واستثمارات وذمم. + +**أرصدة الالتزامات مرتفعة**: لديك التزامات تجاه الآخرين تستحق المتابعة. + +**الدخل الصافي موجب**: استقبلتَ أكثر مما أنفقتَ خلال الفترة — وضع صحي. + +**الدخل الصافي سالب**: أنفقتَ أكثر مما استقبلتَ — يستحق المراجعة والتخطيط. + +## 5. صافي الثروة — السؤال الجوهري + +الميزانية تُتيح لك حساب "صافي ثروتك": + +``` +صافي الثروة = إجمالي الأصول - إجمالي الالتزامات +``` + +هذا الرقم يُخبرك: إذا سُدّدت كل ديونك الآن وبعتَ كل ما تملكه — ما الذي سيتبقى لك؟ + +مراقبة هذا الرقم عبر الزمن تُظهر: هل ثروتك تنمو؟ أم تتآكل؟ + +## 6. الميزانية في لحظة واحدة — لا لفترة + +ميزان المراجعة يُغطي فترة (مثل: إجمالي نشاط هذا الشهر). الميزانية العمومية تُظهر وضعك **في لحظة محددة** (مثل: يوم 31 ديسمبر). + +هذا يعني: الميزانية هي "لقطة شاشة" لوضعك المالي. لقطتان في تاريخين مختلفين تُريانك كيف تطور وضعك. + +## 7. القراءة الصحيحة للميزانية بمرور الوقت + +للحصول على قيمة حقيقية من الميزانية العمومية: + +- **شهرياً**: قارن مجموع الأصول والالتزامات. +- **ربعياً**: قيّم صافي ثروتك ومقارنتها بالربع السابق. +- **سنوياً**: قدّر اتجاه ثروتك: صاعدة، مستقرة، أم هابطة؟ + +الميزانية العمومية هي المرآة المالية الأدق — إذا نظرتَ فيها بانتظام، لن تُفاجأ بوضعك المالي. diff --git a/platform/resources/docs/07_reports_and_outputs/02_voucher_reports.md b/platform/resources/docs/07_reports_and_outputs/02_voucher_reports.md new file mode 100644 index 00000000..a43f7351 --- /dev/null +++ b/platform/resources/docs/07_reports_and_outputs/02_voucher_reports.md @@ -0,0 +1,50 @@ +# تقارير السندات — قراءة النشاط المالي + +## 1. ما الذي يُميّز تقرير السندات عن كشف الحساب؟ + +كشف الحساب يُركّز على حساب واحد ويتتبع كل حركاته. تقرير السندات يُركّز على **الوثائق** نفسها — يُظهر السندات كما أُنشئت، مع حالاتها وتفاصيلها. + +**متى تستخدم كل منهما؟** +- كشف الحساب: لمعرفة ما دخل أو خرج من محفظتي. +- تقرير السندات: لمراجعة وثائق معاملاتي وحالاتها. + +## 2. تصفية تقرير السندات + +تقرير السندات يدعم تصفية متعددة المحاور: + +- **بالتاريخ**: نطاق زمني محدد. +- **بالنوع**: قبوض فقط، أو دفوعات فقط. +- **بالحالة**: المسودات، المؤكَّدة، المُسوَّاة، المسحوبة. +- **بالطرف**: جميع سندات طرف معين. +- **بالحساب**: جميع سندات مرتبطة بحساب معين. +- **بالمبلغ**: سندات فوق مبلغ معين أو في نطاق محدد. + +## 3. قراءة حالات السندات في التقرير + +| الحالة | ما تعنيه | +|--------|----------| +| مسودة | موجود لكن بلا أثر محاسبي بعد | +| مؤكَّد | القيود أُنشئت، الطرف الآخر أُبلغ | +| مُسوَّى | الالتزام اكتمل من الطرفَيْن | +| مسحوب | أُلغي، لا أثر مالي نشط | + +الألوان في قائمة السندات تُعكَس هذه الحالات بشكل مرئي مباشر. + +## 4. قراءة حالة الطرف الآخر + +إضافة للحالة الرئيسية للسند، كل سند يُظهر حالة "اتفاق الطرف الآخر": + +- **تحت الطلب**: لم يُقرّر الطرف الآخر بعد. +- **مقبول**: الطرف الآخر قبل وأكّد توقيعاً. +- **مرفوض**: الطرف الآخر رفض مع سبب. +- **غير مُحقَّق**: لم يتم التحقق من توقيع الطرف الآخر. + +هذه الحالة الثنائية تُخبرك ما إذا كان السند "اتفاقاً موحَّداً" أم "ادعاءً منفرداً بانتظار القبول". + +## 5. السندات المرتبطة بمجموعات + +سندات التحويل الثلاثي تظهر في التقرير مرتبطة ببعضها عبر معرف المجموعة. يمكنك من السند الواحد الوصول للمجموعة كاملة. + +## 6. تصدير تقرير السندات + +للمشاركة أو الأرشفة الخارجية، يمكن تصدير تقرير السندات بصيغة مناسبة من قسم التصدير. diff --git a/platform/resources/docs/07_reports_and_outputs/03_account_statements.md b/platform/resources/docs/07_reports_and_outputs/03_account_statements.md new file mode 100644 index 00000000..293cbe4c --- /dev/null +++ b/platform/resources/docs/07_reports_and_outputs/03_account_statements.md @@ -0,0 +1,45 @@ +# كشوفات الحسابات — قراءة تاريخ حساب بالتفصيل + +## 1. ما هو كشف الحساب؟ + +كشف الحساب هو التسلسل الزمني الكامل لكل القيود التي مرت على حساب معين، مع الرصيد التراكمي بعد كل قيد. + +هو ليس قائمة سندات — هو قائمة **قيود دفتر الأستاذ** المرتبطة بهذا الحساب. القيد هو الإدخال المحاسبي النهائي الذي يُنتجه السند بعد التأكيد. + +## 2. الرصيد التراكمي — كيف تُقرأ الأرقام؟ + +الرصيد التراكمي في كشف الحساب يتحرك بحسب طبيعة الحساب: + +**حساب أصل (طبيعة مدينة)**: كل قيد مدين يرفع الرصيد، كل قيد دائن يخفضه. + +**حساب التزام (طبيعة دائنة)**: كل قيد دائن يرفع الرصيد، كل قيد مدين يخفضه. + +**المصروف (طبيعة مدينة)**: الرصيد يرتفع كلما أنفقتَ أكثر. + +**الإيراد (طبيعة دائنة)**: الرصيد يرتفع كلما اكتسبتَ أكثر. + +## 3. استخدامات كشف الحساب + +**مطابقة البنك**: قارن كشف حساب النقدية في قيد مع كشف حسابك البنكي للتأكد من تطابقهما. + +**مراجعة طرف**: كشف حساب طرف معين يُظهر كل الذمم معه. + +**تتبع أصل**: كشف حساب عقار مثلاً يُظهر كل ما أُضيف أو نقص من قيمته. + +## 4. نقطة البداية والوقت الصفري + +في بعض الحالات، قد تُريد رؤية كشف هذا الشهر فقط. في حالات أخرى، قد تُريد الكشف من يوم أول قيد حتى الآن. + +هر نطاق زمني: +- بداية + نهاية = رؤية فترة محددة. +- بلا بداية + نهاية = من الأزل حتى التاريخ. +- بداية + بلا نهاية = من التاريخ حتى الآن. + +الاختيار الأنسب يعتمد على ما تبحث عنه. + +## 5. كشف المحادثة — عرض الحساب بين طرفَيْن + +طريقة عرض مختلفة: "كشف المحادثة" يُظهر Ali العلاقة المالية بين طرفَيْن على شكل محادثة بدلاً من قائمة. هذا العرض أوضح إنسانياً لكنه أقل دقة محاسبياً من الكشف التقليدي. + +استخدم كشف المحادثة: لفهم سريع للعلاقة مع شخص. +استخدم الكشف التقليدي: للمراجعة الدقيقة والمطابقة. diff --git a/platform/resources/docs/07_reports_and_outputs/04_exports_and_sharing.md b/platform/resources/docs/07_reports_and_outputs/04_exports_and_sharing.md new file mode 100644 index 00000000..7a962d61 --- /dev/null +++ b/platform/resources/docs/07_reports_and_outputs/04_exports_and_sharing.md @@ -0,0 +1,41 @@ +# التصدير والمشاركة — استخراج بياناتك + +## 1. مبدأ التصدير في نظام قيد + +بياناتك ملكك المطلق. التصدير ليس "منحة" من النظام — إنه حق مُضمَّن في فلسفة السيادة. يمكنك دائماً استخراج بياناتك بدون قيود صلاحية. + +## 2. أنواع التصدير المتاحة + +**تصدير التقارير**: تصدير ميزان مراجعة، ميزانية عمومية، وكشوفات حسابات بصيغ مناسبة للاستخدام الخارجي. + +**تصدير السندات**: قائمة السندات مُفلتَرة بأي نطاق تختار. + +**مشاركة السند الواحد**: إرسال سند محدد كمستند مُوقَّع للطرف الآخر (لأغراض التوثيق). + +## 3. مشاركة السندات المُوقَّعة + +السند في قيد يُوجَد كوثيقة مُوقَّعة رقمياً. يمكن مشاركة هذه الوثيقة عبر: + +- واجهة التطبيق للطرف الآخر على نظام قيد. +- أي وسيلة أخرى (العرض كملف أو رابط) للأطراف خارج النظام. + +عند المشاركة: بيانات الوثيقة تُعرض بوضوح: المبلغ، الأطراف، التاريخ، التوقيعات. + +## 4. تصدير نسخة احتياطية كاملة + +خيار النسخة الاحتياطية في الإعدادات يُنشئ ملفاً مُشفَّراً يحتوي على: +- قاعدة البيانات الكاملة. +- إعدادات النظام. + +**لاستعادتها**: تحتاج عبارتك التذكيرية. بدونها، الملف غير قابل للفتح من أي طرف. + +## 5. تحذير — مشاركة غير مقصودة للبيانات الحساسة + +عند مشاركة أي تقرير، تأكد أنك تعرف ما يحتويه: +- التقارير تُظهر أسماء الحسابات والأطراف والمبالغ. +- شارك فقط مع من يُفترض أن يرى هذه المعلومات. +- في حالة المحاسبين والمدققين: يمكنك إنشاء تقرير نطاق محدد بدل تصدير كل شيء. + +## 6. WhatsApp والمشاركة الاجتماعية للكشوفات + +يمكن مشاركة تقارير الكشوفات مع أطراف عبر WhatsApp أو ما يُعادله. الوسيلة التقنية هي نظام المشاركة المدمج في الجهاز. النظام يُهيئ الوثيقة والجهاز يتولى مشاركتها. diff --git a/platform/resources/docs/07_reports_and_outputs/_category_.json b/platform/resources/docs/07_reports_and_outputs/_category_.json new file mode 100644 index 00000000..7bf6e389 --- /dev/null +++ b/platform/resources/docs/07_reports_and_outputs/_category_.json @@ -0,0 +1,4 @@ +{ + "label": "التقارير والمخرجات", + "position": 7 +} diff --git a/platform/resources/docs/08_advanced_accounting/00_what_is_advanced_accounting.md b/platform/resources/docs/08_advanced_accounting/00_what_is_advanced_accounting.md new file mode 100644 index 00000000..341d70b0 --- /dev/null +++ b/platform/resources/docs/08_advanced_accounting/00_what_is_advanced_accounting.md @@ -0,0 +1,49 @@ +# ما هي المحاسبة المتقدمة؟ + +## 1. تعريف المحاسبة المتقدمة في قيد + +"المحاسبة المتقدمة" في قيد هي مجموعة الإعدادات والعمليات التي تُمكّنك من: + +- تخصيص هيكل الحسابات الجوهرية. +- التعامل مع عملات متعددة بشكل منهجي. +- ضبط سياسات استقبال التحويلات. +- إدارة الجوانب التقنية لنظامك المحاسبي. + +## 2. الفرق العملي عن المحاسبة الأساسية + +| المعيار | الأساسية | المتقدمة | +| --------- | --------- | --------- | +| مستوى التأثير | معاملات يومية | هيكل النظام | +| درجة الخطورة عند الخطأ | متوسطة (قابل للتصحيح) | عالية (يؤثر على كل البيانات) | +| تكرار الاستخدام | يومي | نادر | +| متطلب الفهم | مفاهيم أساسية | مفاهيم محاسبية أعمق | + +## 3. ما الذي تشمله المحاسبة المتقدمة في هذا الدليل؟ + +الفصل الثامن يُغطي: + +**تعديل الحسابات الجوهرية**: إعادة هيكلة شجرة الحسابات، إضافة تصنيفات مخصصة. + +**إدارة العملات**: كيف تتعامل مع حسابات بعملات متعددة بدون خلط. + +**سياسات التحويل**: ضبط من يمكنه إرسال طلبات تحويل إليك وكيف تُعالجها. + +## 4. هل تحتاج المحاسبة المتقدمة؟ + +أسئلة للتقييم: + +- هل تملك أصولاً بعملات متعددة؟ → نعم، ستحتاج إدارة العملات. +- هل تعمل وسيطاً بشكل منتظم؟ → نعم، ستستفيد من سياسات التحويل. +- هل التصنيفات الافتراضية لا تُغطي احتياجاتك؟ → نعم، ستحتاج تصنيفات مخصصة. + +إذا أجبتَ بـ"لا" على الأسئلة الثلاثة: احتمال كبير أنك لا تحتاج المتقدم في الوقت الحالي. + +## 5. التحذير الجوهري + +المحاسبة المتقدمة لا تُلغي القواعد الأساسية: + +- قيد مزدوج متوازن: دائم وإلزامي. +- وثيقة قبل القيد: دائم وإلزامي. +- الماضي لا يُمحى: دائم وإلزامي. + +المتقدم يُوسّع قدراتك دون أن يُخفّف هذه الضمانات. diff --git a/platform/resources/docs/08_advanced_accounting/01_modifying_core_accounts.md b/platform/resources/docs/08_advanced_accounting/01_modifying_core_accounts.md new file mode 100644 index 00000000..7a967395 --- /dev/null +++ b/platform/resources/docs/08_advanced_accounting/01_modifying_core_accounts.md @@ -0,0 +1,54 @@ +# تعديل الحسابات الجوهرية — حدود ما يمكن تغييره + +## 1. ما الذي يُعدّ "جوهرياً"؟ + +الحسابات الجوهرية هي التي تُؤثّر تعديلها على أداء النظام الجوهري أو معنى بياناتك التاريخية. تُشمل: + +- الحسابات الافتراضية المحمية (لا يمكن تعديلها البتة). +- الحسابات ذات الأرصدة الكبيرة والتاريخ الطويل. +- حساب النقدية الجذري (محور الجسر الآلي). + +## 2. ما يمكن تعديله فعلاً في الهيكل الجوهري + +**الحسابات المخصصة التي أنشأتَها**: يمكن تعديل أسمائها، ونقلها بين الآباء (بشرط تطابق التصنيف)، وتعديل أوصافها. + +**إضافة تصنيفات مخصصة (Custom)**: النظام يُتيح تصنيفاً مخصصاً يُحدّد أنت طبيعته واسمه. هذا يُتيح إنشاء حسابات لا تندرج تحت العشرة التصنيفات القياسية. + +**هيكلة الحسابات الفرعية**: إضافة طبقات تفصيل بدون حدود طالما تطابقت الأصول. + +## 3. ما لا يمكن تغييره أبداً + +- طبيعة حساب موجود له تاريخ مالي (مدين/دائن). +- تصنيف حساب افتراضي. +- انتماء حساب لأب مختلف تصنيفاً. +- اسم أو طبيعة حساب افتراضي. + +كل هذه القيود موجودة لضمان أن التاريخ المالي يبقى ذا معنى متسق. + +## 4. إضافة تصنيف مخصص — كيف ومتى؟ + +التصنيف المخصص يُتيح لك بناء نوع حساب لا يوجد في الأنواع القياسية العشرة. مثلاً: "تأمين الأصل" أو "ضمان التحويل". + +عند إنشاء تصنيف مخصص: + +- تُحدّد اسمه. +- تُحدّد طبيعته (مدين أم دائن). +- تُحدّد القسم المالي (أصول، التزامات، دخل). + +بعد إنشائه، يُصبح تصنيفاً كبقية التصنيفات — لا يمكن تغيير طبيعته لاحقاً. + +## 5. نقل الحساب إلى أب آخر — الشروط + +نقل حساب في الشجرة الهرمية ممكن بشرط صارم واحد: **تصنيف الأب الجديد يجب أن يتطابق مع تصنيف الحساب الذي تنقله**. + +لا يمكن نقل حساب "ذمم دائنة (عليك)" ليصبح فرعاً تحت "مصروفات شخصية". الطبيعتان والتصنيفان مختلفان. + +هذا القيد يحمي التاريخ: القيود المسجَّلة بالفعل استُندت للتصنيف القديم، والنقل لتصنيف مختلف سيُغيّر معنى هذا التاريخ. + +## 6. متى تتدخل في الهيكل الجوهري؟ + +التدخل في الهيكل الجوهري له توقيت مثالي: **في بداية استخدامك قبل تسجيل كثير من المعاملات**. + +بعد تراكم مئات المعاملات، أي تغيير في الهيكل يستلزم مراجعة ما إذا كان يُؤثّر على التقارير التاريخية. الهيكل الجيد من البداية يُلغي الحاجة للتعديل لاحقاً. + +**خلاصة**: خطط لهيكل حساباتك جيداً في البداية. التعديل لاحقاً ممكن لكن محدود ومحفوف بتحفظات. diff --git a/platform/resources/docs/08_advanced_accounting/02_currency_management.md b/platform/resources/docs/08_advanced_accounting/02_currency_management.md new file mode 100644 index 00000000..481c7afd --- /dev/null +++ b/platform/resources/docs/08_advanced_accounting/02_currency_management.md @@ -0,0 +1,56 @@ +# إدارة العملات — السيادة عبر الحدود النقدية + +## 1. الموقف من العملات في نظام قيد + +نظام قيد يتعامل مع العملات المتعددة بنهج صارم: **لا تحويل ضمني، ولا خلط بين عملات في معاملة واحدة**. + +كل معاملة بعملة واحدة. كل حساب تتبّع رصيده بعملة واحدة. هذا يُعني: + +- لديك حساب بنكي بال﷼ وآخر بالدولار؟ حسابان منفصلان في النظام. +- تحويل من ال﷼ للدولار؟ معاملتان: بيع ﷼ + شراء دولار. + +## 2. لماذا لا تحويل ضمني؟ + +سعر الصرف يتغير كل دقيقة. إذا سمح النظام بتحويل ضمني بسعر "افتراضي"، فبعد سنة تجد أرصدة بعملات مختلفة محسوبة بأسعار لا تعكس واقعاً. + +المستخدم هو من يُقرّر سعر التحويل الذي اتفق عليه فعلاً. هذا القرار لا يُتخذ تلقائياً. + +## 3. كيف تُسجّل تحويل عملة؟ + +عندما تُحوّل ريالاً لدولار (بسعر صرف ستيّرتَه مع الصراف): + +**السند الأول — بيع ال﷼**: + +- نوعه: دفع. +- الطرف الآخر: الصراف. +- الحساب المتأثر: حسابك النقدي بال﷼. +- المبلغ: 3,750 ﷼ (مثلاً). + +**السند الثاني — شراء الدولار**: + +- نوعه: قبض. +- الطرف الآخر: الصراف. +- الحساب المتأثر: حسابك النقدي بالدولار. +- المبلغ: 1,000 دولار (بسعر 3.75). + +النتيجة: رصيدك بال﷼ انخفض بـ3,750، ورصيدك بالدولار ارتفع بـ1,000. كل ﷼ من عملة واضح. + +## 4. عملات الذمم — التتبع بالعملة الأصلية + +إذا أقرضتَ شخصاً مبلغاً بالدولار، تُسجّل الذمة بالدولار. لا تُحوّله ل﷼ في وقت التسجيل — لأن السداد سيكون بالدولار (أو بأي عملة متفق عليها). + +تحويل الذمة لعملة أخرى عند التسجيل يُنشئ إشكالاً: عند السداد لاحقاً، سيتعين عليك "تحويل العائدة" مرة أخرى بسعر قد يكون مختلفاً. السجل يُصبح معقداً وغير دقيق. + +**القاعدة**: سجّل الذمة بالعملة الأصلية للاتفاق. + +## 5. تقارير بعملات متعددة + +إذا كانت لديك حسابات بعملات متعددة، تقارير الميزانية ستُظهر كل عملة منفصلة. الجمع بين العملات في تقرير واحد يتطلب تحويلاً صرفياً تُحدّده أنت — والنظام لا يُجريه تلقائياً. + +هذا يُعني: الميزانية الإجمالية المُوحَّدة لمن لديه عملات متعددة تستلزم عملاً إضافياً خارج النظام لجمع الأرقام بعملة رئيسية واحدة. + +## 6. العملة تُحدَّد عند إنشاء المعاملة وتبقى + +بعد تأكيد سند، عملته ثابتة لا تتغير. إذا أخطأتَ وأدخلتَ ريالاً بدلاً من دولار: تحتاج سند عكس وسند جديد بالعملة الصحيحة. + +لهذا السبب: دائماً تحقق من العملة قبل التأكيد. خاصة إذا كانت لديك حسابات بعملات متعددة. diff --git a/platform/resources/docs/08_advanced_accounting/03_transfer_policy_management.md b/platform/resources/docs/08_advanced_accounting/03_transfer_policy_management.md new file mode 100644 index 00000000..e9d897bf --- /dev/null +++ b/platform/resources/docs/08_advanced_accounting/03_transfer_policy_management.md @@ -0,0 +1,40 @@ +# إدارة سياسات التحويل + +## 1. ما هي سياسة التحويل؟ + +إذا كنت تستخدم نظام قيد كوسيط في تحويلات منتظمة، يمكنك ضبط "سياسات" تُحدّد: + +- من يمكنه إرسال طلبات تحويل إليك. +- ما المبالغ المقبولة. +- ما العملات التي تقبلها. +- ما الرسوم التي تُطبّقها. + +هذه السياسات تُنظّم نشاطك كوسيط بدلاً من التفاوض يدوياً على كل تحويل. + +## 2. متى تحتاج ضبط السياسات؟ + +إذا كنت تُجري تحويلاً أو اثنَيْن في السنة: لا تحتاج سياسة. التفاوض اليدوي كافٍ. + +إذا كنت تُجري عشرات التحويلات شهرياً وتتعامل مع مُرسِلين متعددين: السياسات توفّر وقتاً كبيراً وتُعطي مُرسِليك وضوحاً مسبقاً حول شروطك. + +## 3. الشروط الرئيسية في السياسة + +**الحد الأدنى والأقصى للمبلغ**: ترفض تلقائياً طلبات خارج هذا النطاق. + +**العملات المقبولة**: هل تقبل ريالاً فقط؟ أم دولاراً أيضاً؟ + +**الرسوم الثابتة أو النسبية**: رسوم ثابتة لكل تحويل أو نسبة مئوية من المبلغ. + +**وقت المعالجة**: كم يوم يستغرق التحويل عادةً. + +## 4. السياسة كاتفاقية معلنة + +الجميل في ضبط السياسة: هي اتفاقية معلنة يراها من يُريد التعامل معك. يعرف مسبقاً شروطك قبل إرسال طلب. هذا يقلل من سوء الفهم والنزاعات. + +## 5. تعديل السياسة عبر الزمن + +يمكن تعديل سياستك عند الحاجة. التعديل يُؤثّر على الطلبات المستقبلية فقط — طلبات قيد الإنجاز تسير بالشروط التي بدأت عليها. + +## 6. غياب السياسة — الوضع الافتراضي + +إذا لم تضبط أي سياسة، الوضع لا يمنع التحويلات — يعني ببساطة أنك تُفاوض يدوياً على كل تحويل. هذا مقبول للحجم المنخفض ومرهق للحجم العالي. diff --git a/platform/resources/docs/08_advanced_accounting/04_data_security.md b/platform/resources/docs/08_advanced_accounting/04_data_security.md new file mode 100644 index 00000000..78df01ba --- /dev/null +++ b/platform/resources/docs/08_advanced_accounting/04_data_security.md @@ -0,0 +1,73 @@ +# أمن البيانات — التشفير والسيادة المحلية + +## 1. ما معنى "محلي أولاً"؟ + +كل بياناتك — السندات، الحسابات، القيود، الأرصدة — مُخزَّنة على جهازك أنت. لا توجد نسخة منها على أي خادم خارجي. لا يملك أحد آخر — لا مطوّر النظام، ولا أي طرف ثالث — إمكانية الوصول إليها. + +هذا ليس ميزة في اللائحة التسويقية — إنه قيد بنيوي في هندسة النظام. لا توجد تقنياً قناة وصول لبياناتك إلا من خلال جهازك. + +## 2. التشفير — قاعدة البيانات مشفرة بالكامل + +تُستخدَم تقنية SQLCipher لتشفير ملف قاعدة البيانات على مستوى الصفحات بخوارزمية AES-256-CBC. + +ما هذا يعني عملياً: +- ملف قاعدة البيانات على جهازك غير قابل للقراءة من أي برنامج آخر. +- حتى لو حصل أحد على ملف قاعدة البيانات مباشرة، لا يستطيع قراءة محتواه بدون مفتاح التشفير. +- المفتاح مُشتَق من عبارتك التذكيرية (BIP-39) — وهي لا تُخزَّن في مكان آخر. + +## 3. العبارة التذكيرية — المفتاح الذي لا بديل له + +عند أول تثبيت للتطبيق، يُنشئ النظام عبارة تذكيرية (مجموعة كلمات بالمعيار BIP-39). هذه العبارة هي: + +- المصدر الذي تُشتق منه مفاتيح التشفير. +- الوسيلة الوحيدة لاستعادة بياناتك إذا فُقد الجهاز. +- المفتاح لبناء التواقيع الرقمية للسندات. + +**إذا فقدتَ عبارتك التذكيرية ولم تحتفظ بها، لا توجد استعادة**. النظام لا يملك آلية "نسيتُ كلمة المرور" لأن لا خادم مركزي يُخزّن مفتاحك. + +احتفظ بعبارتك التذكيرية مكتوبة في مكان آمن فيزيائي منفصل عن جهازك. + +## 4. التوقيع الرقمي — ما يجعل السندات غير قابلة للإنكار + +كل سند مُؤكَّد بين طرفَيْن يحمل: +- التوقيع الرقمي للمُرسِل (مشتق من مفتاحه الخاص). +- التوقيع الرقمي للمُستقبِل (مشتق من مفتاحه الخاص). +- المفتاح العام لكل طرف (للتحقق من التوقيع). + +هذان التوقيعان يُثبتان: "هذان الشخصان بالذات أقرّا بهذه المعاملة بالذات". رياضياً، لا يمكن لأي طرف إنكار توقيعه على سند موقَّع. + +## 5. حماية الوقت — منع التلاعب بالتاريخ + +النظام يُراقب باستمرار ساعة الجهاز. إذا لاحَظ تراجعاً كبيراً في الوقت (أكثر من 60 ثانية إلى الخلف)، يُطلق تحذيراً فورياً. + +هذه الآلية موجودة لأن: التسجيل بتاريخ مزوَّر خلفياً يُمكّن من إنشاء سندات "قبل" أحداث لاحقة — مما يُخلّ بتسلسل الأحداث وموثوقية الأدلة الزمنية. + +التاريخ في قيد ليس مجرد بيانات وصفية — إنه جزء من حجية الوثيقة. + +## 6. المسح الطارئ — سيادة في أحلك اللحظات + +يُتيح النظام "مسحاً طارئاً" — حذفاً فورياً لكل البيانات المحلية. هذه الميزة موجودة للحالات القصوى حين يكون الوصول الفيزيائي القسري للجهاز خطراً فعلياً. + +بعد المسح الطارئ: إذا كانت لديك نسخة احتياطية محمية بعبارتك التذكيرية، يمكن استعادة كل شيء. + +**تحذير**: المسح الطارئ لا رجعة فيه إذا لم تكن لديك نسخة احتياطية. + +## 7. المزامنة — متى تسافر البيانات وكيف؟ + +البيانات تبقى محلية. لكن حين تُرسل سنداً لطرف آخر يستخدم قيد: +- المعلومات تُرسَل مشفرة بمفتاحه العام (E2EE — تشفير من الطرف للطرف). +- الخادم المُوصِّل "أعمى" — يُحوّل الرسالة دون أن يستطيع قراءتها. +- الرسالة تُفتح فقط بمفتاح المُستقبِل الخاص. + +هذا يعني: حتى مزود البنية التحتية للمزامنة لا يطّلع على محتوى السندات. + +## 8. النسخة الاحتياطية — الواجب الذي لا يُغفَر تجاهله + +أُنشئ نسخة احتياطية منتظمة. حفظها في مكان غير جهازك (قرص صلب خارجي، أو موقع آمن آخر). الملف مُشفَّر بعبارتك التذكيرية. + +الجدول الزمني المُوصى به: +- نسخة شهرية على الأقل للمستخدم الاعتيادي. +- نسخة أسبوعية لمن يُجري معاملات يومية كثيرة. +- نسخة فورية بعد أي معاملة كبيرة وهامة. + +بياناتك لا تُنسَخ احتياطياً آلياً على السحابة — هذا القرار عائد لك أنت. السيادة تعني المسؤولية. diff --git a/platform/resources/docs/08_advanced_accounting/_category_.json b/platform/resources/docs/08_advanced_accounting/_category_.json new file mode 100644 index 00000000..c1cc381d --- /dev/null +++ b/platform/resources/docs/08_advanced_accounting/_category_.json @@ -0,0 +1,4 @@ +{ + "label": "المحاسبة المتقدمة", + "position": 8 +} diff --git a/platform/resources/docs/09_common_questions/00_mental_model_faq.md b/platform/resources/docs/09_common_questions/00_mental_model_faq.md new file mode 100644 index 00000000..da767179 --- /dev/null +++ b/platform/resources/docs/09_common_questions/00_mental_model_faq.md @@ -0,0 +1,126 @@ +# نموذج التفكير — الأسئلة الشائعة + +## 1. "النظام معقد جداً — لماذا لا يكون بسيطاً مثل تطبيق تتبع النفقات؟" + +تطبيقات تتبع النفقات تُجيب على سؤال واحد: "كم أنفقتُ؟" + +نظام قيد يُجيب على أسئلة أعمق: "كم أنفقتُ، من أين جاء المال، لمن يذهب، وكيف أثّر في ثروتي الإجمالية؟ وهل الأرقام التي أراها موثوقة رياضياً؟" + +هذا التعمق لا يمكن تحقيقه بتبسيط النظام أكثر مما هو. المحاسبة المزدوجة معقدة لأن الواقع المالي نفسه معقد — وأي تبسيط يُفقد الدقة. +*** + +## 2. "أخطأتُ في سند مؤكَّد ولا أستطيع تعديله — هذا غير منطقي!" + +المنطق عكسي تماماً: **لأن المنطق المحاسبي يُلزِم** بعدم التعديل. + +السند المؤكَّد قد يكون وصل للطرف الآخر، وقد يكون ولّد قيوداً في دفتر الأستاذ. تعديله بصمت يُغيّر سجلاً أُبلغ به طرف آخر أو بُنيت عليه تقارير. + +الحل: اسحب السند (إذا لم يُقبَل بعد) وأنشئ جديداً صحيحاً. أو أنشئ سند عكس. التصحيح يتم بالإضافة، لا بالمحو. +*** + +## 3. "لماذا لا أستطيع نقل حساب من تصنيف لآخر؟" + +لأن التصنيف يُحدّد معالجة الأرقام في التقارير. نقل حساب من "أصل" لـ"مصروف" يعني أن عشرات القيود التاريخية ستُعاد تفسيرها بشكل مختلف — وهذا يُزوّر معنى التاريخ المسجَّل. + +الحل الصحيح دائماً: أنشئ حساباً جديداً بالتصنيف الصحيح، وأرشف القديم بعد تصفيته. +*** + +## 4. "لماذا يوجد حسابان لكل معاملة مصروف ولا أرى الثاني؟" + +هذا هو "الجسر الآلي" في عمله. كل مصروف شخصي يُنشئ: +- سنداً رئيسياً باتجاه المتجر أو الجهة. +- سنداً داخلياً تلقائياً يُصنّف المصروف في حساباتك الداخلية. + +السند الثاني يبدو "خلفياً" لأن النظام يُنشئه تلقائياً دون أن تطلبه. كلاهما يظهر في قائمة السندات بالربط الواضح بينهما. +*** + +## 5. "رصيدي في التطبيق لا يتطابق مع رصيدي البنكي — لماذا؟" + +الأسباب المحتملة: + +- **معاملات غير مُسجَّلة**: هناك معاملات في البنك لم تُدخلها في النظام بعد. +- **تاريخ التسجيل مختلف عن تاريخ التنفيذ البنكي**: البنك يُحدث في وقت مختلف. +- **مسودات غير مُؤكَّدة**: بعض السندات لا تزال مسودات، والمسودات لا تُؤثّر على الأرصدة. +- **معاملات بعملة مختلفة**: إذا كانت بعض معاملاتك بعملة أخرى، المقارنة تحتاج لتحويل صرفي منفصل. + +المسار الصحيح: أجرِ مطابقة (تسوية) دورية بين كشف حسابك البنكي ورصيد حساب السيولة في قيد. +*** + +## 6. "أخطأتُ في تصنيف مركز التكلفة ولا يظهر في تقاريري بالشكل الصحيح" + +مراكز التكلفة والأبعاد يمكن تصحيحها على معاملات تاريخية (بخلاف السندات المحاسبية). ابحث عن المعاملات المُصنَّفة خطأً وعدّل ارتباطها بمراكز التكلفة. + +التصحيح يظهر في التقارير التحليلية فوراً، ولا يُؤثّر على أي رصيد محاسبي. +*** + +## 7. "السند أرسلتُه للطرف الآخر لكنه لم يظهر عنده — لماذا؟" + +تحقق من "شريط المزامنة" في أعلى الشاشة: +- هل تظهر حالة "فشل"؟ المزامنة لم تصل — تحتاج إنترنت وإعادة محاولة. +- هل لديك اتصال إنترنت؟ النظام محلي أولاً ولكن المزامنة تحتاج شبكة. +- هل الطرف الآخر لديه اتصال؟ المزامنة تُنجز حين يُفتح التطبيق عند الطرف الآخر أيضاً. + +السند موجود على جهازك بالتأكيد. المزامنة هي الناقل — وهي آلية منفصلة. +*** + +## 8. "ما الفرق بين الحساب المعطَّل والمُؤرشَف عملياً؟" + +| المعيار | معطَّل | مُؤرشَف | +|---------|--------|---------| +| يظهر في قوائم الاختيار | لا | لا | +| يظهر في التقارير | نعم (بيانات تاريخية) | نعم (بيانات تاريخية) | +| يمكن إعادة تفعيله | نعم | لا | +| الشعور المقصود | "نائم مؤقتاً" | "مُغلَق نهائياً" | +*** + +## 9. "ما معنى رصيد سالب في حساب مصروف؟" + +هذا يُشير لحالة نادرة: المبالغ الدائنة على هذا الحساب أكبر من المبالغ المدينة. قد يعني: +- استرداد مبالغ من هذا الحساب أكثر مما أُنفق. +- تصحيح خاطئ لسند ما جعل الدائن أكبر. +- تصنيف خاطئ لإيراد في حساب مصروف. + +تحقق من كشف الحساب التفصيلي لهذا الحساب لتفهم مصدر هذه الحالة. +*** + +## 10. "كيف أُصدّر بياناتي إذا أردتُ الخروج من النظام؟" + +التصدير متاح من قسم الإعدادات. يمكنك تصدير: +- التقارير كملفات قابلة للمشاركة. +- بيانات المعاملات في صيغ شائعة. + +بياناتك على جهازك ولا تحتاج "إذناً" لتصدير ما تملكه. هذه جزء من مبدأ السيادة المطلقة التي يُجسّدها النظام. +*** + +## 11. "أنا وسيط في تحويل ثلاثي — هل سيُؤثّر هذا على رصيدي الشخصي مع المُرسِل والمُستقبِل؟ وأين سيظهر التحويل؟" + +**إجابتان في آنٍ واحد:** + +**أولاً — الأرصدة**: لا تأثير على الحسابات الشخصية — هذا ضمان هيكلي في الكود. قيود التحويل الثلاثي تُسجَّل في **صندوقك النقدي الوسيط** حصراً. + +**ثانياً — المحادثات**: التحويل **لا يظهر في محادثتك مع المُرسِل ولا مع المُستقبِل**. بدلاً من ذلك، يظهر **في محادثة المُرسِل مع المُستقبِل مباشرة** — مع ذكر اسمك كـ"وسيط" على التحويل. + +مثال: علي طلب منك (محمد) أن تُرسل مالاً لبديع. بعد إنجاز التحويل: +- علي يفتح محادثته مع **بديع** → يرى التحويل هناك مع إشارة "عبر وسيط: محمد". +- بديع يفتح محادثته مع **علي** → يرى التحويل هناك مع إشارة "عبر وسيط: محمد". +- محمد يفتح محادثته مع علي → **لا يظهر التحويل هنا**. +- محمد يفتح محادثته مع بديع → **لا يظهر التحويل هنا أيضاً**. + +الحالة الوحيدة التي تتأثر فيها محادثاتك: إذا اخترتَ "التقديم" — أي دفعتَ من مالك لبديع قبل استلام المال من علي. في هذه الحالة، يظهر الدين في محادثتك الشخصية مع علي. + +← راجع: [عزل القيود المحاسبية في التحويل الثلاثي](../06_transfers_system/05_accounting_isolation.md) +*** + +## 12. "ما الفرق بين قيدَيْن متتاليَيْن ثاديَيْن وبين التحويل الثلاثي؟" + +القيدان المتتاليان المنفصلان (سند دفع ثم سند قبض منفصلَيْن): +- لا قفل شرطي — يمكن تأكيد الثاني قبل الأول. +- لا معرف مجموعة — لا رابط تقني بينهما. +- قد يُؤثّران على الحسابات الشخصية حسب كيفية إنشائهما. + +التحويل الثلاثي: +- القفل الشرطي يمنع تأكيد سند الدفع قبل سند القبض. +- معرف المجموعة يربطهما كوحدة واحدة مع الشفافية الثلاثية. +- القيود تمر عبر الصندوق النقدي الوسيط حصراً — لا أثر شخصياً. +- `linkedPartyId` يُخزّن الطرف الأصلي في كل سند للشفافية الكاملة. + diff --git a/platform/resources/docs/09_common_questions/01_common_mistakes.md b/platform/resources/docs/09_common_questions/01_common_mistakes.md new file mode 100644 index 00000000..1a11992d --- /dev/null +++ b/platform/resources/docs/09_common_questions/01_common_mistakes.md @@ -0,0 +1,93 @@ +# الأخطاء الشائعة وكيف تتجنبها + +## الخطأ الأول: إنشاء حساب بتصنيف خاطئ + +**الوصف**: إنشاء حساب "عميل X" تحت تصنيف "مصروفات" بدلاً من "ذمم دائنة (عليك)". + +**لماذا يحدث**: المستخدم يُختبر بالـ"ماذا أسمّيه" قبل "أين تصنيفه". + +**الأثر**: العميل X سيظهر في تقارير المصروفات — وكل فاتورة أرسلتَها له ستُحسب كمصروف لا كذمة. + +**التجنب**: قبل إنشاء أي حساب، اسأل: "ما طبيعة هذا الحساب اقتصادياً؟ هل هو طرف يُقرض/يُقرَض؟ أم أصل أملكه؟ أم مصروف أنفقه؟" + +**التصحيح**: أرشف الحساب الخاطئ (بعد تصفيته)، وأنشئ حساباً جديداً صحيحاً. +*** + +## الخطأ الثاني: التأكيد قبل المراجعة + +**الوصف**: تأكيد السند فوراً دون التحقق من الحساب المتأثر أو الطرف الآخر. + +**لماذا يحدث**: الرغبة في السرعة. + +**الأثر**: قيد محاسبي في الحساب الخاطئ لا يمكن تعديله مباشرة. يستلزم التصحيح سند عكسٍ وسنداً جديداً. + +**التجنب**: اجعل عادتك قراءة حقلَيْن قبل التأكيد: "الحساب المتأثر" و"الطرف الآخر". 5 ثوانٍ توفر دقيقتَيْن من التصحيح. +*** + +## الخطأ الثالث: استخدام تاريخ اليوم لمعاملات قديمة + +**الوصف**: تسجيل مصروف أمس أو الأسبوع الماضي بتاريخ اليوم. + +**لماذا يحدث**: القصور في الانتباه لحقل التاريخ. + +**الأثر**: التقارير الشهرية تُظهر الإنفاق في الشهر الخاطئ. ميزان مراجعة شهر العمل الفعلي لا يعكسه. + +**التجنب**: عادة جيدة: دائماً أول حقل تتحقق منه هو "التاريخ الاقتصادي". +*** + +## الخطأ الرابع: الخلط بين الجهة والتصنيف الداخلي + +**الوصف**: تسجيل "مصروف طعام" كـ"الطرف الآخر" بدلاً من جعله "الحساب المتأثر". + +**لماذا يحدث**: تشابه المفهومَيْن للمستخدم الجديد. + +**الأثر**: قيد مشوّه: طرف "مصروف طعام" (ليس كياناً حقيقياً) يصبح طرف المعاملة. + +**التجنب**: + +- "الطرف الآخر" = الجهة الخارجية (المتجر، الشخص، الشركة). +- "الحساب المتأثر" = تصنيفك الداخلي (غذاء، نقل، صحة). +*** + +## الخطأ الخامس: ترك المسودات بدون تأكيد ثم نسيانها + +**الوصف**: إنشاء سنداً، تركه مسودة، ونسيان تأكيده. + +**لماذا يحدث**: انشغال أو نية "إكماله لاحقاً". + +**الأثر**: الرصيد لا يعكس هذه المعاملة. بعد أشهر، قائمة مسودات مجهولة أو خاطئة. + +**التجنب**: إما أكمل وأكّد فوراً، أو احذف المسودة. "سأعود إليها لاحقاً" نادراً ما يحدث في تطبيقات المحاسبة. +*** + +## الخطأ السادس: عدم التحقق من شريط المزامنة بعد إرسال سند + +**الوصف**: إرسال سند لطرف آخر وافتراض وصوله دون التحقق. + +**لماذا يحدث**: عادة "أرسلتُ = وصل" من تطبيقات المراسلة. + +**الأثر**: الطرف الآخر لم يستلم السند. توقعاتك أنه سيتصرف بناءً عليه لن تتحقق. + +**التجنب**: دائماً تحقق من شريط المزامنة بعد الإرسال. إذا ظهرت حالة "فشل"، أعد المحاولة. +*** + +## الخطأ السابع: إهمال ضبط الأبعاد الافتراضية للحسابات المتكررة + +**الوصف**: عدم ضبط أبعاد مراكز التكلفة الافتراضية على الحسابات التي تستخدمها يومياً. + +**لماذا يحدث**: يبدو مجهوداً إضافياً في البداية. + +**الأثر**: 300 معاملة في السنة كلها "غير مُصنَّفة" — تقارير تحليلية فارغة. + +**التجنب**: خصص 30 دقيقة في الشهر الأول لضبط الأبعاد الافتراضية لأكثر 10 حسابات استخداماً. هذه الـ30 دقيقة توفر ساعات من التصنيف اليدوي لاحقاً. +*** + +## الخطأ الثامن: تجاهل عبارة "مسودة" في القيود + +**الوصف**: الاعتقاد بأن رؤية السند في القائمة تعني أثره مُسجَّل في الحسابات. + +**لماذا يحدث**: بعض التطبيقات تُسجّل فوراً دون تمييز. + +**الأثر**: تصديق أرقام التقارير رغم أنها لا تعكس مسودات قائمة. + +**التجنب**: قاعدة ذهبية: "التقارير لا تعرف المسودات". إذا أردتَ رصيداً دقيقاً، أكّد أولاً. diff --git a/platform/resources/docs/09_common_questions/02_troubleshooting.md b/platform/resources/docs/09_common_questions/02_troubleshooting.md new file mode 100644 index 00000000..677035b0 --- /dev/null +++ b/platform/resources/docs/09_common_questions/02_troubleshooting.md @@ -0,0 +1,93 @@ +# استكشاف الأخطاء وإصلاحها + +## 1. لا يمكنني تأكيد السند — رسالة الخطأ تقول "مبلغ غير صالح" + +**السبب الأكثر شيوعاً**: المبلغ يساوي صفر، أو سالب، أو تم إدخال المبلغ بشكل غير صحيح. + +**الحل**: +- تأكد أن المبلغ موجب ويعكس قيمة حقيقية. +- تحقق أنك لا تُحاول إنشاء معاملة بين نفس الحساب كطرفَيْن. +- تأكد أن العملة واحدة للطرفَيْن. +*** + +## 2. التطبيق يرفض أرشفة حساب وأنا أعلم أنني لا أحتاجه + +**السبب الأكثر شيوعاً**: الحساب له رصيد غير صفري، أو له حسابات فرعية تحته، أو هو حساب افتراضي محمي. + +**الحل**: +- استعرض كشف الحساب وتأكد أن رصيده صفر. +- تحقق من وجود حسابات فرعية: يجب أرشفتها أو نقلها أولاً. +- إذا كان الحساب افتراضياً: لا سبيل للأرشفة، الأرشفة غير متاحة حمايةً للنظام. +*** + +## 3. سند أرسلتُه لا يظهر عند الطرف الآخر + +**الخطوات**: +1. تحقق من شريط المزامنة — هل تظهر رسالة "فشل" أو "جارٍ"؟ +2. تحقق من اتصال الإنترنت لجهازك. +3. اطلب من الطرف الآخر التحقق من اتصاله وفتح التطبيق. +4. إذا استمرت المشكلة: اذهب لإعدادات المزامنة وابحث عن "إعادة إرسال المعلق". +*** + +## 4. رصيدي لا يتطابق مع توقعاتي + +**الأسئلة التشخيصية**: +- هل هناك مسودات لم تُؤكَّد؟ (اعرض فقط المسودات وتحقق). +- هل استعملتَ تاريخ اليوم لمعاملات قديمة؟ (تحقق من توزيع المعاملات زمنياً). +- هل الفترة المختارة في التقرير صحيحة؟ (تأكد من نطاق التاريخ). +- هل هناك سندات بعملات مختلفة تُؤثّر على حساب بعملة واحدة؟ +*** + +## 5. التطبيق يُنبّهني بتلاعب في الساعة + +**هذا تحذير أمني**. السبب: +- تراجعت ساعة جهازك بأكثر من 60 ثانية عما كانت عليه عند آخر استخدام. + +**الحل الأول**: إذا لم تتلاعب بالساعة، قد يكون تعديل NTP شبكي كبير غير معتاد. أعِد ضبط الوقت من الشبكة وافتح التطبيق مجدداً. + +**الحل الثاني**: إذا حاولتَ فعلاً يدوياً تغيير الوقت لأي سبب، اعلم أن التطبيق يكشف هذا دائماً. اعد التوقيت لوضعه الصحيح. +*** + +## 6. التقارير لا تُظهر معاملات أعلم أنني سجّلتُها + +**الأسئلة التشخيصية**: +- هل هذه المعاملات مؤكَّدة أم مسودات؟ (التقارير تعرض المؤكَّدة فقط). +- هل فترة التقرير تغطي تاريخ هذه المعاملات؟ (تحقق من نطاق التاريخ المختار). +- هل تُنظر لحساب معين أو للكل؟ (إذا كانت التصفية بحساب معين، قد المعاملة في حساب آخر). +*** + +## 7. لا أستطيع سحب سند مؤكَّد + +**الأسباب الممكنة**: +- الطرف الآخر قبل السند بالفعل → السحب الأحادي مُحظَر. السند أصبح الآن ثنائياً. +- السند ضمن تحويل ثلاثي وله قيود مترابطة. + +**الحل**: إذا قبل الطرف الآخر: تواصل معه لإلغاء السند باتفاق ثنائي، أو أنشئ سند عكس. +*** + +## 8. النظام يُبلّغني باستحالة الكتابة (governance blocked) + +**المعنى**: حالة حوكمة نظامك لا تسمح بالكتابة الآن. + +**الأسباب الممكنة**: +- انتهى الترخيص ولم يُجدَّد. +- الحساب في حالة تعليق إداري. + +**الحل**: اذهب لإعدادات الترخيص وتحقق من حالة حوكمتك. القراءة لا تزال متاحة — يمكنك استعراض بياناتك ريثما تحل مشكلة الترخيص. +*** + +## 9. أريد تحديث التطبيق لكنني أخشى فقدان البيانات + +**جيد**: التحديثات لا تمسّ قاعدة البيانات المحلية. بياناتك محفوظة على جهازك ولا تُحذَف بالتحديث. + +التحديثات تُضاف عليها بالتدريج. كل إصدار يتضمن هجرة الإصدار السابق إذا احتاجت قاعدة البيانات تحديثاً في بنيتها. +*** + +## 10. أريد نقل بياناتي لجهاز جديد + +**المسار الصحيح**: +1. أنشئ نسخة احتياطية من جهازك القديم (من إعدادات النسخ الاحتياطي). +2. ثبّت التطبيق على الجهاز الجديد. +3. استعادة النسخة الاحتياطية من الجهاز القديم. + +**تحذير حاسم**: ستحتاج عبارتك التذكيرية لفك تشفير النسخة الاحتياطية. إذا لم تحتفظ بها، النسخة بلا فائدة. diff --git a/platform/resources/docs/09_common_questions/_category_.json b/platform/resources/docs/09_common_questions/_category_.json new file mode 100644 index 00000000..63d9b8eb --- /dev/null +++ b/platform/resources/docs/09_common_questions/_category_.json @@ -0,0 +1,4 @@ +{ + "label": "الأسئلة الشائعة", + "position": 9 +} diff --git a/platform/resources/docs/10_migration_tool.mdx b/platform/resources/docs/10_migration_tool.mdx new file mode 100644 index 00000000..ccc19e2b --- /dev/null +++ b/platform/resources/docs/10_migration_tool.mdx @@ -0,0 +1,109 @@ +--- +sidebar_position: 10 +title: أداة الهجرة والتحويل +--- + +import MigrationTool from "@site/src/components/MigrationTool"; + +# وحدة استيراد البيانات من الأنظمة القديمة + +تتيح هذه الأداة نقل بياناتك من أنظمة المحاسبة القديمة (المبنية على SQLite) إلى نظام **قيد** بشكل آمن وكامل — دون الحاجة إلى الإنترنت ودون إرسال أي بيانات لخادم خارجي. + + + +--- + +## كيف تعمل الأداة؟ + +تمرّ عملية الاستيراد بأربع مراحل متتالية: + +``` +ملف .db → تحليل وتحويل → حزمة JSON → استيراد في التطبيق → مراجعة وتأكيد +``` + +### المرحلة ١ — رفع الملف وتحليله + +ترفع ملف قاعدة البيانات (`.db`) من نظامك القديم. تقرأ الأداة الهيكل تلقائياً وتحدد نوعه: + +- **الهيكل الأساسي** — يعتمد على جدولَي `customers` و`transactions`. +- **الهيكل المتقدم** — يعتمد على جدول `doc_hdr` الذي يحتوي على معلومات إضافية كالصناديق والحالة. + +### المرحلة ٢ — تحويل البيانات + +تستخرج الأداة البيانات التالية وتحوّلها إلى صيغة قيد الموحدة: + +| البيانات | المصدر | التحويل | +| --------------- | ----------------------- | ------------------------------------- | +| العملات | جدول `currency` | تحديد الكود الدولي (SAR, YER, USD...) | +| المجموعات | جدول `groups` | تصنيف الحسابات | +| الحسابات | جدول `customers` | أطراف (parties) | +| الحركات العادية | `transactions.in = 1/0` | سندات قبض / صرف | +| التحويلات | `transactions.t_cus_id` | سندان (قبض + صرف) عبر الصندوق | + +### المرحلة ٣ — تحميل الحزمة (JSON v2.0) + +تنتج الأداة ملف JSON منظّماً يحتوي على جميع البيانات المحوّلة. هذا الملف هو **الوسيط** بين نظامك القديم وتطبيق قيد. + +### المرحلة ٤ — الاستيراد في التطبيق + +يعالج تطبيق قيد الحزمة عبر ثلاث مراحل فرعية: + +1. **فرز الحسابات** — يقارن كل حساب قديم بالحسابات الموجودة في قيد (بالاسم والهاتف). +2. **حسم التعارضات** — لكل حساب مكرر تختار: **دمج** أو **إنشاء جديد** أو **تخطي**. +3. **استيراد السندات** — تُنشأ السندات في حالة **انتظار** (مسودة) لمراجعتها وتأكيدها. + +--- + +## تحويل العملات + +تتعرف الأداة على الأسماء العربية والإنجليزية للعملات الشائعة وتحوّلها تلقائياً: + +| الاسم القديم | الكود | الملاحظة | +| ------------- | ----- | ------------------------- | +| سعودي، ﷼ | SAR | | +| محلي، يمني | YER | الافتراضي للأنظمة اليمنية | +| دولار، امريكي | USD | | +| مصري، جنيه | EGP | | +| درهم، إماراتي | AED | | +| كويتي | KWD | | +| قطري | QAR | | + +> إذا لم تكن العملة موجودة في قيد، يُضيفها النظام تلقائياً عند الاستيراد. + +--- + +## حركات التحويل بين الحسابات + +عندما يحتوي سجل المعاملة على حقل `t_cus_id` (طرف ثانٍ للتحويل)، تعامله الأداة كـ**تحويل** ولا تعامله كقبض أو صرف عادي. + +في تطبيق قيد يُترجَم التحويل إلى **سندَّين مترابطين** يمرّان عبر الصندوق: + +``` +الطرف الأول (cus_id) → [سند قبض → الصندوق] → [سند صرف → الصندوق] → الطرف الثاني (t_cus_id) +``` + +كلا السندين يبقى في **حالة انتظار** حتى يعتمدهما صاحب الصندوق. + +--- + +## مراجعة التعارضات في التطبيق + +عند استيراد الحزمة في تطبيق قيد، تظهر شاشة **حسم التعارضات** لكل حساب: + +| الحالة | المعنى | الخيارات المتاحة | +| ------------- | ---------------------- | ----------------------- | +| ✅ تطابق تام | حساب بنفس الاسم موجود | دمج / إنشاء جديد / تخطي | +| 🔶 تطابق جزئي | حساب بنفس الهاتف موجود | دمج / إنشاء جديد / تخطي | +| ➕ جديد | لا يوجد حساب مطابق | يُنشأ تلقائياً | + +بعد حسم التعارضات، تظهر جميع السندات المستوردة في قائمة **انتظار الاعتماد** ليراجعها صاحب الحساب ويوقّعها. + +--- + +## الخطوات بعد تحميل الحزمة + +1. افتح تطبيق **قيد** على هاتفك. +2. اذهب إلى **الإعدادات ← استيراد بيانات**. +3. اختر ملف JSON الذي تم تحميله. +4. راجع الحسابات وحسم التعارضات. +5. اعتمد السندات المستوردة من قائمة الانتظار. diff --git a/platform/resources/docs/11_seo_audit/00_executive_summary.md b/platform/resources/docs/11_seo_audit/00_executive_summary.md new file mode 100644 index 00000000..a348728c --- /dev/null +++ b/platform/resources/docs/11_seo_audit/00_executive_summary.md @@ -0,0 +1,70 @@ +# تقرير التدقيق الشامل: الرؤية في محركات البحث وهيمنة السوق + +## ملخص تنفيذي — qayd.accsystemerp.com + +**تاريخ التدقيق:** يونيو 2026 +**المُدقِّق:** فريق متخصص في هندسة البحث، وتحليل السوق، والمعلومات التنافسية +**الموقع المُدقَّق:** [accsystemerp/](https://qayd.accsystemerp.com/) +**الصناعة:** تطبيقات المحاسبة الشخصية — Local-First + E2EE + القيد المزدوج +**الأسواق المستهدفة:** منطقة MENA (السعودية، الإمارات، مصر، الكويت) — العربية والإنجليزية + +--- + +## الحكم الرئيسي + +> **قيد يمتلك منتجاً استثنائياً لا مثيل له في السوق العربية — لكنه شبه غير مرئي لمحركات البحث.** + +الموقع **غير مُفهرَس عملياً** على جوجل. لا يظهر عند البحث عن `site:qayd.accsystemerp.com`. لا يوجد sitemap. لا يوجد schema markup. الدومين مُستضاف على نطاق فرعي لـ `accsystemerp.com` يفتقر إلى أي سلطة. تقنية SPA (Inertia.js) تُصيّر المحتوى من JavaScript بدون SSR، مما يُضعف قدرة Googlebot على الفهرسة. + +في المقابل، المنافسون (Wafeq، Daftra، Ala-Hasba) يمتلكون مئات المقالات، آلاف الروابط الخلفية، وسنوات من التراكم في سلطة المجال — بينما قيد يبدأ من الصفر تقريباً. + +--- + +## تشخيص الرؤية + +| المشكلة الجذرية | الخطورة | الثقة | +| --- | --- | --- | +| شبه انعدام الفهرسة (لا يظهر site: query) | حرجة | 97% | +| غياب Sitemap.xml | حرجة | مؤكدة | +| غياب JSON-LD Schema | عالية | مؤكدة | +| لا محتوى مُحسَّن للكلمات المفتاحية | حرجة | مؤكدة | +| الدومين الفرعي بلا سلطة (DA ≈ 0) | حرجة | 90% | +| SPA بدون SSR تضعف الزحف | عالية | 95% | +| غياب محتوى المدونة/التسويق | عالية | مؤكدة | +| لا بيانات منظمة للكيانات | عالية | مؤكدة | + +--- + +## الفرصة الاستراتيجية + +قيد يشغل **فراغاً حقيقياً لا منافس له** في السوق العربية: + +- لا يوجد تطبيق محاسبة عربي يجمع: Local-First + E2EE + قيد مزدوج كامل + وساطة ثنائية +- السوق السعودي للبرمجيات المالية الشخصية: **$11.7 مليون (2024) → $17.5 مليون (2033)** +- السوق العالمي لتطبيقات المالية الشخصية: **$25.8 مليار (2024) → $202 مليار (2035)** +- الطلب على تطبيقات E2EE Local-First آخذ في الارتفاع (موجة ما بعد كامبريدج أناليتيكا، تشريعات حماية البيانات PDPL السعودي) + +**المشكلة الوحيدة: لا يستطيع أحد إيجاد قيد.** + +--- + +## أولويات العمل (ملخص) + +### حرجة — تمنع الرؤية اليوم + +1. نقل الدومين إلى `qayd.app` أو `qayd.io` أو `getqayd.com` +2. تطبيق SSR (Server-Side Rendering) أو SSG لصفحات التسويق +3. إنشاء وتسجيل `sitemap.xml` +4. إضافة JSON-LD Schema (SoftwareApplication + Organization + FAQPage) + +### عالية التأثير — نمو كبير + +1. استراتيجية محتوى: 50+ مقالة عربية تستهدف الكلمات ذات القيمة التجارية +2. صفحات Landing مُحسَّنة لكل كلمة مفتاحية رئيسية +3. بناء سلطة الكيانات (Google Knowledge Graph) + +### استراتيجية — هيمنة طويلة الأمد + +1. استراتيجية روابط خلفية (Backlinks) عبر محتوى مرجعي +2. صفحات مقارنة تنافسية +3. تحسين الرؤية في أدوات البحث بالذكاء الاصطناعي (Perplexity، Gemini، ChatGPT) diff --git a/platform/resources/docs/11_seo_audit/01_phase0_indexation_diagnosis.md b/platform/resources/docs/11_seo_audit/01_phase0_indexation_diagnosis.md new file mode 100644 index 00000000..3967a6e2 --- /dev/null +++ b/platform/resources/docs/11_seo_audit/01_phase0_indexation_diagnosis.md @@ -0,0 +1,154 @@ +# المرحلة 0 — تشخيص الفهرسة والاكتشاف + +## النتيجة الأولى والأكثر أهمية + +**البحث عن `site:qayd.accsystemerp.com` لا يُعيد أي نتيجة.** + +هذا يعني أحد أمرين (أو كليهما): + +1. الموقع غير مُفهرَس أصلاً في جوجل. +2. الموقع مُفهرَس بعدد ضئيل جداً من الصفحات لا يظهر في النتائج العامة. + +في كلتا الحالتين، **يعاني قيد من مشكلة فهرسة، وليس فقط مشكلة ترتيب.** + +الفرق جوهري: مشكلة الترتيب تعني "الموقع مفهرَس لكن في الصفحة الخامسة". مشكلة الفهرسة تعني "الموقع غير موجود في جوجل أصلاً". + +--- + +## دليل 1 — غياب Sitemap.xml + +**الحالة:** لا يوجد ملف `sitemap.xml` في الدومين. +**الدليل:** البحث في الكود المصدري، `public/` directory، وملفات التوجيه لا يُظهر أي مولّد sitemap. +**الخطورة:** حرجة +**الثقة:** 100% (مؤكد من الكود المصدري) + +**التأثير:** بدون sitemap، يعتمد Googlebot على: + +- الروابط الخلفية للوصول إلى الموقع +- اكتشاف الصفحات عبر الـ crawl العشوائي + +الموقع لديه 49+ صفحة توثيق + 10 صفحات تسويقية + صفحات قانونية = **~65 صفحة قابلة للفهرسة** لن يعرفها جوجل. + +**الحل:** إضافة حزمة `spatie/laravel-sitemap` وتوليد sitemap ديناميكي يشمل كل المسارات العامة. + +--- + +## دليل 2 — robots.txt مُسرِّف في الإذن، لكن غير مُفيد + +**الحالة الحالية:** + +```txt +User-agent: * +Disallow: +``` + +**التحليل:** + +- السطر `Disallow:` (فارغ) يعني "لا تحجب شيئاً" — وهذا صحيح. +- لكن robots.txt المثالي يجب أن: + 1. يُشير إلى `sitemap.xml` + 2. يحجب صراحةً مسارات الـ admin والـ API + +**الملاحظات الحرجة:** + +- مسار `/admin/*` ليس محجوباً في robots.txt (رغم أنه محمي بـ middleware) +- مسار `/api/*` ليس محجوباً +- لا يوجد سطر `Sitemap: https://qayd.accsystemerp.com/sitemap.xml` + +**robots.txt المثالي:** + +```txt +User-agent: * +Disallow: /admin/ +Disallow: /api/ +Disallow: /login +Disallow: /logout +Disallow: /verify-email/ +Disallow: /reset-password/ + +Sitemap: https://qayd.accsystemerp.com/sitemap.xml +``` + +**الخطورة:** متوسطة +**الثقة:** 100% + +--- + +## دليل 3 — تقنية SPA (Inertia.js) بدون SSR + +**الحالة:** الموقع مبني بـ React + Inertia.js. الصفحات تُصيَّر عبر JavaScript في المتصفح. + +**التحليل التقني:** + +عندما يزور Googlebot الصفحة الرئيسية، يرى HTML أولياً كهذا: + +```html +
+``` + +ثم يحتاج لتنفيذ JavaScript لعرض المحتوى الفعلي. + +**المشكلة:** Googlebot يُنفّذ JavaScript، لكن: + +1. التنفيذ يحدث في وقت لاحق ("second wave crawl") — يتأخر التفهرس أسابيع +2. المحتوى الديناميكي المحمَّل من قاعدة البيانات قد لا يُعرَض بالكامل +3. ميزات التفاعل (hover، animations) لا تُنفَّذ + +**الأكثر خطورة:** محتوى الصفحة الرئيسية يُحمَّل من `LandingPageContent` model في قاعدة البيانات. إذا تأخر تحميل هذا المحتوى، قد يُفهرَس Googlebot صفحة فارغة. + +**الدليل:** + +```tsx +// Home.tsx - المحتوى يأتي من props +const hero = props.hero; // قد يكون null +``` + +**الحل:** + +- SSR كامل عبر `inertia-laravel` مع `@inertiajs/react` SSR adapter +- أو: تحويل الصفحات التسويقية إلى صفحات Blade ثابتة مع Vite + +**الخطورة:** عالية +**الثقة:** 95% + +--- + +## دليل 4 — الدومين الفرعي وأثره على السلطة + +**الدومين الحالي:** `qayd.accsystemerp.com` + +**المشكلة الجذرية:** + +- `accsystemerp.com` هو الدومين الرئيسي لشركة ACCSYSTEM +- الدومين الفرعي `qayd.` يُعامَل من جوجل كموقع **مستقل** بسلطة صفر +- كل روابط خلفية تذهب إلى `accsystemerp.com` لا تنتقل إلى `qayd.accsystemerp.com` + +**مقارنة بالمنافسين:** + +| المنافس | الدومين | سنوات الدومين (تقريبي) | مزايا | +| --- | --- | --- | --- | +| Wafeq | `wafeq.com` | ~6 سنوات | دومين مستقل، Series A $7.5M | +| Daftra | `daftra.com` | ~10 سنوات | دومين مستقل، محتوى ضخم | +| Ala-Hasba | `alahasba.com` | ~5 سنوات | دومين مستقل | +| **قيد** | `qayd.accsystemerp.com` | **غير معروف** | **دومين فرعي بلا سلطة** | + +**التوصية:** الانتقال إلى دومين مستقل مثل `qayd.app` أو `qayd.io` أو `getqayd.com` كأولوية قصوى. + +**الخطورة:** حرجة +**الثقة:** 92% + +--- + +## تصنيف نوع المشكلة + +بناءً على الأدلة: + +```txt +✗ مشكلة ترتيب (Ranking Problem) — جزئياً +✓ مشكلة فهرسة (Indexation Problem) — المشكلة الأساسية +✓ مشكلة قابلية الزحف (Crawlability) — بسبب SPA +✗ مشكلة سلطة (Authority Problem) — عامل مساهم +✓ مشكلة محتوى (Content Problem) — عامل حرج +``` + +**الموقع لا يحتاج أولاً إلى تحسين ترتيبه — بل يحتاج إلى أن يكون موجوداً في جوجل.** diff --git a/platform/resources/docs/11_seo_audit/02_phase1_technical_seo.md b/platform/resources/docs/11_seo_audit/02_phase1_technical_seo.md new file mode 100644 index 00000000..02792fe8 --- /dev/null +++ b/platform/resources/docs/11_seo_audit/02_phase1_technical_seo.md @@ -0,0 +1,215 @@ +# المرحلة 1 — تحليل الاكتشاف التقني لمحركات البحث + +## 1.1 ملف robots.txt + +| العنصر | الحالة | التقييم | +| --- | --- | --- | +| الوجود | موجود | ✓ | +| حجب /admin/ | غير محجوب | ✗ | +| حجب /api/ | غير محجوب | ✗ | +| الإشارة إلى sitemap | غائبة | ✗ | +| الحجب الزائد | لا | ✓ | + +**الخطورة الإجمالية:** متوسطة +**ملاحظة:** غياب حجب `/admin/` لا يُشكّل خطراً أمنياً (المحتوى محمي بـ middleware)، لكنه يهدر زحف الـ crawl budget على صفحات لا قيمة لفهرستها. + +--- + +## 1.2 ملف Sitemap.xml + +**الحالة:** غائب تماماً. + +**الصفحات التي يجب أن يشملها الـ sitemap:** + +```txt +/ — الرئيسية +/pillars — الأعمدة التقنية +/services — الخدمات المؤسسية +/about — من نحن +/pricing — الأسعار +/contact — تواصل معنا +/faq — الأسئلة الشائعة +/privacy-policy — سياسة الخصوصية +/terms-of-use — شروط الاستخدام +/docs/ — التوثيق (الرئيسية) +/docs/00_introduction/... — 49+ صفحة توثيق +``` + +**الإجمالي المقدَّر:** ~65 URL قابلة للفهرسة + +**التوصية:** تثبيت `spatie/laravel-sitemap` وتوليد sitemap ديناميكي. يجب إضافة المسارات التالية يدوياً (لأنها ليست في نموذج eloquent): + +```php +// في SitemapController أو scheduled command +Sitemap::create() + ->add(Url::create('/')) + ->add(Url::create('/pillars')) + ->add(Url::create('/services')) + ->add(Url::create('/about')) + ->add(Url::create('/pricing')) + ->add(Url::create('/contact')) + ->add(Url::create('/faq')) + // + كل صفحات /docs/ عبر DocsController::getDocsList() + ->writeToFile(public_path('sitemap.xml')); +``` + +**الخطورة:** حرجة +**التأثير المتوقع على الفهرسة:** عالي جداً + +--- + +## 1.3 العلامات Canonical + +**الحالة:** لا توجد علامات canonical صريحة في الكود. + +**الخطورة:** متوسطة +**التفسير:** حالياً الموقع بسيط بما يكفي لعدم وجود تعارضات canonical خطيرة، لكن مع نمو المحتوى ستصبح ضرورية. + +**التوصية:** إضافة canonical tag افتراضي في `PublicLayout.tsx` يشير إلى الـ URL الحالي. + +--- + +## 1.4 بنية إعادة التوجيه (Redirect Architecture) + +**الحالة الحالية:** + +- لا توجد redirects ظاهرة في `routes/web.php` +- كل مسار يُعيد Inertia response مباشرة + +**المخاطر المحتملة:** + +- `http://` vs `https://` redirect (يجب إجباره على مستوى الخادم) +- `www.` vs non-www (لا ينطبق على نطاق فرعي) +- Trailing slash consistency (غير مُعرَّف صراحةً) + +**الخطورة:** منخفضة (افتراض أن الاستضافة تُطبّق HTTPS redirect) + +--- + +## 1.5 عمق الزحف (Crawl Depth) + +**بنية التنقل الحالية:** + +```txt +الرئيسية (/) +├── /pillars +├── /services +├── /about +├── /pricing +├── /contact +├── /faq +└── /docs/ + └── [49 صفحة على عمق 2-3] +``` + +**التقييم:** البنية ضحلة وصحية — لا صفحات يتيمة ظاهرة في التنقل الرئيسي. + +**المخاطر:** صفحات التوثيق قد تكون يتيمة إذا كان التنقل الداخلي في الـ sidebar يعتمد على JavaScript فقط بدون روابط HTML قابلة للزحف. + +**الخطورة:** متوسطة +**التوصية:** التأكد من أن روابط sidebar التوثيق هي `` حقيقية وليست event handlers فقط. + +--- + +## 1.6 تنفيذ JavaScript وتصيير SPA + +هذا أكثر مشكلة تقنية تأثيراً على الفهرسة في الموقع. + +### الهيكل الحالي + +```txt +Laravel → Inertia.js → React (Client-Side Rendering) +``` + +### كيف يرى Googlebot الصفحة + +**الطلب الأول (HTML):** + +```html + + + + QaydAPI + + + + +
+ + +``` + +المحتوى المرئي في HTML الأولي = **صفر**. + +**بعد تنفيذ JavaScript:** يظهر المحتوى الكامل. + +### مشكلة إضافية: `dir="ltr"` في HTML للموقع العربي + +```html + +``` + +الموقع عربي بالكامل تقريباً، لكن `dir` مضبوطة على `ltr` (اليسار لليمين). هذا خطأ صريح يُربك: + +- محركات البحث في فهم اتجاه اللغة +- المتصفح في عرض النصوص العربية +- أدوات تحسين إمكانية الوصول + +**الحل الفوري:** + +```html + +``` + +**الخطورة:** عالية (خطأ html lang + dir معاً) +**الثقة:** 100% (مؤكد من الكود) + +--- + +## 1.7 ملاحظات الأداء التقني + +### وزن JavaScript + +التطبيق يعتمد على حزمة Vite + React كاملة في الصفحات التسويقية. يُتوقع أن حجم الـ JavaScript bundle > 200KB (غير مضغوط)، مما يُبطّئ **First Contentful Paint (FCP)** و**Largest Contentful Paint (LCP)**. + +### خطوط Google Fonts + +```html + + + +``` + +تحميل 6 أوزان من Cairo قد يُضيف 150-300ms على الـ TTFB الفعلي للمستخدم. + +**التوصية:** + +- إضافة `font-display: swap` +- تحديد الأوزان المستخدمة فعلياً (غالباً 400، 600، 700 كافية) +- النظر في self-hosting الخط + +### تقدير Core Web Vitals + +| المقياس | التقدير | سبب التقدير | +| --- | --- | --- | +| LCP | بطيء (>2.5s) | SPA + external fonts + بدون SSR | +| CLS | جيد | بنية ثابتة معروفة | +| INP | جيد | تطبيق نظيف بدون تفاعل ثقيل | +| TTFB | مقبول-جيد | Laravel server response | + +**الخطورة الإجمالية للأداء:** متوسطة-عالية للـ SEO، عالية لتجربة المستخدم + +--- + +## 1.8 ملخص المرحلة الأولى + +| المكوّن | الحالة | الأولوية | +| --- | --- | --- | +| robots.txt | موجود لكن ناقص | متوسطة | +| sitemap.xml | **غائب** | **حرجة** | +| Canonical tags | غائبة | متوسطة | +| HTML lang/dir | **خاطئ (ltr لموقع عربي)** | **عالية** | +| SSR/SSG | **غائب** | **عالية** | +| Crawl depth | جيد | منخفضة | +| Core Web Vitals | تقدير ضعيف | متوسطة | +| خطوط خارجية | تحتاج تحسين | منخفضة | diff --git a/platform/resources/docs/11_seo_audit/03_phase2_indexation.md b/platform/resources/docs/11_seo_audit/03_phase2_indexation.md new file mode 100644 index 00000000..91855f49 --- /dev/null +++ b/platform/resources/docs/11_seo_audit/03_phase2_indexation.md @@ -0,0 +1,100 @@ +# المرحلة 2 — تحقيق الفهرسة + +## 2.1 تقدير معدل الفهرسة الحالي + +**تقدير عدد الصفحات المفهرَسة:** 0–3 صفحات +**النسبة المئوية:** أقل من 5% +**الثقة:** 90% + +**الأدلة الداعمة:** + +- `site:qayd.accsystemerp.com` لا يُعيد نتائج في البحث +- لا يوجد sitemap.xml +- SPA بدون SSR +- الدومين الفرعي بدون روابط خلفية تُوجّه الزاحف +- تحقق جوجل موجود (`public/ggl/google1ba3cc4c115ac1d9.html`) — وهذا يعني أن Search Console مُفعَّل، لكن لم تتم إضافة sitemap + +--- + +## 2.2 الصفحات وقابليتها للفهرسة + +| الصفحة | القابلية للفهرسة | عوائق الفهرسة | +| --- | --- | --- | +| `/` | متوسطة | SPA، محتوى من DB | +| `/pillars` | متوسطة | SPA، محتوى من DB | +| `/services` | متوسطة | SPA، محتوى من DB | +| `/about` | متوسطة | SPA، محتوى من DB | +| `/pricing` | متوسطة | SPA، محتوى من DB | +| `/contact` | منخفضة | لا قيمة SEO | +| `/docs/*` (49 صفحة) | منخفضة-متوسطة | SPA، روابط sidebar قد تكون JS | +| `/faq` | متوسطة | محتوى من DB (AppDocument) | +| `/privacy-policy` | منخفضة | قيمة SEO محدودة | +| `/terms-of-use` | منخفضة | قيمة SEO محدودة | + +--- + +## 2.3 مشاكل المحتوى المكرر + +**الحالة:** منخفضة المخاطر حالياً +**التفسير:** الموقع صغير بما يكفي لعدم وجود تكرار خطير. + +**مخاطر محتملة مستقبلاً:** + +- صفحات التوثيق قد تحتوي على مقاطع متكررة (الإدخالات المشتركة) +- URL parameters في الـ docs routing قد تُولّد نسخاً مكررة + +--- + +## 2.4 الصفحات التي لن تُصنَّف + +**صفحات بلا قيمة SEO يجب حجبها في robots.txt:** + +```txt +/admin/* — لوحة الإدارة (محمية بمصادقة) +/api/* — نقاط API +/login — صفحة تسجيل الدخول +/logout — عملية تسجيل الخروج +/verify-email/* — مسارات التحقق +/reset-password/* — مسارات إعادة الضبط +``` + +--- + +## 2.5 ميزانية الزحف (Crawl Budget) + +**التقدير الحالي:** الموقع لا يستفيد من crawl budget لأنه غير مُفهرَس أصلاً. + +**بعد الإصلاح:** الموقع صغير (~70 صفحة)، لذا crawl budget ليس مشكلة فعلية. جوجل يزحف على مواقع من هذا الحجم بالكامل خلال ساعات. + +--- + +## 2.6 خطة الفهرسة الكاملة + +### الخطوة 1 — الفورية (أسبوع 1) + +```txt +1. تصحيح HTML lang="ar" dir="rtl" +2. إنشاء sitemap.xml +3. تحديث robots.txt +4. إرسال sitemap عبر Google Search Console +5. طلب إعادة الفهرسة للصفحات الرئيسية +``` + +### الخطوة 2 — التقنية (أسبوع 2-4) + +```txt +1. تطبيق SSR أو تحويل الصفحات التسويقية إلى Blade ثابتة +2. إضافة canonical tags +3. التأكد من أن روابط /docs/ هي anchor tags حقيقية +4. تحسين meta tags لكل صفحة +``` + +### الخطوة 3 — المراقبة (أسبوع 4+) + +```txt +1. متابعة Google Search Console يومياً +2. رصد Coverage report +3. تتبع اكتشاف الصفحات الجديدة +``` + +**التوقع:** مع تطبيق هذه الخطوات، يُمكن الوصول إلى فهرسة 80%+ من الصفحات خلال 30-60 يوماً. diff --git a/platform/resources/docs/11_seo_audit/04_phase3_ranking_assets.md b/platform/resources/docs/11_seo_audit/04_phase3_ranking_assets.md new file mode 100644 index 00000000..8f022b3f --- /dev/null +++ b/platform/resources/docs/11_seo_audit/04_phase3_ranking_assets.md @@ -0,0 +1,129 @@ +# المرحلة 3 — جرد أصول التصنيف + +## 3.1 الأصول الحالية + +### الصفحات التسويقية (10 صفحات) + +| الصفحة | الغرض | جودة SEO | الإمكانية | +| --- | --- | --- | --- | +| `/` — الرئيسية | Hero + CTA | ضعيفة (محتوى من DB) | عالية جداً | +| `/pillars` — الأعمدة | الميزات التقنية | ضعيفة | عالية | +| `/services` — الخدمات | خدمات مؤسسية | ضعيفة | متوسطة | +| `/about` — من نحن | فلسفة الشركة | ضعيفة | متوسطة | +| `/pricing` — الأسعار | التسعير | ضعيفة | عالية | +| `/contact` | نموذج التواصل | لا قيمة | منخفضة | +| `/faq` | أسئلة شائعة | متوسطة | عالية | +| `/privacy-policy` | قانونية | لا قيمة | منخفضة | +| `/terms-of-use` | قانونية | لا قيمة | منخفضة | +| `/docs/` (49 صفحة) | توثيق تقني | متوسطة | عالية | + +**إجمالي الأصول التسويقية:** 10 صفحات — **ضعيف جداً** + +--- + +### التوثيق (49 صفحة) — أصول مخفية ذات قيمة عالية + +هذه الصفحات تُمثّل أكبر فرصة سريعة لقيد. المحتوى موجود، متعمق، عالي الجودة، وعربي أصيل. + +**تصنيف صفحات التوثيق حسب قيمة البحث:** + +| القسم | عدد الصفحات | قيمة البحث | +| --- | --- | --- | +| 00 - المقدمة والفلسفة | 3 | عالية (محتوى قصصي فريد) | +| 01 - المفاهيم الأساسية | 6 | عالية جداً (كلمات مفتاحية تعليمية) | +| 02 - بنية التطبيق | 4 | متوسطة | +| 03 - العمليات اليومية | 5 | عالية (كلمات "كيف أفعل...") | +| 04 - مراكز التكلفة | 5 | متوسطة | +| 05 - إدارة الحسابات | 6 | عالية | +| 06 - نظام التحويلات | 6 | عالية جداً (فريد) | +| 07 - التقارير | 5 | عالية | +| 08 - المحاسبة المتقدمة | 5 | عالية | +| 09 - الأسئلة الشائعة | 3 | عالية جداً (long-tail) | + +--- + +## 3.2 الأصول المفقودة (فجوات حرجة) + +### أصول مفقودة ذات تأثير عالي + +#### 1. مدونة / مركز محتوى + +**الحالة:** غائب تماماً +**الأثر:** الشركات المنافسة مثل Wafeq تمتلك مئات المقالات. هذا هو السبب الرئيسي في فجوة السلطة. + +**أمثلة على المحتوى المطلوب:** + +- "كيف تُسجّل معاملاتك اليومية بالقيد المزدوج" +- "الفرق بين المحاسبة الشخصية والمحاسبة التجارية" +- "لماذا بياناتك المالية في خطر على التطبيقات السحابية" +- "دليل القيد المزدوج للمبتدئين بالعربية" +- "كيف تُدير الديون والذمم بين الأصدقاء محاسبياً" + +#### 2. صفحات Landing مُحسَّنة للكلمات المفتاحية + +**الحالة:** غائبة +**المطلوب:** صفحة منفصلة لكل cluster رئيسي: + +- صفحة "محاسبة شخصية" +- صفحة "تطبيق قيد مزدوج" +- صفحة "تطبيق مالي مشفر" +- صفحة "إدارة الديون بين الأصدقاء" +- صفحة "سيادة البيانات المالية" + +#### 3. صفحات المقارنة التنافسية + +**الحالة:** غائبة +**الأثر:** الكلمات "قيد vs [منافس]" لها نية شرائية عالية جداً + +**أمثلة:** + +- قيد مقابل Wafeq +- قيد مقابل Daftra +- قيد مقابل Firefly III +- تطبيق محاسبة شخصية مشفر مقابل تطبيق سحابي + +#### 4. محتوى تعليمي (Glossary / Educational Hub) + +**الحالة:** غائب (التوثيق موجود لكن غير منفصل كـ "مدرسة") +**الفرصة:** إنشاء صفحات glossary مثل: + +- "ما هو القيد المزدوج؟" +- "ما هو التشفير E2EE في التطبيقات المالية؟" +- "ما هو مبدأ Local-First؟" + +#### 5. صفحات الحالات الاستخدامية (Use Cases) + +**الحالة:** غائبة +**المطلوب:** صفحة لكل segment: + +- "قيد للأفراد الحريصين على خصوصيتهم المالية" +- "قيد للمهنيين المستقلين والفريلانسر" +- "قيد لإدارة الشراكات والتوزيع المالي" +- "قيد للعائلات (إدارة الأصول المشتركة)" + +--- + +## 3.3 تقييم الأصول مقارنةً بالمنافسين + +| المنافس | عدد الصفحات (تقدير) | مدونة | مقارنات | التوثيق | +| --- | --- | --- | --- | --- | +| Wafeq | 500+ | ✓ (100+ مقالة) | ✓ | ✓ | +| Daftra | 1000+ | ✓ (200+ مقالة) | ✓ | ✓ | +| Ala-Hasba | 200+ | ✓ | محدودة | محدودة | +| **قيد** | **~65** | **✗** | **✗** | **✓ (لكن غير مفهرَسة)** | + +**نسبة تغطية الأصول مقارنةً بالمنافسين:** 6-13% + +--- + +## 3.4 ROI المتوقع لكل نوع من الأصول + +| الأصل | التأثير على الترتيب | الجهد | الأولوية | +| --- | --- | --- | --- | +| تصحيح الفهرسة التقنية | عالي جداً | منخفض | **حرجة** | +| فهرسة صفحات التوثيق الحالية | عالي (أصول جاهزة) | منخفض | **حرجة** | +| مدونة عربية (10 مقالات) | عالي جداً | متوسط | **عالية** | +| صفحات Landing للكلمات المفتاحية | عالي | منخفض-متوسط | **عالية** | +| صفحات المقارنة | متوسط-عالي | منخفض | **عالية** | +| Glossary / التعريفات | متوسط | منخفض | **متوسطة** | +| صفحات الحالات الاستخدامية | متوسط | منخفض | **متوسطة** | diff --git a/platform/resources/docs/11_seo_audit/05_phase4_search_intent.md b/platform/resources/docs/11_seo_audit/05_phase4_search_intent.md new file mode 100644 index 00000000..61483b12 --- /dev/null +++ b/platform/resources/docs/11_seo_audit/05_phase4_search_intent.md @@ -0,0 +1,93 @@ +# المرحلة 4 — خريطة نوايا البحث + +## 4.1 الكون الكامل لنوايا البحث في هذا السوق + +### المجموعة A — نية معلوماتية (Informational) + +هؤلاء يبحثون عن فهم المفاهيم. قيمتهم التجارية متأخرة لكنها تبني الوعي بالعلامة التجارية. + +| الكلمة المفتاحية (عربي) | الكلمة المفتاحية (إنجليزي) | الطلب | الصعوبة | تغطية قيد | +|---|---|---|---|---| +| ما هو القيد المزدوج | What is double-entry accounting | مرتفع | منخفضة | ✗ | +| كيف تُسجّل القيود المحاسبية | How to record journal entries | مرتفع | متوسطة | ✗ | +| ما هو التشفير من طرف إلى طرف | What is E2EE | مرتفع | منخفضة | ✗ | +| ما هو Local-First في التطبيقات | What is local-first software | متوسط | منخفضة | ✗ | +| الفرق بين المحاسبة الشخصية والتجارية | Personal vs business accounting | متوسط | منخفضة | ✗ | +| كيف أُدير ديوني مع الأصدقاء | How to track debts between friends | مرتفع | منخفضة | ✗ | +| خطر التطبيقات السحابية على بياناتي | Cloud app data privacy risks | متوسط | منخفضة | ✗ | +| مبادئ المحاسبة بالقيد المزدوج | Double-entry accounting principles | متوسط | منخفضة | جزئياً (docs) | + +**الوضع:** قيد لا يُغطّي أي من هذه النوايا في صفحاته العامة. + +--- + +### المجموعة B — نية تجارية (Commercial Investigation) + +هؤلاء يقارنون الخيارات ويتجهون نحو القرار. قيمة تجارية عالية. + +| الكلمة المفتاحية | الطلب | الصعوبة | تغطية قيد | +|---|---|---|---| +| أفضل تطبيق محاسبة شخصية عربي | مرتفع | متوسطة | ✗ | +| تطبيق محاسبة للأفراد 2025 | مرتفع | متوسطة | ✗ | +| برنامج محاسبة مشفر | متوسط | منخفضة | ✗ | +| أفضل تطبيق لتتبع الميزانية الشخصية | مرتفع | عالية | ✗ | +| تطبيق محاسبة offline | متوسط | منخفضة | ✗ | +قيد (qayd) | vs Wafeq | منخفض | منخفضة جداً | ✗ | +| بديل Firefly III عربي | منخفض | منخفضة جداً | ✗ | +| تطبيق محاسبة بدون اشتراك شهري | متوسط | منخفضة | ✗ | + +--- + +### المجموعة C — نية تحويلية (Transactional) + +هؤلاء جاهزون للتحويل — أعلى قيمة تجارية. + +| الكلمة المفتاحية | الطلب | الصعوبة | تغطية قيد | +|---|---|---|---| +| تحميل تطبيق محاسبة شخصية | متوسط | متوسطة | ✗ | +| تسجيل في قيد | منخفض | منخفضة جداً | ✗ | +| شراء تطبيق قيد مزدوج | منخفض | منخفضة جداً | ✗ | +| تجربة برنامج محاسبة مجاني | متوسط | عالية | ✗ | + +--- + +### المجموعة D — نية تعليمية مرتبطة بالمنتج (Educational-Commercial) + +هذه الفجوة الأكبر والأكثر استراتيجية لقيد. + +| الكلمة المفتاحية | القيمة | +|---|---| +| كيف أُنشئ ميزانية شخصية بالقيد المزدوج | عالية جداً | +| كيف أُسجّل دخل الفريلانسر في التطبيق | عالية جداً | +| كيف أُتابع الديون بشكل محاسبي صحيح | عالية جداً | +| كيف أُدير أموال الشراكة في التطبيق | عالية | +| ما الفرق بين حساب المدين والدائن | عالية | + +--- + +## 4.2 الفجوات الأكثر قيمة + +**الأولوية 1 — الفجوة التعليمية العربية** + +لا يوجد في السوق العربية مورد تعليمي جيد ومجاني يشرح القيد المزدوج للأفراد (وليس للمحاسبين). هذا فراغ قيد مؤهل لملئه بشكل طبيعي بسبب فلسفة التطبيق نفسها. + +**الأولوية 2 — الفجوة الخصوصية** + +الوعي بمخاطر البيانات السحابية آخذ في الارتفاع في المنطقة. لا يوجد محتوى عربي متخصص يجمع "الخصوصية المالية + حلول عملية". + +**الأولوية 3 — إدارة الديون الشخصية** + +من أعلى الكلمات المفتاحية بحثاً وأقلها تغطيةً من الأدوات الموجودة: "كيف أُتابع مَن أعطيتهم قروضاً" / "كيف أُسجّل الديون بين الأصدقاء". + +--- + +## 4.3 النوايا التي يُغطيها المنافسون ولا يُغطيها قيد + +| المنافس | يُغطي هذه النية قيد (qayd) | يُغطيها؟ | +|---|---|---| +| Wafeq | محاسبة الشركات الصغيرة، الفواتير، VAT | ✗ (خارج نطاق قيد) | +| Daftra | ERP للشركات، المخزون، الرواتب | ✗ (خارج نطاق قيد) | +| Firefly III | تتبع الميزانية الشخصية، الـ self-hosted | ✗ (قيد يُغطيها لكن لا أحد يعرفه) | +| GnuCash | محاسبة شخصية متقدمة، desktop | ✗ (قيد بديل أفضل للعرب) | + +**الاستنتاج:** قيد لا ينافس Wafeq أو Daftra — هدفه مختلف تماماً. منافسوه الحقيقيون هم Firefly III وGnuCash وMoney Manager Ex، وهم أدوات غربية بدون دعم عربي جيد. diff --git a/platform/resources/docs/11_seo_audit/06_phase5_keyword_universe.md b/platform/resources/docs/11_seo_audit/06_phase5_keyword_universe.md new file mode 100644 index 00000000..10cf53b1 --- /dev/null +++ b/platform/resources/docs/11_seo_audit/06_phase5_keyword_universe.md @@ -0,0 +1,129 @@ +# المرحلة 5 — كون الكلمات المفتاحية الكامل + +## 5.1 الكلمات المفتاحية الأساسية (Primary Keywords) + +### عربية — تجارية وتحويلية + +| الكلمة | النية | الأولوية | سهولة الترتيب | +|---|---|---|---| +| تطبيق محاسبة شخصية | تجارية | ⭐⭐⭐⭐⭐ | متوسطة | +| برنامج محاسبة للأفراد | تجارية | ⭐⭐⭐⭐⭐ | متوسطة | +| محاسبة بقيد مزدوج | تجارية | ⭐⭐⭐⭐ | منخفضة | +| تطبيق محاسبة مشفر | تجارية | ⭐⭐⭐⭐ | منخفضة جداً | +| تطبيق ميزانية شخصية | تجارية | ⭐⭐⭐⭐⭐ | عالية | +| برنامج تتبع المصروفات | تجارية | ⭐⭐⭐⭐ | متوسطة | +| تطبيق محاسبة offline | تجارية | ⭐⭐⭐ | منخفضة | +| تطبيق محاسبة بدون انترنت | تجارية | ⭐⭐⭐ | منخفضة | +| محاسبة سحابية مشفرة | تجارية | ⭐⭐⭐ | منخفضة | +| أفضل تطبيق محاسبة عربي | تجارية | ⭐⭐⭐⭐⭐ | عالية | + +### إنجليزية + +| الكلمة | النية | الأولوية | سهولة الترتيب | +|---|---|---|---| +| Arabic accounting app | تجارية | ⭐⭐⭐⭐ | متوسطة | +| personal finance app Arabic | تجارية | ⭐⭐⭐⭐ | متوسطة | +| local-first accounting app | تجارية | ⭐⭐⭐⭐ | منخفضة | +| E2EE personal finance | تجارية | ⭐⭐⭐ | منخفضة | +| double-entry personal finance | تجارية | ⭐⭐⭐ | منخفضة | +| encrypted accounting software | تجارية | ⭐⭐⭐ | منخفضة | + +--- + +## 5.2 الكلمات المفتاحية الثانوية (Secondary Keywords) + +### مرتبطة بالميزات + +| الكلمة | اللغة | الفرصة | +|---|---|---| +| التشفير من طرف إلى طرف في التطبيقات | عربية | عالية | +| ما هو Local-First | عربية | عالية | +| تطبيق مالي بدون خادم | عربية | عالية | +| سيادة البيانات المالية | عربية | عالية (unique positioning) | +| بيانات مالية على جهازي | عربية | عالية | +| AES-256 للبيانات الشخصية | عربية | متوسطة | +| Ed25519 تطبيق مالي | عربية | منخفضة (تقنية جداً) | + +### مرتبطة بالاستخدام اليومي + +| الكلمة | اللغة | الفرصة | +|---|---|---| +| كيف أُسجّل مصاريفي اليومية | عربية | عالية جداً | +| كيف أُتابع ديوني الشخصية | عربية | عالية جداً | +| كيف أُدير أموالي الشخصية | عربية | عالية جداً | +| إدارة الميزانية الشخصية | عربية | عالية | +| تتبع الإيرادات والمصروفات | عربية | عالية | +| دفتر حسابات شخصي | عربية | عالية | +| طريقة تسجيل الأموال المُعطاة | عربية | عالية جداً | + +### مرتبطة بالخصوصية والأمان + +| الكلمة | اللغة | الفرصة | +|---|---|---| +| تطبيق مالي آمن | عربية | عالية | +| حماية البيانات المالية | عربية | عالية | +| خطر تطبيقات المحاسبة السحابية | عربية | عالية | +| من يملك بياناتك المالية | عربية | عالية (content angle) | +| خصوصية التطبيقات المالية | عربية | عالية | + +--- + +## 5.3 كلمات Long-Tail ذات قيمة عالية + +### أسئلة "كيف" (How-To) — أعلى نية تحويلية + +``` +كيف أُنشئ دفتر أستاذ شخصي +كيف أُسجّل راتبي الشهري في تطبيق محاسبة +كيف أُتابع قرض أعطيته لصديق +كيف أُحسب ميزانيتي الشخصية بشكل صحيح +كيف أُفرّق بين المدين والدائن في حياتي اليومية +كيف أُنظّم حساباتي الشخصية والعائلية معاً +كيف أُدير وساطة مالية بين شخصين +كيف أُسجّل استثماراتي في تطبيق محاسبة +``` + +### أسئلة "ما هو" (Definitional) — لبناء السلطة + +``` +ما هو القيد المزدوج بالعربي +ما الفرق بين حساب المدين والدائن +ما هو دفتر الأستاذ العام +ما هو التوازن المحاسبي +ما هو حساب التسوية +ما هو مبدأ الاستحقاق في المحاسبة +``` + +### أسئلة "أفضل" (Comparison) — نية تجارية عالية + +``` +أفضل تطبيق محاسبة شخصية في السعودية +أفضل تطبيق لتتبع المصروفات بدون اشتراك +أفضل بديل لـ Firefly III بالعربية +أفضل تطبيق محاسبة للفريلانسر العربي +أفضل تطبيق لإدارة الديون الشخصية +``` + +--- + +## 5.4 الكلمات المهملة (Quick Wins مضمونة) + +هذه الكلمات سهلة جداً بسبب انعدام المنافسة المباشرة: + +| الكلمة | سبب السهولة | +|---|---| +| "تطبيق محاسبة مشفر E2EE" | لا منافس يستهدفها بالعربية | +| "محاسبة شخصية local-first" | مصطلح جديد بلا محتوى عربي | +| "تطبيق محاسبة بدون سحابة" | طلب حقيقي وبلا إجابة جيدة | +| "وساطة مالية بين شخصين تطبيق" | فريد لقيد تماماً | +| "بيانات مالية على الجهاز فقط" | نية واضحة، لا منافس | +| "قيد مزدوج للأفراد" | high intent، لا منافس | + +--- + +## 5.5 ملخص الفرص المُحددة + +**إجمالي الكلمات المحددة:** 80+ +**تُغطيها قيد حالياً:** 0 +**الفرص السريعة (6 أشهر):** 25+ كلمة بإمكانية الوصول للصفحة الأولى +**السبب:** انعدام المنافسة على معظم كلمات القطاع المتخصص (E2EE، local-first، وساطة) diff --git a/platform/resources/docs/11_seo_audit/07_phase6_content_gap_matrix.md b/platform/resources/docs/11_seo_audit/07_phase6_content_gap_matrix.md new file mode 100644 index 00000000..80171a22 --- /dev/null +++ b/platform/resources/docs/11_seo_audit/07_phase6_content_gap_matrix.md @@ -0,0 +1,128 @@ +# المرحلة 6 — مصفوفة فجوات المحتوى + +## 6.1 المنهجية + +تمت المقارنة بين محتوى قيد ومحتوى أبرز المنافسين: +- **Wafeq** — SaaS محاسبة للشركات الصغيرة (السعودية/الإمارات) +- **Daftra** — ERP عربي (مصر/السعودية) +- **Firefly III** — self-hosted personal finance (جمهور غربي) +- **Ala-Hasba** — محاسبة سحابية للخليج + +> ملاحظة: لا ينافس قيد Wafeq/Daftra في الفئة التجارية — لكن كلاهما يتنافس على الكلمات المعلوماتية العامة. + +--- + +## 6.2 المصفوفة الكاملة + +### القسم A — صفحات تسويقية مفقودة + +| المحتوى المفقود | قيمة الأعمال | قيمة البحث | أولوية التطبيق | +|---|---|---|---| +| صفحة Landing "محاسبة شخصية" | عالية جداً | عالية جداً | **حرجة** | +| صفحة Landing "تطبيق مشفر" | عالية | عالية | **حرجة** | +| صفحة Landing "قيد مزدوج للأفراد" | عالية | عالية | **حرجة** | +| صفحة Landing "بدون سحابة / offline" | عالية | متوسطة-عالية | **عالية** | +| صفحة Landing "إدارة الديون الشخصية" | عالية | عالية جداً | **عالية** | +| صفحة "كيف يعمل قيد" (How It Works) | عالية | عالية | **عالية** | +| صفحة "لمَن هذا التطبيق" (Use Cases) | متوسطة | متوسطة | **متوسطة** | + +--- + +### القسم B — محتوى المدونة/التعليم المفقود + +#### كتل المحتوى ذات الأولوية القصوى + +**كتلة 1: تعليم المحاسبة الشخصية (Topical Authority Cluster)** + +| المقالة المطلوبة | طول مقترح | قيمة البحث | +|---|---|---| +| "القيد المزدوج: الدليل الكامل للمبتدئين بالعربية" | 3000+ كلمة | عالية جداً | +| "ما الفرق بين المدين والدائن؟ شرح مبسّط" | 1500 كلمة | عالية | +| "كيف تُسجّل مصاريفك اليومية بطريقة محاسبية صحيحة" | 2000 كلمة | عالية جداً | +| "دفتر الأستاذ العام: ما هو وكيف تستخدمه؟" | 1500 كلمة | عالية | +| "5 أخطاء شائعة في المحاسبة الشخصية وكيف تتجنبها" | 1500 كلمة | عالية | +| "كيف تُنشئ ميزانية شخصية ناجحة خطوة بخطوة" | 2500 كلمة | عالية جداً | + +**كتلة 2: الخصوصية والأمان المالي** + +| المقالة المطلوبة | طول مقترح | قيمة البحث | +|---|---|---| +| "من يملك بياناتك المالية؟ الحقيقة المقلقة عن تطبيقات المحاسبة" | 2000 كلمة | عالية جداً | +| "E2EE في التطبيقات المالية: دليل المستخدم العادي" | 1500 كلمة | عالية | +| "Local-First Software: لماذا مستقبل التطبيقات يعود إلى جهازك" | 1500 كلمة | عالية | +| "تسريبات البيانات في تطبيقات المالية الشخصية: إحصائيات مقلقة" | 1500 كلمة | متوسطة-عالية | +| "PDPL السعودي وحماية بياناتك المالية" | 2000 كلمة | عالية (محلية) | + +**كتلة 3: إدارة الديون والعلاقات المالية** + +| المقالة المطلوبة | طول مقترح | قيمة البحث | +|---|---|---| +| "كيف تُدير الديون بينك وبين أصدقائك دون خجل" | 2000 كلمة | عالية جداً | +| "أفضل طريقة لتسجيل القروض الشخصية محاسبياً" | 1500 كلمة | عالية | +| "كيف تحسب مَن دفع أكثر في رحلة جماعية؟" | 1200 كلمة | عالية جداً | +| "إدارة المال المشترك بين الزوجين: دليل عملي" | 1500 كلمة | عالية | + +**كتلة 4: المقارنات التنافسية** + +| المقالة المطلوبة | نية المستخدم | قيمة التحويل | +|---|---|---| +| "قيد مقابل Firefly III: أيهما يناسبك؟" | تجارية | عالية جداً | +| "قيد مقابل GnuCash: مقارنة للمستخدم العربي" | تجارية | عالية جداً | +| "تطبيقات المحاسبة الشخصية المفتوحة المصدر 2025: مقارنة شاملة" | تجارية | عالية | +| "لماذا لا تُناسبك تطبيقات الـ SaaS للمحاسبة الشخصية" | تجارية | عالية | + +--- + +### القسم C — توثيق يحتاج إعادة تأطير للـ SEO + +صفحات التوثيق الحالية (49 صفحة) مكتوبة للمستخدم النشط، لكن يمكن إضافة صفحات "gateway" مُحسَّنة تقود إليها: + +| الصفحة Gateway المقترحة | تُقود إلى توثيق | +|---|---| +| "كيف تُسجّل أول قيد في قيد؟" | docs/03_daily_operations | +| "كيف تُنشئ حساباتك في قيد خطوة بخطوة" | docs/05_accounts_management | +| "كيف تُدير التحويلات والوساطة في قيد" | docs/06_transfers_system | +| "كيف تستخرج تقاريرك المالية من قيد" | docs/07_reports_and_outputs | + +--- + +## 6.3 ملخص الفجوة الكمية + +| نوع المحتوى | المنافس الرائد قيد (qayd) | | الفجوة | +|---|---|---|---| +| مقالات المدونة | Wafeq: 100+، Daftra: 200+ | 0 | 100-200 مقالة | +| صفحات Landing | Wafeq: 30+، Daftra: 50+ | 0 مُحسَّنة | 30-50 صفحة | +| صفحات مقارنة | Wafeq: 10+، Daftra: 20+ | 0 | 10-20 صفحة | +| Glossary | Wafeq: 20+، Daftra: 30+ | 0 | 20-30 صفحة | +| صفحات حالات استخدام | Wafeq: 10+ | 0 | 10 صفحات | + +**إجمالي المحتوى المطلوب لمنافسة القادة:** 170-300 قطعة محتوى +**بداية معقولة للنتائج (6 أشهر):** 30-50 قطعة محتوى عالية الجودة + +--- + +## 6.4 خطة المحتوى المرحلية (Content Roadmap) + +### المرحلة 1 — الأشهر 1-3 (الأساس) +``` +1. 10 مقالات من كتلة تعليم المحاسبة +2. 5 صفحات Landing للكلمات الرئيسية +3. صفحة "كيف يعمل قيد" الشاملة +4. تحسين meta tags لجميع صفحات التوثيق +``` + +### المرحلة 2 — الأشهر 4-6 (البناء) +``` +1. 10 مقالات من كتلة الخصوصية والأمان +2. 5 مقالات مقارنة تنافسية +3. 8 مقالات إدارة الديون +4. 15 صفحة Glossary +``` + +### المرحلة 3 — الأشهر 7-12 (الهيمنة) +``` +1. 20+ مقالة إضافية لتعميق الـ topical authority +2. محتوى بالإنجليزية للجمهور الغربي المهتم بالـ privacy +3. محتوى فيديو/podcast (تقوية الـ entity authority) +4. محتوى تعاوني مع مدونيين في مجال المالية الشخصية +``` diff --git a/platform/resources/docs/11_seo_audit/08_phase7_entity_schema.md b/platform/resources/docs/11_seo_audit/08_phase7_entity_schema.md new file mode 100644 index 00000000..e5142934 --- /dev/null +++ b/platform/resources/docs/11_seo_audit/08_phase7_entity_schema.md @@ -0,0 +1,179 @@ +# المرحلة 7 — تحليل الكيانات وبيانات Schema + +## 7.1 سؤال أساسي: هل تعرف جوجل مَن هو قيد؟ + +**الجواب القصير: لا.** + +لكي يفهم Google (وأنظمة البحث بالذكاء الاصطناعي) "قيد" كـ كيان مُحدَّد، يحتاج إلى إجابات واضحة على: + +| السؤال | هل يُجيب عليه الموقع؟ | +|---|---| +| مَن تملك المنتج (الشركة)؟ | جزئياً (ACCSYSTEM مذكورة) | +| ما اسم المنتج الدقيق؟ | جزئياً ("قيد" في النصوص) | +| ما المشكلة التي يحلها؟ | نعم (في النصوص الداخلية) | +| مَن جمهوره المستهدف؟ | غير واضح | +| ما الذي يُميّزه عن المنافسين؟ | جزئياً | +| أين يمكن تحميله؟ | غير واضح (Play Store موجود؟) | +| ما نماذج التسعير؟ | في /pricing | + +--- + +## 7.2 غياب JSON-LD Schema + +**الحالة:** لا يوجد أي JSON-LD في الموقع. +**الأثر:** جوجل لا يستطيع ربط محتوى الموقع بـ Knowledge Graph بدون structured data. + +### Schema المطلوبة فوراً + +#### 1. SoftwareApplication Schema (الأعلى أولوية) +```json +{ + "@context": "https://schema.org", + "@type": "SoftwareApplication", + "name": "قيد", + "applicationCategory": "FinanceApplication", + "operatingSystem": "Android, iOS", + "description": "نظام محاسبة بقيد مزدوج مشفر من طرف إلى طرف للأفراد", + "offers": { + "@type": "Offer", + "price": "...", + "priceCurrency": "USD" + }, + "author": { + "@type": "Organization", + "name": "ACCSYSTEM" + }, + "inLanguage": ["ar", "en"], + "featureList": [ + "تشفير E2EE", + "Local-First Architecture", + "Double-Entry Accounting", + "Offline Support", + "Bilateral Mediation" + ] +} +``` + +#### 2. Organization Schema +```json +{ + "@context": "https://schema.org", + "@type": "Organization", + "name": "ACCSYSTEM", + "url": "https://qayd.accsystemerp.com", + "logo": "...", + "contactPoint": { + "@type": "ContactPoint", + "contactType": "customer support", + "email": "..." + }, + "sameAs": [ + "https://play.google.com/store/apps/..." + ] +} +``` + +#### 3. FAQPage Schema (لصفحة /faq) +```json +{ + "@context": "https://schema.org", + "@type": "FAQPage", + "mainEntity": [ + { + "@type": "Question", + "name": "ما هو قيد؟", + "acceptedAnswer": { + "@type": "Answer", + "text": "قيد هو تطبيق محاسبة شخصية يعمل بنظام القيد المزدوج..." + } + } + ] +} +``` + +#### 4. WebSite Schema (للـ sitelinks search box المستقبلي) +```json +{ + "@context": "https://schema.org", + "@type": "WebSite", + "name": "قيد", + "url": "https://qayd.accsystemerp.com", + "potentialAction": { + "@type": "SearchAction", + "target": "https://qayd.accsystemerp.com/docs?q={search_term}", + "query-input": "required name=search_term" + } +} +``` + +--- + +## 7.3 مشاكل اتساق الكيان + +### مشكلة 1: اسم التطبيق غير موحّد + +في الكود المصدري: +- `config('app.name')` = **"QaydAPI"** (في app.blade.php) +- العنوان في Home.tsx = **"Home"** +- OG title = **"قيد (qayd) — التحكم المالي الكامل"** +- الـ app description = **"قيد"** +- Play Store = **"Qayd Business"** / **"Qayd"** + +**المشكلة:** جوجل يرى ثلاثة أسماء مختلفة للكيان ذاته: "QaydAPI"، "قيد"، "Qayd". هذا يُضعف بناء الكيان في Knowledge Graph. + +**الحل:** توحيد اسم التطبيق عبر كل نقطة تماس: +- `app.name` في config = "قيد | Qayd" +- Page title format = "قيد (qayd) — [وصف الصفحة]" +- OG title = "قيد (qayd) — [شعار]" + +### مشكلة 2: `` لموقع عربي + +كما أُشير في المرحلة الأولى — هذا يُرسل إشارة متضاربة لجوجل: +- اللغة في الـ content: عربية +- اتجاه الـ HTML: LTR + +**الحل:** `` + +### مشكلة 3: غياب الربط بـ Google Play + +`google1ba3cc4c115ac1d9.html` موجود (تحقق Search Console)، لكن: +- لا يوجد رابط صريح لصفحة Google Play في الموقع +- لا يوجد `sameAs` يربط الموقع بحضور التطبيق الرقمي + +--- + +## 7.4 تقييم جاهزية Knowledge Graph + +| العنصر | الحالة | الثغرة | +|---|---|---| +| اسم الكيان موحّد | ✗ ضعيف | 3 أسماء مختلفة | +| وصف واضح للمنتج | جزئي | موجود في النصوص لكن بلا schema | +| ربط بمنصات التحميل | ✗ غائب | لا يوجد sameAs لـ Play Store | +| صفحة Wikipedia/Wikidata | ✗ غائب | طبيعي لشركة ناشئة | +| ذكر في مصادر خارجية | ✗ غائب | لا backlinks، لا mentions | +| Schema.org markup | ✗ غائب | لا JSON-LD على الإطلاق | + +**درجة جاهزية Knowledge Graph:** 8/100 + +--- + +## 7.5 خطوات بناء سلطة الكيان + +``` +المرحلة 1 (فورية): +□ إضافة JSON-LD SoftwareApplication على الرئيسية +□ إضافة JSON-LD Organization +□ إضافة JSON-LD FAQPage على /faq +□ توحيد اسم التطبيق عبر الكود + +المرحلة 2 (1-3 أشهر): +□ إنشاء صفحة Crunchbase للشركة +□ التواجد في Product Hunt +□ الحصول على mentions في مواقع تقنية عربية +□ توحيد الحضور في App Store وGoogle Play + +المرحلة 3 (3-6 أشهر): +□ تقديم للـ App directories العربية +□ مقابلات في بودكاست التقنية العربية +□ توثيق المنتج في مستودع GitHub عام +``` diff --git a/platform/resources/docs/11_seo_audit/09_phase8_ai_search_readiness.md b/platform/resources/docs/11_seo_audit/09_phase8_ai_search_readiness.md new file mode 100644 index 00000000..bd0f72b7 --- /dev/null +++ b/platform/resources/docs/11_seo_audit/09_phase8_ai_search_readiness.md @@ -0,0 +1,141 @@ +# المرحلة 8 — جاهزية البحث بالذكاء الاصطناعي + +## 8.1 درجة الرؤية في أدوات البحث بالذكاء الاصطناعي + +**AI Visibility Score: 12 / 100** + +--- + +## 8.2 تحليل كل منصة + +### Google AI Overviews (السابق: Search Generative Experience) + +**الدرجة: 8/100** + +AI Overviews يسحب المحتوى من المواقع المُفهرَسة والموثوقة. نظراً لأن قيد شبه غير مُفهرَس، فإن احتمال ظهوره في AI Overviews = صفر تقريباً. + +**المطلوب للظهور:** +- فهرسة أولاً +- schema markup واضح +- محتوى يُجيب على الأسئلة بشكل مباشر (Featured Snippet style) +- E-E-A-T signals + +--- + +### ChatGPT Search / Bing Copilot + +**الدرجة: 15/100** + +ChatGPT Search يعتمد على Bing index. نفس مشكلة الفهرسة تنطبق هنا. لكن هناك ميزة محتملة: ChatGPT يُمكنه الإجابة عن موضوعات "local-first E2EE accounting" إذا وُجد محتوى مرجعي واضح على الموقع. + +**تقرير ChatGPT الحالي عند السؤال عن "تطبيق محاسبة شخصية عربي مشفر":** +باحتمال كبير يذكر Firefly III وGnuCash وربما يقول "لا يوجد خيار عربي متخصص" — وهذا يعني أن قيد يُفوّت فرصة ذهبية. + +--- + +### Perplexity AI + +**الدرجة: 10/100** + +Perplexity يعتمد على محتوى الويب المتاح. بما أن قيد لا يظهر في نتائج البحث العادية، لن يظهر في Perplexity. + +**الفرصة الكبرى:** إذا نشر قيد محتوى مرجعياً على منصات مثل GitHub، Hacker News، Medium، أو ProductHunt — سيظهر في Perplexity بسرعة أكبر من جوجل. + +--- + +### Gemini (Google) + +**الدرجة: 12/100** + +Gemini يستخدم Google Search index كمصدر أساسي. نفس قيود الفهرسة تنطبق. + +--- + +## 8.3 تقييم إشارات E-E-A-T + +**E-E-A-T = Experience + Expertise + Authoritativeness + Trustworthiness** + +| الإشارة | الحالة | التقييم | +|---|---|---| +| **Experience** — تجربة حقيقية | الفلسفة والتوثيق يُظهران خبرة عميقة | متوسطة | +| **Expertise** — خبرة متخصصة | التوثيق التقني استثنائي (Ed25519، AES-256) | عالية في المحتوى الداخلي | +| **Authoritativeness** — سلطة خارجية | لا روابط خلفية، لا ذكر خارجي | ضعيفة جداً | +| **Trustworthiness** — الموثوقية | سياسة الخصوصية موجودة، شروط الاستخدام | متوسطة | + +**نقاط القوة:** +- المحتوى التقني عميق ومُحكم (يُظهر Expertise حقيقية) +- فلسفة الشفافية والصدق مُوثَّقة جيداً +- أمان التطبيق مُشروح تقنياً + +**نقاط الضعف:** +- لا اسم مؤلف أو كاتب محدد (E-E-A-T يُفضّل نسب المحتوى لأشخاص حقيقيين) +- لا صفحة "Team" أو "عن الفريق" +- لا شهادات مستخدمين +- لا ذكر في مصادر خارجية موثوقة + +--- + +## 8.4 البنية الدلالية للمحتوى (Semantic Structure) + +**التقييم:** متوسط-جيد للمحتوى الموجود، لكن لا يصل إلى Google + +``` +الهيكل الحالي: +✓ العناوين H1/H2/H3 في التوثيق (ملفات Markdown) +✓ محتوى نصي منظم ومتسق +✓ aria-label في بعض العناصر +✗ لا JSON-LD +✗ HTML dir="ltr" لموقع عربي (إشارة مربكة) +✗ محتوى الصفحات الرئيسية في DB (غير مُصيَّر بدون JS) +``` + +--- + +## 8.5 استراتيجية الظهور في البحث بالذكاء الاصطناعي + +### الأسرع تأثيراً: المحتوى المُختار بعناية (Citable Content) + +أنظمة الذكاء الاصطناعي تُفضّل المحتوى الذي: +1. يُجيب على سؤال محدد بشكل مباشر +2. يمكن الاستشهاد به (مُحكم ودقيق) +3. يظهر في مصادر متعددة + +**التوصيات العملية:** +``` +1. كتابة "تعريفات" قصيرة محكمة لكل مصطلح رئيسي + مثال: "ما هو القيد المزدوج؟ — 3 فقرات بدون حشو" + +2. إنشاء صفحة مقارنة شاملة بين قيد ومنافسيه + (هذا النوع يُستشهد به كثيراً في Perplexity/ChatGPT) + +3. نشر محتوى على GitHub README و Product Hunt + (Perplexity يُفهرَس هذه المصادر بسرعة) + +4. مشاركة في مناقشات Hacker News عن المحاسبة الشخصية + والإشارة إلى قيد كحل للمشكلة المطروحة +``` + +--- + +## 8.6 جدول الإشارات المطلوبة + +| الإشارة | الأولوية | الصعوبة | الأثر على AI Visibility | +|---|---|---|---| +| JSON-LD SoftwareApplication | حرجة | منخفضة | عالي | +| محتوى FAQ محكم | عالية | منخفضة | عالي جداً | +| نسب المحتوى لمؤلف حقيقي | متوسطة | منخفضة | متوسط | +| ذكر في مصادر تقنية (GitHub، HN) | عالية | متوسطة | عالي جداً | +| محتوى مقارنة واضح | عالية | منخفضة | عالي | +| صفحة Wikipedia/Wikidata | متوسطة | عالية | متوسط-عالي | + +--- + +## 8.7 خلاصة + +قيد يمتلك **المحتوى الجوهري المطلوب** للبحث الذكاء الاصطناعي (توثيق عميق، مفاهيم واضحة، تقنية موثقة) — لكنه يُخفيه خلف: +- فهرسة شبه معدومة +- بنية SPA لا تُصيَّر بدون JavaScript +- غياب Schema +- انعدام الحضور الخارجي + +**الهدف الواقعي خلال 12 شهراً:** رفع AI Visibility Score إلى 55-70/100 بتطبيق التوصيات التقنية + استراتيجية المحتوى. diff --git a/platform/resources/docs/11_seo_audit/10_phase10_competitive_intelligence.md b/platform/resources/docs/11_seo_audit/10_phase10_competitive_intelligence.md new file mode 100644 index 00000000..996143fd --- /dev/null +++ b/platform/resources/docs/11_seo_audit/10_phase10_competitive_intelligence.md @@ -0,0 +1,144 @@ +# المرحلة 10 — الاستخبارات التنافسية + +## 10.1 تحديد المنافسين الحقيقيين + +**ملاحظة حرجة:** قيد لا يُنافس Wafeq أو Daftra في الجوهر — أهدافهم مختلفة. + +| المنافس | الجمهور | نمط التعارض مع قيد | +|---|---|---| +| **Wafeq** | شركات صغيرة، محاسبون | تعارض جزئي على كلمات مفتاحية إعلامية | +| **Daftra** | شركات صغيرة-متوسطة | تعارض جزئي على كلمات مفتاحية إعلامية | +| **Firefly III** | أفراد، مطورون | **منافس مباشر في القيمة** | +| **GnuCash** | أفراد، محاسبون شخصيون | **منافس مباشر في القيمة** | +| **Beancount/Ledger** | مطورون، plain-text fans | منافس في الجمهور التقني | +| **Money Manager Ex** | أفراد | منافس في الجمهور العام | +| **Paper Money (HN)** | أفراد، HN community | منافس مباشر صغير | +| **FinBodhi** | أفراد | منافس مباشر ناشئ | + +--- + +## 10.2 تحليل المنافسين الرئيسيين + +### منافس 1: Wafeq +**الموقع:** wafeq.com +**الجمهور:** SMBs في السعودية والإمارات +**التمويل:** Series A $7.5 مليون (Menabytes) + +**نقاط القوة في البحث:** +- مدونة ضخمة (100+ مقالة عربية وإنجليزية) +- تغطية شاملة لكلمات مفتاحية: VAT، فواتير، محاسبة شركات +- دومين مستقل بسلطة متراكمة +- حضور قوي في الـ Arabic search results + +**نقاط الضعف (فرص لقيد):** +- لا يخدم المحاسبة الشخصية +- لا يوفر E2EE أو local-first +- مُلزَم بجمع البيانات (SaaS model) +- لا يصلح للأفراد أو الـ bilateral mediation + +**سبب تفوق Wafeq على قيد في نتائج البحث:** +رغم أن منتجاتهما مختلفة، Wafeq يحتل الصفحة الأولى لكلمات عامة مثل "محاسبة شخصية" لأن له محتوى يستهدفها وقيد لا. + +--- + +### منافس 2: Daftra (دفترة) +**الموقع:** daftra.com +**الجمهور:** شركات صغيرة-متوسطة في MENA + +**نقاط القوة في البحث:** +- 200+ مقالة، حضور طويل الأمد +- تحسين محرك البحث عميق لكل كلمة محاسبية +- حضور قوي في مصر والسعودية + +**الفرق الجوهري:** Daftra ERP للشركات، قيد محاسبة شخصية — لا تنافس حقيقي. + +--- + +### منافس 3: Firefly III ← **المنافس الأكثر أهمية استراتيجياً** +**الموقع:** firefly-iii.org +**الجمهور:** أفراد تقنيون، self-hosters، privacy-conscious +**النموذج:** مفتوح المصدر، مجاني، self-hosted + +**نقاط القوة:** +- سلطة ضخمة في مجتمع الـ open-source +- آلاف النجوم على GitHub +- توثيق شامل +- جمهور عالمي + +**نقاط الضعف — وهي فرصة قيد الذهبية:** +- واجهة معقدة، تتطلب خادماً للاستضافة +- **لا دعم عربي** +- **لا mobile-first** +- **لا bilateral mediation** +- **لا E2EE حقيقي** (self-hosted لكن ليس client-side encrypted) +- منحنى تعلم عالٍ + +**لماذا Firefly III يتصدر البحث ولا يتصدره قيد؟** +1. Firefly III لديه آلاف المقالات الخارجية التي تذكره +2. الموقع يحتوي على توثيق ضخم مُفهرَس بالكامل +3. مجتمع نشط يُنتج محتوى مستمراً + +--- + +### منافس 4: GnuCash +**الموقع:** gnucash.org +**النموذج:** مفتوح المصدر، desktop + +**نقطة الضعف الكبرى لمستخدمي MENA:** +- تطبيق desktop فقط (بدون mobile) +- الواجهة معقدة للمبتدئين +- لا دعم عربي فعلي +- لا مزامنة بين الأجهزة + +**قيد يتفوق عليه في كل هذه النقاط** — لكن لا أحد يعرف. + +--- + +## 10.3 مصفوفة الفجوة التنافسية + +| الميزة | Wafeq | Daftra | Firefly III | GnuCash | **قيد** | +|---|---|---|---|---|---| +| واجهة عربية | ✓ | ✓ | ✗ | جزئي | **✓** | +| Mobile (iOS/Android) | ✓ | ✓ | ✗ | ✗ | **✓** | +| تشفير E2EE | ✗ | ✗ | ✗ | ✗ | **✓** | +| Local-First | ✗ | ✗ | جزئي | ✓ | **✓** | +قيد (qayd) | مزدوج كامل | ✓ (للشركات) | ✓ (للشركات) | ✓ | ✓ | **✓** | +| Bilateral Mediation | ✗ | ✗ | ✗ | ✗ | **✓ (فريد)** | +| للأفراد | ✗ | ✗ | ✓ | ✓ | **✓** | +| بدون خادم | ✗ | ✗ | ✗ | ✓ | **✓** | +| سلطة SEO | عالية | عالية | عالية | متوسطة | **صفر** | +| حضور المحتوى | ضخم | ضخم | ضخم | متوسط | **معدوم** | + +**الاستنتاج:** قيد يتفوق على كل منافسيه في **الميزات** — لكنه يخسر بفارق كبير في **الرؤية**. + +--- + +## 10.4 لماذا يتفوق المنافسون في الترتيب؟ + +**السبب 1: تراكم المحتوى (Content Velocity)** +Wafeq و Daftra ينشران محتوى منذ سنوات. حتى لو نشر قيد 50 مقالاً اليوم، يحتاج 6-12 شهراً للمنافسة. + +**السبب 2: الروابط الخلفية (Backlinks)** +Wafeq لديه روابط من TechCrunch (Arabic)، MenaBites، Forbes Arabia. قيد = صفر. + +**السبب 3: سلطة الدومين** +`wafeq.com` عمره 6+ سنوات، موثوق ومُفهرَس. `qayd.accsystemerp.com` لا تاريخ له. + +**السبب 4: الحضور الاجتماعي** +Wafeq على LinkedIn (42K+ متابع)، Twitter. قيد؟ غير معروف. + +**السبب 5: التغطية الصحفية** +Wafeq Series A = مئات المقالات الإخبارية = backlinks عالية الجودة. + +--- + +## 10.5 الفرصة التي يُفوّتها كل المنافسين + +**لا أحد يخدم:** +1. الفرد العربي الحريص على خصوصيته المالية +2. بدون اشتراك SaaS شهري +3. بتطبيق موبايل native +4. مع تشفير كامل من طرف إلى طرف +5. ودعم الوساطة المالية بين طرفين + +**هذه الفجوة الكاملة = ملعب قيد الحصري.** diff --git a/platform/resources/docs/11_seo_audit/11_phase12_root_cause.md b/platform/resources/docs/11_seo_audit/11_phase12_root_cause.md new file mode 100644 index 00000000..7a7e6e46 --- /dev/null +++ b/platform/resources/docs/11_seo_audit/11_phase12_root_cause.md @@ -0,0 +1,178 @@ +# المرحلة 12 — تحليل الأسباب الجذرية + +## أبرز 10 أسباب تُقيّد رؤية قيد (qayd) — مُرتَّبة بالأدلة + +--- + +### السبب 1: شبه انعدام الفهرسة +**الأثر على الرؤية:** حرج / 10 +**الثقة:** 97% +**الأثر على الأعمال:** الزيارات العضوية = صفر +**التعقيد التقني:** منخفض (ساعات) + +**الدليل:** `site:qayd.accsystemerp.com` لا يُعيد نتائج. + +**السبب الجذري:** +- SPA بدون SSR يجعل فهرسة الصفحات صعبة +- لا sitemap يُرشد Googlebot +- لا روابط خلفية تُوجّه الزاحف للموقع +- الدومين الفرعي الجديد بدون سلطة + +**الإصلاح:** إنشاء sitemap + تقديمه في Search Console + SSR للصفحات الرئيسية + +--- + +### السبب 2: غياب استراتيجية المحتوى بالكامل +**الأثر على الرؤية:** 9.5/10 +**الثقة:** 100% +**الأثر على الأعمال:** لا اكتساب عضوي مستدام +**التعقيد التقني:** منخفض-متوسط (أسابيع-أشهر) + +**الدليل:** لا مدونة، لا مقالات، لا محتوى تسويقي خارج الصفحات الستة. + +**السبب الجذري:** التركيز كان على بناء المنتج وتوثيقه للمستخدمين، وليس على استقطاب مستخدمين جدد. + +**الإصلاح:** إنشاء مدونة + خطة نشر منتظمة + +--- + +### السبب 3: الدومين الفرعي بلا سلطة +**الأثر على الرؤية:** 9/10 +**الثقة:** 90% +**الأثر على الأعمال:** كل جهد SEO يبدأ من الصفر +**التعقيد التقني:** متوسط (أسابيع للانتقال) + +**الدليل:** `qayd.accsystemerp.com` = دومين فرعي تابع لدومين شركة ERP بلا حضور SEO خاص. + +**السبب الجذري:** القرار الأولي باستخدام subdomain بدلاً من دومين مستقل. + +**الإصلاح:** الانتقال إلى `qayd.app` أو `getqayd.com` مع 301 redirects + +--- + +### السبب 4: SPA بدون Server-Side Rendering +**الأثر على الرؤية:** 8/10 +**الثقة:** 95% +**الأثر على الأعمال:** تأخر الفهرسة أسابيع/أشهر +**التعقيد التقني:** متوسط-عالي (1-2 أسبوع) + +**الدليل:** Laravel + Inertia.js + React = client-side rendering. HTML الأولي فارغ من المحتوى. + +**السبب الجذري:** Inertia.js يُسهّل التطوير لكن يتطلب إعداداً إضافياً للـ SEO. + +**الإصلاح:** تفعيل `@inertiajs/react` SSR adapter أو تحويل الصفحات التسويقية إلى Blade ثابتة. + +--- + +### السبب 5: غياب JSON-LD Schema +**الأثر على الرؤية:** 7.5/10 +**الثقة:** 100% +**الأثر على الأعمال:** عدم الظهور في Rich Results وAI search +**التعقيد التقني:** منخفض (ساعات) + +**الدليل:** لا JSON-LD في أي صفحة من صفحات الموقع. + +**الإصلاح:** إضافة SoftwareApplication + Organization + FAQPage schemas + +--- + +### السبب 6: `` لموقع عربي +**الأثر على الرؤية:** 6/10 +**الثقة:** 100% +**الأثر على الأعمال:** إشارة مربكة لجوجل + تجربة مستخدم معيبة +**التعقيد التقني:** منخفض جداً (دقائق) + +**الدليل:** +```html + + +``` +الـ locale العربي سيُعطي `lang="ar"` لكن `dir` ثابتة على `ltr`. + +**الإصلاح:** +```html + +``` +أو ببساطة ثابتة: +```html + +``` + +--- + +### السبب 7: اسم التطبيق غير موحّد (Entity Confusion) +**الأثر على الرؤية:** 5.5/10 +**الثقة:** 95% +**الأثر على الأعمال:** ضعف بناء الكيان في Knowledge Graph +**التعقيد التقني:** منخفض (ساعات) + +**الدليل:** +- `config('app.name')` = "QaydAPI" +- Page title = "Home" +- OG = "قيد (qayd) — التحكم المالي الكامل" + +**الإصلاح:** توحيد الاسم "قيد | Qayd" عبر كل نقاط الاتصال + +--- + +### السبب 8: غياب الروابط الخلفية (Zero Backlinks) +**الأثر على الرؤية:** 8.5/10 +**الثقة:** 88% +**الأثر على الأعمال:** سلطة المجال = صفر +**التعقيد التقني:** عالي (أشهر) + +**الدليل:** لا ذكر خارجي ظهر في أي من عمليات البحث، لا روابط من مواقع تقنية عربية. + +**السبب الجذري:** التطبيق لم يُطلَق علنياً بشكل واسع أو لم يُروَّج له خارج الدوائر الضيقة. + +**الإصلاح:** استراتيجية PR + نشر على HN + تعاون مع مدونيين تقنيين عرب + +--- + +### السبب 9: غياب meta title مُحسَّن للصفحة الرئيسية +**الأثر على الرؤية:** 6.5/10 +**الثقة:** 100% +**الأثر على الأعمال:** CTR منخفض حتى لو ظهرت في النتائج +**التعقيد التقني:** منخفض (دقائق) + +**الدليل:** +```tsx + + Home // ← هذا هو العنوان المُفهرَس! +``` + +"Home" كعنوان للصفحة الرئيسية = فاشل تماماً. يجب أن يكون: +`"قيد (qayd) — تطبيق محاسبة شخصية مشفر بالقيد المزدوج"` + +--- + +### السبب 10: robots.txt لا يُشير إلى sitemap +**الأثر على الرؤية:** 4/10 +**الثقة:** 100% +**التعقيد التقني:** منخفض جداً (دقائق) + +**الدليل:** +``` +User-agent: * +Disallow: +``` +لا سطر `Sitemap:` موجود. + +**الإصلاح:** إضافة `Sitemap: https://qayd.accsystemerp.com/sitemap.xml` + +--- + +## ملخص الأسباب الجذرية مُرتَّبة + +| الترتيب | السبب | الأثر | الثقة | الجهد | +|---|---|---|---|---| +| 1 | شبه انعدام الفهرسة | حرج | 97% | منخفض | +| 2 | غياب استراتيجية المحتوى | 9.5/10 | 100% | عالي | +| 3 | الدومين الفرعي بلا سلطة | 9/10 | 90% | متوسط | +| 4 | SPA بدون SSR | 8/10 | 95% | متوسط-عالي | +| 5 | غياب الروابط الخلفية | 8.5/10 | 88% | عالي | +| 6 | غياب JSON-LD Schema | 7.5/10 | 100% | منخفض | +| 7 | `dir="ltr"` لموقع عربي | 6/10 | 100% | منخفض جداً | +| 8 | `Home` | 6.5/10 | 100% | منخفض جداً | +| 9 | اسم التطبيق غير موحّد | 5.5/10 | 95% | منخفض | +| 10 | robots.txt بدون sitemap reference | 4/10 | 100% | منخفض جداً | diff --git a/platform/resources/docs/11_seo_audit/12_phase13_action_plan.md b/platform/resources/docs/11_seo_audit/12_phase13_action_plan.md new file mode 100644 index 00000000..850af09c --- /dev/null +++ b/platform/resources/docs/11_seo_audit/12_phase13_action_plan.md @@ -0,0 +1,347 @@ +# المرحلة 13 — خطة العمل التنفيذية + +## الإجراءات مُجمَّعة حسب الأثر والأولوية + +--- + +## 🔴 حرجة — تُعيق الرؤية الآن + +هذه الإصلاحات تستغرق ساعات لكنها تُحدث أكبر تأثير فوري. + +--- + +### CR-1: تصحيح `` → `dir="rtl"` + +**الملف:** `resources/views/app.blade.php` +**الوقت:** 5 دقائق +**الأثر:** إزالة إشارة مربكة لجوجل + تحسين تجربة المستخدم + +```html + + + + + +``` + +--- + +### CR-2: تصحيح عنوان الصفحة الرئيسية + +**الملف:** `resources/js/Pages/Home.tsx` +**الوقت:** 5 دقائق +**الأثر:** أول شيء يراه جوجل — "Home" = فاشل، يجب أن يكون الكلمة المفتاحية المستهدفة + +```tsx +// قبل +Home + +// بعد +قيد (qayd) — تطبيق محاسبة شخصية بالقيد المزدوج | مشفر ومحلي +``` + +--- + +### CR-3: توحيد اسم التطبيق + +**الملف:** `config/app.php` +**الوقت:** 5 دقائق + +```php +// قبل +'name' => env('APP_NAME', 'QaydAPI'), + +// بعد +'name' => env('APP_NAME', 'قيد | Qayd'), +``` + +--- + +### CR-4: تحديث robots.txt + +**الملف:** `public/robots.txt` +**الوقت:** 10 دقائق + +```txt +User-agent: * +Disallow: /admin/ +Disallow: /api/ +Disallow: /login +Disallow: /logout +Disallow: /verify-email/ +Disallow: /reset-password/ + +Sitemap: https://qayd.accsystemerp.com/sitemap.xml +``` + +--- + +### CR-5: إنشاء sitemap.xml + +**الوقت:** 2-4 ساعات +**التبعيات:** `composer require spatie/laravel-sitemap` + +**خطوات التنفيذ:** + +```bash +composer require spatie/laravel-sitemap +``` + +```php +// routes/web.php أو SitemapController جديد +Route::get('/sitemap.xml', function () { + $sitemap = \Spatie\Sitemap\Sitemap::create() + ->add(\Spatie\Sitemap\Tags\Url::create('/') + ->setChangeFrequency('weekly')->setPriority(1.0)) + ->add(\Spatie\Sitemap\Tags\Url::create('/pillars') + ->setChangeFrequency('monthly')->setPriority(0.8)) + ->add(\Spatie\Sitemap\Tags\Url::create('/services') + ->setChangeFrequency('monthly')->setPriority(0.8)) + ->add(\Spatie\Sitemap\Tags\Url::create('/about') + ->setChangeFrequency('monthly')->setPriority(0.7)) + ->add(\Spatie\Sitemap\Tags\Url::create('/pricing') + ->setChangeFrequency('weekly')->setPriority(0.9)) + ->add(\Spatie\Sitemap\Tags\Url::create('/faq') + ->setChangeFrequency('monthly')->setPriority(0.8)) + ->add(\Spatie\Sitemap\Tags\Url::create('/contact') + ->setChangeFrequency('yearly')->setPriority(0.5)); + + // إضافة صفحات التوثيق + $docFiles = glob(resource_path('docs/**/*.md')); + foreach ($docFiles as $file) { + $path = str_replace(resource_path('docs'), '', $file); + $path = str_replace('.md', '', $path); + $path = str_replace('.mdx', '', $path); + $urlPath = '/docs' . str_replace('_', '-', $path); + $sitemap->add(\Spatie\Sitemap\Tags\Url::create($urlPath) + ->setChangeFrequency('monthly')->setPriority(0.6)); + } + + return response($sitemap->render(), 200) + ->header('Content-Type', 'application/xml'); +}); +``` + +**بعد الإنشاء:** تقديم الـ sitemap في Google Search Console. + +--- + +### CR-6: إضافة JSON-LD Schema للصفحة الرئيسية + +**الملف:** `resources/js/Pages/Home.tsx` +**الوقت:** 30 دقيقة + +```tsx + + قيد (qayd) — تطبيق محاسبة شخصية بالقيد المزدوج | مشفر ومحلي + + + + + + + + +``` + +--- + +## 🟠 عالية التأثير — نمو كبير + +--- + +### HI-1: SSR للصفحات التسويقية + +**الوقت:** 1-2 أسبوع +**الأثر:** الأكبر على قابلية الفهرسة + +**الخيار السريع (بدون SSR كامل):** تحويل الصفحات التسويقية الرئيسية إلى Blade templates مع محتوى static، مع الإبقاء على Inertia للـ admin فقط. + +**الخيار الصحيح (SSR كامل):** + +```bash +npm install @inertiajs/react +# تفعيل SSR في inertia.php +php artisan inertia:start-ssr +``` + +--- + +### HI-2: مدونة عربية — 10 مقالات الأولى + +**الوقت:** 2-4 أسابيع +**الأثر:** أعلى عائد SEO على المدى المتوسط + +**المقالات الـ 10 الأولى مُرتَّبة حسب الأولوية:** + +```txt +1. "القيد المزدوج: الدليل الكامل للمبتدئين" — 3000 كلمة +2. "من يملك بياناتك المالية؟ الحقيقة المقلقة" — 2000 كلمة +3. "كيف تُدير الديون مع الأصدقاء بدون إحراج" — 2000 كلمة +4. "الفرق بين المدين والدائن: شرح مبسط بأمثلة يومية" — 1500 كلمة +5. "تطبيقات المحاسبة الشخصية: مقارنة شاملة 2025" — 2500 كلمة +6. "كيف تُنشئ ميزانيتك الشخصية بطريقة محاسبية صحيحة" — 2000 كلمة +7. "E2EE في تطبيقات المالية الشخصية: ما تحتاج معرفته" — 1500 كلمة +8. "Local-First Software: مستقبل التطبيقات الحريصة على الخصوصية" — 1500 كلمة +9. "كيف تُسجّل دخل الفريلانسر في تطبيق محاسبة" — 1500 كلمة +10. "قيد مقابل Firefly III: أيهما يناسب المستخدم العربي؟" — 2000 كلمة +``` + +--- + +### HI-3: تحسين meta tags لصفحات التوثيق + +**الوقت:** 1 أسبوع +**الأثر:** تحويل 49 صفحة جاهزة إلى أصول SEO فعلية + +**في `DocsController.php`:** استخراج الـ H1 من كل ملف Markdown وتعيينه كـ `meta title` مع إضافة "| توثيق قيد". + +**إضافة meta description:** أول فقرة من كل صفحة توثيق كـ description. + +--- + +### HI-4: صفحات Landing مُحسَّنة (5 صفحات) + +**الوقت:** 2 أسبوع +**الأثر:** استهداف مباشر للكلمات التجارية + +```txt +/محاسبة-شخصية → "تطبيق محاسبة شخصية عربي" +/قيد-مزدوج → "محاسبة بالقيد المزدوج للأفراد" +/تشفير-مالي → "تطبيق مالي مشفر E2EE" +/ادارة-الديون → "إدارة الديون الشخصية" +/بدون-سحابة → "تطبيق محاسبة offline" +``` + +--- + +## 🟡 استراتيجية — تنافسية طويلة الأمد + +--- + +### ST-1: الانتقال إلى دومين مستقل + +**الجدول الزمني:** الشهر 3-4 +**الخطوات:** + +1. تسجيل `qayd.app` أو `getqayd.com` +2. إعداد 301 redirects من الدومين القديم +3. تحديث Search Console +4. تحديث Google Play وApp Store + +--- + +### ST-2: استراتيجية بناء الروابط + +**الجدول الزمني:** الشهر 2-6 + +```txt +أ) الحضور في منصات التقييم: + - Product Hunt (إطلاق رسمي) + - AlternativeTo (قيد كبديل لـ Firefly III/GnuCash) + - Trustpilot العربي + +ب) التواجد في مجتمعات التقنية: + - Hacker News (Show HN post) + - Reddit r/personalfinance, r/privacy + - مجتمعات التقنية العربية + +ج) التعاون مع المحتوى: + - مقابلات في بودكاست "تك عربي"، "عرب هاردوير" + - مقالات ضيف في مدونات التقنية المالية +``` + +--- + +### ST-3: Topical Authority في المحاسبة الشخصية العربية + +**الجدول الزمني:** الشهر 4-12 + +الهدف: أن يُعتبر qayd.com المرجع الأول للمحاسبة الشخصية العربية — مثلما يُعتبر Wafeq مرجعاً لمحاسبة الشركات الصغيرة. + +**خطة المحتوى الاستراتيجي:** + +```txt +- قسم "مدرسة المحاسبة الشخصية" — 30+ مقالة تعليمية +- قسم "الخصوصية المالية" — 15+ مقالة تخصصية +- قسم "المقارنات" — 10+ مقالات تنافسية +- قسم "أدلة المستخدم" — 20+ دليل تطبيقي +``` + +--- + +## 🟢 هيمنة السوق — قيادة الفئة + +--- + +### ML-1: هيمنة البحث الذكاء الاصطناعي + +**الجدول الزمني:** الشهر 6-12 + +**الهدف:** عندما يسأل أي شخص ChatGPT أو Gemini أو Perplexity "ما أفضل تطبيق محاسبة شخصية عربي مشفر؟" — يظهر قيد في الإجابة. + +**كيف يحدث هذا:** + +1. محتوى مرجعي واضح ومُحكم على الموقع +2. ذكر في مصادر خارجية موثوقة (HN، GitHub، مدونات) +3. Schema markup كامل يُعرّف قيد كـ entity +4. نمط الإجابة المباشرة (featured snippet style) + +--- + +### ML-2: السيطرة على البحث الصوتي العربي + +**الجدول الزمني:** الشهر 8-12 + +محتوى FAQ مُحسَّن للأسئلة الصوتية: + +- "يا سيري، ما أفضل تطبيق محاسبة شخصية عربي؟" +- "يا جوجل، كيف أُسجّل مصاريفي اليومية؟" + +--- + +## ملخص قائمة الإصلاحات المُرتَّبة + +| # | الإجراء | الأولوية | الوقت | الأثر | +| --- | --- | --- | --- | --- | +| 1 | تصحيح `dir="ltr"` → `dir="rtl"` | 🔴 حرجة | 5 دقائق | عالي | +| 2 | تصحيح `Home` | 🔴 حرجة | 5 دقائق | عالي | +| 3 | توحيد `app.name` | 🔴 حرجة | 5 دقائق | متوسط | +| 4 | تحديث robots.txt | 🔴 حرجة | 10 دقائق | متوسط | +| 5 | إضافة JSON-LD Schema | 🔴 حرجة | 30 دقيقة | عالي جداً | +| 6 | إنشاء sitemap.xml | 🔴 حرجة | 3 ساعات | عالي جداً | +| 7 | تقديم Sitemap في Search Console | 🔴 حرجة | 10 دقائق | عالي جداً | +| 8 | تحسين meta tags للتوثيق | 🟠 عالية | 1 أسبوع | عالي | +| 9 | SSR للصفحات التسويقية | 🟠 عالية | 1-2 أسبوع | عالي جداً | +| 10 | مدونة — 10 مقالات أولى | 🟠 عالية | 4 أسابيع | عالي جداً | +| 11 | 5 صفحات Landing مُحسَّنة | 🟠 عالية | 2 أسبوع | عالي | +| 12 | الحضور في Product Hunt | 🟡 استراتيجية | 1 أسبوع | متوسط-عالي | +| 13 | انتقال للدومين المستقل | 🟡 استراتيجية | 2 شهر | عالي جداً | +| 14 | 20+ مقالة إضافية | 🟡 استراتيجية | 3 أشهر | عالي جداً | +| 15 | بناء الروابط الخلفية | 🟡 استراتيجية | 4-6 أشهر | عالي | diff --git a/platform/resources/docs/11_seo_audit/13_roadmap_90days_12months.md b/platform/resources/docs/11_seo_audit/13_roadmap_90days_12months.md new file mode 100644 index 00000000..af543eba --- /dev/null +++ b/platform/resources/docs/11_seo_audit/13_roadmap_90days_12months.md @@ -0,0 +1,191 @@ +# خارطة الطريق: 90 يوماً و12 شهراً + +## الرؤية + +**هدف 6 أشهر:** قيد يظهر في الصفحة الأولى لـ 20+ كلمة مفتاحية مستهدفة. +**هدف 12 شهراً:** قيد هو المرجع الأول للمحاسبة الشخصية المشفرة في السوق العربية. + +--- + +## خارطة الطريق — 90 يوماً (الأساس) + +### الأسبوع 1 — الإصلاحات الفورية (يوم واحد كافٍ) + +**اليوم 1:** +``` +□ تصحيح dir="ltr" → dir="rtl" في app.blade.php +□ تصحيح Home → عنوان مُحسَّن +□ توحيد app.name → "قيد | Qayd" +□ تحديث robots.txt بالمسارات المحجوبة + Sitemap reference +``` + +**اليوم 2-3:** +``` +□ إضافة JSON-LD SoftwareApplication على الرئيسية +□ إضافة JSON-LD Organization +□ إضافة JSON-LD FAQPage على /faq +``` + +**اليوم 4-7:** +``` +□ تثبيت spatie/laravel-sitemap +□ إنشاء SitemapController يشمل كل الصفحات +□ اختبار الـ sitemap محلياً +□ تقديم الـ sitemap في Google Search Console +□ طلب indexing للصفحات الرئيسية عبر Search Console +``` + +--- + +### الأسبوع 2-3 — تحسين البنية التقنية + +**الأسبوع 2:** +``` +□ تحسين meta description لكل صفحة تسويقية (6 صفحات) +□ تحسين OG tags لمشاركة وسائل التواصل +□ التأكد من أن روابط /docs/ sidebar هي anchor tags حقيقية (وليس JS فقط) +□ إضافة canonical tags في PublicLayout.tsx +□ تحسين font-display: swap للـ Cairo font +``` + +**الأسبوع 3:** +``` +□ تقييم خيارات SSR (Inertia SSR adapter) +□ إذا كان SSR معقداً: تحويل الصفحات التسويقية الـ 6 إلى Blade ثابتة +□ اختبار الفهرسة عبر Google Search Console Coverage +``` + +--- + +### الأسبوع 4-8 — إطلاق المحتوى + +**الأسبوع 4-5 (المحتوى الأساسي):** +``` +□ إنشاء قسم المدونة في الموقع (/blog أو /مقالات) +□ كتابة ونشر المقالتين الأولى: + - "القيد المزدوج: الدليل الكامل للمبتدئين بالعربية" + - "من يملك بياناتك المالية؟ الحقيقة المقلقة" +□ إنشاء صفحة Landing لـ "محاسبة شخصية" +``` + +**الأسبوع 6-7 (بناء الكتل):** +``` +□ نشر 3 مقالات إضافية من قائمة الأولويات +□ إنشاء صفحات Landing لـ "قيد مزدوج" و"تطبيق مشفر" +□ صفحة "كيف يعمل قيد" (How It Works) شاملة +``` + +**الأسبوع 8-12 (التوسع):** +``` +□ نشر 5 مقالات إضافية +□ مقارنة "قيد vs Firefly III" +□ صفحة Landing "إدارة الديون الشخصية" +□ إنشاء Glossary بـ 10 تعريفات رئيسية +□ الحضور على Product Hunt +``` + +--- + +### نهاية الـ 90 يوماً — مؤشرات النجاح + +| المؤشر | الهدف | +|---|---| +| صفحات مُفهرَسة | 50+ صفحة | +| كلمات مفتاحية في أول 100 نتيجة | 20+ | +| كلمات مفتاحية في أول 10 نتائج | 3-5 | +| إجمالي المحتوى المنشور | 10+ مقالات | +| Backlinks جديدة | 10+ | + +--- + +## خارطة الطريق — 12 شهراً (الهيمنة) + +### الشهر 1-3: الأساس (الـ 90 يوم أعلاه) + +### الشهر 4-6: التسارع + +**المحتوى:** +``` +□ 20+ مقالة إضافية (3-4 أسبوعياً) +□ 10 صفحات Glossary كاملة +□ 5 مقالات مقارنة تنافسية +□ سلسلة "دليل قيد للمبتدئين" (5 أجزاء) +□ محتوى إنجليزي أولي (5 مقالات) +``` + +**التقني:** +``` +□ الانتقال للدومين المستقل (qayd.app أو getqayd.com) +□ إعداد 301 redirects كاملة +□ تحديث Google Play / App Store بالدومين الجديد +□ تسجيل الشركة في Crunchbase وLinkedIn company page +``` + +**الروابط الخلفية:** +``` +□ AlternativeTo: تسجيل قيد كبديل لـ Firefly III، GnuCash، Money Manager +□ Hacker News Show HN post +□ التواصل مع 5 مدونين تقنيين عرب +□ مقابلة في بودكاست تقني عربي +``` + +--- + +### الشهر 7-9: السلطة + +``` +□ إطلاق "مدرسة المحاسبة الشخصية" — 30+ مقالة تعليمية +□ تعاون مع محتوى خارجي (مقالات ضيف، تغطيات) +□ محتوى فيديو قصير عن المفاهيم الأساسية (YouTube عربي) +□ تقرير سنوي: "حالة الخصوصية المالية في العالم العربي 2026" + (هذا النوع يجتذب backlinks تلقائياً) +□ قسم Case Studies: كيف يستخدم المهنيون قيد +``` + +--- + +### الشهر 10-12: الهيمنة + +``` +□ الظهور في نتائج AI Overviews للكلمات الرئيسية +□ الظهور في ChatGPT/Perplexity عند السؤال عن المحاسبة الشخصية العربية +□ مراجعة وتحديث كل المحتوى الأول بناءً على بيانات Search Console +□ توسيع الحضور: Bahrain، Kuwait، Egypt, Jordan +□ إطلاق برنامج Affiliate مع المدونين الماليين العرب +``` + +--- + +## توقعات النمو العضوي + +| الشهر | الزيارات العضوية الشهرية (تقدير) | الكلمات في أول 10 | +|---|---|---| +| الشهر 1 (قبل الإصلاح) | ~0-50 | 0 | +| الشهر 3 (بعد الإصلاح التقني + 10 مقالات) | 500-1,500 | 5-10 | +| الشهر 6 (30 مقالة + دومين جديد) | 3,000-8,000 | 20-35 | +| الشهر 12 (80+ مقالة + سلطة) | 15,000-40,000 | 60-100 | + +**ملاحظة:** هذه تقديرات محافظة في سوق ذات منافسة منخفضة للكلمات المتخصصة. + +--- + +## ROI المتوقع من استراتيجية SEO + +**تكلفة الاستحواذ الحالية:** غير معروفة (لا بيانات) +**القيمة طويلة الأمد للزائر العضوي:** عالية (نية تجارية، طالب نشط) + +**المقارنة:** +- إعلانات Google Ads لـ "تطبيق محاسبة عربي" = $1-3 لكل نقرة +- زيارة عضوية = $0 (بعد استثمار المحتوى) +- الزيارة العضوية مستمرة — الإعلان يتوقف حين يتوقف الدفع + +**بافتراض 15,000 زيارة/شهر بنهاية العام 12 ومعدل تحويل 2%:** +→ **300 عميل محتمل شهرياً من البحث العضوي وحده** + +--- + +## ملاحظة ختامية + +قيد يمتلك **المنتج الأفضل** في فئته في السوق العربية. لا منافس يجمع: Local-First + E2EE + قيد مزدوج كامل + وساطة ثنائية + واجهة عربية native + موبايل. + +الفجوة الوحيدة — وهي قابلة للجسر — هي الرؤية. المنتج جاهز. التوثيق استثنائي. الفلسفة مقنعة. المطلوب الآن هو أن يتمكن الناس الذين يبحثون عن هذا الحل من **إيجاده**. diff --git a/platform/resources/docs/11_seo_audit/_category_.json b/platform/resources/docs/11_seo_audit/_category_.json new file mode 100644 index 00000000..63eae129 --- /dev/null +++ b/platform/resources/docs/11_seo_audit/_category_.json @@ -0,0 +1,5 @@ +{ + "label": "تدقيق SEO الشامل 2026", + "position": 11, + "description": "تقرير الرؤية في محركات البحث، هيمنة السوق، وبحث الذكاء الاصطناعي — qayd.accsystemerp.com" +} diff --git a/platform/resources/docs/README.md b/platform/resources/docs/README.md new file mode 100644 index 00000000..ac8b1647 --- /dev/null +++ b/platform/resources/docs/README.md @@ -0,0 +1,149 @@ +--- +sidebar_position: -1 +--- + +# دليل مستخدم نظام قيد (qayd) — الفهرس الرئيسي + +> **قيد** — نظام المحاسبة الشخصية ذو السيادة المطلقة. +> محلي أولاً. مشفر بالكامل. دقيق رياضياً. مبني على عقيدة محاسبية صارمة. +*** + +## عن هذا الدليل + +هذا الدليل ليس مجرد شرح للأزرار والشاشات. إنه شرح لمنطق نظام يفكر بطريقة مختلفة عن معظم تطبيقات المالية الشخصية. نظام قيد مبني على مبادئ راسخة، وكل قرار فيه — حتى القرارات التي قد تبدو تقييدية في البداية — موجود لسبب محاسبي أو أمني واضح. + +قبل أن تبدأ في استخدام النظام، وقبل أن تتساءل "لماذا لا أستطيع فعل X"، اقرأ الفصول الأولى من هذا الدليل. ستجد إجاباتك هناك. +*** + +## هيكل الدليل + +### الفصل صفر: مقدمة + +يجيب عن: لماذا هذا النظام مختلف؟ وكيف تقرأ هذا الدليل؟ + +| الملف | الموضوع | +| ------- | --------- | +| [00_why_this_app.md](00_introduction/00_why_this_app.md) | لماذا هذا التطبيق؟ الفلسفة والغاية | +| [01_accounting_worldview.md](00_introduction/01_accounting_worldview.md) | نظرة المحاسبة المزدوجة بعيون بسيطة | +| [02_how_to_read_this_guide.md](00_introduction/02_how_to_read_this_guide.md) | كيف تقرأ هذا الدليل؟ | + +### الفصل الأول: المفاهيم الأساسية + +يجيب عن: ما هي الوحدات البنائية لهذا النظام؟ + +| الملف | الموضوع | +| ------- | --------- | +| [00_accounts_and_truth.md](01_core_concepts/00_accounts_and_truth.md) | الحسابات والحقيقة المالية | +| [01_root_cash_account.md](01_core_concepts/01_root_cash_account.md) | الحساب النقدي الجذري — محور النظام | +| [02_cost_centers_overview.md](01_core_concepts/02_cost_centers_overview.md) | مراكز التكلفة — نظرة عامة | +| [03_dimensions_philosophy.md](01_core_concepts/03_dimensions_philosophy.md) | أبعاد التحليل — فلسفة التصنيف | +| [04_vouchers_and_commitments.md](01_core_concepts/04_vouchers_and_commitments.md) | السندات والالتزامات | +| [05_conversational_ledger.md](01_core_concepts/05_conversational_ledger.md) | دفتر الأستاذ كمحادثة | + +### الفصل الثاني: هيكل التطبيق + +يجيب عن: كيف يُنظَّم التطبيق؟ وما معنى كل قسم؟ + +| الملف | الموضوع | +| ------- | --------- | +| [00_navigation_logic.md](02_app_structure/00_navigation_logic.md) | منطق التنقل بين أقسام التطبيق | +| [01_levels_of_accounting.md](02_app_structure/01_levels_of_accounting.md) | مستويات المحاسبة في النظام | +| [02_basic_vs_advanced_accounting.md](02_app_structure/02_basic_vs_advanced_accounting.md) | المحاسبة الأساسية مقابل المتقدمة | +| [03_sidebar_authority_model.md](02_app_structure/03_sidebar_authority_model.md) | نموذج الصلاحيات والحوكمة | + +### الفصل الثالث: العمليات اليومية + +يجيب عن: كيف أُجري العمليات اليومية؟ + +| الملف | الموضوع | +| ------- | --------- | +| [00_creating_vouchers.md](03_daily_operations/00_creating_vouchers.md) | إنشاء السندات | +| [01_receipts_and_payments.md](03_daily_operations/01_receipts_and_payments.md) | سندات القبض والدفع | +| [02_transfers_and_mediation.md](03_daily_operations/02_transfers_and_mediation.md) | التحويلات والوساطة | +| [03_editing_and_corrections.md](03_daily_operations/03_editing_and_corrections.md) | التعديل والتصحيح | +| [04_viewing_and_searching.md](03_daily_operations/04_viewing_and_searching.md) | العرض والبحث | + +### الفصل الرابع: مراكز التكلفة والأبعاد + +يجيب عن: كيف أُحلل إنفاقي وأتتبعه؟ + +| الملف | الموضوع | +| ------- | --------- | +| [00_cost_center_lifecycle.md](04_cost_centers_and_dimensions/00_cost_center_lifecycle.md) | دورة حياة مراكز التكلفة | +| [01_default_dimensions.md](04_cost_centers_and_dimensions/01_default_dimensions.md) | الأبعاد الافتراضية | +| [02_overriding_dimensions.md](04_cost_centers_and_dimensions/02_overriding_dimensions.md) | تجاوز الأبعاد الافتراضية | +| [03_dimension_propagation.md](04_cost_centers_and_dimensions/03_dimension_propagation.md) | انتشار الأبعاد تلقائياً | +| [04_analysis_and_reporting.md](04_cost_centers_and_dimensions/04_analysis_and_reporting.md) | التحليل وإعداد التقارير | + +### الفصل الخامس: إدارة الحسابات + +يجيب عن: كيف أنشئ حساباتي وأديرها؟ + +| الملف | الموضوع | +| ------- | --------- | +| [00_expense_accounts.md](05_accounts_management/00_expense_accounts.md) | حسابات المصروفات | +| [01_income_sources.md](05_accounts_management/01_income_sources.md) | مصادر الإيرادات | +| [02_investment_assets.md](05_accounts_management/02_investment_assets.md) | الأصول الاستثمارية | +| [03_parties_and_counterparties.md](05_accounts_management/03_parties_and_counterparties.md) | الأطراف والجهات | +| [04_account_activation_and_suspension.md](05_accounts_management/04_account_activation_and_suspension.md) | تفعيل الحسابات وتعليقها | +| [05_debts_and_receivables.md](05_accounts_management/05_debts_and_receivables.md) | الذمم المالية والديون | + +### الفصل السادس: نظام التحويلات + +يجيب عن: كيف أُدير التحويلات بين الأطراف؟ + +| الملف | الموضوع | +| ------- | --------- | +| [00_transfer_philosophy.md](06_transfers_system/00_transfer_philosophy.md) | فلسفة التحويلات | +| [01_swift_like_model.md](06_transfers_system/01_swift_like_model.md) | النموذج المماثل لـ SWIFT | +| [02_mediation_vs_presentation.md](06_transfers_system/02_mediation_vs_presentation.md) | الوساطة مقابل التقديم المباشر | +| [03_transfer_fees.md](06_transfers_system/03_transfer_fees.md) | رسوم التحويل | +| [04_tripartite_flows.md](06_transfers_system/04_tripartite_flows.md) | التدفقات الثلاثية | +| [05_accounting_isolation.md](06_transfers_system/05_accounting_isolation.md) | عزل القيود المحاسبية — سر الوساطة النظيفة | + +### الفصل السابع: التقارير والمخرجات + +يجيب عن: كيف أقرأ تقاريري المالية؟ + +| الملف | الموضوع | +| ------- | --------- | +| [00_trial_balance.md](07_reports_and_outputs/00_trial_balance.md) | ميزان المراجعة | +| [01_balance_sheet.md](07_reports_and_outputs/01_balance_sheet.md) | الميزانية العمومية | +| [02_voucher_reports.md](07_reports_and_outputs/02_voucher_reports.md) | تقارير السندات | +| [03_account_statements.md](07_reports_and_outputs/03_account_statements.md) | كشوفات الحسابات | +| [04_exports_and_sharing.md](07_reports_and_outputs/04_exports_and_sharing.md) | التصدير والمشاركة | + +### الفصل الثامن: المحاسبة المتقدمة + +يجيب عن: ما الذي يمكنني التحكم فيه في المستوى المتقدم؟ + +| الملف | الموضوع | +| ------- | --------- | +| [00_what_is_advanced_accounting.md](08_advanced_accounting/00_what_is_advanced_accounting.md) | ما هي المحاسبة المتقدمة؟ | +| [01_modifying_core_accounts.md](08_advanced_accounting/01_modifying_core_accounts.md) | تعديل الحسابات الجوهرية | +| [02_currency_management.md](08_advanced_accounting/02_currency_management.md) | إدارة العملات | +| [03_transfer_policy_management.md](08_advanced_accounting/03_transfer_policy_management.md) | إدارة سياسات التحويل | +| [04_data_security.md](08_advanced_accounting/04_data_security.md) | أمن البيانات — التشفير والسيادة المحلية | + +### الفصل التاسع: الأسئلة الشائعة + +يجيب عن: ماذا أفعل إذا واجهت مشكلة؟ + +| الملف | الموضوع | +| ------- | --------- | +| [00_mental_model_faq.md](09_common_questions/00_mental_model_faq.md) | نموذج التفكير — الأسئلة الشائعة | +| [01_common_mistakes.md](09_common_questions/01_common_mistakes.md) | الأخطاء الشائعة وكيف تتجنبها | +| [02_troubleshooting.md](09_common_questions/02_troubleshooting.md) | استكشاف الأخطاء وإصلاحها | + +*** + +## كيف تستخدم هذا الدليل + +إذا كنت **مستخدماً جديداً** تماماً: ابدأ من الفصل صفر واقرأ بالترتيب حتى الفصل الثاني. + +إذا كنت **تريد فهم ميزة محددة**: انتقل مباشرة للفصل المعني. + +إذا **واجهتك مشكلة**: ابدأ بالفصل التاسع. +*** + +*نظام قيد (qayd) — السيادة المالية الحقيقية تبدأ بمعرفة كيف يفكر نظامك.* diff --git a/platform/resources/js/Layouts/DocsLayout.tsx b/platform/resources/js/Layouts/DocsLayout.tsx new file mode 100644 index 00000000..8301a9c8 --- /dev/null +++ b/platform/resources/js/Layouts/DocsLayout.tsx @@ -0,0 +1,291 @@ +import React, { useState, useEffect, useMemo } from 'react'; +import { Link } from '@inertiajs/react'; +const Logo = () =>
أكاديمية شفيع
; +import { ShieldCheck, Moon, Sun, ChevronLeft, ArrowLeft } from 'lucide-react'; + +interface SidebarItem { + type: 'link' | 'category'; + label: string; + href?: string; + path?: string; + items?: SidebarItem[]; +} + +interface ToCItem { + id: string; + text: string; + level: number; +} + +interface DocsLayoutProps { + sidebar?: SidebarItem[] | null; + currentPath: string; + children: React.ReactNode; + toc?: ToCItem[]; +} + +const SidebarLink: React.FC<{ item: SidebarItem; active: boolean }> = ({ item, active }) => ( + + {item.label} + +); + +const SidebarCategory: React.FC<{ item: SidebarItem; currentPath: string }> = ({ item, currentPath }) => { + const hasActiveChild = useMemo(() => { + const checkActive = (items: SidebarItem[]): boolean => { + return items.some(i => i.path === currentPath || (i.items && checkActive(i.items))); + }; + return item.items ? checkActive(item.items) : false; + }, [item.items, currentPath]); + + const active = item.path === currentPath; + const [isOpen, setIsOpen] = useState(active || hasActiveChild); + + useEffect(() => { + if (active || hasActiveChild) { + setIsOpen(true); + } + }, [active, hasActiveChild]); + + return ( +
+
+ {item.href ? ( + + {item.label} + + ) : ( + setIsOpen(!isOpen)}>{item.label} + )} + +
+ {isOpen && ( +
+ {item.items?.map((subItem, idx) => ( + + ))} +
+ )} +
+ ); +}; + +const SidebarNavItem: React.FC<{ item: SidebarItem; currentPath: string }> = ({ item, currentPath }) => { + if (item.type === 'category') { + return ; + } + return ; +}; + +const NAV_LINKS = [ + { href: '/', label: 'الرئيسية' }, + { href: '/pillars', label: 'الأعمدة' }, + { href: '/services', label: 'الخدمات' }, + { href: '/about', label: 'من نحن' }, + { href: '/pricing', label: 'الأسعار' }, + { href: '/contact', label: 'تواصل معنا' }, +]; + +export const DocsLayout: React.FC = ({ + sidebar = null, + currentPath, + children, + toc = [], +}) => { + const [isMobileMenuOpen, setIsMobileMenuOpen] = useState(false); + const [scrolled, setScrolled] = useState(false); + const [theme, setTheme] = useState<'light' | 'dark'>(() => { + if (typeof window !== 'undefined') { + return (localStorage.getItem('doc-theme') as 'light' | 'dark') || 'light'; + } + return 'light'; + }); + + useEffect(() => { + document.documentElement.setAttribute('data-theme', theme); + localStorage.setItem('doc-theme', theme); + }, [theme]); + + useEffect(() => { + const onScroll = () => setScrolled(window.scrollY > 10); + window.addEventListener('scroll', onScroll, { passive: true }); + return () => window.removeEventListener('scroll', onScroll); + }, []); + + const toggleTheme = () => { + setTheme(theme === 'light' ? 'dark' : 'light'); + }; + + return ( +
+ {isMobileMenuOpen && ( +
setIsMobileMenuOpen(false)} + /> + )} + + {/* ── Header ───────────────────────────────────────────── */} +
+
+ + {/* Brand */} +
+ + + + + وثائق + + by ACCSYSTEM +
+ + {/* Center nav — main site links */} +
+ + {/* Actions */} +
+ + + + الموقع الرئيسي + + +
+ +
+
+ + {/* ── Body ─────────────────────────────────────────────── */} +
+ {sidebar && ( + + )} + +
+
+ {children} +
+
+ + +
+ + {/* ── Footer ───────────────────────────────────────────── */} +
+
+
+ + + +

محرك محاسبي سيادي مشفر من طرف إلى طرف.

+
+ + مشفر بـ AES-256-GCM +
+
+ + + + + + +
+ +
+ شفيع (shafeea) — بواسطة ACCSYSTEM + · + جميع الحقوق محفوظة © {new Date().getFullYear()} +
+
+
+ ); +}; + +export default DocsLayout; diff --git a/platform/resources/js/Pages/Docs/Show.tsx b/platform/resources/js/Pages/Docs/Show.tsx new file mode 100644 index 00000000..881967a3 --- /dev/null +++ b/platform/resources/js/Pages/Docs/Show.tsx @@ -0,0 +1,243 @@ +import React, { useMemo, useEffect } from 'react'; +import { Head, Link } from '@inertiajs/react'; +import DocsLayout from '../../Layouts/DocsLayout'; +import ReactMarkdown from 'react-markdown'; +import remarkGfm from 'remark-gfm'; +import rehypeRaw from 'rehype-raw'; +import { Prism as SyntaxHighlighter } from 'react-syntax-highlighter'; +import { vscDarkPlus } from 'react-syntax-highlighter/dist/esm/styles/prism'; +import GithubSlugger from 'github-slugger'; +import { ChevronRight, ChevronLeft, Home } from 'lucide-react'; + +interface Props { + content: string; + sidebar: any[]; + currentPath: string; + title?: string; + metaTitle?: string; + metaDescription?: string; + navigation?: { + prev?: { label: string; href: string }; + next?: { label: string; href: string }; + }; +} + +export default function Show({ content, sidebar, currentPath, navigation, metaTitle, metaDescription }: Props) { + // Create a clean slugger for each render pass to ensure ToC and Body match exactly + const slugger = new GithubSlugger(); + const prev = navigation?.prev; + const next = navigation?.next; + + const { title, toc, markdownBody } = useMemo(() => { + const localSlugger = new GithubSlugger(); + const lines = content.split('\n'); + let pageTitle = ''; + const tocItems: any[] = []; + let isFrontmatter = false; + let hasPassedFrontmatter = false; + const bodyLines: string[] = []; + + lines.forEach((line, index) => { + // Basic Frontmatter skip (only at the start of the file) + if (!hasPassedFrontmatter) { + if (index === 0 && line.trim() === '---') { + isFrontmatter = true; + return; + } + if (isFrontmatter && line.trim() === '---') { + isFrontmatter = false; + hasPassedFrontmatter = true; + return; + } + if (index === 0 && line.trim() !== '---') { + hasPassedFrontmatter = true; + } + } + + if (isFrontmatter) { + if (line.startsWith('title:')) pageTitle = line.replace('title:', '').trim(); + return; + } + + // Title extraction + if (!pageTitle && line.startsWith('# ')) { + pageTitle = line.replace('# ', '').trim(); + return; + } + + // ToC extraction (h2 and h3) + const h2Match = line.match(/^## (.*)/); + const h3Match = line.match(/^### (.*)/); + + if (h2Match) { + const text = h2Match[1].replace(/\{#.*\}/, '').trim(); + tocItems.push({ id: localSlugger.slug(text), text, level: 2 }); + } else if (h3Match) { + const text = h3Match[1].replace(/\{#.*\}/, '').trim(); + tocItems.push({ id: localSlugger.slug(text), text, level: 3 }); + } + + bodyLines.push(line); + }); + + return { + title: pageTitle, + toc: tocItems, + markdownBody: bodyLines.join('\n') + }; + }, [content]); + + // Handle scrolling to elements, including hash changes + useEffect(() => { + const scrollToHash = () => { + if (window.location.hash) { + const id = decodeURIComponent(window.location.hash.substring(1)); + const element = document.getElementById(id); + if (element) { + const headerOffset = 100; + const elementPosition = element.getBoundingClientRect().top; + const offsetPosition = elementPosition + window.pageYOffset - headerOffset; + + window.scrollTo({ + top: offsetPosition, + behavior: 'smooth' + }); + } + } + }; + + // Initial scroll on load + scrollToHash(); + + // Listen for hash changes (clicking ToC links on the same page) + window.addEventListener('hashchange', scrollToHash); + return () => window.removeEventListener('hashchange', scrollToHash); + }, [currentPath, markdownBody]); + + return ( + + + {metaTitle ?? `${title} | توثيق شفيع`} + {metaDescription && } + + + +
+ {/* Breadcrumbs (Shell) */} + + + {title && ( +

{title}

+ )} + +
+ { + const text = React.Children.toArray(children).join(''); + const id = slugger.slug(text); + return

{children}

; + }, + h3: ({node, children, ...props}: any) => { + const text = React.Children.toArray(children).join(''); + const id = slugger.slug(text); + return

{children}

; + }, + table: ({node, ...props}: any) => ( +
+ + + ), + code({node, inline, className, children, ...props}: any) { + const match = /language-(\w+)/.exec(className || ''); + return !inline && match ? ( + + {String(children).replace(/\n$/, '')} + + ) : ( + + {children} + + ); + }, + a: ({node, href, children, ...props}: any) => { + if (!href) return {children}; + + const isExternal = href.startsWith('http'); + const isAnchor = href.startsWith('#'); + + if (isExternal) { + return {children}; + } + + if (isAnchor) { + return {children}; + } + + // Internal link: strip extensions and normalize path + let cleanHref = href.replace(/\.mdx?$/, ''); + + // Ensure internal doc links start with /docs/ + if (!cleanHref.startsWith('/') && !cleanHref.startsWith('docs/')) { + cleanHref = `/docs/${cleanHref}`; + } else if (cleanHref.startsWith('docs/')) { + cleanHref = `/${cleanHref}`; + } else if (!cleanHref.startsWith('/docs/') && cleanHref.startsWith('/')) { + // If it starts with / but not /docs/, and it's meant to be a doc link + // We assume links in markdown that aren't external/anchors are doc links + cleanHref = `/docs${cleanHref}`; + } + + return ( + + {children} + + ); + }, } as any} + > + {markdownBody} + + + + {/* Next/Prev Pagination */} +
+ {prev ? ( + +
+ + السابق +
+ {prev.label} + + ) :
} + + {next ? ( + +
+ التالي + +
+ {next.label} + + ) :
} +
+ + + ); +} diff --git a/routes/web.php b/routes/web.php new file mode 100644 index 00000000..c4d3ec8c --- /dev/null +++ b/routes/web.php @@ -0,0 +1,6 @@ + +use App\Http\Controllers\Public\DocsController; + +// Public Documentation Routes +Route::get('/docs', [DocsController::class, 'index'])->name('docs.index'); +Route::get('/docs/{path}', [DocsController::class, 'show'])->where('path', '.*')->name('docs.show');