mirror of
https://github.com/Azure/cosmos-explorer.git
synced 2025-05-02 14:33:52 +01:00
Added logic
This commit is contained in:
parent
07c4ca9c50
commit
152c995ec0
@ -39,7 +39,10 @@ import {
|
||||
migrateTableToManualThroughput,
|
||||
updateTableThroughput,
|
||||
} from "../../Utils/arm/generatedClients/cosmos/tableResources";
|
||||
import { ThroughputSettingsUpdateParameters } from "../../Utils/arm/generatedClients/cosmos/types";
|
||||
import {
|
||||
ThroughputSettingsGetResults,
|
||||
ThroughputSettingsUpdateParameters,
|
||||
} from "../../Utils/arm/generatedClients/cosmos/types";
|
||||
import { logConsoleInfo, logConsoleProgress } from "../../Utils/NotificationConsoleUtils";
|
||||
import { HttpHeaders } from "../Constants";
|
||||
import { client } from "../CosmosClient";
|
||||
@ -146,23 +149,28 @@ const updateSqlContainerOffer = async (params: UpdateOfferParams): Promise<void>
|
||||
const { subscriptionId, resourceGroup, databaseAccount } = userContext;
|
||||
const accountName = databaseAccount.name;
|
||||
|
||||
let updatedOffer: ThroughputSettingsGetResults;
|
||||
|
||||
if (params.migrateToAutoPilot) {
|
||||
await migrateSqlContainerToAutoscale(
|
||||
updatedOffer = (await migrateSqlContainerToAutoscale(
|
||||
subscriptionId,
|
||||
resourceGroup,
|
||||
accountName,
|
||||
params.databaseId,
|
||||
params.collectionId,
|
||||
);
|
||||
)) as ThroughputSettingsGetResults;
|
||||
params.autopilotThroughput = updatedOffer.properties?.resource?.autoscaleSettings?.maxThroughput;
|
||||
} else if (params.migrateToManual) {
|
||||
await migrateSqlContainerToManualThroughput(
|
||||
updatedOffer = (await migrateSqlContainerToManualThroughput(
|
||||
subscriptionId,
|
||||
resourceGroup,
|
||||
accountName,
|
||||
params.databaseId,
|
||||
params.collectionId,
|
||||
);
|
||||
} else {
|
||||
)) as ThroughputSettingsGetResults;
|
||||
params.manualThroughput = updatedOffer.properties?.resource?.throughput;
|
||||
}
|
||||
if (params.throughputBuckets || !(params.migrateToAutoPilot || params.migrateToManual)) {
|
||||
const body: ThroughputSettingsUpdateParameters = createUpdateOfferBody(params);
|
||||
await updateSqlContainerThroughput(
|
||||
subscriptionId,
|
||||
|
@ -106,6 +106,7 @@ export interface SettingsComponentState {
|
||||
changeFeedPolicyBaseline: ChangeFeedPolicyState;
|
||||
isSubSettingsSaveable: boolean;
|
||||
isSubSettingsDiscardable: boolean;
|
||||
isThroughputBucketsSaveable: boolean;
|
||||
|
||||
vectorEmbeddingPolicy: DataModels.VectorEmbeddingPolicy;
|
||||
vectorEmbeddingPolicyBaseline: DataModels.VectorEmbeddingPolicy;
|
||||
@ -179,7 +180,9 @@ export class SettingsComponent extends React.Component<SettingsComponentProps, S
|
||||
|
||||
this.changeFeedPolicyVisible = userContext.features.enableChangeFeedPolicy;
|
||||
this.throughputBucketsEnabled =
|
||||
userContext.features.enableThroughputBuckets && userContext.authType === AuthType.AAD;
|
||||
userContext.apiType === "SQL" &&
|
||||
userContext.features.enableThroughputBuckets &&
|
||||
userContext.authType === AuthType.AAD;
|
||||
|
||||
// Mongo container with system partition key still treat as "Fixed"
|
||||
this.isFixedContainer =
|
||||
@ -218,6 +221,7 @@ export class SettingsComponent extends React.Component<SettingsComponentProps, S
|
||||
changeFeedPolicyBaseline: undefined,
|
||||
isSubSettingsSaveable: false,
|
||||
isSubSettingsDiscardable: false,
|
||||
isThroughputBucketsSaveable: false,
|
||||
|
||||
vectorEmbeddingPolicy: undefined,
|
||||
vectorEmbeddingPolicyBaseline: undefined,
|
||||
@ -450,6 +454,7 @@ export class SettingsComponent extends React.Component<SettingsComponentProps, S
|
||||
isScaleSaveable: false,
|
||||
isScaleDiscardable: false,
|
||||
isSubSettingsSaveable: false,
|
||||
isThroughputBucketsSaveable: false,
|
||||
isSubSettingsDiscardable: false,
|
||||
isContainerPolicyDirty: false,
|
||||
isIndexingPolicyDirty: false,
|
||||
@ -488,6 +493,10 @@ export class SettingsComponent extends React.Component<SettingsComponentProps, S
|
||||
private onIndexingPolicyContentChange = (newIndexingPolicy: DataModels.IndexingPolicy): void =>
|
||||
this.setState({ indexingPolicyContent: newIndexingPolicy });
|
||||
|
||||
private onThroughputBucketsSaveableChange = (isSaveable: boolean): void => {
|
||||
this.setState({ isThroughputBucketsSaveable: isSaveable });
|
||||
};
|
||||
|
||||
private resetShouldDiscardContainerPolicies = (): void => this.setState({ shouldDiscardContainerPolicies: false });
|
||||
|
||||
private resetShouldDiscardIndexingPolicy = (): void => this.setState({ shouldDiscardIndexingPolicy: false });
|
||||
@ -1053,7 +1062,8 @@ export class SettingsComponent extends React.Component<SettingsComponentProps, S
|
||||
currentOffer: this.collection.offer(),
|
||||
autopilotThroughput: this.state.isAutoPilotSelected ? this.state.autoPilotThroughput : undefined,
|
||||
manualThroughput: this.state.isAutoPilotSelected ? undefined : this.state.throughput,
|
||||
...(this.state.throughputBuckets && { throughputBuckets: this.state.throughputBuckets }),
|
||||
...(this.throughputBucketsEnabled &&
|
||||
this.state.isThroughputBucketsSaveable && { throughputBuckets: this.state.throughputBuckets }),
|
||||
};
|
||||
if (this.hasProvisioningTypeChanged()) {
|
||||
if (this.state.isAutoPilotSelected) {
|
||||
@ -1124,6 +1134,7 @@ export class SettingsComponent extends React.Component<SettingsComponentProps, S
|
||||
throughputBuckets: this.state.throughputBuckets,
|
||||
enableThroughputBuckets: this.isCollectionSettingsTab && this.throughputBucketsEnabled,
|
||||
onThroughputBucketChange: this.onThroughputBucketChange,
|
||||
onThroughputBucketsSaveableChange: this.onThroughputBucketsSaveableChange,
|
||||
throughputError: this.state.throughputError,
|
||||
};
|
||||
|
||||
|
@ -38,14 +38,15 @@ export interface ScaleComponentProps {
|
||||
throughputBucketsBaseline: DataModels.ThroughputBucket[];
|
||||
enableThroughputBuckets: boolean;
|
||||
onThroughputBucketChange: (throughputBuckets: DataModels.ThroughputBucket[]) => void;
|
||||
onThroughputBucketsSaveableChange: (isSaveable: boolean) => void;
|
||||
throughputError?: string;
|
||||
}
|
||||
|
||||
interface ScaleComponentState {
|
||||
isThroughputSaveable: boolean;
|
||||
isBucketsSaveable: boolean;
|
||||
isThroughputBucketsSaveable: boolean;
|
||||
isThroughputDiscardable: boolean;
|
||||
isBucketsDiscardable: boolean;
|
||||
isThroughputBucketsDiscardable: boolean;
|
||||
}
|
||||
|
||||
export class ScaleComponent extends React.Component<ScaleComponentProps, ScaleComponentState> {
|
||||
@ -62,9 +63,9 @@ export class ScaleComponent extends React.Component<ScaleComponentProps, ScaleCo
|
||||
this.collectionId = this.props.collection?.id();
|
||||
this.state = {
|
||||
isThroughputSaveable: false,
|
||||
isBucketsSaveable: false,
|
||||
isThroughputBucketsSaveable: false,
|
||||
isThroughputDiscardable: false,
|
||||
isBucketsDiscardable: false,
|
||||
isThroughputBucketsDiscardable: false,
|
||||
};
|
||||
}
|
||||
|
||||
@ -98,7 +99,6 @@ export class ScaleComponent extends React.Component<ScaleComponentProps, ScaleCo
|
||||
if (userContext.isTryCosmosDBSubscription) {
|
||||
return SharedConstants.CollectionCreation.DefaultCollectionRUs400;
|
||||
}
|
||||
|
||||
return this.offer?.minimumThroughput || SharedConstants.CollectionCreation.DefaultCollectionRUs400;
|
||||
};
|
||||
|
||||
@ -193,9 +193,12 @@ export class ScaleComponent extends React.Component<ScaleComponentProps, ScaleCo
|
||||
return hasChanges ? { ...prevState, ...updates } : null;
|
||||
},
|
||||
() => {
|
||||
const isSaveable = this.state.isThroughputSaveable || this.state.isBucketsSaveable;
|
||||
const isDiscardable = this.state.isThroughputDiscardable || this.state.isBucketsDiscardable;
|
||||
const isSaveable = this.state.isThroughputSaveable
|
||||
? this.state.isThroughputDiscardable || this.state.isThroughputBucketsSaveable
|
||||
: this.state.isThroughputBucketsSaveable;
|
||||
const isDiscardable = this.state.isThroughputDiscardable || this.state.isThroughputBucketsDiscardable;
|
||||
this.props.onScaleSaveableChange(isSaveable);
|
||||
this.props.onThroughputBucketsSaveableChange(this.state.isThroughputBucketsSaveable);
|
||||
this.props.onScaleDiscardableChange(isDiscardable);
|
||||
},
|
||||
);
|
||||
@ -209,12 +212,12 @@ export class ScaleComponent extends React.Component<ScaleComponentProps, ScaleCo
|
||||
this.updateScaleSettingsState({ isThroughputDiscardable: isDiscardable });
|
||||
};
|
||||
|
||||
private handleBucketsSaveableChange = (isSaveable: boolean) => {
|
||||
this.updateScaleSettingsState({ isBucketsSaveable: isSaveable });
|
||||
private handleThroughputBucketsSaveableChange = (isSaveable: boolean) => {
|
||||
this.updateScaleSettingsState({ isThroughputBucketsSaveable: isSaveable });
|
||||
};
|
||||
|
||||
private handleBucketsDiscardableChange = (isDiscardable: boolean) => {
|
||||
this.updateScaleSettingsState({ isBucketsDiscardable: isDiscardable });
|
||||
private handleThroughputBucketsDiscardableChange = (isDiscardable: boolean) => {
|
||||
this.updateScaleSettingsState({ isThroughputBucketsDiscardable: isDiscardable });
|
||||
};
|
||||
|
||||
public render(): JSX.Element {
|
||||
@ -232,13 +235,13 @@ export class ScaleComponent extends React.Component<ScaleComponentProps, ScaleCo
|
||||
<MessageBar messageBarType={MessageBarType.warning}>{this.getInitialNotificationElement()}</MessageBar>
|
||||
)}
|
||||
{!this.isAutoScaleEnabled() && <Stack {...subComponentStackProps}>{this.getThroughputInputComponent()}</Stack>}
|
||||
{this.props.enableThroughputBuckets && !this.props.isAutoPilotSelected && (
|
||||
{this.props.enableThroughputBuckets && (
|
||||
<ThroughputBucketsComponent
|
||||
currentBuckets={this.props.throughputBuckets}
|
||||
throughputBucketsBaseline={this.props.throughputBucketsBaseline}
|
||||
onBucketsChange={this.props.onThroughputBucketChange}
|
||||
onSaveableChange={this.handleBucketsSaveableChange}
|
||||
onDiscardableChange={this.handleBucketsDiscardableChange}
|
||||
onSaveableChange={this.handleThroughputBucketsSaveableChange}
|
||||
onDiscardableChange={this.handleThroughputBucketsDiscardableChange}
|
||||
/>
|
||||
)}
|
||||
|
||||
|
@ -1,4 +1,4 @@
|
||||
import { Icon, Label, Slider, Stack, TextField } from "@fluentui/react";
|
||||
import { Label, Slider, Stack, TextField, Toggle } from "@fluentui/react";
|
||||
import { ThroughputBucket } from "Contracts/DataModels";
|
||||
import React, { FC, useEffect, useState } from "react";
|
||||
import { isDirty } from "../../SettingsUtils";
|
||||
@ -26,7 +26,16 @@ export const ThroughputBucketsComponent: FC<ThroughputBucketsComponentProps> = (
|
||||
onDiscardableChange,
|
||||
}) => {
|
||||
const getThroughputBuckets = (buckets: ThroughputBucket[]): ThroughputBucket[] => {
|
||||
return DEFAULT_BUCKETS.map(
|
||||
if (!buckets || buckets.length === 0) {
|
||||
return DEFAULT_BUCKETS;
|
||||
}
|
||||
const maxBuckets = Math.max(DEFAULT_BUCKETS.length, buckets.length);
|
||||
const adjustedDefaultBuckets = Array.from({ length: maxBuckets }, (_, i) => ({
|
||||
id: i + 1,
|
||||
maxThroughputPercentage: 100,
|
||||
}));
|
||||
|
||||
return adjustedDefaultBuckets.map(
|
||||
(defaultBucket) => buckets?.find((bucket) => bucket.id === defaultBucket.id) || defaultBucket,
|
||||
);
|
||||
};
|
||||
@ -54,9 +63,13 @@ export const ThroughputBucketsComponent: FC<ThroughputBucketsComponentProps> = (
|
||||
settingsChanged && onBucketsChange(updatedBuckets);
|
||||
};
|
||||
|
||||
const onToggle = (id: number, checked: boolean) => {
|
||||
handleBucketChange(id, checked ? 50 : 100);
|
||||
};
|
||||
|
||||
return (
|
||||
<Stack tokens={{ childrenGap: "m" }} styles={{ root: { width: "70%", maxWidth: 700 } }}>
|
||||
<Label>Throughput buckets</Label>
|
||||
<Label>Throughput groups</Label>
|
||||
<Stack>
|
||||
{throughputBuckets?.map((bucket) => (
|
||||
<Stack key={bucket.id} horizontal tokens={{ childrenGap: 8 }} verticalAlign="center">
|
||||
@ -67,8 +80,9 @@ export const ThroughputBucketsComponent: FC<ThroughputBucketsComponentProps> = (
|
||||
value={bucket.maxThroughputPercentage}
|
||||
onChange={(newValue) => handleBucketChange(bucket.id, newValue)}
|
||||
showValue={false}
|
||||
label={`Bucket ${bucket.id}`}
|
||||
label={`Group ${bucket.id}${bucket.id === 1 ? " (Data Explorer Query Bucket)" : ""}`}
|
||||
styles={{ root: { flex: 2, maxWidth: 400 } }}
|
||||
disabled={bucket.maxThroughputPercentage === 100}
|
||||
/>
|
||||
<TextField
|
||||
value={bucket.maxThroughputPercentage.toString()}
|
||||
@ -78,13 +92,21 @@ export const ThroughputBucketsComponent: FC<ThroughputBucketsComponentProps> = (
|
||||
styles={{
|
||||
fieldGroup: { width: 80 },
|
||||
}}
|
||||
disabled={bucket.maxThroughputPercentage === 100}
|
||||
/>
|
||||
{bucket.id === 1 && (
|
||||
<Toggle
|
||||
onText="Enabled"
|
||||
offText="Disabled"
|
||||
checked={bucket.maxThroughputPercentage !== 100}
|
||||
onChange={(event, checked) => onToggle(bucket.id, checked)}
|
||||
styles={{ root: { marginBottom: 0 }, text: { fontSize: 12 } }}
|
||||
></Toggle>
|
||||
{/* {bucket.id === 1 && (
|
||||
<Stack horizontal tokens={{ childrenGap: 4 }} verticalAlign="center">
|
||||
<Icon iconName="TagSolid" />
|
||||
<span>Data Explorer Query Bucket</span>
|
||||
</Stack>
|
||||
)}
|
||||
)} */}
|
||||
</Stack>
|
||||
))}
|
||||
</Stack>
|
||||
|
Loading…
x
Reference in New Issue
Block a user