smdev 1.1.1 → 1.2.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (36) hide show
  1. checksums.yaml +4 -4
  2. data/lib/smdev/cursor_rules/backup_manager.rb +103 -0
  3. data/lib/smdev/cursor_rules/config_manager.rb +60 -0
  4. data/lib/smdev/cursor_rules/directory_manager.rb +55 -0
  5. data/lib/smdev/cursor_rules/file_copier.rb +53 -0
  6. data/lib/smdev/cursor_rules/file_operations.rb +83 -0
  7. data/lib/smdev/cursor_rules/installer.rb +128 -0
  8. data/lib/smdev/cursor_rules/templates/.cursor/rules/core-rules/readme.md +1 -0
  9. data/lib/smdev/cursor_rules/templates/.cursor/rules/core-rules/rule-generating-agent.mdc +86 -0
  10. data/lib/smdev/cursor_rules/templates/.cursor/rules/default.mdc +42 -0
  11. data/lib/smdev/cursor_rules/templates/.cursor/rules/documentation/markdown-auto.mdc +59 -0
  12. data/lib/smdev/cursor_rules/templates/.cursor/rules/documentation/readme.md +1 -0
  13. data/lib/smdev/cursor_rules/templates/.cursor/rules/global-rules/emoji-communication-always.mdc +33 -0
  14. data/lib/smdev/cursor_rules/templates/.cursor/rules/global-rules/performance-standards-agent.mdc +36 -0
  15. data/lib/smdev/cursor_rules/templates/.cursor/rules/global-rules/readme.md +5 -0
  16. data/lib/smdev/cursor_rules/templates/.cursor/rules/global-rules/tech-stack-agent.mdc +42 -0
  17. data/lib/smdev/cursor_rules/templates/.cursor/rules/rb-rules/database-standards-agent.mdc +52 -0
  18. data/lib/smdev/cursor_rules/templates/.cursor/rules/rb-rules/rails-conventions-agent.mdc +48 -0
  19. data/lib/smdev/cursor_rules/templates/.cursor/rules/rb-rules/readme.md +1 -0
  20. data/lib/smdev/cursor_rules/templates/.cursor/rules/testing-rules/rspec-standards-agent.mdc +51 -0
  21. data/lib/smdev/cursor_rules/templates/.cursor/rules/tool-rules/gitpush.mdc +35 -0
  22. data/lib/smdev/cursor_rules/templates/.cursor/rules/tool-rules/readme.md +1 -0
  23. data/lib/smdev/cursor_rules/templates/.cursor/rules/ts-rules/readme.md +1 -0
  24. data/lib/smdev/cursor_rules/templates/.cursor/rules/ui-rules/readme.md +11 -0
  25. data/lib/smdev/cursor_rules/templates/.cursor/rules/ui-rules/ui-component-standards-agent.mdc +55 -0
  26. data/lib/smdev/cursor_rules/templates/.cursor/rules/workflows/workflow-agile-manual.mdc +48 -0
  27. data/lib/smdev/cursor_rules/templates/.cursor/templates/template-arch.md +76 -0
  28. data/lib/smdev/cursor_rules/templates/.cursor/templates/template-prd.md +136 -0
  29. data/lib/smdev/cursor_rules/templates/.cursor/templates/template-story.md +146 -0
  30. data/lib/smdev/cursor_rules/templates/docs/agile-readme.md +251 -0
  31. data/lib/smdev/cursor_rules/templates/docs/cursor_rules.md +88 -0
  32. data/lib/smdev/cursor_rules/user_interface.rb +27 -0
  33. data/lib/smdev/cursor_rules.rb +16 -0
  34. data/lib/smdev/ecs_exec.rb +0 -4
  35. data/lib/smdev.rb +117 -101
  36. metadata +107 -5
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: c58945c4808bf1e113f8c9b2b3ea2a7ea56ac7d6d923ca72981e74fb1b0e2a43
4
- data.tar.gz: f019058ffd24ab81660af47afb3d12a379bcbdad54c8f6190bafa6a2380ffa59
3
+ metadata.gz: f7cac5467108208cbfc6bb8222de4812bc7add3e1d754fa42adeadc6aeff8b9b
4
+ data.tar.gz: 5eff861b8d3abe262479fc5c7359a87f7e37cc6a2604fef2432a99ed7df9629b
5
5
  SHA512:
