12 Tutorial API
12.1 Overview
The Tutorial API provides an interface for driving automated interactions with the RStudio IDE. The Tutorial API assumes that RStudio is hosted within an <iframe>
with the hosting page content surrounding it (e.g. in a sidebar).
The hosting <iframe>
must be connected to the DOM and have non-zero dimensions (including not having the display: none
style) when the IDE is loaded into it.
The API supports a variety of interactions with the IDE including typing console input, opening source files, opening projects, creating projects, showing help topics, and executing arbitrary R code.
This document describes the basic workings of the Tutorial API, and related settings. A simple example page is provided to demonstrate invoking the APIs.
The Tutorial API files are installed with RStudio Server in:
/usr/lib/rstudio-server/extras/tutorial
- demo.htm is an example host page
- rstudio.js is used by a hosting page to interact with the Tutorial API; always use the version of rstudio.js that came with the installed version of RStudio Server Pro and ensure it is cache-busted to prevent web browsers from using an older cached version (one option would be to rename it and reference it via that new name, e.g. rstudio001.js)
Important: These instructions, and the example page itself, assume the following regarding the domains utilized:
- The demo host page is served from domain http://localhost:8080
- The RStudio IDE is served from domain http://localhost:8787
If the IDE is being served from a different domain than http://localhost:8787 edit the demo.htm file and change all instances of http://localhost:8787 to the actual domain where the IDE is available.
12.2 Configuration
This section describes how to configure the example page, shown below. The upper-region has controls for experimenting with the Tutorial API calls, and the lower region is an <iframe>
hosting RStudio Server Pro.
12.2.1 Allow IFrame
For security reasons, RStudio Server will not load inside a browser frame (such as an IFrame) by default. You can modify this behavior by using the www-frame-origin
option. See Frame Origin for full details.
To enable the Tutorial API example page to host RStudio Server on a non-production localhost server, do the following:
/etc/rstudio/rserver.conf
www-frame-origin=http://localhost:8080
Note: if the
www-frame-origin
option is set tosame
orany
instead of a URI, you must add the following setting with the actual URI:
/etc/rstudio/rsession.conf
tutorial-api-client-origin=http://localhost:8080
12.2.2 Enable API Calls from Host Page
To enable calling the Tutorial APIs from the hosting page:
/etc/rstudio/rsession.conf
tutorial-api-enabled=1
12.2.3 Enable Callbacks from RStudio to Host Page
RStudio may optionally notify the hosting page of certain events using the JavaScript PostMessage mechanism.
The receiver is responsible for parsing, interpreting, and reacting to the value of the callbacks. Any JavaScript running in the context of the IDE IFrame could do an arbitrary SendMessage to the parent (in addition to those being generated by the RStudio IDE JavaScript). The host page should ensure the response string is valid JSON, and follows one of the patterns described in Tutorial API Callbacks.
To enable callbacks:
/etc/rstudio/rsession.conf
tutorial-api-parent-notify-enabled=1
12.2.4 Disable RStudio Server Pro Home Page
The Tutorial API cannot be used to manipulate the RStudio Server Pro Home Page. To disable the home page:
/etc/rstudio/rserver.conf
server-user-home-page=0
12.2.5 Disable Multiple Session Support
Even with the Home Page disabled, a user can still open new sessions via Session / New Session which will open a new IDE instance outside of the host page. To prevent this:
/etc/rstudio/rserver.conf
server-multiple-sessions=0
If multiple sessions are disabled, the Home Page is automatically turned off, so not necessary to include both settings.
12.2.6 Serve the Example Page
Serve the folder /usr/lib/rstudio-server/extras/tutorial
with a web server. For example, change to that directory in a terminal and run this command:
python -m SimpleHTTPServer 8080
Load http://localhost:8080/demo.htm in a web browser and you should see the page shown earlier.
12.3 Interface
You can access the Tutorial API by including rstudio.js
within your host page. This will enable you to instantiate an RStudio object that has a connection to the RStudio IDE within an IFrame. For example, if the IDE were hosted in an IFrame as follows:
<iframe id="rstudio" src="http://localhost:8787"></iframe>
Then you would instantiate an RStudio object as follows:
var RStudio = new RStudio(document.getElementById("rstudio"),
"http://localhost:8787",
function() { // onReady callback
console.log("API is ready!");
},
function(responseJSON) { // parent-notify callback
console.log(responseJSON);
});
The third argument is a callback that will be invoked once the RStudio API is ready to be called (i.e. once the IDE has loaded). Note that you should be sure to instantiate this object before the IFrame containing the IDE is fully loaded (if you don’t then you might miss the onReady callback). The best way to do this is to either:
Create the object immediately after defining the IFrame within the host page; or
More conservatively, create the IFrame, then create the object, then provide the src to the IFrame (this is however almost certainly not necessary and #1 should suffice).
The fourth argument is a callback that will be invoked when certain events described below in Tutorial API Callbacks are emitted by the IDE. These are only emitted if tutorial-api-parent-notify-enabled=1
was set as described earlier. The response will be a text string in JSON format, as described below in Tutorial API Callbacks.
12.4 Tutorial API Methods
Methods are asynchronous and do not directly return a result.
If Report Result is true below then that API will attempt to invoke a success or error callback when it completes, but this is never guaranteed.
Methods which report a result take an optional final string parameter callerID which will be returned in both success and error callbacks. This can be used to correlate calls and responses.
The RStudio object supports the following methods:
Method | Description | Reports Result |
---|---|---|
isReady() |
Is the RStudio API available yet? (has the IDE loaded) | No |
consoleInput(code) |
Type input in the R console and execute it. | No |
consoleClear() |
Clear all previous input and output from the console. | No |
consoleMaximize() |
Maximize the console so it occupies the full height of the IDE. | No |
executeR(code) |
Execute arbitrary R code within the global environment. | No |
openFile(file, location) |
Open the specified source file and (optionally) navigate it to a specific location. The location parameter can either be a line number (e.g. 42 ) or a regular expression delimited by / (e.g. /foo/ ). |
No |
helpTopic(topic) |
Navigate the help pane to a topic. The topic should be a namespace qualified reference to package documentation (e.g. graphics::plot ). Note that help topics defined within the base package do not need qualification. |
No |
helpDoc(doc) |
Show a markdown (.md) or R Markdown (.Rmd) document within the help pane. | No |
saveAllSourceDocs() |
Save all unsaved source documents. | No |
quitSession() |
Quit session. User cannot cancel but is prompted to save files and workspace if needed. | No |
createProjFromGit(repoUrl, projDir, parentDir, [callerID]) |
Clone a project from Git and open it. | Yes |
createNewProj(projDir, parentDir, createRepo, [callerID]) |
Create and open a new project. | Yes |
openProj(projFile, [callerID]) |
Open an existing project, can specify existing .Rproj, or just the folder. | Yes |
getState([callerID]) |
Request info on current RStudio IDE state. | Yes |
12.4.1 Example Calls
Here are some sample JavaScript calls, followed by the response JSON.
12.4.1.1 Clone project from github and open it (with callerID = ‘abcd’)
createProjFromGit('https://github.com/rstudio/rstudioapi', 'rstudioapi', '~/R', 'abcd');
{
"message":"success",
"api":"createProjFromGit",
"result":"",
"callerID":"abcd"
}
12.4.1.2 Create an new project but don’t create a git repo (no callerID)
createNewProj('myproj', '~/R', false);
{
"message":"success",
"api":"createNewProj",
"result":""
}
12.4.1.3 Try to open a project that doesn’t exist
openProj('~/myproj', 'abcd');
{
"message":"error",
"api":"openProj",
"result":"Unable to find .Rproj file in [~/myproj]",
"callerID":"abcd"
}
12.5 Tutorial API Callbacks
As seen in the examples above, the callback returns JSON. The following are examples of calls that trigger callbacks.
Method | Description | Example payload |
---|---|---|
getState | response from getState |
See examples below |
error | a prior API call failed | {“message”: “error”, “api”: “createProjFromGit”, “result”: “access denied”, “callerID”: “abcd”} |
success | a prior API call succeeded | {“message”: “success”, “api”: “createProjFromGit”, “callerID”: “abcd”} |
There are also callbacks sent directly by RStudio (i.e. not in response to Tutorial API calls).
Method | Description | Example payload |
---|---|---|
fileSave | contents of a file loaded in RStudio IDE were saved (including auto-save of content and/or metadata) | {“message”: “fileSave”} |
sessionDisconnect | connection between RStudio IDE and its rsession process was closed | {“message”: “sessionDisconnect”} |
sessionSuspend | the rsession process has been suspended | {“message”: “sessionSuspend”} |
12.5.1 getState
The getState()
method returns the path to the currently loaded .Rproj (if any) and any git remotes.
The results come via the callback. Here are some examples.
12.5.1.1 Project with remotes
{
"message": "getState",
"callerID": "abcd",
"project": "~/aaa/aaa.Rproj",
"remotes": [
{
"active": true,
"remote": "origin",
"type": "fetch",
"url": "https://github.com/rstudio/aaa"
},
{
"active": true,
"remote": "origin",
"type": "push",
"url": "https://github.com/rstudio/aaa"
}
]
}
12.5.1.2 Project with no remotes
{
"message": "getState",
"callerID": "abcd",
"project": "~/localproj/localproj.Rproj",
"remotes": []
}
12.5.1.3 No project and no remotes
{
"message": "getState",
"callerID": "abcd",
"project": null,
"remotes": []
}