Skip to content

[SR] Create and edit repositories UI#34020

Merged
jen-huang merged 29 commits intoelastic:feature/snapshotsfrom
jen-huang:feature/snapshots-create-repo
Apr 3, 2019
Merged

[SR] Create and edit repositories UI#34020
jen-huang merged 29 commits intoelastic:feature/snapshotsfrom
jen-huang:feature/snapshots-create-repo

Conversation

@jen-huang
Copy link
Copy Markdown
Contributor

Summary

This PR adds ability to create and edit repositories from the Snapshot and Restore app UI. All repository types are supported, including plugin-based repositories! Instructions for setting up repositories are below. After creating or editing a repository, the user will be redirected back to repository list with the newly created or edited repository details flyout open.

Note: The forms do not have client-side validation yet. I will add that next.

This PR also adds repository verification information to the UI, so that users can see which repositories are connected and which ones may potentially have configuration issues.


Instructions

Instructions for setting up repositories for testing

File system

  1. Add the file system path you want to use to elasticsearch.yml or as part of starting up ES:
path:
  repo: /tmp/es-backups

or

yarn es snapshot --license trial -E path.repo=/tmp/es-backups
  1. Use Console to add repository, use the file system path above as location setting:
PUT /_snapshot/my_backup
{
  "type": "fs",
  "settings": {
    "location": "/tmp/es-backups",
    "chunk_size": "10mb"
  }
}
  1. Adjust settings as necessary, all available settings can be found in docs:
    https://www.elastic.co/guide/en/elasticsearch/reference/master/modules-snapshots.html#_shared_file_system_repository

Readonly

Readonly repositories only take url setting. Documentation: https://www.elastic.co/guide/en/elasticsearch/reference/master/modules-snapshots.html#_read_only_url_repository

It's easy to set up a file: url:

PUT _snapshot/my_readonly_repository
{
  "type": "url",
  "settings": {
    "url": "file:///tmp/es-backups"
  }
}

Source only

Source only repositories are special in that they are basically a wrapper around another repository type. Documentation: https://www.elastic.co/guide/en/elasticsearch/reference/master/modules-snapshots.html#_source_only_repository

This means that the settings that are available depends on the delegate_type parameter. For example, this source only repository delegates to fs (file system) type, so all file system rules and available settings apply:

PUT _snapshot/my_src_only_repository
{
  "type" : "source",
  "settings" : {
    "delegate_type" : "fs",
    "location" : "/tmp/es-backups"
  }
}

Plugin-based repositories:

There are four official repository plugins available: S3, GCS, HDFS, Azure. Please refer to the meta ticket Developer notes section : https://github.com/elastic/elasticsearch-team/issues/118

Available plugin repository settings can be found in docs: https://www.elastic.co/guide/en/elasticsearch/plugins/master/repository.html


Screenshots

Verification status in repository list table:
image

Verification status and details in repository details:
image

Register (create) repository form:
image

The form changes based on repository type. Here's a source repository type that delegates to azure:
image

Edit repository form, note that the name and type fields are not editable:
image

@jen-huang jen-huang added the Team:Kibana Management Dev Tools, Index Management, Upgrade Assistant, ILM, Ingest Node Pipelines, and more t// label Mar 27, 2019
@jen-huang jen-huang requested review from cjcenizal and sebelga March 27, 2019 23:48
@elasticmachine
Copy link
Copy Markdown
Contributor

Pinging @elastic/es-ui

@elasticmachine

This comment has been minimized.


import Boom from 'boom';

function extractCausedByChain(causedBy = {}, accumulator = []) {
Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

the changes here are copied from the changes done in CCR to surface ES messages to UI:
https://github.com/elastic/kibana/blob/master/x-pack/plugins/cross_cluster_replication/server/lib/error_wrappers/wrap_es_error.js

@elasticmachine

This comment has been minimized.

@elasticmachine

This comment has been minimized.

@elasticmachine

This comment has been minimized.

@elasticmachine
Copy link
Copy Markdown
Contributor

💚 Build Succeeded

@yaronp68
Copy link
Copy Markdown

yaronp68 commented Mar 28, 2019

@jen-huang I propose to remove the delegate combo and have a toggle for source (source only snapshots)
Another improvement might e is to point to the documentation of repositories plugin next to the list of repo types

@yaronp68
Copy link
Copy Markdown

Another comment - when additional custom settings are supported instead of {} place holder show an example like {my_settings: my_value}

Copy link
Copy Markdown
Contributor

@sebelga sebelga left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Amazing work @jen-huang ! I tested locally and works fine. I did not test any of the plugins as I did not manage to install them (azure, s3, ...).

In the review changes, I made mainly comments about style/personal preferences/reusability of code. Let me know if you agree with me.

There is a very small UI bug. When you click "edit" on a repository, then once in the form you click "cancel", you get back to the table list but with the detail, panel opened.


Note: I am a bit concerned about all the repeated logic in our forms I must say. We are constantly repeating the same pattern in all our apps (ccr, remote clusters, here) for our form rows:

  • Title
  • Description
  • Input label
  • type (text, number, toggle, select)
  • validation

It would be so much simpler, consistent, more robust and faster to build those forms through a Schema. Maybe there is no time to do it now, but I had to mention it 😊 I'll see if I can investigate and find a solution for this ater the testing.

import {
EuiButton,
EuiButtonEmpty,
// @ts-ignore
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

For the missing types from eui, it would be better to create the @elastic/eui folder inside the "typings" folder (from x-pack). And add a index.d.ts file there with

declare module '@elastic/eui' {
  export const EuiDescribedFormGroup: React.SFC<any>;
}

So that's the folder structure:

x-pack > typings > @elastic > eui > index.d.ts

So when eui will provide the type we can just delete our declaration here.

EuiFormRow,
EuiSelect,
EuiSpacer,
// @ts-ignore
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think we can remove this, as EuiSuperSelect is not used

repository: originalRepository,
isEditing,
isSaving,
saveError,
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The naming is a bit misleading 😊 saveError sound like a method... to save the error! I prefer just error. If we had have multiple error type then

errors: {
  save: <some error>,
  delete: <some error>,
}

path: chrome.addBasePath(`${API_BASE_PATH}repository_types`),
method: 'get',
httpClient: http.getClient(),
});
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think that the same way we had actions creators in Redux, we should have requests creators so we have a single place to modify and update them. I played a bit, this is what I came with:

