@carbon/ibm-cloud-cognitive-cdai
Version:
Carbon for Cloud & Cognitive CD&AI UI components
513 lines (511 loc) • 25.2 kB
JavaScript
import _objectWithoutProperties from "@babel/runtime/helpers/objectWithoutProperties";
import _extends from "@babel/runtime/helpers/extends";
import _defineProperty from "@babel/runtime/helpers/defineProperty";
import _classCallCheck from "@babel/runtime/helpers/classCallCheck";
import _createClass from "@babel/runtime/helpers/createClass";
import _possibleConstructorReturn from "@babel/runtime/helpers/possibleConstructorReturn";
import _getPrototypeOf from "@babel/runtime/helpers/getPrototypeOf";
import _inherits from "@babel/runtime/helpers/inherits";
var _excluded = ["isRequired", "descriptionText", "onChange", "value"],
_excluded2 = ["open", "labelText", "heading", "closeLabelText", "onClose", "copyLabelText", "apiKey", "descriptionText", "isAPIKeyGenerating", "generatingLabelText", "apiKeyLabelText", "isAPIKeyVisible", "apiKeyVisibilityToggleAltText", "apiKeySecret", "apiKeySecretLabelText", "apiKeySecretVisibilityToggleAltText", "apiKeyHelperText", "downloadLinkText", "onDownload", "descriptiveNameStep", "generateLabelText", "onGenerateAPIKey", "nextLabelText", "backLabelText", "onNext", "onBack", "customSteps", "className", "onCopyAPIKeyData"];
function ownKeys(e, r) { var t = Object.keys(e); if (Object.getOwnPropertySymbols) { var o = Object.getOwnPropertySymbols(e); r && (o = o.filter(function (r) { return Object.getOwnPropertyDescriptor(e, r).enumerable; })), t.push.apply(t, o); } return t; }
function _objectSpread(e) { for (var r = 1; r < arguments.length; r++) { var t = null != arguments[r] ? arguments[r] : {}; r % 2 ? ownKeys(Object(t), !0).forEach(function (r) { _defineProperty(e, r, t[r]); }) : Object.getOwnPropertyDescriptors ? Object.defineProperties(e, Object.getOwnPropertyDescriptors(t)) : ownKeys(Object(t)).forEach(function (r) { Object.defineProperty(e, r, Object.getOwnPropertyDescriptor(t, r)); }); } return e; }
function _callSuper(t, o, e) { return o = _getPrototypeOf(o), _possibleConstructorReturn(t, _isNativeReflectConstruct() ? Reflect.construct(o, e || [], _getPrototypeOf(t).constructor) : o.apply(t, e)); }
function _isNativeReflectConstruct() { try { var t = !Boolean.prototype.valueOf.call(Reflect.construct(Boolean, [], function () {})); } catch (t) {} return (_isNativeReflectConstruct = function _isNativeReflectConstruct() { return !!t; })(); }
//
// Copyright IBM Corp. 2020, 2020
//
// This source code is licensed under the Apache-2.0 license found in the
// LICENSE file in the root directory of this source tree.
//
import React from 'react';
import PropTypes from 'prop-types';
import { InlineLoading, Link, Modal, TextInput } from 'carbon-components-react';
import { InformationFilled16 } from '@carbon/icons-react';
import { idePrefix } from '../../globals/js/settings';
import { idAttribute } from '../../component_helpers/IDHelper';
import { copyToClipboard } from '../../component_helpers/Clipboard';
var INITIAL_STATE = {
currentStepIndex: 0,
hasAPIKeyGenerationCompleted: true
};
var IdeAPIKeyGeneration = /*#__PURE__*/function (_React$Component) {
function IdeAPIKeyGeneration() {
var _this;
_classCallCheck(this, IdeAPIKeyGeneration);
_this = _callSuper(this, IdeAPIKeyGeneration);
_this.state = _objectSpread(_objectSpread({}, INITIAL_STATE), {}, {
descriptiveName: ''
});
_this.handleDescriptiveNameChange = _this.handleDescriptiveNameChange.bind(_this);
_this.handleGenerateAPIKey = _this.handleGenerateAPIKey.bind(_this);
_this.handleAPIKeyGenerationCompletion = _this.handleAPIKeyGenerationCompletion.bind(_this);
_this.handleCopy = _this.handleCopy.bind(_this);
_this.handleDownload = _this.handleDownload.bind(_this);
_this.handleNext = _this.handleNext.bind(_this);
_this.handleBack = _this.handleBack.bind(_this);
_this.renderDescriptiveNameStep = _this.renderDescriptiveNameStep.bind(_this);
_this.renderAPIKey = _this.renderAPIKey.bind(_this);
return _this;
}
_inherits(IdeAPIKeyGeneration, _React$Component);
return _createClass(IdeAPIKeyGeneration, [{
key: "componentDidMount",
value: function componentDidMount() {
var _this$props = this.props,
descriptiveNameStep = _this$props.descriptiveNameStep,
isAPIKeyGenerating = _this$props.isAPIKeyGenerating;
this.setState(_objectSpread({
hasAPIKeyGenerationCompleted: !isAPIKeyGenerating
}, descriptiveNameStep && descriptiveNameStep.value ? {
descriptiveName: descriptiveNameStep.value
} : null));
}
}, {
key: "componentDidUpdate",
value: function componentDidUpdate(prevProps) {
if (prevProps.isAPIKeyGenerating !== this.props.isAPIKeyGenerating) {
this.setState({
hasAPIKeyGenerationCompleted: !this.props.isAPIKeyGenerating
});
}
if (!prevProps.open && this.props.open) {
// Reset the state when the modal opens
this.setState(INITIAL_STATE);
}
if (prevProps.descriptiveNameStep && this.props.descriptiveNameStep && prevProps.descriptiveNameStep.value !== this.props.descriptiveNameStep.value && this.state.descriptiveName !== this.props.descriptiveNameStep.value) {
this.setState({
descriptiveName: this.props.descriptiveNameStep.value
});
}
}
}, {
key: "getCurrentStep",
value: function getCurrentStep() {
var _this$props2 = this.props,
descriptiveNameStep = _this$props2.descriptiveNameStep,
generateLabelText = _this$props2.generateLabelText,
nextLabelText = _this$props2.nextLabelText,
backLabelText = _this$props2.backLabelText,
heading = _this$props2.heading,
descriptionText = _this$props2.descriptionText,
customSteps = _this$props2.customSteps;
var generationStep = {
id: 'IdeAPIKeyGeneration-APIKeyGen',
descriptionText: descriptionText,
render: this.renderAPIKey,
className: "".concat(idePrefix, "-api-key-generation-api-key--content")
};
var currentStep;
if (descriptiveNameStep && this.state.currentStepIndex == 0) {
currentStep = {
id: 'IdeAPIKeyGeneration-DescriptiveName',
modalProps: {
modalHeading: descriptiveNameStep.heading || heading,
primaryButtonText: generateLabelText,
primaryButtonDisabled: descriptiveNameStep.invalid || descriptiveNameStep.isRequired && !this.state.descriptiveName,
onRequestSubmit: this.handleGenerateAPIKey
},
descriptionText: descriptiveNameStep.descriptionText,
render: this.renderDescriptiveNameStep,
className: "".concat(idePrefix, "-api-key-generation-description--content")
};
if (customSteps && customSteps.length > 0) {
// There are custom steps, so the primary button goes to the next step
currentStep.modalProps = _objectSpread(_objectSpread({}, currentStep.modalProps), {}, {
primaryButtonText: nextLabelText,
onRequestSubmit: this.handleNext
});
}
} else if (customSteps && customSteps.length > 0) {
var stepIndex = this.state.currentStepIndex;
if (descriptiveNameStep) {
// If there is a descriptiveNameStep, stepIndex is the currentStepIndex - 1;
stepIndex -= 1;
}
if (stepIndex < customSteps.length) {
var customStep = customSteps[stepIndex];
currentStep = {
id: "IdeAPIKeyGeneration-".concat(customStep.stepId),
modalProps: {
modalHeading: customStep.stepHeading || heading,
primaryButtonText: nextLabelText,
primaryButtonDisabled: customStep.nextButtonDisabled,
onRequestSubmit: this.handleNext
},
descriptionText: customStep.descriptionText,
render: customStep.renderStep,
className: customStep.stepClassName
};
if (stepIndex === customSteps.length - 1) {
// This is the final custom step, so the primary button now generates the API key
currentStep.modalProps = _objectSpread(_objectSpread({}, currentStep.modalProps), {}, {
primaryButtonText: generateLabelText,
onRequestSubmit: this.handleGenerateAPIKey
});
}
if (this.state.currentStepIndex > 0) {
// This is not the first step, so the secondary button now handles going back a step
currentStep.modalProps = _objectSpread(_objectSpread({}, currentStep.modalProps), {}, {
secondaryButtonText: backLabelText,
onSecondarySubmit: this.handleBack
});
}
} else {
// This is after the final custom step, so show the generation/results step
currentStep = generationStep;
}
} else {
// No descriptiveNameStep or customSteps, so go straight to the generation/results step
currentStep = generationStep;
}
return currentStep;
}
}, {
key: "handleNext",
value: function handleNext() {
var onNext = this.props.onNext;
onNext && onNext(this.state.currentStepIndex);
this.setState({
currentStepIndex: this.state.currentStepIndex + 1
});
}
}, {
key: "handleBack",
value: function handleBack() {
var onBack = this.props.onBack;
onBack && onBack(this.state.currentStepIndex);
this.setState({
currentStepIndex: this.state.currentStepIndex - 1
});
}
}, {
key: "handleDescriptiveNameChange",
value: function handleDescriptiveNameChange(event) {
var descriptiveName = event.target.value;
this.setState({
descriptiveName: descriptiveName
});
var onChange = this.props.descriptiveNameStep.onChange;
onChange && onChange(event);
}
}, {
key: "handleGenerateAPIKey",
value: function handleGenerateAPIKey() {
var onGenerateAPIKey = this.props.onGenerateAPIKey;
this.setState({
hasAPIKeyGenerationCompleted: false,
currentStepIndex: this.state.currentStepIndex + 1
});
onGenerateAPIKey && onGenerateAPIKey();
}
}, {
key: "handleAPIKeyGenerationCompletion",
value: function handleAPIKeyGenerationCompletion() {
this.setState({
hasAPIKeyGenerationCompleted: true
});
}
}, {
key: "getAPIKeyData",
value: function getAPIKeyData() {
var _this$props3 = this.props,
apiKey = _this$props3.apiKey,
apiKeySecret = _this$props3.apiKeySecret,
descriptiveNameStep = _this$props3.descriptiveNameStep;
return _objectSpread(_objectSpread({
apiKey: apiKey
}, apiKeySecret ? {
apiKeySecret: apiKeySecret
} : null), descriptiveNameStep && this.state.descriptiveName ? {
name: this.state.descriptiveName
} : null);
}
}, {
key: "handleCopy",
value: function handleCopy(event) {
var _this$props4 = this.props,
apiKey = _this$props4.apiKey,
apiKeySecret = _this$props4.apiKeySecret,
descriptiveNameStep = _this$props4.descriptiveNameStep,
onCopyAPIKeyData = _this$props4.onCopyAPIKeyData;
// If the apiKeySecret exists, copy a stringified object containing the
// apiKey and the apiKeySecret props to the clipboard.
// If no apiKeySecret exists, just copy the apiKey prop to the clipboard.
var dataToCopy = apiKey;
if (apiKeySecret || descriptiveNameStep) {
dataToCopy = JSON.stringify(this.getAPIKeyData());
}
copyToClipboard(event, dataToCopy);
onCopyAPIKeyData && onCopyAPIKeyData(this.getAPIKeyData());
}
}, {
key: "handleDownload",
value: function handleDownload(event) {
event.preventDefault(); // Prevent anchor href being followed
var onDownload = this.props.onDownload;
onDownload && onDownload(this.getAPIKeyData());
}
}, {
key: "renderDescription",
value: function renderDescription(descriptionText) {
return descriptionText ? /*#__PURE__*/React.createElement("p", _extends({
className: "".concat(idePrefix, "-api-key-generation-description")
}, idAttribute('IdeAPIKeyGeneration-Description')), descriptionText) : null;
}
}, {
key: "renderAPIKey",
value: function renderAPIKey() {
var _this$props5 = this.props,
apiKey = _this$props5.apiKey,
apiKeyLabelText = _this$props5.apiKeyLabelText,
apiKeyHelperText = _this$props5.apiKeyHelperText,
isAPIKeyVisible = _this$props5.isAPIKeyVisible,
apiKeyVisibilityToggleAltText = _this$props5.apiKeyVisibilityToggleAltText,
onDownload = _this$props5.onDownload,
downloadLinkText = _this$props5.downloadLinkText,
isAPIKeyGenerating = _this$props5.isAPIKeyGenerating,
generatingLabelText = _this$props5.generatingLabelText,
apiKeySecret = _this$props5.apiKeySecret,
apiKeySecretLabelText = _this$props5.apiKeySecretLabelText,
apiKeySecretVisibilityToggleAltText = _this$props5.apiKeySecretVisibilityToggleAltText,
descriptiveNameStep = _this$props5.descriptiveNameStep;
var apiKeyProps = _objectSpread(_objectSpread({
value: apiKey,
labelText: apiKeyLabelText,
light: true,
readOnly: true
}, idAttribute('IdeAPIKeyGeneration-APIKey')), {}, {
id: 'IdeAPIKeyGeneration-APIKey'
});
var apiKeySecretProps = apiKeySecret ? _objectSpread(_objectSpread({
value: apiKeySecret,
labelText: apiKeySecretLabelText,
tooltipAlignment: 'end',
alt: apiKeySecretVisibilityToggleAltText,
light: true,
readOnly: true
}, idAttribute('IdeAPIKeyGeneration-APIKeySecret')), {}, {
id: 'IdeAPIKeyGeneration-APIKeySecret'
}) : null;
return !this.state.hasAPIKeyGenerationCompleted ? /*#__PURE__*/React.createElement(InlineLoading, _extends({
status: isAPIKeyGenerating ? 'active' : 'inactive',
description: generatingLabelText,
iconDescription: generatingLabelText,
onSuccess: this.handleAPIKeyGenerationCompletion,
successDelay: 0,
className: "".concat(idePrefix, "-api-key-generation-api-key-generating")
}, idAttribute('IdeAPIKeyGeneration-APIKeyGenerating'))) : /*#__PURE__*/React.createElement(React.Fragment, null, descriptiveNameStep && this.state.descriptiveName && /*#__PURE__*/React.createElement("div", {
className: "".concat(idePrefix, "-api-key-generation-descriptive-name")
}, descriptiveNameStep.labelText && /*#__PURE__*/React.createElement("p", _extends({
className: "".concat(idePrefix, "-api-key-generation-descriptive-name--label")
}, idAttribute('IdeAPIKeyGeneration-DescriptiveName-Label')), descriptiveNameStep.labelText), /*#__PURE__*/React.createElement("p", _extends({
className: "".concat(idePrefix, "-api-key-generation-descriptive-name--value")
}, idAttribute('IdeAPIKeyGeneration-DescriptiveName-Value')), this.state.descriptiveName)), /*#__PURE__*/React.createElement("div", {
className: "".concat(idePrefix, "-api-key-generation-api-key")
}, isAPIKeyVisible ? /*#__PURE__*/React.createElement(TextInput, apiKeyProps) : /*#__PURE__*/React.createElement(TextInput.PasswordInput, _extends({}, apiKeyProps, {
alt: apiKeyVisibilityToggleAltText,
tooltipAlignment: 'end'
}))), apiKeySecret && /*#__PURE__*/React.createElement("div", {
className: "".concat(idePrefix, "-api-key-generation-api-key-secret")
}, /*#__PURE__*/React.createElement(TextInput.PasswordInput, apiKeySecretProps)), apiKeyHelperText && /*#__PURE__*/React.createElement("div", {
className: "".concat(idePrefix, "-api-key-generation-helper-text-container")
}, /*#__PURE__*/React.createElement(InformationFilled16, {
className: "".concat(idePrefix, "-api-key-generation-helper-text-icon"),
description: apiKeyHelperText
}), /*#__PURE__*/React.createElement("p", _extends({
className: "".concat(idePrefix, "-api-key-generation-helper-text")
}, idAttribute('IdeAPIKeyGeneration-APIKey-HelperText')), apiKeyHelperText, onDownload && downloadLinkText && /*#__PURE__*/React.createElement(Link, _extends({
className: "".concat(idePrefix, "-api-key-generation-download-link")
}, idAttribute('IdeAPIKeyGeneration-APIKey-DownloadLink'), {
href: "#",
onClick: this.handleDownload
}), downloadLinkText))));
}
}, {
key: "renderDescriptiveNameStep",
value: function renderDescriptiveNameStep() {
var _this$props$descripti = this.props.descriptiveNameStep,
isRequired = _this$props$descripti.isRequired,
descriptionText = _this$props$descripti.descriptionText,
onChange = _this$props$descripti.onChange,
value = _this$props$descripti.value,
others = _objectWithoutProperties(_this$props$descripti, _excluded);
var descriptiveNameProps = _objectSpread(_objectSpread({
className: "".concat(idePrefix, "-api-key-generation-descriptive-name-input")
}, idAttribute('IdeAPIKeyGeneration-DescriptiveNameInput')), {}, {
id: 'IdeAPIKeyGeneration-DescriptiveNameInput',
light: true,
onChange: this.handleDescriptiveNameChange,
value: this.state.descriptiveName
}, others);
return /*#__PURE__*/React.createElement(TextInput, descriptiveNameProps);
}
}, {
key: "render",
value: function render() {
var _this$props6 = this.props,
open = _this$props6.open,
labelText = _this$props6.labelText,
heading = _this$props6.heading,
closeLabelText = _this$props6.closeLabelText,
onClose = _this$props6.onClose,
copyLabelText = _this$props6.copyLabelText,
apiKey = _this$props6.apiKey,
descriptionText = _this$props6.descriptionText,
isAPIKeyGenerating = _this$props6.isAPIKeyGenerating,
generatingLabelText = _this$props6.generatingLabelText,
apiKeyLabelText = _this$props6.apiKeyLabelText,
isAPIKeyVisible = _this$props6.isAPIKeyVisible,
apiKeyVisibilityToggleAltText = _this$props6.apiKeyVisibilityToggleAltText,
apiKeySecret = _this$props6.apiKeySecret,
apiKeySecretLabelText = _this$props6.apiKeySecretLabelText,
apiKeySecretVisibilityToggleAltText = _this$props6.apiKeySecretVisibilityToggleAltText,
apiKeyHelperText = _this$props6.apiKeyHelperText,
downloadLinkText = _this$props6.downloadLinkText,
onDownload = _this$props6.onDownload,
descriptiveNameStep = _this$props6.descriptiveNameStep,
generateLabelText = _this$props6.generateLabelText,
onGenerateAPIKey = _this$props6.onGenerateAPIKey,
nextLabelText = _this$props6.nextLabelText,
backLabelText = _this$props6.backLabelText,
onNext = _this$props6.onNext,
onBack = _this$props6.onBack,
customSteps = _this$props6.customSteps,
className = _this$props6.className,
onCopyAPIKeyData = _this$props6.onCopyAPIKeyData,
others = _objectWithoutProperties(_this$props6, _excluded2);
var currentStep = this.getCurrentStep();
var modalProps = _objectSpread(_objectSpread(_objectSpread({
open: open,
modalHeading: heading,
modalLabel: labelText,
modalAriaLabel: labelText || heading,
'aria-label': labelText || heading,
primaryButtonText: copyLabelText,
primaryButtonDisabled: !apiKey || !this.state.hasAPIKeyGenerationCompleted,
secondaryButtonText: closeLabelText,
onRequestClose: onClose,
onRequestSubmit: this.handleCopy,
className: ["".concat(idePrefix, "-api-key-generation"), className].join(' ')
}, idAttribute('IdeAPIKeyGeneration')), others), currentStep.modalProps);
var classNames = ["".concat(idePrefix, "-api-key-generation--content"), currentStep.id, currentStep.className].join(' ');
return /*#__PURE__*/React.createElement(Modal, modalProps, /*#__PURE__*/React.createElement("div", _extends({}, idAttribute(currentStep.id), {
className: classNames
}), this.renderDescription(currentStep.descriptionText), currentStep.render()));
}
}]);
}(React.Component);
/* eslint-disable react/sort-prop-types */
export { IdeAPIKeyGeneration as default };
IdeAPIKeyGeneration.propTypes = {
/** CSS class to add to the component */
className: PropTypes.string,
/** Whether the API Key Generation modal is currently open. */
open: PropTypes.bool.isRequired,
/** Modal label text. */
labelText: PropTypes.string,
/** Modal heading text. */
heading: PropTypes.string.isRequired,
/** Modal description text. */
descriptionText: PropTypes.string,
/** Generated API key value */
apiKey: PropTypes.string,
/** Label text for the API key value. */
apiKeyLabelText: PropTypes.string,
/** Whether the API key is visible. If false, a visibility toggle is included. */
isAPIKeyVisible: PropTypes.bool,
/** Alt text for the API key visibilty toggle. */
apiKeyVisibilityToggleAltText: PropTypes.string,
/** Label text for the (primary) generate button. */
generateLabelText: PropTypes.string,
/** API key generation handler. */
onGenerateAPIKey: PropTypes.func,
/** Whether an API Key is currently being generated. */
isAPIKeyGenerating: PropTypes.bool,
/** Label text for the spinner shown while an API key is being generated. */
generatingLabelText: PropTypes.string,
/** Label text for the close (X) button and the (secondary) close button. */
closeLabelText: PropTypes.string.isRequired,
/** Close button handler. */
onClose: PropTypes.func,
/** Label text for the (primary) copy button */
copyLabelText: PropTypes.string.isRequired,
/** Copy button handler. The `apiKey` prop value (and 'apiKeySecret' prop value if it
exists) is automatically copied into the system clipboard. This callback function
can be used to close the modal and handle anything else. */
onCopyAPIKeyData: PropTypes.func,
/** Helper text shown when the API key has been generated. */
apiKeyHelperText: PropTypes.string,
/** Download link handler */
onDownload: PropTypes.func,
/** Link text shown when there is an `onDownload` property. */
downloadLinkText: PropTypes.string,
/** Generated API key secret value */
apiKeySecret: PropTypes.string,
/** Label text for the API key secret value */
apiKeySecretLabelText: PropTypes.string,
/** Alt text for the API key secret visibilty toggle */
apiKeySecretVisibilityToggleAltText: PropTypes.string,
/** API key descriptive name step settings. Any further props are passed to the descriptive
name TextInput component. */
descriptiveNameStep: PropTypes.shape({
/** Whether a descriptive name value is required. If true, and the `value`
prop is empty, a descriptive name field is displayed which must be completed before
the Generate/Next button is enabled. */
isRequired: PropTypes.bool,
/** Value of the API key descriptive name. */
value: PropTypes.string,
/** Modal heading text for the descriptive name step. */
heading: PropTypes.string,
/** Modal description text for the descriptive name step. */
descriptionText: PropTypes.string,
/** Label text for the descriptive name field. */
labelText: PropTypes.string,
/** Helper text for the descriptive name field. */
helperText: PropTypes.string,
/** Placeholder text for the descriptive name field. */
placeholder: PropTypes.string,
/** Handler for changes to the descriptive name field. */
onChange: PropTypes.func,
/** Whether the descriptive name is invalid. If true, the Generate/Next button
is disabled. */
invalid: PropTypes.bool
}),
/** Label text for the (primary) next button */
nextLabelText: PropTypes.string,
/** Handler to notify that the (primary) next button was clicked */
onNext: PropTypes.func,
/** Label text for the (secondary) back button */
backLabelText: PropTypes.string,
/** Handler to notify that the (secondary) back button was clicked */
onBack: PropTypes.func,
/** Custom step settings */
customSteps: PropTypes.arrayOf(PropTypes.shape({
/** Unique id for this step. */
stepId: PropTypes.string.isRequired,
/** Modal heading text for the step. */
stepHeading: PropTypes.string,
/** Modal description text for the step. */
descriptionText: PropTypes.string,
/** Whether the (primary) next button is disabled. */
nextButtonDisabled: PropTypes.bool,
/** Handler to render the step. */
renderStep: PropTypes.func.isRequired,
/** Classname applied to the modal content for the step. */
stepClassName: PropTypes.string
}))
};
IdeAPIKeyGeneration.defaultProps = {
open: false,
heading: 'Generate API key',
apiKeyLabelText: 'API key',
isAPIKeyGenerating: false,
isAPIKeyVisible: true,
copyLabelText: 'Copy',
closeLabelText: 'Close',
nextLabelText: 'Next',
backLabelText: 'Back',
generateLabelText: 'Generate',
downloadLinkText: 'Download'
};