Yuki Takei 6 лет назад
Родитель
Сommit
44b56f954d

+ 1 - 0
resource/locales/en-US/translation.json

@@ -626,6 +626,7 @@
     "connection_status_label_unconfigured": "UNCONFIGURED",
     "connection_status_label_connected": "CONNECTED",
     "connection_status_label_disconnected": "DISCONNECTED",
+    "connection_status_label_erroroccured": "ERROR OCCURED ON SEARCH SERVICE",
     "indices_status": "Indices Status",
     "indices_status_label_normalized": "NORMALIZED",
     "indices_status_label_unnormalized": "REBUILDING or BROKEN",

+ 1 - 0
resource/locales/ja/translation.json

@@ -615,6 +615,7 @@
     "connection_status_label_unconfigured": "設定されていません",
     "connection_status_label_connected": "接続されています",
     "connection_status_label_disconnected": "切断されています",
+    "connection_status_label_erroroccured": "SearchService でエラーが発生しています",
     "indices_status": "インデックスの状態",
     "indices_status_label_normalized": "正規化されています",
     "indices_status_label_unnormalized": "リビルド中 または 破損しています",

+ 21 - 8
src/client/js/components/Admin/ElasticsearchManagement/ElasticsearchManagement.jsx

@@ -18,8 +18,10 @@ class ElasticsearchManagement extends React.Component {
     super(props);
 
     this.state = {
-      isConfigured: null,
-      isConnected: null,
+      isInitialized: false,
+
+      isConnected: false,
+      isConfigured: false,
       isRebuildingProcessing: false,
       isRebuildingCompleted: false,
 
@@ -69,8 +71,8 @@ class ElasticsearchManagement extends React.Component {
       const { info } = await appContainer.apiv3Get('/search/indices');
 
       this.setState({
-        isConfigured: true,
         isConnected: true,
+        isConfigured: true,
 
         indicesData: info.indices,
         aliasesData: info.aliases,
@@ -89,11 +91,16 @@ class ElasticsearchManagement extends React.Component {
 
       toastError(errors);
     }
+    finally {
+      this.setState({ isInitialized: true });
+    }
   }
 
   async reconnect() {
     const { appContainer } = this.props;
 
+    this.setState({ isInitialized: false });
+
     try {
       await appContainer.apiv3Post('/search/connection');
       toastSuccess('Reconnecting to Elasticsearch has succeeded');
@@ -138,19 +145,26 @@ class ElasticsearchManagement extends React.Component {
   }
 
   render() {
-    const { t } = this.props;
+    const { t, appContainer } = this.props;
     const {
-      isConfigured, isConnected, isRebuildingProcessing, isRebuildingCompleted,
+      isInitialized,
+      isConnected, isConfigured, isRebuildingProcessing, isRebuildingCompleted,
       isNormalized, indicesData, aliasesData,
     } = this.state;
 
+    const isErrorOccuredOnSearchService = !appContainer.config.isSearchServiceReachable;
+
+    const isReconnectBtnEnabled = !isInitialized || !isConnected || isErrorOccuredOnSearchService;
+
     return (
       <>
         <div className="row">
           <div className="col-xs-12">
             <StatusTable
-              isConfigured={isConfigured}
+              isInitialized={isInitialized}
+              isErrorOccuredOnSearchService={isErrorOccuredOnSearchService}
               isConnected={isConnected}
+              isConfigured={isConfigured}
               isNormalized={isNormalized}
               indicesData={indicesData}
               aliasesData={aliasesData}
@@ -165,8 +179,7 @@ class ElasticsearchManagement extends React.Component {
           <label className="col-xs-3 control-label">{ t('full_text_search_management.reconnect') }</label>
           <div className="col-xs-6">
             <ReconnectControls
-              isConfigured={isConfigured}
-              isConnected={isConnected}
+              isEnabled={isReconnectBtnEnabled}
               onReconnectingRequested={this.reconnect}
             />
           </div>

+ 2 - 5
src/client/js/components/Admin/ElasticsearchManagement/ReconnectControls.jsx

@@ -7,9 +7,7 @@ import { createSubscribedElement } from '../../UnstatedUtils';
 class ReconnectControls extends React.PureComponent {
 
   render() {
-    const { t, isConfigured, isConnected } = this.props;
-
-    const isEnabled = (isConfigured == null || isConfigured === true) && isConnected === false;
+    const { t, isEnabled } = this.props;
 
     return (
       <>
@@ -41,8 +39,7 @@ const ReconnectControlsWrapper = (props) => {
 ReconnectControls.propTypes = {
   t: PropTypes.func.isRequired, // i18next
 
-  isConfigured: PropTypes.bool,
-  isConnected: PropTypes.bool,
+  isEnabled: PropTypes.bool,
   onReconnectingRequested: PropTypes.func.isRequired,
 };
 

+ 54 - 23
src/client/js/components/Admin/ElasticsearchManagement/StatusTable.jsx

@@ -6,6 +6,46 @@ import { createSubscribedElement } from '../../UnstatedUtils';
 
 class StatusTable extends React.PureComponent {
 
+  renderPreInitializedLabel() {
+    return <span className="label label-default">――</span>;
+  }
+
+  renderConnectionStatusLabels() {
+    const { t } = this.props;
+    const {
+      isErrorOccuredOnSearchService,
+      isConnected, isConfigured,
+    } = this.props;
+
+    const errorOccuredLabel = isErrorOccuredOnSearchService
+      ? <span className="label label-danger ml-2">{ t('full_text_search_management.connection_status_label_erroroccured') }</span>
+      : null;
+
+    let connectionStatusLabel = null;
+    if (!isConfigured) {
+      connectionStatusLabel = <span className="label label-default">{ t('full_text_search_management.connection_status_label_unconfigured') }</span>;
+    }
+    else {
+      connectionStatusLabel = isConnected
+        ? <span className="label label-success">{ t('full_text_search_management.connection_status_label_connected') }</span>
+        : <span className="label label-danger">{ t('full_text_search_management.connection_status_label_disconnected') }</span>;
+    }
+
+    return (
+      <>
+        {connectionStatusLabel}{errorOccuredLabel}
+      </>
+    );
+  }
+
+  renderIndicesStatusLabel() {
+    const { t, isNormalized } = this.props;
+
+    return isNormalized
+      ? <span className="label label-info">{ t('full_text_search_management.indices_status_label_normalized') }</span>
+      : <span className="label label-warning">{ t('full_text_search_management.indices_status_label_unnormalized') }</span>;
+  }
+
   renderIndexInfoPanel(indexName, body = {}, aliases = []) {
     const collapseId = `collapse-${indexName}`;
 
@@ -95,41 +135,29 @@ class StatusTable extends React.PureComponent {
 
   render() {
     const { t } = this.props;
-    const { isConfigured, isConnected, isNormalized } = this.props;
-
-
-    let connectionStatusLabel = <span className="label label-default">――</span>;
-    if (isConfigured != null && !isConfigured) {
-      connectionStatusLabel = <span className="label label-default">{ t('full_text_search_management.connection_status_label_unconfigured') }</span>;
-    }
-    else if (isConnected != null) {
-      connectionStatusLabel = isConnected
-        ? <span className="label label-success">{ t('full_text_search_management.connection_status_label_connected') }</span>
-        : <span className="label label-danger">{ t('full_text_search_management.connection_status_label_disconnected') }</span>;
-    }
-
-    let indicesStatusLabel = <span className="label label-default">――</span>;
-    if (isNormalized != null) {
-      indicesStatusLabel = isNormalized
-        ? <span className="label label-info">{ t('full_text_search_management.indices_status_label_normalized') }</span>
-        : <span className="label label-warning">{ t('full_text_search_management.indices_status_label_unnormalized') }</span>;
-    }
+    const {
+      isInitialized,
+    } = this.props;
 
     return (
       <table className="table table-bordered">
         <tbody>
           <tr>
             <th>{ t('full_text_search_management.connection_status') }</th>
-            <td>{connectionStatusLabel}</td>
+            <td>
+              { isInitialized ? this.renderConnectionStatusLabels() : this.renderPreInitializedLabel() }
+            </td>
           </tr>
           <tr>
             <th>{ t('full_text_search_management.indices_status') }</th>
-            <td>{indicesStatusLabel}</td>
+            <td>
+              { isInitialized ? this.renderIndicesStatusLabel() : this.renderPreInitializedLabel() }
+            </td>
           </tr>
           <tr>
             <th className="col-sm-4">{ t('full_text_search_management.indices_summary') }</th>
             <td className="p-4">
-              { this.renderIndexInfoPanels() }
+              { isInitialized && this.renderIndexInfoPanels() }
             </td>
           </tr>
         </tbody>
@@ -149,8 +177,11 @@ const StatusTableWrapper = (props) => {
 StatusTable.propTypes = {
   t: PropTypes.func.isRequired, // i18next
 
-  isConfigured: PropTypes.bool,
+  isInitialized: PropTypes.bool,
+  isErrorOccuredOnSearchService: PropTypes.bool,
+
   isConnected: PropTypes.bool,
+  isConfigured: PropTypes.bool,
   isNormalized: PropTypes.bool,
   indicesData: PropTypes.object,
   aliasesData: PropTypes.object,