mirror of https://github.com/apache/druid.git
137 lines
4.5 KiB
TypeScript
137 lines
4.5 KiB
TypeScript
/*
|
|
* Licensed to the Apache Software Foundation (ASF) under one
|
|
* or more contributor license agreements. See the NOTICE file
|
|
* distributed with this work for additional information
|
|
* regarding copyright ownership. The ASF licenses this file
|
|
* to you under the Apache License, Version 2.0 (the
|
|
* "License"); you may not use this file except in compliance
|
|
* with the License. You may obtain a copy of the License at
|
|
*
|
|
* http://www.apache.org/licenses/LICENSE-2.0
|
|
*
|
|
* Unless required by applicable law or agreed to in writing, software
|
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
* See the License for the specific language governing permissions and
|
|
* limitations under the License.
|
|
*/
|
|
|
|
import 'core-js/stable';
|
|
import 'regenerator-runtime/runtime';
|
|
import './bootstrap/ace';
|
|
|
|
import { QueryRunner } from '@druid-toolkit/query';
|
|
import React from 'react';
|
|
import { createRoot } from 'react-dom/client';
|
|
|
|
import { bootstrapJsonParse } from './bootstrap/json-parser';
|
|
import { bootstrapReactTable } from './bootstrap/react-table-defaults';
|
|
import { ConsoleApplication } from './console-application';
|
|
import type { Links } from './links';
|
|
import { setLinkOverrides } from './links';
|
|
import { Api, UrlBaser } from './singletons';
|
|
import { setLocalStorageNamespace } from './utils';
|
|
|
|
import './entry.scss';
|
|
|
|
bootstrapReactTable();
|
|
bootstrapJsonParse();
|
|
|
|
const container = document.getElementsByClassName('app-container')[0];
|
|
if (!container) throw new Error('container not found');
|
|
|
|
interface ConsoleConfig {
|
|
// A custom title for the page
|
|
title?: string;
|
|
|
|
// An alternative URL which to use for the stem of an AJAX call
|
|
baseURL?: string;
|
|
|
|
// A custom header name/value to set on every AJAX request
|
|
customHeaderName?: string;
|
|
customHeaderValue?: string;
|
|
|
|
// A set of custom headers name/value to set on every AJAX request
|
|
customHeaders?: Record<string, string>;
|
|
|
|
// The query context to set if the user does not have one saved in local storage, defaults to {}
|
|
defaultQueryContext?: Record<string, any>;
|
|
|
|
// Extra context properties that will be added to all query requests
|
|
mandatoryQueryContext?: Record<string, any>;
|
|
|
|
// Allow for link overriding to different docs
|
|
linkOverrides?: Links;
|
|
|
|
// Allow for namespacing the local storage in case multiple clusters share a URL due to proxying
|
|
localStorageNamespace?: string;
|
|
}
|
|
|
|
const consoleConfig: ConsoleConfig = (window as any).consoleConfig;
|
|
if (typeof consoleConfig.title === 'string') {
|
|
window.document.title = consoleConfig.title;
|
|
}
|
|
|
|
const apiConfig = Api.getDefaultConfig();
|
|
|
|
if (consoleConfig.baseURL) {
|
|
apiConfig.baseURL = consoleConfig.baseURL;
|
|
UrlBaser.baseUrl = consoleConfig.baseURL;
|
|
}
|
|
if (consoleConfig.customHeaderName && consoleConfig.customHeaderValue) {
|
|
// The apiConfig.headers is a union type and TS does not like this assigment
|
|
(apiConfig.headers as any)[consoleConfig.customHeaderName] = consoleConfig.customHeaderValue;
|
|
}
|
|
if (consoleConfig.customHeaders) {
|
|
Object.assign(apiConfig.headers!, consoleConfig.customHeaders);
|
|
}
|
|
|
|
Api.initialize(apiConfig);
|
|
|
|
if (consoleConfig.linkOverrides) {
|
|
setLinkOverrides(consoleConfig.linkOverrides);
|
|
}
|
|
|
|
if (consoleConfig.localStorageNamespace) {
|
|
setLocalStorageNamespace(consoleConfig.localStorageNamespace);
|
|
}
|
|
|
|
QueryRunner.defaultQueryExecutor = (payload, isSql, cancelToken) => {
|
|
return Api.instance.post(`/druid/v2${isSql ? '/sql' : ''}`, payload, { cancelToken });
|
|
};
|
|
|
|
const root = createRoot(container);
|
|
|
|
root.render(
|
|
React.createElement(ConsoleApplication, {
|
|
defaultQueryContext: consoleConfig.defaultQueryContext,
|
|
mandatoryQueryContext: consoleConfig.mandatoryQueryContext,
|
|
}),
|
|
);
|
|
|
|
// ---------------------------------
|
|
// Taken from https://hackernoon.com/removing-that-ugly-focus-ring-and-keeping-it-too-6c8727fefcd2
|
|
|
|
let mode: 'mouse' | 'tab' = 'mouse';
|
|
|
|
function handleTab(e: KeyboardEvent) {
|
|
if (e.key !== 'Tab') return;
|
|
if (mode === 'tab') return;
|
|
mode = 'tab';
|
|
document.body.classList.remove('mouse-mode');
|
|
document.body.classList.add('tab-mode');
|
|
window.removeEventListener('keydown', handleTab);
|
|
window.addEventListener('mousedown', handleMouseDown);
|
|
}
|
|
|
|
function handleMouseDown() {
|
|
if (mode === 'mouse') return;
|
|
mode = 'mouse';
|
|
document.body.classList.remove('tab-mode');
|
|
document.body.classList.add('mouse-mode');
|
|
window.removeEventListener('mousedown', handleMouseDown);
|
|
window.addEventListener('keydown', handleTab);
|
|
}
|
|
|
|
window.addEventListener('keydown', handleTab);
|