// services/http/http_services.ts

class HttpService {
  private client: any;

  public addBasePath: (path: string) => string = () => '';

  public init(httpClient: any, chrome: any) {
    this.addBasePath = chrome.addBasePath.bind(chrome);
    this.client = httpClient;
  }

  get httpClient() {
    return this.client;
  }
}

export const httpService = new HttpService();
// we instantiate it in our main index.tsx file

...
import { httpService } from './services/http';

...

const {
  i18n: { Context: I18nContext },
  http,
  chrome,
} = core;

const appDependencies: AppDependencies = {
  core,
  plugins,
};

DependenciesContext = createContext<AppDependencies>(appDependencies);
httpService.init(http.getClient(), chrome);

...
// Our "requests" creators (./services/http/requests.ts)

import { API_BASE_PATH } from '../../../../common/constants';

import { httpService } from './http_service';
import { useRequest } from './use_request';

export const loadRepositoryTypes = () =>
  useRequest({
    path: httpService.addBasePath(`${API_BASE_PATH}repository_types`),
    method: 'get',
    httpClient: httpService.httpClient,
  });
// repository_form.tsx

...
import { loadRepositoryTypes } from '../../services/http';

// Then we simply have this here

const {
    core: {
      i18n: { FormattedMessage },
    },
  } = useAppDependencies();

  const {
    error: repositoryTypesError,
    loading: repositoryTypesLoading,
    data: repositoryTypes,
  } = loadRepositoryTypes();

What do you think?

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I like this idea, personally. Then we don't need to pass around chrome and http.

