useDoc
useDoc fetches a single Frappe document and keeps it reactive. Documents are shared across every useDoc call for the same doctype/name — two components rendering the same document read the same cached copy and update together.
Basic example
<template>
<div v-if="todo.doc">
{{ todo.doc.description }}
</div>
<Button @click="todo.setValue.submit({ status: 'Closed' })"> Close </Button>
</template>
<script setup>
import { useDoc } from 'frappe-ui'
const todo = useDoc({
doctype: 'ToDo',
name: 'TODO-0001',
})
</script>Reactive name
name accepts a Ref or a getter, so useDoc can follow a document that changes — e.g. a name coming from the route:
<script setup>
import { useRoute } from 'vue-router'
import { useDoc } from 'frappe-ui'
const route = useRoute()
const todo = useDoc({
doctype: 'ToDo',
name: () => route.params.name,
})
</script>The request refires automatically whenever name resolves to a new value.
Document methods
methods exposes whitelisted document methods (doc.run_method(...) on the server) as their own useCall-shaped members:
<script setup>
import { useDoc } from 'frappe-ui'
const todo = useDoc({
doctype: 'ToDo',
name: 'TODO-0001',
methods: {
// shorthand: the server method name
markDone: 'mark_done',
// full options, same shape as useCall (minus url/method/immediate)
reassign: {
name: 'reassign',
onSuccess: () => console.log('reassigned'),
},
},
})
todo.markDone.submit()
todo.reassign.submit({ allocated_to: '[email protected]' })
</script>Options
doctype— the DocType of the document.name— the document's name. Accepts a plain string, aRef<string>or a getter for a reactively-changing document.baseUrl— prefix prepended to the generated request URLs.url— overrides the default/api/v2/document/<doctype>/<name>GET URL.methods— a map of member name to either a server method name (string), or auseCalloptions object (minusurlandbaseUrl) plus a requirednamenaming the server method. Defaults tomethod: 'POST'andimmediate: false; both can be overridden per method. Each becomes auseCall-shaped member on the returned object.immediate— fire the initial GET automatically oncenameresolves. Defaults totrue.staleOnError— whentrue, a failed refetch keeps showing the last knowndocinstead of clearing it. Defaults tofalse.transform— receives the fetched document (withdoctypeset) and returns the valuedocshould hold.
Return value
doc— the document, ornullbefore it has been fetched.error— the error from the last fetch, ornull.loading(aliasisFetching) —truewhile the document is being fetched.isFinished—trueonce the current fetch has settled, either way.canAbort—truewhile a fetch that can still be aborted is in flight.aborted—trueif the last fetch was aborted.execute()(aliasesfetch(),reload()) — refetches the document. Returns a promise that resolves with the response, or rejects if the fetch fails.abort()— aborts the in-flight fetch.setValue— auseCall-shaped member;setValue.submit(values)PUTs a partial update and writes the response back intodoc.delete— auseCall-shaped member;delete.submit()deletes the document and clears it from everyuseDoc/useListreading it.onSuccess(callback)— registers a callback that runs with the document every time thisuseDoccall's own fetch (the initial load, or areload()) succeeds. Returns an unsubscribe function.- one member per entry in
methods, each auseCall-shaped object.
Shared cache
Every useDoc (and matching row in a useList) for the same doctype/name reads from one shared, reactive store. Calling setValue or delete from any of them updates doc everywhere that document is being read, and a document written by useNewDoc is immediately readable through useDoc under its returned name.