Ember Upgrade to 4.4 (#17086)

* runs ember-cli-update to 4.4.0

* updates yarn.lock

* updates dependencies causing runtime errors (#17135)

* Inject Store Service When Accessed Implicitly (#17345)

* adds codemod for injecting store service

* adds custom babylon parser with decorators-legacy plugin for jscodeshift transforms

* updates inject-store-service codemod to only look for .extend object expressions and adds recast options

* runs inject-store-service codemod on js files

* replace query-params helper with hash (#17404)

* Updates/removes dependencies throwing errors in Ember 4.4 (#17396)

* updates ember-responsive to latest

* updates ember-composable-helpers to latest and uses includes helper since contains was removed

* updates ember-concurrency to latest

* updates ember-cli-clipboard to latest

* temporary workaround for toolbar-link component throwing errors for using params arg with LinkTo

* adds missing store injection to auth configure route

* fixes issue with string-list component throwing error for accessing prop in same computation

* fixes non-iterable query params issue in mfa methods controller

* refactors field-to-attrs to handle belongsTo rather than fragments

* converts mount-config fragment to belongsTo on auth-method model

* removes ember-api-actions and adds tune method to auth-method adapter

* converts cluster replication attributes from fragment to relationship

* updates ember-data, removes ember-data-fragments and updates yarn to latest

* removes fragments from secret-engine model

* removes fragment from test-form-model

* removes commented out code

* minor change to inject-store-service codemod and runs again on js files

* Remove LinkTo positional params (#17421)

* updates ember-cli-page-object to latest version

* update toolbar-link to support link-to args and not positional params

* adds replace arg to toolbar-link component

* Clean up js lint errors (#17426)

* replaces assert.equal to assert.strictEqual

* update eslint no-console to error and disables invididual intended uses of console

* cleans up hbs lint warnings (#17432)

* Upgrade bug and test fixes (#17500)

* updates inject-service codemod to take arg for service name and runs for flashMessages service

* fixes hbs lint error after merging main

* fixes flash messages

* updates more deps

* bug fixes

* test fixes

* updates ember-cli-content-security-policy and prevents default form submission throwing errors

* more bug and test fixes

* removes commented out code

* fixes issue with code-mirror modifier sending change event on setup causing same computation error

* Upgrade Clean Up (#17543)

* updates deprecation workflow and filter

* cleans up build errors, removes unused ivy-codemirror and sass and updates ember-cli-sass and node-sass to latest

* fixes control groups test that was skipped after upgrade

* updates control group service tests

* addresses review feedback

* updates control group service handleError method to use router.currentURL rather that transition.intent.url

* adds changelog entry
This commit is contained in:
Jordan Reimer 2022-10-18 09:46:02 -06:00 committed by GitHub
parent 296297e53f
commit be632db682
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
477 changed files with 180338 additions and 3306 deletions

3
changelog/17086.txt Normal file
View File

@ -0,0 +1,3 @@
```release-note:change
ui: Upgrade Ember to version 4.4.0
```

View File

@ -6,5 +6,11 @@
Setting `disableAnalytics` to true will prevent any data from being sent.
*/
"disableAnalytics": true,
"output-path": "../http/web_ui"
"output-path": "../http/web_ui",
/**
Setting `isTypeScriptProject` to true will force the blueprint generators to generate TypeScript
rather than JavaScript by default, when a TypeScript version of a given blueprint is available.
*/
"isTypeScriptProject": false
}

View File

@ -20,6 +20,8 @@
# ember-try
/.node_modules.ember-try/
/bower.json.ember-try
/npm-shrinkwrap.json.ember-try
/package.json.ember-try
/package-lock.json.ember-try
/yarn.lock.ember-try
/tests/helpers/vault-keys.js

View File

@ -23,7 +23,7 @@ module.exports = {
browser: true,
},
rules: {
'no-console': 'warn',
'no-console': 'error',
'ember/no-mixins': 'warn',
'ember/no-new-mixins': 'off', // should be warn but then every line of the mixin is green
// need to be fully glimmerized before these rules can be turned on
@ -63,7 +63,7 @@ module.exports = {
},
},
{
// Test files:
// test files
files: ['tests/**/*-test.{js,ts}'],
extends: ['plugin:qunit/recommended'],
},

45
ui/.github/workflows/ci.yml vendored Normal file
View File

@ -0,0 +1,45 @@
name: CI
on:
push:
branches:
- main
- master
pull_request: {}
concurrency:
group: ci-${{ github.head_ref || github.ref }}
cancel-in-progress: true
jobs:
lint:
name: "Lint"
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v3
- name: Install Node
uses: actions/setup-node@v3
with:
node-version: 12.x
cache: yarn
- name: Install Dependencies
run: yarn install --frozen-lockfile
- name: Lint
run: yarn lint
test:
name: "Test"
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v3
- name: Install Node
uses: actions/setup-node@v3
with:
node-version: 12.x
cache: yarn
- name: Install Dependencies
run: yarn install --frozen-lockfile
- name: Run Tests
run: yarn test

6
ui/.gitignore vendored
View File

@ -22,4 +22,10 @@ package-lock.json
# ember-try
/.node_modules.ember-try/
/bower.json.ember-try
/npm-shrinkwrap.json.ember-try
/package.json.ember-try
/package-lock.json.ember-try
/yarn.lock.ember-try
# broccoli-debug
/DEBUG/

View File

@ -14,8 +14,12 @@
/coverage/
!.*
.eslintcache
.lint-todo/
# ember-try
/.node_modules.ember-try/
/bower.json.ember-try
/npm-shrinkwrap.json.ember-try
/package.json.ember-try
/package-lock.json.ember-try
/yarn.lock.ember-try

View File

@ -29,22 +29,18 @@ try {
prettier: false,
};
} catch (error) {
console.log(error);
console.log(error); // eslint-disable-line
}
module.exports = {
plugins: ['ember-template-lint-plugin-prettier'],
extends: ['recommended', 'ember-template-lint-plugin-prettier:recommended'],
rules: {
'no-bare-strings': 'off',
'no-action': 'off',
'no-duplicate-landmark-elements': 'warn',
'no-implicit-this': {
allow: ['supported-auth-backends'],
},
'require-input-label': 'off',
'no-down-event-binding': 'warn',
'self-closing-void-elements': 'off',
},
ignore: ['lib/story-md', 'tests/**'],
// ember language server vscode extension does not currently respect the ignore field

175346
ui/.yarn/releases/yarn-1.22.19.js vendored Executable file

File diff suppressed because one or more lines are too long

View File

@ -2,5 +2,5 @@
# yarn lockfile v1
lastUpdateCheck 1572032507422
yarn-path ".yarn/releases/yarn-1.19.1.js"
lastUpdateCheck 1664829239911
yarn-path ".yarn/releases/yarn-1.22.19.js"

View File

@ -24,6 +24,7 @@ This README outlines the details of collaborating on this Ember application.
| Vault Version | Ember Version |
| ------------- | ------------- |
| 1.13.x | 4.4.0 |
| 1.10.x | 3.28.5 |
| 1.9.x | 3.22.0 |
| 1.8.x | 3.22.0 |
@ -33,10 +34,11 @@ This README outlines the details of collaborating on this Ember application.
You will need the following things properly installed on your computer.
- [Node.js](https://nodejs.org/) (with NPM)
- [Yarn](https://yarnpkg.com/en/)
- [Git](https://git-scm.com/)
- [Ember CLI](https://ember-cli.com/)
* [Git](https://git-scm.com/)
* [Node.js](https://nodejs.org/)
* [Yarn](https://yarnpkg.com/)
* [Ember CLI](https://cli.emberjs.com/release/)
* [Google Chrome](https://google.com/chrome/)
- [lint-staged\*](https://www.npmjs.com/package/lint-staged)
\* lint-staged is an optional dependency - running `yarn` will install it.
@ -127,8 +129,8 @@ setting `VAULT_UI` environment variable.
## Further Reading / Useful Links
- [ember.js](http://emberjs.com/)
- [ember-cli](https://ember-cli.com/)
- Development Browser Extensions
- [ember inspector for chrome](https://chrome.google.com/webstore/detail/ember-inspector/bmdblncegkenkacieihfhpjfppoconhi)
- [ember inspector for firefox](https://addons.mozilla.org/en-US/firefox/addon/ember-inspector/)
* [ember.js](https://emberjs.com/)
* [ember-cli](https://cli.emberjs.com/release/)
* Development Browser Extensions
* [ember inspector for chrome](https://chrome.google.com/webstore/detail/ember-inspector/bmdblncegkenkacieihfhpjfppoconhi)
* [ember inspector for firefox](https://addons.mozilla.org/en-US/firefox/addon/ember-inspector/)

View File

@ -10,7 +10,7 @@ export default ApplicationAdapter.extend({
return path ? url + '/' + encodePath(path) : url;
},
// used in updateRecord on the model#tune action
// used in updateRecord
pathForType() {
return 'mounts/auth';
},
@ -48,6 +48,7 @@ export default ApplicationAdapter.extend({
return this.ajax(this.url(path), 'POST', { data }).then(() => {
// ember data doesn't like 204s if it's not a DELETE
data.config.id = path; // config relationship needs an id so use path for now
return {
data: assign({}, data, { path: path + '/', id: path }),
};
@ -61,4 +62,9 @@ export default ApplicationAdapter.extend({
exchangeOIDC(path, state, code) {
return this.ajax(`/v1/auth/${encodePath(path)}/oidc/callback`, 'GET', { data: { state, code } });
},
tune(path, data) {
const url = `${this.buildURL()}/${this.pathForType()}/${encodePath(path)}tune`;
return this.ajax(url, 'POST', { data });
},
});

View File

@ -1,11 +1,14 @@
import { assign } from '@ember/polyfills';
import ApplicationAdapter from './application';
import { task } from 'ember-concurrency';
import { inject as service } from '@ember/service';
export default ApplicationAdapter.extend({
store: service(),
namespace: 'v1',
urlForItem() {},
dynamicApiPath: '',
getDynamicApiPath: task(function* (id) {
// TODO: remove yield at some point.
let result = yield this.store.peekRecord('auth-method', id);

View File

@ -1,6 +1,7 @@
import ApplicationAdapter from '../application';
import { encodePath } from 'vault/utils/path-encoding-helpers';
import ControlGroupError from '../../lib/control-group-error';
import { inject as service } from '@ember/service';
function pickKeys(obj, picklist) {
const data = {};
@ -11,7 +12,9 @@ function pickKeys(obj, picklist) {
});
return data;
}
export default class KeymgmtKeyAdapter extends ApplicationAdapter {
@service store;
namespace = 'v1';
pathForType() {

View File

@ -51,6 +51,7 @@ export default ApplicationAdapter.extend({
let data = serializer.serialize(snapshot);
const path = snapshot.attr('path');
// for kv2 we make two network requests
data.config.id = path; // config relationship needs an id so use path for now
if (data.type === 'kv' && data.options.version === 2) {
// data has both data for sys mount and the config, we need to separate them
let splitObjects = splitObject(data, ['max_versions', 'delete_version_after', 'cas_required']);

View File

@ -1,12 +1,16 @@
/* eslint-disable */
import AdapterError from '@ember-data/adapter/error';
import { isEmpty } from '@ember/utils';
import { get } from '@ember/object';
import ApplicationAdapter from './application';
import { encodePath } from 'vault/utils/path-encoding-helpers';
import { inject as service } from '@ember/service';
export default ApplicationAdapter.extend({
store: service(),
namespace: 'v1',
_url(backend, id, infix = 'data') {
let url = `${this.buildURL()}/${encodePath(backend)}/${infix}/`;
if (!isEmpty(id)) {

View File

@ -18,8 +18,10 @@ import { waitFor } from '@ember/test-waiters';
*/
export default AuthConfigComponent.extend({
flashMessages: service(),
router: service(),
wizard: service(),
saveModel: task(
waitFor(function* () {
let data = this.model.config.serialize();

View File

@ -277,7 +277,6 @@ export default Component.extend(DEFAULTS, {
delayAuthMessageReminder: task(function* () {
if (Ember.testing) {
this.showLoading = true;
yield timeout(0);
} else {
yield timeout(5000);
@ -285,15 +284,9 @@ export default Component.extend(DEFAULTS, {
}),
actions: {
doSubmit() {
let passedData, e;
if (arguments.length > 1) {
[passedData, e] = arguments;
} else {
[e] = arguments;
}
if (e) {
e.preventDefault();
doSubmit(passedData, event) {
if (event) {
event.preventDefault();
}
let data = {};
this.setProperties({

View File

@ -88,7 +88,7 @@ class CalendarWidget extends Component {
const year = this.args.endTimeDisplay.split(' ')[1];
setYear = parseInt(year);
} catch (e) {
console.debug('Error resetting display year', e);
console.debug('Error resetting display year', e); // eslint-disable-line
}
}
this.displayYear = setYear;

View File

@ -49,9 +49,10 @@ export default class LineChart extends Component {
const upgradeData = this.args.upgradeData;
if (!upgradeData) return null;
if (!Array.isArray(upgradeData)) {
console.debug('upgradeData must be an array of objects containing upgrade history');
console.debug('upgradeData must be an array of objects containing upgrade history'); // eslint-disable-line
return null;
} else if (!Object.keys(upgradeData[0]).includes('timestampInstalled')) {
// eslint-disable-next-line
console.debug(
`upgrade must be an object with the following key names: ['id', 'previousVersion', 'timestampInstalled']`
);

View File

@ -31,12 +31,14 @@ import { action } from '@ember/object';
*/
export default class ConfigureAwsSecretComponent extends Component {
@action
saveRootCreds(data) {
saveRootCreds(data, event) {
event.preventDefault();
this.args.saveAWSRoot(data);
}
@action
saveLease(data) {
saveLease(data, event) {
event.preventDefault();
this.args.saveAWSLease(data);
}
}

View File

@ -18,7 +18,8 @@ import { action } from '@ember/object';
*/
export default class ConfigureSshSecretComponent extends Component {
@action
saveConfig(data) {
saveConfig(data, event) {
event.preventDefault();
this.args.saveConfig(data);
}
}

View File

@ -70,7 +70,7 @@ export default class DatabaseRoleEdit extends Component {
try {
this.router.transitionTo(LIST_ROOT_ROUTE, backend, { queryParams: { tab: 'role' } });
} catch (e) {
console.debug(e);
console.debug(e); // eslint-disable-line
}
})
.catch((e) => {
@ -97,7 +97,7 @@ export default class DatabaseRoleEdit extends Component {
try {
this.router.transitionTo(SHOW_ROUTE, `role/${secretId}`);
} catch (e) {
console.debug(e);
console.debug(e); // eslint-disable-line
}
})
.catch((e) => {

View File

@ -3,6 +3,7 @@ import Component from '@glimmer/component';
import { inject as service } from '@ember/service';
import { action } from '@ember/object';
import { tracked } from '@glimmer/tracking';
import { htmlSafe } from '@ember/template';
/**
* @module DiffVersionSelector
@ -57,10 +58,11 @@ export default class DiffVersionSelector extends Component {
let delta = diffpatcher.diff(rightSideVersionData, leftSideVersionData);
if (delta === undefined) {
this.statesMatch = true;
this.visualDiff = JSON.stringify(leftSideVersionData, undefined, 2); // params: value, replacer (all properties included), space (white space and indentation, line break, etc.)
// params: value, replacer (all properties included), space (white space and indentation, line break, etc.)
this.visualDiff = htmlSafe(JSON.stringify(leftSideVersionData, undefined, 2));
} else {
this.statesMatch = false;
this.visualDiff = jsondiffpatch.formatters.html.format(delta, rightSideVersionData);
this.visualDiff = htmlSafe(jsondiffpatch.formatters.html.format(delta, rightSideVersionData));
}
}

View File

@ -1,15 +1,10 @@
import { computed } from '@ember/object';
import FlashMessage from 'ember-cli-flash/components/flash-message';
export default FlashMessage.extend({
export default class FlashMessageComponent extends FlashMessage {
// override alertType to get Bulma specific prefix
//https://github.com/poteto/ember-cli-flash/blob/master/addon/components/flash-message.js#L35
alertType: computed('flash.type', {
get() {
const flashType = this.flash.type || '';
let prefix = 'is-';
return `${prefix}${flashType}`;
},
}),
});
//https://github.com/poteto/ember-cli-flash/blob/master/addon/components/flash-message.js#L55
get alertType() {
const flashType = this.args.flash.type || '';
return `is-${flashType}`;
}
}

View File

@ -66,7 +66,9 @@ export default Component.extend({
},
willDestroy() {
this.model.unloadRecord();
if (!this.model.isDestroyed && !this.model.isDestroying) {
this.model.unloadRecord();
}
this._super(...arguments);
},

View File

@ -33,12 +33,6 @@ import KVObject from 'vault/lib/kv-object';
export default class KvObjectEditor extends Component {
@tracked kvData;
constructor() {
super(...arguments);
this.kvData = KVObject.create({ content: [] }).fromJSON(this.args.value);
this.addRow();
}
get placeholders() {
return {
key: this.args.keyPlaceholder || 'key',
@ -49,6 +43,12 @@ export default class KvObjectEditor extends Component {
return this.kvData.uniqBy('name').length !== this.kvData.get('length');
}
// fired on did-insert from render modifier
@action
createKvData(elem, [value]) {
this.kvData = KVObject.create({ content: [] }).fromJSON(value);
this.addRow();
}
@action
addRow() {
if (!isNone(this.kvData.findBy('name', ''))) {

View File

@ -50,6 +50,7 @@ export default class MountBackendForm extends Component {
const type = this.args.mountType || 'auth';
const modelType = type === 'secret' ? 'secret-engine' : 'auth-method';
const model = this.store.createRecord(modelType);
model.set('config', this.store.createRecord('mount-config'));
this.mountModel = model;
}
@ -94,7 +95,8 @@ export default class MountBackendForm extends Component {
@task
@waitFor
*mountBackend() {
*mountBackend(event) {
event.preventDefault();
const mountModel = this.mountModel;
const { type, path } = mountModel;
// only submit form if validations pass

View File

@ -34,7 +34,7 @@ export default class OidcConsentBlockComponent extends Component {
});
return url;
} catch (e) {
console.debug('DEBUG: parsing url failed for', urlString);
console.debug('DEBUG: parsing url failed for', urlString); // eslint-disable-line
throw new Error('Invalid URL');
}
}

View File

@ -31,12 +31,6 @@ export default class OidcProviderForm extends Component {
? 'allow_all'
: 'limited';
constructor() {
super(...arguments);
const { model } = this.args;
model.issuer = model.isNew ? '' : parseURL(model.issuer).origin;
}
// function passed to search select
renderInfoTooltip(selection, dropdownOptions) {
// if a client has been deleted it will not exist in dropdownOptions (response from search select's query)
@ -44,6 +38,12 @@ export default class OidcProviderForm extends Component {
return !clientExists ? 'The application associated with this client_id no longer exists' : false;
}
// fired on did-insert from render modifier
@action
setIssuer(elem, [model]) {
model.issuer = model.isNew ? '' : parseURL(model.issuer).origin;
}
@action
handleClientSelection(selection) {
// if array then coming from search-select component, set selection as model clients

View File

@ -70,7 +70,7 @@ export default Component.extend({
willDestroy() {
const ca = this.model;
if (ca) {
if (ca && !ca.isDestroyed && !ca.isDestroying) {
ca.unloadRecord();
}
this._super(...arguments);

View File

@ -24,7 +24,8 @@ export default Component.extend({
preference: 'join',
showJoinForm: false,
actions: {
advanceFirstScreen() {
advanceFirstScreen(event) {
event.preventDefault();
if (this.preference !== 'join') {
this.onDismiss();
return;

View File

@ -27,11 +27,9 @@ import Component from '@glimmer/component';
import ControlGroupError from 'vault/lib/control-group-error';
import Ember from 'ember';
import keys from 'vault/lib/keycodes';
import { action, set } from '@ember/object';
import { inject as service } from '@ember/service';
import { tracked } from '@glimmer/tracking';
import { isBlank, isNone } from '@ember/utils';
import { task, waitForEvent } from 'ember-concurrency';
@ -52,9 +50,9 @@ export default class SecretCreateOrUpdate extends Component {
@service store;
@service wizard;
constructor() {
super(...arguments);
this.codemirrorString = this.args.secretData.toJSONString();
@action
setup(elem, [secretData, model, mode]) {
this.codemirrorString = secretData.toJSONString();
this.validationMessages = {
path: '',
};
@ -62,16 +60,16 @@ export default class SecretCreateOrUpdate extends Component {
if (Ember.testing) {
this.secretPaths = ['beep', 'bop', 'boop'];
} else {
let adapter = this.store.adapterFor('secret-v2');
let type = { modelName: 'secret-v2' };
let query = { backend: this.args.model.backend };
const adapter = this.store.adapterFor('secret-v2');
const type = { modelName: 'secret-v2' };
const query = { backend: model.backend };
adapter.query(this.store, type, query).then((result) => {
this.secretPaths = result.data.keys;
});
}
this.checkRows();
if (this.args.mode === 'edit') {
if (mode === 'edit') {
this.addRow();
}
}

View File

@ -34,18 +34,17 @@ export default class SecretEdit extends Component {
@tracked isV2 = false;
@tracked codemirrorString = null;
constructor() {
super(...arguments);
let secrets = this.args.model.secretData;
if (!secrets && this.args.model.selectedVersion) {
// fired on did-insert from render modifier
@action
createKvData(elem, [model]) {
if (!model.secretData && model.selectedVersion) {
this.isV2 = true;
secrets = this.args.model.belongsTo('selectedVersion').value().secretData;
model.secretData = model.belongsTo('selectedVersion').value().secretData;
}
const data = KVObject.create({ content: [] }).fromJSON(secrets);
this.secretData = data;
this.codemirrorString = data.toJSONString();
this.secretData = KVObject.create({ content: [] }).fromJSON(model.secretData);
this.codemirrorString = this.secretData.toJSONString();
if (this.wizard.featureState === 'details' && this.args.mode === 'create') {
let engine = this.args.model.backend.includes('kv') ? 'kv' : this.args.model.backend;
const engine = model.backend.includes('kv') ? 'kv' : model.backend;
this.wizard.transitionFeatureMachine('details', 'CONTINUE', engine);
}
}

View File

@ -1,6 +1,9 @@
import TransformBase, { addToList, removeFromList } from './transform-edit-base';
import { inject as service } from '@ember/service';
export default TransformBase.extend({
flashMessages: service(),
store: service(),
initialTransformations: null,
init() {

View File

@ -1,6 +1,9 @@
import TransformBase, { addToList, removeFromList } from './transform-edit-base';
import { inject as service } from '@ember/service';
export default TransformBase.extend({
flashMessages: service(),
store: service(),
initialRoles: null,
init() {

View File

@ -216,7 +216,11 @@ export default Component.extend(TRANSIT_PARAMS, {
this.toggleProperty('isModalActive');
},
doSubmit(data, options = {}) {
doSubmit(data, options = {}, maybeEvent) {
const event = options.type === 'submit' ? options : maybeEvent;
if (event) {
event.preventDefault();
}
const { backend, id } = this.getModelInfo();
const action = this.selectedAction;
const { encodedBase64, ...formData } = data || {};

View File

@ -32,8 +32,8 @@ export default Component.extend({
label='Wrap response'
helperTextDisabled='Will not wrap response'
helperTextEnabled='Will wrap response with a lease of'
enableTTL=wrapResponse
initialValue=ttl
enableTTL=this.wrapResponse
initialValue=this.ttl
onChange=(action 'changedValue')
}}
</div>

View File

@ -10,6 +10,7 @@ export default Controller.extend({
router: service(),
permissions: service(),
namespaceService: service('namespace'),
flashMessages: service(),
vaultVersion: service('version'),
console: service(),

View File

@ -1,7 +1,10 @@
import Controller from '@ember/controller';
import { task } from 'ember-concurrency';
import { inject as service } from '@ember/service';
export default Controller.extend({
flashMessages: service(),
queryParams: {
page: 'page',
pageFilter: 'pageFilter',

View File

@ -1,9 +1,7 @@
import Controller from '@ember/controller';
export default class MfaMethodsListController extends Controller {
queryParams = {
page: 'page',
};
queryParams = ['page'];
page = 1;
}

View File

@ -6,6 +6,7 @@ import { capitalize } from '@ember/string';
import { task } from 'ember-concurrency';
export default class MfaMethodCreateController extends Controller {
@service store;
@service flashMessages;
@service router;

View File

@ -5,6 +5,7 @@ import { task } from 'ember-concurrency';
import { waitFor } from '@ember/test-waiters';
export default class OidcKeyDetailsController extends Controller {
@service store;
@service router;
@service flashMessages;

View File

@ -4,20 +4,18 @@ import Controller, { inject as controller } from '@ember/controller';
import { task, timeout } from 'ember-concurrency';
export default Controller.extend({
flashMessages: service(),
vaultController: controller('vault'),
clusterController: controller('vault.cluster'),
namespaceService: service('namespace'),
featureFlagService: service('featureFlag'),
auth: service(),
router: service(),
queryParams: [{ authMethod: 'with', oidcProvider: 'o' }],
namespaceQueryParam: alias('clusterController.namespaceQueryParam'),
wrappedToken: alias('vaultController.wrappedToken'),
redirectTo: alias('vaultController.redirectTo'),
managedNamespaceRoot: alias('featureFlagService.managedNamespaceRoot'),
authMethod: '',
oidcProvider: '',

View File

@ -3,9 +3,11 @@ import { computed } from '@ember/object';
import Controller from '@ember/controller';
import { task } from 'ember-concurrency';
import { supportedSecretBackends } from 'vault/helpers/supported-secret-backends';
import { inject as service } from '@ember/service';
const LINKED_BACKENDS = supportedSecretBackends();
export default Controller.extend({
flashMessages: service(),
displayableBackends: filterBy('model', 'shouldIncludeInList'),
supportedBackends: computed('displayableBackends', 'displayableBackends.[]', function () {

View File

@ -28,16 +28,22 @@ export default Controller.extend(CONFIG_ATTRS, {
const isDelete = options.delete;
if (this.model.type === 'ssh') {
this.set('loading', true);
this.model.saveCA({ isDelete }).then(() => {
this.set('loading', false);
this.send('refreshRoute');
this.set('configured', !isDelete);
if (isDelete) {
this.flashMessages.success('SSH Certificate Authority Configuration deleted!');
} else {
this.flashMessages.success('SSH Certificate Authority Configuration saved!');
}
});
this.model
.saveCA({ isDelete })
.then(() => {
this.set('loading', false);
this.send('refreshRoute');
this.set('configured', !isDelete);
if (isDelete) {
this.flashMessages.success('SSH Certificate Authority Configuration deleted!');
} else {
this.flashMessages.success('SSH Certificate Authority Configuration saved!');
}
})
.catch((error) => {
const errorMessage = error.errors ? error.errors.join('. ') : error;
this.flashMessages.danger(errorMessage);
});
}
},
@ -57,7 +63,6 @@ export default Controller.extend(CONFIG_ATTRS, {
},
})
.then(() => {
this.model.send('pushedData');
this.reset();
this.flashMessages.success('The backend configuration saved successfully!');
})

View File

@ -16,7 +16,7 @@ export function parsePkiCert([model]) {
let cert_asn1 = asn1js.fromBER(stringToArrayBuffer(cert_der));
cert = new Certificate({ schema: cert_asn1.result });
} catch (error) {
console.debug('DEBUG: Parsing Certificate', error);
console.debug('DEBUG: Parsing Certificate', error); // eslint-disable-line
return {
can_parse: false,
};

View File

@ -2,7 +2,6 @@
<html>
<head>
<meta charset="utf-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta http-equiv="cache-control" content="no-store" />
<meta http-equiv="expires" content="0" />
<meta http-equiv="pragma" content="no-cache" />

View File

@ -5,7 +5,7 @@ export function initialize() {
registerDeprecationHandler((message, options, next) => {
// filter deprecations that are scheduled to be removed in a specific version
// when upgrading or addressing deprecation warnings be sure to update this or remove if not needed
if (options?.until !== '4.0.0') {
if (options?.until !== '5.0.0') {
next(message, options);
}
return;

View File

@ -1,9 +1,8 @@
import Model, { hasMany, attr } from '@ember-data/model';
import Model, { belongsTo, hasMany, attr } from '@ember-data/model';
import { alias } from '@ember/object/computed'; // eslint-disable-line
import { computed } from '@ember/object'; // eslint-disable-line
import { fragment } from 'ember-data-model-fragments/attributes';
import { inject as service } from '@ember/service';
import fieldToAttrs, { expandAttributeMeta } from 'vault/utils/field-to-attrs';
import { memberAction } from 'ember-api-actions';
import apiPath from 'vault/utils/api-path';
import attachCapabilities from 'vault/lib/attach-capabilities';
import { withModelValidations } from 'vault/decorators/model-validations';
@ -17,6 +16,9 @@ const validations = {
@withModelValidations(validations)
class AuthMethodModel extends Model {}
const ModelExport = AuthMethodModel.extend({
store: service(),
config: belongsTo('mount-config', { async: false, inverse: null }), // one-to-none that replaces former fragment
authConfigs: hasMany('auth-config', { polymorphic: true, inverse: 'backend', async: false }),
path: attr('string'),
accessor: attr('string'),
@ -30,7 +32,6 @@ const ModelExport = AuthMethodModel.extend({
description: attr('string', {
editType: 'textarea',
}),
config: fragment('mount-config', { defaultValue: {} }),
local: attr('boolean', {
helpText:
'When Replication is enabled, a local mount will not be replicated across clusters. This can only be specified at mount time.',
@ -67,13 +68,6 @@ const ModelExport = AuthMethodModel.extend({
return expandAttributeMeta(this, tuneAttrs);
}),
// sys/mounts/auth/[auth-path]/tune.
tune: memberAction({
path: 'tune',
type: 'post',
urlType: 'updateRecord',
}),
formFields: computed(function () {
return [
'type',
@ -110,6 +104,10 @@ const ModelExport = AuthMethodModel.extend({
}),
canDisable: alias('deletePath.canDelete'),
canEdit: alias('configPath.canUpdate'),
tune(data) {
return this.store.adapterFor('auth-method').tune(this.path, data);
},
});
export default attachCapabilities(ModelExport, {

View File

@ -1,8 +1,7 @@
import Model, { attr, hasMany } from '@ember-data/model';
import Model, { attr, belongsTo, hasMany } from '@ember-data/model';
import { inject as service } from '@ember/service';
import { alias, and, equal, gte, not, or } from '@ember/object/computed';
import { get, computed } from '@ember/object';
import { fragment } from 'ember-data-model-fragments/attributes';
export default Model.extend({
version: service(),
@ -53,10 +52,10 @@ export default Model.extend({
allReplicationDisabled: and('{dr,performance}.replicationDisabled'),
anyReplicationEnabled: or('{dr,performance}.replicationEnabled'),
dr: fragment('replication-attributes'),
performance: fragment('replication-attributes'),
dr: belongsTo('replication-attributes', { async: false, inverse: null }),
performance: belongsTo('replication-attributes', { async: false, inverse: null }),
// this service exposes what mode the UI is currently viewing
// replicationAttrs will then return the relevant `replication-attributes` fragment
// replicationAttrs will then return the relevant `replication-attributes` model
rm: service('replication-mode'),
drMode: alias('dr.mode'),
replicationMode: alias('rm.mode'),

View File

@ -3,13 +3,16 @@ import { tracked } from '@glimmer/tracking';
import { expandAttributeMeta } from 'vault/utils/field-to-attrs';
import { withModelValidations } from 'vault/decorators/model-validations';
import lazyCapabilities, { apiPath } from 'vault/macros/lazy-capabilities';
import { inject as service } from '@ember/service';
const CRED_PROPS = {
azurekeyvault: ['client_id', 'client_secret', 'tenant_id'],
awskms: ['access_key', 'secret_key', 'session_token', 'endpoint'],
gcpckms: ['service_account_file'],
};
const OPTIONAL_CRED_PROPS = ['session_token', 'endpoint'];
// since we have dynamic credential attributes based on provider we need a dynamic presence validator
// add validators for all cred props and return true for value if not associated with selected provider
const credValidators = Object.keys(CRED_PROPS).reduce((obj, providerKey) => {
@ -27,13 +30,16 @@ const credValidators = Object.keys(CRED_PROPS).reduce((obj, providerKey) => {
});
return obj;
}, {});
const validations = {
name: [{ type: 'presence', message: 'Provider name is required' }],
keyCollection: [{ type: 'presence', message: 'Key Vault instance name' }],
...credValidators,
};
@withModelValidations(validations)
export default class KeymgmtProviderModel extends Model {
@service store;
@attr('string') backend;
@attr('string', {
label: 'Provider name',

View File

@ -4,6 +4,7 @@ import PromiseProxyMixin from '@ember/object/promise-proxy-mixin';
import { methods } from 'vault/helpers/mountable-auth-methods';
import { withModelValidations } from 'vault/decorators/model-validations';
import { isPresent } from '@ember/utils';
import { inject as service } from '@ember/service';
const validations = {
name: [{ type: 'presence', message: 'Name is required' }],
@ -26,8 +27,10 @@ const validations = {
},
],
};
@withModelValidations(validations)
export default class MfaLoginEnforcementModel extends Model {
@service store;
@attr('string') name;
@hasMany('mfa-method') mfa_methods;
@attr('string') namespace_id;

View File

@ -1,41 +1,53 @@
import { attr } from '@ember-data/model';
import Fragment from 'ember-data-model-fragments/fragment';
import Model, { attr } from '@ember-data/model';
export default Fragment.extend({
defaultLeaseTtl: attr({
export default class MountConfigModel extends Model {
@attr({
label: 'Default Lease TTL',
editType: 'ttl',
}),
maxLeaseTtl: attr({
})
defaultLeaseTtl;
@attr({
label: 'Max Lease TTL',
editType: 'ttl',
}),
auditNonHmacRequestKeys: attr({
})
maxLeaseTtl;
@attr({
label: 'Request keys excluded from HMACing in audit',
editType: 'stringArray',
helpText: "Keys that will not be HMAC'd by audit devices in the request data object.",
}),
auditNonHmacResponseKeys: attr({
})
auditNonHmacRequestKeys;
@attr({
label: 'Response keys excluded from HMACing in audit',
editType: 'stringArray',
helpText: "Keys that will not be HMAC'd by audit devices in the response data object.",
}),
listingVisibility: attr('string', {
})
auditNonHmacResponseKeys;
@attr('string', {
editType: 'boolean',
label: 'List method when unauthenticated',
trueValue: 'unauth',
falseValue: 'hidden',
}),
passthroughRequestHeaders: attr({
})
listingVisibility;
@attr({
label: 'Allowed passthrough request headers',
helpText: 'Headers to allow and pass from the request to the backend',
editType: 'stringArray',
}),
tokenType: attr('string', {
})
passthroughRequestHeaders;
@attr('string', {
label: 'Token Type',
helpText:
"The type of token that should be generated via this role. Can be `service`, `batch`, or `default` to use the mount's default (which unless changed will be `service` tokens).",
possibleValues: ['default', 'batch', 'service'],
defaultFormValue: 'default',
}),
});
})
tokenType;
}

View File

@ -1,13 +0,0 @@
import { attr } from '@ember-data/model';
import Fragment from 'ember-data-model-fragments/fragment';
export default Fragment.extend({
version: attr('number', {
label: 'Version',
helpText:
'The KV Secrets Engine can operate in different modes. Version 1 is the original generic Secrets Engine the allows for storing of static key/value pairs. Version 2 added more features including data versioning, TTLs, and check and set.',
possibleValues: [2, 1],
// This shouldn't be defaultValue because if no version comes back from API we should assume it's v1
defaultFormValue: 2, // Set the form to 2 by default
}),
});

View File

@ -1,9 +1,8 @@
import Model, { attr } from '@ember-data/model';
import { match, not } from '@ember/object/computed';
import { computed } from '@ember/object';
import { attr } from '@ember-data/model';
import Fragment from 'ember-data-model-fragments/fragment';
export default Fragment.extend({
export default Model.extend({
clusterId: attr('string'),
clusterIdDisplay: computed('clusterId', 'mode', function () {
const clusterId = this.clusterId;

View File

@ -1,7 +1,6 @@
import Model, { attr } from '@ember-data/model';
import Model, { attr, belongsTo } from '@ember-data/model';
import { computed } from '@ember/object'; // eslint-disable-line
import { equal } from '@ember/object/computed'; // eslint-disable-line
import { fragment } from 'ember-data-model-fragments/attributes';
import fieldToAttrs, { expandAttributeMeta } from 'vault/utils/field-to-attrs';
import { withModelValidations } from 'vault/decorators/model-validations';
@ -29,8 +28,16 @@ export default SecretEngineModel.extend({
description: attr('string', {
editType: 'textarea',
}),
config: fragment('mount-config', { defaultValue: {} }),
options: fragment('mount-options', { defaultValue: {} }),
// will only have value for kv type
version: attr('number', {
label: 'Version',
helpText:
'The KV Secrets Engine can operate in different modes. Version 1 is the original generic Secrets Engine the allows for storing of static key/value pairs. Version 2 added more features including data versioning, TTLs, and check and set.',
possibleValues: [2, 1],
// This shouldn't be defaultValue because if no version comes back from API we should assume it's v1
defaultFormValue: 2, // Set the form to 2 by default
}),
config: belongsTo('mount-config', { async: false, inverse: null }),
local: attr('boolean', {
helpText:
'When Replication is enabled, a local mount will not be replicated across clusters. This can only be specified at mount time.',
@ -60,11 +67,10 @@ export default SecretEngineModel.extend({
helperTextEnabled: 'Delete all new versions of this secret after',
}),
modelTypeForKV: computed('engineType', 'options.version', function () {
modelTypeForKV: computed('engineType', 'version', function () {
let type = this.engineType;
let version = this.options?.version;
let modelType = 'secret';
if ((type === 'kv' || type === 'generic') && version === 2) {
if ((type === 'kv' || type === 'generic') && this.version === 2) {
modelType = 'secret-v2';
}
return modelType;
@ -72,18 +78,17 @@ export default SecretEngineModel.extend({
isV2KV: equal('modelTypeForKV', 'secret-v2'),
formFields: computed('engineType', 'options.version', function () {
formFields: computed('engineType', 'version', function () {
let type = this.engineType;
let version = this.options?.version;
let fields = ['type', 'path', 'description', 'accessor', 'local', 'sealWrap'];
// no ttl options for keymgmt
const ttl = type !== 'keymgmt' ? 'defaultLeaseTtl,maxLeaseTtl,' : '';
fields.push(`config.{${ttl}auditNonHmacRequestKeys,auditNonHmacResponseKeys,passthroughRequestHeaders}`);
if (type === 'kv' || type === 'generic') {
fields.push('options.{version}');
fields.push('version');
}
// version comes in as number not string
if (type === 'kv' && version === 2) {
if (type === 'kv' && this.version === 2) {
fields.push('casRequired', 'deleteVersionAfter', 'maxVersions');
}
return fields;
@ -108,7 +113,7 @@ export default SecretEngineModel.extend({
);
if (type === 'kv' || type === 'generic') {
optionsGroup['Method Options'].unshift('options.{version}');
optionsGroup['Method Options'].unshift('version');
}
if (type === 'database') {
// For the Database Secret Engine we want to highlight the defaultLeaseTtl and maxLeaseTtl, removing them from the options object

View File

@ -2,8 +2,8 @@
//
import AuthMethodModel from './auth-method';
import { fragment } from 'ember-data-model-fragments/attributes';
import { belongsTo } from '@ember-data/model';
export default AuthMethodModel.extend({
otherConfig: fragment('mount-config', { defaultValue: {} }),
otherConfig: belongsTo('mount-config', { async: false, inverse: null }),
});

View File

@ -29,7 +29,10 @@ export default class CodeMirrorModifier extends Modifier {
@action
_onChange(editor) {
this.args.named.onUpdate(editor.getValue(), this._editor);
// avoid sending change event after initial setup when editor value is set to content
if (this.args.named.content !== editor.getValue()) {
this.args.named.onUpdate(editor.getValue(), this._editor);
}
}
@action

View File

@ -17,7 +17,7 @@ export default Route.extend({
error(error, transition) {
let controlGroup = this.controlGroup;
if (error instanceof ControlGroupError) {
return controlGroup.handleError(error, transition);
return controlGroup.handleError(error);
}
if (error.path === '/v1/sys/wrapping/unwrap') {
controlGroup.unmarkTokenForUnwrap();

View File

@ -7,10 +7,13 @@ import Ember from 'ember';
const SPLASH_DELAY = Ember.testing ? 0 : 300;
export default Route.extend({
store: service(),
version: service(),
beforeModel() {
return this.version.fetchVersion();
},
model() {
// hardcode single cluster
const fixture = {

View File

@ -3,6 +3,7 @@ import Route from '@ember/routing/route';
import UnloadModel from 'vault/mixins/unload-model-route';
export default Route.extend(UnloadModel, {
store: service(),
version: service(),
beforeModel() {

View File

@ -3,6 +3,7 @@ import Route from '@ember/routing/route';
import UnloadModel from 'vault/mixins/unload-model-route';
export default Route.extend(UnloadModel, {
store: service(),
version: service(),
beforeModel() {

View File

@ -3,6 +3,7 @@ import Route from '@ember/routing/route';
import UnloadModel from 'vault/mixins/unload-model-route';
export default Route.extend(UnloadModel, {
store: service(),
version: service(),
beforeModel() {

View File

@ -1,8 +1,11 @@
import Route from '@ember/routing/route';
import UnloadModelRoute from 'vault/mixins/unload-model-route';
import UnsavedModelRoute from 'vault/mixins/unsaved-model-route';
import { inject as service } from '@ember/service';
export default Route.extend(UnloadModelRoute, UnsavedModelRoute, {
store: service(),
model(params) {
let itemType = this.modelFor('vault.cluster.access.identity');
let modelType = `identity/${itemType}-alias`;

View File

@ -1,8 +1,11 @@
import Route from '@ember/routing/route';
import UnloadModelRoute from 'vault/mixins/unload-model-route';
import UnsavedModelRoute from 'vault/mixins/unsaved-model-route';
import { inject as service } from '@ember/service';
export default Route.extend(UnloadModelRoute, UnsavedModelRoute, {
store: service(),
model(params) {
let itemType = this.modelFor('vault.cluster.access.identity');
let modelType = `identity/${itemType}-alias`;

View File

@ -1,7 +1,10 @@
import Route from '@ember/routing/route';
import ListRoute from 'core/mixins/list-route';
import { inject as service } from '@ember/service';
export default Route.extend(ListRoute, {
store: service(),
model(params) {
let itemType = this.modelFor('vault.cluster.access.identity');
let modelType = `identity/${itemType}-alias`;
@ -19,10 +22,12 @@ export default Route.extend(ListRoute, {
}
});
},
setupController(controller) {
this._super(...arguments);
controller.set('identityType', this.modelFor('vault.cluster.access.identity'));
},
actions: {
willTransition(transition) {
window.scrollTo(0, 0);

View File

@ -3,8 +3,11 @@ import { hash } from 'rsvp';
import { set } from '@ember/object';
import Route from '@ember/routing/route';
import { TABS } from 'vault/helpers/tabs-for-identity-show';
import { inject as service } from '@ember/service';
export default Route.extend({
store: service(),
model(params) {
let { section } = params;
let itemType = this.modelFor('vault.cluster.access.identity') + '-alias';

View File

@ -1,8 +1,11 @@
import Route from '@ember/routing/route';
import UnloadModelRoute from 'vault/mixins/unload-model-route';
import UnsavedModelRoute from 'vault/mixins/unsaved-model-route';
import { inject as service } from '@ember/service';
export default Route.extend(UnloadModelRoute, UnsavedModelRoute, {
store: service(),
model() {
let itemType = this.modelFor('vault.cluster.access.identity');
let modelType = `identity/${itemType}`;

View File

@ -1,8 +1,11 @@
import Route from '@ember/routing/route';
import UnloadModelRoute from 'vault/mixins/unload-model-route';
import UnsavedModelRoute from 'vault/mixins/unsaved-model-route';
import { inject as service } from '@ember/service';
export default Route.extend(UnloadModelRoute, UnsavedModelRoute, {
store: service(),
model(params) {
let itemType = this.modelFor('vault.cluster.access.identity');
let modelType = `identity/${itemType}`;

View File

@ -1,7 +1,10 @@
import Route from '@ember/routing/route';
import ListRoute from 'core/mixins/list-route';
import { inject as service } from '@ember/service';
export default Route.extend(ListRoute, {
store: service(),
model(params) {
let itemType = this.modelFor('vault.cluster.access.identity');
let modelType = `identity/${itemType}`;

View File

@ -1,13 +1,17 @@
import Route from '@ember/routing/route';
import UnloadModelRoute from 'vault/mixins/unload-model-route';
import { inject as service } from '@ember/service';
export default Route.extend(UnloadModelRoute, {
store: service(),
beforeModel() {
let itemType = this.modelFor('vault.cluster.access.identity');
if (itemType !== 'entity') {
return this.transitionTo('vault.cluster.access.identity');
}
},
model() {
let modelType = `identity/entity-merge`;
return this.store.createRecord(modelType);

View File

@ -4,8 +4,11 @@ import { hash } from 'rsvp';
import { set } from '@ember/object';
import Route from '@ember/routing/route';
import { TABS } from 'vault/helpers/tabs-for-identity-show';
import { inject as service } from '@ember/service';
export default Route.extend({
store: service(),
model(params) {
let { section } = params;
let itemType = this.modelFor('vault.cluster.access.identity');

View File

@ -1,7 +1,10 @@
import Route from '@ember/routing/route';
import ClusterRoute from 'vault/mixins/cluster-route';
import { inject as service } from '@ember/service';
export default Route.extend(ClusterRoute, {
store: service(),
model() {
return this.store.findRecord('capabilities', 'sys/leases/lookup/');
},

View File

@ -1,8 +1,11 @@
import { set } from '@ember/object';
import { hash } from 'rsvp';
import Route from '@ember/routing/route';
import { inject as service } from '@ember/service';
export default Route.extend({
store: service(),
queryParams: {
page: {
refreshModel: true,

View File

@ -2,10 +2,12 @@ import { set } from '@ember/object';
import { hash } from 'rsvp';
import Route from '@ember/routing/route';
import UnloadModelRoute from 'vault/mixins/unload-model-route';
import utils from 'vault/lib/key-utils';
import { inject as service } from '@ember/service';
export default Route.extend(UnloadModelRoute, {
store: service(),
beforeModel() {
const { lease_id: leaseId } = this.paramsFor(this.routeName);
const parentKey = utils.parentKeyForKey(leaseId);

View File

@ -4,7 +4,9 @@ import Route from '@ember/routing/route';
import { inject as service } from '@ember/service';
export default Route.extend({
store: service(),
pathHelp: service('path-help'),
model(params) {
const { path } = params;
return this.store.findAll('auth-method').then((modelArray) => {

View File

@ -2,8 +2,11 @@ import Route from '@ember/routing/route';
import UnloadModelRoute from 'vault/mixins/unload-model-route';
import UnsavedModelRoute from 'vault/mixins/unsaved-model-route';
import { singularize } from 'ember-inflector';
import { inject as service } from '@ember/service';
export default Route.extend(UnloadModelRoute, UnsavedModelRoute, {
store: service(),
model() {
const { item_type: itemType } = this.paramsFor('vault.cluster.access.method.item');
const methodModel = this.modelFor('vault.cluster.access.method');

View File

@ -2,8 +2,11 @@ import Route from '@ember/routing/route';
import UnloadModelRoute from 'vault/mixins/unload-model-route';
import UnsavedModelRoute from 'vault/mixins/unsaved-model-route';
import { singularize } from 'ember-inflector';
import { inject as service } from '@ember/service';
export default Route.extend(UnloadModelRoute, UnsavedModelRoute, {
store: service(),
model(params) {
const id = params.item_id;
const { item_type: itemType } = this.paramsFor('vault.cluster.access.method.item');

View File

@ -4,6 +4,7 @@ import { singularize } from 'ember-inflector';
import ListRoute from 'vault/mixins/list-route';
export default Route.extend(ListRoute, {
store: service(),
wizard: service(),
pathHelp: service('path-help'),
@ -36,6 +37,7 @@ export default Route.extend(ListRoute, {
}
});
},
actions: {
willTransition(transition) {
window.scrollTo(0, 0);
@ -49,6 +51,7 @@ export default Route.extend(ListRoute, {
this.refresh();
},
},
setupController(controller) {
this._super(...arguments);
const { apiPath, authMethodPath, itemType, methodModel } = this.getMethodAndModelInfo();

View File

@ -3,7 +3,9 @@ import { inject as service } from '@ember/service';
import Route from '@ember/routing/route';
export default Route.extend({
store: service(),
pathHelp: service('path-help'),
model(params) {
const id = params.item_id;
const { item_type: itemType } = this.paramsFor('vault.cluster.access.method.item');

View File

@ -1,6 +1,9 @@
import Route from '@ember/routing/route';
import { inject as service } from '@ember/service';
export default Route.extend({
store: service(),
queryParams: {
page: {
refreshModel: true,

View File

@ -1,6 +1,9 @@
import Route from '@ember/routing/route';
import { inject as service } from '@ember/service';
export default class MfaEnforcementsRoute extends Route {
@service store;
model() {
return this.store.query('mfa-login-enforcement', {}).catch((err) => {
if (err.httpStatus === 404) {

View File

@ -1,6 +1,9 @@
import Route from '@ember/routing/route';
import { inject as service } from '@ember/service';
export default class MfaConfigureRoute extends Route {
@service store;
beforeModel() {
return this.store
.query('mfa-method', {})

View File

@ -2,6 +2,7 @@ import Route from '@ember/routing/route';
import { inject as service } from '@ember/service';
export default class MfaMethodsRoute extends Route {
@service store;
@service router;
model() {

View File

@ -1,6 +1,10 @@
import Route from '@ember/routing/route';
import { hash } from 'rsvp';
import { inject as service } from '@ember/service';
export default class MfaMethodRoute extends Route {
@service store;
model({ id }) {
return hash({
method: this.store.findRecord('mfa-method', id).then((data) => data),

View File

@ -3,12 +3,15 @@ import Route from '@ember/routing/route';
import UnloadModel from 'vault/mixins/unload-model-route';
export default Route.extend(UnloadModel, {
store: service(),
version: service(),
beforeModel() {
return this.version.fetchFeatures().then(() => {
return this._super(...arguments);
});
},
model() {
return this.version.hasNamespaces ? this.store.createRecord('namespace') : null;
},

View File

@ -3,12 +3,16 @@ import Route from '@ember/routing/route';
import UnloadModel from 'vault/mixins/unload-model-route';
export default Route.extend(UnloadModel, {
store: service(),
queryParams: {
page: {
refreshModel: true,
},
},
version: service(),
beforeModel() {
this.store.unloadAll('namespace');
return this.version.fetchFeatures().then(() => {
@ -50,6 +54,7 @@ export default Route.extend(UnloadModel, {
});
}
},
actions: {
error(error, transition) {
/* eslint-disable-next-line ember/no-controller-access-in-routes */

View File

@ -1,6 +1,9 @@
import Route from '@ember/routing/route';
import { inject as service } from '@ember/service';
export default class OidcAssignmentRoute extends Route {
@service store;
model({ name }) {
return this.store.findRecord('oidc/assignment', name);
}

View File

@ -1,6 +1,9 @@
import Route from '@ember/routing/route';
import { inject as service } from '@ember/service';
export default class OidcAssignmentsCreateRoute extends Route {
@service store;
model() {
return this.store.createRecord('oidc/assignment');
}

View File

@ -1,6 +1,8 @@
import Route from '@ember/routing/route';
import { inject as service } from '@ember/service';
export default class OidcAssignmentsRoute extends Route {
@service store;
model() {
return this.store.query('oidc/assignment', {}).catch((err) => {
if (err.httpStatus === 404) {

View File

@ -1,6 +1,9 @@
import Route from '@ember/routing/route';
import { inject as service } from '@ember/service';
export default class OidcClientRoute extends Route {
@service store;
model({ name }) {
return this.store.findRecord('oidc/client', name);
}

View File

@ -1,6 +1,9 @@
import Route from '@ember/routing/route';
import { inject as service } from '@ember/service';
export default class OidcClientProvidersRoute extends Route {
@service store;
model() {
const model = this.modelFor('vault.cluster.access.oidc.clients.client');
return this.store

View File

@ -1,6 +1,9 @@
import Route from '@ember/routing/route';
import { inject as service } from '@ember/service';
export default class OidcClientsCreateRoute extends Route {
@service store;
model() {
return this.store.createRecord('oidc/client');
}

View File

@ -1,6 +1,7 @@
import Route from '@ember/routing/route';
import { inject as service } from '@ember/service';
export default class OidcClientsRoute extends Route {
@service store;
@service router;
model() {

View File

@ -2,6 +2,7 @@ import Route from '@ember/routing/route';
import { inject as service } from '@ember/service';
export default class OidcConfigureRoute extends Route {
@service store;
@service router;
beforeModel() {

View File

@ -1,6 +1,9 @@
import Route from '@ember/routing/route';
import { inject as service } from '@ember/service';
export default class OidcKeysCreateRoute extends Route {
@service store;
model() {
return this.store.createRecord('oidc/key');
}

View File

@ -1,5 +1,9 @@
import Route from '@ember/routing/route';
import { inject as service } from '@ember/service';
export default class OidcKeysRoute extends Route {
@service store;
model() {
return this.store.query('oidc/key', {}).catch((err) => {
if (err.httpStatus === 404) {

View File

@ -1,6 +1,9 @@
import Route from '@ember/routing/route';
import { inject as service } from '@ember/service';
export default class OidcKeyRoute extends Route {
@service store;
model({ name }) {
return this.store.findRecord('oidc/key', name);
}

View File

@ -1,6 +1,9 @@
import Route from '@ember/routing/route';
import { inject as service } from '@ember/service';
export default class OidcKeyClientsRoute extends Route {
@service store;
async model() {
const { allowedClientIds } = this.modelFor('vault.cluster.access.oidc.keys.key');
return await this.store.query('oidc/client', { paramKey: 'client_id', filterFor: allowedClientIds });

Some files were not shown because too many files have changed in this diff Show More