Skip to content
Snippets Groups Projects
Commit d306364d authored by uhensler's avatar uhensler
Browse files

OO-4595: Limit number of editable documents for OnlyOffice

parent c515a265
No related branches found
No related tags found
No related merge requests found
Showing
with 280 additions and 7 deletions
......@@ -47,6 +47,7 @@ public class OnlyOfficeModule extends AbstractSpringModule implements ConfigOnOf
private static final String ONLYOFFICE_ENABLED = "onlyoffice.enabled";
private static final String ONLYOFFICE_BASE_URL = "onlyoffice.baseUrl";
private static final String ONLYOFFICE_JWT_SECRET = "onlyoffice.jwt.secret";
private static final String ONLYOFFICE_LICENSE_EDIT = "onlyoffice.license.edit";
private static final String ONLYOFFICE_DATA_TRANSER_CONFIRMATION_ENABLED = "onlyoffice.data.transfer.confirmation.enabled";
private static final String ONLYOFFICE_USAGE_AUTHORS = "onlyoffice.usage.authors";
private static final String ONLYOFFICE_USAGE_COACHES = "onlyoffice.usage.coaches";
......@@ -61,6 +62,8 @@ public class OnlyOfficeModule extends AbstractSpringModule implements ConfigOnOf
private String apiUrl;
private String jwtSecret;
private Key jwtSignKey;
@Value("${onlyoffice.license.edit}")
private Integer licenseEdit;
@Value("${onlyoffice.data.transfer.confirmation.enabled:false}")
private boolean dataTransferConfirmationEnabled;
@Value("${onlyoffice.usage.restricted.authors:false}")
......@@ -107,6 +110,11 @@ public class OnlyOfficeModule extends AbstractSpringModule implements ConfigOnOf
dataTransferConfirmationEnabled = "true".equals(dataTransferConfirmationEnabledObj);
}
String licenseEditObj = getStringPropertyValue(ONLYOFFICE_LICENSE_EDIT, true);
if(StringHelper.containsNonWhitespace(licenseEditObj)) {
licenseEdit = getIntOrNull(licenseEditObj);
}
String usageRestrictedToAuthorsObj = getStringPropertyValue(ONLYOFFICE_USAGE_AUTHORS, true);
if(StringHelper.containsNonWhitespace(usageRestrictedToAuthorsObj)) {
usageRestrictedToAuthors = "true".equals(usageRestrictedToAuthorsObj);
......@@ -122,6 +130,15 @@ public class OnlyOfficeModule extends AbstractSpringModule implements ConfigOnOf
usageRestrictedToManagers = "true".equals(usageRestrictedToManagersObj);
}
}
private Integer getIntOrNull(String val) {
try {
return Integer.valueOf(val);
} catch (Exception e) {
//
}
return null;
}
@Override
public boolean isEnabled() {
......@@ -172,6 +189,15 @@ public class OnlyOfficeModule extends AbstractSpringModule implements ConfigOnOf
return jwtSignKey;
}
public Integer getLicenseEdit() {
return licenseEdit;
}
public void setLicenseEdit(Integer licenseEdit) {
this.licenseEdit = licenseEdit;
setStringProperty(ONLYOFFICE_LICENSE_EDIT, licenseEdit == null? null: licenseEdit.toString(), true);
}
public boolean isDataTransferConfirmationEnabled() {
return dataTransferConfirmationEnabled;
}
......
......@@ -23,6 +23,7 @@ import java.io.File;
import org.olat.core.commons.services.doceditor.DocEditor.Mode;
import org.olat.core.commons.services.doceditor.DocEditorSecurityCallback;
import org.olat.core.commons.services.doceditor.wopi.Access;
import org.olat.core.commons.services.vfs.VFSMetadata;
import org.olat.core.id.Identity;
import org.olat.core.util.vfs.VFSLeaf;
......@@ -41,6 +42,10 @@ public interface OnlyOfficeService {
File getFile(String fileId);
VFSLeaf getVfsLeaf(String fileId);
Access createAccess(VFSMetadata vfsMetadata, Identity identity, DocEditorSecurityCallback secCallback);
void deleteAccess(Access access);
ApiConfig getApiConfig(VFSMetadata vfsMetadata, Identity identity, DocEditorSecurityCallback secCallback);
......@@ -49,6 +54,10 @@ public interface OnlyOfficeService {
boolean canUpdateContent(VFSLeaf vfsLeaf, Identity identity, String documentKey);
boolean updateContent(VFSLeaf vfsLeaf, Identity identity, String url, boolean versionControlled);
boolean isEditLicenseAvailable();
Long getEditLicensesInUse();
boolean isLockNeeded(Mode mode);
......
......@@ -35,6 +35,7 @@ import org.olat.core.commons.services.doceditor.DocEditor.Mode;
import org.olat.core.commons.services.doceditor.DocEditorIdentityService;
import org.olat.core.commons.services.doceditor.DocEditorSecurityCallback;
import org.olat.core.commons.services.doceditor.onlyoffice.ApiConfig;
import org.olat.core.commons.services.doceditor.onlyoffice.OnlyOfficeModule;
import org.olat.core.commons.services.doceditor.onlyoffice.OnlyOfficeSecurityService;
import org.olat.core.commons.services.doceditor.onlyoffice.OnlyOfficeService;
import org.olat.core.commons.services.doceditor.onlyoffice.model.ApiConfigImpl;
......@@ -43,6 +44,8 @@ import org.olat.core.commons.services.doceditor.onlyoffice.model.EditorConfigImp
import org.olat.core.commons.services.doceditor.onlyoffice.model.InfoImpl;
import org.olat.core.commons.services.doceditor.onlyoffice.model.PermissionsImpl;
import org.olat.core.commons.services.doceditor.onlyoffice.model.UserImpl;
import org.olat.core.commons.services.doceditor.wopi.Access;
import org.olat.core.commons.services.doceditor.wopi.WopiService;
import org.olat.core.commons.services.vfs.VFSMetadata;
import org.olat.core.commons.services.vfs.VFSRepositoryService;
import org.olat.core.helpers.Settings;
......@@ -80,6 +83,8 @@ public class OnlyOfficeServiceImpl implements OnlyOfficeService {
private static ObjectMapper mapper = new ObjectMapper();
@Autowired
private OnlyOfficeModule onlyOfficeModule;
@Autowired
private OnlyOfficeSecurityService onlyOfficeSecurityService;
@Autowired
......@@ -88,6 +93,8 @@ public class OnlyOfficeServiceImpl implements OnlyOfficeService {
private VFSRepositoryService vfsRepositoryService;
@Autowired
private VFSLockManager lockManager;
@Autowired
private WopiService wopiService;
@Override
public boolean fileExists(String fileId) {
......@@ -117,6 +124,18 @@ public class OnlyOfficeServiceImpl implements OnlyOfficeService {
return null;
}
@Override
public Access createAccess(VFSMetadata vfsMetadata, Identity identity, DocEditorSecurityCallback secCallback) {
return wopiService.getOrCreateAccess(vfsMetadata, identity, secCallback, LOCK_APP_NAME, null);
}
@Override
public void deleteAccess(Access access) {
if (access == null) return;
wopiService.deleteAccess(access.getToken());
}
@Override
public ApiConfig getApiConfig(VFSMetadata vfsMetadata, Identity identity, DocEditorSecurityCallback secCallback) {
String fileName = vfsMetadata.getFilename();
......@@ -268,6 +287,21 @@ public class OnlyOfficeServiceImpl implements OnlyOfficeService {
lock.setExpiresAt(inADay);
}
}
@Override
public boolean isEditLicenseAvailable() {
Integer licenseEdit = onlyOfficeModule.getLicenseEdit();
if (licenseEdit == null) return true;
if (licenseEdit.intValue() == 0) return false;
Long accessCount = wopiService.getAccessCount(LOCK_APP_NAME, Mode.EDIT);
return accessCount < licenseEdit.byteValue();
}
@Override
public Long getEditLicensesInUse() {
return wopiService.getAccessCount(LOCK_APP_NAME, Mode.EDIT);
}
@Override
public boolean isLockNeeded(Mode mode) {
......
......@@ -20,6 +20,7 @@
package org.olat.core.commons.services.doceditor.onlyoffice.ui;
import static org.olat.core.commons.services.doceditor.onlyoffice.ui.OnlyOfficeUIFactory.validateIsMandatory;
import static org.olat.core.commons.services.doceditor.onlyoffice.ui.OnlyOfficeUIFactory.validatePositiveInteger;
import static org.olat.core.gui.components.util.KeyValues.entry;
import static org.olat.core.gui.translator.TranslatorHelper.translateAll;
......@@ -27,6 +28,7 @@ import java.util.Collection;
import org.olat.core.commons.services.doceditor.onlyoffice.OnlyOfficeModule;
import org.olat.core.commons.services.doceditor.onlyoffice.OnlyOfficeSecurityService;
import org.olat.core.commons.services.doceditor.onlyoffice.OnlyOfficeService;
import org.olat.core.commons.services.doceditor.ui.DocEditorController;
import org.olat.core.gui.UserRequest;
import org.olat.core.gui.components.form.flexible.FormItemContainer;
......@@ -37,6 +39,7 @@ import org.olat.core.gui.components.form.flexible.impl.FormLayoutContainer;
import org.olat.core.gui.components.util.KeyValues;
import org.olat.core.gui.control.Controller;
import org.olat.core.gui.control.WindowControl;
import org.olat.core.util.StringHelper;
import org.olat.core.util.Util;
import org.springframework.beans.factory.annotation.Autowired;
......@@ -57,11 +60,14 @@ public class OnlyOfficeAdminController extends FormBasicController {
private TextElement baseUrlEl;
private TextElement jwtSecretEl;
private MultipleSelectionElement dataTransferConfirmationEnabledEl;
private TextElement licenseEditEl;
private MultipleSelectionElement usageRolesEl;
@Autowired
private OnlyOfficeModule onlyOfficeModule;
@Autowired
private OnlyOfficeService onlyOfficeService;
@Autowired
private OnlyOfficeSecurityService onlyOfficeSecurityService;
public OnlyOfficeAdminController(UserRequest ureq, WindowControl wControl) {
......@@ -91,6 +97,15 @@ public class OnlyOfficeAdminController extends FormBasicController {
translateAll(getTranslator(), ENABLED_KEYS));
dataTransferConfirmationEnabledEl.select(ENABLED_KEYS[0], onlyOfficeModule.isDataTransferConfirmationEnabled());
String licenseEdit = onlyOfficeModule.getLicenseEdit() != null
? onlyOfficeModule.getLicenseEdit().toString()
: null;
licenseEditEl = uifactory.addTextElement("admin.license.edit", 10, licenseEdit, formLayout);
Long editLicensesInUse = onlyOfficeService.getEditLicensesInUse();
editLicensesInUse = editLicensesInUse != null? editLicensesInUse: 0;
uifactory.addStaticTextElement("admin.license.edit.in.use", editLicensesInUse.toString(), formLayout);
KeyValues usageRolesKV = new KeyValues();
usageRolesKV.add(entry(USAGE_AUTHOR, translate("admin.usage.roles.author")));
usageRolesKV.add(entry(USAGE_COACH, translate("admin.usage.roles.coach")));
......@@ -119,6 +134,8 @@ public class OnlyOfficeAdminController extends FormBasicController {
jwtSecretOk = false;
}
allOk &= jwtSecretOk;
allOk &= validatePositiveInteger(licenseEditEl);
}
return allOk & super.validateFormLogic(ureq);
......@@ -139,6 +156,12 @@ public class OnlyOfficeAdminController extends FormBasicController {
boolean dataTransferConfirmationEnabled = dataTransferConfirmationEnabledEl.isAtLeastSelected(1);
onlyOfficeModule.setDataTransferConfirmationEnabled(dataTransferConfirmationEnabled);
String licenseEditValue = licenseEditEl.getValue();
Integer licenseEdit = StringHelper.containsNonWhitespace(licenseEditValue)
? Integer.valueOf(licenseEditValue)
: null;
onlyOfficeModule.setLicenseEdit(licenseEdit);
Collection<String> restrictionKeys = usageRolesEl.getSelectedKeys();
onlyOfficeModule.setUsageRestrictedToAuthors(restrictionKeys.contains(USAGE_AUTHOR));
onlyOfficeModule.setUsageRestrictedToCoaches(restrictionKeys.contains(USAGE_COACH));
......
......@@ -19,12 +19,14 @@
*/
package org.olat.core.commons.services.doceditor.onlyoffice.ui;
import org.apache.logging.log4j.Logger;
import org.olat.core.commons.services.doceditor.DocEditor.Mode;
import org.olat.core.commons.services.doceditor.DocEditorSecurityCallback;
import org.olat.core.commons.services.doceditor.DocEditorSecurityCallbackBuilder;
import org.olat.core.commons.services.doceditor.onlyoffice.ApiConfig;
import org.olat.core.commons.services.doceditor.onlyoffice.OnlyOfficeModule;
import org.olat.core.commons.services.doceditor.onlyoffice.OnlyOfficeService;
import org.olat.core.commons.services.doceditor.wopi.Access;
import org.olat.core.commons.services.vfs.VFSMetadata;
import org.olat.core.gui.UserRequest;
import org.olat.core.gui.components.Component;
......@@ -32,7 +34,6 @@ import org.olat.core.gui.components.velocity.VelocityContainer;
import org.olat.core.gui.control.Event;
import org.olat.core.gui.control.WindowControl;
import org.olat.core.gui.control.controller.BasicController;
import org.apache.logging.log4j.Logger;
import org.olat.core.logging.Tracing;
import org.olat.core.util.CodeHelper;
import org.olat.core.util.vfs.VFSLeaf;
......@@ -48,6 +49,8 @@ public class OnlyOfficeEditorController extends BasicController {
private static final Logger log = Tracing.createLoggerFor(OnlyOfficeEditorController.class);
private Access access;
@Autowired
private OnlyOfficeModule onlyOfficeModule;
@Autowired
......@@ -59,6 +62,13 @@ public class OnlyOfficeEditorController extends BasicController {
DocEditorSecurityCallback secCallback = securityCallback;
if (Mode.EDIT == secCallback.getMode() && !onlyOfficeService.isEditLicenseAvailable()) {
secCallback = DocEditorSecurityCallbackBuilder.clone(secCallback)
.withMode(Mode.VIEW)
.build();
showWarning("editor.warning.no.edit.license");
}
if (onlyOfficeService.isLockNeeded(secCallback.getMode())) {
if (onlyOfficeService.isLockedForMe(vfsLeaf, getIdentity())) {
secCallback = DocEditorSecurityCallbackBuilder.clone(secCallback)
......@@ -82,6 +92,7 @@ public class OnlyOfficeEditorController extends BasicController {
if (apiConfig == null) {
mainVC.contextPut("warning", translate("editor.warning.no.api.configs"));
} else {
this.access = onlyOfficeService.createAccess(vfsMetadata, getIdentity(), secCallback);
mainVC.contextPut("id", "o_" + CodeHelper.getRAMUniqueID());
mainVC.contextPut("apiUrl", onlyOfficeModule.getApiUrl());
mainVC.contextPut("apiConfig", apiConfigJson);
......@@ -98,7 +109,7 @@ public class OnlyOfficeEditorController extends BasicController {
@Override
protected void doDispose() {
//
onlyOfficeService.deleteAccess(access);
}
}
......@@ -42,5 +42,25 @@ class OnlyOfficeUIFactory {
}
return allOk;
}
public static boolean validatePositiveInteger(TextElement el) {
boolean allOk = true;
el.clearError();
if(el.isEnabled() && el.isVisible()) {
String val = el.getValue();
if(StringHelper.containsNonWhitespace(val)) {
try {
int intVal = Integer.parseInt(val);
if (intVal < 0) {
el.setErrorKey("error.positive.integer", null);
}
} catch (NumberFormatException e) {
el.setErrorKey("error.positive.integer", null);
allOk = false;
}
}
}
return allOk;
}
}
admin.base.url=URL
admin.desc=ONLYOFFICE ist eine Software zur einzelnen oder gemeinsamen Bearbeitung von Dokumenten. Es unterst\u00FCtzt alle g\u00E4ngigen Dateiformate zur Textverarbeitung, Tabellenkalkulation und Pr\u00E4sentationen. Weitere Informationen sind auf der <a href\="http\://www.onlyoffice.com/" target\=_blank>Webseite</a> von ONLYOFFICE zu finden.
admin.license.edit=Verf\u00FCgbare Bearbeitungslizezen
admin.license.edit.in.use=Aktuelle genutzte Bearbeitungslizenzen
admin.enabled=Modul "ONLYOFFICE"
admin.jwt.secret=Secret
admin.jwt.secret.invalid=Das Secret ist nicht g\u00FCltig. Vermutlich ist es zu kurz. Siehe: JWA Specification (RFC 7518, Section 3.2).
......@@ -7,4 +9,6 @@ admin.title=ONLYOFFICE
editor.display.name=ONLYOFFICE
editor.warning.locked=Das Dokument wird bereits in einem anderen Editor bearbeitet und kann deshalb in ONLYOFFICE nicht bearbeitet werden.
editor.warning.no.api.config=Dieses Dokument kann nicht angezeigt werden!
editor.warning.no.metadata=Dieses Dokument kann nicht angezeigt werden!
\ No newline at end of file
editor.warning.no.edit.license=Es sind bereits alle Lizenzen zur Bearbeitung von Dokumenten in Verwendung. Das Dokument wird in der Lese-Ansicht ge\u00F6ffnet.
editor.warning.no.metadata=Dieses Dokument kann nicht angezeigt werden!
error.positive.integer=Geben Sie bitte eine positive Zahl ein.
\ No newline at end of file
admin.base.url=URL
admin.desc=ONLYOFFICE is a software to edit documents online. It supports all major document, spreadsheet and presentation file formats. Key features are collaborative editing and excellent office file format support. Further information is available on the <a href\="https\://www.onlyoffice.com/" target\=_blank>website</a> of ONLYOFFICE
admin.license.edit=Available edit licenses
admin.license.edit.in.use=Edit licenses in use
admin.enabled=Module "ONLYOFFICE"
admin.jwt.secret=Secret
admin.jwt.secret.invalid=The secret is not valid. Probably it is too short. See: JWA Specification (RFC 7518, Section 3.2).
admin.title=ONLYOFFICE
editor.display.name=ONLYOFFICE
editor.warning.locked=That document is already edited in another editor and therefore it is displayed in a read-only view.
editor.warning.no.api.config=It is not possible to display that document.
editor.warning.no.metadata=It is not possible to display that document.
\ No newline at end of file
editor.warning.no.api.config=It is not possible to display that document!
editor.warning.no.edit.license=All licenses for editing documents are already in use. The document is opened in read-only mode.
editor.warning.no.metadata=It is not possible to display that document.
error.positive.integer=Enter a positive number.
\ No newline at end of file
......@@ -22,6 +22,7 @@ package org.olat.core.commons.services.doceditor.wopi;
import java.util.Collection;
import java.util.Date;
import org.olat.core.commons.services.doceditor.DocEditor.Mode;
import org.olat.core.commons.services.doceditor.DocEditorSecurityCallback;
import org.olat.core.commons.services.vfs.VFSMetadata;
import org.olat.core.id.Identity;
......@@ -69,9 +70,11 @@ public interface WopiService {
String app, Date expiresAt);
Access getAccess(String accessToken);
VFSLeaf getVfsLeaf(Access access);
Long getAccessCount(String app, Mode mode);
void deleteAccess(String accessToken);
}
......@@ -26,6 +26,7 @@ import javax.annotation.PostConstruct;
import org.olat.core.commons.persistence.DB;
import org.olat.core.commons.persistence.QueryBuilder;
import org.olat.core.commons.services.doceditor.DocEditor.Mode;
import org.olat.core.commons.services.doceditor.wopi.Access;
import org.olat.core.commons.services.doceditor.wopi.model.AccessImpl;
import org.olat.core.commons.services.vfs.VFSMetadata;
......@@ -119,6 +120,23 @@ class AccessDAO {
return accesses.isEmpty() ? null : accesses.get(0);
}
Long getAccessCount(String app, Mode mode) {
QueryBuilder sb = new QueryBuilder();
sb.append("select count(*)");
sb.append(" from wopiaccess access");
sb.and().append("access.canEdit = :canEdit");
if (app != null) {
sb.and().append("access.app = :app");
}
return dbInstance.getCurrentEntityManager()
.createQuery(sb.toString(), Long.class)
.setParameter("canEdit", Mode.EDIT == mode)
.setParameter("app", app)
.getResultList()
.get(0);
}
void deleteAccess(String token) {
if (!StringHelper.containsNonWhitespace(token)) return;
......
......@@ -170,6 +170,11 @@ public class WopiServiceImpl implements WopiService {
}
return null;
}
@Override
public Long getAccessCount(String app, Mode mode) {
return accessDao.getAccessCount(app, mode);
}
@Override
public void deleteAccess(String accessToken) {
......
......@@ -1585,9 +1585,12 @@ collabora.usage.restricted.managers=false
onlyoffice.enabled=false
onlyoffice.baseUrl=https://onlyoffice.example.org/
onlyoffice.api.path=web-apps/apps/api/documents/api.js
# Number of usable edit license.
# You may leave the field blank to supress the licnese check.
onlyoffice.license.edit=
onlyoffice.data.transfer.confirmation.enabled=false
onlyoffice.usage.restricted.authors=false
onlyofficeusage.restricted.coaches=false
onlyoffice.usage.restricted.coaches=false
onlyoffice.usage.restricted.managers=false
......
/**
* <a href="http://www.openolat.org">
* OpenOLAT - Online Learning and Training</a><br>
* <p>
* Licensed under the Apache License, Version 2.0 (the "License"); <br>
* you may not use this file except in compliance with the License.<br>
* You may obtain a copy of the License at the
* <a href="http://www.apache.org/licenses/LICENSE-2.0">Apache homepage</a>
* <p>
* Unless required by applicable law or agreed to in writing,<br>
* software distributed under the License is distributed on an "AS IS" BASIS, <br>
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. <br>
* See the License for the specific language governing permissions and <br>
* limitations under the License.
* <p>
* Initial code contributed and copyrighted by<br>
* frentix GmbH, http://www.frentix.com
* <p>
*/
package org.olat.core.commons.services.doceditor.onlyoffice.manager;
import static org.assertj.core.api.Assertions.assertThat;
import static org.mockito.ArgumentMatchers.any;
import static org.mockito.Mockito.when;
import org.junit.Before;
import org.junit.Test;
import org.mockito.InjectMocks;
import org.mockito.Mock;
import org.mockito.MockitoAnnotations;
import org.olat.core.commons.services.doceditor.onlyoffice.OnlyOfficeModule;
import org.olat.core.commons.services.doceditor.wopi.WopiService;
/**
*
* Initial date: 26 Mar 2020<br>
* @author uhensler, urs.hensler@frentix.com, http://www.frentix.com
*
*/
public class OnlyOfficeServiceImplTest {
@Mock
private OnlyOfficeModule onlyOfficeModuleMock;
@Mock
private WopiService wopiServiceMock;
@InjectMocks
private OnlyOfficeServiceImpl sut ;
@Before
public void setUp() {
MockitoAnnotations.initMocks(this);
}
@Test
public void shouldAllowEditIfNoLicensesSet() {
when(onlyOfficeModuleMock.getLicenseEdit()).thenReturn(null);
boolean editLicenseAvailable = sut.isEditLicenseAvailable();
assertThat(editLicenseAvailable).isTrue();
}
@Test
public void shouldNotAllowEditIfZeroLicenses() {
when(onlyOfficeModuleMock.getLicenseEdit()).thenReturn(0);
boolean editLicenseAvailable = sut.isEditLicenseAvailable();
assertThat(editLicenseAvailable).isFalse();
}
@Test
public void shouldAllowEditIfNotAllLicensesInUse() {
when(onlyOfficeModuleMock.getLicenseEdit()).thenReturn(10);
when(wopiServiceMock.getAccessCount(any(), any())).thenReturn(Long.valueOf(4));
boolean editLicenseAvailable = sut.isEditLicenseAvailable();
assertThat(editLicenseAvailable).isTrue();
}
@Test
public void shouldNotAllowEditIfAllLicensesInUse() {
when(onlyOfficeModuleMock.getLicenseEdit()).thenReturn(10);
when(wopiServiceMock.getAccessCount(any(), any())).thenReturn(Long.valueOf(10));
boolean editLicenseAvailable = sut.isEditLicenseAvailable();
assertThat(editLicenseAvailable).isFalse();
}
}
......@@ -30,6 +30,7 @@ import org.assertj.core.api.SoftAssertions;
import org.junit.Before;
import org.junit.Test;
import org.olat.core.commons.persistence.DB;
import org.olat.core.commons.services.doceditor.DocEditor.Mode;
import org.olat.core.commons.services.doceditor.wopi.Access;
import org.olat.core.commons.services.vfs.VFSMetadata;
import org.olat.core.commons.services.vfs.manager.VFSMetadataDAO;
......@@ -136,6 +137,24 @@ public class AccessDAOTest extends OlatTestCase {
assertThat(reloadedAccess).isEqualTo(access);
}
@Test
public void shouldGetAccessCount() {
Identity identity1 = JunitTestHelper.createAndPersistIdentityAsRndUser("wopi");
Identity identity2 = JunitTestHelper.createAndPersistIdentityAsRndUser("wopi2");
Identity identity3 = JunitTestHelper.createAndPersistIdentityAsRndUser("wopi3");
VFSMetadata vfsMetadata = vfsMetadataDAO.createMetadata(random(), "relPath", "file.name", new Date(), 1000l, false, "file://" + random(), "file", null);
boolean canEdit = true;
sut.createAccess(vfsMetadata, identity1, "app1", random(), canEdit, true, true, null);
sut.createAccess(vfsMetadata, identity2, "app1", random(), canEdit, true, true, null);
sut.createAccess(vfsMetadata, identity1, "app2", random(), canEdit, true, true, null);
sut.createAccess(vfsMetadata, identity3, "app1", random(), false, true, true, null);
dbInstance.commitAndCloseSession();
Long accessCount = sut.getAccessCount("app1", Mode.EDIT);
assertThat(accessCount).isEqualTo(2);
}
@Test
public void shouldDeleteAccess() {
......
......@@ -462,6 +462,7 @@ import org.junit.runners.Suite;
*/
org.olat.core.commons.services.doceditor.office365.manager.UrlParserTest.class,
org.olat.core.commons.services.doceditor.onlyoffice.manager.OnlyOfficeSecurityServiceImplTest.class,
org.olat.core.commons.services.doceditor.onlyoffice.manager.OnlyOfficeServiceImplTest.class,
org.olat.core.commons.services.doceditor.wopi.manager.WopiServiceImplTest.class,
org.olat.core.commons.services.doceditor.wopi.manager.WopiXStreamTest.class,
org.olat.core.commons.services.commentAndRating.manager.CommentAndRatingServiceTest.class,
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment