Skip to content
This repository has been archived by the owner on Dec 6, 2024. It is now read-only.

Commit

Permalink
chore: merge feature rstudio (#807)
Browse files Browse the repository at this point in the history
* Implementation for RstudioV2 (backed by ALB) feature
  • Loading branch information
SanketD92 authored Nov 18, 2021
1 parent c6e04ca commit ed2e7dc
Show file tree
Hide file tree
Showing 90 changed files with 8,405 additions and 14,028 deletions.
2 changes: 1 addition & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -228,7 +228,7 @@ Pre-requisites: Before creating a workspace, you must setup Service Catalog. Ref
4. Your workspace may take some time to launch. Once it is up and running, you can connect to it by choosing Connect. For more details, see the following documentation pages:
+ AWS SageMaker: Service Workbench takes care of provisioning the workspace for you, so you can jump straight to working with SageMaker Notebooks. For more information, see the [SageMaker Getting Started Guide](https://docs.aws.amazon.com/sagemaker/latest/dg/gs-console.html) (you can jump straight to Step 4).
+ AWS ElasticMapReduce (EMR): Service Workbench takes care of setting up the EMR instance for you, so you can jump straight to working with EMR Notebooks. For more information on using EMR Notebooks, see [Using EMR Notebooks](https://docs.aws.amazon.com/emr/latest/ManagementGuide/emr-managed-notebooks.html). **Note:** A password may be required to access the EMR Notebooks. By default, this password is 'go-research-on-aws' (without the quotes).
+ RStudio: See the [RStudio Server Documentation](https://support.rstudio.com/hc/en-us/sections/200150693-RStudio-Server) for assistance.
+ RStudio: You can connect to RStudio workspace type by using the template and AMI provided in AWS partner's [repository](https://github.com/RLOpenCatalyst/Service_Workbench_Templates). For more information, refer to the [Create RStudio ALB workspace](/deployment/post_deployment/aws_accounts#creating-rstudio-alb-workspace) section of *Service Workbench Post Deployment Guide*.
+ AWS Elastic Compute Cloud (EC2): EC2 instances are essentially Virtual Machines in the cloud. For more information, see the [EC2 Documentation](https://aws.amazon.com/ec2/).

## Create a Study
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@
const Service = require('@aws-ee/base-services-container/lib/service');
const { runAndCatch } = require('@aws-ee/base-services/lib/helpers/utils');

const createOrUpdateSchema = require('./schema/deployment-item');
const createOrUpdateSchema = require('./schema/deployment-item.json');

const settingKeys = {
tableName: 'dbDeploymentStore',
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -28,7 +28,7 @@ const UserService = require('@aws-ee/base-services/lib/user/user-service');
const DbPasswordService = require('@aws-ee/base-services/lib/db-password/db-password-service');
const AuthenticationProviderTypeService = require('@aws-ee/base-api-services/lib/authentication-providers/authentication-provider-type-service');
const AuthenticationProviderConfigService = require('@aws-ee/base-api-services/lib/authentication-providers/authentication-provider-config-service');
const registerBuiltInAuthProvisioners = require('@aws-ee/base-api-services/lib/authentication-providers/register-built-in-provisioner-services.js');
const registerBuiltInAuthProvisioners = require('@aws-ee/base-api-services/lib/authentication-providers/register-built-in-provisioner-services');

const DeploymentStoreService = require('../deployment-store-service');

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@
const Service = require('@aws-ee/base-services-container/lib/service');
const { runAndCatch } = require('@aws-ee/base-services/lib/helpers/utils');

const createOrUpdateSchema = require('./schema/deployment-item');
const createOrUpdateSchema = require('./schema/deployment-item.json');

const settingKeys = {
tableName: 'dbDeploymentStore',
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -28,7 +28,7 @@ const UserService = require('@aws-ee/base-services/lib/user/user-service');
const DbPasswordService = require('@aws-ee/base-services/lib/db-password/db-password-service');
const AuthenticationProviderTypeService = require('@aws-ee/base-api-services/lib/authentication-providers/authentication-provider-type-service');
const AuthenticationProviderConfigService = require('@aws-ee/base-api-services/lib/authentication-providers/authentication-provider-config-service');
const registerBuiltInAuthProvisioners = require('@aws-ee/base-api-services/lib/authentication-providers/register-built-in-provisioner-services.js');
const registerBuiltInAuthProvisioners = require('@aws-ee/base-api-services/lib/authentication-providers/register-built-in-provisioner-services');

const DeploymentStoreService = require('../deployment-store-service');

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,7 @@ import React from 'react';
import { decorate, computed } from 'mobx';
import { observer, inject } from 'mobx-react';
import { withRouter } from 'react-router-dom';
import { Header, Label, Popup, Icon, Divider, Message, Table, Grid, Segment } from 'semantic-ui-react';
import { Header, Label, Popup, Icon, Divider, Message, Table, Grid, Segment, List } from 'semantic-ui-react';
import TimeAgo from 'react-timeago';
import { niceNumber, swallowError } from '@aws-ee/base-ui/dist/helpers/utils';
import { isStoreLoading, isStoreNotEmpty, isStoreError } from '@aws-ee/base-ui/dist/models/BaseStore';
Expand Down Expand Up @@ -92,6 +92,7 @@ class ScEnvironmentCard extends React.Component {
{this.renderTitle(env)}
{this.renderError(env)}
{this.renderWarning(env)}
{this.renderLegacyRStudioWarning(env)}
<Divider className="mt1 mb1" />
{this.renderButtons(env)}
<Divider className="mt1" />
Expand Down Expand Up @@ -176,6 +177,35 @@ class ScEnvironmentCard extends React.Component {
);
}

renderLegacyRStudioWarning(env) {
const metaConnection1Type = env.outputs.find(obj => obj.OutputKey === 'MetaConnection1Type');
if (metaConnection1Type && metaConnection1Type.OutputValue.toLowerCase() === 'rstudio' && env.state.canTerminate) {
return (
<>
<Message
icon="warning"
header="Legacy RStudio environment found"
content="Please terminate this workspace as soon as possible. Support for this environment type has been deprecated. Please use RStudioV2 instead."
/>
<div className="mt3">
For more information, refer to the Create RStudio ALB workspace section of our Post Deployment Guide:
</div>
<List bulleted>
<List.Item
href="https://github.com/awslabs/service-workbench-on-aws/blob/mainline/docs/Service_Workbench_Post_Deployment_Guide.pdf"
target="_blank"
rel="noopener noreferrer"
>
Post Deployment Guide
</List.Item>
</List>
</>
);
}

return null;
}

renderWarning(env) {
if (isAppStreamEnabled && !env.isAppStreamConfigured && env.state.canTerminate) {
return (
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -89,8 +89,28 @@ class ScEnvironmentHttpConnections extends React.Component {
url = urlObj.url;

if (url) {
const newTab = openWindow('about:blank');
newTab.location = url;
if (connectInfo.type.toLowerCase() === 'rstudiov2') {
const rstudioUrl = url.split('?v=')[0];
const token = url.split('auth-do-sign-in?')[1];
const tokenKey = 'v';
const tokenVal = token.split('v=')[1];
const mapForm = document.createElement('form');
mapForm.target = 'Map';
mapForm.method = 'POST';
mapForm.action = rstudioUrl;
mapForm.style.display = 'none';

const mapInput = document.createElement('input');
mapInput.name = tokenKey;
mapInput.value = decodeURIComponent(tokenVal);
mapForm.appendChild(mapInput);

document.body.appendChild(mapForm);
mapForm.submit();
} else {
const newTab = openWindow('about:blank');
newTab.location = url;
}
}
}
} catch (error) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -71,6 +71,7 @@ class ScEnvironmentUpdateCidrs extends React.Component {
return this.stores.ready;
}, sideEffect);
sideEffect(this.stores.ready);
this.validateMaxCidrs = false;
}

componentDidMount() {
Expand Down Expand Up @@ -184,6 +185,19 @@ class ScEnvironmentUpdateCidrs extends React.Component {
return invalidCidrFound;
};

const validateMaxRStudioCidr = () => {
let status = false;
const envOutputs = this.environment.outputs;
const metaConnection1Type = envOutputs.find(obj => obj.OutputKey === 'MetaConnection1Type');
if (metaConnection1Type) {
const productName = metaConnection1Type.OutputValue;
if (productName === 'RStudioV2') {
status = this.validateMaxCidrs;
}
}
return status;
};

return (
<Segment clearing className="p3 mb3">
{fields.value.length === 0 && (
Expand Down Expand Up @@ -217,13 +231,22 @@ class ScEnvironmentUpdateCidrs extends React.Component {
content="One or more options entered are not valid IPv4 CIDR blocks. Please enter CIDR blocks in the format: '255.255.255.255/32'"
/>
)}
{validateMaxRStudioCidr() && (
<Message
negative
className="mb4"
icon="warning"
header="Maximum limit CIDR reached"
content="You can set maximum number of 4 IPv4 CIDR in this blocks"
/>
)}
<Button
className="ml2"
size="mini"
floated="right"
color="blue"
icon
disabled={processing || anyInvalidCidr()}
disabled={processing || anyInvalidCidr() || validateMaxRStudioCidr()}
type="submit"
>
Submit
Expand Down Expand Up @@ -260,6 +283,24 @@ class ScEnvironmentUpdateCidrs extends React.Component {
return _.some(this.ingressRules[index].cidrBlocks, cidr => IsCidr(cidr) !== 4);
};

const validateMaxRStudioCidr = () => {
this.validateMaxCidrs = false;
const eEnvOutputs = this.environment.outputs;
const metaConnection1Type = eEnvOutputs.find(obj => obj.OutputKey === 'MetaConnection1Type');
if (metaConnection1Type) {
const productName = metaConnection1Type.OutputValue;
const fromPort = field.value.fromPort;
if (productName === 'RStudioV2' && fromPort === 443) {
const cidrBlocks = field.value.cidrBlocks;
const cidrLen = cidrBlocks.length;
if (cidrLen > 4) {
this.validateMaxCidrs = true;
}
}
}
return this.validateMaxCidrs;
};

// If you're using this component for reference:
// The dropdown cell in this table is using the semantic-ui-react properties to display warnings and errors
// These validation mechanisms have already been implemented in the built-in Form component which are better suited for such scenarios
Expand All @@ -275,7 +316,7 @@ class ScEnvironmentUpdateCidrs extends React.Component {
<Table.Cell>
<Input disabled field={field.$('toPort')} />
</Table.Cell>
<Table.Cell warning={anyWideCidr()} error={anyInvalidCidr()}>
<Table.Cell warning={anyWideCidr()} error={(anyInvalidCidr(), validateMaxRStudioCidr())}>
<Dropdown
field={field.$('cidrBlocks')}
allowAdditions
Expand Down Expand Up @@ -307,7 +348,6 @@ decorate(ScEnvironmentUpdateCidrs, {
environment: computed,
envsStore: computed,
clientInformationStore: computed,

ingressRules: observable,
form: observable,
handleSave: action,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@ import ec2WindowsInstance from '../templates/ec2-windows-instance.cfn.yml';
import sagemakerInstance from '../templates/sagemaker-notebook-instance.cfn.yml';
import onboardAccount from '../templates/onboard-account.cfn.yml';
import storageGatewayNetworkInfra from '../templates/storage-gateway/network-infrastructure.cfn.yml';
import applicationLoadBalancer from '../templates/application-load-balancer.cfn.yml';

const add = (name, yaml) => ({ name, yaml });

Expand All @@ -32,6 +33,7 @@ const templates = [
add('sagemaker-notebook-instance', sagemakerInstance),
add('onboard-account', onboardAccount),
add('storage-gateway-network-infra', storageGatewayNetworkInfra),
add('application-load-balancer', applicationLoadBalancer),
];

async function registerCfnTemplates(registry) {
Expand Down
Loading

0 comments on commit ed2e7dc

Please sign in to comment.