Dmytro Nikolaiev

Ruff Adoption Skill

ruff is great. Every Python developer knows that1.

Nevertheless, there’s a lot of existing Python code that doesn’t use it and really should. Previously you'd have spent a week of sprint time manually introducing ruff as a dev dependency and fixing the errors. But it's 2026, so instead of a week let's do it in a day with coding agents!

What's That?

ruff adoption skill that instructs an agent to install ruff in your project with your existing package manager2 and iteratively applies either the default set of rules or one you're asking for.

Example

For the following sample Python file:

import json, os
from pathlib import Path


DEFAULT_USER = "anonymous"


def normalize_name(name = None):
    if name == None:
        return DEFAULT_USER
    cleaned = name.strip()
    return cleaned or DEFAULT_USER


def is_enabled(flag):
    if flag == True:
        return True
    return False


def load_config(path, fallback=None):
    if fallback is None:
        fallback = {}
    try:
        contents = Path(path).read_text()
        return json.loads(contents)
    except:
        return fallback


def append_tag(tag, tags=[]):
    tags.append(tag)
    return tags

The diff will look like this after applying the skill3:

-import json, os
+import json
 from pathlib import Path
 
-
 DEFAULT_USER = "anonymous"
 
 
-def normalize_name(name = None):
-    if name == None:
+def normalize_name(name=None):
+    if name is None:
         return DEFAULT_USER
... 
 
 def is_enabled(flag):
-    if flag == True:
-        return True
-    return False
+    return bool(flag)
 
 
...
     try:
         contents = Path(path).read_text()
         return json.loads(contents)
-    except:
+    except (FileNotFoundError, json.JSONDecodeError):
         return fallback
 
 
-def append_tag(tag, tags=[]):
+def append_tag(tag, tags=[]):  # noqa: B006
     tags.append(tag)
     return tags

With the following commit history:

Full PR is here.

Conclusion

It's a very powerful paradigm to curate and share agent skills as they're so easy to develop, distribute and improve. The exercise of doing the same for a type checker such as ty or mypy is left to the reader. It's your turn to wrap something in a skill and share it with the world!


  1. Or most, I should say. And that's our mission, my dear reader - to spread the word.

  2. If that's not uv you'd better migrate to it 🙂. I really resisted the urge to bake this behavior into the skill.

  3. As you can see this wouldn't add type hints, which is out of scope for linting itself, but you could ask the agent to do it too.

#project