mirror of
https://github.com/hcengineering/platform.git
synced 2026-08-17 18:05:42 +02:00
Configure available spaces for anonymous guests in settings (#10802)
Signed-off-by: Artem Savchenko <armisav@gmail.com>
This commit is contained in:
@@ -174,8 +174,11 @@
|
||||
"GuestSignUpDescription": "Umožňuje anonymním uživatelům připojit se k vašemu pracovnímu prostoru jako hosté s omezenými editačními právy",
|
||||
"GuestChannelsDescription": "Kanály, kde hosté mohou psát zprávy po připojení",
|
||||
"GuestChannelsArrayLabel": "Vybrat kanály",
|
||||
"GuestSelectSpaces": "Vybrat prostory",
|
||||
"GuestAutoJoinAvailableSpaces": "Automatické připojení k prostorům",
|
||||
"GuestAutoJoinAvailableSpacesHint": "Každá karta aplikace má vlastní řádek „Automatické připojení k prostorům“: vyberte, kam se hosté při aktivaci přidají. Změny se projeví okamžitě.",
|
||||
"GuestAnonymousVisibleSpaces": "Prostory viditelné anonymně",
|
||||
"GuestAnonymousVisibleSpacesHint": "Každá karta aplikace má vlastní řádek: vyberte prostory, do kterých se přidá anonymní účet pouze pro čtení mezi členy, aby je návštěvníci bez účtu mohli otevřít. Změny se projeví okamžitě.",
|
||||
"ManageIdentities": "Spravovat identity",
|
||||
"Release": "Uvolnění",
|
||||
"ReleaseSocialId": "Uvolnit sociální ID",
|
||||
|
||||
@@ -174,8 +174,11 @@
|
||||
"GuestSignUpDescription": "Ermöglicht anonymen Benutzern den Beitritt zu Ihrem Arbeitsbereich als Gäste mit eingeschränkten Bearbeitungsrechten",
|
||||
"GuestChannelsDescription": "Kanäle, in denen Gäste nach dem Beitritt Nachrichten schreiben können",
|
||||
"GuestChannelsArrayLabel": "Kanäle auswählen",
|
||||
"GuestSelectSpaces": "Bereiche auswählen",
|
||||
"GuestAutoJoinAvailableSpaces": "Automatischer Beitritt zu Bereichen",
|
||||
"GuestAutoJoinAvailableSpacesHint": "Jede Anwendungskarte hat eine eigene Zeile „Automatischer Beitritt zu Bereichen“: Wählen Sie, wo Gäste bei der Aktivierung hinzugefügt werden. Änderungen gelten sofort.",
|
||||
"GuestAnonymousVisibleSpaces": "Für anonyme sichtbare Bereiche",
|
||||
"GuestAnonymousVisibleSpacesHint": "Jede Anwendungskarte hat eine eigene Zeile: Wählen Sie Bereiche, in denen das anonyme Nur-Lese-Konto als Mitglied hinzugefügt wird, damit Besucher ohne Konto sie öffnen können. Änderungen gelten sofort.",
|
||||
"ManageIdentities": "Identitäten verwalten",
|
||||
"Release": "Freigeben",
|
||||
"ReleaseSocialId": "Social ID freigeben",
|
||||
|
||||
@@ -174,8 +174,11 @@
|
||||
"GuestSignUpDescription": "Allows anonymous users to join your workspace as guests with limited editing rights",
|
||||
"GuestChannelsDescription": "Channels where guests can write messages after joining",
|
||||
"GuestChannelsArrayLabel": "Select channels",
|
||||
"GuestSelectSpaces": "Select spaces",
|
||||
"GuestAutoJoinAvailableSpaces": "Auto-join spaces",
|
||||
"GuestAutoJoinAvailableSpacesHint": "Each application card has its own “Auto-join spaces” row: choose where workspace guests are added when they activate. Changes apply immediately.",
|
||||
"GuestAnonymousVisibleSpaces": "Spaces visible to anonymous",
|
||||
"GuestAnonymousVisibleSpacesHint": "Each application card has its own row: pick spaces where the read-only anonymous account is added as a member so visitors without an account can open them. Changes apply immediately.",
|
||||
"ManageIdentities": "Manage identities",
|
||||
"Release": "Release",
|
||||
"ReleaseSocialId": "Release social ID",
|
||||
|
||||
@@ -165,8 +165,11 @@
|
||||
"GuestSignUpDescription": "Permite a usuarios anónimos unirse a su espacio de trabajo como invitados con derechos de edición limitados",
|
||||
"GuestChannelsDescription": "Canales donde los invitados pueden escribir mensajes después de unirse",
|
||||
"GuestChannelsArrayLabel": "Seleccionar canales",
|
||||
"GuestSelectSpaces": "Seleccionar espacios",
|
||||
"GuestAutoJoinAvailableSpaces": "Unión automática a espacios",
|
||||
"GuestAutoJoinAvailableSpacesHint": "Cada tarjeta de aplicación tiene su propia fila « Unión automática a espacios »: elija dónde se añaden los invitados al activarse. Los cambios son inmediatos.",
|
||||
"GuestAnonymousVisibleSpaces": "Espacios visibles de forma anónima",
|
||||
"GuestAnonymousVisibleSpacesHint": "Cada tarjeta de aplicación tiene su propia fila: elija espacios donde se añade la cuenta anónima de solo lectura como miembro para que los visitantes sin cuenta puedan abrirlos. Los cambios son inmediatos.",
|
||||
"ManageIdentities": "Gestionar identidades",
|
||||
"Release": "Liberar",
|
||||
"ReleaseSocialId": "Liberar ID social",
|
||||
|
||||
@@ -174,8 +174,11 @@
|
||||
"GuestSignUpDescription": "Permet aux utilisateurs anonymes de rejoindre votre espace de travail en tant qu'invités avec des droits d'édition limités",
|
||||
"GuestChannelsDescription": "Canaux où les invités peuvent écrire des messages après leur adhésion",
|
||||
"GuestChannelsArrayLabel": "Sélectionner des canaux",
|
||||
"GuestSelectSpaces": "Sélectionner des espaces",
|
||||
"GuestAutoJoinAvailableSpaces": "Espaces en adhésion automatique",
|
||||
"GuestAutoJoinAvailableSpacesHint": "Chaque carte d’application a sa propre ligne « Espaces en adhésion automatique » : choisissez où les invités sont ajoutés lorsqu’ils activent leur accès. Les changements sont immédiats.",
|
||||
"GuestAnonymousVisibleSpaces": "Espaces visibles en anonyme",
|
||||
"GuestAnonymousVisibleSpacesHint": "Chaque carte d’application a sa propre ligne : choisissez les espaces où le compte anonyme en lecture seule est ajouté comme membre afin que les visiteurs sans compte puissent les ouvrir. Les changements sont immédiats.",
|
||||
"ManageIdentities": "Gérer les identités",
|
||||
"Release": "Libération",
|
||||
"ReleaseSocialId": "Libérer l'ID social",
|
||||
|
||||
@@ -174,8 +174,11 @@
|
||||
"GuestSignUpDescription": "Consente agli utenti anonimi di unirsi al tuo spazio di lavoro come ospiti con diritti di modifica limitati",
|
||||
"GuestChannelsDescription": "Canali in cui gli ospiti possono scrivere messaggi dopo essersi uniti",
|
||||
"GuestChannelsArrayLabel": "Seleziona canali",
|
||||
"GuestSelectSpaces": "Seleziona spazi",
|
||||
"GuestAutoJoinAvailableSpaces": "Ingresso automatico negli spazi",
|
||||
"GuestAutoJoinAvailableSpacesHint": "Ogni scheda applicazione ha la propria riga « Ingresso automatico negli spazi »: scegli dove vengono aggiunti gli ospiti all’attivazione. Le modifiche sono immediate.",
|
||||
"GuestAnonymousVisibleSpaces": "Spazi visibili in anonimo",
|
||||
"GuestAnonymousVisibleSpacesHint": "Ogni scheda applicazione ha la propria riga: scegli gli spazi in cui l’account anonimo in sola lettura viene aggiunto come membro, così i visitatori senza account possono aprirli. Le modifiche sono immediate.",
|
||||
"ManageIdentities": "Gestisci identità",
|
||||
"Release": "Rilascio",
|
||||
"ReleaseSocialId": "Rilascia ID social",
|
||||
|
||||
@@ -174,8 +174,11 @@
|
||||
"GuestSignUpDescription": "匿名ユーザーがゲストとしてワークスペースに参加し、制限された編集権限を得られるようにします",
|
||||
"GuestChannelsDescription": "参加後、ゲストがメッセージを書き込めるチャンネル",
|
||||
"GuestChannelsArrayLabel": "チャンネルを選択",
|
||||
"GuestSelectSpaces": "スペースを選択",
|
||||
"GuestAutoJoinAvailableSpaces": "自動参加するスペース",
|
||||
"GuestAutoJoinAvailableSpacesHint": "各アプリのカードに「自動参加するスペース」の行があります。ゲストが有効化したときに追加される場所を選びます。変更はすぐに反映されます。",
|
||||
"GuestAnonymousVisibleSpaces": "匿名ユーザーに見えるスペース",
|
||||
"GuestAnonymousVisibleSpacesHint": "各アプリのカードに専用の行があります。読み取り専用の匿名アカウントをメンバーとして追加するスペースを選ぶと、アカウントを持たない訪問者がそのスペースを開けます。変更はすぐに反映されます。",
|
||||
"ManageIdentities": "IDを管理",
|
||||
"Release": "リリース",
|
||||
"ReleaseSocialId": "ソーシャルIDをリリース",
|
||||
|
||||
@@ -165,8 +165,11 @@
|
||||
"GuestSignUpDescription": "Permite que usuários anônimos entrem em seu espaço de trabalho como convidados com direitos de edição limitados",
|
||||
"GuestChannelsDescription": "Canais onde convidados podem escrever mensagens após entrar",
|
||||
"GuestChannelsArrayLabel": "Selecionar canais",
|
||||
"GuestSelectSpaces": "Selecionar espaços",
|
||||
"GuestAutoJoinAvailableSpaces": "Adesão automática a espaços",
|
||||
"GuestAutoJoinAvailableSpacesHint": "Cada cartão de app tem sua própria linha « Adesão automática a espaços »: escolha onde os convidados são adicionados ao ativarem. As alterações são aplicadas na hora.",
|
||||
"GuestAnonymousVisibleSpaces": "Espaços visíveis de forma anônima",
|
||||
"GuestAnonymousVisibleSpacesHint": "Cada cartão de app tem sua própria linha: escolha os espaços em que a conta anônima somente leitura é adicionada como membro para que visitantes sem conta possam abri-los. As alterações são aplicadas na hora.",
|
||||
"ManageIdentities": "Gerenciar identidades",
|
||||
"Release": "Liberação",
|
||||
"ReleaseSocialId": "Liberar ID social",
|
||||
|
||||
@@ -165,8 +165,11 @@
|
||||
"GuestSignUpDescription": "Permite que usuários anônimos entrem em seu espaço de trabalho como convidados com direitos de edição limitados",
|
||||
"GuestChannelsDescription": "Canais onde convidados podem escrever mensagens após ingressar",
|
||||
"GuestChannelsArrayLabel": "Selecionar canais",
|
||||
"GuestSelectSpaces": "Selecionar espaços",
|
||||
"GuestAutoJoinAvailableSpaces": "Adesão automática a espaços",
|
||||
"GuestAutoJoinAvailableSpacesHint": "Cada cartão de aplicação tem a sua própria linha « Adesão automática a espaços »: escolha onde os convidados são adicionados ao ativarem. As alterações aplicam-se de imediato.",
|
||||
"GuestAnonymousVisibleSpaces": "Espaços visíveis em anónimo",
|
||||
"GuestAnonymousVisibleSpacesHint": "Cada cartão de aplicação tem a sua própria linha: escolha os espaços em que a conta anónima só de leitura é adicionada como membro para que visitantes sem conta os possam abrir. As alterações aplicam-se de imediato.",
|
||||
"ManageIdentities": "Gerenciar identidades",
|
||||
"Release": "Libertação",
|
||||
"ReleaseSocialId": "Liberar ID social",
|
||||
|
||||
@@ -179,8 +179,11 @@
|
||||
"GuestSignUpDescription": "Позволяет анонимным пользователям присоединяться к вашему рабочему пространству в качестве гостей с ограниченными правами редактирования",
|
||||
"GuestChannelsDescription": "Каналы, в которых гости могут писать сообщения после присоединения",
|
||||
"GuestChannelsArrayLabel": "Выбрать каналы",
|
||||
"GuestSelectSpaces": "Выбрать пространства",
|
||||
"GuestAutoJoinAvailableSpaces": "Автоприсоединение к пространствам",
|
||||
"GuestAutoJoinAvailableSpacesHint": "У каждого приложения ниже своя строка «Автоприсоединение к пространствам»: выберите, куда при активации добавлять гостей воркспейса. Изменения применяются сразу.",
|
||||
"GuestAnonymousVisibleSpaces": "Пространства, видимые анонимно",
|
||||
"GuestAnonymousVisibleSpacesHint": "У каждой карточки приложения своя строка: выберите пространства, куда добавляется анонимная учётная запись только для чтения в участники, чтобы посетители без аккаунта могли их открыть. Изменения применяются сразу.",
|
||||
"ManageIdentities": "Управление идентификаторами",
|
||||
"Release": "Освободить",
|
||||
"ReleaseSocialId": "Освободить социальный ID",
|
||||
|
||||
@@ -174,8 +174,11 @@
|
||||
"GuestSignUpDescription": "Anonim kullanıcıların çalışma alanınıza sınırlı düzenleme haklarıyla misafir olarak katılmasına izin verir",
|
||||
"GuestChannelsDescription": "Misafirlerin katıldıktan sonra mesaj yazabileceği kanallar",
|
||||
"GuestChannelsArrayLabel": "Kanalları seç",
|
||||
"GuestSelectSpaces": "Alanları seç",
|
||||
"GuestAutoJoinAvailableSpaces": "Otomatik katılım alanları",
|
||||
"GuestAutoJoinAvailableSpacesHint": "Her uygulama kartının kendi « Otomatik katılım alanları » satırı vardır: misafirler etkinleştirildiğinde nereye ekleneceğini seçin. Değişiklikler hemen uygulanır.",
|
||||
"GuestAnonymousVisibleSpaces": "Anonim için görünür alanlar",
|
||||
"GuestAnonymousVisibleSpacesHint": "Her uygulama kartının kendi satırı vardır: Hesabı olmayan ziyaretçilerin açabilmesi için salt okunur anonim hesabın üye olarak eklendiği alanları seçin. Değişiklikler hemen uygulanır.",
|
||||
"ManageIdentities": "Kimlikleri yönet",
|
||||
"Release": "Serbest bırak",
|
||||
"ReleaseSocialId": "Sosyal ID'yi serbest bırak",
|
||||
|
||||
@@ -174,8 +174,11 @@
|
||||
"GuestSignUpDescription": "允许匿名用户以访客身份加入您的工作区,获得有限的编辑权限",
|
||||
"GuestChannelsDescription": "访客加入后可以发送消息的频道",
|
||||
"GuestChannelsArrayLabel": "选择频道",
|
||||
"GuestSelectSpaces": "选择空间",
|
||||
"GuestAutoJoinAvailableSpaces": "自动加入空间",
|
||||
"GuestAutoJoinAvailableSpacesHint": "每个应用卡片都有各自的「自动加入空间」行:选择在访客激活时要添加到的位置;更改会立即生效。",
|
||||
"GuestAnonymousVisibleSpaces": "匿名访客可见的空间",
|
||||
"GuestAnonymousVisibleSpacesHint": "每个应用卡片都有各自的行:选择在哪些空间将只读匿名账号添加为成员,以便未登录访客可以打开这些空间;更改会立即生效。",
|
||||
"ManageIdentities": "管理身份",
|
||||
"Release": "释放",
|
||||
"ReleaseSocialId": "释放社交ID",
|
||||
|
||||
@@ -0,0 +1,126 @@
|
||||
<!--
|
||||
// Copyright © 2026 Hardcore Engineering Inc.
|
||||
//
|
||||
// Licensed under the Eclipse Public License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License. You may
|
||||
// obtain a copy of the License at https://www.eclipse.org/legal/epl-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
-->
|
||||
<script lang="ts">
|
||||
import { Analytics } from '@hcengineering/analytics'
|
||||
import { readOnlyGuestAccountUuid, type ModulePermissionGroup, type Space } from '@hcengineering/core'
|
||||
import { getClient } from '@hcengineering/presentation'
|
||||
import { DropdownLabels, type DropdownTextItem } from '@hcengineering/ui'
|
||||
import settingsRes from '../plugin'
|
||||
|
||||
export let group: ModulePermissionGroup
|
||||
export let disabled = false
|
||||
|
||||
const client = getClient()
|
||||
|
||||
let loading = true
|
||||
let saving = false
|
||||
let loadedGroupId: string | undefined
|
||||
let dropdownItems: DropdownTextItem[] = []
|
||||
let selectedKeys: string[] = []
|
||||
let persistedSelectedKeys: string[] = []
|
||||
let docById: Map<string, Space> = new Map<string, Space>()
|
||||
|
||||
async function loadSpaces (): Promise<void> {
|
||||
if (group.spaceClass === undefined) {
|
||||
dropdownItems = []
|
||||
selectedKeys = []
|
||||
persistedSelectedKeys = []
|
||||
docById = new Map<string, Space>()
|
||||
loading = false
|
||||
return
|
||||
}
|
||||
|
||||
loading = true
|
||||
try {
|
||||
const res = await client.findAll(group.spaceClass, { archived: false })
|
||||
docById = new Map(res.map((d) => [d._id, d as Space]))
|
||||
const docs = [...docById.values()]
|
||||
dropdownItems = docs.map((d) => ({ id: d._id, label: d.name })).sort((a, b) => a.label.localeCompare(b.label))
|
||||
selectedKeys = docs
|
||||
.filter((d) => (d.members ?? []).includes(readOnlyGuestAccountUuid))
|
||||
.map((d) => d._id)
|
||||
.sort()
|
||||
persistedSelectedKeys = [...selectedKeys]
|
||||
} catch (err) {
|
||||
Analytics.handleError(err as Error)
|
||||
dropdownItems = []
|
||||
selectedKeys = []
|
||||
persistedSelectedKeys = []
|
||||
docById = new Map<string, Space>()
|
||||
} finally {
|
||||
loading = false
|
||||
}
|
||||
}
|
||||
|
||||
async function handleSelected (e: CustomEvent<string[]>): Promise<void> {
|
||||
const nextKeys = new Set(e.detail)
|
||||
const prevKeys = new Set(persistedSelectedKeys)
|
||||
const toEnable = [...nextKeys].filter((k) => !prevKeys.has(k))
|
||||
const toDisable = [...prevKeys].filter((k) => !nextKeys.has(k))
|
||||
|
||||
if (toEnable.length === 0 && toDisable.length === 0) {
|
||||
return
|
||||
}
|
||||
|
||||
saving = true
|
||||
try {
|
||||
const ops: Array<Promise<unknown>> = []
|
||||
for (const key of toEnable) {
|
||||
const doc = docById.get(key)
|
||||
if (doc === undefined) continue
|
||||
const members = [...(doc.members ?? [])]
|
||||
if (!members.includes(readOnlyGuestAccountUuid)) {
|
||||
members.push(readOnlyGuestAccountUuid)
|
||||
ops.push(client.diffUpdate(doc, { members }))
|
||||
}
|
||||
}
|
||||
for (const key of toDisable) {
|
||||
const doc = docById.get(key)
|
||||
if (doc === undefined) continue
|
||||
const members = (doc.members ?? []).filter((m) => m !== readOnlyGuestAccountUuid)
|
||||
ops.push(client.diffUpdate(doc, { members }))
|
||||
}
|
||||
|
||||
await Promise.all(ops)
|
||||
selectedKeys = [...nextKeys].sort()
|
||||
persistedSelectedKeys = [...selectedKeys]
|
||||
} catch (err) {
|
||||
Analytics.handleError(err as Error)
|
||||
selectedKeys = [...persistedSelectedKeys]
|
||||
await loadSpaces()
|
||||
} finally {
|
||||
saving = false
|
||||
}
|
||||
}
|
||||
|
||||
$: if (group._id !== loadedGroupId) {
|
||||
loadedGroupId = group._id
|
||||
void loadSpaces()
|
||||
}
|
||||
</script>
|
||||
|
||||
<DropdownLabels
|
||||
multiselect
|
||||
autoSelect={false}
|
||||
items={dropdownItems}
|
||||
selected={[...(selectedKeys ?? [])]}
|
||||
label={settingsRes.string.GuestSelectSpaces}
|
||||
showDropdownIcon
|
||||
kind={'no-border'}
|
||||
size={'large'}
|
||||
width={'min(18rem, 100%)'}
|
||||
disabled={disabled || loading || saving || dropdownItems.length === 0}
|
||||
loading={saving}
|
||||
on:selected={handleSelected}
|
||||
/>
|
||||
@@ -132,7 +132,7 @@
|
||||
autoSelect={false}
|
||||
items={dropdownItems}
|
||||
selected={[...(selectedKeys ?? [])]}
|
||||
label={settingsRes.string.GuestAutoJoinAvailableSpaces}
|
||||
label={settingsRes.string.GuestSelectSpaces}
|
||||
showDropdownIcon
|
||||
kind={'no-border'}
|
||||
size={'large'}
|
||||
|
||||
@@ -48,6 +48,7 @@
|
||||
} from '@hcengineering/ui'
|
||||
import setting from '@hcengineering/setting'
|
||||
import { onMount } from 'svelte'
|
||||
import AnonymousGuestSpaceInput from './AnonymousGuestSpaceInput.svelte'
|
||||
import AvailableSpacesInput from './AvailableSpacesInput.svelte'
|
||||
import settingsRes from '../plugin'
|
||||
|
||||
@@ -381,6 +382,10 @@
|
||||
<div class="sectionHint">
|
||||
<Label label={settingsRes.string.GuestAutoJoinAvailableSpacesHint} />
|
||||
</div>
|
||||
{:else if guestPermissionsTab === 'anonymous'}
|
||||
<div class="sectionHint">
|
||||
<Label label={settingsRes.string.GuestAnonymousVisibleSpacesHint} />
|
||||
</div>
|
||||
{/if}
|
||||
</div>
|
||||
|
||||
@@ -393,7 +398,12 @@
|
||||
guestPermissionsTab === 'guest' &&
|
||||
group.role === AccountRole.Guest &&
|
||||
group.spaceClass !== undefined}
|
||||
{@const hasPermissionRowsBlock = permissionCount > 0 || hasGuestAutoJoinRow}
|
||||
{@const hasAnonymousGuestSpacesRow =
|
||||
guestPermissionsTab === 'anonymous' &&
|
||||
group.role === AccountRole.ReadOnlyGuest &&
|
||||
group.spaceClass !== undefined}
|
||||
{@const hasPermissionRowsBlock =
|
||||
permissionCount > 0 || hasGuestAutoJoinRow || hasAnonymousGuestSpacesRow}
|
||||
<div class="permissionModuleCard" class:permissionModuleCard-off={!moduleOn}>
|
||||
<div
|
||||
class="permissionModuleCard-header"
|
||||
@@ -452,6 +462,18 @@
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
{:else if hasAnonymousGuestSpacesRow}
|
||||
<div class="permissionRow permissionRow--guestSpaces">
|
||||
<div class="permissionRow-label">
|
||||
<Label label={settingsRes.string.GuestAnonymousVisibleSpaces} />
|
||||
</div>
|
||||
<div class="permissionRow-editorCell">
|
||||
<AnonymousGuestSpaceInput
|
||||
{group}
|
||||
disabled={!moduleOn || anonymousModulePermissionsReadOnly}
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
{/if}
|
||||
</div>
|
||||
{/if}
|
||||
|
||||
@@ -137,8 +137,11 @@ export default mergeIds(settingId, setting, {
|
||||
GuestSignUpDescription: '' as IntlString,
|
||||
GuestChannelsDescription: '' as IntlString,
|
||||
GuestChannelsArrayLabel: '' as IntlString,
|
||||
GuestSelectSpaces: '' as IntlString,
|
||||
GuestAutoJoinAvailableSpaces: '' as IntlString,
|
||||
GuestAutoJoinAvailableSpacesHint: '' as IntlString,
|
||||
GuestAnonymousVisibleSpaces: '' as IntlString,
|
||||
GuestAnonymousVisibleSpacesHint: '' as IntlString,
|
||||
ApiAccess: '' as IntlString,
|
||||
ApiToken: '' as IntlString,
|
||||
GenerateApiToken: '' as IntlString,
|
||||
|
||||
Reference in New Issue
Block a user