# Path-Based Addressing in OfficeCLI: How `/slide[1]/shape[2]` 1-Based Indexing Works

> Learn how OfficeCLI uses path-based addressing like /slide[1]/shape[2] with 1-based indexing to easily locate elements within your Office documents. Discover the power of OfficeCLI's syntax.

- Repository: [OfficeAI/OfficeCLI](https://github.com/iofficeai/OfficeCLI)
- Tags: internals
- Published: 2026-08-01

---

**OfficeCLI locates elements inside Office documents using hierarchical paths that follow `/type[index]` syntax with 1-based indexing, where the first element is `[1]` and the final element can be referenced using `last()`.**

OfficeCLI (iOfficeAI/OfficeCLI) provides a command-line interface for programmatically manipulating Word, Excel, and PowerPoint files. Understanding **path-based addressing** is essential for scripting document modifications, as every element—from slides to shapes to paragraphs—is identified via filesystem-like paths that use 1-based numerical indexing rather than conventional 0-based arrays.

## Path Syntax Fundamentals

OfficeCLI treats Office documents as hierarchical XML trees where each element is addressed by a path segment consisting of the element's local XML tag name followed by an index in square brackets. According to the [`README.md`](https://github.com/iOfficeAI/OfficeCLI/blob/main/README.md) (lines 14-16), the standard format follows this pattern:

```

/<element-type>[<index>]/<child-type>[<index>]

```

The index values start at **1**, not 0. This means `/slide[1]` refers to the first slide in a presentation, while `/slide[1]/shape[2]` targets the second shape on that first slide. When the index is omitted entirely, as in `/slide`, the command operates on **all** matching children of that type.

## Indexing Strategies and Selectors

### Positional Indexing (1-Based)

Positional indexes reflect an element's current location in the document structure. The first element of any type is always `[1]`, the second `[2]`, and so forth. As documented in [`skills/officecli-pptx/SKILL.md`](https://github.com/iOfficeAI/OfficeCLI/blob/main/skills/officecli-pptx/SKILL.md) (lines 30-33), these indexes are dynamic—they shift immediately when elements are added or removed, making positional addressing convenient for sequential access but potentially unstable during batch operations that modify structure.

### Named Attribute Selectors

For stable references that survive structural changes, OfficeCLI supports attribute selectors using the `@` symbol. Instead of relying on the positional index `/slide[1]/shape[2]`, you can reference `/slide[1]/shape[@name=Subtitle]` to target a shape by its `name` property. This approach remains valid even if the shape's numerical position changes due to insertions or deletions elsewhere in the document.

### Special Selectors

The **`last()`** function provides a convenient way to address the most recently added element without knowing its numerical index. For example, `/slide[last()]` targets the final slide in a presentation, while `/slide[1]/shape[last()]` selects the last shape on the first slide regardless of how many shapes exist.

## Element Types and Document Hierarchy

Different Office formats use specific XML tag names as path segments that correspond to their underlying Open XML structure:

- **PowerPoint**: `slide`, `shape`, `chart`, `table`
- **Word**: `paragraph`, `table`, `run`
- **Excel**: `sheet`, `row`, `cell`, `chart`

The TypeScript interfaces in [`sdk/node/index.d.ts`](https://github.com/iOfficeAI/OfficeCLI/blob/main/sdk/node/index.d.ts) define these paths as strings passed to the `path` parameter across SDK methods, validating that the element type names match the local XML tags for each Office format.

## Shell Quoting Requirements

Because paths contain square brackets and special characters that trigger shell globbing patterns, they must be properly quoted when used in terminal commands. The documentation in [`skills/officecli-pptx/SKILL.md`](https://github.com/iOfficeAI/OfficeCLI/blob/main/skills/officecli-pptx/SKILL.md) specifically warns that unquoted brackets may cause the shell to interpret them as wildcard patterns. Always use single or double quotes around paths:

```bash
officecli get deck.pptx '/slide[1]/shape[2]'

```

## Practical Implementation Examples

The following workflow demonstrates creating a presentation, navigating its structure via 1-based paths, and manipulating elements using both positional and named addressing:

```bash

# Create a new presentation

officecli create deck.pptx

# Add a slide (automatically becomes /slide[1])

officecli add deck.pptx / --type slide --prop title="Q4 Report"

# Add two shapes to the first slide

officecli add deck.pptx '/slide[1]' --type shape --prop name=Title --prop text="Revenue"
officecli add deck.pptx '/slide[1]' --type shape --prop name=Subtitle --prop text="25% Growth"

# Retrieve the second shape by positional index (1-based)

officecli get deck.pptx '/slide[1]/shape[2]' --json

# Returns: {"tag":"shape","path":"/slide[1]/shape[2]","attributes":{"name":"Subtitle","text":"25% Growth"}}

# Access the same element using stable name attribute

officecli get deck.pptx '/slide[1]/shape[@name=Subtitle]' --json

# Update fill color using positional path

officecli set deck.pptx '/slide[1]/shape[1]' --prop fill=FF0000

# Remove the final slide regardless of total count

officecli remove deck.pptx '/slide[last()]'

# Batch operations targeting specific paths

cat <<EOF | officecli batch deck.pptx --json
[
  {"command":"set","path":"/slide[1]/shape[1]","props":{"text":"Q4 Revenue"}},
  {"command":"set","path":"/slide[1]/shape[2]","props":{"text":"+25% YoY"}}
]
EOF

```

After any structural mutation—such as adding, removing, or reordering slides or shapes—you should re-query the document to confirm current indexes, as positional references may have shifted.

## Summary

- OfficeCLI uses **1-based indexing** where the first element is `[1]`, not `[0]`, as documented in [`README.md`](https://github.com/iOfficeAI/OfficeCLI/blob/main/README.md)
- Paths follow the syntax `/<element-type>[<index>]` and support arbitrary nesting depth for parent-child relationships
- **Positional indexes** reflect current document state and shift during structural edits, while **named selectors** (`[@name=value]`) provide stable references across mutations
- The **`last()`** selector addresses the final element of a type without requiring knowledge of the total count
- Always **quote paths** containing brackets to prevent shell interpretation errors
- Omitting the index operates on all matching elements of that type

## Frequently Asked Questions

### Why does OfficeCLI use 1-based indexing instead of 0-based?

OfficeCLI adopts 1-based indexing to align with user expectations from traditional document editing interfaces and Microsoft Office's internal object model conventions. According to the repository's [`README.md`](https://github.com/iOfficeAI/OfficeCLI/blob/main/README.md), this makes the CLI more intuitive for non-programmers while maintaining consistency with how Office applications natively reference slide numbers and paragraph positions.

### How do I address the last element without knowing its index?

Use the **`last()`** function in your path, such as `/slide[last()]` for the final slide or `/slide[1]/shape[last()]` for the last shape on the first slide. This selector dynamically resolves to the highest index currently present for that element type, making it ideal for scripts that append elements and then need to modify the most recent addition.

### What happens to indexes when I add or remove elements?

Positional indexes are **dynamic** and shift immediately after structural changes. If you delete `/slide[1]`, what was previously `/slide[2]` becomes `/slide[1]`. Similarly, inserting a new slide before existing ones renumbers all subsequent slides. For stable scripting across document mutations, use attribute selectors like `[@name=Title]` rather than numeric indexes.

### Do I need special syntax for attribute values containing spaces?

Yes, when using attribute selectors with values containing spaces, ensure proper shell quoting and include the value in quotes within the path. For example: `'/slide[1]/shape[@name="Main Title"]'`. Regardless of content, the square brackets and equals sign in paths always require shell quoting to prevent glob expansion, as noted in the PPTX skill documentation.