mirror of
https://github.com/Azure/cosmos-explorer.git
synced 2025-12-20 09:20:16 +00:00
Move queryDocuments out of DataAccessUtility (#334)
This commit is contained in:
@@ -16,18 +16,16 @@ import * as TelemetryProcessor from "../../Shared/Telemetry/TelemetryProcessor";
|
||||
import SaveIcon from "../../../images/save-cosmos.svg";
|
||||
import DiscardIcon from "../../../images/discard.svg";
|
||||
import DeleteIcon from "../../../images/delete.svg";
|
||||
import { QueryIterator, ItemDefinition, Resource, ConflictDefinition } from "@azure/cosmos";
|
||||
import { QueryIterator, Resource, ConflictDefinition, FeedOptions } from "@azure/cosmos";
|
||||
import { MinimalQueryIterator } from "../../Common/IteratorUtilities";
|
||||
import Explorer from "../Explorer";
|
||||
import {
|
||||
queryConflicts,
|
||||
deleteConflict,
|
||||
deleteDocument,
|
||||
createDocument,
|
||||
updateDocument
|
||||
} from "../../Common/DocumentClientUtilityBase";
|
||||
import { CommandButtonComponentProps } from "../Controls/CommandButton/CommandButtonComponent";
|
||||
import { getErrorMessage, getErrorStack } from "../../Common/ErrorHandlingUtils";
|
||||
import { createDocument } from "../../Common/dataAccess/createDocument";
|
||||
import { deleteDocument } from "../../Common/dataAccess/deleteDocument";
|
||||
import { updateDocument } from "../../Common/dataAccess/updateDocument";
|
||||
import { deleteConflict } from "../../Common/dataAccess/deleteConflict";
|
||||
import { queryConflicts } from "../../Common/dataAccess/queryConflicts";
|
||||
|
||||
export default class ConflictsTab extends TabsBase {
|
||||
public selectedConflictId: ko.Observable<ConflictId>;
|
||||
@@ -225,25 +223,15 @@ export default class ConflictsTab extends TabsBase {
|
||||
});
|
||||
}
|
||||
|
||||
public refreshDocumentsGrid(): Q.Promise<any> {
|
||||
// clear documents grid
|
||||
this.conflictIds([]);
|
||||
return this.createIterator()
|
||||
.then(
|
||||
// reset iterator
|
||||
iterator => {
|
||||
this._documentsIterator = iterator;
|
||||
}
|
||||
)
|
||||
.then(
|
||||
// load documents
|
||||
() => {
|
||||
return this.loadNextPage();
|
||||
}
|
||||
)
|
||||
.catch(error => {
|
||||
window.alert(getErrorMessage(error));
|
||||
});
|
||||
public async refreshDocumentsGrid(): Promise<void> {
|
||||
try {
|
||||
// clear documents grid
|
||||
this.conflictIds([]);
|
||||
this._documentsIterator = this.createIterator();
|
||||
await this.loadNextPage();
|
||||
} catch (error) {
|
||||
window.alert(getErrorMessage(error));
|
||||
}
|
||||
}
|
||||
|
||||
public onRefreshButtonKeyDown = (source: any, event: KeyboardEvent): boolean => {
|
||||
@@ -265,9 +253,9 @@ export default class ConflictsTab extends TabsBase {
|
||||
return Q();
|
||||
}
|
||||
|
||||
public onAcceptChangesClick = (): Q.Promise<any> => {
|
||||
public onAcceptChangesClick = async (): Promise<void> => {
|
||||
if (this.isEditorDirty() && !this._isIgnoreDirtyEditor()) {
|
||||
return Q();
|
||||
return;
|
||||
}
|
||||
|
||||
this.isExecutionError(false);
|
||||
@@ -285,81 +273,79 @@ export default class ConflictsTab extends TabsBase {
|
||||
conflictResourceId: selectedConflict.resourceId
|
||||
});
|
||||
|
||||
let operationPromise: Q.Promise<any> = Q();
|
||||
if (selectedConflict.operationType === Constants.ConflictOperationType.Replace) {
|
||||
const documentContent = JSON.parse(this.selectedConflictContent());
|
||||
try {
|
||||
if (selectedConflict.operationType === Constants.ConflictOperationType.Replace) {
|
||||
const documentContent = JSON.parse(this.selectedConflictContent());
|
||||
|
||||
operationPromise = updateDocument(
|
||||
this.collection,
|
||||
selectedConflict.buildDocumentIdFromConflict(documentContent[selectedConflict.partitionKeyProperty]),
|
||||
documentContent
|
||||
);
|
||||
}
|
||||
await updateDocument(
|
||||
this.collection,
|
||||
selectedConflict.buildDocumentIdFromConflict(documentContent[selectedConflict.partitionKeyProperty]),
|
||||
documentContent
|
||||
);
|
||||
}
|
||||
|
||||
if (selectedConflict.operationType === Constants.ConflictOperationType.Create) {
|
||||
const documentContent = JSON.parse(this.selectedConflictContent());
|
||||
if (selectedConflict.operationType === Constants.ConflictOperationType.Create) {
|
||||
const documentContent = JSON.parse(this.selectedConflictContent());
|
||||
|
||||
operationPromise = createDocument(this.collection, documentContent);
|
||||
}
|
||||
await createDocument(this.collection, documentContent);
|
||||
}
|
||||
|
||||
if (selectedConflict.operationType === Constants.ConflictOperationType.Delete && !!this.selectedConflictContent()) {
|
||||
const documentContent = JSON.parse(this.selectedConflictContent());
|
||||
if (
|
||||
selectedConflict.operationType === Constants.ConflictOperationType.Delete &&
|
||||
!!this.selectedConflictContent()
|
||||
) {
|
||||
const documentContent = JSON.parse(this.selectedConflictContent());
|
||||
|
||||
operationPromise = deleteDocument(
|
||||
this.collection,
|
||||
selectedConflict.buildDocumentIdFromConflict(documentContent[selectedConflict.partitionKeyProperty])
|
||||
);
|
||||
}
|
||||
await deleteDocument(
|
||||
this.collection,
|
||||
selectedConflict.buildDocumentIdFromConflict(documentContent[selectedConflict.partitionKeyProperty])
|
||||
);
|
||||
}
|
||||
|
||||
return operationPromise
|
||||
.then(
|
||||
() => {
|
||||
return deleteConflict(this.collection, selectedConflict).then(() => {
|
||||
this.conflictIds.remove((conflictId: ConflictId) => conflictId.rid === selectedConflict.rid);
|
||||
this.selectedConflictContent("");
|
||||
this.selectedConflictCurrent("");
|
||||
this.selectedConflictId(null);
|
||||
this.editorState(ViewModels.DocumentExplorerState.noDocumentSelected);
|
||||
TelemetryProcessor.traceSuccess(
|
||||
Action.ResolveConflict,
|
||||
{
|
||||
databaseAccountName: this.collection && this.collection.container.databaseAccount().name,
|
||||
defaultExperience: this.collection && this.collection.container.defaultExperience(),
|
||||
dataExplorerArea: Constants.Areas.Tab,
|
||||
tabTitle: this.tabTitle(),
|
||||
conflictResourceType: selectedConflict.resourceType,
|
||||
conflictOperationType: selectedConflict.operationType,
|
||||
conflictResourceId: selectedConflict.resourceId
|
||||
},
|
||||
startKey
|
||||
);
|
||||
});
|
||||
await deleteConflict(this.collection, selectedConflict);
|
||||
this.conflictIds.remove((conflictId: ConflictId) => conflictId.rid === selectedConflict.rid);
|
||||
this.selectedConflictContent("");
|
||||
this.selectedConflictCurrent("");
|
||||
this.selectedConflictId(null);
|
||||
this.editorState(ViewModels.DocumentExplorerState.noDocumentSelected);
|
||||
TelemetryProcessor.traceSuccess(
|
||||
Action.ResolveConflict,
|
||||
{
|
||||
databaseAccountName: this.collection && this.collection.container.databaseAccount().name,
|
||||
defaultExperience: this.collection && this.collection.container.defaultExperience(),
|
||||
dataExplorerArea: Constants.Areas.Tab,
|
||||
tabTitle: this.tabTitle(),
|
||||
conflictResourceType: selectedConflict.resourceType,
|
||||
conflictOperationType: selectedConflict.operationType,
|
||||
conflictResourceId: selectedConflict.resourceId
|
||||
},
|
||||
error => {
|
||||
this.isExecutionError(true);
|
||||
const errorMessage = getErrorMessage(error);
|
||||
window.alert(errorMessage);
|
||||
TelemetryProcessor.traceFailure(
|
||||
Action.ResolveConflict,
|
||||
{
|
||||
databaseAccountName: this.collection && this.collection.container.databaseAccount().name,
|
||||
defaultExperience: this.collection && this.collection.container.defaultExperience(),
|
||||
dataExplorerArea: Constants.Areas.Tab,
|
||||
tabTitle: this.tabTitle(),
|
||||
conflictResourceType: selectedConflict.resourceType,
|
||||
conflictOperationType: selectedConflict.operationType,
|
||||
conflictResourceId: selectedConflict.resourceId,
|
||||
error: errorMessage,
|
||||
errorStack: getErrorStack(error)
|
||||
},
|
||||
startKey
|
||||
);
|
||||
}
|
||||
)
|
||||
.finally(() => this.isExecuting(false));
|
||||
startKey
|
||||
);
|
||||
} catch (error) {
|
||||
this.isExecutionError(true);
|
||||
const errorMessage = getErrorMessage(error);
|
||||
window.alert(errorMessage);
|
||||
TelemetryProcessor.traceFailure(
|
||||
Action.ResolveConflict,
|
||||
{
|
||||
databaseAccountName: this.collection && this.collection.container.databaseAccount().name,
|
||||
defaultExperience: this.collection && this.collection.container.defaultExperience(),
|
||||
dataExplorerArea: Constants.Areas.Tab,
|
||||
tabTitle: this.tabTitle(),
|
||||
conflictResourceType: selectedConflict.resourceType,
|
||||
conflictOperationType: selectedConflict.operationType,
|
||||
conflictResourceId: selectedConflict.resourceId,
|
||||
error: errorMessage,
|
||||
errorStack: getErrorStack(error)
|
||||
},
|
||||
startKey
|
||||
);
|
||||
} finally {
|
||||
this.isExecuting(false);
|
||||
}
|
||||
};
|
||||
|
||||
public onDeleteClick = (): Q.Promise<any> => {
|
||||
public onDeleteClick = async (): Promise<void> => {
|
||||
this.isExecutionError(false);
|
||||
this.isExecuting(true);
|
||||
|
||||
@@ -375,50 +361,48 @@ export default class ConflictsTab extends TabsBase {
|
||||
conflictResourceId: selectedConflict.resourceId
|
||||
});
|
||||
|
||||
return deleteConflict(this.collection, selectedConflict)
|
||||
.then(
|
||||
() => {
|
||||
this.conflictIds.remove((conflictId: ConflictId) => conflictId.rid === selectedConflict.rid);
|
||||
this.selectedConflictContent("");
|
||||
this.selectedConflictCurrent("");
|
||||
this.selectedConflictId(null);
|
||||
this.editorState(ViewModels.DocumentExplorerState.noDocumentSelected);
|
||||
TelemetryProcessor.traceSuccess(
|
||||
Action.DeleteConflict,
|
||||
{
|
||||
databaseAccountName: this.collection && this.collection.container.databaseAccount().name,
|
||||
defaultExperience: this.collection && this.collection.container.defaultExperience(),
|
||||
dataExplorerArea: Constants.Areas.Tab,
|
||||
tabTitle: this.tabTitle(),
|
||||
conflictResourceType: selectedConflict.resourceType,
|
||||
conflictOperationType: selectedConflict.operationType,
|
||||
conflictResourceId: selectedConflict.resourceId
|
||||
},
|
||||
startKey
|
||||
);
|
||||
try {
|
||||
await deleteConflict(this.collection, selectedConflict);
|
||||
this.conflictIds.remove((conflictId: ConflictId) => conflictId.rid === selectedConflict.rid);
|
||||
this.selectedConflictContent("");
|
||||
this.selectedConflictCurrent("");
|
||||
this.selectedConflictId(null);
|
||||
this.editorState(ViewModels.DocumentExplorerState.noDocumentSelected);
|
||||
TelemetryProcessor.traceSuccess(
|
||||
Action.DeleteConflict,
|
||||
{
|
||||
databaseAccountName: this.collection && this.collection.container.databaseAccount().name,
|
||||
defaultExperience: this.collection && this.collection.container.defaultExperience(),
|
||||
dataExplorerArea: Constants.Areas.Tab,
|
||||
tabTitle: this.tabTitle(),
|
||||
conflictResourceType: selectedConflict.resourceType,
|
||||
conflictOperationType: selectedConflict.operationType,
|
||||
conflictResourceId: selectedConflict.resourceId
|
||||
},
|
||||
error => {
|
||||
this.isExecutionError(true);
|
||||
const errorMessage = getErrorMessage(error);
|
||||
window.alert(errorMessage);
|
||||
TelemetryProcessor.traceFailure(
|
||||
Action.DeleteConflict,
|
||||
{
|
||||
databaseAccountName: this.collection && this.collection.container.databaseAccount().name,
|
||||
defaultExperience: this.collection && this.collection.container.defaultExperience(),
|
||||
dataExplorerArea: Constants.Areas.Tab,
|
||||
tabTitle: this.tabTitle(),
|
||||
conflictResourceType: selectedConflict.resourceType,
|
||||
conflictOperationType: selectedConflict.operationType,
|
||||
conflictResourceId: selectedConflict.resourceId,
|
||||
error: errorMessage,
|
||||
errorStack: getErrorStack(error)
|
||||
},
|
||||
startKey
|
||||
);
|
||||
}
|
||||
)
|
||||
.finally(() => this.isExecuting(false));
|
||||
startKey
|
||||
);
|
||||
} catch (error) {
|
||||
this.isExecutionError(true);
|
||||
const errorMessage = getErrorMessage(error);
|
||||
window.alert(errorMessage);
|
||||
TelemetryProcessor.traceFailure(
|
||||
Action.DeleteConflict,
|
||||
{
|
||||
databaseAccountName: this.collection && this.collection.container.databaseAccount().name,
|
||||
defaultExperience: this.collection && this.collection.container.defaultExperience(),
|
||||
dataExplorerArea: Constants.Areas.Tab,
|
||||
tabTitle: this.tabTitle(),
|
||||
conflictResourceType: selectedConflict.resourceType,
|
||||
conflictOperationType: selectedConflict.operationType,
|
||||
conflictResourceId: selectedConflict.resourceId,
|
||||
error: errorMessage,
|
||||
errorStack: getErrorStack(error)
|
||||
},
|
||||
startKey
|
||||
);
|
||||
} finally {
|
||||
this.isExecuting(false);
|
||||
}
|
||||
};
|
||||
|
||||
public onDiscardClick = (): Q.Promise<any> => {
|
||||
@@ -445,60 +429,47 @@ export default class ConflictsTab extends TabsBase {
|
||||
return Q();
|
||||
}
|
||||
|
||||
public onTabClick(): Q.Promise<any> {
|
||||
return super.onTabClick().then(() => {
|
||||
this.collection && this.collection.selectedSubnodeKind(ViewModels.CollectionTabKind.Conflicts);
|
||||
});
|
||||
public onTabClick(): void {
|
||||
super.onTabClick();
|
||||
this.collection && this.collection.selectedSubnodeKind(ViewModels.CollectionTabKind.Conflicts);
|
||||
}
|
||||
|
||||
public onActivate(): Q.Promise<any> {
|
||||
return super.onActivate().then(() => {
|
||||
if (this._documentsIterator) {
|
||||
return Q.resolve(this._documentsIterator);
|
||||
}
|
||||
public async onActivate(): Promise<void> {
|
||||
super.onActivate();
|
||||
|
||||
return this.createIterator().then(
|
||||
(iterator: QueryIterator<ItemDefinition & Resource>) => {
|
||||
this._documentsIterator = iterator;
|
||||
return this.loadNextPage();
|
||||
},
|
||||
error => {
|
||||
if (this.onLoadStartKey != null && this.onLoadStartKey != undefined) {
|
||||
TelemetryProcessor.traceFailure(
|
||||
Action.Tab,
|
||||
{
|
||||
databaseAccountName: this.collection.container.databaseAccount().name,
|
||||
databaseName: this.collection.databaseId,
|
||||
collectionName: this.collection.id(),
|
||||
defaultExperience: this.collection.container.defaultExperience(),
|
||||
dataExplorerArea: Constants.Areas.Tab,
|
||||
tabTitle: this.tabTitle(),
|
||||
error: getErrorMessage(error),
|
||||
errorStack: getErrorStack(error)
|
||||
},
|
||||
this.onLoadStartKey
|
||||
);
|
||||
this.onLoadStartKey = null;
|
||||
}
|
||||
if (!this._documentsIterator) {
|
||||
try {
|
||||
this._documentsIterator = await this.createIterator();
|
||||
await this.loadNextPage();
|
||||
} catch (error) {
|
||||
if (this.onLoadStartKey != null && this.onLoadStartKey != undefined) {
|
||||
TelemetryProcessor.traceFailure(
|
||||
Action.Tab,
|
||||
{
|
||||
databaseAccountName: this.collection.container.databaseAccount().name,
|
||||
databaseName: this.collection.databaseId,
|
||||
collectionName: this.collection.id(),
|
||||
defaultExperience: this.collection.container.defaultExperience(),
|
||||
dataExplorerArea: Constants.Areas.Tab,
|
||||
tabTitle: this.tabTitle(),
|
||||
error: getErrorMessage(error),
|
||||
errorStack: getErrorStack(error)
|
||||
},
|
||||
this.onLoadStartKey
|
||||
);
|
||||
this.onLoadStartKey = null;
|
||||
}
|
||||
);
|
||||
});
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public onRefreshClick(): Q.Promise<any> {
|
||||
return this.refreshDocumentsGrid().then(() => {
|
||||
this.selectedConflictContent("");
|
||||
this.selectedConflictId(null);
|
||||
this.editorState(ViewModels.DocumentExplorerState.noDocumentSelected);
|
||||
});
|
||||
}
|
||||
|
||||
public createIterator(): Q.Promise<QueryIterator<ConflictDefinition & Resource>> {
|
||||
public createIterator(): QueryIterator<ConflictDefinition & Resource> {
|
||||
// TODO: Conflict Feed does not allow filtering atm
|
||||
const query: string = undefined;
|
||||
let options: any = {};
|
||||
options.enableCrossPartitionQuery = HeadersUtility.shouldEnableCrossPartitionKey();
|
||||
return queryConflicts(this.collection.databaseId, this.collection.id(), query, options);
|
||||
const options = {
|
||||
enableCrossPartitionQuery: HeadersUtility.shouldEnableCrossPartitionKey()
|
||||
};
|
||||
return queryConflicts(this.collection.databaseId, this.collection.id(), query, options as FeedOptions);
|
||||
}
|
||||
|
||||
public loadNextPage(): Q.Promise<any> {
|
||||
|
||||
@@ -429,11 +429,10 @@ export default class DatabaseSettingsTab extends TabsBase implements ViewModels.
|
||||
return Q();
|
||||
};
|
||||
|
||||
public onActivate(): Q.Promise<any> {
|
||||
return super.onActivate().then(async () => {
|
||||
this.database.selectedSubnodeKind(ViewModels.CollectionTabKind.DatabaseSettings);
|
||||
await this.database.loadOffer();
|
||||
});
|
||||
public async onActivate(): Promise<void> {
|
||||
super.onActivate();
|
||||
this.database.selectedSubnodeKind(ViewModels.CollectionTabKind.DatabaseSettings);
|
||||
await this.database.loadOffer();
|
||||
}
|
||||
|
||||
private _setBaseline() {
|
||||
|
||||
@@ -103,7 +103,7 @@
|
||||
<button
|
||||
class="filterbtnstyle queryButton"
|
||||
data-bind="
|
||||
click: onApplyFilterClick,
|
||||
click: refreshDocumentsGrid,
|
||||
enable: applyFilterButton.enabled"
|
||||
aria-label="Apply filter"
|
||||
tabindex="0"
|
||||
|
||||
@@ -19,19 +19,24 @@ import SaveIcon from "../../../images/save-cosmos.svg";
|
||||
import DiscardIcon from "../../../images/discard.svg";
|
||||
import DeleteDocumentIcon from "../../../images/DeleteDocument.svg";
|
||||
import UploadIcon from "../../../images/Upload_16x16.svg";
|
||||
import { extractPartitionKey, PartitionKeyDefinition, QueryIterator, ItemDefinition, Resource } from "@azure/cosmos";
|
||||
import {
|
||||
extractPartitionKey,
|
||||
PartitionKeyDefinition,
|
||||
QueryIterator,
|
||||
ItemDefinition,
|
||||
Resource,
|
||||
Item
|
||||
} from "@azure/cosmos";
|
||||
import { ConsoleDataType } from "../Menus/NotificationConsole/NotificationConsoleComponent";
|
||||
import * as NotificationConsoleUtils from "../../Utils/NotificationConsoleUtils";
|
||||
import Explorer from "../Explorer";
|
||||
import {
|
||||
readDocument,
|
||||
queryDocuments,
|
||||
deleteDocument,
|
||||
updateDocument,
|
||||
createDocument
|
||||
} from "../../Common/DocumentClientUtilityBase";
|
||||
import { CommandButtonComponentProps } from "../Controls/CommandButton/CommandButtonComponent";
|
||||
import { getErrorMessage, getErrorStack } from "../../Common/ErrorHandlingUtils";
|
||||
import { queryDocuments } from "../../Common/dataAccess/queryDocuments";
|
||||
import { readDocument } from "../../Common/dataAccess/readDocument";
|
||||
import { deleteDocument } from "../../Common/dataAccess/deleteDocument";
|
||||
import { updateDocument } from "../../Common/dataAccess/updateDocument";
|
||||
import { createDocument } from "../../Common/dataAccess/createDocument";
|
||||
|
||||
export default class DocumentsTab extends TabsBase {
|
||||
public selectedDocumentId: ko.Observable<DocumentId>;
|
||||
@@ -369,36 +374,22 @@ export default class DocumentsTab extends TabsBase {
|
||||
return true;
|
||||
};
|
||||
|
||||
public onApplyFilterClick(): Q.Promise<any> {
|
||||
public async refreshDocumentsGrid(): Promise<void> {
|
||||
// clear documents grid
|
||||
this.documentIds([]);
|
||||
return this.createIterator()
|
||||
.then(
|
||||
// reset iterator
|
||||
iterator => {
|
||||
this._documentsIterator = iterator;
|
||||
}
|
||||
)
|
||||
.then(
|
||||
// load documents
|
||||
() => {
|
||||
return this.loadNextPage();
|
||||
}
|
||||
)
|
||||
.then(() => {
|
||||
// collapse filter
|
||||
this.appliedFilter(this.filterContent());
|
||||
this.isFilterExpanded(false);
|
||||
const focusElement = document.getElementById("errorStatusIcon");
|
||||
focusElement && focusElement.focus();
|
||||
})
|
||||
.catch(error => {
|
||||
window.alert(getErrorMessage(error));
|
||||
});
|
||||
}
|
||||
|
||||
public refreshDocumentsGrid(): Q.Promise<any> {
|
||||
return this.onApplyFilterClick();
|
||||
try {
|
||||
// reset iterator
|
||||
this._documentsIterator = this.createIterator();
|
||||
// load documents
|
||||
await this.loadNextPage();
|
||||
// collapse filter
|
||||
this.appliedFilter(this.filterContent());
|
||||
this.isFilterExpanded(false);
|
||||
document.getElementById("errorStatusIcon")?.focus();
|
||||
} catch (error) {
|
||||
window.alert(getErrorMessage(error));
|
||||
}
|
||||
}
|
||||
|
||||
public onRefreshButtonKeyDown = (source: any, event: KeyboardEvent): boolean => {
|
||||
@@ -434,7 +425,7 @@ export default class DocumentsTab extends TabsBase {
|
||||
return Q();
|
||||
};
|
||||
|
||||
public onSaveNewDocumentClick = (): Q.Promise<any> => {
|
||||
public onSaveNewDocumentClick = (): Promise<any> => {
|
||||
this.isExecutionError(false);
|
||||
const startKey: number = TelemetryProcessor.traceStart(Action.CreateDocument, {
|
||||
databaseAccountName: this.collection && this.collection.container.databaseAccount().name,
|
||||
@@ -502,7 +493,7 @@ export default class DocumentsTab extends TabsBase {
|
||||
return Q();
|
||||
};
|
||||
|
||||
public onSaveExisitingDocumentClick = (): Q.Promise<any> => {
|
||||
public onSaveExisitingDocumentClick = (): Promise<any> => {
|
||||
const selectedDocumentId = this.selectedDocumentId();
|
||||
const documentContent = JSON.parse(this.selectedDocumentContent());
|
||||
|
||||
@@ -571,17 +562,15 @@ export default class DocumentsTab extends TabsBase {
|
||||
return Q();
|
||||
};
|
||||
|
||||
public onDeleteExisitingDocumentClick = (): Q.Promise<any> => {
|
||||
public onDeleteExisitingDocumentClick = async (): Promise<void> => {
|
||||
const selectedDocumentId = this.selectedDocumentId();
|
||||
const msg = !this.isPreferredApiMongoDB
|
||||
? "Are you sure you want to delete the selected item ?"
|
||||
: "Are you sure you want to delete the selected document ?";
|
||||
|
||||
if (window.confirm(msg)) {
|
||||
return this._deleteDocument(selectedDocumentId);
|
||||
await this._deleteDocument(selectedDocumentId);
|
||||
}
|
||||
|
||||
return Q();
|
||||
};
|
||||
|
||||
public onValidDocumentEdit(): Q.Promise<any> {
|
||||
@@ -617,63 +606,50 @@ export default class DocumentsTab extends TabsBase {
|
||||
return Q();
|
||||
}
|
||||
|
||||
public onTabClick(): Q.Promise<any> {
|
||||
return super.onTabClick().then(() => {
|
||||
this.collection && this.collection.selectedSubnodeKind(ViewModels.CollectionTabKind.Documents);
|
||||
});
|
||||
public onTabClick(): void {
|
||||
super.onTabClick();
|
||||
this.collection && this.collection.selectedSubnodeKind(ViewModels.CollectionTabKind.Documents);
|
||||
}
|
||||
|
||||
public onActivate(): Q.Promise<any> {
|
||||
return super.onActivate().then(() => {
|
||||
if (this._documentsIterator) {
|
||||
return Q.resolve(this._documentsIterator);
|
||||
}
|
||||
public async onActivate(): Promise<void> {
|
||||
super.onActivate();
|
||||
|
||||
return this.createIterator().then(
|
||||
(iterator: QueryIterator<ItemDefinition & Resource>) => {
|
||||
this._documentsIterator = iterator;
|
||||
return this.loadNextPage();
|
||||
},
|
||||
error => {
|
||||
if (this.onLoadStartKey != null && this.onLoadStartKey != undefined) {
|
||||
TelemetryProcessor.traceFailure(
|
||||
Action.Tab,
|
||||
{
|
||||
databaseAccountName: this.collection.container.databaseAccount().name,
|
||||
databaseName: this.collection.databaseId,
|
||||
collectionName: this.collection.id(),
|
||||
defaultExperience: this.collection.container.defaultExperience(),
|
||||
dataExplorerArea: Constants.Areas.Tab,
|
||||
tabTitle: this.tabTitle(),
|
||||
error: getErrorMessage(error),
|
||||
errorStack: getErrorStack(error)
|
||||
},
|
||||
this.onLoadStartKey
|
||||
);
|
||||
this.onLoadStartKey = null;
|
||||
}
|
||||
if (!this._documentsIterator) {
|
||||
try {
|
||||
this._documentsIterator = this.createIterator();
|
||||
await this.loadNextPage();
|
||||
} catch (error) {
|
||||
if (this.onLoadStartKey != null && this.onLoadStartKey != undefined) {
|
||||
TelemetryProcessor.traceFailure(
|
||||
Action.Tab,
|
||||
{
|
||||
databaseAccountName: this.collection.container.databaseAccount().name,
|
||||
databaseName: this.collection.databaseId,
|
||||
collectionName: this.collection.id(),
|
||||
defaultExperience: this.collection.container.defaultExperience(),
|
||||
dataExplorerArea: Constants.Areas.Tab,
|
||||
tabTitle: this.tabTitle(),
|
||||
error: getErrorMessage(error),
|
||||
errorStack: getErrorStack(error)
|
||||
},
|
||||
this.onLoadStartKey
|
||||
);
|
||||
this.onLoadStartKey = null;
|
||||
}
|
||||
);
|
||||
});
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public onRefreshClick(): Q.Promise<any> {
|
||||
return this.refreshDocumentsGrid().then(() => {
|
||||
this.selectedDocumentContent("");
|
||||
this.selectedDocumentId(null);
|
||||
this.editorState(ViewModels.DocumentExplorerState.noDocumentSelected);
|
||||
});
|
||||
}
|
||||
private _isIgnoreDirtyEditor = (): boolean => {
|
||||
var msg: string = "Changes will be lost. Do you want to continue?";
|
||||
return window.confirm(msg);
|
||||
};
|
||||
|
||||
protected __deleteDocument(documentId: DocumentId): Q.Promise<any> {
|
||||
protected __deleteDocument(documentId: DocumentId): Promise<void> {
|
||||
return deleteDocument(this.collection, documentId);
|
||||
}
|
||||
|
||||
private _deleteDocument(selectedDocumentId: DocumentId): Q.Promise<any> {
|
||||
private _deleteDocument(selectedDocumentId: DocumentId): Promise<void> {
|
||||
this.isExecutionError(false);
|
||||
const startKey: number = TelemetryProcessor.traceStart(Action.DeleteDocument, {
|
||||
databaseAccountName: this.collection && this.collection.container.databaseAccount().name,
|
||||
@@ -684,7 +660,7 @@ export default class DocumentsTab extends TabsBase {
|
||||
this.isExecuting(true);
|
||||
return this.__deleteDocument(selectedDocumentId)
|
||||
.then(
|
||||
(result: any) => {
|
||||
() => {
|
||||
this.documentIds.remove((documentId: DocumentId) => documentId.rid === selectedDocumentId.rid);
|
||||
this.selectedDocumentContent("");
|
||||
this.selectedDocumentId(null);
|
||||
@@ -720,7 +696,7 @@ export default class DocumentsTab extends TabsBase {
|
||||
.finally(() => this.isExecuting(false));
|
||||
}
|
||||
|
||||
public createIterator(): Q.Promise<QueryIterator<ItemDefinition & Resource>> {
|
||||
public createIterator(): QueryIterator<ItemDefinition & Resource> {
|
||||
let filters = this.lastFilterContents();
|
||||
const filter: string = this.filterContent().trim();
|
||||
const query: string = this.buildQuery(filter);
|
||||
@@ -734,11 +710,10 @@ export default class DocumentsTab extends TabsBase {
|
||||
return queryDocuments(this.collection.databaseId, this.collection.id(), query, options);
|
||||
}
|
||||
|
||||
public selectDocument(documentId: DocumentId): Q.Promise<any> {
|
||||
public async selectDocument(documentId: DocumentId): Promise<void> {
|
||||
this.selectedDocumentId(documentId);
|
||||
return readDocument(this.collection, documentId).then((content: any) => {
|
||||
this.initDocumentEditor(documentId, content);
|
||||
});
|
||||
const content = await readDocument(this.collection, documentId);
|
||||
this.initDocumentEditor(documentId, content);
|
||||
}
|
||||
|
||||
public loadNextPage(): Q.Promise<any> {
|
||||
|
||||
@@ -114,10 +114,9 @@ export default class GraphTab extends TabsBase {
|
||||
: `${account.name}.graphs.azure.com:443/`;
|
||||
}
|
||||
|
||||
public onTabClick(): Q.Promise<any> {
|
||||
return super.onTabClick().then(() => {
|
||||
this.collection.selectedSubnodeKind(ViewModels.CollectionTabKind.Graph);
|
||||
});
|
||||
public onTabClick(): void {
|
||||
super.onTabClick();
|
||||
this.collection.selectedSubnodeKind(ViewModels.CollectionTabKind.Graph);
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
@@ -289,7 +289,7 @@
|
||||
<button
|
||||
class="filterbtnstyle queryButton"
|
||||
data-bind="
|
||||
click: onApplyFilterClick,
|
||||
click: refreshDocumentsGrid,
|
||||
enable: applyFilterButton.enabled"
|
||||
>
|
||||
Apply Filter
|
||||
|
||||
@@ -44,7 +44,7 @@ export default class MongoDocumentsTab extends DocumentsTab {
|
||||
super.buildCommandBarOptions();
|
||||
}
|
||||
|
||||
public onSaveNewDocumentClick = (): Q.Promise<any> => {
|
||||
public onSaveNewDocumentClick = (): Promise<any> => {
|
||||
const documentContent = JSON.parse(this.selectedDocumentContent());
|
||||
this.displayedError("");
|
||||
const startKey: number = TelemetryProcessor.traceStart(Action.CreateDocument, {
|
||||
@@ -78,12 +78,12 @@ export default class MongoDocumentsTab extends DocumentsTab {
|
||||
startKey
|
||||
);
|
||||
Logger.logError("Failed to save new document: Document shard key not defined", "MongoDocumentsTab");
|
||||
return Q.reject("Document without shard key");
|
||||
throw new Error("Document without shard key");
|
||||
}
|
||||
|
||||
this.isExecutionError(false);
|
||||
this.isExecuting(true);
|
||||
return Q(createDocument(this.collection.databaseId, this.collection, this.partitionKeyProperty, documentContent))
|
||||
return createDocument(this.collection.databaseId, this.collection, this.partitionKeyProperty, documentContent)
|
||||
.then(
|
||||
(savedDocument: any) => {
|
||||
let partitionKeyArray = extractPartitionKey(
|
||||
@@ -136,7 +136,7 @@ export default class MongoDocumentsTab extends DocumentsTab {
|
||||
.finally(() => this.isExecuting(false));
|
||||
};
|
||||
|
||||
public onSaveExisitingDocumentClick = (): Q.Promise<any> => {
|
||||
public onSaveExisitingDocumentClick = (): Promise<any> => {
|
||||
const selectedDocumentId = this.selectedDocumentId();
|
||||
const documentContent = this.selectedDocumentContent();
|
||||
this.isExecutionError(false);
|
||||
@@ -148,7 +148,7 @@ export default class MongoDocumentsTab extends DocumentsTab {
|
||||
tabTitle: this.tabTitle()
|
||||
});
|
||||
|
||||
return Q(updateDocument(this.collection.databaseId, this.collection, selectedDocumentId, documentContent))
|
||||
return updateDocument(this.collection.databaseId, this.collection, selectedDocumentId, documentContent)
|
||||
.then(
|
||||
(updatedDocument: any) => {
|
||||
let value: string = this.renderObjectForEditor(updatedDocument || {}, null, 4);
|
||||
@@ -204,13 +204,10 @@ export default class MongoDocumentsTab extends DocumentsTab {
|
||||
return filter || "{}";
|
||||
}
|
||||
|
||||
public selectDocument(documentId: DocumentId): Q.Promise<any> {
|
||||
public async selectDocument(documentId: DocumentId): Promise<void> {
|
||||
this.selectedDocumentId(documentId);
|
||||
return Q(
|
||||
readDocument(this.collection.databaseId, this.collection, documentId).then((content: any) => {
|
||||
this.initDocumentEditor(documentId, content);
|
||||
})
|
||||
);
|
||||
const content = await readDocument(this.collection.databaseId, this.collection, documentId);
|
||||
this.initDocumentEditor(documentId, content);
|
||||
}
|
||||
|
||||
public loadNextPage(): Q.Promise<any> {
|
||||
@@ -330,7 +327,7 @@ export default class MongoDocumentsTab extends DocumentsTab {
|
||||
return partitionKey;
|
||||
}
|
||||
|
||||
protected __deleteDocument(documentId: DocumentId): Q.Promise<any> {
|
||||
return Q(deleteDocument(this.collection.databaseId, this.collection, documentId));
|
||||
protected __deleteDocument(documentId: DocumentId): Promise<void> {
|
||||
return deleteDocument(this.collection.databaseId, this.collection, documentId);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -53,10 +53,9 @@ export default class MongoShellTab extends TabsBase {
|
||||
// }
|
||||
}
|
||||
|
||||
public onTabClick(): Q.Promise<any> {
|
||||
return super.onTabClick().then(() => {
|
||||
this.collection.selectedSubnodeKind(ViewModels.CollectionTabKind.Documents);
|
||||
});
|
||||
public onTabClick(): void {
|
||||
super.onTabClick();
|
||||
this.collection.selectedSubnodeKind(ViewModels.CollectionTabKind.Documents);
|
||||
}
|
||||
|
||||
public handleMessage(event: MessageEvent) {
|
||||
|
||||
@@ -15,9 +15,10 @@ import { QueryUtils } from "../../Utils/QueryUtils";
|
||||
import SaveQueryIcon from "../../../images/save-cosmos.svg";
|
||||
|
||||
import { MinimalQueryIterator } from "../../Common/IteratorUtilities";
|
||||
import { queryDocuments, queryDocumentsPage } from "../../Common/DocumentClientUtilityBase";
|
||||
import { CommandButtonComponentProps } from "../Controls/CommandButton/CommandButtonComponent";
|
||||
import { getErrorMessage, getErrorStack } from "../../Common/ErrorHandlingUtils";
|
||||
import { queryDocuments } from "../../Common/dataAccess/queryDocuments";
|
||||
import { queryDocumentsPage } from "../../Common/dataAccess/queryDocumentsPage";
|
||||
|
||||
enum ToggleState {
|
||||
Result,
|
||||
@@ -163,20 +164,19 @@ export default class QueryTab extends TabsBase implements ViewModels.WaitsForTem
|
||||
this._buildCommandBarOptions();
|
||||
}
|
||||
|
||||
public onTabClick(): Q.Promise<any> {
|
||||
return super.onTabClick().then(() => {
|
||||
this.collection && this.collection.selectedSubnodeKind(ViewModels.CollectionTabKind.Query);
|
||||
});
|
||||
public onTabClick(): void {
|
||||
super.onTabClick();
|
||||
this.collection && this.collection.selectedSubnodeKind(ViewModels.CollectionTabKind.Query);
|
||||
}
|
||||
|
||||
public onExecuteQueryClick = (): Q.Promise<any> => {
|
||||
public onExecuteQueryClick = async (): Promise<void> => {
|
||||
const sqlStatement: string = this.selectedContent() || this.sqlQueryEditorContent();
|
||||
this.sqlStatementToExecute(sqlStatement);
|
||||
this.allResultsMetadata([]);
|
||||
this.queryResults("");
|
||||
this._iterator = null;
|
||||
this._iterator = undefined;
|
||||
|
||||
return this._executeQueryDocumentsPage(0);
|
||||
await this._executeQueryDocumentsPage(0);
|
||||
};
|
||||
|
||||
public onLoadQueryClick = (): void => {
|
||||
@@ -191,13 +191,13 @@ export default class QueryTab extends TabsBase implements ViewModels.WaitsForTem
|
||||
this.collection && this.collection.container && this.collection.container.browseQueriesPane.open();
|
||||
};
|
||||
|
||||
public onFetchNextPageClick(): Q.Promise<any> {
|
||||
public async onFetchNextPageClick(): Promise<void> {
|
||||
const allResultsMetadata = (this.allResultsMetadata && this.allResultsMetadata()) || [];
|
||||
const metadata: ViewModels.QueryResultsMetadata = allResultsMetadata[allResultsMetadata.length - 1];
|
||||
const firstResultIndex: number = (metadata && Number(metadata.firstItemIndex)) || 1;
|
||||
const itemCount: number = (metadata && Number(metadata.itemCount)) || 0;
|
||||
|
||||
return this._executeQueryDocumentsPage(firstResultIndex + itemCount - 1);
|
||||
await this._executeQueryDocumentsPage(firstResultIndex + itemCount - 1);
|
||||
}
|
||||
|
||||
public onErrorDetailsClick = (src: any, event: MouseEvent): boolean => {
|
||||
@@ -265,19 +265,18 @@ export default class QueryTab extends TabsBase implements ViewModels.WaitsForTem
|
||||
return true;
|
||||
};
|
||||
|
||||
private _executeQueryDocumentsPage(firstItemIndex: number): Q.Promise<any> {
|
||||
private async _executeQueryDocumentsPage(firstItemIndex: number): Promise<any> {
|
||||
this.error("");
|
||||
this.roundTrips(undefined);
|
||||
if (this._iterator == null) {
|
||||
const queryIteratorPromise = this._initIterator();
|
||||
return queryIteratorPromise.finally(() => this._queryDocumentsPage(firstItemIndex));
|
||||
if (this._iterator === undefined) {
|
||||
this._initIterator();
|
||||
}
|
||||
|
||||
return this._queryDocumentsPage(firstItemIndex);
|
||||
await this._queryDocumentsPage(firstItemIndex);
|
||||
}
|
||||
|
||||
// TODO: Position and enable spinner when request is in progress
|
||||
private _queryDocumentsPage(firstItemIndex: number): Q.Promise<any> {
|
||||
private async _queryDocumentsPage(firstItemIndex: number): Promise<void> {
|
||||
this.isExecutionError(false);
|
||||
this._resetAggregateQueryMetrics();
|
||||
const startKey: number = TelemetryProcessor.traceStart(Action.ExecuteQuery, {
|
||||
@@ -289,90 +288,90 @@ export default class QueryTab extends TabsBase implements ViewModels.WaitsForTem
|
||||
let options: any = {};
|
||||
options.enableCrossPartitionQuery = HeadersUtility.shouldEnableCrossPartitionKey();
|
||||
|
||||
const queryDocuments = (firstItemIndex: number) =>
|
||||
queryDocumentsPage(this.collection && this.collection.id(), this._iterator, firstItemIndex, options);
|
||||
const queryDocuments = async (firstItemIndex: number) =>
|
||||
await queryDocumentsPage(this.collection && this.collection.id(), this._iterator, firstItemIndex);
|
||||
this.isExecuting(true);
|
||||
return QueryUtils.queryPagesUntilContentPresent(firstItemIndex, queryDocuments)
|
||||
.then(
|
||||
(queryResults: ViewModels.QueryResults) => {
|
||||
const allResultsMetadata = (this.allResultsMetadata && this.allResultsMetadata()) || [];
|
||||
const metadata: ViewModels.QueryResultsMetadata = allResultsMetadata[allResultsMetadata.length - 1];
|
||||
const resultsMetadata: ViewModels.QueryResultsMetadata = {
|
||||
hasMoreResults: queryResults.hasMoreResults,
|
||||
itemCount: queryResults.itemCount,
|
||||
firstItemIndex: queryResults.firstItemIndex,
|
||||
lastItemIndex: queryResults.lastItemIndex
|
||||
};
|
||||
this.allResultsMetadata.push(resultsMetadata);
|
||||
this.activityId(queryResults.activityId);
|
||||
this.roundTrips(queryResults.roundTrips);
|
||||
|
||||
this._updateQueryMetricsMap(queryResults.headers[Constants.HttpHeaders.queryMetrics]);
|
||||
try {
|
||||
const queryResults: ViewModels.QueryResults = await QueryUtils.queryPagesUntilContentPresent(
|
||||
firstItemIndex,
|
||||
queryDocuments
|
||||
);
|
||||
const allResultsMetadata = (this.allResultsMetadata && this.allResultsMetadata()) || [];
|
||||
const metadata: ViewModels.QueryResultsMetadata = allResultsMetadata[allResultsMetadata.length - 1];
|
||||
const resultsMetadata: ViewModels.QueryResultsMetadata = {
|
||||
hasMoreResults: queryResults.hasMoreResults,
|
||||
itemCount: queryResults.itemCount,
|
||||
firstItemIndex: queryResults.firstItemIndex,
|
||||
lastItemIndex: queryResults.lastItemIndex
|
||||
};
|
||||
this.allResultsMetadata.push(resultsMetadata);
|
||||
this.activityId(queryResults.activityId);
|
||||
this.roundTrips(queryResults.roundTrips);
|
||||
|
||||
if (queryResults.itemCount == 0 && metadata != null && metadata.itemCount >= 0) {
|
||||
// we let users query for the next page because the SDK sometimes specifies there are more elements
|
||||
// even though there aren't any so we should not update the prior query results.
|
||||
return;
|
||||
}
|
||||
this._updateQueryMetricsMap(queryResults.headers[Constants.HttpHeaders.queryMetrics]);
|
||||
|
||||
const documents: any[] = queryResults.documents;
|
||||
const results = this.renderObjectForEditor(documents, null, 4);
|
||||
if (queryResults.itemCount == 0 && metadata != null && metadata.itemCount >= 0) {
|
||||
// we let users query for the next page because the SDK sometimes specifies there are more elements
|
||||
// even though there aren't any so we should not update the prior query results.
|
||||
return;
|
||||
}
|
||||
|
||||
const resultsDisplay: string =
|
||||
queryResults.itemCount > 0 ? `${queryResults.firstItemIndex} - ${queryResults.lastItemIndex}` : `0 - 0`;
|
||||
this.showingDocumentsDisplayText(resultsDisplay);
|
||||
this.requestChargeDisplayText(`${queryResults.requestCharge} RUs`);
|
||||
const documents: any[] = queryResults.documents;
|
||||
const results = this.renderObjectForEditor(documents, null, 4);
|
||||
|
||||
if (!this.queryResults() && !results) {
|
||||
const errorMessage: string = JSON.stringify({
|
||||
error: `Returned no results after query execution`,
|
||||
accountName: this.collection && this.collection.container.databaseAccount(),
|
||||
databaseName: this.collection && this.collection.databaseId,
|
||||
collectionName: this.collection && this.collection.id(),
|
||||
sqlQuery: this.sqlStatementToExecute(),
|
||||
hasMoreResults: resultsMetadata.hasMoreResults,
|
||||
itemCount: resultsMetadata.itemCount,
|
||||
responseHeaders: queryResults && queryResults.headers
|
||||
});
|
||||
Logger.logError(errorMessage, "QueryTab");
|
||||
}
|
||||
const resultsDisplay: string =
|
||||
queryResults.itemCount > 0 ? `${queryResults.firstItemIndex} - ${queryResults.lastItemIndex}` : `0 - 0`;
|
||||
this.showingDocumentsDisplayText(resultsDisplay);
|
||||
this.requestChargeDisplayText(`${queryResults.requestCharge} RUs`);
|
||||
|
||||
this.queryResults(results);
|
||||
if (!this.queryResults() && !results) {
|
||||
const errorMessage: string = JSON.stringify({
|
||||
error: `Returned no results after query execution`,
|
||||
accountName: this.collection && this.collection.container.databaseAccount(),
|
||||
databaseName: this.collection && this.collection.databaseId,
|
||||
collectionName: this.collection && this.collection.id(),
|
||||
sqlQuery: this.sqlStatementToExecute(),
|
||||
hasMoreResults: resultsMetadata.hasMoreResults,
|
||||
itemCount: resultsMetadata.itemCount,
|
||||
responseHeaders: queryResults && queryResults.headers
|
||||
});
|
||||
Logger.logError(errorMessage, "QueryTab");
|
||||
}
|
||||
|
||||
TelemetryProcessor.traceSuccess(
|
||||
Action.ExecuteQuery,
|
||||
{
|
||||
databaseAccountName: this.collection && this.collection.container.databaseAccount().name,
|
||||
defaultExperience: this.collection && this.collection.container.defaultExperience(),
|
||||
dataExplorerArea: Constants.Areas.Tab,
|
||||
tabTitle: this.tabTitle()
|
||||
},
|
||||
startKey
|
||||
);
|
||||
this.queryResults(results);
|
||||
|
||||
TelemetryProcessor.traceSuccess(
|
||||
Action.ExecuteQuery,
|
||||
{
|
||||
databaseAccountName: this.collection && this.collection.container.databaseAccount().name,
|
||||
defaultExperience: this.collection && this.collection.container.defaultExperience(),
|
||||
dataExplorerArea: Constants.Areas.Tab,
|
||||
tabTitle: this.tabTitle()
|
||||
},
|
||||
(error: any) => {
|
||||
this.isExecutionError(true);
|
||||
const errorMessage = getErrorMessage(error);
|
||||
this.error(errorMessage);
|
||||
TelemetryProcessor.traceFailure(
|
||||
Action.ExecuteQuery,
|
||||
{
|
||||
databaseAccountName: this.collection && this.collection.container.databaseAccount().name,
|
||||
defaultExperience: this.collection && this.collection.container.defaultExperience(),
|
||||
dataExplorerArea: Constants.Areas.Tab,
|
||||
tabTitle: this.tabTitle(),
|
||||
error: errorMessage,
|
||||
errorStack: getErrorStack(error)
|
||||
},
|
||||
startKey
|
||||
);
|
||||
document.getElementById("error-display").focus();
|
||||
}
|
||||
)
|
||||
.finally(() => {
|
||||
this.isExecuting(false);
|
||||
this.togglesOnFocus();
|
||||
});
|
||||
startKey
|
||||
);
|
||||
} catch (error) {
|
||||
this.isExecutionError(true);
|
||||
const errorMessage = getErrorMessage(error);
|
||||
this.error(errorMessage);
|
||||
TelemetryProcessor.traceFailure(
|
||||
Action.ExecuteQuery,
|
||||
{
|
||||
databaseAccountName: this.collection && this.collection.container.databaseAccount().name,
|
||||
defaultExperience: this.collection && this.collection.container.defaultExperience(),
|
||||
dataExplorerArea: Constants.Areas.Tab,
|
||||
tabTitle: this.tabTitle(),
|
||||
error: errorMessage,
|
||||
errorStack: getErrorStack(error)
|
||||
},
|
||||
startKey
|
||||
);
|
||||
document.getElementById("error-display").focus();
|
||||
} finally {
|
||||
this.isExecuting(false);
|
||||
this.togglesOnFocus();
|
||||
}
|
||||
}
|
||||
|
||||
private _updateQueryMetricsMap(metricsMap: { [partitionKeyRange: string]: DataModels.QueryMetrics }): void {
|
||||
@@ -477,16 +476,17 @@ export default class QueryTab extends TabsBase implements ViewModels.WaitsForTem
|
||||
}
|
||||
}
|
||||
|
||||
protected _initIterator(): Q.Promise<MinimalQueryIterator> {
|
||||
protected _initIterator(): void {
|
||||
const options: any = QueryTab.getIteratorOptions(this.collection);
|
||||
if (this._resourceTokenPartitionKey) {
|
||||
options.partitionKey = this._resourceTokenPartitionKey;
|
||||
}
|
||||
|
||||
return Q(
|
||||
queryDocuments(this.collection.databaseId, this.collection.id(), this.sqlStatementToExecute(), options).then(
|
||||
iterator => (this._iterator = iterator)
|
||||
)
|
||||
this._iterator = queryDocuments(
|
||||
this.collection.databaseId,
|
||||
this.collection.id(),
|
||||
this.sqlStatementToExecute(),
|
||||
options
|
||||
);
|
||||
}
|
||||
|
||||
|
||||
@@ -161,17 +161,16 @@ export default class QueryTablesTab extends TabsBase {
|
||||
return null;
|
||||
};
|
||||
|
||||
public onActivate(): Q.Promise<any> {
|
||||
return super.onActivate().then(() => {
|
||||
const columns =
|
||||
!!this.tableEntityListViewModel() &&
|
||||
!!this.tableEntityListViewModel().table &&
|
||||
this.tableEntityListViewModel().table.columns;
|
||||
if (!!columns) {
|
||||
columns.adjust();
|
||||
$(window).resize();
|
||||
}
|
||||
});
|
||||
public onActivate(): void {
|
||||
super.onActivate();
|
||||
const columns =
|
||||
!!this.tableEntityListViewModel() &&
|
||||
!!this.tableEntityListViewModel().table &&
|
||||
this.tableEntityListViewModel().table.columns;
|
||||
if (!!columns) {
|
||||
columns.adjust();
|
||||
$(window).resize();
|
||||
}
|
||||
}
|
||||
|
||||
protected getTabsButtons(): CommandButtonComponentProps[] {
|
||||
|
||||
@@ -186,12 +186,11 @@ export default abstract class ScriptTabBase extends TabsBase implements ViewMode
|
||||
this._setBaselines();
|
||||
}
|
||||
|
||||
public onTabClick(): Q.Promise<any> {
|
||||
return super.onTabClick().then(() => {
|
||||
if (this.isNew()) {
|
||||
this.collection.selectedSubnodeKind(this.tabKind);
|
||||
}
|
||||
});
|
||||
public onTabClick(): void {
|
||||
super.onTabClick();
|
||||
if (this.isNew()) {
|
||||
this.collection.selectedSubnodeKind(this.tabKind);
|
||||
}
|
||||
}
|
||||
|
||||
public abstract onSaveClick: () => Promise<any>;
|
||||
|
||||
@@ -42,54 +42,49 @@ export default class SettingsTabV2 extends TabsBase {
|
||||
});
|
||||
}
|
||||
|
||||
public onActivate(): Q.Promise<unknown> {
|
||||
this.isExecuting(true);
|
||||
this.currentCollection.loadOffer().then(
|
||||
() => {
|
||||
// passed in options and set by parent as "Settings" by default
|
||||
this.tabTitle(this.currentCollection.offer() ? "Settings" : "Scale & Settings");
|
||||
this.offerRead(true);
|
||||
this.options.getPendingNotification.then(
|
||||
(data: DataModels.Notification) => {
|
||||
this.notification = data;
|
||||
this.notificationRead(true);
|
||||
this.isExecuting(false);
|
||||
},
|
||||
error => {
|
||||
const errorMessage = getErrorMessage(error);
|
||||
this.notification = undefined;
|
||||
this.notificationRead(true);
|
||||
this.isExecuting(false);
|
||||
traceFailure(
|
||||
Action.Tab,
|
||||
{
|
||||
databaseAccountName: this.options.collection.container.databaseAccount().name,
|
||||
databaseName: this.options.collection.databaseId,
|
||||
collectionName: this.options.collection.id(),
|
||||
defaultExperience: this.options.collection.container.defaultExperience(),
|
||||
dataExplorerArea: Constants.Areas.Tab,
|
||||
tabTitle: this.tabTitle,
|
||||
error: errorMessage,
|
||||
errorStack: getErrorStack(error)
|
||||
},
|
||||
this.options.onLoadStartKey
|
||||
);
|
||||
logConsoleError(
|
||||
`Error while fetching container settings for container ${this.options.collection.id()}: ${errorMessage}`
|
||||
);
|
||||
throw error;
|
||||
}
|
||||
);
|
||||
},
|
||||
() => {
|
||||
this.offerRead(true);
|
||||
this.isExecuting(false);
|
||||
}
|
||||
);
|
||||
public async onActivate(): Promise<void> {
|
||||
try {
|
||||
this.isExecuting(true);
|
||||
await this.currentCollection.loadOffer();
|
||||
// passed in options and set by parent as "Settings" by default
|
||||
this.tabTitle(this.currentCollection.offer() ? "Settings" : "Scale & Settings");
|
||||
|
||||
return super.onActivate().then(() => {
|
||||
this.collection.selectedSubnodeKind(ViewModels.CollectionTabKind.SettingsV2);
|
||||
});
|
||||
this.options.getPendingNotification.then(
|
||||
(data: DataModels.Notification) => {
|
||||
this.notification = data;
|
||||
this.notificationRead(true);
|
||||
},
|
||||
error => {
|
||||
const errorMessage = getErrorMessage(error);
|
||||
this.notification = undefined;
|
||||
this.notificationRead(true);
|
||||
traceFailure(
|
||||
Action.Tab,
|
||||
{
|
||||
databaseAccountName: this.options.collection.container.databaseAccount().name,
|
||||
databaseName: this.options.collection.databaseId,
|
||||
collectionName: this.options.collection.id(),
|
||||
defaultExperience: this.options.collection.container.defaultExperience(),
|
||||
dataExplorerArea: Constants.Areas.Tab,
|
||||
tabTitle: this.tabTitle,
|
||||
error: errorMessage,
|
||||
errorStack: getErrorStack(error)
|
||||
},
|
||||
this.options.onLoadStartKey
|
||||
);
|
||||
logConsoleError(
|
||||
`Error while fetching container settings for container ${this.options.collection.id()}: ${errorMessage}`
|
||||
);
|
||||
throw error;
|
||||
}
|
||||
);
|
||||
} finally {
|
||||
this.offerRead(true);
|
||||
this.isExecuting(false);
|
||||
}
|
||||
|
||||
super.onActivate();
|
||||
this.collection.selectedSubnodeKind(ViewModels.CollectionTabKind.SettingsV2);
|
||||
}
|
||||
|
||||
public getSettingsTabContainer(): Explorer {
|
||||
|
||||
@@ -94,9 +94,8 @@ export default class TabsBase extends WaitsForTemplateViewModel {
|
||||
});
|
||||
}
|
||||
|
||||
public onTabClick(): Q.Promise<any> {
|
||||
public onTabClick(): void {
|
||||
this.getContainer().tabsManager.activateTab(this);
|
||||
return Q();
|
||||
}
|
||||
|
||||
protected updateSelectedNode(): void {
|
||||
@@ -128,7 +127,7 @@ export default class TabsBase extends WaitsForTemplateViewModel {
|
||||
return this.onSpaceOrEnterKeyPress(event, () => this.onCloseTabButtonClick());
|
||||
};
|
||||
|
||||
public onActivate(): Q.Promise<any> {
|
||||
public onActivate(): void {
|
||||
this.updateSelectedNode();
|
||||
if (!!this.collection) {
|
||||
this.collection.selectedSubnodeKind(this.tabKind);
|
||||
@@ -151,7 +150,6 @@ export default class TabsBase extends WaitsForTemplateViewModel {
|
||||
tabTitle: this.tabTitle(),
|
||||
tabId: this.tabId
|
||||
});
|
||||
return Q();
|
||||
}
|
||||
|
||||
public onErrorDetailsClick = (src: any, event: MouseEvent): boolean => {
|
||||
|
||||
Reference in New Issue
Block a user