@mytechtoday/augment-extensions 0.1.2 → 0.4.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +614 -39
- package/augment-extensions/coding-standards/bash/README.md +196 -0
- package/augment-extensions/coding-standards/bash/module.json +163 -0
- package/augment-extensions/coding-standards/bash/rules/naming-conventions.md +336 -0
- package/augment-extensions/coding-standards/bash/rules/universal-standards.md +289 -0
- package/augment-extensions/coding-standards/css/README.md +40 -0
- package/augment-extensions/coding-standards/css/examples/css-examples.css +550 -0
- package/augment-extensions/coding-standards/css/module.json +44 -0
- package/augment-extensions/coding-standards/css/rules/css-modern-features.md +448 -0
- package/augment-extensions/coding-standards/css/rules/css-standards.md +492 -0
- package/augment-extensions/coding-standards/html/README.md +40 -0
- package/augment-extensions/coding-standards/html/examples/html-examples.html +267 -0
- package/augment-extensions/coding-standards/html/examples/responsive-layout.html +505 -0
- package/augment-extensions/coding-standards/html/module.json +44 -0
- package/augment-extensions/coding-standards/html/rules/html-standards.md +349 -0
- package/augment-extensions/coding-standards/html-css-js/README.md +194 -0
- package/augment-extensions/coding-standards/html-css-js/examples/async-examples.js +487 -0
- package/augment-extensions/coding-standards/html-css-js/examples/css-examples.css +550 -0
- package/augment-extensions/coding-standards/html-css-js/examples/dom-examples.js +667 -0
- package/augment-extensions/coding-standards/html-css-js/examples/html-examples.html +267 -0
- package/augment-extensions/coding-standards/html-css-js/examples/javascript-examples.js +612 -0
- package/augment-extensions/coding-standards/html-css-js/examples/responsive-layout.html +505 -0
- package/augment-extensions/coding-standards/html-css-js/module.json +48 -0
- package/augment-extensions/coding-standards/html-css-js/rules/async-patterns.md +515 -0
- package/augment-extensions/coding-standards/html-css-js/rules/css-modern-features.md +448 -0
- package/augment-extensions/coding-standards/html-css-js/rules/css-standards.md +492 -0
- package/augment-extensions/coding-standards/html-css-js/rules/dom-manipulation.md +439 -0
- package/augment-extensions/coding-standards/html-css-js/rules/html-standards.md +349 -0
- package/augment-extensions/coding-standards/html-css-js/rules/javascript-standards.md +486 -0
- package/augment-extensions/coding-standards/html-css-js/rules/performance.md +463 -0
- package/augment-extensions/coding-standards/html-css-js/rules/tooling.md +543 -0
- package/augment-extensions/coding-standards/js/README.md +46 -0
- package/augment-extensions/coding-standards/js/examples/async-examples.js +487 -0
- package/augment-extensions/coding-standards/js/examples/dom-examples.js +667 -0
- package/augment-extensions/coding-standards/js/examples/javascript-examples.js +612 -0
- package/augment-extensions/coding-standards/js/module.json +49 -0
- package/augment-extensions/coding-standards/js/rules/async-patterns.md +515 -0
- package/augment-extensions/coding-standards/js/rules/dom-manipulation.md +439 -0
- package/augment-extensions/coding-standards/js/rules/javascript-standards.md +486 -0
- package/augment-extensions/coding-standards/js/rules/performance.md +463 -0
- package/augment-extensions/coding-standards/js/rules/tooling.md +543 -0
- package/augment-extensions/coding-standards/php/README.md +248 -0
- package/augment-extensions/coding-standards/php/examples/api-endpoint-example.php +204 -0
- package/augment-extensions/coding-standards/php/examples/cli-command-example.php +206 -0
- package/augment-extensions/coding-standards/php/examples/legacy-refactoring-example.php +234 -0
- package/augment-extensions/coding-standards/php/examples/web-application-example.php +211 -0
- package/augment-extensions/coding-standards/php/examples/woocommerce-extension-example.php +215 -0
- package/augment-extensions/coding-standards/php/examples/wordpress-plugin-example.php +189 -0
- package/augment-extensions/coding-standards/php/module.json +166 -0
- package/augment-extensions/coding-standards/php/rules/api-development.md +480 -0
- package/augment-extensions/coding-standards/php/rules/category-configuration.md +332 -0
- package/augment-extensions/coding-standards/php/rules/cli-tools.md +472 -0
- package/augment-extensions/coding-standards/php/rules/cms-integration.md +561 -0
- package/augment-extensions/coding-standards/php/rules/code-quality.md +402 -0
- package/augment-extensions/coding-standards/php/rules/documentation.md +425 -0
- package/augment-extensions/coding-standards/php/rules/ecommerce.md +627 -0
- package/augment-extensions/coding-standards/php/rules/error-handling.md +336 -0
- package/augment-extensions/coding-standards/php/rules/legacy-migration.md +677 -0
- package/augment-extensions/coding-standards/php/rules/naming-conventions.md +279 -0
- package/augment-extensions/coding-standards/php/rules/performance.md +392 -0
- package/augment-extensions/coding-standards/php/rules/psr-standards.md +186 -0
- package/augment-extensions/coding-standards/php/rules/security.md +358 -0
- package/augment-extensions/coding-standards/php/rules/testing.md +403 -0
- package/augment-extensions/coding-standards/php/rules/type-declarations.md +331 -0
- package/augment-extensions/coding-standards/php/rules/web-applications.md +426 -0
- package/augment-extensions/coding-standards/powershell/README.md +154 -0
- package/augment-extensions/coding-standards/powershell/examples/admin-example.ps1 +272 -0
- package/augment-extensions/coding-standards/powershell/examples/automation-example.ps1 +173 -0
- package/augment-extensions/coding-standards/powershell/examples/cloud-example.ps1 +243 -0
- package/augment-extensions/coding-standards/powershell/examples/cross-platform-example.ps1 +297 -0
- package/augment-extensions/coding-standards/powershell/examples/dsc-example.ps1 +224 -0
- package/augment-extensions/coding-standards/powershell/examples/legacy-migration-example.ps1 +340 -0
- package/augment-extensions/coding-standards/powershell/examples/module-example.psm1 +255 -0
- package/augment-extensions/coding-standards/powershell/module.json +165 -0
- package/augment-extensions/coding-standards/powershell/rules/administrative-tools.md +439 -0
- package/augment-extensions/coding-standards/powershell/rules/automation-scripts.md +240 -0
- package/augment-extensions/coding-standards/powershell/rules/cloud-orchestration.md +384 -0
- package/augment-extensions/coding-standards/powershell/rules/configuration-schema.md +383 -0
- package/augment-extensions/coding-standards/powershell/rules/cross-platform-scripts.md +482 -0
- package/augment-extensions/coding-standards/powershell/rules/dsc-configurations.md +296 -0
- package/augment-extensions/coding-standards/powershell/rules/error-handling.md +314 -0
- package/augment-extensions/coding-standards/powershell/rules/legacy-migrations.md +466 -0
- package/augment-extensions/coding-standards/powershell/rules/modules-functions.md +244 -0
- package/augment-extensions/coding-standards/powershell/rules/naming-conventions.md +266 -0
- package/augment-extensions/coding-standards/powershell/rules/performance-optimization.md +209 -0
- package/augment-extensions/coding-standards/powershell/rules/security-practices.md +314 -0
- package/augment-extensions/coding-standards/powershell/rules/testing-guidelines.md +268 -0
- package/augment-extensions/coding-standards/powershell/rules/universal-standards.md +197 -0
- package/augment-extensions/coding-standards/python/README.md +12 -8
- package/augment-extensions/coding-standards/python/examples/best-practices.py +373 -0
- package/augment-extensions/coding-standards/python/module.json +8 -4
- package/augment-extensions/coding-standards/python/rules/async-patterns.md +884 -0
- package/augment-extensions/coding-standards/python/rules/documentation.md +831 -0
- package/augment-extensions/coding-standards/python/rules/error-handling.md +855 -68
- package/augment-extensions/coding-standards/python/rules/testing.md +409 -0
- package/augment-extensions/coding-standards/python/rules/tooling.md +446 -0
- package/augment-extensions/coding-standards/python/rules/type-hints.md +115 -50
- package/augment-extensions/collections/html-css-js/README.md +82 -0
- package/augment-extensions/collections/html-css-js/collection.json +41 -0
- package/augment-extensions/domain-rules/database/README.md +161 -0
- package/augment-extensions/domain-rules/database/examples/flat-database-example.md +793 -0
- package/augment-extensions/domain-rules/database/examples/hybrid-database-example.md +1132 -0
- package/augment-extensions/domain-rules/database/examples/nosql-document-example.md +868 -0
- package/augment-extensions/domain-rules/database/examples/nosql-graph-example.md +805 -0
- package/augment-extensions/domain-rules/database/examples/relational-schema-example.md +621 -0
- package/augment-extensions/domain-rules/database/examples/vector-database-example.md +965 -0
- package/augment-extensions/domain-rules/database/module.json +28 -0
- package/augment-extensions/domain-rules/database/rules/flat-databases.md +624 -0
- package/augment-extensions/domain-rules/database/rules/nosql-databases.md +588 -0
- package/augment-extensions/domain-rules/database/rules/nosql-document-stores.md +856 -0
- package/augment-extensions/domain-rules/database/rules/nosql-graph-databases.md +778 -0
- package/augment-extensions/domain-rules/database/rules/nosql-key-value-stores.md +963 -0
- package/augment-extensions/domain-rules/database/rules/performance-optimization.md +1076 -0
- package/augment-extensions/domain-rules/database/rules/relational-databases.md +697 -0
- package/augment-extensions/domain-rules/database/rules/relational-indexing.md +671 -0
- package/augment-extensions/domain-rules/database/rules/relational-query-optimization.md +607 -0
- package/augment-extensions/domain-rules/database/rules/relational-schema-design.md +907 -0
- package/augment-extensions/domain-rules/database/rules/relational-transactions.md +783 -0
- package/augment-extensions/domain-rules/database/rules/security-standards.md +980 -0
- package/augment-extensions/domain-rules/database/rules/universal-best-practices.md +485 -0
- package/augment-extensions/domain-rules/database/rules/vector-databases.md +521 -0
- package/augment-extensions/domain-rules/database/rules/vector-embeddings.md +858 -0
- package/augment-extensions/domain-rules/database/rules/vector-indexing.md +934 -0
- package/augment-extensions/domain-rules/mcp/README.md +150 -0
- package/augment-extensions/domain-rules/mcp/examples/compressed-example.md +522 -0
- package/augment-extensions/domain-rules/mcp/examples/graph-augmented-example.md +520 -0
- package/augment-extensions/domain-rules/mcp/examples/hybrid-example.md +570 -0
- package/augment-extensions/domain-rules/mcp/examples/state-based-example.md +427 -0
- package/augment-extensions/domain-rules/mcp/examples/token-based-example.md +435 -0
- package/augment-extensions/domain-rules/mcp/examples/vector-based-example.md +502 -0
- package/augment-extensions/domain-rules/mcp/module.json +49 -0
- package/augment-extensions/domain-rules/mcp/rules/compressed-mcp.md +595 -0
- package/augment-extensions/domain-rules/mcp/rules/configuration.md +345 -0
- package/augment-extensions/domain-rules/mcp/rules/graph-augmented-mcp.md +687 -0
- package/augment-extensions/domain-rules/mcp/rules/hybrid-mcp.md +636 -0
- package/augment-extensions/domain-rules/mcp/rules/state-based-mcp.md +484 -0
- package/augment-extensions/domain-rules/mcp/rules/testing-validation.md +360 -0
- package/augment-extensions/domain-rules/mcp/rules/token-based-mcp.md +393 -0
- package/augment-extensions/domain-rules/mcp/rules/universal-rules.md +194 -0
- package/augment-extensions/domain-rules/mcp/rules/vector-based-mcp.md +625 -0
- package/augment-extensions/domain-rules/wordpress/README.md +163 -0
- package/augment-extensions/domain-rules/wordpress/module.json +32 -0
- package/augment-extensions/domain-rules/wordpress/rules/coding-standards.md +617 -0
- package/augment-extensions/domain-rules/wordpress/rules/directory-structure.md +270 -0
- package/augment-extensions/domain-rules/wordpress/rules/file-patterns.md +423 -0
- package/augment-extensions/domain-rules/wordpress/rules/gutenberg-blocks.md +493 -0
- package/augment-extensions/domain-rules/wordpress/rules/performance.md +568 -0
- package/augment-extensions/domain-rules/wordpress/rules/plugin-development.md +510 -0
- package/augment-extensions/domain-rules/wordpress/rules/project-detection.md +251 -0
- package/augment-extensions/domain-rules/wordpress/rules/rest-api.md +501 -0
- package/augment-extensions/domain-rules/wordpress/rules/security.md +564 -0
- package/augment-extensions/domain-rules/wordpress/rules/theme-development.md +388 -0
- package/augment-extensions/domain-rules/wordpress/rules/woocommerce.md +441 -0
- package/augment-extensions/domain-rules/wordpress-plugin/README.md +139 -0
- package/augment-extensions/domain-rules/wordpress-plugin/examples/ajax-plugin.md +1599 -0
- package/augment-extensions/domain-rules/wordpress-plugin/examples/custom-post-type-plugin.md +1727 -0
- package/augment-extensions/domain-rules/wordpress-plugin/examples/gutenberg-block-plugin.md +428 -0
- package/augment-extensions/domain-rules/wordpress-plugin/examples/gutenberg-block.md +422 -0
- package/augment-extensions/domain-rules/wordpress-plugin/examples/mvc-plugin.md +1623 -0
- package/augment-extensions/domain-rules/wordpress-plugin/examples/object-oriented-plugin.md +1343 -0
- package/augment-extensions/domain-rules/wordpress-plugin/examples/rest-endpoint.md +734 -0
- package/augment-extensions/domain-rules/wordpress-plugin/examples/settings-page-plugin.md +1350 -0
- package/augment-extensions/domain-rules/wordpress-plugin/examples/simple-procedural-plugin.md +503 -0
- package/augment-extensions/domain-rules/wordpress-plugin/examples/singleton-plugin.md +971 -0
- package/augment-extensions/domain-rules/wordpress-plugin/module.json +53 -0
- package/augment-extensions/domain-rules/wordpress-plugin/rules/activation-hooks.md +770 -0
- package/augment-extensions/domain-rules/wordpress-plugin/rules/admin-interface.md +874 -0
- package/augment-extensions/domain-rules/wordpress-plugin/rules/ajax-handlers.md +629 -0
- package/augment-extensions/domain-rules/wordpress-plugin/rules/asset-management.md +559 -0
- package/augment-extensions/domain-rules/wordpress-plugin/rules/context-providers.md +709 -0
- package/augment-extensions/domain-rules/wordpress-plugin/rules/cron-jobs.md +736 -0
- package/augment-extensions/domain-rules/wordpress-plugin/rules/database-management.md +1057 -0
- package/augment-extensions/domain-rules/wordpress-plugin/rules/documentation-standards.md +463 -0
- package/augment-extensions/domain-rules/wordpress-plugin/rules/frontend-functionality.md +478 -0
- package/augment-extensions/domain-rules/wordpress-plugin/rules/gutenberg-blocks.md +818 -0
- package/augment-extensions/domain-rules/wordpress-plugin/rules/internationalization.md +416 -0
- package/augment-extensions/domain-rules/wordpress-plugin/rules/migration.md +667 -0
- package/augment-extensions/domain-rules/wordpress-plugin/rules/performance-optimization.md +878 -0
- package/augment-extensions/domain-rules/wordpress-plugin/rules/plugin-architecture.md +693 -0
- package/augment-extensions/domain-rules/wordpress-plugin/rules/plugin-structure.md +352 -0
- package/augment-extensions/domain-rules/wordpress-plugin/rules/rest-api.md +818 -0
- package/augment-extensions/domain-rules/wordpress-plugin/rules/scaffolding-workflow.md +624 -0
- package/augment-extensions/domain-rules/wordpress-plugin/rules/security-best-practices.md +866 -0
- package/augment-extensions/domain-rules/wordpress-plugin/rules/testing-patterns.md +1165 -0
- package/augment-extensions/domain-rules/wordpress-plugin/rules/testing.md +414 -0
- package/augment-extensions/domain-rules/wordpress-plugin/rules/vscode-integration.md +751 -0
- package/augment-extensions/domain-rules/wordpress-plugin/rules/woocommerce-integration.md +949 -0
- package/augment-extensions/domain-rules/wordpress-plugin/rules/wordpress-org-submission.md +458 -0
- package/augment-extensions/examples/gutenberg-block-plugin/README.md +101 -0
- package/augment-extensions/examples/gutenberg-block-plugin/examples/testimonial-block.md +428 -0
- package/augment-extensions/examples/gutenberg-block-plugin/module.json +40 -0
- package/augment-extensions/examples/rest-api-plugin/README.md +98 -0
- package/augment-extensions/examples/rest-api-plugin/examples/task-manager-api.md +1299 -0
- package/augment-extensions/examples/rest-api-plugin/module.json +40 -0
- package/augment-extensions/examples/woocommerce-extension/README.md +98 -0
- package/augment-extensions/examples/woocommerce-extension/examples/product-customizer.md +763 -0
- package/augment-extensions/examples/woocommerce-extension/module.json +40 -0
- package/augment-extensions/workflows/beads/module.json +4 -3
- package/augment-extensions/workflows/database/README.md +195 -0
- package/augment-extensions/workflows/database/ai-prompt-testing.md +295 -0
- package/augment-extensions/workflows/database/examples/migration-example.md +498 -0
- package/augment-extensions/workflows/database/examples/optimization-example.md +496 -0
- package/augment-extensions/workflows/database/examples/schema-design-example.md +444 -0
- package/augment-extensions/workflows/database/module.json +42 -0
- package/augment-extensions/workflows/database/rules/data-migration.md +249 -0
- package/augment-extensions/workflows/database/rules/documentation-standards.md +339 -0
- package/augment-extensions/workflows/database/rules/migration-workflow.md +352 -0
- package/augment-extensions/workflows/database/rules/optimization-workflow.md +435 -0
- package/augment-extensions/workflows/database/rules/schema-design-workflow.md +535 -0
- package/augment-extensions/workflows/database/rules/testing-patterns.md +305 -0
- package/augment-extensions/workflows/database/rules/workflow.md +458 -0
- package/augment-extensions/workflows/openspec/module.json +4 -3
- package/augment-extensions/workflows/wordpress-plugin/README.md +232 -0
- package/augment-extensions/workflows/wordpress-plugin/ai-prompts.md +839 -0
- package/augment-extensions/workflows/wordpress-plugin/bead-decomposition-patterns.md +854 -0
- package/augment-extensions/workflows/wordpress-plugin/examples/complete-plugin-example.md +540 -0
- package/augment-extensions/workflows/wordpress-plugin/examples/custom-post-type-example.md +1083 -0
- package/augment-extensions/workflows/wordpress-plugin/examples/feature-addition-workflow.md +669 -0
- package/augment-extensions/workflows/wordpress-plugin/examples/plugin-creation-workflow.md +597 -0
- package/augment-extensions/workflows/wordpress-plugin/examples/secure-form-handler-example.md +925 -0
- package/augment-extensions/workflows/wordpress-plugin/examples/security-audit-workflow.md +752 -0
- package/augment-extensions/workflows/wordpress-plugin/examples/wordpress-org-submission-workflow.md +773 -0
- package/augment-extensions/workflows/wordpress-plugin/module.json +49 -0
- package/augment-extensions/workflows/wordpress-plugin/rules/best-practices.md +942 -0
- package/augment-extensions/workflows/wordpress-plugin/rules/development-workflow.md +702 -0
- package/augment-extensions/workflows/wordpress-plugin/rules/submission-workflow.md +728 -0
- package/augment-extensions/workflows/wordpress-plugin/rules/testing-workflow.md +775 -0
- package/augment-extensions/writing-standards/screenplay/README.md +171 -0
- package/augment-extensions/writing-standards/screenplay/examples/aaa-hollywood-scene.fountain +164 -0
- package/augment-extensions/writing-standards/screenplay/module.json +124 -0
- package/augment-extensions/writing-standards/screenplay/rules/universal-formatting.md +339 -0
- package/cli/MODULES.md +302 -0
- package/cli/dist/cli.js +142 -9
- package/cli/dist/cli.js.map +1 -1
- package/cli/dist/commands/catalog.d.ts +13 -0
- package/cli/dist/commands/catalog.d.ts.map +1 -0
- package/cli/dist/commands/catalog.js +104 -0
- package/cli/dist/commands/catalog.js.map +1 -0
- package/cli/dist/commands/gui.d.ts +6 -0
- package/cli/dist/commands/gui.d.ts.map +1 -0
- package/cli/dist/commands/gui.js +211 -0
- package/cli/dist/commands/gui.js.map +1 -0
- package/cli/dist/commands/init.d.ts.map +1 -1
- package/cli/dist/commands/init.js +12 -0
- package/cli/dist/commands/init.js.map +1 -1
- package/cli/dist/commands/install-rules.d.ts +14 -0
- package/cli/dist/commands/install-rules.d.ts.map +1 -0
- package/cli/dist/commands/install-rules.js +127 -0
- package/cli/dist/commands/install-rules.js.map +1 -0
- package/cli/dist/commands/link.d.ts.map +1 -1
- package/cli/dist/commands/link.js +9 -11
- package/cli/dist/commands/link.js.map +1 -1
- package/cli/dist/commands/list.d.ts.map +1 -1
- package/cli/dist/commands/list.js +11 -28
- package/cli/dist/commands/list.js.map +1 -1
- package/cli/dist/commands/mcp.d.ts +48 -0
- package/cli/dist/commands/mcp.d.ts.map +1 -0
- package/cli/dist/commands/mcp.js +229 -0
- package/cli/dist/commands/mcp.js.map +1 -0
- package/cli/dist/commands/self-remove.d.ts +7 -0
- package/cli/dist/commands/self-remove.d.ts.map +1 -0
- package/cli/dist/commands/self-remove.js +179 -0
- package/cli/dist/commands/self-remove.js.map +1 -0
- package/cli/dist/commands/show.d.ts.map +1 -1
- package/cli/dist/commands/show.js +42 -71
- package/cli/dist/commands/show.js.map +1 -1
- package/cli/dist/commands/skill.d.ts +67 -0
- package/cli/dist/commands/skill.d.ts.map +1 -0
- package/cli/dist/commands/skill.js +513 -0
- package/cli/dist/commands/skill.js.map +1 -0
- package/cli/dist/commands/unlink.d.ts +6 -0
- package/cli/dist/commands/unlink.d.ts.map +1 -0
- package/cli/dist/commands/unlink.js +115 -0
- package/cli/dist/commands/unlink.js.map +1 -0
- package/cli/dist/commands/validate.d.ts +6 -0
- package/cli/dist/commands/validate.d.ts.map +1 -0
- package/cli/dist/commands/validate.js +159 -0
- package/cli/dist/commands/validate.js.map +1 -0
- package/cli/dist/utils/catalog-sync.d.ts +22 -0
- package/cli/dist/utils/catalog-sync.d.ts.map +1 -0
- package/cli/dist/utils/catalog-sync.js +157 -0
- package/cli/dist/utils/catalog-sync.js.map +1 -0
- package/cli/dist/utils/character-count.d.ts +56 -0
- package/cli/dist/utils/character-count.d.ts.map +1 -0
- package/cli/dist/utils/character-count.js +190 -0
- package/cli/dist/utils/character-count.js.map +1 -0
- package/cli/dist/utils/documentation-validator.d.ts +18 -0
- package/cli/dist/utils/documentation-validator.d.ts.map +1 -0
- package/cli/dist/utils/documentation-validator.js +233 -0
- package/cli/dist/utils/documentation-validator.js.map +1 -0
- package/cli/dist/utils/install-rules.d.ts +32 -0
- package/cli/dist/utils/install-rules.d.ts.map +1 -0
- package/cli/dist/utils/install-rules.js +375 -0
- package/cli/dist/utils/install-rules.js.map +1 -0
- package/cli/dist/utils/mcp-integration.d.ts +70 -0
- package/cli/dist/utils/mcp-integration.d.ts.map +1 -0
- package/cli/dist/utils/mcp-integration.js +292 -0
- package/cli/dist/utils/mcp-integration.js.map +1 -0
- package/cli/dist/utils/module-system.d.ts +153 -0
- package/cli/dist/utils/module-system.d.ts.map +1 -0
- package/cli/dist/utils/module-system.js +528 -0
- package/cli/dist/utils/module-system.js.map +1 -0
- package/cli/dist/utils/modules-catalog.d.ts +33 -0
- package/cli/dist/utils/modules-catalog.d.ts.map +1 -0
- package/cli/dist/utils/modules-catalog.js +163 -0
- package/cli/dist/utils/modules-catalog.js.map +1 -0
- package/cli/dist/utils/rule-install-hooks.d.ts +19 -0
- package/cli/dist/utils/rule-install-hooks.d.ts.map +1 -0
- package/cli/dist/utils/rule-install-hooks.js +224 -0
- package/cli/dist/utils/rule-install-hooks.js.map +1 -0
- package/cli/dist/utils/skill-system.d.ts +95 -0
- package/cli/dist/utils/skill-system.d.ts.map +1 -0
- package/cli/dist/utils/skill-system.js +313 -0
- package/cli/dist/utils/skill-system.js.map +1 -0
- package/modules.md +534 -70
- package/package.json +12 -3
|
@@ -0,0 +1,667 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* DOM Manipulation Examples
|
|
3
|
+
*
|
|
4
|
+
* Demonstrates modern DOM manipulation patterns including:
|
|
5
|
+
* - querySelector and querySelectorAll
|
|
6
|
+
* - Event delegation
|
|
7
|
+
* - Event listener cleanup
|
|
8
|
+
* - Data attributes for JS hooks
|
|
9
|
+
* - Creating and modifying elements
|
|
10
|
+
* - Performance best practices
|
|
11
|
+
*/
|
|
12
|
+
|
|
13
|
+
// ============================================================================
|
|
14
|
+
// SELECTING ELEMENTS
|
|
15
|
+
// ============================================================================
|
|
16
|
+
|
|
17
|
+
/**
|
|
18
|
+
* querySelector - Select single element (returns first match)
|
|
19
|
+
*/
|
|
20
|
+
function selectSingleElement() {
|
|
21
|
+
// By ID (prefer getElementById for IDs)
|
|
22
|
+
const header = document.querySelector('#header');
|
|
23
|
+
|
|
24
|
+
// By class
|
|
25
|
+
const firstButton = document.querySelector('.btn');
|
|
26
|
+
|
|
27
|
+
// By attribute
|
|
28
|
+
const submitButton = document.querySelector('[type="submit"]');
|
|
29
|
+
|
|
30
|
+
// By data attribute (preferred for JS hooks)
|
|
31
|
+
const userCard = document.querySelector('[data-user-id="123"]');
|
|
32
|
+
|
|
33
|
+
// Complex selector
|
|
34
|
+
const activeNavLink = document.querySelector('nav .nav-link.active');
|
|
35
|
+
|
|
36
|
+
return { header, firstButton, submitButton, userCard, activeNavLink };
|
|
37
|
+
}
|
|
38
|
+
|
|
39
|
+
/**
|
|
40
|
+
* querySelectorAll - Select multiple elements (returns NodeList)
|
|
41
|
+
*/
|
|
42
|
+
function selectMultipleElements() {
|
|
43
|
+
// All elements with class
|
|
44
|
+
const buttons = document.querySelectorAll('.btn');
|
|
45
|
+
|
|
46
|
+
// All elements with data attribute
|
|
47
|
+
const userCards = document.querySelectorAll('[data-user-card]');
|
|
48
|
+
|
|
49
|
+
// Convert NodeList to Array for array methods
|
|
50
|
+
const buttonsArray = Array.from(buttons);
|
|
51
|
+
|
|
52
|
+
// Or use spread operator
|
|
53
|
+
const cardsArray = [...userCards];
|
|
54
|
+
|
|
55
|
+
return { buttons, userCards, buttonsArray, cardsArray };
|
|
56
|
+
}
|
|
57
|
+
|
|
58
|
+
/**
|
|
59
|
+
* Prefer specific methods when available
|
|
60
|
+
*/
|
|
61
|
+
function useSpecificMethods() {
|
|
62
|
+
// Faster than querySelector
|
|
63
|
+
const element = document.getElementById('my-element');
|
|
64
|
+
const elements = document.getElementsByClassName('my-class');
|
|
65
|
+
const tags = document.getElementsByTagName('div');
|
|
66
|
+
|
|
67
|
+
return { element, elements, tags };
|
|
68
|
+
}
|
|
69
|
+
|
|
70
|
+
// ============================================================================
|
|
71
|
+
// DATA ATTRIBUTES FOR JS HOOKS
|
|
72
|
+
// ============================================================================
|
|
73
|
+
|
|
74
|
+
/**
|
|
75
|
+
* Use data attributes to separate styling from behavior
|
|
76
|
+
* DON'T use classes for JS hooks (they might change for styling)
|
|
77
|
+
* DO use data-* attributes
|
|
78
|
+
*/
|
|
79
|
+
|
|
80
|
+
// HTML: <button data-action="delete" data-user-id="123">Delete</button>
|
|
81
|
+
|
|
82
|
+
function handleDataAttributes() {
|
|
83
|
+
const deleteButton = document.querySelector('[data-action="delete"]');
|
|
84
|
+
|
|
85
|
+
if (deleteButton) {
|
|
86
|
+
// Get data attribute value
|
|
87
|
+
const userId = deleteButton.dataset.userId; // "123"
|
|
88
|
+
const action = deleteButton.dataset.action; // "delete"
|
|
89
|
+
|
|
90
|
+
// Set data attribute
|
|
91
|
+
deleteButton.dataset.status = 'pending';
|
|
92
|
+
|
|
93
|
+
// Remove data attribute
|
|
94
|
+
delete deleteButton.dataset.status;
|
|
95
|
+
}
|
|
96
|
+
}
|
|
97
|
+
|
|
98
|
+
// ============================================================================
|
|
99
|
+
// EVENT DELEGATION
|
|
100
|
+
// ============================================================================
|
|
101
|
+
|
|
102
|
+
/**
|
|
103
|
+
* Event delegation - attach listener to parent instead of each child
|
|
104
|
+
* Benefits: Better performance, works with dynamically added elements
|
|
105
|
+
*/
|
|
106
|
+
function setupEventDelegation() {
|
|
107
|
+
const todoList = document.querySelector('[data-todo-list]');
|
|
108
|
+
|
|
109
|
+
if (!todoList) return;
|
|
110
|
+
|
|
111
|
+
// Single listener on parent handles all child clicks
|
|
112
|
+
todoList.addEventListener('click', (event) => {
|
|
113
|
+
const target = event.target;
|
|
114
|
+
|
|
115
|
+
// Check if clicked element matches selector
|
|
116
|
+
if (target.matches('[data-action="delete"]')) {
|
|
117
|
+
const todoItem = target.closest('[data-todo-item]');
|
|
118
|
+
const todoId = todoItem?.dataset.todoId;
|
|
119
|
+
|
|
120
|
+
console.log(`Delete todo: ${todoId}`);
|
|
121
|
+
todoItem?.remove();
|
|
122
|
+
}
|
|
123
|
+
|
|
124
|
+
if (target.matches('[data-action="complete"]')) {
|
|
125
|
+
const todoItem = target.closest('[data-todo-item]');
|
|
126
|
+
todoItem?.classList.toggle('completed');
|
|
127
|
+
}
|
|
128
|
+
});
|
|
129
|
+
}
|
|
130
|
+
|
|
131
|
+
/**
|
|
132
|
+
* Event delegation with multiple event types
|
|
133
|
+
*/
|
|
134
|
+
function setupMultipleEventDelegation() {
|
|
135
|
+
const form = document.querySelector('[data-form]');
|
|
136
|
+
|
|
137
|
+
if (!form) return;
|
|
138
|
+
|
|
139
|
+
// Handle different events on form children
|
|
140
|
+
form.addEventListener('input', (event) => {
|
|
141
|
+
if (event.target.matches('[data-validate]')) {
|
|
142
|
+
validateField(event.target);
|
|
143
|
+
}
|
|
144
|
+
});
|
|
145
|
+
|
|
146
|
+
form.addEventListener('blur', (event) => {
|
|
147
|
+
if (event.target.matches('[data-validate]')) {
|
|
148
|
+
validateField(event.target);
|
|
149
|
+
}
|
|
150
|
+
}, true); // Use capture phase for blur
|
|
151
|
+
}
|
|
152
|
+
|
|
153
|
+
function validateField(field) {
|
|
154
|
+
// Validation logic
|
|
155
|
+
console.log('Validating:', field.name);
|
|
156
|
+
}
|
|
157
|
+
|
|
158
|
+
// ============================================================================
|
|
159
|
+
// EVENT LISTENER CLEANUP
|
|
160
|
+
// ============================================================================
|
|
161
|
+
|
|
162
|
+
/**
|
|
163
|
+
* Proper event listener cleanup to prevent memory leaks
|
|
164
|
+
*/
|
|
165
|
+
class ComponentWithCleanup {
|
|
166
|
+
constructor(element) {
|
|
167
|
+
this.element = element;
|
|
168
|
+
this.boundHandleClick = this.handleClick.bind(this);
|
|
169
|
+
this.boundHandleResize = this.handleResize.bind(this);
|
|
170
|
+
}
|
|
171
|
+
|
|
172
|
+
init() {
|
|
173
|
+
// Store bound functions to remove later
|
|
174
|
+
this.element.addEventListener('click', this.boundHandleClick);
|
|
175
|
+
window.addEventListener('resize', this.boundHandleResize);
|
|
176
|
+
}
|
|
177
|
+
|
|
178
|
+
destroy() {
|
|
179
|
+
// Clean up event listeners
|
|
180
|
+
this.element.removeEventListener('click', this.boundHandleClick);
|
|
181
|
+
window.removeEventListener('resize', this.boundHandleResize);
|
|
182
|
+
}
|
|
183
|
+
|
|
184
|
+
handleClick(event) {
|
|
185
|
+
console.log('Clicked:', event.target);
|
|
186
|
+
}
|
|
187
|
+
|
|
188
|
+
handleResize(event) {
|
|
189
|
+
console.log('Window resized');
|
|
190
|
+
}
|
|
191
|
+
}
|
|
192
|
+
|
|
193
|
+
/**
|
|
194
|
+
* Using AbortController for easy cleanup (modern approach)
|
|
195
|
+
*/
|
|
196
|
+
function setupWithAbortController() {
|
|
197
|
+
const controller = new AbortController();
|
|
198
|
+
const { signal } = controller;
|
|
199
|
+
|
|
200
|
+
// Add multiple listeners with same signal
|
|
201
|
+
document.addEventListener('click', handleClick, { signal });
|
|
202
|
+
document.addEventListener('keydown', handleKeydown, { signal });
|
|
203
|
+
window.addEventListener('resize', handleResize, { signal });
|
|
204
|
+
|
|
205
|
+
// Later, abort all listeners at once
|
|
206
|
+
function cleanup() {
|
|
207
|
+
controller.abort();
|
|
208
|
+
}
|
|
209
|
+
|
|
210
|
+
return cleanup;
|
|
211
|
+
}
|
|
212
|
+
|
|
213
|
+
function handleClick(event) {
|
|
214
|
+
console.log('Click:', event.target);
|
|
215
|
+
}
|
|
216
|
+
|
|
217
|
+
function handleKeydown(event) {
|
|
218
|
+
console.log('Keydown:', event.key);
|
|
219
|
+
}
|
|
220
|
+
|
|
221
|
+
function handleResize(event) {
|
|
222
|
+
console.log('Resize');
|
|
223
|
+
}
|
|
224
|
+
|
|
225
|
+
// ============================================================================
|
|
226
|
+
// CREATING AND MODIFYING ELEMENTS
|
|
227
|
+
// ============================================================================
|
|
228
|
+
|
|
229
|
+
/**
|
|
230
|
+
* Create elements programmatically
|
|
231
|
+
*/
|
|
232
|
+
function createElements() {
|
|
233
|
+
// Create element
|
|
234
|
+
const div = document.createElement('div');
|
|
235
|
+
|
|
236
|
+
// Set attributes
|
|
237
|
+
div.className = 'card';
|
|
238
|
+
div.id = 'user-card-123';
|
|
239
|
+
div.setAttribute('data-user-id', '123');
|
|
240
|
+
|
|
241
|
+
// Set content
|
|
242
|
+
div.textContent = 'User Name';
|
|
243
|
+
|
|
244
|
+
// Or use innerHTML (be careful with user input - XSS risk!)
|
|
245
|
+
div.innerHTML = '<strong>User Name</strong>';
|
|
246
|
+
|
|
247
|
+
// Add to DOM
|
|
248
|
+
document.body.appendChild(div);
|
|
249
|
+
|
|
250
|
+
return div;
|
|
251
|
+
}
|
|
252
|
+
|
|
253
|
+
/**
|
|
254
|
+
* Create complex element structure
|
|
255
|
+
*/
|
|
256
|
+
function createUserCard(user) {
|
|
257
|
+
// Create container
|
|
258
|
+
const card = document.createElement('div');
|
|
259
|
+
card.className = 'user-card';
|
|
260
|
+
card.dataset.userId = user.id;
|
|
261
|
+
|
|
262
|
+
// Create header
|
|
263
|
+
const header = document.createElement('div');
|
|
264
|
+
header.className = 'user-card__header';
|
|
265
|
+
|
|
266
|
+
const name = document.createElement('h3');
|
|
267
|
+
name.className = 'user-card__name';
|
|
268
|
+
name.textContent = user.name;
|
|
269
|
+
|
|
270
|
+
header.appendChild(name);
|
|
271
|
+
|
|
272
|
+
// Create body
|
|
273
|
+
const body = document.createElement('div');
|
|
274
|
+
body.className = 'user-card__body';
|
|
275
|
+
|
|
276
|
+
const email = document.createElement('p');
|
|
277
|
+
email.className = 'user-card__email';
|
|
278
|
+
email.textContent = user.email;
|
|
279
|
+
|
|
280
|
+
body.appendChild(email);
|
|
281
|
+
|
|
282
|
+
// Create footer with button
|
|
283
|
+
const footer = document.createElement('div');
|
|
284
|
+
footer.className = 'user-card__footer';
|
|
285
|
+
|
|
286
|
+
const button = document.createElement('button');
|
|
287
|
+
button.className = 'btn btn--primary';
|
|
288
|
+
button.dataset.action = 'view-profile';
|
|
289
|
+
button.dataset.userId = user.id;
|
|
290
|
+
button.textContent = 'View Profile';
|
|
291
|
+
|
|
292
|
+
footer.appendChild(button);
|
|
293
|
+
|
|
294
|
+
// Assemble card
|
|
295
|
+
card.appendChild(header);
|
|
296
|
+
card.appendChild(body);
|
|
297
|
+
card.appendChild(footer);
|
|
298
|
+
|
|
299
|
+
return card;
|
|
300
|
+
}
|
|
301
|
+
|
|
302
|
+
/**
|
|
303
|
+
* Using template literals for complex HTML (use with caution)
|
|
304
|
+
*/
|
|
305
|
+
function createUserCardWithTemplate(user) {
|
|
306
|
+
const card = document.createElement('div');
|
|
307
|
+
card.className = 'user-card';
|
|
308
|
+
card.dataset.userId = user.id;
|
|
309
|
+
|
|
310
|
+
// Escape user input to prevent XSS
|
|
311
|
+
const escapedName = escapeHtml(user.name);
|
|
312
|
+
const escapedEmail = escapeHtml(user.email);
|
|
313
|
+
|
|
314
|
+
card.innerHTML = `
|
|
315
|
+
<div class="user-card__header">
|
|
316
|
+
<h3 class="user-card__name">${escapedName}</h3>
|
|
317
|
+
</div>
|
|
318
|
+
<div class="user-card__body">
|
|
319
|
+
<p class="user-card__email">${escapedEmail}</p>
|
|
320
|
+
</div>
|
|
321
|
+
<div class="user-card__footer">
|
|
322
|
+
<button class="btn btn--primary" data-action="view-profile" data-user-id="${user.id}">
|
|
323
|
+
View Profile
|
|
324
|
+
</button>
|
|
325
|
+
</div>
|
|
326
|
+
`;
|
|
327
|
+
|
|
328
|
+
return card;
|
|
329
|
+
}
|
|
330
|
+
|
|
331
|
+
function escapeHtml(text) {
|
|
332
|
+
const div = document.createElement('div');
|
|
333
|
+
div.textContent = text;
|
|
334
|
+
return div.innerHTML;
|
|
335
|
+
}
|
|
336
|
+
|
|
337
|
+
// ============================================================================
|
|
338
|
+
// MODIFYING ELEMENTS
|
|
339
|
+
// ============================================================================
|
|
340
|
+
|
|
341
|
+
/**
|
|
342
|
+
* Modify element classes
|
|
343
|
+
*/
|
|
344
|
+
function modifyClasses(element) {
|
|
345
|
+
// Add class
|
|
346
|
+
element.classList.add('active');
|
|
347
|
+
|
|
348
|
+
// Remove class
|
|
349
|
+
element.classList.remove('inactive');
|
|
350
|
+
|
|
351
|
+
// Toggle class
|
|
352
|
+
element.classList.toggle('expanded');
|
|
353
|
+
|
|
354
|
+
// Check if has class
|
|
355
|
+
if (element.classList.contains('active')) {
|
|
356
|
+
console.log('Element is active');
|
|
357
|
+
}
|
|
358
|
+
|
|
359
|
+
// Replace class
|
|
360
|
+
element.classList.replace('old-class', 'new-class');
|
|
361
|
+
|
|
362
|
+
// Add multiple classes
|
|
363
|
+
element.classList.add('class1', 'class2', 'class3');
|
|
364
|
+
}
|
|
365
|
+
|
|
366
|
+
/**
|
|
367
|
+
* Modify element styles
|
|
368
|
+
*/
|
|
369
|
+
function modifyStyles(element) {
|
|
370
|
+
// Set individual style
|
|
371
|
+
element.style.color = 'red';
|
|
372
|
+
element.style.backgroundColor = 'blue';
|
|
373
|
+
|
|
374
|
+
// Set multiple styles
|
|
375
|
+
Object.assign(element.style, {
|
|
376
|
+
color: 'red',
|
|
377
|
+
backgroundColor: 'blue',
|
|
378
|
+
padding: '1rem',
|
|
379
|
+
borderRadius: '0.5rem'
|
|
380
|
+
});
|
|
381
|
+
|
|
382
|
+
// Remove style
|
|
383
|
+
element.style.color = '';
|
|
384
|
+
|
|
385
|
+
// Get computed style
|
|
386
|
+
const computedStyle = window.getComputedStyle(element);
|
|
387
|
+
const color = computedStyle.color;
|
|
388
|
+
const fontSize = computedStyle.fontSize;
|
|
389
|
+
}
|
|
390
|
+
|
|
391
|
+
/**
|
|
392
|
+
* Modify element attributes
|
|
393
|
+
*/
|
|
394
|
+
function modifyAttributes(element) {
|
|
395
|
+
// Set attribute
|
|
396
|
+
element.setAttribute('aria-label', 'Close dialog');
|
|
397
|
+
element.setAttribute('data-status', 'active');
|
|
398
|
+
|
|
399
|
+
// Get attribute
|
|
400
|
+
const status = element.getAttribute('data-status');
|
|
401
|
+
|
|
402
|
+
// Check if has attribute
|
|
403
|
+
if (element.hasAttribute('data-status')) {
|
|
404
|
+
console.log('Has status attribute');
|
|
405
|
+
}
|
|
406
|
+
|
|
407
|
+
// Remove attribute
|
|
408
|
+
element.removeAttribute('data-status');
|
|
409
|
+
|
|
410
|
+
// Boolean attributes
|
|
411
|
+
element.disabled = true;
|
|
412
|
+
element.hidden = false;
|
|
413
|
+
}
|
|
414
|
+
|
|
415
|
+
// ============================================================================
|
|
416
|
+
// TRAVERSING THE DOM
|
|
417
|
+
// ============================================================================
|
|
418
|
+
|
|
419
|
+
/**
|
|
420
|
+
* Navigate DOM tree
|
|
421
|
+
*/
|
|
422
|
+
function traverseDOM(element) {
|
|
423
|
+
// Parent
|
|
424
|
+
const parent = element.parentElement;
|
|
425
|
+
const parentNode = element.parentNode;
|
|
426
|
+
|
|
427
|
+
// Children
|
|
428
|
+
const children = element.children; // HTMLCollection
|
|
429
|
+
const childNodes = element.childNodes; // NodeList (includes text nodes)
|
|
430
|
+
const firstChild = element.firstElementChild;
|
|
431
|
+
const lastChild = element.lastElementChild;
|
|
432
|
+
|
|
433
|
+
// Siblings
|
|
434
|
+
const nextSibling = element.nextElementSibling;
|
|
435
|
+
const prevSibling = element.previousElementSibling;
|
|
436
|
+
|
|
437
|
+
// Find closest ancestor matching selector
|
|
438
|
+
const form = element.closest('form');
|
|
439
|
+
const card = element.closest('[data-card]');
|
|
440
|
+
|
|
441
|
+
// Check if element matches selector
|
|
442
|
+
if (element.matches('.active')) {
|
|
443
|
+
console.log('Element is active');
|
|
444
|
+
}
|
|
445
|
+
}
|
|
446
|
+
|
|
447
|
+
// ============================================================================
|
|
448
|
+
// INSERTING AND REMOVING ELEMENTS
|
|
449
|
+
// ============================================================================
|
|
450
|
+
|
|
451
|
+
/**
|
|
452
|
+
* Insert elements at different positions
|
|
453
|
+
*/
|
|
454
|
+
function insertElements() {
|
|
455
|
+
const container = document.querySelector('[data-container]');
|
|
456
|
+
const newElement = document.createElement('div');
|
|
457
|
+
|
|
458
|
+
// Append to end
|
|
459
|
+
container.appendChild(newElement);
|
|
460
|
+
|
|
461
|
+
// Prepend to beginning
|
|
462
|
+
container.prepend(newElement);
|
|
463
|
+
|
|
464
|
+
// Insert before specific child
|
|
465
|
+
const referenceElement = container.firstElementChild;
|
|
466
|
+
container.insertBefore(newElement, referenceElement);
|
|
467
|
+
|
|
468
|
+
// Insert adjacent (modern approach)
|
|
469
|
+
container.insertAdjacentElement('beforebegin', newElement); // Before container
|
|
470
|
+
container.insertAdjacentElement('afterbegin', newElement); // First child
|
|
471
|
+
container.insertAdjacentElement('beforeend', newElement); // Last child
|
|
472
|
+
container.insertAdjacentElement('afterend', newElement); // After container
|
|
473
|
+
|
|
474
|
+
// Insert HTML
|
|
475
|
+
container.insertAdjacentHTML('beforeend', '<div>New content</div>');
|
|
476
|
+
}
|
|
477
|
+
|
|
478
|
+
/**
|
|
479
|
+
* Remove elements
|
|
480
|
+
*/
|
|
481
|
+
function removeElements() {
|
|
482
|
+
const element = document.querySelector('[data-remove-me]');
|
|
483
|
+
|
|
484
|
+
// Modern approach
|
|
485
|
+
element?.remove();
|
|
486
|
+
|
|
487
|
+
// Old approach (still works)
|
|
488
|
+
element?.parentNode?.removeChild(element);
|
|
489
|
+
|
|
490
|
+
// Remove all children
|
|
491
|
+
const container = document.querySelector('[data-container]');
|
|
492
|
+
container.innerHTML = ''; // Fast but loses event listeners
|
|
493
|
+
|
|
494
|
+
// Or remove children properly
|
|
495
|
+
while (container.firstChild) {
|
|
496
|
+
container.removeChild(container.firstChild);
|
|
497
|
+
}
|
|
498
|
+
|
|
499
|
+
// Modern approach with replaceChildren
|
|
500
|
+
container.replaceChildren(); // Removes all children
|
|
501
|
+
}
|
|
502
|
+
|
|
503
|
+
/**
|
|
504
|
+
* Replace elements
|
|
505
|
+
*/
|
|
506
|
+
function replaceElements() {
|
|
507
|
+
const oldElement = document.querySelector('[data-old]');
|
|
508
|
+
const newElement = document.createElement('div');
|
|
509
|
+
newElement.textContent = 'New content';
|
|
510
|
+
|
|
511
|
+
// Replace element
|
|
512
|
+
oldElement?.replaceWith(newElement);
|
|
513
|
+
}
|
|
514
|
+
|
|
515
|
+
// ============================================================================
|
|
516
|
+
// PERFORMANCE BEST PRACTICES
|
|
517
|
+
// ============================================================================
|
|
518
|
+
|
|
519
|
+
/**
|
|
520
|
+
* Batch DOM updates to minimize reflows
|
|
521
|
+
*/
|
|
522
|
+
function batchDOMUpdates(items) {
|
|
523
|
+
const container = document.querySelector('[data-container]');
|
|
524
|
+
|
|
525
|
+
// BAD: Multiple reflows
|
|
526
|
+
items.forEach(item => {
|
|
527
|
+
const element = document.createElement('div');
|
|
528
|
+
element.textContent = item.name;
|
|
529
|
+
container.appendChild(element); // Reflow on each append
|
|
530
|
+
});
|
|
531
|
+
|
|
532
|
+
// GOOD: Single reflow with DocumentFragment
|
|
533
|
+
const fragment = document.createDocumentFragment();
|
|
534
|
+
items.forEach(item => {
|
|
535
|
+
const element = document.createElement('div');
|
|
536
|
+
element.textContent = item.name;
|
|
537
|
+
fragment.appendChild(element);
|
|
538
|
+
});
|
|
539
|
+
container.appendChild(fragment); // Single reflow
|
|
540
|
+
}
|
|
541
|
+
|
|
542
|
+
/**
|
|
543
|
+
* Use requestAnimationFrame for visual updates
|
|
544
|
+
*/
|
|
545
|
+
function animateElement(element) {
|
|
546
|
+
let position = 0;
|
|
547
|
+
|
|
548
|
+
function update() {
|
|
549
|
+
position += 1;
|
|
550
|
+
element.style.transform = `translateX(${position}px)`;
|
|
551
|
+
|
|
552
|
+
if (position < 100) {
|
|
553
|
+
requestAnimationFrame(update);
|
|
554
|
+
}
|
|
555
|
+
}
|
|
556
|
+
|
|
557
|
+
requestAnimationFrame(update);
|
|
558
|
+
}
|
|
559
|
+
|
|
560
|
+
/**
|
|
561
|
+
* Debounce expensive DOM operations
|
|
562
|
+
*/
|
|
563
|
+
function debounce(fn, delay = 300) {
|
|
564
|
+
let timeoutId;
|
|
565
|
+
|
|
566
|
+
return function(...args) {
|
|
567
|
+
clearTimeout(timeoutId);
|
|
568
|
+
timeoutId = setTimeout(() => fn.apply(this, args), delay);
|
|
569
|
+
};
|
|
570
|
+
}
|
|
571
|
+
|
|
572
|
+
// Usage
|
|
573
|
+
const handleSearch = debounce((event) => {
|
|
574
|
+
const query = event.target.value;
|
|
575
|
+
// Expensive DOM operation
|
|
576
|
+
updateSearchResults(query);
|
|
577
|
+
}, 300);
|
|
578
|
+
|
|
579
|
+
function updateSearchResults(query) {
|
|
580
|
+
console.log('Searching for:', query);
|
|
581
|
+
}
|
|
582
|
+
|
|
583
|
+
// ============================================================================
|
|
584
|
+
// PRACTICAL EXAMPLES
|
|
585
|
+
// ============================================================================
|
|
586
|
+
|
|
587
|
+
/**
|
|
588
|
+
* Complete example: Todo list with event delegation
|
|
589
|
+
*/
|
|
590
|
+
class TodoList {
|
|
591
|
+
constructor(containerSelector) {
|
|
592
|
+
this.container = document.querySelector(containerSelector);
|
|
593
|
+
this.todos = [];
|
|
594
|
+
this.init();
|
|
595
|
+
}
|
|
596
|
+
|
|
597
|
+
init() {
|
|
598
|
+
this.render();
|
|
599
|
+
this.setupEventListeners();
|
|
600
|
+
}
|
|
601
|
+
|
|
602
|
+
setupEventListeners() {
|
|
603
|
+
// Event delegation on container
|
|
604
|
+
this.container.addEventListener('click', (event) => {
|
|
605
|
+
const target = event.target;
|
|
606
|
+
|
|
607
|
+
if (target.matches('[data-action="delete"]')) {
|
|
608
|
+
const todoId = target.closest('[data-todo-item]')?.dataset.todoId;
|
|
609
|
+
this.deleteTodo(todoId);
|
|
610
|
+
}
|
|
611
|
+
|
|
612
|
+
if (target.matches('[data-action="toggle"]')) {
|
|
613
|
+
const todoId = target.closest('[data-todo-item]')?.dataset.todoId;
|
|
614
|
+
this.toggleTodo(todoId);
|
|
615
|
+
}
|
|
616
|
+
});
|
|
617
|
+
}
|
|
618
|
+
|
|
619
|
+
addTodo(text) {
|
|
620
|
+
const todo = {
|
|
621
|
+
id: Date.now().toString(),
|
|
622
|
+
text,
|
|
623
|
+
completed: false
|
|
624
|
+
};
|
|
625
|
+
this.todos.push(todo);
|
|
626
|
+
this.render();
|
|
627
|
+
}
|
|
628
|
+
|
|
629
|
+
deleteTodo(id) {
|
|
630
|
+
this.todos = this.todos.filter(todo => todo.id !== id);
|
|
631
|
+
this.render();
|
|
632
|
+
}
|
|
633
|
+
|
|
634
|
+
toggleTodo(id) {
|
|
635
|
+
const todo = this.todos.find(todo => todo.id === id);
|
|
636
|
+
if (todo) {
|
|
637
|
+
todo.completed = !todo.completed;
|
|
638
|
+
this.render();
|
|
639
|
+
}
|
|
640
|
+
}
|
|
641
|
+
|
|
642
|
+
render() {
|
|
643
|
+
const fragment = document.createDocumentFragment();
|
|
644
|
+
|
|
645
|
+
this.todos.forEach(todo => {
|
|
646
|
+
const item = document.createElement('div');
|
|
647
|
+
item.className = `todo-item ${todo.completed ? 'completed' : ''}`;
|
|
648
|
+
item.dataset.todoItem = '';
|
|
649
|
+
item.dataset.todoId = todo.id;
|
|
650
|
+
|
|
651
|
+
item.innerHTML = `
|
|
652
|
+
<input type="checkbox" ${todo.completed ? 'checked' : ''} data-action="toggle">
|
|
653
|
+
<span class="todo-text">${escapeHtml(todo.text)}</span>
|
|
654
|
+
<button class="btn-delete" data-action="delete">Delete</button>
|
|
655
|
+
`;
|
|
656
|
+
|
|
657
|
+
fragment.appendChild(item);
|
|
658
|
+
});
|
|
659
|
+
|
|
660
|
+
this.container.replaceChildren(fragment);
|
|
661
|
+
}
|
|
662
|
+
}
|
|
663
|
+
|
|
664
|
+
// Usage
|
|
665
|
+
// const todoList = new TodoList('[data-todo-list]');
|
|
666
|
+
// todoList.addTodo('Learn DOM manipulation');
|
|
667
|
+
|