
Research
/Security News
9 Malicious NuGet Packages Deliver Time-Delayed Destructive Payloads
Socket researchers discovered nine malicious NuGet packages that use time-delayed payloads to crash applications and corrupt industrial control systems.
Twyn is a security tool that compares the name of your dependencies against a set of the most popular ones,
in order to determine if there is any similarity between them, preventing you from using a potentially illegitimate one.
In short, Twyn protects you against typosquatting attacks.
It works as follows:
--dependency-file) or some dependencies introduced through the CLI (--dependency). If no option was provided, it will try to find a dependencies file in your working path. It will try to parse all the supported dependency files that it finds. To know which files are supported head to the Dependency files section.Twyn will prompt an error.Twyn assumes that you're using either a not so popular package (therefore it can't verify its legitimacy) or a package created by yourself, therefore unknown for the rest.Twyn is available on PyPi repository, you can install it by running
pip install twyn[cli]
Twyn provides a Docker image, which can be found here.
Use it like so:
docker pull elementsinteractive/twyn:latest
docker run elementsinteractive/twyn --help
| Option / Argument | Type / Values | Description |
|---|---|---|
--config | str (path) | Path to configuration file (twyn.toml or pyproject.toml by default). |
--dependency-file | str (path) | Dependency file to analyze. Supported: requirements.txt, poetry.lock, uv.lock, etc. |
--dependency | str (multiple allowed) | Dependency to analyze directly. Can be specified multiple times. |
--selector-method | all, first-letter, nearby-letter | Method for selecting possible typosquats. |
--package-ecosystem | pypi, npm | Package ecosystem for analysis. |
-v | flag | Enable info-level logging. |
-vv | flag | Enable debug-level logging. |
--no-cache | flag | Disable use of trusted packages cache. Always fetch from the source. |
--no-track | flag | Do not show the progress bar while processing packages. |
--json | flag | Display results in JSON format. Implies --no-track. |
-r, --recursive | flag | Scan directories recursively for dependency files. |
Usage Example:
twyn run <OPTIONS>
or get help with
twyn run --help
If you want your output in JSON format, you can run Twyn with the following flag:
twyn run --json
This will output:
{"results":[{"errors":[{"dependency":"my-package","similars":["mypackage"]}],"source":"manual_input"}]}
If Twyn was run by manually giving it dependencies (with --dependency), the source will be manual_input.
In any other case (when dependencies are parsed from a file), the source will be the path to the dependencies file. One entry will be created for every source.
Twyn also supports being used as 3rd party library for you project. To install it, run:
pip install twyn
Example usage in your code:
from twyn import check_dependencies
typos = check_dependencies()
for typo in typos.errors:
print(f"Dependency:{typo.dependency}")
print(f"Did you mean any of [{','.join(typo.similars)}]")
By default, logging is disabled when running as a 3rd party library. To override this behaviour, you can:
logging.basicConfig(level=logging.INFO)
logging.getLogger("twyn").setLevel(logging.INFO)
It can happen that a legitimate package known by the user raises an error because it is too similar to one of the most trusted ones. Imagine that you are using internally a package that you developed called reqests. You can then add this packages to the allowlist, so it will not be reported as a typo:
twyn allowlist add <package>
To remove it simply:
twyn allowlist remove <package>
To specify a dependency file through the command line run:
twyn run --dependency-file <file path>
The following dependency file formats are supported:
requirements.txtpoetry.lock (<1.5, >=1.5)uv.lockpackage-lock.json (v1, v2, v3)yarn.lock (v1, v2)pnpm-lock.yaml (v9)You can also check a dependency by entering it through the command line:
twyn run --dependency <dependency>
It does accept multiple dependencies at a time:
twyn run --dependency <dependency> --dependency <another_dependency>
When this option is selected, no dependency file is checked.
You can choose between different operational modes. These will determine which dependencies from the trusted set the analyzed dependency can be a typosquat of.
all: Default option. It is the most exhaustive mode. It will check your package names against all the trusted ones without any assumption.nearby-letter: It will assume a typo on the first letter of the dependency is possible, but improbable if letters are farther apart in the keyboard. Specifically, it will compare the analyzed dependency against dependencies whose first letter is one step away in an ANSI keyboard layout.first-letter: It will assume a typo on the first letter is very improbable, and won't compare the analyzed dependency against dependencies with a different first letter.[!NOTE] Selecting an option is a matter of preference:
allis the slowest, but will have more false positives and less false negatives; whilefirst-letteris the fastest, but it will have less false positives and more false negatives.
To select a specific operational mode through the CLI use the following command
twyn run --selector-method <method>
You can save your configurations in a .toml file, so you don't need to specify them everytime you run Twyn in your terminal.
By default, it will try to find a twyn.toml file in your working directory when it's trying to load your configurations. If it does not find it, it will fallback to pyproject.toml.
However, you can specify a config file as follows:
twyn run --config <file>
All the configurations available through the command line are also supported in the config file.
[tool.twyn]
dependency_file="/my/path/requirements.txt" # it can be either a string or a list of strings
selector_method="first_letter"
logging_level="debug"
allowlist=["my_package"]
pypi_source="https://mirror-with-trusted-dependencies.com/file-pypi.json"
npm_source="https://mirror-with-trusted-dependencies.com/file-npm.json"
The file format for each reference is as follows:
{
"date": "string (ISO 8601 format, e.g. 2025-09-10T14:23:00+00)",
"packages": [
{ "name": "string" }
]
}
By default, Twyn will cache the list of trusted packages to a cache file, within the .twyn directory that will be automatically created.
You can disable the cache by adding the following flag:
twyn run --no-cache
In which case it will download again the list of trusted packages, withou saving them to the cache file.
Cache file is valid for 30 days, after that period it will download again the trusted packages list.
To clear the cache, run:
twyn cache clear
FAQs
Security tool against dependency typosquatting attacks
We found that twyn demonstrated a healthy version release cadence and project activity because the last version was released less than a year ago. It has 1 open source maintainer collaborating on the project.
Did you know?

Socket for GitHub automatically highlights issues in each pull request and monitors the health of all your open source dependencies. Discover the contents of your packages and block harmful activity before you install or update your dependencies.

Research
/Security News
Socket researchers discovered nine malicious NuGet packages that use time-delayed payloads to crash applications and corrupt industrial control systems.

Security News
Socket CTO Ahmad Nassri discusses why supply chain attacks now target developer machines and what AI means for the future of enterprise security.

Security News
Learn the essential steps every developer should take to stay secure on npm and reduce exposure to supply chain attacks.