How to configure Cursor for Ruff
Cursor is a fork of VS Code, so the Ruff extension installs and behaves the same way. The one Cursor-specific difference is the extension source: Cursor uses the Open VSX Registry instead of the VS Code Marketplace. The extension ID (charliermarsh.ruff) is the same.
Tip
This guide focuses on Ruff configuration. If you haven’t set up your Python interpreter in Cursor yet, start with How to configure Cursor for a uv project.
uv add --dev ruff to add Ruff as a project dependency before proceeding.Install the Ruff extension
Open Cursor’s extension panel (Ctrl+Shift+X / Cmd+Shift+X) and search for Ruff. Install the extension published by Astral Software (ID: charliermarsh.ruff).
If the Black Formatter extension or the isort extension is installed, disable or uninstall them. Ruff covers both tasks; running two formatters on save causes conflicts.
Configure format-on-save
Create or open .vscode/settings.json at the project root and add:
{
"[python]": {
"editor.formatOnSave": true,
"editor.defaultFormatter": "charliermarsh.ruff",
"editor.codeActionsOnSave": {
"source.fixAll.ruff": "explicit",
"source.organizeImports.ruff": "explicit"
}
}
}source.fixAll.ruff applies Ruff’s auto-fixable lint rules on every save. source.organizeImports.ruff sorts imports. The .ruff suffix scopes each action to this extension only, so adding another formatter later won’t interfere.
Rule selection and other linting settings live in pyproject.toml, not in this file. Commit .vscode/settings.json so everyone on the project gets the same formatter behavior.
Use the project’s Ruff, not the bundled one
The extension defaults to importStrategy: "fromEnvironment", which looks for Ruff in the active Python environment before falling back to the binary bundled with the extension. Because uv add --dev ruff installs Ruff into .venv, this default means the editor and uv run ruff use the same binary.
No settings change is needed for this to work. The prerequisite is that Ruff is in the project’s dev dependencies, not just installed globally.
To confirm which Ruff the editor loaded, open the Command Palette (Ctrl+Shift+P / Cmd+Shift+P) and run Ruff: Show server logs. The output channel shows the path to the Ruff executable on startup. A path under .venv/ confirms the editor is using the project’s version.
Configure project-level rules
The extension reads pyproject.toml (under [tool.ruff]), ruff.toml, or .ruff.toml from the project root. Editor configuration is not needed for rule selection. Add rules to pyproject.toml:
[tool.ruff.lint]
extend-select = ["I", "UP", "RET", "SIM"]Both the editor and uv run ruff check . read the same file, so linting stays consistent between the editor and CI. For a curated starter set, see How to configure recommended Ruff defaults.
Troubleshoot common issues
Extension not formatting on save. Open Settings and confirm charliermarsh.ruff is the default Python formatter. If another formatter extension is active, it may have overridden the setting. Disable any Black Formatter or isort extensions, then reload the window.
Editor and terminal enforce different rules. Run Ruff: Show server logs to check which binary the editor loaded. If the path is inside the extension directory rather than .venv/, run uv add --dev ruff to install Ruff in the project environment, then reload the window.
Ruff not finding your config. The extension reads config from the project root, not a subdirectory. Open the root folder in Cursor (not a subfolder) so the extension finds pyproject.toml or ruff.toml.
Import sorting not working. Confirm the I rule category is enabled in your Ruff config (extend-select = ["I"]). If it’s in ignore, the source.organizeImports.ruff action has nothing to sort.
Learn More
- Ruff reference
- How to configure Cursor for a uv project for Python interpreter and pytest setup
- How to configure recommended Ruff defaults for rule selection
- How to sort Python imports with Ruff
- How to migrate from Black to the Ruff formatter
- Ruff editor integrations (official docs)
- ruff-vscode repository