@@ -209,6 +214,16 @@ export default {
email() {
return this.account.emailAddress
},
+ allowNewAliases() {
+ return this.mainStore.getPreference('allow-new-aliases', true)
+ },
+ showProviderAppPassword() {
+ // Show the password reset section if:
+ // 1. Account is managed by a provider (managedByProvider is set)
+ // 2. Provider supports app passwords
+ return this.account.managedByProvider
+ && this.account.providerCapabilities?.appPasswords === true
+ },
},
watch: {
diff --git a/src/components/AliasSettings.vue b/src/components/AliasSettings.vue
index 1371d50417..2bf5ed65c5 100644
--- a/src/components/AliasSettings.vue
+++ b/src/components/AliasSettings.vue
@@ -53,7 +53,7 @@
@@ -125,7 +125,9 @@ export default {
aliases() {
return this.account.aliases
},
-
+ allowNewAliases() {
+ return this.mainStore.getPreference('allow-new-aliases', true)
+ },
accountAlias() {
return {
alias: this.account.emailAddress,
diff --git a/src/components/settings/AdminSettings.vue b/src/components/settings/AdminSettings.vue
index 78f999f90c..b8fdfb7e29 100644
--- a/src/components/settings/AdminSettings.vue
+++ b/src/components/settings/AdminSettings.vue
@@ -136,6 +136,18 @@
+
+
{{ t('mail', 'Allow aliases') }}
+
+
+
+ {{ t('mail', 'Allow users to create mail aliases') }}
+
+
+
+
@@ -300,6 +312,7 @@ import {
setImportanceClassificationEnabledByDefault,
setLayoutMessageView,
updateAllowNewMailAccounts,
+ updateAllowNewMailAliases,
updateEnabledSmartReply,
updateLlmEnabled,
updateProvisioningSettings,
@@ -368,6 +381,7 @@ export default {
},
allowNewMailAccounts: loadState('mail', 'allow_new_mail_accounts', true),
+ allowNewMailAliases: loadState('mail', 'allow_new_mail_aliases', true),
isLlmSummaryConfigured: loadState('mail', 'enabled_llm_summary_backend'),
isLlmEnabled: loadState('mail', 'llm_processing', true),
isLlmFreePromptConfigured: loadState('mail', 'enabled_llm_free_prompt_backend'),
@@ -431,6 +445,9 @@ export default {
async updateAllowNewMailAccounts(checked) {
await updateAllowNewMailAccounts(checked)
},
+ async updateAllowNewMailAliases(checked) {
+ await updateAllowNewMailAliases(checked)
+ },
async updateLlmEnabled(checked) {
await updateLlmEnabled(checked)
diff --git a/src/init.js b/src/init.js
index 980c886668..cbdcd61f5f 100644
--- a/src/init.js
+++ b/src/init.js
@@ -69,6 +69,10 @@ export default function initAfterAppCreation() {
key: 'allow-new-accounts',
value: loadState('mail', 'allow-new-accounts', true),
})
+ mainStore.savePreferenceMutation({
+ key: 'allow-new-aliases',
+ value: loadState('mail', 'allow-new-aliases', true),
+ })
mainStore.savePreferenceMutation({
key: 'password-is-unavailable',
value: loadState('mail', 'password-is-unavailable', false),
diff --git a/src/service/SettingsService.js b/src/service/SettingsService.js
index fe95eab8a4..2fb9772351 100644
--- a/src/service/SettingsService.js
+++ b/src/service/SettingsService.js
@@ -61,6 +61,14 @@ export function updateAllowNewMailAccounts(allowed) {
return axios.post(url, data).then((resp) => resp.data)
}
+export function updateAllowNewMailAliases(allowed) {
+ const url = generateUrl('/apps/mail/api/settings/allownewaliases')
+ const data = {
+ allowed,
+ }
+ return axios.post(url, data).then((resp) => resp.data)
+}
+
export async function updateLlmEnabled(enabled) {
const url = generateUrl('/apps/mail/api/settings/llm')
const data = {
diff --git a/tests/Unit/Controller/AliasesControllerTest.php b/tests/Unit/Controller/AliasesControllerTest.php
index 51e36e7933..b22dc3306f 100644
--- a/tests/Unit/Controller/AliasesControllerTest.php
+++ b/tests/Unit/Controller/AliasesControllerTest.php
@@ -18,6 +18,7 @@
use OCP\AppFramework\Db\DoesNotExistException;
use OCP\AppFramework\Http;
use OCP\AppFramework\Http\JSONResponse;
+use OCP\IConfig;
class AliasesControllerTest extends TestCase {
private $controller;
@@ -46,8 +47,12 @@ public function setUp(): void {
$this->aliasMapper = $this->createMock(AliasMapper::class);
$this->mailAccountMapper = $this->createMock(MailAccountMapper::class);
+ $config = $this->createMock(IConfig::class);
+ $config->method('getAppValue')
+ ->with('mail', 'allow_new_mail_aliases', 'yes')
+ ->willReturn('yes');
- $this->aliasService = new AliasesService($this->aliasMapper, $this->mailAccountMapper);
+ $this->aliasService = new AliasesService($this->aliasMapper, $this->mailAccountMapper, $config);
$this->controller = new AliasesController($this->appName, $this->request, $this->aliasService, $this->userId);
}
diff --git a/tests/Unit/Controller/PageControllerTest.php b/tests/Unit/Controller/PageControllerTest.php
index 804b9df2ef..32ed433061 100644
--- a/tests/Unit/Controller/PageControllerTest.php
+++ b/tests/Unit/Controller/PageControllerTest.php
@@ -269,7 +269,7 @@ public function testIndex(): void {
['version', '0.0.0', '26.0.0'],
['app.mail.attachment-size-limit', 0, 123],
]);
- $this->config->expects($this->exactly(7))
+ $this->config->expects($this->exactly(8))
->method('getAppValue')
->withConsecutive(
[ 'mail', 'installed_version' ],
@@ -279,6 +279,7 @@ public function testIndex(): void {
['mail', 'microsoft_oauth_tenant_id' ],
['core', 'backgroundjobs_mode', 'ajax' ],
['mail', 'allow_new_mail_accounts', 'yes'],
+ ['mail', 'allow_new_mail_aliases', 'yes'],
)->willReturnOnConsecutiveCalls(
$this->returnValue('1.2.3'),
$this->returnValue('threaded'),
@@ -287,7 +288,7 @@ public function testIndex(): void {
$this->returnValue(''),
$this->returnValue('cron'),
$this->returnValue('yes'),
- $this->returnValue('no')
+ $this->returnValue('yes'),
);
$this->aiIntegrationsService->expects(self::exactly(4))
->method('isLlmProcessingEnabled')
diff --git a/tests/Unit/Service/AliasesServiceTest.php b/tests/Unit/Service/AliasesServiceTest.php
index fa550a3e05..b5bdb51431 100644
--- a/tests/Unit/Service/AliasesServiceTest.php
+++ b/tests/Unit/Service/AliasesServiceTest.php
@@ -14,6 +14,7 @@
use OCA\Mail\Exception\ClientException;
use OCA\Mail\Service\AliasesService;
use OCP\AppFramework\Db\DoesNotExistException;
+use OCP\IConfig;
class AliasesServiceTest extends TestCase {
/** @var AliasesService */
@@ -28,15 +29,24 @@ class AliasesServiceTest extends TestCase {
/** @var MailAccountMapper */
private $mailAccountMapper;
+ /** @var IConfig */
+ private $config;
+
protected function setUp(): void {
parent::setUp();
$this->aliasMapper = $this->createMock(AliasMapper::class);
$this->mailAccountMapper = $this->createMock(MailAccountMapper::class);
+ $this->config = $this->createMock(IConfig::class);
+
+ $this->config->method('getAppValue')
+ ->with('mail', 'allow_new_mail_aliases', 'yes')
+ ->willReturn('yes');
$this->service = new AliasesService(
$this->aliasMapper,
- $this->mailAccountMapper
+ $this->mailAccountMapper,
+ $this->config,
);
}
@@ -123,6 +133,23 @@ public function testCreateForbiddenAccountId(): void {
);
}
+ public function testCreateDisabledByAdmin(): void {
+ $this->expectException(ClientException::class);
+ $this->expectExceptionMessage('Creating aliases has been disabled by the administrator.');
+
+ $this->config->expects(self::once())
+ ->method('getAppValue')
+ ->with('mail', 'allow_new_mail_aliases', 'yes')
+ ->willReturn('no');
+
+ $this->mailAccountMapper->expects(self::never())
+ ->method('find');
+ $this->aliasMapper->expects(self::never())
+ ->method('insert');
+
+ $this->service->create(300, 200, 'jane@doe.com', 'Jane Doe');
+ }
+
public function testDelete(): void {
$entity = new Alias();
$entity->setId(101);
diff --git a/tests/Unit/Settings/AdminSettingsTest.php b/tests/Unit/Settings/AdminSettingsTest.php
index b53df84efc..c83a7ed440 100644
--- a/tests/Unit/Settings/AdminSettingsTest.php
+++ b/tests/Unit/Settings/AdminSettingsTest.php
@@ -37,7 +37,7 @@ public function testGetSection() {
}
public function testGetForm() {
- $this->serviceMock->getParameter('initialStateService')->expects($this->exactly(14))
+ $this->serviceMock->getParameter('initialStateService')->expects($this->exactly(15))
->method('provideInitialState')
->withConsecutive(
[
@@ -55,6 +55,11 @@ public function testGetForm() {
'allow_new_mail_accounts',
$this->anything()
],
+ [
+ Application::APP_ID,
+ 'allow_new_mail_aliases',
+ $this->anything()
+ ],
[
Application::APP_ID,
'layout_message_view',