Static-Analysis
26. SAST: Static Application Security Testing
66.8 Annotating Third-Party Libraries Without Stubs
Right, so you’ve imported a glorious third-party library that does exactly what you need. You’ve dutifully annotated your own code, feeling the warm glow of type safety. You run mypy and… a firestorm of red. The library has no type hints. Your brilliant annotations are now pointing into a void, and your type checker is having a panic attack. Welcome to the most common real-world hurdle in Python’s type system. You can’t change the library’s source code, but you also refuse to surrender to Any and the ensuing chaos. Let’s fix this.
66.7 Type Stubs (.pyi) and the Typeshed Repository
Right, so you’ve got your code nicely typed, you run mypy, and it passes. Then you try to import a third-party library and… boom. A cascade of errors. The library has no type hints. Your brilliant, statically-verified masterpiece is now festooned with Any annotations and your type checker is giving you the silent treatment. This is where type stubs and the Typeshed repository come in—they’re the duct tape and baling wire that hold the Python type ecosystem together, and you need to understand them.
66.6 beartype and typeguard: Runtime Type Validation
Alright, let’s get our hands dirty. You’ve run mypy or pyright and your code is “clean.” You feel good. But then your code actually runs, and some function that expected a list[int] gets handed a single '42' because it came from a JSON API or, heaven forbid, user input. Your beautiful static types, which exist only in the ether of your editor and CI checks, are powerless at runtime. The runtime doesn’t care about your type hints. It’s the wild west.
66.5 Inline Type: Ignore Comments and Their Overuse
Alright, let’s talk about the nuclear option of type checking: the # type: ignore comment. It’s the equivalent of duct tape for your type errors. It’s you, looking mypy or Pyright dead in the eye and saying, “I see your valid, technically correct point, and I’m choosing to ignore it.” And sometimes, that’s exactly what you need to do. But wield this power carelessly, and you’re not patching a hole; you’re just papering over the cracks until the whole wall collapses.
66.4 Common mypy Errors and How to Fix Them
Alright, let’s get our hands dirty. You’ve run mypy on your beautiful, seemingly perfect code, and it has responded by throwing a tantrum fit for a toddler denied candy. Don’t take it personally. mypy isn’t being a jerk; it’s just a deeply pedantic friend who takes your type hints more seriously than you do. Its errors are its way of saying, “I’m trying to protect you from yourself.” Let’s decode its unique brand of angst.
66.3 Pyright and Pylance: Microsoft's Type Checker
Now, let’s talk about the new kid on the block who showed up with a trust fund and a surprisingly sharp intellect: Pyright. This is Microsoft’s open-source type checker, and its closed-source, deeply integrated sibling for VS Code is called Pylance. Don’t get them confused: Pyright is the standalone engine you can run from the command line, and Pylance is the VS Code extension that uses Pyright’s brain but also adds incredible IntelliSense, auto-imports, and other editor magic that will make you weep with joy.
66.2 Strict Mode and Incremental Type Checking
Right, let’s talk about getting serious with your type checker. You’ve dipped your toes in, added a few str and int annotations, and maybe mypy has stopped yelling at you. Congrats, you’re typing. But you’re not type checking. There’s a vast, desolate chasm between the two, and on the other side lies maintainable, robust, and frankly, less-infuriating code. The bridge across that chasm is called “strict Mode.” Think of your type checker’s default settings as training wheels. They’re there so you don’t get overwhelmed and give up entirely. Strict mode is when you, an adult, take the training wheels off, throw them in the dumpster, and set the dumpster on fire. It’s a collection of settings that force the type checker to be pedantic, exhaustive, and actually useful. Without it, you’re just giving your code a suggestive glance, not a real audit.
66.1 mypy: Configuration, Running, and Reading Errors
Right, so you’ve decided to stop flying blind and let a static type checker yell at you about your code before it explodes in production. Good choice. mypy is the grumpy, pedantic, and ultimately brilliant old guard of Python type checking. It’s not here to be your friend; it’s here to be right. Let’s get it configured and learn how to interpret its particular brand of tough love. First things first, you don’t just run mypy on a random file and call it a day. You need a configuration file to tell it how to behave. This is non-negotiable. Without it, you’re just getting generic, often useless, advice. The file is called mypy.ini or pyproject.toml (the modern, cooler choice). We’ll use pyproject.toml because it’s where the industry is headed.