diff --git a/docs/_scripts/generate_api_reference_links.py b/docs/_scripts/generate_api_reference_links.py index 30a75440d..714dc641f 100644 --- a/docs/_scripts/generate_api_reference_links.py +++ b/docs/_scripts/generate_api_reference_links.py @@ -47,6 +47,8 @@ (["langgraph.graph"], "langgraph.constants", "END", "constants"), (["langgraph.constants"], "langgraph.types", "Send", "types"), (["langgraph.constants"], "langgraph.types", "Interrupt", "types"), + (["langgraph.constants"], "langgraph.types", "interrupt", "types"), + (["langgraph.constants"], "langgraph.types", "Command", "types"), ([], "langgraph.types", "RetryPolicy", "types"), ([], "langgraph.checkpoint.base", "Checkpoint", "checkpoints"), ([], "langgraph.checkpoint.base", "CheckpointMetadata", "checkpoints"), @@ -115,10 +117,10 @@ def _get_doc_title(data: str, file_name: str) -> str: class ImportInformation(TypedDict): - imported: str # imported class name - source: str # module path - docs: str # URL to the documentation - title: str # Title of the document + imported: str # The name of the class that was imported. + source: str # The full module path from which the class was imported. + docs: str # The URL pointing to the class's documentation. + title: str # The title of the document where the import is used. def _get_imports( @@ -211,36 +213,73 @@ def _get_imports( return imports -class ImportPreprocessor(Preprocessor): - """A preprocessor to replace imports in each Python code cell with links to their - documentation and append the import info in a comment.""" +def get_imports(code: str, doc_title: str) -> List[ImportInformation]: + """Retrieve all import references from the given code for specified ecosystems. - def preprocess(self, nb, resources): - self.all_imports = [] - file_name = os.path.basename(resources.get("metadata", {}).get("name", "")) - _DOC_TITLE = _get_doc_title(nb.cells[0].source, file_name) + Args: + code: The source code from which to extract import references. + doc_title: The documentation title associated with the code. - cells = [] - for cell in nb.cells: - if cell.cell_type == "code": - cells.append(cell) - imports = _get_imports( - cell.source, _DOC_TITLE, "langchain" - ) + _get_imports(cell.source, _DOC_TITLE, "langgraph") - if not imports: - continue + Returns: + A list of import information for each import found. + """ + ecosystems = ["langchain", "langgraph"] + all_imports = [] + for package_ecosystem in ecosystems: + all_imports.extend(_get_imports(code, doc_title, package_ecosystem)) + return all_imports - cells.append( - nbformat.v4.new_markdown_cell( - source=f""" -
.*?)\n(?P=indent)```', re.DOTALL
+ )
+
+ def replace_code_block(match: re.Match) -> str:
+ """Replace the matched code block with additional API reference links if imports are found.
+
+ Args:
+ match (re.Match): The regex match object containing the code block.
+
+ Returns:
+ str: The modified code block with API reference links appended if applicable.
+ """
+ indent = match.group('indent')
+ code_block = match.group('code')
+ language = match.group('language') # Preserve the language from the regex match
+ # Retrieve import information from the code block
+ imports = get_imports(code_block, "__unused__")
+
+ original_code_block = match.group(0)
+ # If no imports are found, return the original code block
+ if not imports:
+ return original_code_block
+
+ # Generate API reference links for each import
+ api_links = ' | '.join(
+ f'{imp["imported"]}' for imp in imports
+ )
+ # Return the code block with appended API reference links
+ return f'{original_code_block}\n\n{indent}API Reference: {api_links}'
+
+ # Apply the replace_code_block function to all matches in the markdown
+ updated_markdown = code_block_pattern.sub(replace_code_block, markdown)
+ return updated_markdown
\ No newline at end of file
diff --git a/docs/_scripts/notebook_convert.py b/docs/_scripts/notebook_convert.py
index 5db6d7d0c..6523372dc 100644
--- a/docs/_scripts/notebook_convert.py
+++ b/docs/_scripts/notebook_convert.py
@@ -6,8 +6,6 @@
from nbconvert.exporters import MarkdownExporter
from nbconvert.preprocessors import Preprocessor
-from generate_api_reference_links import ImportPreprocessor
-
class EscapePreprocessor(Preprocessor):
def preprocess_cell(self, cell, resources, cell_index):
@@ -107,7 +105,6 @@ def preprocess_cell(self, cell, resources, cell_index):
preprocessors=[
EscapePreprocessor,
ExtractAttachmentsPreprocessor,
- ImportPreprocessor,
],
template_name="mdoutput",
extra_template_basedirs=[
diff --git a/docs/_scripts/notebook_hooks.py b/docs/_scripts/notebook_hooks.py
index b18e3dad5..9eb161c8f 100644
--- a/docs/_scripts/notebook_hooks.py
+++ b/docs/_scripts/notebook_hooks.py
@@ -7,6 +7,7 @@
from mkdocs.structure.pages import Page
from notebook_convert import convert_notebook
+from generate_api_reference_links import update_markdown_with_imports
logger = logging.getLogger(__name__)
logging.basicConfig()
@@ -111,7 +112,9 @@ def on_page_markdown(markdown: str, page: Page, **kwargs: Dict[str, Any]):
if page.file.src_path.endswith(".ipynb"):
logger.info("Processing Jupyter notebook: %s", page.file.src_path)
markdown = convert_notebook(page.file.abs_src_path)
+
+ # Append API reference links to code blocks
+ markdown = update_markdown_with_imports(markdown)
# Apply highlight comments to code blocks
markdown = _highlight_code_blocks(markdown)
-
return markdown