diff --git a/.pre-commit-config.yaml b/.pre-commit-config.yaml
index d84a1c6bf6..3b17534533 100644
--- a/.pre-commit-config.yaml
+++ b/.pre-commit-config.yaml
@@ -5,6 +5,7 @@ exclude: |
.github/workflows/release.yml|
crates/ty_vendored/vendor/.*|
crates/ty_project/resources/.*|
+ crates/ty/docs/rules.md|
crates/ruff_benchmark/resources/.*|
crates/ruff_linter/resources/.*|
crates/ruff_linter/src/rules/.*/snapshots/.*|
diff --git a/Cargo.lock b/Cargo.lock
index 45855fee99..d325171eec 100644
--- a/Cargo.lock
+++ b/Cargo.lock
@@ -2726,6 +2726,7 @@ dependencies = [
"tracing-indicatif",
"tracing-subscriber",
"ty_project",
+ "url",
]
[[package]]
diff --git a/crates/ruff_dev/Cargo.toml b/crates/ruff_dev/Cargo.toml
index c007005860..e6194130f4 100644
--- a/crates/ruff_dev/Cargo.toml
+++ b/crates/ruff_dev/Cargo.toml
@@ -44,6 +44,7 @@ toml = { workspace = true, features = ["parse"] }
tracing = { workspace = true }
tracing-indicatif = { workspace = true }
tracing-subscriber = { workspace = true, features = ["env-filter"] }
+url = { workspace = true }
[dev-dependencies]
indoc = { workspace = true }
diff --git a/crates/ruff_dev/src/generate_all.rs b/crates/ruff_dev/src/generate_all.rs
index d4fd30a869..9a2963bb60 100644
--- a/crates/ruff_dev/src/generate_all.rs
+++ b/crates/ruff_dev/src/generate_all.rs
@@ -2,7 +2,9 @@
use anyhow::Result;
-use crate::{generate_cli_help, generate_docs, generate_json_schema, generate_ty_schema};
+use crate::{
+ generate_cli_help, generate_docs, generate_json_schema, generate_ty_rules, generate_ty_schema,
+};
pub(crate) const REGENERATE_ALL_COMMAND: &str = "cargo dev generate-all";
@@ -38,5 +40,6 @@ pub(crate) fn main(args: &Args) -> Result<()> {
generate_docs::main(&generate_docs::Args {
dry_run: args.mode.is_dry_run(),
})?;
+ generate_ty_rules::main(&generate_ty_rules::Args { mode: args.mode })?;
Ok(())
}
diff --git a/crates/ruff_dev/src/generate_ty_rules.rs b/crates/ruff_dev/src/generate_ty_rules.rs
new file mode 100644
index 0000000000..6586afc738
--- /dev/null
+++ b/crates/ruff_dev/src/generate_ty_rules.rs
@@ -0,0 +1,144 @@
+//! Generates the rules table for ty
+#![allow(clippy::print_stdout, clippy::print_stderr)]
+
+use std::borrow::Cow;
+use std::fmt::Write as _;
+use std::fs;
+use std::path::PathBuf;
+
+use anyhow::{bail, Result};
+use itertools::Itertools as _;
+use pretty_assertions::StrComparison;
+
+use crate::generate_all::{Mode, REGENERATE_ALL_COMMAND};
+use crate::ROOT_DIR;
+
+#[derive(clap::Args)]
+pub(crate) struct Args {
+ /// Write the generated table to stdout (rather than to `ty.schema.json`).
+ #[arg(long, default_value_t, value_enum)]
+ pub(crate) mode: Mode,
+}
+
+pub(crate) fn main(args: &Args) -> Result<()> {
+ let markdown = generate_markdown();
+ let filename = "crates/ty/docs/rules.md";
+ let schema_path = PathBuf::from(ROOT_DIR).join(filename);
+
+ match args.mode {
+ Mode::DryRun => {
+ println!("{markdown}");
+ }
+ Mode::Check => {
+ let current = fs::read_to_string(schema_path)?;
+ if current == markdown {
+ println!("Up-to-date: {filename}");
+ } else {
+ let comparison = StrComparison::new(¤t, &markdown);
+ bail!("{filename} changed, please run `{REGENERATE_ALL_COMMAND}`:\n{comparison}");
+ }
+ }
+ Mode::Write => {
+ let current = fs::read_to_string(&schema_path)?;
+ if current == markdown {
+ println!("Up-to-date: {filename}");
+ } else {
+ println!("Updating: {filename}");
+ fs::write(schema_path, markdown.as_bytes())?;
+ }
+ }
+ }
+
+ Ok(())
+}
+
+fn generate_markdown() -> String {
+ let registry = &*ty_project::DEFAULT_LINT_REGISTRY;
+
+ let mut output = String::new();
+
+ let _ = writeln!(&mut output, "# Rules\n");
+
+ let mut lints: Vec<_> = registry.lints().iter().collect();
+ lints.sort_by(|a, b| {
+ a.default_level()
+ .cmp(&b.default_level())
+ .reverse()
+ .then_with(|| a.name().cmp(&b.name()))
+ });
+
+ for lint in lints {
+ let _ = writeln!(&mut output, "## `{rule_name}`\n", rule_name = lint.name());
+
+ // Increase the header-level by one
+ let documentation = lint
+ .documentation_lines()
+ .map(|line| {
+ if line.starts_with('#') {
+ Cow::Owned(format!("#{line}"))
+ } else {
+ Cow::Borrowed(line)
+ }
+ })
+ .join("\n");
+
+ let _ = writeln!(
+ &mut output,
+ r#"**Default level**: {level}
+
+
+{summary}
+
+{documentation}
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20{encoded_name})
+* [View source](https://github.com/astral-sh/ruff/blob/main/{file}#L{line})
+
+"#,
+ level = lint.default_level(),
+ // GitHub doesn't support markdown in `summary` headers
+ summary = replace_inline_code(lint.summary()),
+ encoded_name = url::form_urlencoded::byte_serialize(lint.name().as_str().as_bytes())
+ .collect::(),
+ file = url::form_urlencoded::byte_serialize(lint.file().replace('\\', "/").as_bytes())
+ .collect::(),
+ line = lint.line(),
+ );
+ }
+
+ output
+}
+
+/// Replaces inline code blocks (`code`) with `code`
+fn replace_inline_code(input: &str) -> String {
+ let mut output = String::new();
+ let mut parts = input.split('`');
+
+ while let Some(before) = parts.next() {
+ if let Some(between) = parts.next() {
+ output.push_str(before);
+ output.push_str("");
+ output.push_str(between);
+ output.push_str("");
+ } else {
+ output.push_str(before);
+ }
+ }
+
+ output
+}
+
+#[cfg(test)]
+mod tests {
+ use anyhow::Result;
+
+ use crate::generate_all::Mode;
+
+ use super::{main, Args};
+
+ #[test]
+ fn ty_rules_up_to_date() -> Result<()> {
+ main(&Args { mode: Mode::Check })
+ }
+}
diff --git a/crates/ruff_dev/src/main.rs b/crates/ruff_dev/src/main.rs
index f562d1d0ea..cfbbd039fe 100644
--- a/crates/ruff_dev/src/main.rs
+++ b/crates/ruff_dev/src/main.rs
@@ -15,6 +15,7 @@ mod generate_docs;
mod generate_json_schema;
mod generate_options;
mod generate_rules_table;
+mod generate_ty_rules;
mod generate_ty_schema;
mod print_ast;
mod print_cst;
@@ -44,6 +45,7 @@ enum Command {
GenerateTySchema(generate_ty_schema::Args),
/// Generate a Markdown-compatible table of supported lint rules.
GenerateRulesTable,
+ GenerateTyRules(generate_ty_rules::Args),
/// Generate a Markdown-compatible listing of configuration options.
GenerateOptions,
/// Generate CLI help.
@@ -88,6 +90,7 @@ fn main() -> Result {
Command::GenerateJSONSchema(args) => generate_json_schema::main(&args)?,
Command::GenerateTySchema(args) => generate_ty_schema::main(&args)?,
Command::GenerateRulesTable => println!("{}", generate_rules_table::generate()),
+ Command::GenerateTyRules(args) => generate_ty_rules::main(&args)?,
Command::GenerateOptions => println!("{}", generate_options::generate()),
Command::GenerateCliHelp(args) => generate_cli_help::main(&args)?,
Command::GenerateDocs(args) => generate_docs::main(&args)?,
diff --git a/crates/ty/docs/rules.md b/crates/ty/docs/rules.md
new file mode 100644
index 0000000000..7dba79499c
--- /dev/null
+++ b/crates/ty/docs/rules.md
@@ -0,0 +1,1554 @@
+# Rules
+
+## `byte-string-type-annotation`
+
+**Default level**: error
+
+
+detects byte strings in type annotation positions
+
+### What it does
+Checks for byte-strings in type annotation positions.
+
+### Why is this bad?
+Static analysis tools like ty can't analyse type annotations that use byte-string notation.
+
+### Examples
+```python
+def test(): -> b"int":
+ ...
+```
+
+Use instead:
+```python
+def test(): -> "int":
+ ...
+```
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20byte-string-type-annotation)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fstring_annotation.rs#L36)
+
+
+## `call-non-callable`
+
+**Default level**: error
+
+
+detects calls to non-callable objects
+
+### What it does
+Checks for calls to non-callable objects.
+
+### Why is this bad?
+Calling a non-callable object will raise a `TypeError` at runtime.
+
+### Examples
+```python
+4() # TypeError: 'int' object is not callable
+```
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20call-non-callable)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fdiagnostic.rs#L84)
+
+
+## `conflicting-argument-forms`
+
+**Default level**: error
+
+
+detects when an argument is used as both a value and a type form in a call
+
+### What it does
+Checks whether an argument is used as both a value and a type form in a call
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20conflicting-argument-forms)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fdiagnostic.rs#L115)
+
+
+## `conflicting-declarations`
+
+**Default level**: error
+
+
+detects conflicting declarations
+
+### What it does
+Checks whether a variable has been declared as two conflicting types.
+
+### Why is this bad
+A variable with two conflicting declarations likely indicates a mistake.
+Moreover, it could lead to incorrect or ill-defined type inference for
+other code that relies on these variables.
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20conflicting-declarations)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fdiagnostic.rs#L125)
+
+
+## `conflicting-metaclass`
+
+**Default level**: error
+
+
+detects conflicting metaclasses
+
+TODO #14889
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20conflicting-metaclass)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fdiagnostic.rs#L140)
+
+
+## `cyclic-class-definition`
+
+**Default level**: error
+
+
+detects cyclic class definitions
+
+### What it does
+Checks for class definitions with a cyclic inheritance chain.
+
+### Why is it bad?
+TODO #14889
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20cyclic-class-definition)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fdiagnostic.rs#L149)
+
+
+## `division-by-zero`
+
+**Default level**: error
+
+
+detects division by zero
+
+### What it does
+It detects division by zero.
+
+### Why is this bad?
+Dividing by zero raises a `ZeroDivisionError` at runtime.
+
+### Examples
+```python
+5 / 0
+```
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20division-by-zero)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fdiagnostic.rs#L162)
+
+
+## `duplicate-base`
+
+**Default level**: error
+
+
+detects class definitions with duplicate bases
+
+### What it does
+Checks for class definitions with duplicate bases.
+
+### Why is this bad?
+Class definitions with duplicate bases raise a `TypeError` at runtime.
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20duplicate-base)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fdiagnostic.rs#L180)
+
+
+## `escape-character-in-forward-annotation`
+
+**Default level**: error
+
+
+detects forward type annotations with escape characters
+
+TODO #14889
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20escape-character-in-forward-annotation)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fstring_annotation.rs#L120)
+
+
+## `fstring-type-annotation`
+
+**Default level**: error
+
+
+detects F-strings in type annotation positions
+
+### What it does
+Checks for f-strings in type annotation positions.
+
+### Why is this bad?
+Static analysis tools like ty can't analyse type annotations that use f-string notation.
+
+### Examples
+```python
+def test(): -> f"int":
+ ...
+```
+
+Use instead:
+```python
+def test(): -> "int":
+ ...
+```
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20fstring-type-annotation)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fstring_annotation.rs#L11)
+
+
+## `implicit-concatenated-string-type-annotation`
+
+**Default level**: error
+
+
+detects implicit concatenated strings in type annotations
+
+### What it does
+Checks for implicit concatenated strings in type annotation positions.
+
+### Why is this bad?
+Static analysis tools like ty can't analyse type annotations that use implicit concatenated strings.
+
+### Examples
+```python
+def test(): -> "Literal[" "5" "]":
+ ...
+```
+
+Use instead:
+```python
+def test(): -> "Literal[5]":
+ ...
+```
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20implicit-concatenated-string-type-annotation)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fstring_annotation.rs#L86)
+
+
+## `incompatible-slots`
+
+**Default level**: error
+
+
+detects class definitions whose MRO has conflicting __slots__
+
+### What it does
+Checks for classes whose bases define incompatible `__slots__`.
+
+### Why is this bad?
+Inheriting from bases with incompatible `__slots__`s
+will lead to a `TypeError` at runtime.
+
+Classes with no or empty `__slots__` are always compatible:
+
+```python
+class A: ...
+class B:
+ __slots__ = ()
+class C:
+ __slots__ = ("a", "b")
+
+## fine
+class D(A, B, C): ...
+```
+
+Multiple inheritance from more than one different class
+defining non-empty `__slots__` is not allowed:
+
+```python
+class A:
+ __slots__ = ("a", "b")
+
+class B:
+ __slots__ = ("a", "b") # Even if the values are the same
+
+## TypeError: multiple bases have instance lay-out conflict
+class C(A, B): ...
+```
+
+### Known problems
+Dynamic (not tuple or string literal) `__slots__` are not checked.
+Additionally, classes inheriting from built-in classes with implicit layouts
+like `str` or `int` are also not checked.
+
+```pycon
+>>> hasattr(int, "__slots__")
+False
+>>> hasattr(str, "__slots__")
+False
+>>> class A(int, str): ...
+Traceback (most recent call last):
+ File "", line 1, in
+ class A(int, str): ...
+TypeError: multiple bases have instance lay-out conflict
+```
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20incompatible-slots)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fdiagnostic.rs#L193)
+
+
+## `inconsistent-mro`
+
+**Default level**: error
+
+
+detects class definitions with an inconsistent MRO
+
+### What it does
+Checks for classes with an inconsistent method resolution order (MRO).
+
+### Why is this bad?
+Classes with an inconsistent MRO will raise a `TypeError` at runtime.
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20inconsistent-mro)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fdiagnostic.rs#L279)
+
+
+## `index-out-of-bounds`
+
+**Default level**: error
+
+
+detects index out of bounds errors
+
+### What it does
+Checks for attempts to use an out of bounds index to get an item from
+a container.
+
+### Why is this bad?
+Using an out of bounds index will raise an `IndexError` at runtime.
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20index-out-of-bounds)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fdiagnostic.rs#L292)
+
+
+## `invalid-argument-type`
+
+**Default level**: error
+
+
+detects call arguments whose type is not assignable to the corresponding typed parameter
+
+### What it does
+Detects call arguments whose type is not assignable to the corresponding typed parameter.
+
+### Why is this bad?
+Passing an argument of a type the function (or callable object) does not accept violates
+the expectations of the function author and may cause unexpected runtime errors within the
+body of the function.
+
+### Examples
+```python
+def func(x: int): ...
+func("foo") # error: [invalid-argument-type]
+```
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20invalid-argument-type)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fdiagnostic.rs#L306)
+
+
+## `invalid-assignment`
+
+**Default level**: error
+
+
+detects invalid assignments
+
+TODO #14889
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20invalid-assignment)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fdiagnostic.rs#L346)
+
+
+## `invalid-attribute-access`
+
+**Default level**: error
+
+
+Invalid attribute access
+
+### What it does
+Makes sure that instance attribute accesses are valid.
+
+### Examples
+```python
+class C:
+ var: ClassVar[int] = 1
+
+C.var = 3 # okay
+C().var = 3 # error: Cannot assign to class variable
+```
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20invalid-attribute-access)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fdiagnostic.rs#L1099)
+
+
+## `invalid-base`
+
+**Default level**: error
+
+
+detects class definitions with an invalid base
+
+TODO #14889
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20invalid-base)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fdiagnostic.rs#L355)
+
+
+## `invalid-context-manager`
+
+**Default level**: error
+
+
+detects expressions used in with statements that don't implement the context manager protocol
+
+TODO #14889
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20invalid-context-manager)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fdiagnostic.rs#L364)
+
+
+## `invalid-declaration`
+
+**Default level**: error
+
+
+detects invalid declarations
+
+TODO #14889
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20invalid-declaration)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fdiagnostic.rs#L373)
+
+
+## `invalid-exception-caught`
+
+**Default level**: error
+
+
+detects exception handlers that catch classes that do not inherit from BaseException
+
+### What it does
+Checks for exception handlers that catch non-exception classes.
+
+### Why is this bad?
+Catching classes that do not inherit from `BaseException` will raise a TypeError at runtime.
+
+### Example
+```python
+try:
+ 1 / 0
+except 1:
+ ...
+```
+
+Use instead:
+```python
+try:
+ 1 / 0
+except ZeroDivisionError:
+ ...
+```
+
+### References
+- [Python documentation: except clause](https://docs.python.org/3/reference/compound_stmts.html#except-clause)
+- [Python documentation: Built-in Exceptions](https://docs.python.org/3/library/exceptions.html#built-in-exceptions)
+
+### Ruff rule
+ This rule corresponds to Ruff's [`except-with-non-exception-classes` (`B030`)](https://docs.astral.sh/ruff/rules/except-with-non-exception-classes)
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20invalid-exception-caught)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fdiagnostic.rs#L382)
+
+
+## `invalid-generic-class`
+
+**Default level**: error
+
+
+detects invalid generic classes
+
+### What it does
+Checks for the creation of invalid generic classes
+
+### Why is this bad?
+There are several requirements that you must follow when defining a generic class.
+
+### Examples
+```python
+from typing import Generic, TypeVar
+
+T = TypeVar("T") # okay
+
+## error: class uses both PEP-695 syntax and legacy syntax
+class C[U](Generic[T]): ...
+```
+
+### References
+- [Typing spec: Generics](https://typing.python.org/en/latest/spec/generics.html#introduction)
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20invalid-generic-class)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fdiagnostic.rs#L418)
+
+
+## `invalid-legacy-type-variable`
+
+**Default level**: error
+
+
+detects invalid legacy type variables
+
+### What it does
+Checks for the creation of invalid legacy `TypeVar`s
+
+### Why is this bad?
+There are several requirements that you must follow when creating a legacy `TypeVar`.
+
+### Examples
+```python
+from typing import TypeVar
+
+T = TypeVar("T") # okay
+Q = TypeVar("S") # error: TypeVar name must match the variable it's assigned to
+T = TypeVar("T") # error: TypeVars should not be redefined
+
+## error: TypeVar must be immediately assigned to a variable
+def f(t: TypeVar("U")): ...
+```
+
+### References
+- [Typing spec: Generics](https://typing.python.org/en/latest/spec/generics.html#introduction)
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20invalid-legacy-type-variable)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fdiagnostic.rs#L444)
+
+
+## `invalid-metaclass`
+
+**Default level**: error
+
+
+detects invalid metaclass= arguments
+
+### What it does
+Checks for arguments to `metaclass=` that are invalid.
+
+### Why is this bad?
+Python allows arbitrary expressions to be used as the argument to `metaclass=`.
+These expressions, however, need to be callable and accept the same arguments
+as `type.__new__`.
+
+### Example
+
+```python
+def f(): ...
+
+## TypeError: f() takes 0 positional arguments but 3 were given
+class B(metaclass=f): ...
+```
+
+### References
+- [Python documentation: Metaclasses](https://docs.python.org/3/reference/datamodel.html#metaclasses)
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20invalid-metaclass)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fdiagnostic.rs#L472)
+
+
+## `invalid-overload`
+
+**Default level**: error
+
+
+detects invalid @overload usages
+
+### What it does
+Checks for various invalid `@overload` usages.
+
+### Why is this bad?
+The `@overload` decorator is used to define functions and methods that accepts different
+combinations of arguments and return different types based on the arguments passed. This is
+mainly beneficial for type checkers. But, if the `@overload` usage is invalid, the type
+checker may not be able to provide correct type information.
+
+### Example
+
+Defining only one overload:
+
+```py
+from typing import overload
+
+@overload
+def foo(x: int) -> int: ...
+def foo(x: int | None) -> int | None:
+ return x
+```
+
+Or, not providing an implementation for the overloaded definition:
+
+```py
+from typing import overload
+
+@overload
+def foo() -> None: ...
+@overload
+def foo(x: int) -> int: ...
+```
+
+### References
+- [Python documentation: `@overload`](https://docs.python.org/3/library/typing.html#typing.overload)
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20invalid-overload)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fdiagnostic.rs#L499)
+
+
+## `invalid-parameter-default`
+
+**Default level**: error
+
+
+detects default values that can't be assigned to the parameter's annotated type
+
+### What it does
+Checks for default values that can't be assigned to the parameter's annotated type.
+
+### Why is this bad?
+TODO #14889
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20invalid-parameter-default)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fdiagnostic.rs#L542)
+
+
+## `invalid-protocol`
+
+**Default level**: error
+
+
+detects invalid protocol class definitions
+
+### What it does
+Checks for invalidly defined protocol classes.
+
+### Why is this bad?
+An invalidly defined protocol class may lead to the type checker inferring
+unexpected things. It may also lead to `TypeError`s at runtime.
+
+### Examples
+A `Protocol` class cannot inherit from a non-`Protocol` class;
+this raises a `TypeError` at runtime:
+
+```pycon
+>>> from typing import Protocol
+>>> class Foo(int, Protocol): ...
+...
+Traceback (most recent call last):
+ File "", line 1, in
+ class Foo(int, Protocol): ...
+TypeError: Protocols can only inherit from other protocols, got
+```
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20invalid-protocol)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fdiagnostic.rs#L251)
+
+
+## `invalid-raise`
+
+**Default level**: error
+
+
+detects raise statements that raise invalid exceptions or use invalid causes
+
+Checks for `raise` statements that raise non-exceptions or use invalid
+causes for their raised exceptions.
+
+### Why is this bad?
+Only subclasses or instances of `BaseException` can be raised.
+For an exception's cause, the same rules apply, except that `None` is also
+permitted. Violating these rules results in a `TypeError` at runtime.
+
+### Examples
+```python
+def f():
+ try:
+ something()
+ except NameError:
+ raise "oops!" from f
+
+def g():
+ raise NotImplemented from 42
+```
+
+Use instead:
+```python
+def f():
+ try:
+ something()
+ except NameError as e:
+ raise RuntimeError("oops!") from e
+
+def g():
+ raise NotImplementedError from None
+```
+
+### References
+- [Python documentation: The `raise` statement](https://docs.python.org/3/reference/simple_stmts.html#raise)
+- [Python documentation: Built-in Exceptions](https://docs.python.org/3/library/exceptions.html#built-in-exceptions)
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20invalid-raise)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fdiagnostic.rs#L555)
+
+
+## `invalid-return-type`
+
+**Default level**: error
+
+
+detects returned values that can't be assigned to the function's annotated return type
+
+### What it does
+Detects returned values that can't be assigned to the function's annotated return type.
+
+### Why is this bad?
+Returning an object of a type incompatible with the annotated return type may cause confusion to the user calling the function.
+
+### Examples
+```python
+def func() -> int:
+ return "a" # error: [invalid-return-type]
+```
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20invalid-return-type)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fdiagnostic.rs#L327)
+
+
+## `invalid-super-argument`
+
+**Default level**: error
+
+
+detects invalid arguments for super()
+
+### What it does
+Detects `super()` calls where:
+- the first argument is not a valid class literal, or
+- the second argument is not an instance or subclass of the first argument.
+
+### Why is this bad?
+`super(type, obj)` expects:
+- the first argument to be a class,
+- and the second argument to satisfy one of the following:
+ - `isinstance(obj, type)` is `True`
+ - `issubclass(obj, type)` is `True`
+
+Violating this relationship will raise a `TypeError` at runtime.
+
+### Examples
+```python
+class A:
+ ...
+class B(A):
+ ...
+
+super(A, B()) # it's okay! `A` satisfies `isinstance(B(), A)`
+
+super(A(), B()) # error: `A()` is not a class
+
+super(B, A()) # error: `A()` does not satisfy `isinstance(A(), B)`
+super(B, A) # error: `A` does not satisfy `issubclass(A, B)`
+```
+
+### References
+- [Python documentation: super()](https://docs.python.org/3/library/functions.html#super)
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20invalid-super-argument)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fdiagnostic.rs#L598)
+
+
+## `invalid-syntax-in-forward-annotation`
+
+**Default level**: error
+
+
+detects invalid syntax in forward annotations
+
+TODO #14889
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20invalid-syntax-in-forward-annotation)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fstring_annotation.rs#L111)
+
+
+## `invalid-type-checking-constant`
+
+**Default level**: error
+
+
+detects invalid TYPE_CHECKING constant assignments
+
+### What it does
+Checks for a value other than `False` assigned to the `TYPE_CHECKING` variable, or an
+annotation not assignable from `bool`.
+
+### Why is this bad?
+The name `TYPE_CHECKING` is reserved for a flag that can be used to provide conditional
+code seen only by the type checker, and not at runtime. Normally this flag is imported from
+`typing` or `typing_extensions`, but it can also be defined locally. If defined locally, it
+must be assigned the value `False` at runtime; the type checker will consider its value to
+be `True`. If annotated, it must be annotated as a type that can accept `bool` values.
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20invalid-type-checking-constant)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fdiagnostic.rs#L637)
+
+
+## `invalid-type-form`
+
+**Default level**: error
+
+
+detects invalid type forms
+
+### What it does
+Checks for invalid type expressions.
+
+### Why is this bad?
+TODO #14889
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20invalid-type-form)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fdiagnostic.rs#L655)
+
+
+## `invalid-type-variable-constraints`
+
+**Default level**: error
+
+
+detects invalid type variable constraints
+
+TODO #14889
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20invalid-type-variable-constraints)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fdiagnostic.rs#L668)
+
+
+## `missing-argument`
+
+**Default level**: error
+
+
+detects missing required arguments in a call
+
+### What it does
+Checks for missing required arguments in a call.
+
+### Why is this bad?
+Failing to provide a required argument will raise a `TypeError` at runtime.
+
+### Examples
+```python
+def func(x: int): ...
+func() # TypeError: func() missing 1 required positional argument: 'x'
+```
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20missing-argument)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fdiagnostic.rs#L677)
+
+
+## `no-matching-overload`
+
+**Default level**: error
+
+
+detects calls that do not match any overload
+
+### What it does
+Checks for calls to an overloaded function that do not match any of the overloads.
+
+### Why is this bad?
+Failing to provide the correct arguments to one of the overloads will raise a `TypeError`
+at runtime.
+
+### Examples
+```python
+@overload
+def func(x: int): ...
+@overload
+def func(x: bool): ...
+func("string") # error: [no-matching-overload]
+```
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20no-matching-overload)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fdiagnostic.rs#L696)
+
+
+## `non-subscriptable`
+
+**Default level**: error
+
+
+detects subscripting objects that do not support subscripting
+
+### What it does
+Checks for subscripting objects that do not support subscripting.
+
+### Why is this bad?
+Subscripting an object that does not support it will raise a `TypeError` at runtime.
+
+### Examples
+```python
+4[1] # TypeError: 'int' object is not subscriptable
+```
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20non-subscriptable)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fdiagnostic.rs#L719)
+
+
+## `not-iterable`
+
+**Default level**: error
+
+
+detects iteration over an object that is not iterable
+
+### What it does
+Checks for objects that are not iterable but are used in a context that requires them to be.
+
+### Why is this bad?
+Iterating over an object that is not iterable will raise a `TypeError` at runtime.
+
+### Examples
+
+```python
+for i in 34: # TypeError: 'int' object is not iterable
+ pass
+```
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20not-iterable)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fdiagnostic.rs#L737)
+
+
+## `parameter-already-assigned`
+
+**Default level**: error
+
+
+detects multiple arguments for the same parameter
+
+### What it does
+Checks for calls which provide more than one argument for a single parameter.
+
+### Why is this bad?
+Providing multiple values for a single parameter will raise a `TypeError` at runtime.
+
+### Examples
+
+```python
+def f(x: int) -> int: ...
+
+f(1, x=2) # Error raised here
+```
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20parameter-already-assigned)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fdiagnostic.rs#L788)
+
+
+## `raw-string-type-annotation`
+
+**Default level**: error
+
+
+detects raw strings in type annotation positions
+
+### What it does
+Checks for raw-strings in type annotation positions.
+
+### Why is this bad?
+Static analysis tools like ty can't analyse type annotations that use raw-string notation.
+
+### Examples
+```python
+def test(): -> r"int":
+ ...
+```
+
+Use instead:
+```python
+def test(): -> "int":
+ ...
+```
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20raw-string-type-annotation)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fstring_annotation.rs#L61)
+
+
+## `static-assert-error`
+
+**Default level**: error
+
+
+Failed static assertion
+
+### What it does
+Makes sure that the argument of `static_assert` is statically known to be true.
+
+### Examples
+```python
+from ty_extensions import static_assert
+
+static_assert(1 + 1 == 3) # error: evaluates to `False`
+
+static_assert(int(2.0 * 3.0) == 6) # error: does not have a statically known truthiness
+```
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20static-assert-error)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fdiagnostic.rs#L1080)
+
+
+## `subclass-of-final-class`
+
+**Default level**: error
+
+
+detects subclasses of final classes
+
+### What it does
+Checks for classes that subclass final classes.
+
+### Why is this bad?
+Decorating a class with `@final` declares to the type checker that it should not be subclassed.
+
+### Example
+
+```python
+from typing import final
+
+@final
+class A: ...
+class B(A): ... # Error raised here
+```
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20subclass-of-final-class)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fdiagnostic.rs#L858)
+
+
+## `too-many-positional-arguments`
+
+**Default level**: error
+
+
+detects calls passing too many positional arguments
+
+### What it does
+Checks for calls that pass more positional arguments than the callable can accept.
+
+### Why is this bad?
+Passing too many positional arguments will raise `TypeError` at runtime.
+
+### Example
+
+```python
+def f(): ...
+
+f("foo") # Error raised here
+```
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20too-many-positional-arguments)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fdiagnostic.rs#L903)
+
+
+## `type-assertion-failure`
+
+**Default level**: error
+
+
+detects failed type assertions
+
+### What it does
+Checks for `assert_type()` and `assert_never()` calls where the actual type
+is not the same as the asserted type.
+
+### Why is this bad?
+`assert_type()` allows confirming the inferred type of a certain value.
+
+### Example
+
+```python
+def _(x: int):
+ assert_type(x, int) # fine
+ assert_type(x, str) # error: Actual type does not match asserted type
+```
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20type-assertion-failure)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fdiagnostic.rs#L881)
+
+
+## `unavailable-implicit-super-arguments`
+
+**Default level**: error
+
+
+detects invalid super() calls where implicit arguments are unavailable.
+
+### What it does
+Detects invalid `super()` calls where implicit arguments like the enclosing class or first method argument are unavailable.
+
+### Why is this bad?
+When `super()` is used without arguments, Python tries to find two things:
+the nearest enclosing class and the first argument of the immediately enclosing function (typically self or cls).
+If either of these is missing, the call will fail at runtime with a `RuntimeError`.
+
+### Examples
+```python
+super() # error: no enclosing class or function found
+
+def func():
+ super() # error: no enclosing class or first argument exists
+
+class A:
+ f = super() # error: no enclosing function to provide the first argument
+
+ def method(self):
+ def nested():
+ super() # error: first argument does not exist in this nested function
+
+ lambda: super() # error: first argument does not exist in this lambda
+
+ (super() for _ in range(10)) # error: argument is not available in generator expression
+
+ super() # okay! both enclosing class and first argument are available
+```
+
+### References
+- [Python documentation: super()](https://docs.python.org/3/library/functions.html#super)
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20unavailable-implicit-super-arguments)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fdiagnostic.rs#L924)
+
+
+## `unknown-argument`
+
+**Default level**: error
+
+
+detects unknown keyword arguments in calls
+
+### What it does
+Checks for keyword arguments in calls that don't match any parameter of the callable.
+
+### Why is this bad?
+Providing an unknown keyword argument will raise `TypeError` at runtime.
+
+### Example
+
+```python
+def f(x: int) -> int: ...
+
+f(x=1, y=2) # Error raised here
+```
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20unknown-argument)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fdiagnostic.rs#L979)
+
+
+## `unresolved-attribute`
+
+**Default level**: error
+
+
+detects references to unresolved attributes
+
+### What it does
+Checks for unresolved attributes.
+
+### Why is this bad?
+Accessing an unbound attribute will raise an `AttributeError` at runtime. An unresolved attribute is not guaranteed to exist from the type alone, so this could also indicate that the object is not of the type that the user expects.
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20unresolved-attribute)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fdiagnostic.rs#L1000)
+
+
+## `unresolved-import`
+
+**Default level**: error
+
+
+detects unresolved imports
+
+### What it does
+Checks for import statements for which the module cannot be resolved.
+
+### Why is this bad?
+Importing a module that cannot be resolved will raise an `ImportError`
+at runtime.
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20unresolved-import)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fdiagnostic.rs#L1013)
+
+
+## `unsupported-bool-conversion`
+
+**Default level**: error
+
+
+detects boolean conversion where the object incorrectly implements __bool__
+
+### What it does
+Checks for bool conversions where the object doesn't correctly implement `__bool__`.
+
+### Why is this bad?
+If an exception is raised when you attempt to evaluate the truthiness of an object,
+using the object in a boolean context will fail at runtime.
+
+### Examples
+
+```python
+class NotBoolable:
+ __bool__ = None
+
+b1 = NotBoolable()
+b2 = NotBoolable()
+
+if b1: # exception raised here
+ pass
+
+b1 and b2 # exception raised here
+not b1 # exception raised here
+b1 < b2 < b1 # exception raised here
+```
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20unsupported-bool-conversion)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fdiagnostic.rs#L757)
+
+
+## `unsupported-operator`
+
+**Default level**: error
+
+
+detects binary, unary, or comparison expressions where the operands don't support the operator
+
+### What it does
+Checks for binary expressions, comparisons, and unary expressions where
+the operands don't support the operator.
+
+### Why is this bad?
+Attempting to use an unsupported operator will raise a `TypeError` at
+runtime.
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20unsupported-operator)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fdiagnostic.rs#L1046)
+
+
+## `zero-stepsize-in-slice`
+
+**Default level**: error
+
+
+detects a slice step size of zero
+
+### What it does
+Checks for step size 0 in slices.
+
+### Why is this bad?
+A slice with a step size of zero will raise a `ValueError` at runtime.
+
+### Examples
+```python
+l = list(range(10))
+l[1:10:0] # ValueError: slice step cannot be zero
+```
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20zero-stepsize-in-slice)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fdiagnostic.rs#L1061)
+
+
+## `call-possibly-unbound-method`
+
+**Default level**: warn
+
+
+detects calls to possibly unbound methods
+
+### What it does
+Checks for calls to possibly unbound methods.
+
+### Why is this bad?
+Calling an unbound method will raise an `AttributeError` at runtime.
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20call-possibly-unbound-method)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fdiagnostic.rs#L102)
+
+
+## `invalid-ignore-comment`
+
+**Default level**: warn
+
+
+detects ignore comments that use invalid syntax
+
+### What it does
+Checks for `type: ignore` and `ty: ignore` comments that are syntactically incorrect.
+
+### Why is this bad?
+A syntactically incorrect ignore comment is probably a mistake and is useless.
+
+### Examples
+```py
+a = 20 / 0 # type: ignoree
+```
+
+Use instead:
+
+```py
+a = 20 / 0 # type: ignore
+```
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20invalid-ignore-comment)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Fsuppression.rs#L65)
+
+
+## `possibly-unbound-attribute`
+
+**Default level**: warn
+
+
+detects references to possibly unbound attributes
+
+### What it does
+Checks for possibly unbound attributes.
+
+### Why is this bad?
+Attempting to access an unbound attribute will raise an `AttributeError` at runtime.
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20possibly-unbound-attribute)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fdiagnostic.rs#L809)
+
+
+## `possibly-unbound-import`
+
+**Default level**: warn
+
+
+detects possibly unbound imports
+
+### What it does
+Checks for imports of symbols that may be unbound.
+
+### Why is this bad?
+Importing an unbound module or name will raise a `ModuleNotFoundError`
+or `ImportError` at runtime.
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20possibly-unbound-import)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fdiagnostic.rs#L822)
+
+
+## `possibly-unresolved-reference`
+
+**Default level**: warn
+
+
+detects references to possibly undefined names
+
+### What it does
+Checks for references to names that are possibly not defined.
+
+### Why is this bad?
+Using an undefined variable will raise a `NameError` at runtime.
+
+### Example
+
+```python
+for i in range(0):
+ x = i
+
+print(x) # NameError: name 'x' is not defined
+```
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20possibly-unresolved-reference)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fdiagnostic.rs#L836)
+
+
+## `redundant-cast`
+
+**Default level**: warn
+
+
+detects redundant cast calls
+
+### What it does
+Detects redundant `cast` calls where the value already has the target type.
+
+### Why is this bad?
+These casts have no effect and can be removed.
+
+### Example
+```python
+def f() -> int:
+ return 10
+
+cast(int, f()) # Redundant
+```
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20redundant-cast)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fdiagnostic.rs#L1118)
+
+
+## `undefined-reveal`
+
+**Default level**: warn
+
+
+detects usages of reveal_type without importing it
+
+### What it does
+Checks for calls to `reveal_type` without importing it.
+
+### Why is this bad?
+Using `reveal_type` without importing it will raise a `NameError` at runtime.
+
+### Examples
+TODO #14889
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20undefined-reveal)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fdiagnostic.rs#L963)
+
+
+## `unknown-rule`
+
+**Default level**: warn
+
+
+detects ty: ignore comments that reference unknown rules
+
+### What it does
+Checks for `ty: ignore[code]` where `code` isn't a known lint rule.
+
+### Why is this bad?
+A `ty: ignore[code]` directive with a `code` that doesn't match
+any known rule will not suppress any type errors, and is probably a mistake.
+
+### Examples
+```py
+a = 20 / 0 # ty: ignore[division-by-zer]
+```
+
+Use instead:
+
+```py
+a = 20 / 0 # ty: ignore[division-by-zero]
+```
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20unknown-rule)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Fsuppression.rs#L40)
+
+
+## `unresolved-reference`
+
+**Default level**: warn
+
+
+detects references to names that are not defined
+
+### What it does
+Checks for references to names that are not defined.
+
+### Why is this bad?
+Using an undefined variable will raise a `NameError` at runtime.
+
+### Example
+
+```python
+print(x) # NameError: name 'x' is not defined
+```
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20unresolved-reference)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Ftypes%2Fdiagnostic.rs#L1027)
+
+
+## `unused-ignore-comment`
+
+**Default level**: warn
+
+
+detects unused type: ignore comments
+
+### What it does
+Checks for `type: ignore` or `ty: ignore` directives that are no longer applicable.
+
+### Why is this bad?
+A `type: ignore` directive that no longer matches any diagnostic violations is likely
+included by mistake, and should be removed to avoid confusion.
+
+### Examples
+```py
+a = 20 / 2 # ty: ignore[division-by-zero]
+```
+
+Use instead:
+
+```py
+a = 20 / 2
+```
+
+### Links
+* [Related issues](https://github.com/astral-sh/ty/issues?q=sort%3Aupdated-desc%20is%3Aissue%20is%3Aopen%20unused-ignore-comment)
+* [View source](https://github.com/astral-sh/ruff/blob/main/crates%2Fty_python_semantic%2Fsrc%2Fsuppression.rs#L15)
+
+
diff --git a/crates/ty_python_semantic/src/types/diagnostic.rs b/crates/ty_python_semantic/src/types/diagnostic.rs
index 25dd0c69ba..17a1cadd51 100644
--- a/crates/ty_python_semantic/src/types/diagnostic.rs
+++ b/crates/ty_python_semantic/src/types/diagnostic.rs
@@ -646,7 +646,7 @@ declare_lint! {
/// must be assigned the value `False` at runtime; the type checker will consider its value to
/// be `True`. If annotated, it must be annotated as a type that can accept `bool` values.
pub(crate) static INVALID_TYPE_CHECKING_CONSTANT = {
- summary: "detects invalid TYPE_CHECKING constant assignments",
+ summary: "detects invalid `TYPE_CHECKING` constant assignments",
status: LintStatus::preview("1.0.0"),
default_level: Level::Error,
}
diff --git a/ty.schema.json b/ty.schema.json
index a070b862cc..8750c208ed 100644
--- a/ty.schema.json
+++ b/ty.schema.json
@@ -551,7 +551,7 @@
]
},
"invalid-type-checking-constant": {
- "title": "detects invalid TYPE_CHECKING constant assignments",
+ "title": "detects invalid `TYPE_CHECKING` constant assignments",
"description": "## What it does\nChecks for a value other than `False` assigned to the `TYPE_CHECKING` variable, or an\nannotation not assignable from `bool`.\n\n## Why is this bad?\nThe name `TYPE_CHECKING` is reserved for a flag that can be used to provide conditional\ncode seen only by the type checker, and not at runtime. Normally this flag is imported from\n`typing` or `typing_extensions`, but it can also be defined locally. If defined locally, it\nmust be assigned the value `False` at runtime; the type checker will consider its value to\nbe `True`. If annotated, it must be annotated as a type that can accept `bool` values.",
"default": "error",
"oneOf": [