() => {
const repositoryTypeOptions = [...repositoryTypes];
const { type } = repository;
if (isEditing && REPOSITORY_PLUGINS_MAP[type] && !repositoryTypes.includes(type)) {
Copy link
Copy Markdown
Contributor

@sebelga sebelga Mar 29, 2019

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Curious to know why is this only executed on isEditing ?

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

this is for an edge case like the following:

  1. user creates plugin-based repository like s3
  2. user uninstalls plugin for some reason
  3. repository will still exist and show in the list, but the list of types available will not include s3, so this logic pushes the repository into the list anyway

this scenario is not encountered for creation of a new repository, hence the isEditing check 🙂

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ah ok, I see

error,
loading,
data: { repository, verification },
} = useRequest({
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

To be changed if we go the "requests creator" path 😊

setIsSaving(true);
setSaveError(null);
const { name } = newRepository;
const { error } = await sendRequest({
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Here too it'd be cleaner a request creator: await saveRepository(newRepository)

/**
* Utility to remove empty fields ("") from repository settings
*/
export const cleanSettings = (settings: Repository['settings']) =>
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We might want to be able to use the same method for other forms object? What about naming it something like removeEmptyStringsFromObject(...). It could even do it deeply (with an optional parameter), but then you'd be passing the interview a second time 😄

Copy link
Copy Markdown
Contributor

@cjcenizal cjcenizal Apr 1, 2019

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Just to play devil's advocate, I think there is a benefit to preserving this as specialized logic for cleaning the settings object, as opposed to generalizing it. In its current form it's really clear to me what its purpose is: empty strings have a special meaning in the context of the settings object, and this logic tells me that we don't want to keep them (for some reason). It's really simple to grok the intention behind this code. I understand that there's a business rule here and if we make changes to this code it will because we're adapting to changes in the business rule.

On the other hand, if we extract this out into a generalized utility, now the context has changed and we've invited new features (like the ability to clean an object deeply, which may not be necessary or even desired for our use case). If our business rules change then adapting the code is not as simple. As a contrived example, if we switch to using null instead of empty strings, then we'd need to either modify the generalized function and make sure we're not breaking anything for consumers, or write entirely new code.

Based on these pros and cons I really don't think we should bother generalizing this. :)

Copy link
Copy Markdown
Contributor

@sebelga sebelga Apr 2, 2019

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The more I keep reading about functional programming the more we will have a discrepancy on this. 😊 In lean towards functions that do not have any business "specialized logic" baked in them. I believe in small functions that do 1 thing well and that are composable (especially utilities functions).

In the composition of those small function resides the business logic.

In the long run, it makes code cleaner, the webpage faster (no need to send the same JS over and over in differents .bundle.js), lower memory footprint, and I would even say more robust as the same piece of code is being executed hundreds of time (and thus fully tested).
And it goes without saying the fact that it saves in development time by not having to re-think, re-write and re-test the same exact code.

I mention it because.... I wrote a very similar function in CCR I think 😊 and the "empty strings have a special meaning in the context of the settings object" statement is not totally true. We need it in all those scenarios where we don't want the client to send form fields that haven't been modified.


const unmountReactApp = (elem: Element | undefined | null): void => {
const unmountReactApp = (): void => {
const elem = document.getElementById(REACT_ROOT_ID);
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Are you sure about this refactor? We kept the reference to the elem outside so we could unmount the react app without losing the reference to the dom node (as Angular was creating a new div in the DOM)...

Did you fully test this?

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

yep. these changes were made due to the react app mounting twice when navigating away and coming back (React dev tools showed 2 apps)

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ok.... then we might have the bug in our other apps as they are all using this pattern. I'll check.

/**
* Utility to coerce ES boolean strings to actual booleans
*/
export const booleanizeSettings = (repository: Repository) => {
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Same comment as above. I'd give it a generic name so it could be used and reused at will 😊

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Maybe as a compromise we can follow the rule of threes, and wait for multiple use cases to arise before generalizing?

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

So here I was just saying to give it a generic name. By now we should have a common library of all those generic utils functions instead of re-writing them over and over.

…inition file for some EUI components to x-pack, rename saveError
Copy link
Copy Markdown
Contributor

@cjcenizal cjcenizal left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is terrific! I had a few suggestions about UI/UX, but nothing that can't be addressed later. I will be able to hop onboard this week so I can even address them myself if you prefer.

Objects are misrendering in detail panel

Looks like object details are rendering as [object Object]. I didn't dig into it, but maybe we just need to do some JSON stringifying?

image

Type doclink needs grow={false}

Looks like this button is expanding to fill the container. I think we just need grow={false} on the EuiFlexItem that contains it.

image

Edit button could be a link

Can we make the "Edit" button a link so users can open it in a new tab?

image

Standardizing the detail panel

In the Rollup Jobs list, we have two columns in the detail panel and we make the value of each stat stand out more than the label. Can we tweak this detail panel to match this pattern?

image

image

<div>
<Switch>
<Redirect exact from={`${BASE_PATH}`} to={`${BASE_PATH}/repositories`} />
<Route exact path={`${BASE_PATH}/repositories/add`} component={RepositoryAdd} />
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I just found one limitation with encoding the name of the entity you're viewing in the URL, which is that you can't give it a name which conflicts with other routes. For example, if you name a repository "add" the router will never let you view its details.

image

I know this is kind of a silly corner case, but I think it's worth addressing. I can think of three solutions:

  1. Differentiate the "detail view" route from the others, e.g. snapshot_restore/detail/:name.
  2. Add validation in the form, so if someone tries to use the name "add", we disallow it. This of course doesn't prevent the user from doing this via direct API call so it's not really viable.
  3. Go back to putting the name in a query parameter. Blech!

path: chrome.addBasePath(`${API_BASE_PATH}repository_types`),
method: 'get',
httpClient: http.getClient(),
});
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I like this idea, personally. Then we don't need to pass around chrome and http.

() => {
const repositoryTypeOptions = [...repositoryTypes];
const { type } = repository;
if (isEditing && REPOSITORY_PLUGINS_MAP[type] && !repositoryTypes.includes(type)) {
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I tested this by removing the gcs plugin and going to edit a repo created for GCS. It looks like the option doesn't make it into the select:

image

It looks like the type is "gcs", but REPOSITORY_PLUGINS_MAP doesn't contain that key -- it's actually "repository-gcs". I didn't test the other plugins, but there's a chance the same applies to them as well.

fullWidth
onChange={e => {
onRepositoryChange({
...repository,
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think this would be a nice improvement too, because it also makes it clear in the onRepositoryChange implementation that we're not accidentally mutating newRepository, which is how I originally interpreted the code since it's provided as an argument.

renderLoadingRepositoryTypesError()
) : (
<EuiSelect
disabled={isEditing}
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

When we're in editing mode, how about rendering this as a read-only text field instead? That way the text is a bit easier to read and you don't have the "noise" of the select-dropdown caret and other styling.

image

      <EuiFormRow
        label={
          <FormattedMessage
            id="xpack.snapshotRestore.repositoryForm.fields.typeLabel"
            defaultMessage="Type"
          />
        }
        describedByIds={['repositoryTypeDescription']}
        fullWidth
      >
        {repositoryTypesError ? (
          renderLoadingRepositoryTypesError()
        ) : isEditing ? (
          <EuiFieldText
            readOnly={true}
            value={repository.type}
            fullWidth
          />
        ) : (
          <EuiSelect
            isLoading={repositoryTypesLoading}
            options={availableRepositoryTypes.map(type => {
              return {
                value: type,
                text: ReactDOMServer.renderToString(<RepositoryTypeName type={type} />),
              };
            })}
            value={
              availableRepositoryTypes.includes(repository.type)
                ? repository.type
                : REPOSITORY_TYPES.fs
            }
            onChange={e => {
              onRepositoryChange({
                ...repository,
                type: e.target.value,
                settings: {},
              });
            }}
            fullWidth
          />
        )}
      </EuiFormRow>

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I like the idea but then we'd need to update the other apps to follow that pattern, no?

fullWidth
describedByIds={['readonlyRepositoryURLDescription']}
>
<EuiFieldText
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

What do you think of using an inline select to list the available protocol options? That will make it easier for users to see what their options are, select one without a typo, and it will also reduce the amount of help text we need to show at one time, since we can just show the help text that matches whatever the user has selected. It will definitely add some complexity to the code though. :)

image

// just to convey the idea

        <div>
          <EuiFlexGroup gutterSize="s">
            <EuiFlexItem grow={false}>
              <EuiFormRow
                label={
                  <FormattedMessage
                    id="xpack.snapshotRestore.repositoryForm.typeReadonly.urlLabel"
                    defaultMessage="Protocol"
                  />
                }
                fullWidth
                describedByIds={['readonlyRepositoryURLDescription']}
              >
                <EuiSelect options={[{ value: 'http', text: 'http://' }]} value="http" />
              </EuiFormRow>
            </EuiFlexItem>

            <EuiFlexItem>
              <EuiFormRow
                label={
                  <FormattedMessage
                    id="xpack.snapshotRestore.repositoryForm.typeReadonly.urlLabel"
                    defaultMessage="Path"
                  />
                }
                fullWidth
                describedByIds={['readonlyRepositoryURLDescription']}
              >
                <EuiFieldText
                  defaultValue={url || ''}
                  fullWidth
                  onChange={e => {
                    onSettingsChange({
                      ...repository.settings,
                      url: e.target.value,
                    });
                  }}
                />
              </EuiFormRow>
            </EuiFlexItem>
          </EuiFlexGroup>

          {/* This will need some ARIA props to associate it with the above fields */}
          <EuiFormHelpText>
            <FormattedMessage
              id="xpack.snapshotRestore.repositoryForm.typeReadonly.urlWhitelistDescription"
              defaultMessage="URL repositories with {httpType} must be whitelisted as part of the {settingKey} Elasticsearch setting."
              values={{
                httpType: <EuiCode>http:</EuiCode>,
                settingKey: <EuiCode>repositories.url.allowed_urls</EuiCode>,
              }}
            />
          </EuiFormHelpText>
        </div>

};

const renderTypeSettings = (repositoryType: RepositoryType) => {
switch (repositoryType) {
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

If you prefer I think you could also use the map pattern from repository_type_name.tsx instead of a switch.

<EuiHealth color="success">
<FormattedMessage
id="xpack.snapshotRestore.repositoryVerification.verificationSuccessfulValue"
defaultMessage="Success"
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Since we're talking about the concept of "verification" here how about we use "Verified" and "Not verified" instead of "Success" and "Error"? We should probably check with the copywriting team but I think those terms will hold more meaning to the casual reader.

image

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

to me, "Not verified" means "we didn't check this repository" rather than that there was an error with connecting to the repository. although ES uses the term "verification", I think "repository status" or "connection status" is more accurate. let's defer this until copywriting review, but maybe we can simply say "Status" instead, maybe with the values "Connected" or "Error"

/**
* Utility to remove empty fields ("") from repository settings
*/
export const cleanSettings = (settings: Repository['settings']) =>
Copy link
Copy Markdown
Contributor

@cjcenizal cjcenizal Apr 1, 2019

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Just to play devil's advocate, I think there is a benefit to preserving this as specialized logic for cleaning the settings object, as opposed to generalizing it. In its current form it's really clear to me what its purpose is: empty strings have a special meaning in the context of the settings object, and this logic tells me that we don't want to keep them (for some reason). It's really simple to grok the intention behind this code. I understand that there's a business rule here and if we make changes to this code it will because we're adapting to changes in the business rule.

On the other hand, if we extract this out into a generalized utility, now the context has changed and we've invited new features (like the ability to clean an object deeply, which may not be necessary or even desired for our use case). If our business rules change then adapting the code is not as simple. As a contrived example, if we switch to using null instead of empty strings, then we'd need to either modify the generalized function and make sure we're not breaking anything for consumers, or write entirely new code.

Based on these pros and cons I really don't think we should bother generalizing this. :)

/**
* Utility to coerce ES boolean strings to actual booleans
*/
export const booleanizeSettings = (repository: Repository) => {
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Maybe as a compromise we can follow the rule of threes, and wait for multiple use cases to arise before generalizing?

@jen-huang
Copy link
Copy Markdown
Contributor Author

Thanks for the in-depth feedback, everyone! I've addressed most of them:

  • Removed breaks
  • Adjusted add and edit repo routes so they don't conflict with list route
  • Added repository plugin and types doc links to form
  • Bootstrap documentation service
  • Bootstrap text service and replace RepositoryTypeName component with it
  • Bootstrap breadcrumb service and replace usages
  • Bootstrap httpService, remove chrome and http from app dependencies(!)
  • Add request creator and replace all instances of useRequest and sendRequest with it
  • Simplify update repository and update repository setting methods

The major ones that I will defer are UI changes/improvements (as suggested by @yaronp68 and @cjcenizal) as these will take longer and I'd like to get this PR merged so that the upstream feature branch is in a good place to begin shared dev work 😄

@elasticmachine

This comment has been minimized.

@elasticmachine

This comment has been minimized.

@elasticmachine

This comment has been minimized.

@elasticmachine
Copy link
Copy Markdown
Contributor

💚 Build Succeeded

@jen-huang jen-huang merged commit 9147f87 into elastic:feature/snapshots Apr 3, 2019
@jen-huang jen-huang deleted the feature/snapshots-create-repo branch April 3, 2019 00:04
@cjcenizal cjcenizal added the Feature:Snapshot and Restore Elasticsearch snapshots and repositories UI label Apr 5, 2019
@cjcenizal cjcenizal added the non-issue Indicates to automation that a pull request should not appear in the release notes label Apr 17, 2019
jen-huang added a commit that referenced this pull request May 13, 2019
* [SR] Snapshot and restore plugin boilerplate (#32276)

* Initial plugin set up

* Set up client shell

* Add initial repository list routes

* Fix merge issues and some typings

* Decouple server from plugin.ts files, tighten up typings

* Use exported constant for required license

* Translate plugin name, more typings

* Fix more types, move list components under /home

* Remove unused var

* Change scss prefix

* Uncouple unmount logic from routing shim, and some other PR feedback

* [SR] Repository list and details UI (#33367)

* Initial pass at repositories list UI

* Add detail panel for file system repositories, and a generic detail panel with json settings view

* Add detail components for other types

* Add detail panel footer, rename `useStateValue` to `useAppState`

* Fix detail panel footer

* Fix unused vars

* PR feedback

* PR feedback

* [SR] Refactor proposal (#33690)

* Move app dependencies to its own context provider

* Add index.ts barrel file for common types

* Move Enums to constants.ts file

* Refactor function component using `React.FunctionComponent<Props>`

* Refactor service folder structure

* Fix type import

* Move REPOSITORY_DOC_PATHS from common to public constants

* Move AppCore and AppPlugins interfaces back to shim and re-export them from app types

* [SR] Create and edit repositories UI (#34020)

* Add routing and placeholder form

* Fix typings

* Set up edit repository route, and basic form UI

* Add typings for wrapCustomError, and copy extractCausedByChain from CCR wrapEsError

* Throw errors that are already boomified

* Create and edit for basic repository types (fs, url, source)

* Add repository verification UI to table and details

* Create and edit for plugin repository types (hdfs, azure, s3, gcs)

* Fix linting

* Fix test

* Fix test

* Remove unused import

* Fix duplicate i18n key

* Fix details opening on cancel edit, remove unnecessary Fragments, definition file for some EUI components to x-pack, rename saveError

* Remove breaks

* Adjust add and edit repo routes so they don't conflict with list route

* Add repo plugin and types doc links to form

* Bootstrap documentation service

* Bootstrap text service and replace RepositoryTypeName component with it

* Bootstrap breadcrumb service and replace usages

* Bootstrap httpService, remove chrome and http from app dependencies(!)

* Add request creator and replace all instances of useRequest and sendRequest with it

* Fix typo

* Simplify update repository and update repository setting methods

* Adjust copy

* Lint

* Remove unused var

* Remove unused import

* [SR] Add API for retrieving snapshots. (#34598)

* [SR] Single and multiple repository delete (#34593)

* Add single/multi repository delete API and UI

* Address PR feedback

* [SR] Add SnapshotTable and SnapshotDetails. (#34837)

* Remove associations between multiple repositories with a single snapshot.
* Retrieve complete snapshot details in getAllHandler.
* Fix cleanup function bug in useRequest hook.
* Fix bug in useRequest which prevented old data from being cleared when subsequent requests returned errors.
* Add initialValue config option to useRequest.
* Add formatDate service to text module.

* [SR] Fix linting and add (de)serialization for repositories (#35031)

* Fix eslint issues and add (de)serialization for repositories

* Add comment about flattening settings

* [SR] Surface repository errors and index failures more prominently (#35042)

* Add links to repositories from Snapshot Table and Snapshot Details.
- Rename services/breadcrumbs to services/navigation and add linkToRepository function.
- Refactor home component to update active tab when URL was changed.
* Add warning callout to let user know when their repositories contain errors.
* Sort failures by shard and add test for snapshot serialization.
* Sort failures and indices.
* Add filter for filtering snapshots by their repository.
* Surface states with humanized text, icons, and tooltips where necessary.
* Fix pluralization of seconds.
* Surface failures tab even if there are none.
- Display a '-' for missing times and durations.
- Create DataPlaceholder component.

* [SR] Polish repositories UX (#35123)

* Refactor repository detail panel to load repository based directly on route param.
* Display repository detail panel while table is loading.
* Make 'Edit repository' table action a link instead of a button.
* Render disabled EuiSelect as a readonly EuiFieldText.
* Prepend HDFS URI with hdfs:// protocol.
* Present scheme options for Read-Only URL repository as a select.

* [SR] Add client-side validation to repository form and link to snapshots from details (#35238)

* Add client side repository form validation, extract `flatten` into common lib

* Add snapshot count to repository details and link to snapshot list

* Reset validation when changing repository type

* Fix snapshot list filter deep linking for repository names with slashes and spaces

* Fix imports

* PR feedback

* [SR] Design and copywriting fixes (#35591)

* Split repository form into two steps; move `clean_settings.ts` to server

* Default to snapshots tab, adjust snapshot empty prompt, add app description

* Add minimum timeout to list view requests to avoid flicker, use EuiEmptyPrompt for loading screen, add doc link to settings step

* Add information about snapshots to delete repository behavior, add doc link for source only toggle, add size notation help text

* Add main doc link

* Copywriting and i18n fixes, and add some common settings to third party repo types

* Add fields to third party repo detail panel

* More copywriting fixes

* Use spinner for duration and end time if snapshotting is still in progress

* Show all repository type options, mark missing plugins

* Revert "Show all repository type options, mark missing plugins"

This reverts commit e34ee47.

* Fix space

* [SR] Add permissions UI and Cloud-specific repository type UI branch (#35833)

* Add missing permissions UI and cloud-specific repository type UI branch

* Add ES UI as owners of /snapshot_restore directory

* Add no repository types callout for Cloud edge case

* Redirect invalid section param to repositories

* Add warning empty prompt if all repositories have errrors

* Replace repository cards with EuiCard

* Add snapshot doc link to repository error empty prompt

* Remove auto-verification from list and get routes, add separate verification route, add manual verification to repository detail panel

* Update copy and remove obsolete test

* Remove unused scss files

* Final changes to repository cards
jen-huang added a commit to jen-huang/kibana that referenced this pull request May 13, 2019
* [SR] Snapshot and restore plugin boilerplate (elastic#32276)

* Initial plugin set up

* Set up client shell

* Add initial repository list routes

* Fix merge issues and some typings

* Decouple server from plugin.ts files, tighten up typings

* Use exported constant for required license

* Translate plugin name, more typings

* Fix more types, move list components under /home

* Remove unused var

* Change scss prefix

* Uncouple unmount logic from routing shim, and some other PR feedback

* [SR] Repository list and details UI (elastic#33367)

* Initial pass at repositories list UI

* Add detail panel for file system repositories, and a generic detail panel with json settings view

* Add detail components for other types

* Add detail panel footer, rename `useStateValue` to `useAppState`

* Fix detail panel footer

* Fix unused vars

* PR feedback

* PR feedback

* [SR] Refactor proposal (elastic#33690)

* Move app dependencies to its own context provider

* Add index.ts barrel file for common types

* Move Enums to constants.ts file

* Refactor function component using `React.FunctionComponent<Props>`

* Refactor service folder structure

* Fix type import

* Move REPOSITORY_DOC_PATHS from common to public constants

* Move AppCore and AppPlugins interfaces back to shim and re-export them from app types

* [SR] Create and edit repositories UI (elastic#34020)

* Add routing and placeholder form

* Fix typings

* Set up edit repository route, and basic form UI

* Add typings for wrapCustomError, and copy extractCausedByChain from CCR wrapEsError

* Throw errors that are already boomified

* Create and edit for basic repository types (fs, url, source)

* Add repository verification UI to table and details

* Create and edit for plugin repository types (hdfs, azure, s3, gcs)

* Fix linting

* Fix test

* Fix test

* Remove unused import

* Fix duplicate i18n key

* Fix details opening on cancel edit, remove unnecessary Fragments, definition file for some EUI components to x-pack, rename saveError

* Remove breaks

* Adjust add and edit repo routes so they don't conflict with list route

* Add repo plugin and types doc links to form

* Bootstrap documentation service

* Bootstrap text service and replace RepositoryTypeName component with it

* Bootstrap breadcrumb service and replace usages

* Bootstrap httpService, remove chrome and http from app dependencies(!)

* Add request creator and replace all instances of useRequest and sendRequest with it

* Fix typo

* Simplify update repository and update repository setting methods

* Adjust copy

* Lint

* Remove unused var

* Remove unused import

* [SR] Add API for retrieving snapshots. (elastic#34598)

* [SR] Single and multiple repository delete (elastic#34593)

* Add single/multi repository delete API and UI

* Address PR feedback

* [SR] Add SnapshotTable and SnapshotDetails. (elastic#34837)

* Remove associations between multiple repositories with a single snapshot.
* Retrieve complete snapshot details in getAllHandler.
* Fix cleanup function bug in useRequest hook.
* Fix bug in useRequest which prevented old data from being cleared when subsequent requests returned errors.
* Add initialValue config option to useRequest.
* Add formatDate service to text module.

* [SR] Fix linting and add (de)serialization for repositories (elastic#35031)

* Fix eslint issues and add (de)serialization for repositories

* Add comment about flattening settings

* [SR] Surface repository errors and index failures more prominently (elastic#35042)

* Add links to repositories from Snapshot Table and Snapshot Details.
- Rename services/breadcrumbs to services/navigation and add linkToRepository function.
- Refactor home component to update active tab when URL was changed.
* Add warning callout to let user know when their repositories contain errors.
* Sort failures by shard and add test for snapshot serialization.
* Sort failures and indices.
* Add filter for filtering snapshots by their repository.
* Surface states with humanized text, icons, and tooltips where necessary.
* Fix pluralization of seconds.
* Surface failures tab even if there are none.
- Display a '-' for missing times and durations.
- Create DataPlaceholder component.

* [SR] Polish repositories UX (elastic#35123)

* Refactor repository detail panel to load repository based directly on route param.
* Display repository detail panel while table is loading.
* Make 'Edit repository' table action a link instead of a button.
* Render disabled EuiSelect as a readonly EuiFieldText.
* Prepend HDFS URI with hdfs:// protocol.
* Present scheme options for Read-Only URL repository as a select.

* [SR] Add client-side validation to repository form and link to snapshots from details (elastic#35238)

* Add client side repository form validation, extract `flatten` into common lib

* Add snapshot count to repository details and link to snapshot list

* Reset validation when changing repository type

* Fix snapshot list filter deep linking for repository names with slashes and spaces

* Fix imports

* PR feedback

* [SR] Design and copywriting fixes (elastic#35591)

* Split repository form into two steps; move `clean_settings.ts` to server

* Default to snapshots tab, adjust snapshot empty prompt, add app description

* Add minimum timeout to list view requests to avoid flicker, use EuiEmptyPrompt for loading screen, add doc link to settings step

* Add information about snapshots to delete repository behavior, add doc link for source only toggle, add size notation help text

* Add main doc link

* Copywriting and i18n fixes, and add some common settings to third party repo types

* Add fields to third party repo detail panel

* More copywriting fixes

* Use spinner for duration and end time if snapshotting is still in progress

* Show all repository type options, mark missing plugins

* Revert "Show all repository type options, mark missing plugins"

This reverts commit e34ee47.

* Fix space

* [SR] Add permissions UI and Cloud-specific repository type UI branch (elastic#35833)

* Add missing permissions UI and cloud-specific repository type UI branch

* Add ES UI as owners of /snapshot_restore directory

* Add no repository types callout for Cloud edge case

* Redirect invalid section param to repositories

* Add warning empty prompt if all repositories have errrors

* Replace repository cards with EuiCard

* Add snapshot doc link to repository error empty prompt

* Remove auto-verification from list and get routes, add separate verification route, add manual verification to repository detail panel

* Update copy and remove obsolete test

* Remove unused scss files

* Final changes to repository cards
jen-huang added a commit that referenced this pull request May 13, 2019
* [SR] Snapshot and restore plugin boilerplate (#32276)

* Initial plugin set up

* Set up client shell

* Add initial repository list routes

* Fix merge issues and some typings

* Decouple server from plugin.ts files, tighten up typings

* Use exported constant for required license

* Translate plugin name, more typings

* Fix more types, move list components under /home

* Remove unused var

* Change scss prefix

* Uncouple unmount logic from routing shim, and some other PR feedback

* [SR] Repository list and details UI (#33367)

* Initial pass at repositories list UI

* Add detail panel for file system repositories, and a generic detail panel with json settings view

* Add detail components for other types

* Add detail panel footer, rename `useStateValue` to `useAppState`

* Fix detail panel footer

* Fix unused vars

* PR feedback

* PR feedback

* [SR] Refactor proposal (#33690)

* Move app dependencies to its own context provider

* Add index.ts barrel file for common types

* Move Enums to constants.ts file

* Refactor function component using `React.FunctionComponent<Props>`

* Refactor service folder structure

* Fix type import

* Move REPOSITORY_DOC_PATHS from common to public constants

* Move AppCore and AppPlugins interfaces back to shim and re-export them from app types

* [SR] Create and edit repositories UI (#34020)

* Add routing and placeholder form

* Fix typings

* Set up edit repository route, and basic form UI

* Add typings for wrapCustomError, and copy extractCausedByChain from CCR wrapEsError

* Throw errors that are already boomified

* Create and edit for basic repository types (fs, url, source)

* Add repository verification UI to table and details

* Create and edit for plugin repository types (hdfs, azure, s3, gcs)

* Fix linting

* Fix test

* Fix test

* Remove unused import

* Fix duplicate i18n key

* Fix details opening on cancel edit, remove unnecessary Fragments, definition file for some EUI components to x-pack, rename saveError

* Remove breaks

* Adjust add and edit repo routes so they don't conflict with list route

* Add repo plugin and types doc links to form

* Bootstrap documentation service

* Bootstrap text service and replace RepositoryTypeName component with it

* Bootstrap breadcrumb service and replace usages

* Bootstrap httpService, remove chrome and http from app dependencies(!)

* Add request creator and replace all instances of useRequest and sendRequest with it

* Fix typo

* Simplify update repository and update repository setting methods

* Adjust copy

* Lint

* Remove unused var

* Remove unused import

* [SR] Add API for retrieving snapshots. (#34598)

* [SR] Single and multiple repository delete (#34593)

* Add single/multi repository delete API and UI

* Address PR feedback

* [SR] Add SnapshotTable and SnapshotDetails. (#34837)

* Remove associations between multiple repositories with a single snapshot.
* Retrieve complete snapshot details in getAllHandler.
* Fix cleanup function bug in useRequest hook.
* Fix bug in useRequest which prevented old data from being cleared when subsequent requests returned errors.
* Add initialValue config option to useRequest.
* Add formatDate service to text module.

* [SR] Fix linting and add (de)serialization for repositories (#35031)

* Fix eslint issues and add (de)serialization for repositories

* Add comment about flattening settings

* [SR] Surface repository errors and index failures more prominently (#35042)

* Add links to repositories from Snapshot Table and Snapshot Details.
- Rename services/breadcrumbs to services/navigation and add linkToRepository function.
- Refactor home component to update active tab when URL was changed.
* Add warning callout to let user know when their repositories contain errors.
* Sort failures by shard and add test for snapshot serialization.
* Sort failures and indices.
* Add filter for filtering snapshots by their repository.
* Surface states with humanized text, icons, and tooltips where necessary.
* Fix pluralization of seconds.
* Surface failures tab even if there are none.
- Display a '-' for missing times and durations.
- Create DataPlaceholder component.

* [SR] Polish repositories UX (#35123)

* Refactor repository detail panel to load repository based directly on route param.
* Display repository detail panel while table is loading.
* Make 'Edit repository' table action a link instead of a button.
* Render disabled EuiSelect as a readonly EuiFieldText.
* Prepend HDFS URI with hdfs:// protocol.
* Present scheme options for Read-Only URL repository as a select.

* [SR] Add client-side validation to repository form and link to snapshots from details (#35238)

* Add client side repository form validation, extract `flatten` into common lib

* Add snapshot count to repository details and link to snapshot list

* Reset validation when changing repository type

* Fix snapshot list filter deep linking for repository names with slashes and spaces

* Fix imports

* PR feedback

* [SR] Design and copywriting fixes (#35591)

* Split repository form into two steps; move `clean_settings.ts` to server

* Default to snapshots tab, adjust snapshot empty prompt, add app description

* Add minimum timeout to list view requests to avoid flicker, use EuiEmptyPrompt for loading screen, add doc link to settings step

* Add information about snapshots to delete repository behavior, add doc link for source only toggle, add size notation help text

* Add main doc link

* Copywriting and i18n fixes, and add some common settings to third party repo types

* Add fields to third party repo detail panel

* More copywriting fixes

* Use spinner for duration and end time if snapshotting is still in progress

* Show all repository type options, mark missing plugins

* Revert "Show all repository type options, mark missing plugins"

This reverts commit e34ee47.

* Fix space

* [SR] Add permissions UI and Cloud-specific repository type UI branch (#35833)

* Add missing permissions UI and cloud-specific repository type UI branch

* Add ES UI as owners of /snapshot_restore directory

* Add no repository types callout for Cloud edge case

* Redirect invalid section param to repositories

* Add warning empty prompt if all repositories have errrors

* Replace repository cards with EuiCard

* Add snapshot doc link to repository error empty prompt

* Remove auto-verification from list and get routes, add separate verification route, add manual verification to repository detail panel

* Update copy and remove obsolete test

* Remove unused scss files

* Final changes to repository cards
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

Feature:Snapshot and Restore Elasticsearch snapshots and repositories UI non-issue Indicates to automation that a pull request should not appear in the release notes Team:Kibana Management Dev Tools, Index Management, Upgrade Assistant, ILM, Ingest Node Pipelines, and more t//

Projects

None yet

Development

Successfully merging this pull request may close these issues.

5 participants