collectRefs

Run an action and return both its result and the refs collected during its reads.

collectRefsComputed and Effects

Run an action and return both its result and the refs collected during its reads.

Overview

The collectRefs function allows you to collect a set of reactive references (refs) within a specific scope and return both the result of an action and the collected refs. This is useful for managing and tracking the refs used within a certain code block.

Try it live

See which reads become dependenciesLive API

Current refs: 1 / 10

Last effect: 1 + 10 = 11

1Effect runs
0Effect cleanups
1Collected dependencies

The silenced read does not rerun the effect. collectRefs captures one dependency and returns the sampled sum: 11.

import { collectRefs, html, ref, silence, watchEffect } from 'regor'

export function createEffects(interactive = false) {
  const tracked = ref(1),
    untracked = ref(10)
  const runs = ref(0),
    cleanups = ref(0),
    result = ref('')
  const collected = ref(0),
    inspected = ref(0)
  watchEffect((onCleanup) => {
    const value = tracked()
    silence(() => {
      runs(runs() + 1)
      result(`${value} + ${untracked()} = ${value + untracked()}`)
    })
    onCleanup?.(() => silence(() => cleanups(cleanups() + 1)))
  })
  const inspect = () => {
    const read = collectRefs(() => tracked() + silence(() => untracked()))
    collected(read.refs.length)
    inspected(read.value)
  }
  inspect()
  return {
    interactive,
    tracked,
    untracked,
    runs,
    cleanups,
    result,
    collected,
    inspected,
    inspect,
    bumpTracked: () => tracked(tracked() + 1),
    bumpUntracked: () => untracked(untracked() + 1),
  }
}

export const effectsTemplate = html` <div class="guide-demo">
  <div class="guide-session-bar">
    <button type="button" @click="bumpTracked" :disabled="!interactive">
      Update tracked</button
    ><button type="button" @click="bumpUntracked" :disabled="!interactive">
      Update silenced read</button
    ><button type="button" @click="inspect" :disabled="!interactive">
      Collect the reads
    </button>
  </div>
  <p>Current refs: <strong>{{ tracked }} / {{ untracked }}</strong></p>
  <p class="guide-event">Last effect: {{ result }}</p>
  <div class="guide-metrics">
    <div><output>{{ runs }}</output><span>Effect runs</span></div>
    <div><output>{{ cleanups }}</output><span>Effect cleanups</span></div>
    <div>
      <output>{{ collected }}</output><span>Collected dependencies</span>
    </div>
  </div>
  <p class="guide-hint">
    The silenced read does not rerun the effect. collectRefs captures one
    dependency and returns the sampled sum: {{ inspected }}.
  </p>
</div>`
import { createApp, RegorConfig, useScope } from 'regor'
import { apiExamples } from './examples'

const element = document.getElementById('api-demo')
const name = element?.dataset.example
if (element && name && Object.hasOwn(apiExamples, name)) {
  const example = apiExamples[name as keyof typeof apiExamples]
  const scope = useScope<object>(() => example.create(true))
  const config =
    'config' in scope.context && scope.context.config instanceof RegorConfig
      ? scope.context.config
      : undefined
  createApp(scope, { element, template: example.template }, config)
}

Change the tracked and silenced values separately. Collect the reads to inspect the dependency count and returned result.

Usage

Collecting Refs

To collect refs using collectRefs, you provide an action function that performs some logic involving refs. The function will execute within a scope where the refs are collected, and you can access the collected refs along with the result of the action.

import { collectRefs, ref } from 'regor'

const myRef1 = ref(5)
const myRef2 = ref('Hello')

const { value, refs } = collectRefs(() => {
  console.log(myRef1.value)
  myRef2.value = 'World'
})

console.log(value) // Outputs undefined (result of the action)
console.log(refs) // Outputs an array containing myRef1 and myRef2

Parameters

  • action: A function that performs some logic and may involve reactive refs. The function is executed within a scope where the refs are collected.

Return Value

  • The collectRefs function returns an object with two properties:
    • value: The result of the action function.
    • refs: An array containing the collected refs used within the action function.

Example

import { collectRefs, ref } from 'regor'

const myRef1 = ref(5)
const myRef2 = ref('Hello')

const { value, refs } = collectRefs(() => {
  console.log(myRef1.value)
  myRef2.value = 'World'
})

console.log(value) // Outputs undefined (result of the action)
console.log(refs) // Outputs an array containing myRef1 and myRef2
Collection is a snapshot of an action

collectRefs reports dependencies read during that invocation. It does not create a subscription by itself.

See Also

Related APIs and guides Continue with the references connected to collectRefs.

Back to the API list