import EmberObject from '@ember/object'; import { inject as service } from '@ember/service'; import { get, set } from '@ember/object'; import { hash, resolve } from 'rsvp'; import Route from '@ember/routing/route'; import Ember from 'ember'; import C from 'ui/utils/constants'; export default Route.extend({ prefs: service(), clusterStore: service(), beforeModel() { const promises = {}; if (!window.Prettycron) { set(promises, 'Prettycron', import('prettycron')); } if (!window.ShellQuote) { set(promises, 'ShellQuote', import('shell-quote')); } return hash(promises).then((resolved) => { if (resolved.Prettycron) { window.Prettycron = resolved.Prettycron; } if (resolved.ShellQuote) { window.ShellQuote = resolved.ShellQuote; } return resolved; }); }, model(params/* , transition*/) { var store = get(this, 'store'); let promise = null; if (params.workloadId) { // Existing Service promise = store.find('workload', params.workloadId).then((workload) => this.modelForExisting(workload, params)); } else { promise = resolve(this.modelForNew(params)); } return hash({ dataMap: promise }).then((hash) => ({ loggingEnabled: false, dataMap: hash.dataMap, })) }, resetController(controller, isExiting/* , transition*/) { if (isExiting) { set(controller, 'namespaceId', null); set(controller, 'workloadId', null); set(controller, 'podId', null); set(controller, 'upgrade', null); set(controller, 'addSidekick', null); set(controller, 'launchConfigIndex', null); } }, queryParams: { launchConfigIndex: { refreshModel: true } }, modelForNew(params) { let scaleMode = get(this, `prefs.${ C.PREFS.LAST_SCALE_MODE }`) || 'deployment'; if (scaleMode === 'container' || scaleMode === 'service') { scaleMode = 'deployment'; } return EmberObject.create({ scaleMode, workload: this.emptyWorkload(params), container: this.emptyContainer(params), isUpgrade: false, }); }, modelForExisting(_workload, params) { if (!_workload) { return Ember.RVP.reject('Workload not found'); } const clone = _workload.clone(); const cloneType = clone.type; if ( !params.upgrade && params.addSidekick !== 'true' ) { delete clone['workloadAnnotations']; delete clone['workloadLabels']; delete clone['publicEndpoints']; set(clone, 'type', 'workload'); if ( clone.labels ) { delete clone.labels['workload.user.cattle.io/workloadselector']; } if ( clone.selector && clone.selector.matchLabels) { delete clone.selector.matchLabels['workload.user.cattle.io/workloadselector']; if ( !Object.keys(clone.selector.matchLabels).length ) { delete clone.selector['matchLabels']; } } } const containerNames = clone.containers.map((x) => get(x, 'name')); let containerName = null; if (params.launchConfigIndex !== null) { const launchConfigIndex = parseInt(params.launchConfigIndex, 10) if (launchConfigIndex > -1) { containerName = clone.containers[launchConfigIndex + 1].name; } else if (launchConfigIndex === -1) { containerName = ''; } } // Add a sidekick if (params.addSidekick) { return EmberObject.create({ scaleMode: 'sidekick', workload: clone, container: this.emptyContainer(params, get(clone, 'namespaceId')), isUpgrade: false, }); } else if (containerName === null) { // Figure out the container name if (containerNames.length > 1) { if (params.upgrade) { // If there are sidekicks, you need to pick one & come back return EmberObject.create({ workload: clone, containerNames, selectLaunchConfig: true, }); } else { // Clone with multiple containers not supported yet return Ember.RVP.reject('Cloning a workload with multiple containers not supported'); } } else { // Otherwise use primary containerName = ''; } } let container; if (containerName === '') { // The primary/only container container = clone.containers[0]; } else { // Existing container container = clone.containers.findBy('name', containerName); } if (params.upgrade) { // Upgrade workload let out = EmberObject.create({ scaleMode: (containerName ? 'sidekick' : cloneType), workload: clone, container, isUpgrade: true }); return out; } else { // Clone workload with one container let neu = get(this, 'store').createRecord(clone.serializeForNew()); delete neu.deploymentStatus; container = neu.containers[0]; // Cleanup port mappings so they get new services (neu.containers || []).forEach((container) => { (container.ports || []).forEach((port) => { delete port.name; delete port.dnsName; }); }); return EmberObject.create({ scaleMode: cloneType, workload: neu, container, isUpgrade: false // no launchConfigIndex because this will be a new service or sidekick }); } }, getNamespaceId(params) { const clusterStore = get(this, 'clusterStore'); let ns = null; if (params.namespaceId) { ns = clusterStore.getById('namespace', params.namespaceId); } if (!ns) { const project = window.l('route:application').modelFor('authenticated.project') .get('project'); const projectId = project.get('id'); const lastNamespace = clusterStore.getById('namespace', get(this, `prefs.${ C.PREFS.LAST_NAMESPACE }`)); if ( lastNamespace && get(lastNamespace, 'projectId') === projectId ) { ns = lastNamespace; } } let namespaceId = null; if (ns) { namespaceId = ns.get('id'); } return namespaceId; }, emptyWorkload(params) { const store = get(this, 'store'); return store.createRecord({ type: 'workload', namespaceId: this.getNamespaceId(params), scale: 1, dnsPolicy: 'ClusterFirst', restartPolicy: 'Always', labels: {}, containers: [], }); }, emptyContainer(params, namespaceId) { return get(this, 'store').createRecord({ type: 'container', tty: true, stdin: true, privileged: false, allowPrivilegeEscalation: false, readOnly: false, runAsNonRoot: false, namespaceId: namespaceId ? namespaceId : this.getNamespaceId(params), imagePullPolicy: get(this, `prefs.${ C.PREFS.LAST_IMAGE_PULL_POLICY }`) || 'Always', }); }, });