module documentation

Sparse checkout pattern handling.

Exception BlobNotFoundError Raised when a requested blob is not found in the repository's object store.
Exception SparseCheckoutConflictError Raised when local modifications would be overwritten by a sparse checkout operation.
Function apply_included_paths Apply the sparse-checkout inclusion set to the index and working tree.
Function compute_included_paths_cone Implement a simplified 'cone' approach for sparse-checkout.
Function compute_included_paths_full Use .gitignore-style parsing and matching to determine included paths.
Function determine_included_paths Determine which paths in the index should be included based on either a full-pattern match or a cone-mode approach.
Function match_sparse_patterns Check whether a path is included based on .gitignore-style patterns.
Function parse_sparse_patterns Parse pattern lines from a sparse-checkout file (.git/info/sparse-checkout).
def apply_included_paths(repo: Repo, included_paths: Set[str], force: bool = False):

Apply the sparse-checkout inclusion set to the index and working tree.

This function updates skip-worktree bits in the index based on whether each path is included or not. It then adds or removes files in the working tree accordingly. If force=False, files that have local modifications will cause an error instead of being removed.

Parameters
repo:RepoA path to the repository or a Repo object.
included_paths:Set[str]A set of paths (strings) that should remain included.
force:boolWhether to forcibly remove locally modified files (default False).
Returns
None
def compute_included_paths_cone(index: Index, lines: Sequence[str]) -> set[str]:

Implement a simplified 'cone' approach for sparse-checkout.

By default, this can include top-level files, exclude all subdirectories, and re-include specified directories. The logic is less comprehensive than Git's built-in cone mode (recursive vs parent) and is essentially an implementation of the recursive cone mode.

Parameters
index:IndexAn Index object containing the repository's index.
lines:Sequence[str]A list of pattern lines (strings), typically including entries like "/", "!//", or "/mydir/".
Returns
set[str]A set of included path strings.
def compute_included_paths_full(index: Index, lines: Sequence[str]) -> set[str]:

Use .gitignore-style parsing and matching to determine included paths.

Each file path in the index is tested against the parsed sparse patterns. If it matches the final (most recently applied) positive pattern, it is included.

Parameters
index:IndexAn Index object containing the repository's index.
lines:Sequence[str]A list of pattern lines (strings) from sparse-checkout config.
Returns
set[str]A set of included path strings.
def determine_included_paths(index: Index, lines: Sequence[str], cone: bool) -> set[str]:

Determine which paths in the index should be included based on either a full-pattern match or a cone-mode approach.

Parameters
index:IndexAn Index object containing the repository's index.
lines:Sequence[str]A list of pattern lines (strings) from sparse-checkout config.
cone:boolA bool indicating cone mode.
Returns
set[str]A set of included path strings.
def match_sparse_patterns(path_str: str, parsed_patterns: Sequence[tuple[str, bool, bool, bool]], path_is_dir: bool = False) -> bool:

Check whether a path is included based on .gitignore-style patterns.

This is a simplified approach that:
  1. Iterates over patterns in order.
  2. If a pattern matches, we set the "include" state depending on negation.
  3. Later matches override earlier ones.

In a sparse checkout, lines that do not start with '!' are positive patterns, indicating files/directories to check out (include in the index), and those that start with '!' are negative ('negated'), meaning they indicate files not to check out (not included in the index). This is fairly straightforward.

In a .gitignore, it's the same syntax but with a reverse effect: positive means "ignore" (exclude from the index) and negative means "unignore" (re-include in the index).

Many routines still rely on the same final logic: the last matching pattern decides "excluded" vs. "included."

We'll interpret "include" as returning True, "exclude" as returning False.

Each pattern can include negation ('!'), directory-only markers ('/' as suffix), or be anchored ('/' as prefix). The last matching pattern determines whether the path is ultimately included or excluded.

Parameters
path_str:strThe path (string) to test.
parsed_patterns:Sequence[tuple[str, bool, bool, bool]]A list of (pattern, negation, dir_only, anchored) tuples as returned by parse_sparse_patterns.
path_is_dir:boolWhether to treat the path as a directory (default False).
Returns
boolTrue if the path is included by the last matching pattern, False otherwise.
def parse_sparse_patterns(lines: Sequence[str]) -> list[tuple[str, bool, bool, bool]]:

Parse pattern lines from a sparse-checkout file (.git/info/sparse-checkout).

This simplified parser:
  1. Strips comments (#...) and empty lines.
  2. Returns a list of (pattern, is_negation, is_dir_only, anchored) tuples.

These lines are similar to .gitignore patterns but are used for sparse-checkout logic. This function strips comments and blank lines, identifies negation, anchoring, and directory-only markers, and returns data suitable for matching.

Example

line = "*.txt" -> ("*.txt", False, False, False) not negated/dir/anchored line = "/*.txt" -> ("*.txt", False, False, True) anchored, not negated/dir line = "!/*.txt" -> ("*.txt", False, False, True) anchored/negated, not dir line = "!/mydir/" -> ("mydir", True, True, True) anchored/negated/dir

Parameters
lines:Sequence[str]A list of raw lines (strings) from the sparse-checkout file.
Returns
list[tuple[str, bool, bool, bool]]A list of tuples (pattern, negation, dir_only, anchored), representing the essential details needed to perform matching.