Packages
metastatic
0.19.0
0.26.0
0.25.0
0.24.1
0.24.0
0.23.0
0.22.2
0.22.1
0.22.0
0.21.3
0.21.2
0.21.1
0.21.0
0.20.3
0.20.2
0.20.1
0.20.0
0.19.0
0.18.0
0.17.0
0.16.0
0.15.1
0.15.0
0.14.2
0.14.1
0.14.0
0.13.3
0.13.2
0.13.1
0.13.0
0.12.0
0.11.0
0.10.4
0.10.3
0.10.2
0.10.1
0.10.0
0.9.2
0.9.1
0.9.0
0.8.6
0.8.5
0.8.4
0.8.3
0.8.2
0.8.1
0.8.0
0.7.7
0.7.6
0.7.5
0.7.4
0.7.3
0.7.1
0.7.0
0.6.1
0.6.0
0.5.2
0.5.1
0.5.0
0.4.2
0.4.1
0.4.0
0.3.5
0.3.4
0.3.3
0.3.2
0.3.1
0.3.0
0.2.0
0.1.3
0.1.2
0.1.1
0.1.0
Cross-language code meta-model library using unified MetaAST representation. Parse, transform, and translate code across Python, Elixir, Ruby, Erlang, Haskell, and more via a shared three-tuple AST format.
Current section
Files
Jump to
Current section
Files
lib/mix/tasks/metastatic.security_scan.ex
defmodule Mix.Tasks.Metastatic.SecurityScan do
@shortdoc "Scans for security vulnerabilities"
@moduledoc """
Scans source code for security vulnerabilities using pattern-based detection.
## Usage
mix metastatic.security_scan FILE [options]
## Options
* `--format` - Output format: text (default) or json
* `--language` - Source language: python, elixir, erlang, ruby, or haskell (auto-detected if not specified)
## Examples
# Scan for security issues
mix metastatic.security_scan my_file.py
# JSON output with CWE details
mix metastatic.security_scan my_file.ex --format json
## Vulnerability Categories
* Dangerous functions (eval, exec, pickle.loads)
* Hardcoded secrets (passwords, API keys, tokens) - CWE-798
* Weak cryptography (MD5, SHA1, DES)
* Insecure protocols (HTTP for sensitive data)
* SQL injection patterns - CWE-89
* Command injection patterns - CWE-78
## Severity Levels
Critical, High, Medium, Low
## Exit Codes
* 0 - No vulnerabilities found
* 1 - Vulnerabilities detected
* 2 - Error during analysis
"""
use Mix.Task
@dialyzer {:no_return, run: 1}
alias Metastatic.Analysis.Security
alias Metastatic.Builder
@impl Mix.Task
def run(args) do
{opts, files, _} = OptionParser.parse(args, strict: [format: :string, language: :string])
case files do
[] ->
Mix.shell().error("Usage: mix metastatic.security_scan FILE")
exit({:shutdown, 2})
[file | _] ->
analyze(file, opts[:language], opts[:format] || "text")
end
end
defp analyze(file, language, format) do
unless File.exists?(file),
do:
(
Mix.shell().error("File not found")
exit({:shutdown, 2})
)
source = File.read!(file)
lang = language || detect_lang(file)
case Builder.from_source(source, String.to_atom(lang)) do
{:ok, doc} ->
{:ok, result} = Security.analyze(doc)
output =
if format == "json",
do: Jason.encode!(Security.Result.to_map(result), pretty: true),
else: result.summary
Mix.shell().info(output)
exit({:shutdown, if(result.has_vulnerabilities?, do: 1, else: 0)})
{:error, reason} ->
Mix.shell().error("Parse error: #{inspect(reason)}")
exit({:shutdown, 2})
end
end
defp detect_lang(file) do
case Path.extname(file) do
".py" ->
"python"
".ex" ->
"elixir"
".exs" ->
"elixir"
".erl" ->
"erlang"
".rb" ->
"ruby"
".hs" ->
"haskell"
_ ->
Mix.shell().error("Cannot detect language")
exit({:shutdown, 2})
end
end
end