aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorElmar Ludwig <elmar.ludwig@uni-osnabrueck.de>2022-07-06 15:35:21 +0200
committerElmar Ludwig <elmar.ludwig@uni-osnabrueck.de>2022-07-06 15:35:21 +0200
commitd3d7342255f2ba09507b14b4e8f65e7a0f8e4173 (patch)
treecb0c6f6f41e98c0ae4acf1098dea075dd9a8232d
parent5ebdfdc4bb3e8c02c9ba98e2d30367a0c48dbac7 (diff)
draft of a simple mechanism to override the edit lock, re #887biest-887-50
This commit is a sketch of how to: - check the edit lock when starting an edit operation - allow overriding an active lock
-rwxr-xr-xlib/classes/JsonApi/Routes/Courseware/Authority.php14
-rwxr-xr-xresources/vue/components/courseware/CoursewareDefaultBlock.vue40
-rwxr-xr-xresources/vue/components/courseware/CoursewareDefaultContainer.vue40
3 files changed, 73 insertions, 21 deletions
diff --git a/lib/classes/JsonApi/Routes/Courseware/Authority.php b/lib/classes/JsonApi/Routes/Courseware/Authority.php
index 5e30a41..ea14090 100755
--- a/lib/classes/JsonApi/Routes/Courseware/Authority.php
+++ b/lib/classes/JsonApi/Routes/Courseware/Authority.php
@@ -58,10 +58,6 @@ class Authority
public static function canUpdateBlock(User $user, Block $resource)
{
- if ($resource->isBlocked()) {
- return $resource->getBlockerUserId() == $user->id;
- }
-
return self::canUpdateContainer($user, $resource->container);
}
@@ -72,7 +68,15 @@ class Authority
public static function canUpdateEditBlocker(User $user, $resource)
{
- return $resource->edit_blocker_id == '' || $resource->edit_blocker_id === $user->id;
+ if ($resource instanceof Block) {
+ return self::canUpdateBlock($user, $resource);
+ } else if ($resource instanceof Container) {
+ return self::canUpdateContainer($user, $resource);
+ } else if ($resource instanceof StructuralElement) {
+ return self::canUpdateStructuralElement($user, $resource);
+ } else {
+ return false;
+ }
}
public static function canShowContainer(User $user, Container $resource)
diff --git a/resources/vue/components/courseware/CoursewareDefaultBlock.vue b/resources/vue/components/courseware/CoursewareDefaultBlock.vue
index 6390265..ee33279 100755
--- a/resources/vue/components/courseware/CoursewareDefaultBlock.vue
+++ b/resources/vue/components/courseware/CoursewareDefaultBlock.vue
@@ -53,6 +53,15 @@
/>
</div>
<studip-dialog
+ v-if="showEditWarning"
+ :title="textEditWarningTitle"
+ :question="textEditWarningAlert"
+ height="220"
+ width="450"
+ @confirm="displayFeature('Edit', true)"
+ @close="showEditWarning = false"
+ ></studip-dialog>
+ <studip-dialog
v-if="showDeleteDialog"
:title="textDeleteTitle"
:question="textDeleteAlert"
@@ -117,8 +126,11 @@ export default {
showInfo: false,
showContent: true,
showEditModeShortcut: false,
+ showEditWarning: false,
showDeleteDialog: false,
currentComments: [],
+ textEditWarningTitle: this.$gettext('Dieser Block wird gerade bearbeitet'),
+ textEditWarningAlert: '',
textDeleteTitle: this.$gettext('Block unwiderruflich löschen'),
textDeleteAlert: this.$gettext('Möchten Sie diesen Block wirklich löschen?'),
};
@@ -153,6 +165,17 @@ export default {
blockedByAnotherUser() {
return this.blocked && this.userId !== this.blockerId;
},
+ blockingUserName() {
+ if (this.blocked) {
+ const user = this.$store.getters["users/related"]({
+ parent: { type: this.block.type, id: this.block.id },
+ relationship: "edit-blocker"
+ });
+ return user ? user.attributes['formatted-name'] : this.$gettext('unbekannt');
+ }
+
+ return null;
+ },
blockTitle() {
const type = this.block.attributes['block-type'];
@@ -181,10 +204,13 @@ export default {
loadContainer: 'loadContainer',
updateContainer: 'updateContainer',
}),
- async displayFeature(element) {
+ async displayFeature(element, override_lock = false) {
if (this.showEdit && element === 'Edit') {
return false;
}
+ if (override_lock && element === 'Edit') {
+ this.showEditWarning = false;
+ }
this.showFeatures = false;
this.showExportOptions = false;
this.showEdit = false;
@@ -193,15 +219,11 @@ export default {
if (element) {
if (element === 'Edit') {
await this.loadContainer(this.block.relationships.container.data.id);
- if (!this.blocked) {
+ if (!this.blocked || override_lock) {
try {
await this.lockObject({ id: this.block.id, type: 'courseware-blocks' });
} catch(error) {
- if (error.status === 403) {
- this.companionInfo({ info: this.$gettext('Dieser Block wird bereits bearbeitet.') });
- } else {
- console.log(error);
- }
+ console.log(error);
return false;
}
@@ -218,7 +240,9 @@ export default {
this['show' + element] = true;
this.showFeatures = true;
} else {
- this.companionInfo({ info: this.$gettext('Dieser Block wird bereits bearbeitet.') });
+ this.textEditWarningAlert = this.$gettext('Dieser Block wird bereits von %{username} bearbeitet. Möchten Sie den Block trotzdem bearbeiten?');
+ this.textEditWarningAlert = this.$gettextInterpolate(this.textEditWarningAlert, { username: this.blockingUserName });
+ this.showEditWarning = true;
}
}
} else {
diff --git a/resources/vue/components/courseware/CoursewareDefaultContainer.vue b/resources/vue/components/courseware/CoursewareDefaultContainer.vue
index a24e9a8..9acfa47 100755
--- a/resources/vue/components/courseware/CoursewareDefaultContainer.vue
+++ b/resources/vue/components/courseware/CoursewareDefaultContainer.vue
@@ -36,6 +36,15 @@
</studip-dialog>
<studip-dialog
+ v-if="showEditWarning"
+ :title="textEditWarningTitle"
+ :question="textEditWarningAlert"
+ height="220"
+ width="450"
+ @confirm="displayEditDialog(true)"
+ @close="showEditWarning = false"
+ ></studip-dialog>
+ <studip-dialog
v-if="showDeleteDialog"
:title="textDeleteTitle"
:question="textDeleteAlert"
@@ -68,7 +77,10 @@ export default {
data() {
return {
showDeleteDialog: false,
+ showEditWarning: false,
showEditDialog: false,
+ textEditWarningTitle: this.$gettext('Dieser Abschnitt wird gerade bearbeitet'),
+ textEditWarningAlert: '',
textEditConfirm: this.$gettext('Speichern'),
textEditClose: this.$gettext('Schließen'),
textEditTitle: this.$gettext('Abschnitt bearbeiten'),
@@ -98,6 +110,17 @@ export default {
blockedByAnotherUser() {
return this.blocked && this.userId !== this.blockerId;
},
+ blockingUserName() {
+ if (this.blocked) {
+ const user = this.$store.getters["users/related"]({
+ parent: { type: this.container.type, id: this.container.id },
+ relationship: "edit-blocker"
+ });
+ return user ? user.attributes['formatted-name'] : this.$gettext('unbekannt');
+ }
+
+ return null;
+ },
},
methods: {
...mapActions({
@@ -106,20 +129,21 @@ export default {
unlockObject: 'unlockObject',
companionInfo: 'companionInfo',
}),
- async displayEditDialog() {
- if (this.blockedByAnotherUser) {
- this.companionInfo({ info: this.$gettext('Dieser Abschnitt wird bereits bearbeitet.') });
+ async displayEditDialog(override_lock = false) {
+ if (override_lock) {
+ this.showEditWarning = false;
+ }
+ if (this.blockedByAnotherUser && !override_lock) {
+ this.textEditWarningAlert = this.$gettext('Dieser Abschnitt wird bereits von %{username} bearbeitet. Möchten Sie den Abschnitt trotzdem bearbeiten?');
+ this.textEditWarningAlert = this.$gettextInterpolate(this.textEditWarningAlert, { username: this.blockingUserName });
+ this.showEditWarning = true;
return false;
}
try {
await this.lockObject({ id: this.container.id, type: 'courseware-containers' });
} catch(error) {
- if (error.status === 409) {
- this.companionInfo({ info: this.$gettext('Dieser Abschnitt wird bereits bearbeitet.') });
- } else {
- console.log(error);
- }
+ console.log(error);
return false;
}