6
- metadata.gz: c0949fa365a34eebafd409ca28a9ebedc390fd817f32908571f9475b0d981bfa80cdb4dccb2ffdaabb8b98516c7be1c3c920ae3d5f3a5a7df218716f2c865510
7
- data.tar.gz: a314498451823793038cf014c529b2ccc1c1aa98283b5f507f05b5d5c68f2ec732908371f16ac95400d7d8b495758ea6590231815c489fecb91ab40717d3c909
6
+ metadata.gz: 242145f0fb4353bc5a0258f5b806284d7a59ff9567e12c4333a155801cbd617f74d72590762386091938425cdb9ad76ae580ca0454ceefeed05d690479028ef6
7
+ data.tar.gz: ac154eb5afc942887d1bbd7270092f946da4f5175c3ca67c2256c45b02a1766f25c3329a9ee0023d2bf95da275d31932e262f7256cb0799c499c9c0dce9ba5d6
@@ -0,0 +1,103 @@
1
+ require 'fileutils'
2
+
3
+ module Smdev
4
+ module CursorRules
5
+ class BackupManager
6
+ def initialize(target_dir, timestamp)
7
+ @target_dir = target_dir
8
+ @timestamp = timestamp
9
+ @backup_created = false
10
+ end
11
+
12
+ def create_backup
13
+ @backup_dir = File.join(@target_dir, '.cursor/backups', @timestamp)
14
+ FileUtils.mkdir_p(@backup_dir)
15
+
16
+ backup_cursor_directory
17
+ backup_docs
18
+
19
+ puts "📦 Created backup in: #{@backup_dir}"
20
+ @backup_created = true
21
+ true
22
+ end
23
+
24
+ def restore
25
+ return unless backup_exists?
26
+
27
+ restore_directory('rules')
28
+ restore_directory('templates')
29
+ restore_docs
30
+
31
+ puts "♻️ Restored previous version from backup"
32
+ true
33
+ end
34
+
35
+ def backup_exists?
36
+ @backup_created
37
+ end
38
+
39
+ private
40
+
41
+ def backup_cursor_directory
42
+ ['rules', 'templates'].each do |dir|
43
+ backup_subdirectory(dir)
44
+ end
45
+ end
46
+
47
+ def backup_subdirectory(dir)
48
+ source_dir = File.join(@target_dir, '.cursor', dir)
49
+ return unless File.directory?(source_dir)
50
+
51
+ target_dir = File.join(@backup_dir, dir)
52
+ FileUtils.mkdir_p(target_dir)
53
+
54
+ copy_directory_contents(source_dir, target_dir)
55
+ end
56
+
57
+ def copy_directory_contents(source_dir, target_dir)
58
+ Dir.glob(File.join(source_dir, '**/*')).each do |file|
59
+ next unless File.file?(file)
60
+ copy_file(file, source_dir, target_dir)
61
+ end
62
+ end
63
+
64
+ def copy_file(file, source_dir, target_dir)
65
+ rel_path = Pathname.new(file).relative_path_from(Pathname.new(source_dir)).to_s
66
+ target_file = File.join(target_dir, rel_path)
67
+
68
+ FileUtils.mkdir_p(File.dirname(target_file))
69
+ FileUtils.cp(file, target_file)
70
+ end
71
+
72
+ def backup_docs
73
+ docs_dir = File.join(@target_dir, 'docs')
74
+ return unless File.directory?(docs_dir)
75
+
76
+ target_dir = File.join(@backup_dir, 'docs')
77
+ FileUtils.mkdir_p(target_dir)
78
+
79
+ copy_directory_contents(docs_dir, target_dir)
80
+ end
81
+
82
+ def restore_directory(dir)
83
+ source_dir = File.join(@backup_dir, dir)
84
+ return unless File.directory?(source_dir)
85
+
86
+ target_dir = File.join(@target_dir, '.cursor', dir)
87
+ FileUtils.mkdir_p(target_dir)
88
+
89
+ copy_directory_contents(source_dir, target_dir)
90
+ end
91
+
92
+ def restore_docs
93
+ source_dir = File.join(@backup_dir, 'docs')
94
+ return unless File.directory?(source_dir)
95
+
96
+ target_dir = File.join(@target_dir, 'docs')
97
+ FileUtils.mkdir_p(target_dir)
98
+
99
+ copy_directory_contents(source_dir, target_dir)
100
+ end
101
+ end
102
+ end
103
+ end
@@ -0,0 +1,60 @@
1
+ module Smdev
2
+ module CursorRules
3
+ # Handles configuration file updates for cursor rules
4
+ module ConfigManager
5
+ # Updates configuration files (.gitignore, .cursorignore, .cursorindexingignore)
6
+ #
7
+ # @return [void]
8
+ def update_configuration_files
9
+ update_gitignore
10
+ update_cursorignore
11
+ update_cursorindexingignore
12
+ puts "📝 Updated configuration files"
13
+ end
14
+
15
+ private
16
+
17
+ def update_gitignore
18
+ gitignore_path = File.join(@target_dir, '.gitignore')
19
+ gitignore_entries = [
20
+ "\n# Private individual user cursor rules",
21
+ ".cursor/rules/_*.mdc"
22
+ ]
23
+
24
+ update_config_file(gitignore_path, gitignore_entries)
25
+ end
26
+
27
+ def update_cursorignore
28
+ cursorignore_path = File.join(@target_dir, '.cursorignore')
29
+ cursorignore_entries = [
30
+ "\n# Project notes and templates",
31
+ "xnotes/"
32
+ ]
33
+
34
+ update_config_file(cursorignore_path, cursorignore_entries)
35
+ end
36
+
37
+ def update_cursorindexingignore
38
+ indexingignore_path = File.join(@target_dir, '.cursorindexingignore')
39
+ indexingignore_entries = [
40
+ "\n# Templates - accessible but not indexed",
41
+ ".cursor/templates/"
42
+ ]
43
+
44
+ update_config_file(indexingignore_path, indexingignore_entries)
45
+ end
46
+
47
+ def update_config_file(file_path, entries)
48
+ content = File.exist?(file_path) ? File.read(file_path) : ""
49
+
50
+ entries.each do |entry|
51
+ unless content.include?(entry)
52
+ content += "\n#{entry}"
53
+ end
54
+ end
55
+
56
+ File.write(file_path, content.strip + "\n")
57
+ end
58
+ end
59
+ end
60
+ end
@@ -0,0 +1,55 @@
1
+ module Smdev
2
+ module CursorRules
3
+ # Handles directory creation and validation operations
4
+ class DirectoryManager
5
+ # Directory containing cursor rules and templates
6
+ CURSOR_DIR = '.cursor'
7
+ # Directory for cursor rules
8
+ RULES_DIR = File.join(CURSOR_DIR, 'rules')
9
+ # Directory for cursor templates
10
+ TEMPLATES_DIR = File.join(CURSOR_DIR, 'templates')
11
+ # Directory for documentation
12
+ DOCS_DIR = 'docs'
13
+ # Directory for backups
14
+ BACKUPS_DIR = File.join(CURSOR_DIR, 'backups')
15
+
16
+ def initialize(target_dir)
17
+ @target_dir = target_dir
18
+ end
19
+
20
+ def create_required_directories
21
+ [
22
+ CURSOR_DIR,
23
+ RULES_DIR,
24
+ TEMPLATES_DIR,
25
+ DOCS_DIR,
26
+ BACKUPS_DIR
27
+ ].each do |dir|
28
+ path = File.join(@target_dir, dir)
29
+ FileUtils.mkdir_p(path)
30
+ puts "📁 Created directory: #{dir}"
31
+ end
32
+ end
33
+
34
+ def cursor_rules_exist?
35
+ File.directory?(File.join(@target_dir, CURSOR_DIR))
36
+ end
37
+
38
+ def validate_target_directory
39
+ unless File.directory?(@target_dir)
40
+ raise Error, "Target directory '#{@target_dir}' does not exist"
41
+ end
42
+ end
43
+
44
+ def validate_source_directory(source_dir)
45
+ return if Dir.exist?(source_dir)
46
+ raise Error, "Source cursor directory not found in gem"
47
+ end
48
+
49
+ def validate_docs_directory(source_docs)
50
+ return if Dir.exist?(source_docs)
51
+ raise Error, "Source documentation not found in gem"
52
+ end
53
+ end
54
+ end
55
+ end
@@ -0,0 +1,53 @@
1
+ require 'fileutils'
2
+ require 'pathname'
3
+
4
+ module Smdev
5
+ module CursorRules
6
+ class FileCopier
7
+ def initialize(source_dir, target_dir)
8
+ @source_dir = source_dir
9
+ @target_dir = target_dir
10
+ end
11
+
12
+ def copy_rules(source_rules, target_rules)
13
+ FileUtils.mkdir_p(target_rules)
14
+
15
+ Dir.glob(File.join(source_rules, '**', '*.mdc')).each do |source_file|
16
+ copy_with_path(source_file, source_rules, target_rules)
17
+ end
18
+ end
19
+
20
+ def copy_templates(source_templates, target_templates)
21
+ return unless Dir.exist?(source_templates)
22
+
23
+ FileUtils.mkdir_p(target_templates)
24
+ FileUtils.cp_r(Dir.glob("#{source_templates}/*"), target_templates)
25
+ end
26
+
27
+ def copy_documentation(source_docs, target_docs)
28
+ FileUtils.mkdir_p(target_docs)
29
+
30
+ Dir.glob(File.join(source_docs, '**', '*')).each do |file|
31
+ if File.file?(file)
32
+ copy_with_path(file, source_docs, target_docs)
33
+ elsif File.directory?(file)
34
+ rel_path = Pathname.new(file).relative_path_from(Pathname.new(source_docs)).to_s
35
+ FileUtils.mkdir_p(File.join(target_docs, rel_path))
36
+ end
37
+ end
38
+ end
39
+
40
+ private
41
+
42
+ def copy_with_path(source_file, source_base, target_base)
43
+ return unless File.file?(source_file)
44
+
45
+ relative_path = Pathname.new(source_file).relative_path_from(Pathname.new(source_base)).to_s
46
+ target_file = File.join(target_base, relative_path)
47
+
48
+ FileUtils.mkdir_p(File.dirname(target_file))
49
+ FileUtils.cp(source_file, target_file)
50
+ end
51
+ end
52
+ end
53
+ end
@@ -0,0 +1,83 @@
1
+ require 'fileutils'
2
+
3
+ module Smdev
4
+ module CursorRules
5
+ # Handles file operations for cursor rules installation
6
+ module FileOperations
7
+ # Constants for directory paths
8
+ CURSOR_DIR = '.cursor'
9
+ DOCS_DIR = 'docs'
10
+ CURSOR_SUBDIRS = ['rules', 'templates'].freeze
11
+
12
+ # Copies cursor rules and templates from source to target
13
+ #
14
+ # @raise [Error] if source directory is not found
15
+ def copy_cursor_files
16
+ validate_source_directory(File.join(@source_dir, CURSOR_DIR))
17
+ debug("Copying cursor files from #{@source_dir} to #{File.join(@target_dir, CURSOR_DIR)}")
18
+
19
+ create_cursor_directories
20
+ copy_cursor_subdirectories
21
+
22
+ puts "📝 Copied cursor rules and templates"
23
+ end
24
+
25
+ # Copies documentation files from source to target
26
+ #
27
+ # @raise [Error] if source documentation is not found
28
+ def copy_docs
29
+ docs_source = File.join(@source_dir, DOCS_DIR)
30
+ validate_source_directory(docs_source)
31
+
32
+ debug("Copying docs from #{docs_source} to #{File.join(@target_dir, DOCS_DIR)}")
33
+
34
+ # Create target directory
35
+ FileUtils.mkdir_p(File.join(@target_dir, DOCS_DIR))
36
+
37
+ # Copy documentation files
38
+ copy_directory_contents(docs_source, File.join(@target_dir, DOCS_DIR))
39
+
40
+ puts "📚 Copied documentation files"
41
+ end
42
+
43
+ private
44
+
45
+ def create_cursor_directories
46
+ CURSOR_SUBDIRS.each do |dir|
47
+ FileUtils.mkdir_p(File.join(@target_dir, CURSOR_DIR, dir))
48
+ end
49
+ end
50
+
51
+ def copy_cursor_subdirectories
52
+ CURSOR_SUBDIRS.each do |dir|
53
+ source = File.join(@source_dir, CURSOR_DIR, dir)
54
+ target = File.join(@target_dir, CURSOR_DIR, dir)
55
+
56
+ copy_directory_contents(source, target) if File.directory?(source)
57
+ end
58
+ end
59
+
60
+ def copy_directory_contents(source_dir, target_dir)
61
+ Dir.glob(File.join(source_dir, '**/*')).each do |file|
62
+ next unless File.file?(file)
63
+
64
+ rel_path = Pathname.new(file).relative_path_from(Pathname.new(source_dir)).to_s
65
+ target_file = File.join(target_dir, rel_path)
66
+
67
+ debug("Copying #{file} to #{target_file}")
68
+ FileUtils.mkdir_p(File.dirname(target_file))
69
+ FileUtils.cp(file, target_file)
70
+ end
71
+ end
72
+
73
+ def validate_source_directory(dir)
74
+ return if File.directory?(dir)
75
+ raise Error, "Source directory '#{dir}' does not exist"
76
+ end
77
+
78
+ def debug(message)
79
+ puts "Debug: #{message}"
80
+ end
81
+ end
82
+ end
83
+ end
@@ -0,0 +1,128 @@
1
+ require 'fileutils'
2
+ require 'time'
3
+ require_relative 'backup_manager'
4
+ require_relative 'directory_manager'
5
+ require_relative 'file_copier'
6
+ require_relative 'user_interface'
7
+ require_relative 'config_manager'
8
+
9
+ module Smdev
10
+ module CursorRules
11
+ class Installer
12
+ include ConfigManager
13
+
14
+ CURSOR_DIR = '.cursor'
15
+ RULES_DIR = File.join(CURSOR_DIR, 'rules')
16
+ TEMPLATES_DIR = File.join(CURSOR_DIR, 'templates')
17
+ DOCS_DIR = 'docs'
18
+ BACKUPS_DIR = File.join(CURSOR_DIR, 'backups')
19
+
20
+ def initialize(target_dir, ui: UserInterface.new)
21
+ @target_dir = target_dir
22
+ @source_dir = CursorRules.templates_path
23
+ @directory_manager = DirectoryManager.new(target_dir)
24
+ @file_copier = FileCopier.new(@source_dir, target_dir)
25
+ @ui = ui
26
+ @backup_manager = BackupManager.new(target_dir, Time.now.strftime('%Y%m%d_%H%M%S'))
27
+ end
28
+
29
+ def install
30
+ begin
31
+ validate_and_prepare
32
+ perform_installation
33
+ @ui.display_success_message(@target_dir)
34
+ true
35
+ rescue StandardError => e
36
+ handle_error(e)
37
+ raise
38
+ end
39
+ end
40
+
41
+ private
42
+
43
+ def validate_and_prepare
44
+ @directory_manager.validate_target_directory
45
+ check_target_directory
46
+ end
47
+
48
+ def check_target_directory
49
+ if @directory_manager.cursor_rules_exist?
50
+ @ui.prompt_for_override
51
+ @backup_manager.create_backup
52
+ end
53
+ @directory_manager.create_required_directories
54
+ end
55
+
56
+ def perform_installation
57
+ copy_cursor_files
58
+ copy_docs
59
+ update_configuration_files
60
+ end
61
+
62
+ def copy_cursor_files
63
+ @directory_manager.validate_source_directory(@source_dir)
64
+
65
+ source_rules = File.join(@source_dir, DirectoryManager::CURSOR_DIR, 'rules')
66
+ target_rules = File.join(@target_dir, DirectoryManager::RULES_DIR)
67
+ @file_copier.copy_rules(source_rules, target_rules)
68
+
69
+ source_templates = File.join(@source_dir, DirectoryManager::CURSOR_DIR, 'templates')
70
+ target_templates = File.join(@target_dir, DirectoryManager::TEMPLATES_DIR)
71
+ @file_copier.copy_templates(source_templates, target_templates)
72
+
73
+ puts "📝 Copied cursor rules and templates"
74
+ end
75
+
76
+ def copy_docs
77
+ source_docs = File.join(@source_dir, DirectoryManager::DOCS_DIR)
78
+ target_docs = File.join(@target_dir, DirectoryManager::DOCS_DIR)
79
+
80
+ @directory_manager.validate_docs_directory(source_docs)
81
+ @file_copier.copy_documentation(source_docs, target_docs)
82
+ puts "📚 Copied documentation files"
83
+ end
84
+
85
+ def handle_error(error)
86
+ @ui.display_error(error)
87
+ @backup_manager.restore if @backup_manager.backup_exists?
88
+ end
89
+
90
+ def update_configuration_files
91
+ update_gitignore
92
+ update_cursorignore
93
+ update_cursorindexingignore
94
+ puts "📝 Updated configuration files"
95
+ end
96
+
97
+ def update_gitignore
98
+ gitignore_path = File.join(@target_dir, '.gitignore')
99
+ gitignore_entries = [
100
+ "\n# Private individual user cursor rules",
101
+ ".cursor/rules/_*.mdc"
102
+ ]
103
+
104
+ update_config_file(gitignore_path, gitignore_entries)
105
+ end
106
+
107
+ def update_cursorignore
108
+ cursorignore_path = File.join(@target_dir, '.cursorignore')
109
+ cursorignore_entries = [
110
+ "\n# Project notes and templates",
111
+ "xnotes/"
112
+ ]
113
+
114
+ update_config_file(cursorignore_path, cursorignore_entries)
115
+ end
116
+
117
+ def update_cursorindexingignore
118
+ indexingignore_path = File.join(@target_dir, '.cursorindexingignore')
119
+ indexingignore_entries = [
120
+ "\n# Templates - accessible but not indexed",
121
+ ".cursor/templates/"
122
+ ]
123
+
124
+ update_config_file(indexingignore_path, indexingignore_entries)
125
+ end
126
+ end
127
+ end
128
+ end
@@ -0,0 +1 @@
1
+ Core rules related to cursor or rule generation
@@ -0,0 +1,86 @@
1
+ ---
2
+ description: Always follow this when the user requests that a rule be added or modified, or asks you to remember to always do something in the future
3
+ globs:
4
+ alwaysApply: false
5
+ ---
6
+ # Cursor Rules Format
7
+
8
+ ## Template Structure for Rules Files
9
+
10
+ ```mdc
11
+ ---
12
+ description: `Explicit concise description to ensure the agent knows when to apply the rule` OR blank
13
+ globs: .cursor/rules/**/*.mdc OR blank
14
+ alwaysApply: {true or false}
15
+ ---
16
+
17
+ # Rule Title
18
+
19
+ ## Context
20
+
21
+ - When to apply this rule
22
+ - Prerequisites or conditions
23
+ - Why the rule was added or is needed
24
+
25
+ ## Critical Rules
26
+
27
+ - Concise, bulleted list of actionable rules the agent MUST follow
28
+
29
+ ## Examples
30
+
31
+ <example>
32
+ {valid rule application}
33
+ </example>
34
+
35
+ <example type="invalid">
36
+ {invalid rule application}
37
+ <example>
38
+ ```
39
+
40
+ ### Organizational Folders (Create if non existent)
41
+ All rules files will be under an organizational folder:
42
+ - .cursor/rules/core-rules - rules related to cursor agent behavior or rule generation specifically
43
+ - .cursor/rules/my-rules - gitignore in a shared repo, rules specifically for ME only
44
+ - .cursor/rules/global-rules - these will be rules that are ALWAYS applied to every chat and cmd/ctrl-k context
45
+ - .cursor/rules/testing-rules - rules about testing
46
+ - .cursor/rules/tool-rules - rules specific to different tools, such as git, linux commands, direction of usage of MCP tools
47
+ - .cursor/rules/ts-rules - typescript language specific rules
48
+ - .cursor/rules/rb-rules - ruby specific rules
49
+ - .cursor/rules/py-rules - python specific rules
50
+ - .cursor/rules/ui-rules - rules about html, css, react
51
+ * create new folders under .cursor/rules/ as needed following similar grouping conventions,
52
+ - for example `.cursor/rules/cs-rules` if we started using c# in a project
53
+
54
+ ## Glob Pattern Examples
55
+ Common glob patterns for different rule types:
56
+ - Core standards: .cursor/rules/*.mdc
57
+ - Language rules: *.cs, *.cpp
58
+ - Testing standards: *.test.ts, *.test.js
59
+ - React components: src/components/**/*.tsx
60
+ - Documentation: docs/**/*.md, *.md
61
+ - Configuration files: *.config.js
62
+ - Build artifacts: dist/**/*
63
+ - Multiple extensions: *.js, *.ts, *.tsx, *.rb
64
+ - Multiple patterns: dist/**/*.*, docs/**/*.md, *test*.*
65
+
66
+ ## Critical Rules
67
+ - Rule files will be located and named ALWAYS as: `.cursor/rules/{organizational-folder}/rule-name-{auto|agent|manual|always}.mdc`
68
+ - FrontMatter Rules Types:
69
+ - The front matter section must always start the file and include all 3 fields, even if the field value will be blank - the types are:
70
+ - Manual Rule: IF a Manual rule is requested - description and globs MUST be blank and alwaysApply: false and filename ends with -manual.mdc.
71
+ - Auto Rule: IF a rule is requested that should apply always to certain glob patterns (example all typescript files or all markdown files) - description must be blank, and alwaysApply: false and filename ends with -auto.mdc.
72
+ - Always Rule: Global Rule applies to every chat and cmd/ctrl-k - description and globs blank, and alwaysApply: true and filename ends with -always.mdc.
73
+ - Agent Select Rule: The rule does not need to be loaded into every chat thread, it serves a specific purpose. The agent can see the descriptions, and choose to load the full rule in to context on its own - description is critical, globs blank, and alwaysApply:false and filename ends with -agent.mdc
74
+ - For the Rule Context and Bullets - do not repeat yourself and do not be overly explanatory
75
+ - When a rule will only be used sometimes (useAlways: false) it is CRITICAL that the description describes when the AI will load the full rule into its context
76
+ - Use Concise Markdown Tailored to Agent Context Window usage
77
+ - Always indent content within XML Example section with 2 spaces
78
+ - Emojis and Mermaid diagrams are allowed and encouraged if it is not redundant and better explains the rule for the AI comprehension.
79
+ - TRY to keep the total rule line count under 50 lines, better under 25 lines
80
+ - Always include a valid and invalid example
81
+ - NEVER use quotes around glob patterns, NEVER group glob extensions with `{}`
82
+ - If the request for a rule or a future behavior change includes context of a mistake is made, this would be great to use in the example for the rule
83
+ - After rule is created or updated, Respond with the following:
84
+ - AutoRuleGen Success: path/rule-name.mdc
85
+ - Rule Type: {Rule Type}
86
+ - Short summary of what the rule will do
@@ -0,0 +1,42 @@
1
+ ---
2
+ description:
3
+ globs:
4
+ alwaysApply: false
5
+ ---
6
+ # Default Cursor Rules
7
+
8
+ ## Manual Rules
9
+ These rules can be triggered manually by the user.
10
+
11
+ ```cursor
12
+ # Example manual rule
13
+ @manual("Generate test file")
14
+ def generate_test():
15
+ """Generate a new test file for the current module"""
16
+ # Your rule implementation here
17
+ pass
18
+ ```
19
+
20
+ ## Auto Rules
21
+ These rules are triggered automatically based on file patterns.
22
+
23
+ ```cursor
24
+ # Example auto rule
25
+ @auto("*.py")
26
+ def format_python(file):
27
+ """Format Python files on save"""
28
+ # Your rule implementation here
29
+ pass
30
+ ```
31
+
32
+ ## Always Rules
33
+ These rules are always active.
34
+
35
+ ```cursor
36
+ # Example always rule
37
+ @always
38
+ def maintain_style():
39
+ """Maintain code style consistency"""
40
+ # Your rule implementation here
41
+ pass
42
+ ```
@@ -0,0 +1,59 @@
1
+ ---
2
+ description: ALWAYS use when writing or updating Markdown files to ensure consistent formatting and readability
3
+ globs: **/*.md
4
+ alwaysApply: false
5
+ ---
6
+
7
+ # Markdown Documentation Standards
8
+
9
+ ## Context
10
+
11
+ - When creating or modifying any Markdown documentation
12
+ - When establishing documentation structure and style
13
+ - When including diagrams, code blocks, or special elements in documentation
14
+
15
+ ## Critical Rules
16
+
17
+ - Follow Markdown best practices for formatting
18
+ - Maintain clear document structure with proper heading hierarchy
19
+ - Use Mermaid UML diagrams for documenting complex sequences or architecture
20
+ - Maximum heading depth: 4 levels
21
+ - Indent content within XML tags by 2 spaces
22
+ - Code Block need to indicate the language properly after the initial 3 backticks
23
+ - Keep tables properly aligned
24
+
25
+ ## Examples
26
+
27
+ <example>
28
+ # Document Title
29
+
30
+ ## Section Heading
31
+
32
+ Content with **bold text** and *italics*.
33
+
34
+ ```typescript
35
+ function example(): void {
36
+ console.log('Hello, Universe!');
37
+ }
38
+ ```
39
+
40
+ | Name | Type | Description |
41
+ |:-----:|:------:|:------------:|
42
+ | id | number | Primary key |
43
+ | name | string | User's name |
44
+
45
+ > 💡 **Tip:** Helpful suggestion.
46
+ </example>
47
+
48
+ <example type="invalid">
49
+ #Incorrect Heading
50
+ content without proper spacing
51
+
52
+ ```
53
+ function withoutLanguageSpecified() {
54
+ }
55
+ ```
56
+
57
+ |No|proper|alignment|And|invalid|table
58
+ | or | proper | formatting |||||
59
+ </example>
@@ -0,0 +1 @@
1
+ Rules related to documenting files