# Claude-Obsidian Source Kinds: File, URL, and Manual Types Explained

> Explore Claude-Obsidian source kinds: file, url, and manual. Understand how each type integrates knowledge into your vault and applies authority levels for seamless processing. Learn more now.

- Repository: [Agrici.Daniel/claude-obsidian](https://github.com/AgriciDaniel/claude-obsidian)
- Tags: how-to-guide
- Published: 2026-08-26

---

**Claude-obsidian recognizes exactly three source kinds—`file`, `url`, and `manual`—which dictate how knowledge enters the vault, how it is validated in the ledger, and what authority levels apply to downstream processing.**

The claude-obsidian project enforces strict provenance tracking by categorizing every knowledge entry through its **source kind** classification system. Defined as the `SOURCE_KINDS` constant in [`claude_obsidian/ledgers.py`](https://github.com/AgriciDaniel/claude-obsidian/blob/main/claude_obsidian/ledgers.py), this enumeration ensures that every piece of imported data carries validated metadata about its origin, whether harvested from local filesystems, fetched from remote web resources, or synthesized through manual user input.

## The Three Source Kinds Defined

Claude-obsidian classifies sources into three mutually exclusive categories. Any attempt to use a value outside this set triggers a validation error during ledger processing.

### File Sources

The `file` kind indicates that the source originated from a local file imported into the vault. These entries typically carry the `official` or `primary` authority designation and use content kinds like `document`. When ingesting local Markdown files, PDFs, or datasets, the system calculates a SHA-256 hash of the file contents to ensure content integrity.

### URL Sources

The `url` kind represents remote web resources—such as webpages, APIs, or media files—that were fetched and recorded. Like file sources, URL sources generally receive `primary` authority and use content kinds like `webpage`. The system stores the hash of the fetched content to detect changes if the source is re-fetched later.

### Manual Sources

The `manual` kind标识用户手动创建的内容，without an automatic import step. This includes hand-written notes, synthetic entries, or user-generated content. Manual sources must use the `synthetic` authority and the `synthetic` content kind. Unlike file or URL sources, manual entries may omit the `content_sha256` field since the content originates from the user rather than an external binary source.

## Source Kind Validation in [`claude_obsidian/ledgers.py`](https://github.com/AgriciDaniel/claude-obsidian/blob/main/claude_obsidian/ledgers.py)

The canonical definition of allowed source kinds resides in [`claude_obsidian/ledgers.py`](https://github.com/AgriciDaniel/claude-obsidian/blob/main/claude_obsidian/ledgers.py) at lines 25–37, where `SOURCE_KINDS` is defined as a constant containing exactly three string values: `"file"`, `"url"`, and `"manual"`.

When the system processes source ledger entries, the `validate_source_ledger` function enforces strict membership checks at multiple validation points (lines [514](https://github.com/AgriciDaniel/claude-obsidian/blob/main/claude_obsidian/ledgers.py#L514), [609](https://github.com/AgriciDaniel/claude-obsidian/blob/main/claude_obsidian/ledgers.py#L609), and [768](https://github.com/AgriciDaniel/claude-obsidian/blob/main/claude_obsidian/ledgers.py#L768)). If a source entry contains an `origin` field (the JSON key that stores the source kind) with any value outside the `SOURCE_KINDS` set—such as `"email"` or `"database"`—the validator raises a `LedgerValidationError` and rejects the transaction.

## Code Examples: Implementing Each Source Kind

The following Python examples demonstrate how to construct valid source entries for each recognized kind. All examples assume you are appending to the JSON source ledger at [`wiki/meta/ledgers/source-ledger.json`](https://github.com/AgriciDaniel/claude-obsidian/blob/main/wiki/meta/ledgers/source-ledger.json).

### Adding a File Source

```python
import json
from pathlib import Path

# Construct a valid file source entry

source_entry = {
    "source_id": "file-2024-09-01-article",
    "origin": "file",
    "authority": "official",
    "content_kind": "document",
    "content_sha256": "a3f5…",  # SHA-256 of the file contents

    "ingested_at": "2024-09-01",
    "review_status": "unreviewed",
    "pages": ["wiki/sources/Article.md"],
}

# Append to the source ledger

ledger_path = Path("wiki/meta/ledgers/source-ledger.json")
ledger = json.loads(ledger_path.read_text())
ledger["sources"][source_entry["source_id"]] = source_entry
ledger_path.write_text(json.dumps(ledger, indent=2))

```

### Adding a URL Source

```python
source_entry = {
    "source_id": "url-2024-09-01-https-example.com",
    "origin": "url",
    "authority": "primary",
    "content_kind": "webpage",
    "content_sha256": "e4b0…",  # Hash of the fetched HTML

    "ingested_at": "2024-09-01",
    "review_status": "unreviewed",
    "pages": ["wiki/sources/Example.md"],
}

```

### Adding a Manual (Synthetic) Source

```python
source_entry = {
    "source_id": "manual-2024-09-01-note",
    "origin": "manual",
    "authority": "synthetic",
    "content_kind": "synthetic",
    "content_sha256": None,  # Synthetic entries may omit the hash

    "ingested_at": "2024-09-01",
    "review_status": "unreviewed",
    "pages": ["wiki/sources/Note.md"],
}

```

## Downstream Effects of Source Classification

The source kind determination influences several critical pipeline behaviors beyond simple validation:

- **Authority Handling**: While `file` and `url` sources typically carry `official` or `primary` authority to indicate external provenance, `manual` sources must declare `synthetic` authority to flag user-generated content.

- **Content-Type Validation**: The system enforces that `synthetic` content kinds align with `synthetic` authority. File sources use `document`, URL sources use `webpage`, and manual sources use `synthetic` as their respective content kind values.

- **Import Pipeline Routing**: The CLI command `wiki-mode route source` uses the source kind to determine the appropriate storage location within the vault hierarchy. The routing logic is exercised in [`tests/test_wiki_mode.py`](https://github.com/AgriciDaniel/claude-obsidian/blob/main/tests/test_wiki_mode.py), ensuring that files land in the correct wiki subdirectory based on their origin type.

- **Transaction Safety**: The atomic transaction system implemented in [`claude_obsidian/transaction.py`](https://github.com/AgriciDaniel/claude-obsidian/blob/main/claude_obsidian/transaction.py) handles ledger updates, ensuring that source kind validation occurs before any persistent write to [`wiki/meta/ledgers/source-ledger.json`](https://github.com/AgriciDaniel/claude-obsidian/blob/main/wiki/meta/ledgers/source-ledger.json).

## Summary

- Claude-obsidian recognizes exactly three **source kinds**: `file`, `url`, and `manual`, defined in [`claude_obsidian/ledgers.py`](https://github.com/AgriciDaniel/claude-obsidian/blob/main/claude_obsidian/ledgers.py) as the `SOURCE_KINDS` constant.
- The `validate_source_ledger` function enforces strict validation at lines 514, 609, and 768, rejecting any source with an invalid origin.
- **File** and **URL** sources require SHA-256 content hashes and typically use `official` or `primary` authority.
- **Manual** sources use `synthetic` authority and content kind, and may omit content hashes.
- Source kinds drive CLI routing behavior via `wiki-mode route source` and determine vault storage paths.

## Frequently Asked Questions

### What happens if I use an invalid source kind?

The ledger validation system raises a `LedgerValidationError` during processing. Because `validate_source_ledger` checks membership against the `SOURCE_KINDS` set at multiple points (lines 514, 609, and 768 in [`claude_obsidian/ledgers.py`](https://github.com/AgriciDaniel/claude-obsidian/blob/main/claude_obsidian/ledgers.py)), any value other than `file`, `url`, or `manual` causes the transaction to abort without modifying the source ledger.

### How do source kinds affect authority assignment?

Source kinds enforce specific authority constraints. `file` and `url` origins typically receive `official` or `primary` authority to reflect external provenance, while `manual` origins must use `synthetic` authority. This distinction allows the vault to differentiate between scraped/imported knowledge and user-generated content when resolving conflicts or calculating trust scores.

### Can I extend claude-obsidian to recognize additional source kinds?

No, not without modifying the core source code. The `SOURCE_KINDS` constant is hardcoded as a closed set in [`claude_obsidian/ledgers.py`](https://github.com/AgriciDaniel/claude-obsidian/blob/main/claude_obsidian/ledgers.py). Adding new kinds would require updating the constant definition, modifying the validation logic in `validate_source_ledger`, and potentially adjusting the routing logic in the wiki-mode CLI and [`claude_obsidian/paths.py`](https://github.com/AgriciDaniel/claude-obsidian/blob/main/claude_obsidian/paths.py) to handle storage for the new origin type.

### Where is the source kind field stored in the ledger entry?

The source kind is stored in the `origin` field of the source entry JSON object. When constructing ledger entries, set `"origin": "file"`, `"origin": "url"`, or `"origin": "manual"` to classify the source. This field is the value checked against the `SOURCE_KINDS` constant during validation.