# `Yex.Doc`
[🔗](https://github.com/satoren/y_ex/blob/main/lib/doc.ex#L1)

Document module.

### Cross-Process Operations
  When a Doc or SharedType operation is performed from a process different from the process that created the Doc,
  a message like `{Yex.Doc, :run, fun}` is sent to the creator process via `GenServer.call` and the processing
  is delegated to that process. If you encounter a `GenServer.call` timeout, this delegation mechanism may be the cause.
  Make sure the worker process can handle the GenServer call messages properly.

  It is recommended to start a GenServer process such as `Yex.DocServer` when executing operations from other processes.

# `t`

```elixir
@type t() :: %Yex.Doc{reference: any(), worker_pid: pid() | nil}
```

# `auto_load`

# `client_id`

# `collection_id`

# `demonitor_update`

```elixir
@spec demonitor_update(reference()) :: :ok | {:error, term()}
```

Stop monitoring document updates.

# `demonitor_update_v1`

# `demonitor_update_v2`

# `get_array`

```elixir
@spec get_array(t(), String.t()) :: Yex.Array.t()
```

Get or insert the array type.

# `get_map`

```elixir
@spec get_map(t(), String.t()) :: Yex.Map.t()
```

Get or insert the map type.

# `get_pending_ds`

```elixir
@spec get_pending_ds(t()) :: {:ok, binary() | nil} | {:error, term()}
```

Returns the pending delete set (v1 encoded) for the document, if any.

A pending delete set holds deletions that arrived out of order and could
not yet be applied. Returns `{:ok, binary()}` when a pending delete set
exists, `{:ok, nil}` otherwise.

# `get_pending_update`

```elixir
@spec get_pending_update(t()) :: {:ok, binary() | nil} | {:error, term()}
```

Returns the pending update (v1 encoded) for the document, if any.

A pending update accumulates operations that arrived out of order and
could not yet be applied because their causal predecessors are missing.
Returns `{:ok, binary()}` when a pending update exists, `{:ok, nil}` otherwise.

# `get_text`

```elixir
@spec get_text(t(), String.t()) :: Yex.Text.t()
```

Get or insert the text type.

# `get_xml_fragment`

Get or insert the xml fragment type.

# `guid`

# `json_path`

```elixir
@spec json_path(t(), binary()) :: {:ok, list()} | {:error, term()}
```

Evaluates a JSONPath expression against the current document state.

Returns all matched values as a list. The path grammar follows yrs JSONPath
support (for example: `$.users[*].name`, `$.users..nick`).

# `monitor_subdocs`

# `monitor_update`

```elixir
@spec monitor_update(
  t(),
  keyword()
) :: {:ok, reference()} | {:error, term()}
```

Monitor document updates.
 You can pass metadata as an option. This value is passed as the fourth element of the message.If omitted, it will be passed as a structure of Doc itself.

The third element is the transaction's origin: the term passed to `transaction/3`,
`nil` when none was given, or the `%Yex.UndoManager{}` for a transaction committed
by `Yex.UndoManager.undo/1` or `Yex.UndoManager.redo/1`.

# `monitor_update_v1`

# `monitor_update_v2`

# `new`

```elixir
@spec new(pid()) :: t()
```

Create a new document.

worker_pid:
   If there is a possibility of passing the created document to another process, please specify the process responsible for operating the document.
   This process needs to handle the GenServer handle_call messages as follows:

    @impl true
    def handle_call(
          {Yex.Doc, :run, fun},
          _from,
          state
        ) do
      {:reply, fun.(), state}
    end

# `offset_kind`

# `prune_pending`

```elixir
@spec prune_pending(t()) :: {:ok, binary() | nil} | {:error, term()}
```

Removes and returns the pending update and pending delete set (v1 encoded,
merged into one update) for the document, if any.

Pending state holds structs and deletions that arrived before their causal
predecessors and are waiting on them. After this returns, both
`get_pending_update/1` and `get_pending_ds/1` return `{:ok, nil}`, and the
pruned content will no longer be integrated when the missing predecessors
arrive. The returned binary can be re-applied later, for example once the
missing updates have been fetched.

Works both inside and outside `transaction/3`. Returns `{:ok, nil}` when
nothing is pending. Raises `Yex.TransactionAcqError` when a
transaction held by another process prevents opening one.

# `run_in_worker_process`
*macro* 

Executes the given block in the document's worker process.
If the current process is already the worker process, executes directly.
Otherwise, delegates execution to the worker process via GenServer.call.

Raises if worker_pid is not set.

# `should_load`

# `skip_gc`

# `transaction`

```elixir
@spec transaction(t(), origin :: term(), fun()) :: term()
```

Start a transaction.

Raises `Yex.TransactionAcqError` if a transaction is already in progress.

## Examples
    iex> doc = Doc.new()
    iex> text = Doc.get_text(doc, "text")
    iex> Yex.Doc.monitor_update(doc)
    iex> Doc.transaction(doc, fn ->
    iex>   Text.insert(text, 0, "Hello")
    iex>   Text.insert(text, 0, "Hello", %{"bold" => true})
    iex> end)
    iex> assert_receive {:update_v1, _, nil, _}
    iex> refute_receive {:update_v1, _, nil, _}, 10 # only one update message

# `with_options`

```elixir
@spec with_options(Yex.Doc.Options.t(), pid()) :: t()
```

Create a new document with options.

---

*Consult [api-reference.md](api-reference.md) for complete listing*
