|
1 | | -# XenoAtom.Terminal.UI Code Contribution Instructions |
| 1 | +# XenoAtom.Terminal.UI — Agent Instructions |
2 | 2 |
|
3 | 3 | XenoAtom.Terminal.UI is a modern, reactive retained-mode terminal UI framework for .NET. |
4 | 4 |
|
5 | | -The project is still in a pre-release state. Remove this line when the project reaches a stable release. |
| 5 | +Pre-release project. Remove this line at stable release. |
6 | 6 |
|
7 | | -## Overview |
| 7 | +Paths/commands below are relative to this directory (repo root). |
8 | 8 |
|
9 | | -- In the `readme.md` file, you will find general information about the XenoAtom.Terminal.UI project. |
10 | | -- In the `site/docs/readme.md` file you will find the user guide documentation for the XenoAtom.Terminal.UI library. |
11 | | -- For control/framework implementation guidelines, you must follow `site/docs/control-development.md`. |
| 9 | +## Orientation |
12 | 10 |
|
13 | | -## Project Structure |
| 11 | +- Library: `src/XenoAtom.Terminal.UI/` |
| 12 | +- Source generator: `src/XenoAtom.Terminal.UI.SourceGen/` |
| 13 | +- Tests (MSTest): `src/XenoAtom.Terminal.UI.Tests/` |
| 14 | +- Samples: `samples/` |
| 15 | +- Docs/site: `site/` (user docs: `site/docs/`, specs: `site/docs/specs/`) |
| 16 | +- Must-read dev docs: `site/docs/readme.md`, `site/docs/control-development.md` |
14 | 17 |
|
15 | | -- In the `src/XenoAtom.Terminal.UI` folder you will find the code for the main XenoAtom.Terminal.UI library. |
16 | | -- In the `src/XenoAtom.Terminal.UI.SourceGen` folder you will find the Roslyn source generator used by the library. |
17 | | -- In the `src/XenoAtom.Terminal.UI.Tests` folder you will find the unit tests for the library. |
18 | | -- In the `samples` folder you will find sample applications demonstrating the usage of XenoAtom.Terminal.UI. |
19 | | -- In the `site` folder you will find the website and documentation; user docs are in `site/docs` and specs are in `site/docs/specs`. |
| 18 | +## Build & Test |
20 | 19 |
|
21 | | -## Building and Testing |
| 20 | +```sh |
| 21 | +cd src |
| 22 | +dotnet build -c Release |
| 23 | +dotnet test -c Release |
| 24 | +``` |
22 | 25 |
|
23 | | -- To build the project, navigate to the `src` directory and run `dotnet build -c Release`. |
24 | | -- To run the unit tests, navigate to the `src` directory and run `dotnet test -c Release`. |
25 | | -- To regenerate the website control screenshots, run `dotnet run -c Release --project samples/ControlsDemo -- --export-screenshots` (outputs to `site/img/controls`). |
26 | | -- To build the website, navigate to the `site` directory and run `lunet build`. |
27 | | -- Ensure that all tests pass successfully before submitting any changes. |
28 | | -- Ensure that user guide documentation (`site/docs/readme.md`) and top-level readme are updated to reflect any changes made to the library. |
29 | | -- Ensure that the website builds successfully (`lunet build` from the `site` directory) when changing `site/**`. |
| 26 | +Website (only if touching `site/**`): |
30 | 27 |
|
31 | | -## General Coding Instructions |
| 28 | +```sh |
| 29 | +cd site |
| 30 | +lunet build |
| 31 | +``` |
32 | 32 |
|
33 | | -- Follow the coding style and conventions used in the existing code base. |
34 | | -- Write clear and concise inline comments to explain the purpose and functionality of your code. This is about the "why" more than the "what". |
35 | | -- All public APIs must have XML documentation comments to avoid CS1591 warnings. |
36 | | -- Ensure that your code is well-structured and modular to facilitate maintenance and future enhancements. |
37 | | -- Adhere to best practices for error handling and input validation. |
38 | | -- Write unit tests for any new functionality you add to ensure code quality and reliability. |
39 | | - - When fixing a bug, add a unit test that reproduces the bug before implementing the fix. |
40 | | -- Use meaningful variable and method names that accurately reflect their purpose. |
41 | | -- Avoid code duplication by reusing existing methods and classes whenever possible. |
| 33 | +Screenshots (only if control visuals changed): |
42 | 34 |
|
43 | | -## C# Coding Conventions |
| 35 | +```sh |
| 36 | +dotnet run -c Release --project samples/ControlsDemo -- --export-screenshots |
| 37 | +# outputs to site/img/controls |
| 38 | +``` |
44 | 39 |
|
45 | | -### Naming Conventions |
| 40 | +## Rules (Do/Don't) |
46 | 41 |
|
47 | | -- Use `PascalCase` for public members, types, and namespaces. |
48 | | -- Use `camelCase` for local variables and parameters. |
49 | | -- Use `_camelCase` (with underscore prefix) for private fields. |
50 | | -- Prefix interfaces with `I` (e.g., `IMyInterface`). |
51 | | -- Use descriptive names; avoid abbreviations unless widely understood (e.g., `Id`, `Url`). |
| 42 | +- Keep diffs focused; avoid drive-by refactors/formatting and unnecessary dependencies. |
| 43 | +- Follow existing patterns/naming; add comments only for non-obvious "why". |
| 44 | +- New/changed behavior requires tests; bug fix = regression test first, then fix. |
| 45 | +- Public APIs require XML docs (avoid CS1591) and should document thrown exceptions. |
| 46 | +- If behavior changes, update docs: `readme.md` and `site/docs/**` (especially `site/docs/readme.md`). |
52 | 47 |
|
53 | | -### Code Style |
| 48 | +## C# Defaults |
54 | 49 |
|
55 | | -- Use file-scoped namespaces (e.g., `namespace XenoAtom.Terminal.UI;`) unless the file requires multiple namespaces. |
56 | | -- Use `var` when the type is obvious from the right-hand side; otherwise, use explicit types. |
57 | | -- Prefer expression-bodied members for single-line implementations. |
58 | | -- Use pattern matching and switch expressions where they improve readability. |
59 | | -- Place `using` directives outside the namespace, sorted alphabetically with `System` namespaces first. |
| 50 | +- Naming: `PascalCase` public/types/namespaces, `camelCase` locals/params, `_camelCase` private fields, `I*` interfaces. |
| 51 | +- Style: file-scoped namespaces; `using` outside namespace (`System` first); `var` when type is obvious. |
| 52 | +- Nullability: enabled; respect annotations; prefer `is null`/`is not null`; no warning suppressions without a brief justification comment. |
| 53 | +- Validation: use `ArgumentNullException.ThrowIfNull()`/`ArgumentException.ThrowIfNullOrEmpty()`; throw specific exceptions with helpful messages. |
| 54 | +- Async: `Async` suffix; no `async void` (except event handlers); `ConfigureAwait(false)` in library code; consider `ValueTask<T>` on hot paths. |
60 | 55 |
|
61 | | -### Nullable Reference Types |
| 56 | +## Perf / AOT / Trimming |
62 | 57 |
|
63 | | -- This project uses nullable reference types. Respect nullability annotations. |
64 | | -- Never suppress nullable warnings (`#pragma warning disable`) without a comment explaining why. |
65 | | -- Use `ArgumentNullException.ThrowIfNull()` for null checks on parameters. |
66 | | -- Prefer `is null` and `is not null` over `== null` and `!= null`. |
| 58 | +- Minimize allocations (`Span<T>`, `ArrayPool<T>`, `StringBuilder` in loops). |
| 59 | +- Keep code AOT/trimmer-friendly: avoid reflection; prefer source generators; use `[DynamicallyAccessedMembers]` when reflection is required. |
| 60 | +- Use `sealed` for non-inheritable classes. |
67 | 61 |
|
68 | | -### Error Handling |
| 62 | +## API Design |
69 | 63 |
|
70 | | -- Throw `ArgumentException` or `ArgumentNullException` for invalid arguments. |
71 | | -- Use specific exception types rather than generic `Exception`. |
72 | | -- Include meaningful error messages that help diagnose the issue. |
73 | | -- Document exceptions in XML comments using `<exception cref="...">`. |
| 64 | +- Prefer overloads over optional params (binary compatibility); consider `Try*` alongside throwing APIs. |
| 65 | +- Obsolete before removal once stable (`[Obsolete("...", error: false)]`). |
74 | 66 |
|
75 | | -### Async/Await |
| 67 | +## Related Repos |
76 | 68 |
|
77 | | -- Suffix async methods with `Async` (e.g., `RunAsync`). |
78 | | -- Use `ConfigureAwait(false)` in library code unless context capture is required. |
79 | | -- Prefer `ValueTask<T>` over `Task<T>` for hot paths that often complete synchronously. |
80 | | -- Never use `async void` except for event handlers. |
| 69 | +These repos are optional local checkouts and may not exist in the current workspace. If present, consult their `AGENTS.md` |
| 70 | +for cross-repo changes; otherwise treat them as external dependencies (typically consumed via NuGet). |
81 | 71 |
|
82 | | -## Performance Considerations |
| 72 | +- `XenoAtom.Ansi`: `../XenoAtom.Ansi` (if checked out) |
| 73 | +- `XenoAtom.Terminal`: `../XenoAtom.Terminal` (if checked out) |
83 | 74 |
|
84 | | -- Ensure that the code is optimized for performance without sacrificing readability. |
85 | | -- Ensure that the code minimizes GC allocations where possible. |
86 | | - - Use `Span<T>`/`ReadOnlySpan<T>` where appropriate to reduce memory allocations. |
87 | | - - Use `stackalloc` for small, fixed-size buffers in performance-critical paths. |
88 | | - - Prefer `StringBuilder` for string concatenation in loops. |
89 | | - - Use `ArrayPool<T>` for temporary arrays that would otherwise cause allocations. |
90 | | -- Ensure generated code is AOT-compatible and trimmer-friendly. |
91 | | - - Avoid reflection where possible; prefer source generators. |
92 | | - - Use `[DynamicallyAccessedMembers]` attributes when reflection is necessary. |
93 | | -- Use `sealed` on classes that are not designed for inheritance to enable devirtualization. |
94 | | -- Prefer `ReadOnlySpan<char>` over `string` for parsing and substring operations. |
| 75 | +## Git / Pre-submit |
95 | 76 |
|
96 | | -## Testing Guidelines |
97 | | - |
98 | | -### Test Organization |
99 | | - |
100 | | -- Name test classes as `{ClassName}Tests` (e.g., `ParserTests`). |
101 | | -- Name test methods descriptively: `{MethodName}_{Scenario}_{ExpectedResult}` or use plain English. |
102 | | -- Group related tests using `#region` or nested classes if the test file is large. |
103 | | - |
104 | | -### Test Quality |
105 | | - |
106 | | -- Each test should verify one specific behavior (single assertion concept). |
107 | | -- Use the Arrange-Act-Assert (AAA) pattern. |
108 | | -- Include edge cases: null inputs, empty collections, boundary values, and error conditions. |
109 | | -- Avoid test interdependencies; each test must be able to run in isolation. |
110 | | - |
111 | | -### Test Coverage |
112 | | - |
113 | | -- Aim for high coverage of public APIs and critical code paths. |
114 | | -- Prioritize testing complex logic, error handling, and edge cases over trivial code. |
115 | | -- When fixing a bug, first write a test that reproduces the bug, then fix it. |
116 | | - |
117 | | -## API Design Guidelines |
118 | | - |
119 | | -- Follow .NET API design guidelines for consistency with the ecosystem. |
120 | | -- Don't over engineer APIs; keep them simple and focused. |
121 | | -- Don't introduce unnecessary interface abstractions; prefer concrete types unless specific extensibility is required and preferred through an interface. |
122 | | -- Use immutable types where possible to enhance thread safety and predictability. |
123 | | -- Allow mutable types when necessary for performance or usability. |
124 | | -- Make APIs hard to misuse: validate inputs early, use strong types. |
125 | | -- Prefer method overloads over optional parameters for binary compatibility. |
126 | | -- Use `params ReadOnlySpan<T>` for variadic methods (C# 13+) when targeting modern runtimes. |
127 | | -- Consider adding `Try*` pattern methods (returning `bool`) alongside throwing versions. |
128 | | -- Mark obsolete APIs with `[Obsolete("message", error: false)]` before removal. |
129 | | - - Unless this file is stating that the project is still in a pre-release state. |
130 | | - |
131 | | -## Git Commit Instructions |
132 | | - |
133 | | -- Write a concise and descriptive commit message that summarizes the changes made. |
134 | | -- Start the commit message with a verb in imperative mood (e.g., "Add", "Fix", "Update", "Remove"). |
135 | | -- Keep the first line under 72 characters; add details in the body if needed. |
136 | | -- Create a commit for each logical change or feature added to facilitate easier code review and tracking of changes. |
137 | | -- Reference related issues in commit messages when applicable (e.g., "Fix #123"). |
138 | | -- DO NOT remove files that was added/changed locally but is not part of your intended changes. |
139 | | - |
140 | | -## Resources |
141 | | - |
142 | | -The following libraries and resources are relevant to help specify this project: |
143 | | - |
144 | | -- `XenoAtom.Ansi` library: `C:\code\XenoAtom\XenoAtom.Ansi`, the library has guidance at `C:\code\XenoAtom\XenoAtom.Ansi\AGENTS.md`. |
145 | | -- `XenoAtom.Terminal` library: `C:\code\XenoAtom\XenoAtom.Terminal`, the library has guidance at `C:\code\XenoAtom\XenoAtom.Terminal\AGENTS.md`. |
146 | | - - This library depends on `XenoAtom.Ansi`. |
147 | | -- `XenoAtom.Collections` library: `C:\code\XenoAtom\XenoAtom.Collections`, used for internal collections handling that are faster than standard .NET collections. |
148 | | - - It has `UnsafeDictionary` and `UnsafeList` that can be used for internal data structures. |
149 | | - - These are structs that can be stored as non-readonly fields in other structs/classes. |
150 | | - |
151 | | -The NuGet packages of these libraries are used by XenoAtom.Terminal.UI. |
152 | | - |
153 | | -## Pre-Submission Checklist |
154 | | - |
155 | | -Before submitting changes, verify: |
156 | | - |
157 | | -- [ ] Code builds without errors or warnings (`dotnet build -c Release`). |
158 | | -- [ ] All tests pass (`dotnet test -c Release`). |
159 | | -- [ ] New public APIs have XML documentation comments. |
160 | | -- [ ] Changes are covered by unit tests. |
161 | | -- [ ] No unintended files are included in the commit. |
162 | | -- [ ] Documentation is updated if behavior changes. |
163 | | -- [ ] Screenshots are up to date when changing control visuals (`dotnet run -c Release --project samples/ControlsDemo -- --export-screenshots`). |
| 77 | +- Commits: one logical change per commit unless the user asks for a single commit; imperative subject, < 72 chars. |
| 78 | +- Pre-submit: `dotnet build -c Release` + `dotnet test -c Release`; `lunet build` when touching `site/**`; refresh screenshots when control visuals change. |
| 79 | +- Do not delete unrelated local files. |
0 commit comments