I am trying to integrate obsidian with anki and would like to get entire content of uri
obsidian://adv-uri?vault=prep&filepath=3.1%20Economics%2FAIM%2FW1D4.md&heading=Q1, this would fetch the entire content under heading Q1
Hacked together this quick script, let me know if you are able to improve upon this
import os
import re
import sys
import urllib.parse
# Update this to your specific vault path
VAULT_PATH = "PATH_TO_YOUR_VAULT"
def fetch_content_from_obsidian(uri):
print(f"Received URI: {uri}")
# Parse the URI
match = re.match(
r"obsidian://adv-uri\?vault=(.+)&filepath=(.+)&(heading|block)=(.+)",
uri,
)
if not match:
raise ValueError("Invalid URI format")
vault, filepath, type, identifier = match.groups()
print(f"Parsed vault: {vault}")
print(f"Parsed filepath: {filepath}")
print(f"Parsed type: {type}")
print(f"Parsed identifier: {identifier}")
# Decode the URL-encoded filepath
filepath = urllib.parse.unquote(filepath)
print(f"Decoded filepath: {filepath}")
# Construct the full path to the file
full_path = os.path.join(VAULT_PATH, filepath)
print(f"Constructed full path: {full_path}")
content = ""
try:
with open(full_path, "r") as file:
lines = file.readlines()
print(f"Read {len(lines)} lines from file")
if type == "heading":
start_collecting = False
target_heading_level = None
heading_pattern = re.compile(r"^(#{1,6})\s+(.*)")
for line in lines:
match = heading_pattern.match(line.strip())
if match:
heading_level = len(match.group(1))
heading_text = match.group(2)
if start_collecting:
if heading_level <= target_heading_level:
print(
"Reached next main heading, stopping collection"
)
break
if heading_text == identifier:
print(f"Found heading: {identifier}")
target_heading_level = heading_level
start_collecting = True
if start_collecting:
content += line
elif type == "block":
block_id = re.compile(r"\^[a-zA-Z0-9]+")
list_pattern = re.compile(r"^\s*[-*]\s+")
start_collecting = False
for line in lines:
if block_id.search(line) and identifier in line:
print(f"Found block ID: {identifier}")
content = line
start_collecting = True
continue
if start_collecting:
if list_pattern.match(line) or line.strip() == "":
content += line
else:
break
except FileNotFoundError:
raise FileNotFoundError(f"File not found: {full_path}")
except PermissionError:
raise PermissionError(f"Permission denied: {full_path}")
print(f"Collected content: {content}")
return content
if __name__ == "__main__":
if len(sys.argv) != 2:
print("Usage: python script.py <obsidian-uri>")
sys.exit(1)
uri = sys.argv[1]
content = fetch_content_from_obsidian(uri)
print(f"Final content: {content}")