fix(core): prompt for password once when installing recommended apps

Wire the password-confirmation interceptors into the recommendedapps
entry point and switch the installer to a single bulk enable call so
the strict password confirmation on enableApps is satisfied.

Fixes #60068
-e
Signed-off-by: Peter Ringelmann <peter.ringelmann@nextcloud.com>
This commit is contained in:
Peter Ringelmann 2026-05-05 14:30:01 +02:00
parent d56ad83c1c
commit 82fb2e1bb3
2 changed files with 37 additions and 27 deletions

View file

@ -62,8 +62,8 @@
import axios from '@nextcloud/axios'
import { loadState } from '@nextcloud/initial-state'
import { t } from '@nextcloud/l10n'
import { PwdConfirmationMode } from '@nextcloud/password-confirmation'
import { generateUrl, imagePath } from '@nextcloud/router'
import pLimit from 'p-limit'
import NcButton from '@nextcloud/vue/components/NcButton'
import NcCheckboxRadioSwitch from '@nextcloud/vue/components/NcCheckboxRadioSwitch'
import logger from '../../logger.js'
@ -147,35 +147,41 @@ export default {
},
methods: {
installApps() {
this.installingApps = true
const limit = pLimit(1)
const installing = this.recommendedApps
async installApps() {
const apps = this.recommendedApps
.filter((app) => !app.active && app.isCompatible && app.canInstall && app.isSelected)
.map((app) => limit(async () => {
logger.info(`installing ${app.id}`)
app.loading = true
return axios.post(generateUrl('settings/apps/enable'), { appIds: [app.id], groups: [] })
.catch((error) => {
logger.error(`could not install ${app.id}`, { error })
app.isSelected = false
app.installationError = true
})
.then(() => {
logger.info(`installed ${app.id}`)
app.loading = false
app.active = true
})
}))
logger.debug(`installing ${installing.length} recommended apps`)
Promise.all(installing)
.then(() => {
logger.info('all recommended apps installed, redirecting …')
if (apps.length === 0) {
return
}
window.location = this.defaultPageUrl
this.installingApps = true
apps.forEach((app) => {
app.loading = true
})
const appIds = apps.map((app) => app.id)
logger.debug(`installing ${apps.length} recommended apps`, { appIds })
try {
await axios.post(
generateUrl('settings/apps/enable'),
{ appIds, groups: [] },
{ confirmPassword: PwdConfirmationMode.Strict },
)
apps.forEach((app) => {
app.loading = false
app.active = true
})
.catch((error) => logger.error('could not install recommended apps', { error }))
logger.info('all recommended apps installed, redirecting …')
window.location = this.defaultPageUrl
} catch (error) {
logger.error('could not install recommended apps', { error })
apps.forEach((app) => {
app.loading = false
app.isSelected = false
app.installationError = true
})
this.installingApps = false
}
},
customIcon(appId) {

View file

@ -4,11 +4,15 @@
*/
import { getCSPNonce } from '@nextcloud/auth'
import axios from '@nextcloud/axios'
import { translate as t } from '@nextcloud/l10n'
import { addPasswordConfirmationInterceptors } from '@nextcloud/password-confirmation'
import Vue from 'vue'
import RecommendedApps from './components/setup/RecommendedApps.vue'
import logger from './logger.js'
addPasswordConfirmationInterceptors(axios)
__webpack_nonce__ = getCSPNonce()
Vue.mixin({