API Reference

Panopticas provides constants and functions for file type detection and metadata extraction.

Everything listed here is exported from the top-level package:

import panopticas

panopticas.get_language("app.py")   # "Python"
panopticas.VERSION                  # "0.0.19"

The examples below import from panopticas.core and panopticas.constants, which is equivalent and makes the origin of each name explicit.

Constants

EXT_FILETYPES

A dictionary mapping file extensions to file type names. 81 entries covering programming languages, data formats, configuration files and binary formats.

from panopticas.constants import EXT_FILETYPES

EXT_FILETYPES[".py"]      # "Python"
EXT_FILETYPES[".js"]      # "JavaScript"
EXT_FILETYPES[".yaml"]    # "YAML"
EXT_FILETYPES["dockerfile"]  # "Dockerfile" (special case)

Sample entries:

LANGUAGE_FILETYPES and NON_LANGUAGE_FILETYPES

EXT_FILETYPES mixes two kinds of value: things that are programming languages (Python, Go) and things that are file types but not languages (PNG, Gitignore, Lock). These two collections classify every value in the table — 32 languages and 44 non-languages. get_languages() and get_filetypes() read from them.

from panopticas.constants import LANGUAGE_FILETYPES, NON_LANGUAGE_FILETYPES

"Python" in LANGUAGE_FILETYPES       # True
"PNG" in NON_LANGUAGE_FILETYPES      # True

A test asserts that every EXT_FILETYPES value appears in exactly one of the two, so adding an extension without classifying it fails the suite.

LANGUAGE_BY_BASENAME

A dictionary for special filenames that identify a file type by their exact name, used where a file has no meaningful extension, or where the extension is too ambiguous to map globally.

from panopticas.constants import LANGUAGE_BY_BASENAME

LANGUAGE_BY_BASENAME["go.mod"]     # "go.mod"
LANGUAGE_BY_BASENAME["go.sum"]     # "go.sum"
LANGUAGE_BY_BASENAME["setup.cfg"]  # "INI"

setup.cfg is the illustrative case: it is read by configparser, so it is INI — but .cfg is used for arbitrary formats elsewhere, so the mapping is by basename rather than by extension.

METADATA_RULES

A dictionary containing rules for tagging files with metadata. Rules are organized by:

Example tags:

File Tags
pyproject.toml build, dependencies, Python
setup.py build, dependencies, Python, setuptools
package.json npm, dependencies
.github/workflows/ci.yml workflow, pipeline, GitHub, Git
Dockerfile IaC, Docker, dependencies
go.mod Go, module, dependencies

AI_RULES

The AI coding agent detection table. Maps an indicator to a (product, kind) pair across three match modes:

Mode Entries Matched against
exact_filename 25 the basename, lowercased
path_contains 31 a fragment of the path, ending in /
filename_suffix 4 the end of the basename

Precedence is exact filename, then the longest matching path fragment, then the longest matching suffix. First hit wins, so exactly one (product, kind) is returned for any path.

from panopticas.constants import AI_RULES

AI_RULES["exact_filename"]["claude.md"]   # ("Claude", "instructions")
AI_RULES["path_contains"][".cursor/rules/"]  # ("Cursor", "rules")

Products are brand-level — Claude covers both Claude Code and Claude Desktop. Artifacts owned by no single brand use a pseudo-product (Agents, MCP, llms.txt).

See the AI detection rules reference for the full inventory, the source that confirms each convention, and the candidates that were investigated and rejected.

AI_ARTIFACT_KINDS

The closed set of 14 artifact kinds an AI_RULES entry may use:

agent, chatmode, command, config, directory, docs, history, hook, ignore, instructions, plugin, prompt, rules, skill

IMPLICIT_TAGS

Tags that are assigned by detection logic rather than by a METADATA_RULES entry — currently ("AI", "license"). get_tags() unions these with the tags derived from the rule tables so the published vocabulary stays complete.

VERSION

The installed package version, read from package metadata via importlib.metadata. pyproject.toml is the single source of truth.

Functions

find_files

Find all files in a directory, respecting .gitignore patterns.

from panopticas.core import find_files

files = find_files("/path/to/project")
# Returns: ["src/main.py", "README.md", "pyproject.toml", ...]

Parameters:

Returns: List of paths relative to directory

Paths are relative to the scanned directory, not to the current working directory. Join them back onto directory before opening them.

get_language

Get the file type of a file based on extension, basename, or shebang.

from panopticas.core import get_language

get_language("app.py")           # "Python"
get_language("server.js")        # "JavaScript"
get_language("go.mod")           # "go.mod"
get_language("unknown_script")   # May detect via shebang, or "Unknown"

Parameters:

Returns: File type name as a string, or "Unknown" (also available as panopticas.core.UNKNOWN)

get_fileext

Get the extension of a path, falling back to the basename when there is none.

from panopticas.core import get_fileext

get_fileext("app.py")          # ".py"
get_fileext("Dockerfile")      # "Dockerfile"
get_fileext("src/.gitignore")  # ".gitignore"

Returns: The extension including the leading dot, or the basename if the path has no extension.

get_extension_filetype

Look up a single extension in EXT_FILETYPES. Case-insensitive.

from panopticas.core import get_extension_filetype

get_extension_filetype(".PY")     # "Python"
get_extension_filetype(".nope")   # None

Returns: File type name, or None if the extension is not known.

get_language_edge_cases

Look up a basename in LANGUAGE_BY_BASENAME.

from panopticas.core import get_language_edge_cases

get_language_edge_cases("setup.cfg")  # "INI"
get_language_edge_cases("app.py")     # None

get_filename_metatypes

Get metadata tags for a file based on its name and path.

from panopticas.core import get_filename_metatypes

