9 Security & Auditing
9.1 API Security
9.1.1 Preventing Brute Force & Dictionary Attacks
By default, RStudio Connect allows as many login attempts as it can handle from any source when using the PAM, LDAP, and Password authentication providers. Users will be able to log in directly by entering their user name and password.
Setting the Authentication.ChallengeResponseEnabled
flag to
true
enables a CAPTCHA form in the login screen, and requires that CAPTCHA
be solved in order to authenticate. Both visual and audio CAPTCHA challenges
are provided for accessibility needs.
9.1.2 Hiding RStudio Connect Server Version and Build Information
By default RStudio Connect sets the Server
HTTP header to the Connect version and
build number, which looks something like RStudio Connect v1.2.3-1234
. If you would
like to hide this information you can configure Server.ServerName
to be any string. If you would also like to hide the version and build information
within the Connect dashboard you may configure the Server.HideVersion
setting to be true
.
9.2 Browser Security
There are a variety of security settings that can be configured in RStudio Connect. Some of these settings are enabled by default but can be customized while others are opt-in. Below are some of the security features worth considering.
9.2.1 Web Sudo Mode
When a user performs a sensitive operation in a web browser (such as creating a
new API key), they will be asked to reenter their login credentials. Once the
user enters their password properly, their session will enter a privileged
state internally referred to as “web sudo mode” which will allow them to perform
these sensitive operations for a certain window of time without entering their
password again. Note that this privileged mode is a notion purely internal to
RStudio Connect and entirely unrelated to the server’s actual sudo
or PAM
settings.
This feature is not available on servers configured to use proxied authentication or Google OAuth2, as these providers don’t have a mechanism for reprompting the user for their password.
For all other authentication providers, the WebSudoMode
and
WebSudoModeDuration
configuration options are available within the section
pertaining to that provider. If WebSudoMode
is set to false
, then this
protection is disabled; effectively, all authenticated users are always in
privileged mode. WebSudoModeDuration
controls the length of time for which a
user stays in this privileged mode. From within the section pertaining to your
authentication provider (such as [Password]
, [PAM]
, or [LDAP]
), you could
configure:
; /etc/rstudio-connect/rstudio-connect.gcfg
; This example is using password authentication. Use PAM or LDAP as appropriate.
[Password]
WebSudoMode = true
WebSudoModeDuration = 10m
In this case, users would be prompted for their password before performing sensitive actions, then would be allowed to continue performing sensitive actions for up to 10 minutes without additional prompts. After that point, any sensitive actions would require entering their password again.
Regardless of the setting, web sudo mode will never affect calls made outside of a browser using a token or an API key.
9.2.2 Limiting Session Lifetime
By default RStudio Connect uses a session cookie that will keep a user logged
in for 30 days. You may adjust this session lifetime by configuring the
Authentication.Lifetime
configuration option. It is a good
security practice to request user credentials daily to ensure the user still
has access to Connect. Use a value of 24 hours for Authentication.Lifetime
to follow this recommendation.
NOTE: If a user’s session expires with an application left running in their browser that application’s process will be terminated.
You may further restrict a user’s session lifetime by configuring the setting
Authentication.Inactivity
. When this is set to a non-zero
value that is less than Authentication.Lifetime
the user’s
session will expire after they have not been actively using the Connect dashboard
for the configured amount of time. The security practice is to make the inactivity
period as short as possible. Our current recommendation is setting it to 8 hours,
which allows most users to go through their office hours without being asked for
credentials a second time.
9.2.3 Guaranteeing HTTPS
If you can guarantee that your server should only ever be accessed over a
TLS/SSL connection (HTTPS), then you can consider enabling the
HTTPS.Permanent
setting. This elevates the security of your
server by requiring that future interactions between your users and this
server must be encrypted.
Enabling this setting may keep users from being able to access your RStudio Connect instance if you later disable HTTPS or if your certificate expires. Use this setting only if you will permanently provide a valid TLS/SSL certificate on this server.
Behind the scenes, this makes two changes:
- Introduces HTTP Strict Transport Security
(HSTS) by adding a
Strict-Transport-Security
HTTP header with amax-age
set to 30 days. HSTS ensures that your users’ browsers will not trust a service hosted at this location unless it is protected with a trusted TLS/SSL certificate. - Enforces the
Secure
flag on cookies that are set. This prohibits your users’ browsers from sending their RStudio Connect cookies to a server without an HTTPS-secured connection.
9.2.4 Strong HTTPS
Even with HTTPS, you may wish even more constraints on transport settings. Two settings are available to constrain HTTPS even further:
NOTE: Some Windows builds of the
RCurl
package are not compatible with TLS 1.1 or TLS 1.2. Windows users should executeoptions(rsconnect.http = 'curl')
to use the localcurl
binary, if installed, instead of the outdatedRCurl
package.
NOTE: Older versions of the RStudio IDE may use webviews that are not compatible with TLS 1.1 or TLS 1.2. In this case, attempting to pair with RStudio Connect without TLS 1.0 would open a blank screen instead of a login window. Open the blue link from the pairing window in the browser, or install a newer version of RStudio Connect as a workaround.
HTTPS.MinimumTLS
: This setting sets the minimum TLS version. By default, the minimum TLS version supported by RStudio Connect is TLS 1.0. You can choose to set this configuration setting to “1.1” or “1.2”; before doing so, you should check the SSL Labs User Agent List to ensure your clients will be compatible with the version you select.HTTPS.ExcludedCiphers
: This setting removes a cipher from the list of ciphers available. This may be useful if your organization has a security policy that disallows certain ciphers to be used.
An example exclusion list could be:
[HTTPS]
Listen = 443
MinimumTLS = 1.2
ExcludedCiphers = TLS_ECDHE_RSA_WITH_3DES_EDE_CBC_SHA
ExcludedCiphers = TLS_RSA_WITH_3DES_EDE_CBC_SHA
ExcludedCiphers = TLS_RSA_WITH_AES_128_GCM_SHA256
ExcludedCiphers = TLS_RSA_WITH_AES_256_GCM_SHA384
ExcludedCiphers = TLS_RSA_WITH_AES_128_CBC_SHA256
ExcludedCiphers = TLS_RSA_WITH_AES_128_CBC_SHA
ExcludedCiphers = TLS_RSA_WITH_AES_256_CBC_SHA
ExcludedCiphers = TLS_RSA_WITH_3DES_EDE_CBC_SHA
The strings for the ciphers may be found in the
IANA TLS Parameters List.
For a list of supported ciphers on your platform that may be excluded,
start up RStudio Connect and look for the log line beginning
Enabled HTTPS Ciphers:
.
9.2.5 Using a Secure Proxy
If you would prefer that the RStudio Connect process not have access to your TLS/SSL certificates, you may wish to configure a proxy to handle HTTPS requests. To accomplish this:
- Ensure that your
Server.Address
is set to the proxy address and uses thehttps
scheme. - Set
HTTP.ForceSecure
totrue
, which will set theSecure
flag on all cookies. - Set
HTTP.NoWarning
totrue
to suppress the warning regarding running RStudio Connect over an unsecured connection, because the connection between the client and the proxy will be secured. - If necessary, enable the
HTTPRedirect.Listen
option to redirect proxied plain HTTP connections to HTTPS.
NOTE: Because the connection between the proxy and RStudio Connect is not secured in this case, please ensure that the proxy and RStudio Connect are connecting on a trusted network where an adversary would not be able to capture plain text credentials. For example, many cloud providers allow isolating servers from the internet while permitting load balancers to access them. Please see your cloud provider’s documentation for more details.
9.2.6 Content Sniffing
The Server.ContentTypeSniffing
setting can be used to
configure HTTP responses with the X-Content-Type-Options
header. This header
can protect your users from a certain class of malicious
uploads.
When Server.ContentTypeSniffing
is disabled (the default),
the X-Content-Type-Options
HTTP header is given the value of nosniff
. This
instructs browsers not to inspect the content in an attempt to identify its
type.
When Server.ContentTypeSniffing
is enabled, the
X-Content-Type-Options
HTTP header is not sent; browsers are free to analyze
the content to detect its type.
9.2.7 Content Embedding
The X-Frame-Options
HTTP header is used to control what content can be
embedded inside other content in a web browser. The relevant attack is
commonly referred to as a “clickjack
attack”
and involves having your users interact with a sensitive service without their
knowledge.
For the purposes of the X-Frame-Options
header, RStudio Connect
distinguishes between “dashboard” and “user” content. The dashboard is
any of the internal services or assets that are shipped with RStudio Connect.
User content is anything uploaded by a user (reports, Shiny applications,
Plumber APIs, etc.)
Server.FrameOptionsContent
configures the X-Frame-Options
header value for user-uploaded content. By default it is empty, meaning that
the header will not be set. This allows user-provided content to be embedded
in iframes from any location. If you do not intend for others to embed user
content on their sites, you can set this to a value of SAMEORIGIN
to ensure
that only sites on the same server will be able to embed your users’ content.
The RStudio Connect dashboard itself uses iframes to present user content in
the dashboard, so it is not recommended to set this option to DENY
.
Server.FrameOptionsDashboard
configures the
X-Frame-Options
header value for internal services and assets provided with
RStudio Connect and defaults to a value of DENY
. This means that other sites
will not be able to embed the RStudio Connect dashboard. This setting is more
secure in that it protects against clickjacking attacks against the Connect
dashboard, but if you plan to embed the dashboard elsewhere you may need to
tune this setting.
Some advertised values for this header are not supported across all browsers. RStudio Connect does not restrict the values of these headers.
9.2.8 Custom Headers
If you need to include additional HTTP headers that are not covered by any of
the above features, you can include your own custom headers on all responses
from RStudio Connect using the Server.CustomHeader
setting.
This feature can be used to accommodate various other security practices that are not explicitly available as options elsewhere in Connect. For instance, X-XSS-Protection, Content Security Policy (CSP), HTTP Public Key Pinning (HPKP), and Cross-origin Resource Sharing (CORS) could all be configured using custom headers.
Custom headers are added to the HTTP response early during request processing. Values may later be overwritten or modified by other header settings. This includes both the security preferences described earlier in this chapter and other headers used internally by RStudio Connect, by Plumber, or by Shiny. You should not depend on a custom header that conflicts with a header already in use by RStudio Connect.
The Server.CustomHeader
takes a value of the header name and its value
separated by a colon. Whitespace surrounding the header name and its value are
trimmed. You can use this setting multiple times as in the following example:
; /etc/rstudio-connect/rstudio-connect.gcfg
[Server]
CustomHeader = “HeaderA: some value”
CustomHeader = “HeaderB: another value”
9.3 Audit Logs
RStudio Connect records information about changes to the system. These events can later be retrieved for auditing purposes.
This table contains the event types logged by the auditing system:
Event | Description |
---|---|
add_user |
Create a user |
edit_user |
Change an existing user |
remove_user |
*Delete a user |
update_lock_user |
Set or remove a lock for an existing user |
add_application |
Add new content |
upload_bundle |
Upload a bundle for a content |
deploy_application |
Deploy content to the server. Content may need to be published after deployment. |
edit_application |
Change content settings |
remove_application |
Delete content |
activate_token |
Activate a token. Tokens are used by the rsconnect package to authenticate a user. |
add_group |
Create a group |
edit_group |
*Change an existing group |
remove_group |
Delete a group |
add_group_member |
Add a user to a group |
remove_group_member |
Remove a user from a group |
assign_user_app_role |
Give a user view or edit access to content |
remove_user_app_role |
Remove a user from view or edit access list |
assign_group_app_role |
Give a group view or edit access to content |
remove_group_app_role |
Remove a group from view or edit access list |
clear_app_viewer_acl |
Change from a specific list of viewers to “just me” |
add_api_key |
Add API key |
edit_api_key |
*Change an existing API key |
remove_api_key |
Remove API key |
add_vanity |
Add vanity URL |
update_vanity |
Update vanity URL |
remove_vantiy |
Remove vanity URL |
remove_bundle |
Remove a bundle |
download_bundle |
Download a bundle |
add_tag |
Create a tag/category |
remove_tag |
Delete a tag/category |
update_tag |
Update a tag/category |
assign_tag_to_parent |
Associate a tag with some parent tag/category |
add_app_tag |
Associate a tag with content |
remove_app_tag |
Disassociate a tag with content |
updated_environment_variables |
Change to application environment variables |
user_login |
A user has started a dashboard session |
web_sudo |
A user needed to re-authenticate for a privileged action after a WebSudo timeout |
Note: The items marked with an asterisk can only be done via the
usermanager
CLI.
9.3.1 Audit Log File Output
If you have a need for audited events to be written to a file, in a way similar to
RStudio Connect’s access log, you can use the Server.AuditLogFormat
and Server.AuditLog
configuration options to control this.
The Server.AuditLogFormat
configuration option can be set to None
,
CSV
or JSON
. Setting it to None
disables echoing audit log entries to a file and
is the default. Setting it to CSV
or JSON
will format audit log entries in CSV or
JSON, respectively, and write the formatted data to the file named by the
Server.AuditLog
configuration option. The Server.AuditLog
option is ignored if Server.AuditLogFormat
is set to None
.
When formatting entries in CSV, fields are written in the following order:
- The database ID of the audit log record.
- The timestamp of the record, in RFC 3339.
- The database ID of the user that performed the action.
- The description of the user.
- The action the user performed.
- The description of the event.
When formatting entries in JSON, each text line written to the audit log file will be
a single, complete JSON object with the same data as for CSV with field names, id
,
time
, user_id
, user_description
, action
and event_description
, respectively.
RStudio will refuse to start if the specified audit log file already exists and has content that appears to contradict the requested entry format. In other words, if the file looks like it is in CSV format but the configuration requests JSON or looks like JSON and the configuration requests CSV, the server will not start.
The specification of the JSON object is the one used for Audit Logs in the Connect Server API.
9.3.2 Audit Logs Command-Line Interface
The usermanager
CLI tool can produce the same output present in the audit log file
output with the flags --csvlog
and --jsonlog
. Filtering by a time interval is also possible.
See Appendix B for more information on using the usermanager
CLI to
dump audit logs.
9.4 Application Environment Variables
User-specified environment variables for applications are encrypted on-disk and in-memory. They are decrypted only when a process is about to be started.