Developer guide
OData & analytics
Explore Workroomly’s read-only OData v4 service, authorized datasets and Power BI connection setup.
On this page
What OData gives you
OData exposes business data as discoverable entity sets with a common query syntax. Use it for reporting, scheduled exports and analytics without writing a separate REST integration for each dataset.
Workroomly implements a read-only OData v4 subset at https://api.workroomly.com/odata/. Use the endpoint shown in Settings → Developers → Data Access if your application uses a different environment. Data Access keys determine the workroom, modules and permitted subspaces.
Authenticate and discover
Create a Data Access key with explicit modules and, for CRM/Board/Desk, selected subspaces. Integration keys and MCP OAuth tokens do not authenticate this service. Never send your Workroomly login password.
Use Bearer authentication in code. In a client’s Basic authentication dialog, use Workroomly as the username and the full Data Access key as the password. Use HTTPS.
# Discover only the datasets permitted by this key.
curl --fail-with-body --silent --show-error \
'https://api.workroomly.com/odata/' \
-H "Authorization: Bearer $WORKROOMLY_API_KEY"
# Discover field names, EDM types and nullability.
curl --fail-with-body --silent --show-error \
'https://api.workroomly.com/odata/$metadata' \
-H "Authorization: Bearer $WORKROOMLY_API_KEY"The service root returns an @odata.context URL and a value array of entity-set names and URLs. The metadata document is XML. Both are filtered by your key’s module permissions. Data rows remain restricted to its authorized subspaces and the dataset’s visibility rules.
Query your data
This example selects a few CRM contact columns, filters by modification date, sorts deterministically and requests at most 50 rows. The single-quoted query arguments keep Bash from expanding the dollar signs.
curl --fail-with-body --silent --show-error --get \
'https://api.workroomly.com/odata/crm_contacts' \
-H "Authorization: Bearer $WORKROOMLY_API_KEY" \
--data-urlencode '$select=id,name,email,updated_at' \
--data-urlencode '$filter=updated_at ge 2026-01-01T00:00:00Z' \
--data-urlencode '$orderby=updated_at asc,id asc' \
--data-urlencode '$top=50' \
--data-urlencode '$count=true'| Query option | Supported behavior |
|---|---|
| $select | Choose exposed columns; * selects all exposed columns. |
| $filter | Field comparisons eq/ne/gt/ge/lt/le where the field supports them; and/or/not, parentheses and supported string functions. |
| $orderby | Allowed fields with asc or desc; id is added as a tie-breaker. |
| $top | Non-negative total row cap; 0 returns an empty collection. |
| $skip | Non-negative direct offset, capped at 10,000. Prefer continuation links. |
| $count=true | Include @odata.count. Counting is skipped unless requested. |
| $format | JSON only; supports IEEE754Compatible for exact numeric strings. |
| $skiptoken | Server-issued continuation token. Follow nextLink instead of constructing it. |
String filters can use contains, startswith and endswith on supported string fields. Escape an apostrophe by doubling it inside an OData string literal. Unsupported expressions fail instead of being silently ignored.
Single-record URLs use /odata/crm_contacts(<record-UUID>) with optional $select/$format. /odata/crm_contacts/$count returns a plain-text count and supports only $filter/$format.
Protocol limits: $expand, $batch, $search, $apply, $delta, navigation properties, arithmetic and lambda expressions are not implemented. Relationships are exposed as selected scalar IDs/labels; join them in your reporting model. POST/PUT/PATCH/DELETE return a read-only error.
Pagination and query limits
Collections return value and may include @odata.nextLink. Follow that URL unchanged with the same credential until no nextLink remains. It binds the query, key, permissions and position; editing query options, changing keys or altering scopes invalidates the continuation. Tokens expire after 24 hours, so restart the query if one expires.
The default page size is 100, constrained by the deployment’s read limit. The default workroom concurrency limit is four requests and the PostgreSQL statement timeout is 15 seconds. Deployments can tune these values. Filters are limited to 2,048 characters and bounded expression depth. Use narrower fields/filters and avoid parallel full-dataset scans.
Continuation uses a timestamp cutoff and stable ordering; it is not a durable historical snapshot. Rows modified or removed while an export runs may be omitted. Reconcile mutable data on later refreshes.
A collection’s count appears only when requested. For large integer/decimal values, request Accept: application/json;IEEE754Compatible=true to receive exact numeric strings and avoid JavaScript precision loss. Successful response bytes consume the shared workroom Data Transfer allowance; failed requests and HEAD responses do not consume response-byte allowance.
Connect Power BI Desktop
Use the OData Feed connector in Power BI Desktop with OData v4 and your Data Access key.
- Copy the OData endpoint from Settings → Developers → Data Access. Create a dedicated Data Access key for reporting.
- In Power BI Desktop, choose Get data → OData feed and enter the service root, including its trailing slash.
- Choose Basic authentication. Enter Workroomly as the username and the Data Access key as the password. Apply it to that service root.
- In Navigator, select an authorized dataset. Choose Transform Data to filter/select columns, or Load.
- Refresh and confirm that the expected workroom records appear. An empty table may reflect the key’s scopes or dataset visibility rules.
Microsoft documents the connector flow in OData Feed. To replace a rotated key, use File → Options and settings → Data source settings → Edit Permissions → Credentials → Edit, then refresh. See desktop authentication settings.
For published reports, configure Power BI service credentials and scheduled refresh separately. Follow Microsoft’s gateway requirements for Basic authentication in online connections, then run a refresh to confirm your report can retrieve data. Keep the key in the connector’s credential store, outside M query source.
Available datasets
Browse 32 datasets for your reporting workflows. Your service root lists the datasets available to your key. Expand a dataset for its columns. Files expose shared metadata; Goals expose workroom-visible trees; Pages expose public metadata without submitted form values.
assets_assetsAsset
Permission: assets.* · REST resource: assets.asset
Selectable columns
idasset_numbernamecategory_namelifecycle_stateoperational_statecustody_statefinancial_stateconditionmanufacturermodel_nameserial_numberacquisition_methodacquisition_dateacquisition_costincidental_costcurrencyvendor_namepurchase_order_reflocation_namedepartmentsource_typecreated_atupdated_atInspect /odata/$metadata with your key for exact EDM types and nullability. Use only exposed sortable/filterable fields; unsupported queries return an error.
assets_incidentsAssets Incidents
Permission: assets.* · REST resource: assets.incident
Selectable columns
idasset_idincident_numberincident_typeseverityreported_atstatuscondition_beforecondition_afterdamage_cost_estimatecurrencyclosed_atcreated_atupdated_atInspect /odata/$metadata with your key for exact EDM types and nullability. Use only exposed sortable/filterable fields; unsupported queries return an error.
assets_maintenance_work_ordersAssets Maintenance Work Orders
Permission: assets.* · REST resource: assets.maintenance_work_order
Selectable columns
idasset_idrequest_idwork_order_numbermaintenance_typeprioritystatusscheduled_datecompleted_dateestimated_costactual_costdowntime_hourscondition_afternext_maintenance_datefinance_journal_idcreated_atupdated_atInspect /odata/$metadata with your key for exact EDM types and nullability. Use only exposed sortable/filterable fields; unsupported queries return an error.
board_epicsBoard Epic
Permission: board.* · REST resource: board.epic
Rows are limited to the subspaces selected on your Data Access key.
Selectable columns
idnamedescriptionstatusstatus_keyboard_keyproject_namesprint_nameassignee_emailsstart_dateend_datecreated_atupdated_atInspect /odata/$metadata with your key for exact EDM types and nullability. Use only exposed sortable/filterable fields; unsupported queries return an error.
board_projectsBoard Project
Permission: board.* · REST resource: board.project
Rows are limited to the subspaces selected on your Data Access key.
Selectable columns
idnamedescriptionstatusstatus_keyboard_keyowner_emailassignee_emailsstart_dateend_datecreated_atupdated_atInspect /odata/$metadata with your key for exact EDM types and nullability. Use only exposed sortable/filterable fields; unsupported queries return an error.
board_sprintsBoard Sprint
Permission: board.* · REST resource: board.sprint
Rows are limited to the subspaces selected on your Data Access key.
Selectable columns
idnamedescriptionstatusstatus_keyboard_keystart_dateend_dateis_activecreated_atupdated_atInspect /odata/$metadata with your key for exact EDM types and nullability. Use only exposed sortable/filterable fields; unsupported queries return an error.
board_tasksBoard Task
Permission: board.* · REST resource: board.task
Rows are limited to the subspaces selected on your Data Access key.
Selectable columns
idtitledescriptionstatusstatus_keyboard_keydue_dateplanned_start_dateestimated_hourslogged_hoursassignee_emailscreated_atupdated_atInspect /odata/$metadata with your key for exact EDM types and nullability. Use only exposed sortable/filterable fields; unsupported queries return an error.
crm_accountsCRM Account
Permission: crm.* · REST resource: crm.account
Rows are limited to the subspaces selected on your Data Access key.
Selectable columns
idnameindustrysegmentregionhealth_statusowner_emailcrm_space_keywebsitecreated_atupdated_atInspect /odata/$metadata with your key for exact EDM types and nullability. Use only exposed sortable/filterable fields; unsupported queries return an error.
crm_contactsCRM Contact
Permission: crm.* · REST resource: crm.contact
Rows are limited to the subspaces selected on your Data Access key.
Selectable columns
idnamefirst_namelast_nameemailtitlephonelifecycle_statusaccount_nameaccount_idowner_emailcrm_space_keycreated_atupdated_atInspect /odata/$metadata with your key for exact EDM types and nullability. Use only exposed sortable/filterable fields; unsupported queries return an error.
crm_dealsCRM Deal
Permission: crm.* · REST resource: crm.deal
Rows are limited to the subspaces selected on your Data Access key.
Selectable columns
idnamestagestatusamountcurrencyaccount_nameaccount_idprimary_contact_nameprimary_contact_idconverted_from_lead_idowner_emailcrm_space_keyclose_datecreated_atupdated_atInspect /odata/$metadata with your key for exact EDM types and nullability. Use only exposed sortable/filterable fields; unsupported queries return an error.
crm_leadsCRM Lead
Permission: crm.* · REST resource: crm.lead
Rows are limited to the subspaces selected on your Data Access key.
Selectable columns
idnamefull_nameemailcompany_namephonestatusstagesourceowner_emailcrm_space_keyaccount_nameaccount_idcontact_idis_convertedconverted_to_deal_idcreated_atupdated_atInspect /odata/$metadata with your key for exact EDM types and nullability. Use only exposed sortable/filterable fields; unsupported queries return an error.
crm_notesCRM Note
Permission: crm.* · REST resource: crm.note
Rows are limited to the subspaces selected on your Data Access key.
Selectable columns
idsubjectnoteentity_typeentity_idcrm_space_keyagent_emailoccurred_atcreated_atInspect /odata/$metadata with your key for exact EDM types and nullability. Use only exposed sortable/filterable fields; unsupported queries return an error.
crm_prospectsCRM Prospect
Permission: crm.* · REST resource: crm.prospect
Rows are limited to the subspaces selected on your Data Access key.
Selectable columns
idnameemailphonestatussourceowner_emailcrm_space_keycompany_namecreated_atupdated_atlast_activity_atnext_action_atInspect /odata/$metadata with your key for exact EDM types and nullability. Use only exposed sortable/filterable fields; unsupported queries return an error.
desk_commentsDesk Comment
Permission: desk.* · REST resource: desk.comment
Rows are limited to the subspaces selected on your Data Access key.
Selectable columns
idbodyauthor_typesourceticket_idreceived_atcreated_atInspect /odata/$metadata with your key for exact EDM types and nullability. Use only exposed sortable/filterable fields; unsupported queries return an error.
desk_ticketsDesk Ticket
Permission: desk.* · REST resource: desk.ticket
Rows are limited to the subspaces selected on your Data Access key.
Selectable columns
idtitlesummaryrequester_namerequester_emailprioritystatusstatus_keychanneldesk_keyticket_referenceowner_emailcreated_atupdated_atclosed_atInspect /odata/$metadata with your key for exact EDM types and nullability. Use only exposed sortable/filterable fields; unsupported queries return an error.
files_filesVault File
Permission: files.* · REST resource: files.file
Selectable columns
idnamefile_typesizecreated_by_emailcreated_atupdated_atfolder_idInspect /odata/$metadata with your key for exact EDM types and nullability. Use only exposed sortable/filterable fields; unsupported queries return an error.
files_foldersVault Folder
Permission: files.* · REST resource: files.folder
Selectable columns
idnamecreated_by_emailcreated_atparent_idInspect /odata/$metadata with your key for exact EDM types and nullability. Use only exposed sortable/filterable fields; unsupported queries return an error.
finance_customer_paymentsFinance Customer Payments
Permission: finance.* · REST resource: finance.customer_payment
Selectable columns
idpayment_numbercustomer_idcash_account_idpayment_dateamountunapplied_amountfunctional_amountcurrencyexchange_ratestatuspayment_methodjournal_idreversed_by_payment_idcompleted_atcreated_atupdated_atInspect /odata/$metadata with your key for exact EDM types and nullability. Use only exposed sortable/filterable fields; unsupported queries return an error.
finance_invoicesFinance Invoice
Permission: finance.* · REST resource: finance.invoice
Selectable columns
idinvoice_numberclient_namecustomer_idcustomer_namestatuscurrencyamountsubtotalvat_amountdiscount_amountissue_datedue_datenotescreated_by_emailcreated_atupdated_atInspect /odata/$metadata with your key for exact EDM types and nullability. Use only exposed sortable/filterable fields; unsupported queries return an error.
finance_invoice_itemsFinance Invoice Line
Permission: finance.* · REST resource: finance.invoice_item
Selectable columns
idinvoice_iddescriptionquantityunit_pricediscount_amountrecognition_methodcreated_atupdated_atInspect /odata/$metadata with your key for exact EDM types and nullability. Use only exposed sortable/filterable fields; unsupported queries return an error.
finance_journal_entriesFinance Journal Entries
Permission: finance.* · REST resource: finance.journal_entry
Selectable columns
idnumberentry_dateperiod_idkindstatusnarrationtransaction_currencysource_typesource_idreversal_of_idapproved_atposted_atcreated_atupdated_atInspect /odata/$metadata with your key for exact EDM types and nullability. Use only exposed sortable/filterable fields; unsupported queries return an error.
finance_journal_linesFinance Journal Lines
Permission: finance.* · REST resource: finance.journal_line
Selectable columns
idjournal_idsequenceaccount_iddebitcredittransaction_amounttransaction_currencyexchange_ratedescriptiondepartment_idproject_idcustomer_idvendor_idcreated_atupdated_atInspect /odata/$metadata with your key for exact EDM types and nullability. Use only exposed sortable/filterable fields; unsupported queries return an error.
finance_ledger_accountsFinance Ledger Accounts
Permission: finance.* · REST resource: finance.ledger_account
Selectable columns
idcodenameaccount_typesubtypenormal_balanceparent_idcontrol_purposeis_systemis_activecurrencycreated_atupdated_atInspect /odata/$metadata with your key for exact EDM types and nullability. Use only exposed sortable/filterable fields; unsupported queries return an error.
finance_vendor_paymentsFinance Vendor Payments
Permission: finance.* · REST resource: finance.vendor_payment
Selectable columns
idpayment_numbervendor_idcash_account_idpayment_dateamountunapplied_amountfunctional_amountcurrencyexchange_ratestatuspayment_methodjournal_idreversed_by_payment_idcompleted_atcreated_atupdated_atInspect /odata/$metadata with your key for exact EDM types and nullability. Use only exposed sortable/filterable fields; unsupported queries return an error.
goals_itemsGoals Items
Permission: goals.* · REST resource: goals.item
Selectable columns
idtitletypeparent_idteamyearquarterstart_dateend_datestatusconfidencemetricunittargetprogresscurrentcreated_atupdated_atInspect /odata/$metadata with your key for exact EDM types and nullability. Use only exposed sortable/filterable fields; unsupported queries return an error.
pages_pagesPages Pages
Permission: pages.* · REST resource: pages.page
Selectable columns
idnameslugtemplate_categorystatuspublished_atcreated_atupdated_atInspect /odata/$metadata with your key for exact EDM types and nullability. Use only exposed sortable/filterable fields; unsupported queries return an error.
pages_submissionsPages Submissions
Permission: pages.* · REST resource: pages.submission
Selectable columns
idpage_idform_block_idstatusoccurred_atprocessed_atcreated_atupdated_atInspect /odata/$metadata with your key for exact EDM types and nullability. Use only exposed sortable/filterable fields; unsupported queries return an error.
people_departmentsPeople Department
Permission: people.* · REST resource: people.department
Selectable columns
idnamedescriptionparent_department_idparent_department_namelead_employee_idcreated_atupdated_atInspect /odata/$metadata with your key for exact EDM types and nullability. Use only exposed sortable/filterable fields; unsupported queries return an error.
people_employeesPeople Employee
Permission: people.* · REST resource: people.employee
Selectable columns
idfull_namefirst_namelast_nameemaildepartment_iddepartment_namemanager_idemployment_typestatusjoin_datelocationteamcreated_atupdated_atInspect /odata/$metadata with your key for exact EDM types and nullability. Use only exposed sortable/filterable fields; unsupported queries return an error.
procure_purchase_ordersProcure Purchase Orders
Permission: procure.* · REST resource: procure.purchase_order
Selectable columns
idvendor_idpo_numbercurrencyapproval_statusissue_statusreceipt_statusbilling_statusclosure_statuspurchase_request_idcontract_idamountdelivery_datestatusdepartmentcreated_atupdated_atInspect /odata/$metadata with your key for exact EDM types and nullability. Use only exposed sortable/filterable fields; unsupported queries return an error.
procure_purchase_requestsProcure Purchase Requests
Permission: procure.* · REST resource: procure.purchase_request
Selectable columns
idtitlerequisition_numbercurrencyapproval_statusdepartment_idvendor_idcategoryneed_by_dateprocurement_stageselected_routecompleted_atclosed_atstatusamountprioritysubmitted_atcreated_atupdated_atInspect /odata/$metadata with your key for exact EDM types and nullability. Use only exposed sortable/filterable fields; unsupported queries return an error.
procure_vendorsProcure Supplier
Permission: procure.* · REST resource: procure.vendor
Selectable columns
idnamesupplier_numberlegal_namecategorystatuscountrycurrencyratinglifetime_spendperformance_scoreactive_contractscontact_emailis_activecreated_atupdated_atInspect /odata/$metadata with your key for exact EDM types and nullability. Use only exposed sortable/filterable fields; unsupported queries return an error.
Troubleshoot a connection
If authentication fails, check that the credential’s purpose is Data Access, that it is active, and that you copied the entire key. Remove an old cached credential in your analytics client after rotation. Check module/subspace grants, Developer-tools availability and Data Transfer balance for a 403.
For odata_option_unsupported, remove unsupported options such as $expand. For odata_invalid_skiptoken, restart from the original collection URL. For a timeout, reduce columns and narrow filters. For rate/concurrency limits, reduce parallel refreshes. Use the full error guide and retain X-Request-ID.
Keep the request ID, endpoint and time of the failure. Remove credentials and private records before contacting Workroomly.