# Hodios paste pack: Conventions

Everything in Conventions from Hodios, the open prompt library by Hermes IDE: 11 entries, catalog 2026.1003.0.

Every entry is dedicated to the public domain under CC0 1.0. Copy, change and share them freely, no attribution needed.

Browse and search the library at https://hermes-ide.com/prompts

## How to use

Find an entry below and copy the text inside its block into ChatGPT, claude.ai or any chat. Replace each [PLACEHOLDER] with your own material. Personas, rules and styles work best as custom instructions or project instructions.

## Contents

- Conventions
  - [C# style rules](#csharp-style-rules) (rule)
  - [Go style rules](#go-style-rules) (rule)
  - [HTTP API design rules](#api-design-rules) (rule)
  - [Java style rules](#java-style-rules) (rule)
  - [Kotlin style rules](#kotlin-style-rules) (rule)
  - [Python style rules](#python-style-rules) (rule)
  - [React component rules](#react-component-rules) (rule)
  - [Rust style rules](#rust-style-rules) (rule)
  - [SQL style rules](#sql-style-rules) (rule)
  - [Swift style rules](#swift-style-rules) (rule)
  - [TypeScript strict rules](#typescript-strict-rules) (rule)

---

<a id="csharp-style-rules"></a>

## C# style rules

`csharp-style-rules` · rule · Conventions · https://hermes-ide.com/prompts/csharp-style-rules

Standing rules for C# an assistant writes, covering nullable reference types, async all the way with cancellation tokens, records and pattern matching, dependency injection and xUnit tests.

````markdown
Follow these rules for the rest of this conversation.

Apply these rules to files matching: `**/*.cs`.

When you write or change C# code in this project:

**Tooling and version**
- Use the target framework and `LangVersion` the project files declare, and only features they support. Do not change them on your own.
- Follow the repository's `.editorconfig` and analyzers, and keep the build free of new warnings. Use file-scoped namespaces and the project's existing conventions for `using` directives.
- Add NuGet packages only when the base class library cannot do the job in a few lines, through the project's central package management if it has it.

**Nullable reference types**
- Code assumes `<Nullable>enable</Nullable>`. Annotate every reference that can be null with `?` and handle it; never silence warnings with the null-forgiving operator unless a comment explains why the value cannot be null.
- Validate public arguments with `ArgumentNullException.ThrowIfNull(arg)` and the related `ThrowIf` helpers.
- Return empty collections, not `null`. Use the `Try` pattern (`bool TryGet(..., out T value)`) or a nullable return when absence is normal.

**Async**
- Async all the way: never block on tasks with `.Result`, `.Wait()` or `GetAwaiter().GetResult()`. Return `Task` or `Task<T>`; use `async void` only for event handlers.
- Every async method that does I/O takes a `CancellationToken cancellationToken` as its last parameter (optional with `= default` on public APIs, as the framework does) and passes it to every call that accepts one; analyzer CA2016 flags the calls where it is dropped.
- Name async methods with the `Async` suffix. Use `ConfigureAwait(false)` in library code; it is not needed in ASP.NET Core application code.
- Use `ValueTask` only where a measurement shows allocation matters. Use `IAsyncEnumerable<T>` for streaming results, and `await using` for `IAsyncDisposable`.

**Types and language features**
- Use records (or `record struct`) for immutable data, `init` accessors and `required` members for object construction, and keep mutable state private.
- Prefer switch expressions and pattern matching over `if`/`else` chains on types or values, with a discard arm that throws for unexpected cases.
- Use `DateTimeOffset` for timestamps and inject `TimeProvider` (.NET 8 and later; otherwise the project's clock abstraction) where code needs the current time, never `DateTime.Now` in logic. Use `decimal` for money.
- Always pass a `StringComparison` to string comparisons and `IndexOf`/`StartsWith` calls; use `StringComparer.OrdinalIgnoreCase` for case-insensitive keys.

**Dependency injection and configuration**
- Use constructor injection (primary constructors if the project uses them). No service locator calls to `IServiceProvider` inside business code.
- Register lifetimes correctly: never inject a scoped service (such as a `DbContext`) into a singleton. Bind configuration to options classes with `IOptions<T>` and validate them at startup.
- Create HTTP clients through `IHttpClientFactory` or typed clients, never `new HttpClient()` per call.

**Errors and resources**
- Throw specific exceptions with useful messages. Rethrow with `throw;` to keep the stack trace, never `throw ex;`. Never catch `Exception` to ignore it; catch broadly only at a boundary that logs and translates.
- Dispose `IDisposable` resources with `using` declarations. Do not use exceptions for normal control flow.

**Data access and LINQ**
- Keep LINQ readable; avoid enumerating the same `IEnumerable` twice (materialise once with `ToList()` when needed).
- With Entity Framework Core, use async query methods with the cancellation token, `AsNoTracking()` for read-only queries, and projections or `Include` to avoid N+1 queries.

**Logging**
- Use `ILogger<T>` with message templates and named placeholders: `logger.LogInformation("Order {OrderId} shipped", orderId)`. Never string interpolation in log calls, and never log secrets or personal data. Use the `LoggerMessage` source generator on hot paths if the project does.

**Tests (xUnit)**
- Use `[Fact]` for single cases and `[Theory]` with `[InlineData]` or `[MemberData]` for input tables. Name tests `Method_Scenario_ExpectedResult` or follow the project's existing scheme.
- Put setup in the constructor and cleanup in `Dispose` or `IAsyncLifetime`; no shared static mutable state between tests.
- Use the assertion library the project already uses, and `await Assert.ThrowsAsync<TException>(...)` for async failures, checking the exception type and message.
- Mock only at boundaries (HTTP, storage, time) with the project's mocking library; use a fake `TimeProvider` for time. Never `Thread.Sleep` or `Task.Delay` to wait for work in tests.
````

---

<a id="go-style-rules"></a>

## Go style rules

`go-style-rules` · rule · Conventions · https://hermes-ide.com/prompts/go-style-rules

Standing rules for Go an assistant writes, covering wrapped errors, context propagation, small consumer-side interfaces, table-driven tests and no goroutines without an owner.

````markdown
Follow these rules for the rest of this conversation.

Apply these rules to files matching: `**/*.go`.

When you write or change Go code in this project:

**Tooling**
- Code must be `gofmt`-formatted with imports grouped by `goimports`, and pass `go vet`. Follow the project's linter configuration (such as golangci-lint) if one exists.
- Use the Go version in `go.mod`. Keep `go.mod` tidy, and do not add a dependency for something the standard library does in a few lines.

**Errors**
- Return errors as the last result and handle every one. Never discard an error with `_` unless a comment says why it is safe.
- Add context once per layer with `fmt.Errorf("load config %q: %w", path, err)`. Use `%w` so callers can inspect the cause with `errors.Is` and `errors.As`; never compare error strings.
- Either handle an error or return it. Do not log it and return it too.
- Do not panic for expected failures. Reserve `panic` for programmer errors and impossible states, and do not let it cross a package's public API.
- Error strings start lowercase and have no trailing punctuation.

**Context**
- Any function that does I/O, blocks or may be cancelled takes `ctx context.Context` as its first parameter and passes it on.
- Never store a context in a struct, never pass `nil`, and create `context.Background()` only in `main`, initialisation and tests.
- Respect cancellation in loops and blocking operations, and do not use context values for optional parameters.

**Interfaces and types**
- Define interfaces in the package that uses them, keep them small (one to three methods), and accept interfaces while returning concrete types.
- Do not create an interface for a single implementation unless it is a deliberate seam for testing at a system boundary.
- Make zero values useful where possible, and avoid package-level mutable state and `init()` side effects.

**Concurrency**
- Write sequential code first. Add a goroutine only for a measured need or a real requirement for parallelism.
- Every goroutine has an owner who knows how it stops: it exits on context cancellation, and its errors reach the caller (prefer `errgroup`).
- The sender closes a channel. Protect shared state with a mutex or confine it to one goroutine, and never copy a struct that contains a mutex.
- Run tests with `-race` when concurrency is involved.

**Tests**
- Write table-driven tests with named `t.Run` subtests. Use `t.Helper()` in helpers and `t.Parallel()` where tests are independent.
- Report failures as `got X, want Y`, and use `cmp.Diff` or similar for structs.
- No `time.Sleep` for synchronisation. Wait on channels or conditions with a timeout. Put fixtures under `testdata/`.

**Naming and docs**
- Use MixedCaps, short receiver names that stay consistent, short lowercase package names, and no stutter (`http.Server`, not `http.HTTPServer`).
- Every exported identifier has a doc comment that starts with its name.
- Check the error from `Close` on anything you wrote to.
````

---

<a id="api-design-rules"></a>

## HTTP API design rules

`api-design-rules` · rule · Conventions · https://hermes-ide.com/prompts/api-design-rules

Rules for HTTP APIs covering resource naming, status codes, problem+json errors, cursor pagination, idempotency keys and versioning. Load when designing or changing HTTP endpoints.

````markdown
Follow these rules for the rest of this conversation.

When you design or change an HTTP API in this project, apply these rules. Where an existing API already follows a different convention, stay consistent with it and point out the difference instead of mixing styles.

**Resources and methods**
- Name resources with plural nouns in lowercase (`/orders`, `/orders/{order_id}/items`). Nest at most one level, and never put verbs in paths for create, read, update or delete.
- Model actions that are not CRUD as a sub-resource or a clearly named action endpoint (`POST /orders/{id}/cancellation`), following the existing pattern.
- `GET` is safe and has no body. `PUT` replaces and is idempotent. `PATCH` applies a partial update with a documented format (JSON Merge Patch unless the API already uses something else). `DELETE` is idempotent.
- Use one field casing across the whole API, matching what exists.

**Status codes**
- `201` with a `Location` header for creation, `200` with a body or `204` without, `400` for malformed requests, `401` when unauthenticated, `403` when authenticated but not allowed, `404` when the resource does not exist or must not be revealed, `409` for state conflicts, `412` for failed preconditions, `422` for validation errors if the API already uses it, and `429` with `Retry-After` for rate limits.
- Never return `200` with an error body, or a `5xx` for a client mistake.

**Errors**
- Return errors as `application/problem+json` (RFC 9457) with `type`, `title`, `status`, `detail` and `instance`. Add an `errors` array with a JSON pointer and message per invalid field for validation failures.
- Make `type` a stable identifier clients can branch on. Never expose stack traces, SQL or internal hostnames.

**Collections**
- Paginate every collection that can grow. Use opaque cursors with a `limit` that has a documented maximum, and return the next cursor or link. Use offset pagination only for small, stable sets.
- Sort deterministically, and keep filter and sort parameter names consistent across endpoints.

**Idempotency and concurrency**
- Accept an `Idempotency-Key` header on `POST` endpoints that create resources or move money. Store the key with a hash of the request and the response for a documented window. Replay the stored response for a repeated key, and reject the same key with a different body.
- Support optimistic concurrency on updates with `ETag` and `If-Match` where lost updates matter.

**Data formats**
- Timestamps are RFC 3339 strings in UTC. Money is integer minor units or a decimal string, always with an ISO 4217 currency code. Identifiers are strings.
- Document enums as extensible, and require clients to ignore unknown fields and values.

**Versioning and change**
- Within a version, make only additive changes: new endpoints, new optional fields, new enum values that clients were told to expect.
- Any breaking change (removing or renaming a field, changing a type or meaning, tightening validation) goes into a new version using the API's existing scheme. Announce deprecations with `Deprecation` and `Sunset` headers and in the docs.

**Security and documentation**
- Authenticate every endpoint unless it is deliberately public, and check authorisation on every resource access, not just at login, so one user cannot read another's objects by changing an id.
- Never put secrets or personal data in URLs.
- Update the API description (such as the OpenAPI document) and its examples in the same change as the code.
````

---

<a id="java-style-rules"></a>

## Java style rules

`java-style-rules` · rule · Conventions · https://hermes-ide.com/prompts/java-style-rules

Standing rules for Java an assistant writes, covering modern language features, immutability, Optional and null handling, exceptions, restrained streams, records and JUnit 5 tests.

````markdown
Follow these rules for the rest of this conversation.

Apply these rules to files matching: `**/*.java`.

When you write or change Java code in this project:

**Tooling and version**
- Use the Java version the build declares (`maven.compiler.release`, the Gradle toolchain) and only language features it supports. Do not raise the version on your own.
- Follow the project's formatter and static analysis (Spotless, google-java-format, Checkstyle, Error Prone, SpotBugs) and keep the build free of new warnings.
- Do not add a dependency for something the JDK does in a few lines; when one is needed, add it through the build file with an explicit version or the project's version catalog or BOM.

**Modern language features**
- Use records for immutable data carriers, sealed interfaces for closed hierarchies, switch expressions and pattern matching (`instanceof` patterns, record patterns where available) instead of `instanceof`-and-cast chains, and text blocks for multi-line strings.
- Use `var` only when the type is obvious from the right-hand side. Keep explicit types on fields, parameters and return types.
- Use `java.time` for all dates and times (`Instant` for timestamps, `LocalDate` for calendar dates, a `Clock` injected where code needs "now"). Never `java.util.Date` or `Calendar` in new code.
- Use `BigDecimal` for money with an explicit `RoundingMode`, and compare it with `compareTo`, not `equals`.

**Immutability**
- Make fields `final` by default and classes immutable where practical. Return `List.copyOf`, `Map.copyOf` or unmodifiable views, never internal mutable collections.
- Prefer static factory methods or builders over constructors with many parameters of the same type.

**Null handling and Optional**
- Do not return `null` for collections or arrays; return empty ones.
- Use `Optional` only as a return type for "may be absent". Never as a field, parameter or collection element, and never call `Optional.get()`; use `orElseThrow`, `orElse`, `map` or `ifPresent`.
- Validate arguments at public boundaries with `Objects.requireNonNull(value, "name")`. Follow the project's nullness annotations (for example JSpecify `@Nullable` and `@NullMarked`) if it uses them.
- Compare strings with `equals`, putting the constant or non-null side first, never with `==`.

**Exceptions**
- Throw specific exceptions with a message that includes the offending value. Use unchecked exceptions for programming errors and checked exceptions only where the caller can actually recover.
- Never swallow an exception. When wrapping, pass the cause. Do not catch `Exception` or `Throwable` except at a top-level boundary that logs and translates.
- Close resources with try-with-resources. Do not use exceptions for normal control flow.

**Streams and collections**
- Use streams for clear transformations (filter, map, collect). Use a plain loop when the stream would need nested lambdas, checked exceptions, index juggling or side effects.
- No side effects inside stream operations except in `forEach` at the end. Do not use `parallelStream()` without a measurement showing it helps.
- Implement `equals` and `hashCode` together (records do this for you), and never mutate an object while it is a key in a map or a member of a set.

**Concurrency**
- Prefer `java.util.concurrent` types and executors over raw threads, and shut executors down (try-with-resources on `ExecutorService` where the Java version allows).
- Share only immutable state between threads, or guard it with a single, documented mechanism. Use virtual threads only if the project already does. Before Java 24, a blocking call inside `synchronized` pins the carrier thread, so guard such sections with a `ReentrantLock` instead; do not pool virtual threads, and limit concurrency to scarce resources with a `Semaphore`.

**Logging**
- Use the project's logging facade (usually SLF4J) with parameterised messages: `log.info("Order {} shipped", orderId)`. Never `System.out`, string concatenation in log calls, or logging secrets and personal data.

**Tests (JUnit 5)**
- Use JUnit Jupiter: `@Test`, `@ParameterizedTest` with `@CsvSource` or `@MethodSource` for input tables, `@Nested` to group cases, and `assertThrows` for expected exceptions, checking the message or type.
- Use the project's assertion library (AssertJ or JUnit assertions) consistently. One behaviour per test, named for it.
- Mock only at system boundaries (HTTP clients, repositories, clocks), never the class under test. Inject a fixed `Clock` instead of mocking static time.
- No `Thread.sleep` to wait for asynchronous work; use the project's awaiting utility (such as Awaitility) or synchronise explicitly.
````

---

<a id="kotlin-style-rules"></a>

## Kotlin style rules

`kotlin-style-rules` · rule · Conventions · https://hermes-ide.com/prompts/kotlin-style-rules

Standing rules for Kotlin an assistant writes, covering null safety, immutability, coroutines with structured concurrency, and data and sealed classes.

````markdown
Follow these rules for the rest of this conversation.

Apply these rules to files matching: `**/*.kt`, `**/*.kts`.

When you write or change Kotlin code in this project:

**Tooling**
- Follow the Kotlin coding conventions and the project's formatter or linter (ktlint, detekt, or the IDE's settings in `.editorconfig`). Do not reformat code you are not changing.
- Use the Kotlin version, JVM target and libraries already in the build. Do not add a dependency for what the standard library does.

**Null safety**
- No not-null assertions (the !! operator) in production code. Use `?.`, `?:` with a meaningful default or an early `return` or `throw`, `requireNotNull` or `checkNotNull` with a message, or a smart cast after a check.
- Treat values from Java and platform APIs (platform types) as nullable unless their contract says otherwise, and convert them to Kotlin types at the boundary.
- Do not use `lateinit` to dodge initialisation order. Reserve it for framework-injected fields and test setup.

**Immutability and types**
- Prefer `val` over `var`, and read-only collection types (`List`, `Map`) in signatures. Return copies or read-only views, never a backing mutable collection.
- Use `data class` for values and update them with `copy`. Keep data classes free of behaviour that depends on identity.
- Model closed sets of states and results with `sealed interface` or `sealed class` and handle them with exhaustive `when` expressions, without an `else` branch, so the compiler flags new cases.
- Use `enum class` for simple fixed constants, and `@JvmInline value class` for domain identifiers and units (`UserId`, `Cents`) to avoid mixing them up.

**Errors**
- Throw exceptions for programmer errors and truly exceptional failures. For expected failures that callers must handle, return a sealed result type.
- Never swallow exceptions. In coroutines, never catch `CancellationException` without rethrowing it; avoid broad `catch (e: Exception)` around suspend calls, or rethrow cancellation explicitly. Prefer `runCatching` only where cancellation cannot occur.

**Coroutines and structured concurrency**
- Launch coroutines only in a scope with a clear owner (`viewModelScope`, `lifecycleScope`, a scope tied to a component's lifecycle, or `coroutineScope` inside a suspend function). Never use `GlobalScope`.
- Suspend functions must be main-safe: move blocking or CPU-heavy work with `withContext(Dispatchers.IO)` or `Dispatchers.Default` inside the function, not at the call site. Inject dispatchers so tests can replace them.
- Use `coroutineScope` or `supervisorScope` for parallel work with `async`, and pick deliberately: one failure cancels siblings, or not.
- Never call `runBlocking` in production code paths, especially on the main thread.
- Expose streams as `Flow`. Expose UI state as `StateFlow` built with `stateIn` and an appropriate sharing strategy, and collect it in a lifecycle-aware way.

**Functions and style**
- Use expression bodies for short functions, named arguments for booleans and same-typed parameters, and default arguments instead of overload chains.
- Use extension functions for helpers that read naturally on a type, kept close to their use. Do not add extensions on broad types (`Any`, `String`) for one call site.
- Keep visibility as narrow as possible: `private` by default, `internal` for module-wide use, `public` only for real API.
- Use scope functions (`let`, `apply`, `also`, `run`, `with`) when they make code clearer, not as a habit; never nest them.

**Tests**
- Use the project's test framework (JUnit 5, kotlin.test or Kotest) and test behaviour, one scenario per test, with descriptive names (backtick names are fine in tests).
- Test coroutines with `kotlinx-coroutines-test` (`runTest` and a test dispatcher). No `Thread.sleep` or real delays.
- Prefer fakes over mocks for your own interfaces; mock only at system boundaries.
````

---

<a id="python-style-rules"></a>

## Python style rules

`python-style-rules` · rule · Conventions · https://hermes-ide.com/prompts/python-style-rules

Standing rules for Python an assistant writes, covering type hints, pathlib, logging over print, explicit exceptions, safe subprocess calls, project layout and the project's own tooling.

````markdown
Follow these rules for the rest of this conversation.

Apply these rules to files matching: `**/*.py`.

When you write or change Python code in this project:

**Version and tooling**
- Target the Python version declared in `pyproject.toml` (`requires-python`). Do not use syntax or standard-library features newer than that.
- Use the formatter, linter and type checker the project already configures (for example ruff, black, mypy or pyright) with its settings. Do not add new tools or reformat code you did not change.
- Add or change dependencies only through the project's tool (uv, poetry, pip-tools or similar) so the lock file stays in sync. Never install packages globally.

**Types**
- Annotate every function and method signature, including return types. Use built-in generics (`list[str]`, `dict[str, int]`) and `X | None` where the target version allows.
- Avoid `Any`. Model structured data with `dataclass`, `TypedDict`, `NamedTuple` or the project's validation library instead of loose dictionaries, and use `Protocol` for duck-typed interfaces.

**Files, paths and resources**
- Use `pathlib.Path`, not string concatenation or `os.path` joins.
- Open text files with an explicit `encoding="utf-8"`, and manage files, locks and connections with `with` blocks.
- Use timezone-aware datetimes (`datetime.now(tz=UTC)`); never mix naive and aware values.

**Logging and output**
- In library and service code, log through `logger = logging.getLogger(__name__)`, never `print`. Use `print` only for a command-line program's intended output.
- Pass values as logging arguments (`logger.info("loaded %d rows", n)`) instead of formatting the string yourself, and never log secrets, tokens or personal data.

**Errors**
- Catch the narrowest exception that you can handle. Never write a bare `except:` or `except Exception: pass`.
- Re-raise with context (`raise ConfigError("missing DB_URL") from err`) and give messages that say what failed and what to do.
- Validate input at the boundaries (CLI arguments, HTTP handlers, file parsing), not deep inside the code.

**Safety**
- Call `subprocess.run` with a list of arguments and `check=True`. Never use `shell=True` with interpolated input.
- Never use `eval`, `exec` or `pickle` on untrusted data. Build SQL with parameters, never with f-strings.
- Never use mutable default arguments. Use `None` and create the value inside the function.

**Layout and style**
- Follow the existing package layout. For new projects, use a `src/` layout with `pyproject.toml` and tests under `tests/`.
- Keep `__init__.py` to imports and exports. Guard script entry points with `if __name__ == "__main__":`.
- Use f-strings for formatting. Keep comprehensions to one level of nesting; use a loop when the logic needs more.
- Write docstrings for public modules, classes and functions that say what they do and what they raise, not how.
````

---

<a id="react-component-rules"></a>

## React component rules

`react-component-rules` · rule · Conventions · https://hermes-ide.com/prompts/react-component-rules

Standing rules for React code an assistant writes, covering function components, the rules of hooks, colocated state, stable list keys, accessible markup and no effect-driven derived state.

````markdown
Follow these rules for the rest of this conversation.

Apply these rules to files matching: `**/*.tsx`, `**/*.jsx`.

When you write or change React components in this project:

**Components**
- Write function components with hooks. Do not add class components.
- Give each component one responsibility. Split it when it mixes data loading, state logic and layout, or grows hard to read in one screen.
- Never define a component inside another component's body; it remounts on every render and loses its state.
- Type props explicitly in TypeScript files. Do not spread unknown props onto DOM elements.
- Follow the project's existing patterns for styling, file naming, exports and data fetching.

**Hooks**
- Call hooks only at the top level of components and custom hooks, never inside conditions, loops or callbacks. Name custom hooks `useSomething`.
- Satisfy the exhaustive-deps lint rule by fixing the dependencies, not by disabling the rule.

**State**
- Keep state as close as possible to where it is used, and lift it only when siblings must share it.
- Store the minimum. Compute anything derivable from props or state during render, and do not copy props into state (unless the prop is only an initial value, named like `initialCount`).
- Reset a component's state by changing its `key`, not with an effect.
- Use context for values that change rarely (theme, current user, locale), not for fast-changing state.
- Never mutate state or props. Create new objects and arrays.

**Effects**
- Use `useEffect` only to synchronise with something outside React: subscriptions, timers, imperative DOM or third-party widgets.
- Never use an effect to compute derived state or to react to an event. Put event logic in the event handler.
- Clean up every subscription, listener and timer in the effect's cleanup function.
- Fetch data with the project's data layer (framework loaders or a query library). If you must fetch in an effect, cancel stale requests with an `AbortController` or an ignore flag.

**Lists**
- Give list items a stable, unique `key` from the data, such as an id. Never use `Math.random()`, and use the array index only for static lists that are never reordered, filtered or inserted into.

**Accessibility**
- Use semantic elements: `button` for actions, `a` with `href` for navigation, headings in order, lists for lists.
- Never attach `onClick` to a `div` or `span` for an action; use a `button`.
- Every form control has an associated label, every meaningful image has `alt` text (decorative images get `alt=""`), and icon-only buttons have an accessible name.
- Custom widgets must be operable by keyboard, with visible focus. Dialogs move focus in and return it when closed.
- Add ARIA attributes only when no native element provides the semantics.

**Performance and safety**
- Do not wrap everything in `useMemo`, `useCallback` or `memo`. Use them when profiling shows a cost, or when a stable reference is needed by a memoised child or an effect dependency. If the project uses the React Compiler, do not add manual memoisation at all unless the compiler skips that component.
- Never pass untrusted content to `dangerouslySetInnerHTML`. Sanitise it, or render it as text.
````

---

<a id="rust-style-rules"></a>

## Rust style rules

`rust-style-rules` · rule · Conventions · https://hermes-ide.com/prompts/rust-style-rules

Standing rules for Rust an assistant writes, covering ownership-first APIs, Result over panic, clippy-clean code, typed errors, async hygiene and minimal, justified unsafe.

````markdown
Follow these rules for the rest of this conversation.

Apply these rules to files matching: `**/*.rs`.

When you write or change Rust code in this project:

**Tooling**
- Code must pass `cargo fmt` and `cargo clippy --all-targets` with no warnings under the project's lint settings.
- Never silence a lint crate-wide. Allow a specific lint on the narrowest item, with a comment explaining why.
- Use the edition and minimum Rust version in `Cargo.toml`. Add a dependency only when it earns its place, with the fewest features needed.

**Ownership and APIs**
- Borrow in parameters when the function does not keep the value: `&str`, `&[T]`, `&Path` or `impl AsRef<Path>`. Take ownership (`String`, `Vec<T>`) when the value is stored.
- Do not add `.clone()` just to satisfy the borrow checker. Restructure the code first, and when a clone is the right answer, make it visible and cheap or explain it.
- Return owned values or iterators rather than references tied to temporary state. Use `Cow` when a value is only sometimes owned.
- Model states with enums rather than booleans or sentinel values, and wrap ids and units in newtypes.
- Implement standard traits (`From`, `TryFrom`, `Display`, `Default`, `Debug`) instead of ad hoc conversion methods, and mark results that must not be ignored with `#[must_use]`.

**Errors**
- Return `Result` for anything that can fail at runtime, and propagate with `?`.
- Do not call `unwrap()` in library or request-handling code. Use `expect("reason this cannot fail")` only for real invariants.
- Follow the project's error approach. Where there is none, use typed error enums (for example with `thiserror`) in libraries and contextual errors (for example `anyhow` with `.context(...)`) in binaries.
- Never panic across an FFI boundary or in a `Drop` implementation.

**Unsafe**
- Avoid `unsafe`. If it is necessary, keep the block as small as possible, put a `// SAFETY:` comment on it that states the invariants that make it sound, and wrap it in a safe API.
- Document every `unsafe fn` with a `# Safety` section, and test unsafe code under Miri where the project supports it.

**Concurrency and async**
- Prefer message passing or owned data over shared mutable state. When state is shared, use `Arc` with a `Mutex` or `RwLock` and keep critical sections short.
- Never hold a `std::sync::Mutex` guard across `.await`. Use the runtime's async mutex or restructure.
- Never block inside async code. Move blocking or CPU-heavy work to `spawn_blocking` or a dedicated thread.

**Style**
- Prefer iterator chains to index loops when they read clearly, and avoid collecting into a `Vec` only to iterate it again.
- Keep items private by default, and use `pub(crate)` before `pub`.
- Document public items with `///` comments, with an example for non-trivial APIs.
- Put unit tests in a `#[cfg(test)] mod tests` beside the code, and integration tests in `tests/`.
````

---

<a id="sql-style-rules"></a>

## SQL style rules

`sql-style-rules` · rule · Conventions · https://hermes-ide.com/prompts/sql-style-rules

Standing rules for SQL an assistant writes, covering formatting, naming, explicit column lists, parameterised queries, NULL handling, data types and safe migrations.

````markdown
Follow these rules for the rest of this conversation.

Apply these rules to files matching: `**/*.sql`, `**/migrations/**`, `**/migrate/**`.

When you write or change SQL in this project:

**Dialect and formatting**
- Write for the project's database engine and version. Do not use features it lacks, and flag engine-specific syntax when portability matters.
- Match the existing formatting. Where there is none: uppercase keywords, one major clause per line (`SELECT`, `FROM`, `JOIN`, `WHERE`, `GROUP BY`, `ORDER BY`), one column per line in long lists, and consistent indentation.
- Prefer common table expressions to deeply nested subqueries, with names that say what each step contains.
- Comment the reason for non-obvious logic, not what the SQL does.

**Naming**
- Use `snake_case` with no quoted identifiers, reserved words or unexplained abbreviations. Follow the existing singular or plural convention for table names.
- Name foreign keys `<referenced_table>_id`, booleans `is_` or `has_`, timestamps `_at` and dates `_on` or `_date`.
- Name constraints and indexes explicitly (`orders_customer_id_fkey`, `orders_created_at_idx`) so migrations can refer to them.

**Queries**
- List columns explicitly in `SELECT` and `INSERT`. Use `SELECT *` only in ad hoc exploration, never in application code, views or models.
- Use explicit `JOIN ... ON`, never comma joins, and qualify every column with a table alias when more than one table is involved.
- Add `ORDER BY` whenever the order matters, and always with `LIMIT` or `OFFSET`. Make the ordering deterministic with a unique tie-breaker.
- Check for fan-out before aggregating over joins, and aggregate before joining when that avoids it.

**Parameters and safety**
- Pass values as bound parameters, always. Never build SQL by concatenating or interpolating user input.
- When an identifier such as a sort column must be dynamic, choose it from an allowlist in code.
- Grant application roles only the privileges they need.

**NULLs and types**
- Compare with `IS NULL` or `IS DISTINCT FROM`, never `= NULL`. Prefer `NOT EXISTS` to `NOT IN` when the subquery can return NULL.
- Store money as `NUMERIC`/`DECIMAL` or integer minor units, never floating point. Store timestamps with time zone, in UTC.
- Enforce integrity in the schema with `NOT NULL`, `CHECK`, `UNIQUE` and foreign keys, not only in application code.

**Migrations**
- One logical change per migration. Never edit a migration that has already run anywhere shared; write a new one.
- Separate schema changes from data backfills. Run backfills in batches with short transactions.
- On large or busy tables, use lock-safe forms: build indexes concurrently or online, add constraints without validation and validate them separately, add columns as nullable first, and set a lock timeout.
- Make destructive changes (drop, rename, type narrowing) only after a release in which no deployed code uses the old shape, and give every migration a tested rollback or an explicit note that it cannot be reversed.
````

---

<a id="swift-style-rules"></a>

## Swift style rules

`swift-style-rules` · rule · Conventions · https://hermes-ide.com/prompts/swift-style-rules

Standing rules for Swift an assistant writes, covering value types, optionals without force unwraps, structured concurrency, access control and API Design Guidelines naming.

````markdown
Follow these rules for the rest of this conversation.

Apply these rules to files matching: `**/*.swift`.

When you write or change Swift code in this project:

**Tooling and versions**
- Use the Swift language version and concurrency checking level the project already sets (in `Package.swift` or the Xcode build settings). Do not raise or lower them as a side effect.
- Follow the project's formatter and linter (swift-format or SwiftLint) if configured. Do not reformat code you are not changing.

**Types and values**
- Prefer `struct` and `enum` for models and values. Use a `class` only for identity, shared mutable state or framework requirements, and mark it `final` unless it is designed for subclassing.
- Prefer `let` over `var`. Keep mutation local and explicit with `mutating` methods.
- Model closed sets of states with enums with associated values instead of several optionals or boolean flags.
- Use `Codable` with explicit `CodingKeys` when the wire format differs from Swift naming. Decode dates and numbers with explicit strategies.

**Optionals and errors**
- No force unwraps (postfix !), try! or forced casts (as!) in production code. Use `guard let`, `if let`, `??` with a meaningful default, or throw. The only exceptions are values that are guaranteed by construction (such as a URL literal), and they get a comment saying why.
- Use `guard` for early exit and keep the happy path unindented.
- Throw errors for recoverable failures with an error type that callers can match on. Do not return `nil` to signal an error the caller needs to understand.
- Use `precondition` or `fatalError` only for programmer errors, never for bad input or network failures.

**Concurrency**
- Use `async`/`await` and structured concurrency (`async let`, task groups) for new asynchronous code. Wrap callback-based APIs with checked continuations rather than mixing styles.
- Annotate UI-facing types and functions with `@MainActor`. Protect shared mutable state with an actor rather than locks or dispatch queues in new code.
- Types crossing concurrency domains must be `Sendable`. Do not silence warnings with `@unchecked Sendable` or `nonisolated(unsafe)` unless you document the synchronisation that makes it safe.
- Do not create unstructured `Task { }` without an owner. Store and cancel long-lived tasks, and check `Task.isCancelled` or call `try Task.checkCancellation()` in long loops.
- In escaping closures that capture `self` in classes, use `[weak self]` when the closure can outlive the object.

**Access control**
- Default to `private`, then `fileprivate`, then `internal`. Make something `public` or `open` only when it is part of a module's intended API.
- Keep properties `private(set)` when callers need to read but not write.

**Naming (Swift API Design Guidelines)**
- Aim for clarity at the point of use: `remove(at: index)`, `users.filter(isActive)`, not abbreviations.
- Types and protocols in UpperCamelCase, everything else in lowerCamelCase. Booleans read as assertions (`isEmpty`, `hasAccess`).
- Methods with side effects read as verbs (`sort()`), and non-mutating counterparts use the "ed" or "ing" form (`sorted()`).
- Document public API with `///` comments that describe what it does, its parameters, what it throws and its complexity if not obvious.

**SwiftUI (when used)**
- Mark view-owned state `@State private`. Pass bindings down only when the child must write.
- Keep views small and free of business logic. Put logic in an observable model (`@Observable` on the deployment targets that support it, otherwise `ObservableObject`) that can be tested without the view.
- Do not start work in a view's `init`; use `.task` so it is tied to the view's lifetime and cancelled automatically.

**Tests**
- Use the test framework the project already uses (Swift Testing or XCTest). Write tests for behaviour, one scenario each, with clear names.
- Test async code with `async` tests, not sleeps or expectations with long timeouts.
- Inject dependencies (network, clock, storage) through protocols or closures so tests do not hit real services.
````

---

<a id="typescript-strict-rules"></a>

## TypeScript strict rules

`typescript-strict-rules` · rule · Conventions · https://hermes-ide.com/prompts/typescript-strict-rules

Keeps TypeScript code fully type-safe under strict mode, with no any, no unchecked casts, validated external data and exhaustive unions. Use in any TypeScript project.

````markdown
Follow these rules for the rest of this conversation.

Apply these rules to files matching: `**/*.ts`, `**/*.tsx`, `**/*.mts`, `**/*.cts`.

When you write or change TypeScript:

- Do not loosen the compiler settings. Never turn off `strict`, `noUncheckedIndexedAccess`, `exactOptionalPropertyTypes` or other checks in `tsconfig.json` to make an error go away; fix the code.
- Do not use `any`. Use `unknown` for values of unknown shape and narrow them with type guards, `typeof`, `instanceof` or `in` checks. If a third-party type forces `any`, contain it in one small, typed wrapper.
- Do not silence errors with `@ts-ignore` or `@ts-nocheck`. If an error cannot be fixed, use `@ts-expect-error` with a comment explaining why, so it fails when the cause goes away.
- Avoid type assertions (`as Foo`) and non-null assertions (a postfix exclamation mark, as in `user!.name`). Prefer narrowing. Allow an assertion only where you can state the invariant that makes it safe, and write that invariant in a comment next to it. Never write `as unknown as Foo` to force a type.
- Validate data that crosses a trust boundary before you type it: HTTP bodies, query strings, environment variables, files, `JSON.parse` results and third-party API responses. Use the schema library the project already uses, and derive the type from the schema instead of writing both by hand.
- Model states that cannot coexist as discriminated unions rather than objects with many optional fields. Handle every member in a `switch`, and add a default branch that assigns the value to `never` so a new member becomes a compile error.
- Use `satisfies` to check that a value matches a type without widening it, and `as const` for fixed lookup tables.
- Mark data that should not change as `readonly` (`readonly T[]`, `Readonly<T>`), especially function parameters.
- Give exported functions explicit parameter and return types. Let inference handle local variables.
- Use `import type` and `export type` for type-only imports and exports.
- Prefer union types of string literals or `as const` objects over `enum` and `namespace`, unless the project already uses them, because they are not erasable syntax and break type stripping in runtimes that run TypeScript directly.
- In `catch` blocks, treat the error as `unknown` and narrow it before reading properties.
- Never leave a promise floating. `await` it, return it, or explicitly mark it as intentionally ignored with `void` and a comment.
- Index access may return `undefined`. Handle that case instead of asserting it away.
- Before you say the work is done, run the project's type check (for example `tsc --noEmit` or the repo's `typecheck` script) and report the result.
````
