Get summary data with or without details by running a report synchronously or
asynchronously through the API. When you run a report, the API returns data
for the same number of records that are available when the report is run in
the Salesforce user interface. Include the filters
argument in your
request to get specific results on the fly by passing dynamic filters,
groupings, and aggregates in the report metadata. Finally, you may want to
use sf_run_report
.
Usage
sf_execute_report(
report_id,
async = FALSE,
include_details = TRUE,
labels = TRUE,
guess_types = TRUE,
bind_using_character_cols = deprecated(),
as_tbl = TRUE,
report_metadata = NULL,
verbose = FALSE
)
Arguments
- report_id
character
; the Salesforce Id assigned to a created analytics report. It will start with"00O"
.- async
logical
; an indicator, by default set toTRUE
, which executes the report asynchronously. If executed asynchronously, this function will return a list of attributes of the created report instance. The results can be pulled down by providing the report id and instance id to the functionsf_get_report_instance_results
. Refer to the details of the documentation on why executing a report asynchronously is preferred.- include_details
logical
; an indicator applying to a synchronous indicating whether the run should return summary data with details.- labels
logical
; an indicator of whether the returned data should be the label (i.e. formatted value) or the actual value. By default, the labels are returned because these are what appear in the Salesforce dashboard and more closely align with the column names. For example, "Account.Name" label may be"Account B"
and the value0016A0000035mJEQAY
. The former (label) more accurately reflects the "Account.Name".- guess_types
logical
; indicating whether or not to usecol_guess()
to try and cast the data returned in the recordset. IfTRUE
thencol_guess()
is used along withanytime()
andanydate()
. IfFALSE
then all fields will be returned as character. SpecifyingFALSE
helpful when guessing the column data type will result in NA values and you would like to return the results as strings and then cast in your script according to your unique specifications.- bind_using_character_cols
logical
; an indicator of whether to cast the data to all character columns to ensure thatbind_rows
does not fail because two paginated recordsets have differing datatypes for the same column. Set this toTRUE
rarely, typically only when having this set toFALSE
returns an error or you want all columns in the data to be character.- as_tbl
logical
; an indicator of whether to convert the parsed JSON into atbl_df
.- report_metadata
list
; alist
with one element named"reportMetadata"
having additional list elements underneath. All possible elements ofreportMetadata
are documented HERE, but you will most commonly only need to specify the following 3 elements to filter or query the results of an existing report:- reportFormat
A
character
specifying the format of the report with possible values:"TABULAR"
,"SUMMARY"
,"MATRIX"
, or"MULTI_BLOCK"
.- reportBooleanFilter
A
character
denoting how the individuals filters specified inreportFilters
should be combined. For example,"(1OR4)AND2AND3"
.
- reportFilters
A
list
of reportFilter specifications. Each must be a list with 3 elements: 1)column
, 2)operator
, and 3)value
. You can find out how certain field types can be filtered by reviewing the results ofsf_list_report_filter_operators
.
- verbose
logical
; an indicator of whether to print additional detail for each API call, which is useful for debugging. More specifically, when set toTRUE
the URL, header, and body will be printed for each request, along with additional diagnostic information where available.
Value
tbl_df
by default, but a list
when as_tbl=FALSE
,
which means that the content from the API is converted from JSON to a list
with no other post-processing.
Details
Run a report synchronously if you expect it to finish running quickly. Otherwise, we recommend that you run reports through the API asynchronously for these reasons:
Long running reports have a lower risk of reaching the timeout limit when run asynchronously.
The 2-minute overall Salesforce API timeout limit doesn’t apply to asynchronous runs.
The Salesforce Reports and Dashboards REST API can handle a higher number of asynchronous run requests at a time.
Since the results of an asynchronously run report are stored for a 24-hr rolling period, they’re available for recurring access.
Before you filter a report, it helpful to check the following properties in the metadata that tell you if a field can be filtered, the values and criteria you can filter by, and filters that already exist in the report:
filterable
filterValues
dataTypeFilterOperatorMap
reportFilters
See also
Other Report functions:
sf_copy_report()
,
sf_create_report()
,
sf_delete_report()
,
sf_describe_report()
,
sf_describe_report_type()
,
sf_list_report_fields()
,
sf_list_report_filter_operators()
,
sf_list_report_types()
,
sf_list_reports()
,
sf_query_report()
,
sf_run_report()
,
sf_update_report()
Examples
if (FALSE) { # \dontrun{
# first, get the Id of a report in your Org
all_reports <- sf_query("SELECT Id, Name FROM Report")
this_report_id <- all_reports$Id[1]
# then execute a synchronous report that will wait for the results
results <- sf_execute_report(this_report_id)
# alternatively, you can execute an async report and then grab its results when done
# - The benefit of an async report is that the results will be stored for up to
# 24 hours for faster recall, if needed
results <- sf_execute_report(this_report_id, async=TRUE)
# check if completed and proceed if the status is "Success"
instance_list <- sf_list_report_instances(report_id)
instance_status <- instance_list[[which(instance_list$id == results$id), "status"]]
if(instance_status == "Success"){
results <- sf_get_report_instance_results(report_id, results$id)
}
# Note: For more complex execution use the report_metadata argument.
# This can be done by building the list from scratch based on Salesforce
# documentation (not recommended) or pulling down the existing reportMetadata
# property of the report and modifying the list slightly (recommended).
# In addition, for relatively simple changes, you can leverage the convenience
# function sf_report_wrapper() which makes it easier to retrieve report results
report_details <- sf_describe_report(this_report_id)
report_metadata <- list(reportMetadata = report_details$reportMetadata)
report_metadata$reportMetadata$showGrandTotal <- FALSE
report_metadata$reportMetadata$showSubtotals <- FALSE
fields <- sf_execute_report(this_report_id,
report_metadata = report_metadata)
} # }