Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We鈥檒l occasionally send you account related emails.

Already on GitHub? Sign in to your account

fix: helm ls -> click results in error #9136

Merged
merged 1 commit into from
Dec 7, 2022
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
2 changes: 1 addition & 1 deletion plugins/plugin-kubectl/helm/src/controller/helm/list.ts
Original file line number Diff line number Diff line change
Expand Up @@ -31,7 +31,7 @@ async function doList(args: Arguments<KubeOptions>) {
// nothing to list
return true
} else {
return formatTable('helm', 'get', undefined, args, preTables[0])
return formatTable('helm', 'status', undefined, args, preTables[0])
}
}

Expand Down
181 changes: 54 additions & 127 deletions plugins/plugin-kubectl/helm/src/controller/helm/status.ts
Original file line number Diff line number Diff line change
Expand Up @@ -15,8 +15,8 @@
*/

import Debug from 'debug'
import { Arguments, ExecOptions, Registrar, NavResponse, i18n } from '@kui-shell/core'
import { doHelp, KubeOptions } from '@kui-shell/plugin-kubectl'
import { Arguments, DescriptionList, ExecOptions, Registrar, Menu, NavResponse, i18n } from '@kui-shell/core'
import { doHelp, withKubeconfigFrom, KubeOptions } from '@kui-shell/plugin-kubectl'

import isUsage from './usage'
import doExecWithStdout from './exec'
Expand All @@ -34,7 +34,7 @@ export const format = async (
args: Arguments<KubeOptions>,
response: string,
execOptions: ExecOptions
) => {
): Promise<NavResponse> => {
const command = 'kubectl'
const verb = 'get'

Expand All @@ -52,135 +52,62 @@ export const format = async (
const revisionFromHelmStatusOutput = revisionMatch[1]
debug('revision', revisionFromHelmStatusOutput)

// const namespaceFor = (entityType: string) => {
/* const namespaceFor = () => {
return namespaceFromHelmStatusOutput
} */

const resources = [] /* resourcesString
.split(/==>/)
.map(_ => _.split(/[\n\r]/))
.filter(A => A.length > 0 && A[0])
.map(A => {
const kind = A[0].trim()

// "v1/pod(related)" => "pod"
const entityType = kind.replace(/(v\w+\/)?([^()]*)(\s*\(.*\))?/, '$2')

if (!/\s*NAME(\s+|$)/.test(A[1])) {
// no header row? this seems to be a bug in helm
const match = A[1].match(/(.+\s+)(.+)/)
if (match && match[1]) {
const secondColIdx = match[1].length
const firstCol = 'NAME'
const secondCol = 'AGE'
const spaces = (nSpaces: number) => new Array(nSpaces).join(' ')
const header = `${firstCol}${spaces(secondColIdx - firstCol.length)}${secondCol}`
A.splice(1, 0, header)
}
}

return {
kind,
table: formatTable(
command,
verb,
entityType,
Object.assign({}, args, {
parsedOptions: Object.assign({}, args.parsedOptions, { namespace: namespaceFor() })
}),
preprocessTable([A.slice(1).join('\n')])[0]
)
}
}) */

debug('resources', resources)

if (execOptions.nested) {
debug('returning tables for nested call')
return Promise.all(
resources.map(async ({ kind, table }) => {
const T = await table
T.title = kind
return T
})
)
} else {
const notesMatch = response.match(/NOTES:\n([\s\S]+)?/)

const statusMatch = headerString.match(/LAST DEPLOYED: (.*)\nNAMESPACE: (.*)\nSTATUS: (.*)/)
const status = !statusMatch
? headerString
: `### ${strings2('Last Deployed')}
${statusMatch[1]}

### ${strings2('Namespace')}
${statusMatch[2]}

### ${strings2('Revision')}
${revisionFromHelmStatusOutput}

### ${strings('status')}
\`${statusMatch[3]}\`
`

const summary = ''
const notes = notesMatch && notesMatch[1]

const overviewMenu = {
label: 'Overview',
items: [
{
mode: 'status',
label: strings('status'),
content: status,
contentType: 'text/markdown'
}
const statusMatch = headerString.match(/LAST DEPLOYED: (.*)\nNAMESPACE: (.*)\nSTATUS: (.*)/)
const status: DescriptionList = {
apiVersion: 'kui-shell/v1',
kind: 'DescriptionList',
spec: {
groups: [
{ term: strings2('Last Deployed'), description: statusMatch[1] },
{ term: strings2('Revision'), description: revisionFromHelmStatusOutput },
{ term: strings('status'), description: statusMatch[3] }
]
.concat(
!summary
? []
: [
{
mode: 'summary',
label: strings('summary'),
content: summary,
contentType: 'text/markdown'
}
]
)
.concat(
!notes
? []
: [
{
mode: 'notes',
label: strings2('Notes'),
content: `\`\`\`${notes}\`\`\``,
contentType: 'text/markdown'
}
]
)
}
}

const resourcesMenu = {
label: 'Resources',
items: await Promise.all(
resources.map(async _ => ({
mode: _.kind,
content: await _.table
}))
)
}
const summary = ''

const commandResponse: NavResponse = {
apiVersion: 'kui-shell/v1',
kind: 'NavResponse',
breadcrumbs: [{ label: 'helm' }, { label: 'release', command: `helm ls` }, { label: name }],
menus: [overviewMenu, resourcesMenu]
}
const notesMatch = response.match(/NOTES:\n([\s\S]+)?/)
const notes = notesMatch && notesMatch[1]

const overviewMenu: Menu = {
label: 'Overview',
items: []
}

overviewMenu.items.push({
mode: 'status',
label: strings('status'),
content: status
})

if (summary) {
overviewMenu.items.push({
mode: 'summary',
label: strings('summary'),
content: summary,
contentType: 'text/markdown'
})
}

if (notes) {
overviewMenu.items.push({
mode: 'notes',
label: strings2('Notes'),
content: `\`\`\`${notes}\`\`\``,
contentType: 'text/markdown'
})
}

return commandResponse
return {
apiVersion: 'kui-shell/v1',
kind: 'NavResponse',
breadcrumbs: [
{ label: 'helm' },
{ label: 'release', command: withKubeconfigFrom(args, `helm ls`) },
{ label: name }
],
menus: [overviewMenu]
}
}

Expand Down
6 changes: 2 additions & 4 deletions plugins/plugin-kubectl/src/lib/view/formatTable.ts
Original file line number Diff line number Diff line change
Expand Up @@ -232,16 +232,14 @@ export const formatTable = async <O extends KubeOptions>(
// otherwise, stay with the command (kubectl or helm) that we
// started with
const isHelmStatus = command === 'helm' && verb === 'status'
const drilldownCommand = isHelmStatus ? 'kubectl' : command
const drilldownCommand = command

const drilldownVerb =
(verb === 'get' || verb === 'top'
? 'get'
: command === 'helm' && (verb === 'list' || verb === 'ls')
? 'get'
: isHelmStatus
? 'get'
: verb === 'krew'
: isHelmStatus || verb === 'krew'
? verb
: undefined) || undefined

Expand Down