get_filename_metatypes("pyproject.toml")
# Returns: ["build", "dependencies", "Python"]

get_filename_metatypes(".github/workflows/ci.yml")
# Returns: ["workflow", "pipeline", "GitHub", "Git"]

get_filename_metatypes("requirements.txt")
# Returns: ["pip", "Python", "PyPi", "dependencies"]

get_filename_metatypes("CLAUDE.md")
# Returns: ["AI", "Claude", "instructions"]

Parameters:

Returns: List of metadata tag strings

AI tags are derived from get_ai_metadata(), so any product added to AI_RULES appears here without further changes.

get_ai_metadata

Return AI coding agent metadata for a path.

from panopticas.core import get_ai_metadata

get_ai_metadata("CLAUDE.md")
# Returns: {"product": "Claude", "kind": "instructions"}

get_ai_metadata(".cursor/rules/style.mdc")
# Returns: {"product": "Cursor", "kind": "rules"}

get_ai_metadata("README.md")
# Returns: None

Parameters:

Returns: {"product": str, "kind": str}, or None if the path is not a recognised AI agent artifact

This is pure path inspection — the file is never opened, and it does not need to exist. It is the single source of truth for AI detection; get_filename_metatypes() and the panopticas ai command both derive from it.

find_ai_files

Find the AI coding agent artifacts in a directory tree.

from panopticas.core import find_ai_files

find_ai_files("/path/to/project")
# Returns: {
#   "CLAUDE.md": {"product": "Claude", "kind": "instructions"},
#   ".claude/settings.local.json": {"product": "Claude", "kind": "config"},
# }

Parameters:

Returns: Dictionary mapping relative path to its AI metadata

identify_files

Scan a directory and identify the file type of all files.

from panopticas.core import identify_files

results = identify_files("/path/to/project")
# Returns: {
#   "src/main.py": "Python",
#   "package.json": "JSON",
#   "Dockerfile": "Dockerfile",
#   ...
# }

Parameters:

Returns: Dictionary mapping relative file paths to their file type

identify_files_with_metrics

As identify_files, but also counts lines.

from panopticas.core import identify_files_with_metrics

identify_files_with_metrics("/path/to/project")
# Returns: {
#   "src/main.py": {"type": "Python", "lines": 240},
#   "logo.png":    {"type": "PNG", "lines": "N/A"},
# }

Returns: Dictionary mapping relative file path to {"type": ..., "lines": ...}

count_lines

Count the lines in a file.

from panopticas.core import count_lines

count_lines("src/main.py")   # 240
count_lines("logo.png")      # "N/A"

Returns: int, or the string "N/A" for binary files, missing files, and other read errors. This function does not raise.

get_tags

Return every tag panopticas can assign to a file.

from panopticas.core import get_tags

get_tags()
# Returns: ['.NET', 'agent', 'Agents', 'AI', 'Aider', ..., 'yarn']  (85 tags)

Returns: Sorted list of tag strings, case-insensitively ordered

The vocabulary is derived from the detection rules themselves — METADATA_RULES, AI_RULES and IMPLICIT_TAGS — rather than maintained as a separate list, so it cannot drift from what the tool actually assigns.

get_filetypes

Return every file type panopticas recognises, languages or not.

from panopticas.core import get_filetypes

get_filetypes()
# Returns: ['Apache JMeter', 'ASP.NET', ..., 'ZIP']  (76 file types)

Returns: Sorted list of file type strings

get_languages

Return every file type that is a programming language.

from panopticas.core import get_languages

get_languages()
# Returns: ['C', 'C Header', 'C#', 'C++', 'CSS', ..., 'Vue']  (32 languages)

Returns: Sorted list of language names — the subset of get_filetypes() classified as LANGUAGE_FILETYPES

check_shebang

Read the first line of a file and return it if it is a shebang.

from panopticas.core import check_shebang

check_shebang("script")   # "#!/usr/bin/env python3"
check_shebang("app.py")   # None

Returns: The stripped shebang line, or None if there is none, the file is missing, or it cannot be decoded. This function does not raise.

extract_shebang_language / get_shebang_language

Map a shebang line to a language name. get_shebang_language is a thin wrapper over extract_shebang_language.

from panopticas.core import extract_shebang_language

extract_shebang_language("#!/usr/bin/env python3")  # "Python"
extract_shebang_language("#!/bin/bash")             # "bash"
extract_shebang_language("#!/usr/local/bin/perl")   # "perl"

Returns: Language or interpreter name as a string, or None

extract_urls

Extract HTTP/HTTPS URLs from a string.

from panopticas.core import extract_urls

extract_urls("see https://a.com and http://b.org/x")
# Returns: ["https://a.com", "http://b.org/x"]

extract_urls_from_file

Extract all HTTP/HTTPS URLs from a file.

from panopticas.core import extract_urls_from_file

urls = extract_urls_from_file("README.md")
# Returns: ["https://github.com/example/repo", "https://docs.example.com"]

Parameters:

Returns: List of URL strings

Raises:

is_pip_requirements

Test whether a filename looks like a pip requirements file.

from panopticas.core import is_pip_requirements

is_pip_requirements("requirements.txt")       # True
is_pip_requirements("requirements-dev.txt")   # True
is_pip_requirements("reqs.txt")               # False

Returns: bool. Used as a function_rule in METADATA_RULES.

load_gitignore_patterns

Load the .gitignore patterns for a directory.

from panopticas.core import load_gitignore_patterns

spec = load_gitignore_patterns("/path/to/project")
spec.match_file("build/output.o")   # True

Returns: A pathspec.PathSpec, or None if the directory has no .gitignore. Used internally by find_files, identify_files and find_ai_files.