{{Announce|Updated with Version 10:}} Renamed from ''Jobs Module'' to ''Job Module''.
This [[Module Library|XQuery Module]] provides functions for organizing scheduled, queued, running and cached jobs. Jobs can be commands, queries, client or HTTP requests.
=Services=
A job can be registered as ''service'' by supplying the {{Code|service}} option to {{Function|Jobs|jobsjob:eval}}:
<syntaxhighlight lang="xquery">
(: register job as service; will be run every day at 1 am :)
There are cases in which a client does not, or cannot, wait until a request is fully processed. The client may be a browser, which sends an HTTP request to the server in order to start another time-consuming query job. The functions in this section allow you to register a new query job from a running query. Jobs can be executed immediately (i.e., as soon as the [[Transaction Management#Concurrency Control|Concurrency Control]] allows it) or scheduled for repeated execution. Each registered job gets a job id, and the id can be used to retrieve a query result, stop a job, or wait for its termination.
==jobsjob:eval==
{| width='100%'
|-
| width='120' | '''Signatures'''
|{{Func|jobsjob:eval|$query as xs:anyAtomicItem|xs:string}}<br />{{Func|jobsjob:eval|$query as xs:anyAtomicItem, $bindings as map(*)?|xs:string}}<br />{{Func|jobsjob:eval|$query as xs:anyAtomicItem, $bindings as map(*)?, $options as map(*)?|xs:string}}<br />
|-
| '''Summary'''
|Schedules the evaluation of the supplied {{Code|$query}} ({{Code|xs:string}}, or of type {{Code|xs:anyURI}}, pointing to a resource), and returns a query id. The query will be queued, and the result will optionally be cached. Queries can be updating. Variables and the context value can be declared via {{Code|$bindings}} (see [[XQuery Module#xquery:eval|xquery:eval]] for more details). The following {{Code|$options}} can be supplied:
* {{Code|cache}}: indicates if the query result will be cached or ignored (default: <code>false</code>):
** The result will be cached in main-memory until it is fetched via [[#jobsjob:result|jobsjob:result]], or until {{Option|CACHETIMEOUT}} is exceeded.
** If the query raises an error, it will be cached and returned instead.
* {{Code|start}}: a dayTimeDuration, time, dateTime or integer can be specified to delay the execution of the query:
| '''Examples'''
|
* Cache query result. The returned id can be used to pick up the result with [[#jobsjob:result|jobsjob:result]]:
<syntaxhighlight lang="xquery">
jobsjob:eval("1+3", (), map { 'cache': true() })
</syntaxhighlight>
* A happy birthday mail will be sent at the given date:
declare %rest:path('/stop-scheduling/{$id}') function local:stop($id) {
jobsjob:stop($id)
};
</syntaxhighlight>
* Query execution is scheduled for every second, and for 10 seconds in total. As the query itself will take 1.5 seconds, it will only be executed every second time:
* The query in the specified file will be evaluated once:
<syntaxhighlight lang="xquery">
jobsjob:eval(xs:anyURI('cleanup.xq'))
</syntaxhighlight>
* The following expression, if stored in a file, will be evaluated every 5 seconds:
<syntaxhighlight lang="xquery">
jobsjob:eval(
static-base-uri(),
map { },
|}
==jobsjob:result==
{| width='100%'
|-
| width='120' | '''Signatures'''
|{{Func|jobsjob:result|$id as xs:string|item()*}}
|-
| '''Summary'''
<syntaxhighlight lang="xquery">
declare %rest:path('/result/{$id}') function local:result($id) {
jobsjob:result($id)
};
</syntaxhighlight>
* The following query demonstrates how the results of an executed query can be returned within the same query (see below why you should avoid this pattern in practice):
<syntaxhighlight lang="xquery">
let $query := jobsjob:eval('(1 to 10000000)[. = 1]', map { }, map { 'cache': true() })
return (
jobsjob:wait($query), jobsjob:result($query)
)
</syntaxhighlight>
|}
==jobsjob:stop==
{| width='100%'
|-
| width='120' | '''Signatures'''
|{{Func|jobsjob:stop|$id as xs:string|empty-sequence()}}
|-
| '''Summary'''
|-
| '''Examples'''
| <code>jobsjob:list()[. != jobsjob:current()] ! jobsjob:stop(.)</code> stops and discards all jobs except for the current one.
|}
==jobsjob:wait==
{| width='100%'
|-
| width='120' | '''Signatures'''
|{{Func|jobsjob:wait|$id as xs:string|empty-sequence()}}
|-
| '''Summary'''
=Listing Jobs=
==jobsjob:current==
{| width='100%'
|-
| width='120' | '''Signatures'''
|{{Func|jobsjob:current||xs:string}}
|-
| '''Summary'''
|}
==jobsjob:list==
{| width='100%'
|-
| width='120' | '''Signatures'''
|{{Func|jobsjob:list||xs:string*}}
|-
| '''Summary'''
|-
| '''Examples'''
| <code>jobsjob:list()</code> returns the same job id as {{Function|Jobs|jobsjob:current}} if no other job is registered.
|}
==jobsjob:list-details==
{| width='100%'
|-
| width='120' | '''Signatures'''
|{{Func|jobsjob:list-details||element(job)*}}<br/>{{Func|jobsjob:list-details|$id as xs:string|element(job)*}}
|-
| '''Summary'''
|-
| '''Examples'''
| <code>jobsjob:list-details()</code> returns information on the currently running job and possibly others: