mirror of
https://github.com/gristlabs/grist-core.git
synced 2026-03-02 04:09:24 +00:00
(core) Trim unapplicable permissions bits for column rules, both at parse time, and in UI
Summary: - UI now trims column rules before saving. - When rules are loaded, bits that aren't applicable to a resource get ignored. This should fix the incorrect behavior in existing docs without a migration. Test Plan: - Added test of UI, that it now sends trimmed rules - Added a unitteset of new trimPermissions() function - Add test of fixed interpretation of existing rules: now only permission bits applicable to a resource get respected. I.e. create/delete/schemaEdit are ignored in column rules, and schemaEdit is also ignored in table rules. - Note that DuplicateTest was affected: updated on the assumption that schemaEdit still can't actually apply at a table level. Reviewers: georgegevoian, paulfitz Reviewed By: paulfitz Differential Revision: https://phab.getgrist.com/D4205
This commit is contained in:
@@ -41,7 +41,10 @@ export type PartialPermissionSet = PermissionSet<PartialPermissionValue>;
|
||||
export type MixedPermissionSet = PermissionSet<MixedPermissionValue>;
|
||||
export type TablePermissionSet = PermissionSet<TablePermissionValue>;
|
||||
|
||||
const PERMISSION_BITS: {[letter: string]: keyof PermissionSet} = {
|
||||
// One of the strings 'read', 'update', etc.
|
||||
export type PermissionKey = keyof PermissionSet;
|
||||
|
||||
const PERMISSION_BITS: {[letter: string]: PermissionKey} = {
|
||||
R: 'read',
|
||||
C: 'create',
|
||||
U: 'update',
|
||||
@@ -60,6 +63,9 @@ const ALIASES: {[key: string]: string} = {
|
||||
};
|
||||
const REVERSE_ALIASES = fromPairs(Object.entries(ALIASES).map(([alias, value]) => [value, alias]));
|
||||
|
||||
export const AVAILABLE_BITS_TABLES: PermissionKey[] = ['read', 'update', 'create', 'delete'];
|
||||
export const AVAILABLE_BITS_COLUMNS: PermissionKey[] = ['read', 'update'];
|
||||
|
||||
// Comes in useful for initializing unset PermissionSets.
|
||||
export function emptyPermissionSet(): PartialPermissionSet {
|
||||
return {read: "", create: "", update: "", delete: "", schemaEdit: ""};
|
||||
@@ -141,6 +147,20 @@ export function mergePartialPermissions(a: PartialPermissionSet, b: PartialPermi
|
||||
return mergePermissions([a, b], ([_a, _b]) => combinePartialPermission(_a, _b));
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns permissions trimmed to include only the available bits, and empty for any other bits.
|
||||
*/
|
||||
export function trimPermissions(
|
||||
permissions: PartialPermissionSet, availableBits: PermissionKey[]
|
||||
): PartialPermissionSet {
|
||||
const trimmed = emptyPermissionSet();
|
||||
for (const bit of availableBits) {
|
||||
trimmed[bit] = permissions[bit];
|
||||
}
|
||||
return trimmed;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Merge a list of PermissionSets by combining individual bits.
|
||||
*/
|
||||
|
||||
@@ -1,4 +1,5 @@
|
||||
import {parsePermissions, permissionSetToText, splitSchemaEditPermissionSet} from 'app/common/ACLPermissions';
|
||||
import {AVAILABLE_BITS_COLUMNS, AVAILABLE_BITS_TABLES, trimPermissions} from 'app/common/ACLPermissions';
|
||||
import {ACLShareRules, TableWithOverlay} from 'app/common/ACLShareRules';
|
||||
import {AclRuleProblem} from 'app/common/ActiveDocAPI';
|
||||
import {DocData} from 'app/common/DocData';
|
||||
@@ -537,13 +538,18 @@ function readAclRules(docData: DocData, {log, compile, enrichRulesForImplementat
|
||||
if (hasShares && rule.id >= 0) {
|
||||
aclFormulaParsed = shareRules.transformNonShareRules({rule, aclFormulaParsed});
|
||||
}
|
||||
let permissions = parsePermissions(String(rule.permissionsText));
|
||||
if (tableId !== '*' && tableId !== SPECIAL_RULES_TABLE_ID) {
|
||||
const availableBits = (colIds === '*') ? AVAILABLE_BITS_TABLES : AVAILABLE_BITS_COLUMNS;
|
||||
permissions = trimPermissions(permissions, availableBits);
|
||||
}
|
||||
body.push({
|
||||
origRecord: rule,
|
||||
aclFormula: String(rule.aclFormula),
|
||||
matchFunc: rule.aclFormula ? compile?.(aclFormulaParsed) : defaultMatchFunc,
|
||||
memo: rule.memo,
|
||||
permissions: parsePermissions(String(rule.permissionsText)),
|
||||
permissionsText: String(rule.permissionsText),
|
||||
permissions,
|
||||
permissionsText: permissionSetToText(permissions)
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user