Jobs: recurrence workflows and lists
Read the CRM2 mapped recurrence table or an unpaged list using its screen filters
/a/JobRecurrences_getDataTable
Read the CRM2 mapped recurrence table or an unpaged list using its screen filters.
When to use this endpoint
Use for Recurring Jobs table rows and the filtered ID discovery step before CRM2 export. This is not the positional CRM1 getDT response.
Authentication and permissions
Authenticate with signed API-key fields or a logged-in CRM session; all data is tenant-scoped.
For non-client-administrators, pageMain departmentBasedFilter restricts customer targets to customers in the user’s departments and their owned assets. accountManagerBasedFilter restricts to customers managed by the acting user and their owned assets. When both are enabled, the customer sets intersect; an empty set yields no rows. Administrators bypass these two filters.
These visibility filters are specific to this mapped table. They are not repeated by list, getRequestedDetails, contract lookups or the legacy table. No Job edit-bit check is needed to read.
Parameters
| Parameter | Type | Required | Description |
|---|---|---|---|
fields | Native string array | Yes | Mapped names, not a JSON string; unknown names ignored, id always included. Picker dependencies are selected internally. |
isTable | Integer-like flag | No | Default table mode. intval(value)=0 disables paging/count envelope. |
start, length, draw | Integer-like scalars | No | Table defaults 0,10,0. No endpoint range/upper-bound validation. Unpaged mode ignores these. |
limit | Integer-like scalar | No | In isTable=0 mode only, positive value limits rows; default 0 means unlimited. |
orderBy, orderDesc | Strings | Together | Mapped ordering field and validated asc/desc direction, normalized to lowercase. Unknown fields fall back to the first usable requested field/id. |
order | DataTables order array | No | Fallback table ordering: first column index minus 1, clamped at 0, into fields. Exact desc only. Without explicit order, first usable requested field ascending. No guaranteed ID tiebreaker. |
Mapped field filters | Scalars or native arrays | No | Same mapped keys listed below. Numeric scalar exact match/array IN; quoted scalar case-insensitive substring/array exact IN. customer={id,type} or identity array; user={id}. |
userID | Native picker array | No | Wrapper special case: first element’s id only; an empty array or scalar is replaced with blank, which generic numeric filtering coerces to 0. Use user={id} for a scalar picker identity. |
searchField, searchValue | String/array, string | No | Generic mapped substring search; omitted field searches All. Special scalar searchField=contractsFilter searches contract names, customer searches joined customer/asset names. These special branches bypass normal generic search handling. |
customerParent | Native ID array | No | Immediate parent customer IDs; matches customer targets only, not assets. Empty/coerced-zero list forces no matches. |
withExpiryDate | Native single-element array | No | [1] requires eDate NOT NULL, [0] requires NULL. Two/other-sized arrays impose no expiry-presence filter. Zero-date sentinels are non-NULL. |
isCompleted | Native single-element array | No | Single [1] selects expiry on or before server today; otherwise strictly after today. NULL expiry matches neither. This is expiry, not child-job completion. |
invoice | Integer-like scalar | No | Exact linked invoice recurrence ID in metadata. |
contractsFilter | Native ID array | No | Native contract ID array. Finds non-deleted linked jobs and matches their complete cached CSV IDs, with whitespace/leading-zero tolerance. Empty/no-job selections force no matches. |
customer, childJobAndAsset | Identity object/array and option array | No | Expansion requires both. For customer targets: 0 adds immediate child customers; 1 adds directly owned or customer-located assets; 2 first clears accumulated targets then adds those assets. For asset-only targets, 10 adds immediately contained assets. Mixed selections take the customer branch; option order matters. |
hasFiles | Native option array | No | Single [0] means EXISTS attached file (type_enum=5), [1] means NOT EXISTS. The values are counterintuitive. No deleted-file condition is added. |
referenceDate, dateFrom, dateTo | Mapped date name, day offsets | No | Date range is enabled only for a valid referenceDate with both offsets. Integers are relative to tenant-local today; date fields use inclusive days, datetime fields full-day bounds. |
offsetFrom, offsetTo | Native {hour,minute} objects | No | Optional datetime-bound adjustments: hour is negated, minute added. Date-only reference fields ignore these. |
timeRangeFrom, timeRangeTo | Integer-like hours | No | With a valid referenceDate, timeRangeFrom activates hour filtering; timeRangeTo alone does not. Endpoints default 0/23 and are swapped if reversed. Uses tenant SQL timezone, fallback Europe/London; offsetFrom.hour also shifts hours. |
groupBy | Native mapped-name array | No | Adds SQL GROUP BY. Counts remain record counts, not group counts; arbitrary nonaggregated projections are not a reporting guarantee. |
advanceSearch | Native condition array | No | Native mapped condition array with column, condition, value and optional andOr/special grouping. Supported comparisons: equal, contains, notEqual, greaterThan, greaterThanOrEqual, lesserThan, lesserThanOrEqual. Raw where is rejected. |
Example request
$result = FM_api('JobRecurrences_getDataTable', ['fields'=>['id','name','customer'], 'start'=>'0', 'length'=>'10', 'active'=>['1']]);
Example response
{"data":[{"id":"1042","name":"Monthly checks","customer":{"id":"101","type":"0"}}],"draw":0,"recordsTotal":"12","recordsFiltered":"1"}
Table mode returns data, draw, recordsTotal and recordsFiltered. isTable=0 returns only {"data":[...]}; order/count behavior is different. Numeric cells/counts normally remain strings. Picker backing keys are removed unless explicitly requested.
Errors and unusual responses
| Response | Condition |
|---|---|
{"error":"not logged in"} | No authenticated tenant context is available. Invalid signed credentials can be rejected by the dispatcher before the handler runs. |
{"error":"missing or invalid parameter: fields"} | No requested field array. |
{"error":"error in database query"} | Generated row query failed; invalid inputs may also produce PHP failures rather than a structured validation error. |
{"error":"unsupported raw advanced search"} | A raw where clause was supplied. |
{"error":"missing or invalid parameter: orderDesc"} | Direction is not asc/desc. |
{"error":"missing or invalid parameter: advanceSearch"} | Invalid mapped condition/value/grouping. |
Legacy application errors may be returned with HTTP 200. Check the decoded response for error, not only the HTTP status.
Behaviour and edge cases
- Mapped names:
id, name, ids, cDate, eDate, active, every, onArr, customerID, customerType, customer, nextDate, userID, user, notes, files, editedUUID, lastEdited, daysInAdvance, copyUser, copyCustRef, departmentID, formID, schedule, meta, custom, copyJobRef, createdBy, skipWeekends, metaJobType. Stored JSON fields remain encoded strings; customer/user return identity objects, not resolved display names. - No default recurrence active/deleted filter: this table is absent from DataProcessClass’s soft-delete table list. recordsTotal is the tenant table total and is not reduced by custom visibility filters; recordsFiltered applies all conditions.
- The child expansion is one level, not recursive. Customer-based expansion does not preserve a separately selected asset list when it takes the customer branch.
- Only the configured mapped table applies the described customer-based visibility filters. Do not infer equivalent authorization for all recurrence routes.
- Contract filtering matches complete positive CSV tokens, permitting whitespace/leading zeroes but not numeric substrings. Only non-deleted linked jobs are considered; no matching jobs means no sequences.
- Special customer-name search uses type-aware non-deleted customer/asset joins and SQL-mode-independent text literals. Same-numbered unrelated targets cannot match.
- Mapped query controls are validated before SQL: raw where clauses, unsafe ordering and malformed native picker/filter/advanced-search structures are rejected.
Side effects
- Read-only; does not repair membership, change targets, update edit timestamps or reconcile generation. Queries may include additional joins for mapped lookup searches.
See it in Fieldmotion
CRM1
No direct CRM1 caller found; its Recurring Jobs screen uses JobRecurrences_getDT.
CRM2
Recurring Jobs uses the shared mapped table infrastructure. moduleRecurring explicitly calls JobRecurrences_getDataTable with isTable=0, fields=[id], limit=0 and active screen filters to discover export IDs. Inspect that request before JobRecurrences_getExportData.
Related endpoints
JobRecurrence_getRequestedDetailsreads details without these table-specific visibility rules.JobRecurrences_getExportDatafetches export fields for selected IDs.