mirror of
https://github.com/haiwen/seahub.git
synced 2025-05-11 09:24:38 +00:00
Multi office suite (#7127)
* initiate * update * test * Update file.py * update * update * update * optimize fronted * optimize * update * update * update * Update test_utils.py * update * remove-useless-code * Update repo_office_suite.py * optimize ui and sql * optimize * update * add is pro version for api * Update settings.py * update * Update models.py * add-repo-owner-validation --------- Co-authored-by: 孙永强 <11704063+s-yongqiang@user.noreply.gitee.com>
This commit is contained in:
parent
1b89e8e2f1
commit
037c3f3a3d
frontend/src
components/dialog
css
models
pages/my-libs
utils
seahub
tests/seahub/role_permissions
112
frontend/src/components/dialog/repo-office-suite-dialog.js
Normal file
112
frontend/src/components/dialog/repo-office-suite-dialog.js
Normal file
@ -0,0 +1,112 @@
|
||||
import React from 'react';
|
||||
import PropTypes from 'prop-types';
|
||||
import { Button, Modal, ModalHeader, ModalBody, ModalFooter, TabContent, TabPane } from 'reactstrap';
|
||||
import makeAnimated from 'react-select/animated';
|
||||
import { userAPI } from '../../utils/user-api';
|
||||
import { gettext, isPro } from '../../utils/constants';
|
||||
import { Utils } from '../../utils/utils';
|
||||
import toaster from '../toast';
|
||||
import { SeahubSelect } from '../common/select';
|
||||
import '../../css/repo-office-suite-dialog.css';
|
||||
|
||||
const propTypes = {
|
||||
itemName: PropTypes.string.isRequired,
|
||||
toggleDialog: PropTypes.func.isRequired,
|
||||
submit: PropTypes.func.isRequired,
|
||||
repoID: PropTypes.string.isRequired,
|
||||
|
||||
};
|
||||
|
||||
class OfficeSuiteDialog extends React.Component {
|
||||
constructor(props) {
|
||||
super(props);
|
||||
this.state = {
|
||||
selectedOption: null,
|
||||
errorMsg: []
|
||||
};
|
||||
this.options = [];
|
||||
}
|
||||
|
||||
handleSelectChange = (option) => {
|
||||
this.setState({ selectedOption: option });
|
||||
};
|
||||
|
||||
submit = () => {
|
||||
let suite_id = this.state.selectedOption.value;
|
||||
this.props.submit(suite_id);
|
||||
};
|
||||
|
||||
componentDidMount() {
|
||||
if (isPro) {
|
||||
userAPI.getOfficeSuite(this.props.repoID).then((res) => {
|
||||
this.updateOptions(res);
|
||||
}).catch(error => {
|
||||
let errMessage = Utils.getErrorMsg(error);
|
||||
toaster.danger(errMessage);
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
updateOptions = (officeSuites) => {
|
||||
officeSuites.data.suites_info.forEach(item => {
|
||||
let option = {
|
||||
value: item.id,
|
||||
label: item.name,
|
||||
is_selected: item.is_selected,
|
||||
};
|
||||
this.options.push(option);
|
||||
});
|
||||
let selectedOption = this.options.find(op => op.is_selected);
|
||||
this.setState({ selectedOption });
|
||||
};
|
||||
|
||||
|
||||
renderOfficeSuiteContent = () => {
|
||||
return (
|
||||
<React.Fragment>
|
||||
<div className="repo-office-suite-dialog-main">
|
||||
<TabContent>
|
||||
{isPro &&
|
||||
<TabPane role="tabpanel" id="office-suite-panel">
|
||||
<SeahubSelect
|
||||
isClearable
|
||||
maxMenuHeight={200}
|
||||
hideSelectedOptions={true}
|
||||
components={makeAnimated()}
|
||||
placeholder={gettext('Select a office suite')}
|
||||
options={this.options}
|
||||
onChange={this.handleSelectChange}
|
||||
value={this.state.selectedOption}
|
||||
className="repo-select-office-suite"
|
||||
/>
|
||||
</TabPane>}
|
||||
</TabContent>
|
||||
</div>
|
||||
</React.Fragment>
|
||||
);
|
||||
};
|
||||
|
||||
render() {
|
||||
const { itemName: repoName } = this.props;
|
||||
let title = gettext('{library_name} Office Suite');
|
||||
title = title.replace('{library_name}', '<span class="op-target text-truncate mx-1">' + Utils.HTMLescape(repoName) + '</span>');
|
||||
return (
|
||||
<Modal isOpen={true} toggle={this.props.toggleDialog} className="repo-office-suite-dialog">
|
||||
<ModalHeader toggle={this.props.toggleDialog}>
|
||||
<span dangerouslySetInnerHTML={{ __html: title }} className="d-flex mw-100"></span>
|
||||
</ModalHeader>
|
||||
<ModalBody className="repo-office-suite-dialog-content" role="tablist">
|
||||
{this.renderOfficeSuiteContent()}
|
||||
</ModalBody>
|
||||
<ModalFooter>
|
||||
<Button color="secondary" onClick={this.props.toggleDialog}>{gettext('Cancel')}</Button>
|
||||
<Button color="primary" onClick={this.submit}>{gettext('Submit')}</Button>
|
||||
</ModalFooter>
|
||||
</Modal>
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
OfficeSuiteDialog.propTypes = propTypes;
|
||||
|
||||
export default OfficeSuiteDialog;
|
30
frontend/src/css/repo-office-suite-dialog.css
Normal file
30
frontend/src/css/repo-office-suite-dialog.css
Normal file
@ -0,0 +1,30 @@
|
||||
.repo-office-suite-dialog .repo-office-suite-dialog-content {
|
||||
padding: 0;
|
||||
min-height: 5.5rem;
|
||||
min-width: 10rem;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
@media (min-width: 268px) {
|
||||
.repo-office-suite-dialog .repo-office-suite-dialog-content {
|
||||
flex-direction: column;
|
||||
}
|
||||
}
|
||||
|
||||
.repo-office-suite-dialog-content .repo-office-suite-dialog-main {
|
||||
display: flex;
|
||||
flex-basis: 48%;
|
||||
padding: 1rem;
|
||||
}
|
||||
|
||||
.repo-office-suite-dialog-content .repo-office-suite-dialog-main .tab-content {
|
||||
flex: 1;
|
||||
}
|
||||
|
||||
|
||||
.repo-office-suite-dialog-content .repo-office-suite-dialog-main .repo-select-office-suite {
|
||||
padding: 8px 0;
|
||||
}
|
||||
|
||||
|
@ -23,6 +23,7 @@ class RepoInfo {
|
||||
this.lib_need_decrypt = object.lib_need_decrypt;
|
||||
this.last_modified = object.last_modified;
|
||||
this.status = object.status;
|
||||
this.enable_onlyoffice = object.enable_onlyoffice;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -20,6 +20,7 @@ import Rename from '../../components/rename';
|
||||
import MylibRepoMenu from './mylib-repo-menu';
|
||||
import RepoAPITokenDialog from '../../components/dialog/repo-api-token-dialog';
|
||||
import RepoShareAdminDialog from '../../components/dialog/repo-share-admin-dialog';
|
||||
import OfficeSuiteDialog from '../../components/dialog/repo-office-suite-dialog';
|
||||
import RepoMonitoredIcon from '../../components/repo-monitored-icon';
|
||||
import { LIST_MODE } from '../../components/dir-view-mode/constants';
|
||||
import { userAPI } from '../../utils/user-api';
|
||||
@ -57,6 +58,7 @@ class MylibRepoListItem extends React.Component {
|
||||
isAPITokenDialogShow: false,
|
||||
isRepoShareAdminDialogOpen: false,
|
||||
isRepoDeleted: false,
|
||||
isOfficeSuiteDialogShow: false,
|
||||
};
|
||||
}
|
||||
|
||||
@ -128,6 +130,9 @@ class MylibRepoListItem extends React.Component {
|
||||
case 'Share Admin':
|
||||
this.toggleRepoShareAdminDialog();
|
||||
break;
|
||||
case 'Office Suite':
|
||||
this.onOfficeSuiteToggle();
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
@ -221,6 +226,10 @@ class MylibRepoListItem extends React.Component {
|
||||
this.setState({ isAPITokenDialogShow: !this.state.isAPITokenDialogShow });
|
||||
};
|
||||
|
||||
onOfficeSuiteToggle = () => {
|
||||
this.setState({ isOfficeSuiteDialogShow: !this.state.isOfficeSuiteDialogShow });
|
||||
};
|
||||
|
||||
toggleRepoShareAdminDialog = () => {
|
||||
this.setState({ isRepoShareAdminDialogOpen: !this.state.isRepoShareAdminDialogOpen });
|
||||
};
|
||||
@ -266,6 +275,21 @@ class MylibRepoListItem extends React.Component {
|
||||
this.onTransferToggle();
|
||||
};
|
||||
|
||||
onOfficeSuiteChange = (suiteID) => {
|
||||
let repoID = this.props.repo.repo_id;
|
||||
userAPI.setOfficeSuite(repoID, suiteID).then(res => {
|
||||
let message = gettext('Successfully change office suite.');
|
||||
toaster.success(message);
|
||||
}).catch(error => {
|
||||
if (error.response) {
|
||||
toaster.danger(error.response.data.error_msg || gettext('Error'), { duration: 3 });
|
||||
} else {
|
||||
toaster.danger(gettext('Failed. Please check the network.'), { duration: 3 });
|
||||
}
|
||||
});
|
||||
this.onOfficeSuiteToggle();
|
||||
};
|
||||
|
||||
onDeleteRepo = (repo) => {
|
||||
seafileAPI.deleteRepo(repo.repo_id).then((res) => {
|
||||
|
||||
@ -548,6 +572,17 @@ class MylibRepoListItem extends React.Component {
|
||||
</ModalPortal>
|
||||
)}
|
||||
|
||||
{this.state.isOfficeSuiteDialogShow && (
|
||||
<ModalPortal>
|
||||
<OfficeSuiteDialog
|
||||
repoID={repo.repo_id}
|
||||
itemName={repo.repo_name}
|
||||
submit={this.onOfficeSuiteChange}
|
||||
toggleDialog={this.onOfficeSuiteToggle}
|
||||
/>
|
||||
</ModalPortal>
|
||||
)}
|
||||
|
||||
</Fragment>
|
||||
);
|
||||
}
|
||||
|
@ -1,7 +1,7 @@
|
||||
import React from 'react';
|
||||
import PropTypes from 'prop-types';
|
||||
import { Dropdown, DropdownMenu, DropdownToggle, DropdownItem } from 'reactstrap';
|
||||
import { gettext, isPro, folderPermEnabled, enableRepoSnapshotLabel, enableResetEncryptedRepoPassword, isEmailConfigured } from '../../utils/constants';
|
||||
import { gettext, isPro, folderPermEnabled, enableRepoSnapshotLabel, enableResetEncryptedRepoPassword, isEmailConfigured, enableMultipleOfficeSuite } from '../../utils/constants';
|
||||
import { Utils } from '../../utils/utils';
|
||||
|
||||
const propTypes = {
|
||||
@ -120,6 +120,9 @@ class MylibRepoMenu extends React.Component {
|
||||
if (this.props.isPC && enableRepoSnapshotLabel) {
|
||||
operations.push('Label Current State');
|
||||
}
|
||||
if (enableMultipleOfficeSuite && isPro) {
|
||||
operations.push('Office Suite');
|
||||
}
|
||||
return operations;
|
||||
};
|
||||
|
||||
@ -174,6 +177,9 @@ class MylibRepoMenu extends React.Component {
|
||||
case 'SeaTable integration':
|
||||
translateResult = gettext('SeaTable integration');
|
||||
break;
|
||||
case 'Office Suite':
|
||||
translateResult = gettext('Office Suite');
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
@ -90,6 +90,7 @@ export const ocmRemoteServers = window.app.pageOptions.ocmRemoteServers;
|
||||
export const enableOCMViaWebdav = window.app.pageOptions.enableOCMViaWebdav;
|
||||
export const enableSSOToThirdpartWebsite = window.app.pageOptions.enableSSOToThirdpartWebsite;
|
||||
export const enableSeadoc = window.app.pageOptions.enableSeadoc;
|
||||
export const enableMultipleOfficeSuite = window.app.pageOptions.enableMultipleOfficeSuite;
|
||||
|
||||
export const curNoteMsg = window.app.pageOptions.curNoteMsg;
|
||||
export const curNoteID = window.app.pageOptions.curNoteID;
|
||||
|
@ -63,6 +63,18 @@ class UserAPI {
|
||||
form.append('reshare', reshare);
|
||||
return this.req.put(url, form);
|
||||
}
|
||||
|
||||
getOfficeSuite(repoID) {
|
||||
const url = this.server + '/api/v2.1/repos/' + repoID + '/office-suite/';
|
||||
return this.req.get(url);
|
||||
}
|
||||
|
||||
setOfficeSuite(repoID, suiteID) {
|
||||
const url = this.server + '/api/v2.1/repos/' + repoID + '/office-suite/';
|
||||
const form = new FormData();
|
||||
form.append('suite_id', suiteID);
|
||||
return this.req.put(url, form);
|
||||
}
|
||||
}
|
||||
|
||||
let userAPI = new UserAPI();
|
||||
|
@ -1,4 +1,4 @@
|
||||
import { mediaUrl, gettext, serviceURL, siteRoot, isPro, fileAuditEnabled, canGenerateShareLink, canGenerateUploadLink, shareLinkPasswordMinLength, username, folderPermEnabled, onlyofficeConverterExtensions, enableOnlyoffice, enableSeadoc, enableFileTags, enableRepoSnapshotLabel,
|
||||
import { mediaUrl, gettext, serviceURL, siteRoot, isPro, fileAuditEnabled, canGenerateShareLink, canGenerateUploadLink, shareLinkPasswordMinLength, username, folderPermEnabled, onlyofficeConverterExtensions, enableSeadoc, enableFileTags, enableRepoSnapshotLabel,
|
||||
enableResetEncryptedRepoPassword, isEmailConfigured, isSystemStaff } from './constants';
|
||||
import TextTranslation from './text-translation';
|
||||
import React from 'react';
|
||||
@ -664,7 +664,7 @@ export const Utils = {
|
||||
list.push(HISTORY);
|
||||
}
|
||||
|
||||
if (permission == 'rw' && enableOnlyoffice &&
|
||||
if (permission == 'rw' && currentRepoInfo.enable_onlyoffice &&
|
||||
onlyofficeConverterExtensions.includes(Utils.getFileExtension(dirent.name, false))) {
|
||||
list.push(ONLYOFFICE_CONVERT);
|
||||
}
|
||||
|
88
seahub/api2/endpoints/repo_office_suite.py
Normal file
88
seahub/api2/endpoints/repo_office_suite.py
Normal file
@ -0,0 +1,88 @@
|
||||
import json
|
||||
|
||||
from rest_framework.authentication import SessionAuthentication
|
||||
from rest_framework.permissions import IsAuthenticated
|
||||
from rest_framework.response import Response
|
||||
from rest_framework.views import APIView
|
||||
from rest_framework import status
|
||||
|
||||
from seaserv import seafile_api
|
||||
|
||||
from seahub.api2.throttling import UserRateThrottle
|
||||
from seahub.api2.authentication import TokenAuthentication
|
||||
from seahub.api2.utils import api_error
|
||||
from seahub.api2.permissions import IsProVersion
|
||||
|
||||
from seahub.onlyoffice.models import RepoExtraConfig, REPO_OFFICE_CONFIG
|
||||
from seahub.settings import OFFICE_SUITE_LIST
|
||||
from seahub.utils.repo import get_repo_owner
|
||||
|
||||
class OfficeSuiteConfig(APIView):
|
||||
|
||||
authentication_classes = (TokenAuthentication, SessionAuthentication)
|
||||
permission_classes = (IsAuthenticated, IsProVersion)
|
||||
throttle_classes = (UserRateThrottle,)
|
||||
|
||||
def get(self, request, repo_id):
|
||||
if not request.user.permissions.can_choose_office_suite():
|
||||
error_msg = 'Permission denied.'
|
||||
return api_error(status.HTTP_403_FORBIDDEN, error_msg)
|
||||
|
||||
repo = seafile_api.get_repo(repo_id)
|
||||
if not repo:
|
||||
error_msg = 'Library %s not found.' % repo_id
|
||||
return api_error(status.HTTP_404_NOT_FOUND, error_msg)
|
||||
|
||||
repo_owner = get_repo_owner(request, repo_id)
|
||||
if '@seafile_group' in repo_owner:
|
||||
error_msg = 'Department repo can not use this feature.'
|
||||
return api_error(status.HTTP_400_BAD_REQUEST, error_msg)
|
||||
|
||||
current_suite = RepoExtraConfig.objects.filter(repo_id=repo_id, config_type=REPO_OFFICE_CONFIG).first()
|
||||
suites_info = []
|
||||
for office_suite in OFFICE_SUITE_LIST:
|
||||
suite_info = {}
|
||||
suite_info['id'] = office_suite.get('id')
|
||||
suite_info['name'] = office_suite.get('name')
|
||||
suite_info['is_default'] = office_suite.get('is_default')
|
||||
if current_suite:
|
||||
config_details = json.loads(current_suite.config_details)
|
||||
office_config = config_details.get('office_suite')
|
||||
suite_info['is_selected'] = (True if office_config and office_config.get('suite_id') == office_suite.get('id') else False)
|
||||
else:
|
||||
suite_info['is_selected'] = office_suite.get('is_default')
|
||||
suites_info.append(suite_info)
|
||||
|
||||
return Response({'suites_info': suites_info})
|
||||
|
||||
def put(self, request, repo_id):
|
||||
# arguments check
|
||||
suite_id = request.data.get('suite_id', '')
|
||||
if suite_id not in ['collabora', 'onlyoffice']:
|
||||
error_msg = 'suite_id invalid.'
|
||||
return api_error(status.HTTP_400_BAD_REQUEST, error_msg)
|
||||
|
||||
if not request.user.permissions.can_choose_office_suite():
|
||||
error_msg = 'Permission denied.'
|
||||
return api_error(status.HTTP_403_FORBIDDEN, error_msg)
|
||||
|
||||
# resource check
|
||||
repo = seafile_api.get_repo(repo_id)
|
||||
if not repo:
|
||||
error_msg = 'Library %s not found.' % repo_id
|
||||
return api_error(status.HTTP_404_NOT_FOUND, error_msg)
|
||||
|
||||
repo_owner = get_repo_owner(request, repo_id)
|
||||
if '@seafile_group' in repo_owner:
|
||||
error_msg = 'Department repo can not use this feature.'
|
||||
return api_error(status.HTTP_400_BAD_REQUEST, error_msg)
|
||||
|
||||
config_details = {
|
||||
'office_suite': {
|
||||
'suite_id': suite_id
|
||||
}
|
||||
}
|
||||
RepoExtraConfig.objects.update_or_create(repo_id=repo_id, config_type=REPO_OFFICE_CONFIG,
|
||||
defaults= {'config_details':json.dumps(config_details)} )
|
||||
|
||||
return Response({"success": True}, status=status.HTTP_200_OK)
|
@ -36,6 +36,7 @@ from seahub.avatar.templatetags.avatar_tags import api_avatar_url
|
||||
from seahub.settings import ENABLE_STORAGE_CLASSES
|
||||
|
||||
from seaserv import seafile_api
|
||||
from seahub.views.file import get_office_feature_by_repo
|
||||
|
||||
logger = logging.getLogger(__name__)
|
||||
|
||||
@ -125,6 +126,8 @@ class ReposView(APIView):
|
||||
continue
|
||||
url, _, _ = api_avatar_url(email)
|
||||
|
||||
enable_onlyoffice, _ = get_office_feature_by_repo(r)
|
||||
|
||||
repo_info = {
|
||||
"type": "mine",
|
||||
"repo_id": r.id,
|
||||
@ -144,6 +147,7 @@ class ReposView(APIView):
|
||||
"monitored": r.repo_id in monitored_repo_id_list,
|
||||
"status": normalize_repo_status_code(r.status),
|
||||
"salt": r.salt if r.enc_version >= 3 else '',
|
||||
"enable_onlyoffice": enable_onlyoffice
|
||||
}
|
||||
|
||||
if is_pro_version() and ENABLE_STORAGE_CLASSES:
|
||||
@ -199,6 +203,8 @@ class ReposView(APIView):
|
||||
owner_contact_email = '' if is_group_owned_repo else contact_email_dict.get(owner_email, '')
|
||||
url, _, _ = api_avatar_url(owner_email)
|
||||
|
||||
enable_onlyoffice, _ = get_office_feature_by_repo(r)
|
||||
|
||||
repo_info = {
|
||||
"type": "shared",
|
||||
"repo_id": r.repo_id,
|
||||
@ -218,6 +224,7 @@ class ReposView(APIView):
|
||||
"monitored": r.repo_id in monitored_repo_id_list,
|
||||
"status": normalize_repo_status_code(r.status),
|
||||
"salt": r.salt if r.enc_version >= 3 else '',
|
||||
"enable_onlyoffice": enable_onlyoffice
|
||||
}
|
||||
|
||||
if r.repo_id in repos_with_admin_share_to:
|
||||
@ -259,7 +266,7 @@ class ReposView(APIView):
|
||||
if is_wiki_repo(r):
|
||||
continue
|
||||
|
||||
|
||||
enable_onlyoffice, _ = get_office_feature_by_repo(r)
|
||||
repo_info = {
|
||||
"type": "group",
|
||||
"group_id": r.group_id,
|
||||
@ -277,6 +284,7 @@ class ReposView(APIView):
|
||||
"monitored": r.repo_id in monitored_repo_id_list,
|
||||
"status": normalize_repo_status_code(r.status),
|
||||
"salt": r.salt if r.enc_version >= 3 else '',
|
||||
"enable_onlyoffice": enable_onlyoffice
|
||||
}
|
||||
repo_info_list.append(repo_info)
|
||||
|
||||
@ -310,6 +318,7 @@ class ReposView(APIView):
|
||||
|
||||
repo_owner = repo_id_owner_dict[r.repo_id]
|
||||
url, _, _ = api_avatar_url(repo_owner)
|
||||
enable_onlyoffice, _ = get_office_feature_by_repo(r)
|
||||
repo_info = {
|
||||
"type": "public",
|
||||
"repo_id": r.repo_id,
|
||||
@ -328,6 +337,7 @@ class ReposView(APIView):
|
||||
"starred": r.repo_id in starred_repo_id_list,
|
||||
"status": normalize_repo_status_code(r.status),
|
||||
"salt": r.salt if r.enc_version >= 3 else '',
|
||||
"enable_onlyoffice": enable_onlyoffice
|
||||
}
|
||||
repo_info_list.append(repo_info)
|
||||
|
||||
@ -369,6 +379,7 @@ class RepoView(APIView):
|
||||
return api_error(status.HTTP_403_FORBIDDEN, error_msg)
|
||||
|
||||
username = request.user.username
|
||||
enable_onlyoffice, _ = get_office_feature_by_repo(repo)
|
||||
|
||||
lib_need_decrypt = False
|
||||
if repo.encrypted \
|
||||
@ -405,6 +416,7 @@ class RepoView(APIView):
|
||||
"lib_need_decrypt": lib_need_decrypt,
|
||||
"last_modified": timestamp_to_isoformat_timestr(repo.last_modify),
|
||||
"status": normalize_repo_status_code(repo.status),
|
||||
"enable_onlyoffice": enable_onlyoffice
|
||||
}
|
||||
|
||||
return Response(result)
|
||||
|
@ -110,6 +110,7 @@ from seahub.settings import THUMBNAIL_EXTENSION, THUMBNAIL_ROOT, \
|
||||
from seahub.subscription.utils import subscription_check
|
||||
from seahub.organizations.models import OrgAdminSettings, DISABLE_ORG_ENCRYPTED_LIBRARY
|
||||
from seahub.seadoc.utils import get_seadoc_file_uuid, gen_seadoc_image_parent_path, get_seadoc_asset_upload_link
|
||||
from seahub.views.file import get_office_feature_by_repo
|
||||
|
||||
try:
|
||||
from seahub.settings import CLOUD_MODE
|
||||
@ -124,11 +125,6 @@ try:
|
||||
except ImportError:
|
||||
ORG_MEMBER_QUOTA_DEFAULT = None
|
||||
|
||||
try:
|
||||
from seahub.settings import ENABLE_OFFICE_WEB_APP
|
||||
except ImportError:
|
||||
ENABLE_OFFICE_WEB_APP = False
|
||||
|
||||
try:
|
||||
from seahub.settings import ORG_MEMBER_QUOTA_ENABLED
|
||||
except ImportError:
|
||||
@ -2828,6 +2824,8 @@ class OwaFileView(APIView):
|
||||
error_msg = 'Library %s not found.' % repo_id
|
||||
return api_error(status.HTTP_404_NOT_FOUND, error_msg)
|
||||
|
||||
_, ENABLE_OFFICE_WEB_APP = get_office_feature_by_repo(repo)
|
||||
|
||||
action = request.GET.get('action', 'view')
|
||||
if action not in ('view', 'edit'):
|
||||
error_msg = 'action invalid.'
|
||||
|
@ -450,6 +450,11 @@ class UserPermissions(object):
|
||||
if not settings.ENABLE_WIKI:
|
||||
return False
|
||||
return self._get_perm_by_roles('can_publish_wiki')
|
||||
|
||||
def can_choose_office_suite(self):
|
||||
if not settings.ENABLE_MULTIPLE_OFFICE_SUITE:
|
||||
return False
|
||||
return self._get_perm_by_roles('can_choose_office_suite')
|
||||
|
||||
|
||||
class AdminPermissions(object):
|
||||
|
@ -14,3 +14,15 @@ class OnlyOfficeDocKey(models.Model):
|
||||
file_path = models.TextField()
|
||||
repo_id_file_path_md5 = models.CharField(max_length=100, db_index=True, unique=True)
|
||||
created_time = models.DateTimeField(default=datetime.datetime.now)
|
||||
|
||||
|
||||
REPO_OFFICE_CONFIG = 'office'
|
||||
class RepoExtraConfig(models.Model):
|
||||
|
||||
repo_id = models.CharField(max_length=36, db_index=True)
|
||||
config_type = models.CharField(max_length=50)
|
||||
config_details = models.TextField()
|
||||
|
||||
class Meta:
|
||||
db_table = 'repo_extra_config'
|
||||
unique_together = ('repo_id', 'config_type')
|
||||
|
@ -1,5 +1,6 @@
|
||||
# Copyright (c) 2012-2016 Seafile Ltd.
|
||||
from django.conf import settings
|
||||
from seahub.settings import ENABLE_MULTIPLE_OFFICE_SUITE, OFFICE_SUITE_LIST, OFFICE_SUITE_ENABLED_FILE_TYPES, OFFICE_SUITE_ENABLED_EDIT_FILE_TYPES
|
||||
|
||||
ENABLE_ONLYOFFICE = getattr(settings, 'ENABLE_ONLYOFFICE', False)
|
||||
ONLYOFFICE_APIJS_URL = getattr(settings, 'ONLYOFFICE_APIJS_URL', '')
|
||||
@ -44,3 +45,23 @@ EXT_DOCUMENT = [
|
||||
".html", ".htm", ".mht", ".xml",
|
||||
".pdf", ".djvu", ".fb2", ".epub", ".xps"
|
||||
]
|
||||
|
||||
|
||||
if ENABLE_MULTIPLE_OFFICE_SUITE:
|
||||
OFFICE_SUITE_ONLY_OFFICE = 'onlyoffice'
|
||||
office_info = {}
|
||||
for s in OFFICE_SUITE_LIST:
|
||||
if s.get('id') == OFFICE_SUITE_ONLY_OFFICE:
|
||||
office_info = s
|
||||
break
|
||||
ONLYOFFICE_APIJS_URL = office_info.get('ONLYOFFICE_APIJS_URL')
|
||||
ONLYOFFICE_CONVERTER_URL = ONLYOFFICE_APIJS_URL and ONLYOFFICE_APIJS_URL.replace("/web-apps/apps/api/documents/api.js", "/ConvertService.ashx")
|
||||
ONLYOFFICE_FORCE_SAVE = office_info.get('ONLYOFFICE_FORCE_SAVE', False)
|
||||
ONLYOFFICE_JWT_SECRET = office_info.get('ONLYOFFICE_JWT_SECRET', '')
|
||||
ONLYOFFICE_JWT_HEADER = office_info.get('ONLYOFFICE_JWT_HEADER', 'Authorization')
|
||||
ONLYOFFICE_DESKTOP_EDITOR_HTTP_USER_AGENT = office_info.get('ONLYOFFICE_DESKTOP_EDITOR_HTTP_USER_AGENT', 'AscDesktopEditor')
|
||||
VERIFY_ONLYOFFICE_CERTIFICATE = office_info.get('VERIFY_ONLYOFFICE_CERTIFICATE', True)
|
||||
ONLYOFFICE_FILE_EXTENSION = OFFICE_SUITE_ENABLED_FILE_TYPES
|
||||
ONLYOFFICE_EDIT_FILE_EXTENSION = OFFICE_SUITE_ENABLED_EDIT_FILE_TYPES
|
||||
|
||||
|
@ -25,7 +25,7 @@ from django.views.decorators.csrf import csrf_exempt
|
||||
|
||||
from seaserv import seafile_api
|
||||
|
||||
from seahub.onlyoffice.models import OnlyOfficeDocKey
|
||||
|
||||
from seahub.onlyoffice.settings import VERIFY_ONLYOFFICE_CERTIFICATE, ONLYOFFICE_JWT_SECRET
|
||||
from seahub.onlyoffice.utils import get_onlyoffice_dict, get_doc_key_by_repo_id_file_path
|
||||
from seahub.onlyoffice.utils import delete_doc_key, get_file_info_by_doc_key
|
||||
@ -40,6 +40,7 @@ from seahub.views import check_folder_permission
|
||||
from seahub.utils.file_types import SPREADSHEET
|
||||
|
||||
|
||||
|
||||
# Get an instance of a logger
|
||||
logger = logging.getLogger('onlyoffice')
|
||||
|
||||
@ -506,4 +507,3 @@ class OnlyofficeGetReferenceData(APIView):
|
||||
}
|
||||
result['token'] = jwt.encode(result, ONLYOFFICE_JWT_SECRET)
|
||||
return Response({'data': result})
|
||||
|
||||
|
@ -48,7 +48,8 @@ DEFAULT_ENABLED_ROLE_PERMISSIONS = {
|
||||
'upload_rate_limit': 0,
|
||||
'download_rate_limit': 0,
|
||||
'monthly_rate_limit': '',
|
||||
'monthly_rate_limit_per_user': ''
|
||||
'monthly_rate_limit_per_user': '',
|
||||
'can_choose_office_suite': True,
|
||||
},
|
||||
GUEST_USER: {
|
||||
'can_add_repo': False,
|
||||
@ -73,7 +74,8 @@ DEFAULT_ENABLED_ROLE_PERMISSIONS = {
|
||||
'upload_rate_limit': 0,
|
||||
'download_rate_limit': 0,
|
||||
'monthly_rate_limit': '',
|
||||
'monthly_rate_limit_per_user': ''
|
||||
'monthly_rate_limit_per_user': '',
|
||||
'can_choose_office_suite': False,
|
||||
},
|
||||
}
|
||||
|
||||
|
@ -973,6 +973,26 @@ ENABLE_METADATA_MANAGEMENT = False
|
||||
METADATA_SERVER_URL = ''
|
||||
METADATA_SERVER_SECRET_KEY = ''
|
||||
|
||||
#############################
|
||||
# multi office suite support
|
||||
#############################
|
||||
ENABLE_MULTIPLE_OFFICE_SUITE = False
|
||||
OFFICE_SUITE_LIST = [
|
||||
{
|
||||
"id": "onlyoffice",
|
||||
"name": "OnlyOffice",
|
||||
"is_default": True,
|
||||
},
|
||||
{
|
||||
"id": "collabora",
|
||||
"name": "CollaboraOnline",
|
||||
"is_default": False,
|
||||
}
|
||||
]
|
||||
ROLES_DEFAULT_OFFCICE_SUITE = {}
|
||||
OFFICE_SUITE_ENABLED_FILE_TYPES = []
|
||||
OFFICE_SUITE_ENABLED_EDIT_FILE_TYPES = []
|
||||
|
||||
# file tags
|
||||
ENABLE_FILE_TAGS = True
|
||||
|
||||
|
@ -158,6 +158,7 @@
|
||||
enableMetadataManagement: {% if enable_metadata_management %} true {% else %} false {% endif %},
|
||||
enableFileTags: {% if enable_file_tags %} true {% else %} false {% endif %},
|
||||
enableShowAbout: {% if enable_show_about %} true {% else %} false {% endif %},
|
||||
enableMultipleOfficeSuite: {% if user.permissions.can_choose_office_suite %} true {% else %} false {% endif %},
|
||||
showWechatSupportGroup: {% if show_wechat_support_group %} true {% else %} false {% endif %},
|
||||
baiduMapKey: '{{ baidu_map_key }}',
|
||||
googleMapKey: '{{ google_map_key }}',
|
||||
|
@ -212,6 +212,7 @@ from seahub.api2.endpoints.wiki2 import Wikis2View, Wiki2View, Wiki2ConfigView,
|
||||
from seahub.api2.endpoints.subscription import SubscriptionView, SubscriptionPlansView, SubscriptionLogsView
|
||||
from seahub.api2.endpoints.user_list import UserListView
|
||||
from seahub.api2.endpoints.seahub_io import SeahubIOStatus
|
||||
from seahub.api2.endpoints.repo_office_suite import OfficeSuiteConfig
|
||||
|
||||
|
||||
urlpatterns = [
|
||||
@ -463,6 +464,7 @@ urlpatterns = [
|
||||
re_path(r'^api/v2.1/repos/(?P<repo_id>[-0-9a-f]{36})/upload-links/(?P<token>[a-f0-9]+)/$', RepoUploadLink.as_view(), name='api-v2.1-repo-upload-link'),
|
||||
re_path(r'^api/v2.1/repos/(?P<repo_id>[-0-9a-f]{36})/share-info/$', RepoShareInfoView.as_view(), name='api-v2.1-repo-share-info-view'),
|
||||
re_path(r'^api/v2.1/repos/(?P<repo_id>[-0-9a-f]{36})/image-rotate/$', RepoImageRotateView.as_view(), name='api-v2.1-repo-image-rotate-view'),
|
||||
re_path(r'^api/v2.1/repos/(?P<repo_id>[-0-9a-f]{36})/office-suite/$', OfficeSuiteConfig.as_view(), name='api-v2.1-repo-office-suite'),
|
||||
|
||||
## user:: repo-api-tokens
|
||||
re_path(r'^api/v2.1/repos/(?P<repo_id>[-0-9a-f]{36})/repo-api-tokens/$', RepoAPITokensView.as_view(), name='api-v2.1-repo-api-tokens'),
|
||||
@ -1006,7 +1008,7 @@ if getattr(settings, 'ENABLE_MULTI_ADFS', False) or getattr(settings, 'ENABLE_AD
|
||||
path('saml2/complete/', auth_complete, name='saml2_complete'),
|
||||
]
|
||||
|
||||
if getattr(settings, 'ENABLE_ONLYOFFICE', False):
|
||||
if getattr(settings, 'ENABLE_ONLYOFFICE', False) or getattr(settings, 'ENABLE_MULTIPLE_OFFICE_SUITE', False):
|
||||
urlpatterns += [
|
||||
path('onlyoffice/', include('seahub.onlyoffice.urls')),
|
||||
path('onlyoffice-api/', include('seahub.onlyoffice.api_urls')),
|
||||
|
@ -1150,7 +1150,6 @@ def react_fake_view(request, **kwargs):
|
||||
'enable_metadata_management': ENABLE_METADATA_MANAGEMENT,
|
||||
'enable_file_tags': settings.ENABLE_FILE_TAGS,
|
||||
'enable_show_about': settings.ENABLE_SHOW_ABOUT
|
||||
|
||||
}
|
||||
|
||||
if ENABLE_METADATA_MANAGEMENT:
|
||||
|
@ -34,17 +34,18 @@ from django.template.defaultfilters import filesizeformat
|
||||
from seaserv import seafile_api, ccnet_api
|
||||
from seaserv import get_repo, get_commits, \
|
||||
get_file_id_by_path, get_commit, get_file_size, \
|
||||
seafserv_threaded_rpc
|
||||
seafserv_threaded_rpc, get_org_id_by_repo_id
|
||||
|
||||
from seahub.settings import SITE_ROOT
|
||||
from seahub.share.utils import check_share_link_user_access
|
||||
from seahub.tags.models import FileUUIDMap
|
||||
from seahub.wopi.utils import get_wopi_dict
|
||||
from seahub.onlyoffice.utils import get_onlyoffice_dict
|
||||
from seahub.onlyoffice.models import RepoExtraConfig, REPO_OFFICE_CONFIG
|
||||
from seahub.auth.decorators import login_required
|
||||
from seahub.auth import SESSION_MOBILE_LOGIN_KEY
|
||||
from seahub.base.decorators import repo_passwd_set_required
|
||||
from seahub.base.accounts import ANONYMOUS_EMAIL
|
||||
from seahub.base.accounts import ANONYMOUS_EMAIL, User
|
||||
from seahub.base.templatetags.seahub_tags import file_icon_filter
|
||||
from seahub.share.models import FileShare, check_share_link_common
|
||||
from seahub.share.decorators import share_link_audit, share_link_login_required
|
||||
@ -66,6 +67,7 @@ from seahub.utils.http import json_response, \
|
||||
BadRequestException
|
||||
from seahub.utils.file_op import check_file_lock, \
|
||||
ONLINE_OFFICE_LOCK_OWNER, if_locked_by_online_office
|
||||
from seahub.utils.user_permissions import get_user_role
|
||||
from seahub.views import check_folder_permission, \
|
||||
get_unencry_rw_repos_by_user
|
||||
from seahub.utils.repo import is_repo_owner, parse_repo_perm, is_repo_admin
|
||||
@ -87,33 +89,34 @@ from seahub.settings import FILE_ENCODING_LIST, FILE_PREVIEW_MAX_SIZE, \
|
||||
SHARE_LINK_EXPIRE_DAYS_MIN, SHARE_LINK_EXPIRE_DAYS_MAX, SHARE_LINK_PASSWORD_MIN_LENGTH, \
|
||||
SHARE_LINK_FORCE_USE_PASSWORD, SHARE_LINK_PASSWORD_STRENGTH_LEVEL, \
|
||||
SHARE_LINK_EXPIRE_DAYS_DEFAULT, ENABLE_SHARE_LINK_REPORT_ABUSE, SEADOC_SERVER_URL, \
|
||||
ENABLE_METADATA_MANAGEMENT, BAIDU_MAP_KEY, GOOGLE_MAP_KEY, GOOGLE_MAP_ID
|
||||
ENABLE_METADATA_MANAGEMENT, BAIDU_MAP_KEY, GOOGLE_MAP_KEY, GOOGLE_MAP_ID, ENABLE_MULTIPLE_OFFICE_SUITE, \
|
||||
OFFICE_SUITE_LIST
|
||||
|
||||
|
||||
# wopi
|
||||
try:
|
||||
from seahub.settings import ENABLE_OFFICE_WEB_APP
|
||||
from seahub.wopi.settings import ENABLE_OFFICE_WEB_APP
|
||||
except ImportError:
|
||||
ENABLE_OFFICE_WEB_APP = False
|
||||
|
||||
try:
|
||||
from seahub.settings import ENABLE_OFFICE_WEB_APP_EDIT
|
||||
from seahub.wopi.settings import ENABLE_OFFICE_WEB_APP_EDIT
|
||||
except ImportError:
|
||||
ENABLE_OFFICE_WEB_APP_EDIT = False
|
||||
|
||||
try:
|
||||
from seahub.settings import OFFICE_WEB_APP_FILE_EXTENSION
|
||||
from seahub.wopi.settings import OFFICE_WEB_APP_FILE_EXTENSION
|
||||
except ImportError:
|
||||
OFFICE_WEB_APP_FILE_EXTENSION = ()
|
||||
|
||||
try:
|
||||
from seahub.settings import OFFICE_WEB_APP_EDIT_FILE_EXTENSION
|
||||
from seahub.wopi.settings import OFFICE_WEB_APP_EDIT_FILE_EXTENSION
|
||||
except ImportError:
|
||||
OFFICE_WEB_APP_EDIT_FILE_EXTENSION = ()
|
||||
|
||||
# onlyoffice
|
||||
try:
|
||||
from seahub.settings import ENABLE_ONLYOFFICE
|
||||
from seahub.onlyoffice.settings import ENABLE_ONLYOFFICE
|
||||
except ImportError:
|
||||
ENABLE_ONLYOFFICE = False
|
||||
|
||||
@ -130,6 +133,7 @@ except ImportError:
|
||||
from seahub.thirdparty_editor.settings import ENABLE_THIRDPARTY_EDITOR
|
||||
from seahub.thirdparty_editor.settings import THIRDPARTY_EDITOR_ACTION_URL_DICT
|
||||
from seahub.thirdparty_editor.settings import THIRDPARTY_EDITOR_ACCESS_TOKEN_EXPIRATION
|
||||
from seahub.settings import ROLES_DEFAULT_OFFCICE_SUITE
|
||||
|
||||
# Get an instance of a logger
|
||||
logger = logging.getLogger(__name__)
|
||||
@ -140,6 +144,57 @@ FILE_TYPE_FOR_NEW_FILE_LINK = [
|
||||
MARKDOWN
|
||||
]
|
||||
|
||||
def _check_feature(repo_id):
|
||||
office_suite = RepoExtraConfig.objects.filter(repo_id=repo_id, config_type=REPO_OFFICE_CONFIG).first()
|
||||
if office_suite:
|
||||
repo_config_details = json.loads(office_suite.config_details)
|
||||
office_config = repo_config_details.get('office_suite')
|
||||
return office_config.get('suite_id') if office_config else None
|
||||
return None
|
||||
|
||||
def get_office_feature_by_repo(repo):
|
||||
enable_onlyoffice, enable_office_app = False, False
|
||||
if not ENABLE_MULTIPLE_OFFICE_SUITE:
|
||||
return ENABLE_ONLYOFFICE, ENABLE_OFFICE_WEB_APP
|
||||
|
||||
if not OFFICE_SUITE_LIST:
|
||||
return ENABLE_ONLYOFFICE, ENABLE_OFFICE_WEB_APP
|
||||
|
||||
org_id = get_org_id_by_repo_id(repo.repo_id)
|
||||
if org_id > 0:
|
||||
repo_owner = seafile_api.get_org_repo_owner(repo.repo_id)
|
||||
else:
|
||||
repo_owner = seafile_api.get_repo_owner(repo.repo_id)
|
||||
if '@seafile_group' in repo_owner:
|
||||
repo_feature = None
|
||||
else:
|
||||
repo_feature = _check_feature(repo.repo_id)
|
||||
|
||||
if not repo_feature and '@seafile_group' not in repo_owner:
|
||||
user = User.objects.get(email=repo_owner)
|
||||
role = get_user_role(user)
|
||||
repo_feature = ROLES_DEFAULT_OFFCICE_SUITE.get(role)
|
||||
|
||||
if not repo_feature:
|
||||
default_suite = {}
|
||||
for s in OFFICE_SUITE_LIST:
|
||||
if s.get('is_default'):
|
||||
default_suite = s
|
||||
break
|
||||
if default_suite.get('id') == 'onlyoffice':
|
||||
enable_onlyoffice = True
|
||||
if default_suite.get('id') == 'collabora':
|
||||
enable_office_app = True
|
||||
else:
|
||||
if repo_feature == 'onlyoffice':
|
||||
enable_onlyoffice = True
|
||||
if repo_feature == 'collabora':
|
||||
enable_office_app = True
|
||||
|
||||
return enable_onlyoffice, enable_office_app
|
||||
|
||||
|
||||
|
||||
def gen_path_link(path, repo_name):
|
||||
"""
|
||||
Generate navigate paths and links in repo page.
|
||||
@ -333,6 +388,8 @@ def can_preview_file(file_name, file_size, repo):
|
||||
|
||||
filetype, fileext = get_file_type_and_ext(file_name)
|
||||
|
||||
ENABLE_ONLYOFFICE, ENABLE_OFFICE_WEB_APP = get_office_feature_by_repo(repo)
|
||||
|
||||
# Seafile defines 10 kinds of filetype:
|
||||
# TEXT, MARKDOWN, IMAGE, DOCUMENT, SPREADSHEET, VIDEO, AUDIO, PDF, SVG
|
||||
if filetype in (TEXT, MARKDOWN, IMAGE) or fileext in get_conf_text_ext():
|
||||
@ -387,7 +444,7 @@ def can_edit_file(file_name, file_size, repo):
|
||||
"""Check whether Seafile supports edit file.
|
||||
Returns (True, None) if Yes, otherwise (False, error_msg).
|
||||
"""
|
||||
|
||||
ENABLE_ONLYOFFICE, ENABLE_OFFICE_WEB_APP = get_office_feature_by_repo(repo)
|
||||
can_preview, err_msg = can_preview_file(file_name, file_size, repo)
|
||||
if not can_preview:
|
||||
return False, err_msg
|
||||
@ -474,7 +531,7 @@ def convert_repo_path_when_can_not_view_file(request, repo_id, path):
|
||||
@login_required
|
||||
@repo_passwd_set_required
|
||||
def view_lib_file(request, repo_id, path):
|
||||
|
||||
|
||||
# resource check
|
||||
repo = seafile_api.get_repo(repo_id)
|
||||
if not repo:
|
||||
@ -484,6 +541,8 @@ def view_lib_file(request, repo_id, path):
|
||||
file_id = seafile_api.get_file_id_by_path(repo_id, path)
|
||||
if not file_id:
|
||||
return render_error(request, _('File does not exist'))
|
||||
|
||||
ENABLE_ONLYOFFICE, ENABLE_OFFICE_WEB_APP = get_office_feature_by_repo(repo)
|
||||
|
||||
# permission check
|
||||
username = request.user.username
|
||||
@ -926,6 +985,8 @@ def view_history_file_common(request, repo_id, ret_dict):
|
||||
path = request.GET.get('p', '/')
|
||||
path = normalize_file_path(path)
|
||||
|
||||
ENABLE_ONLYOFFICE, ENABLE_OFFICE_WEB_APP = get_office_feature_by_repo(repo)
|
||||
|
||||
commit_id = request.GET.get('commit_id', '')
|
||||
if not commit_id:
|
||||
raise Http404
|
||||
@ -1176,6 +1237,8 @@ def view_shared_file(request, fileshare):
|
||||
obj_id = seafile_api.get_file_id_by_path(repo_id, path)
|
||||
if not obj_id:
|
||||
return render_error(request, _('File does not exist'))
|
||||
|
||||
ENABLE_ONLYOFFICE, ENABLE_OFFICE_WEB_APP = get_office_feature_by_repo(repo)
|
||||
|
||||
# permission check
|
||||
shared_by = fileshare.username
|
||||
@ -1430,6 +1493,8 @@ def view_file_via_shared_dir(request, fileshare):
|
||||
if not repo:
|
||||
raise Http404
|
||||
|
||||
ENABLE_ONLYOFFICE, ENABLE_OFFICE_WEB_APP = get_office_feature_by_repo(repo)
|
||||
|
||||
# recourse check
|
||||
# Get file path from frontend, and construct request file path
|
||||
# with fileshare.path to real path, used to fetch file content by RPC.
|
||||
@ -1671,6 +1736,7 @@ def view_raw_file(request, repo_id, file_path):
|
||||
repo = get_repo(repo_id)
|
||||
if not repo:
|
||||
raise Http404
|
||||
|
||||
|
||||
file_path = file_path.rstrip('/')
|
||||
if file_path[0] != '/':
|
||||
@ -1734,7 +1800,7 @@ def download_file(request, repo_id, obj_id):
|
||||
repo = get_repo(repo_id)
|
||||
if not repo:
|
||||
raise Http404
|
||||
|
||||
|
||||
if repo.encrypted and not seafile_api.is_password_set(repo_id, username):
|
||||
reverse_url = reverse('lib_view', args=[repo_id, repo.name, ''])
|
||||
return HttpResponseRedirect(reverse_url)
|
||||
@ -1922,6 +1988,7 @@ def office_convert_get_page(request, repo_id, commit_id, path, filename):
|
||||
"""
|
||||
if not HAS_OFFICE_CONVERTER:
|
||||
raise Http404
|
||||
|
||||
|
||||
if not _OFFICE_PAGE_PATTERN.match(filename):
|
||||
return HttpResponseForbidden()
|
||||
|
@ -1,6 +1,5 @@
|
||||
# Copyright (c) 2012-2016 Seafile Ltd.
|
||||
import seahub.settings as settings
|
||||
|
||||
# OfficeOnlineServer, OnlyOffice, CollaboraOffice
|
||||
OFFICE_SERVER_TYPE = getattr(settings, 'OFFICE_SERVER_TYPE', '')
|
||||
|
||||
@ -26,6 +25,26 @@ OFFICE_WEB_APP_CLIENT_PEM = getattr(settings, 'OFFICE_WEB_APP_CLIENT_PEM', '')
|
||||
|
||||
|
||||
## Server certificates ##
|
||||
|
||||
# Path to a CA_BUNDLE file or directory with certificates of trusted CAs
|
||||
OFFICE_WEB_APP_SERVER_CA = getattr(settings, 'OFFICE_WEB_APP_SERVER_CA', True)
|
||||
|
||||
if settings.ENABLE_MULTIPLE_OFFICE_SUITE:
|
||||
OFFICE_SUITE_COLLA = 'collabora'
|
||||
office_info = {}
|
||||
for s in settings.OFFICE_SUITE_LIST:
|
||||
if s.get('id') == OFFICE_SUITE_COLLA:
|
||||
office_info = s
|
||||
break
|
||||
OFFICE_SERVER_TYPE = office_info.get('OFFICE_SERVER_TYPE', 'collaboraoffice')
|
||||
OFFICE_WEB_APP_BASE_URL = office_info.get('OFFICE_WEB_APP_BASE_URL', '')
|
||||
WOPI_ACCESS_TOKEN_EXPIRATION = office_info.get('WOPI_ACCESS_TOKEN_EXPIRATION', 12 * 60 * 60)
|
||||
OFFICE_WEB_APP_DISCOVERY_EXPIRATION = office_info.get('OFFICE_WEB_APP_DISCOVERY_EXPIRATION', 7 * 24 * 60 * 60)
|
||||
OFFICE_WEB_APP_CLIENT_CERT = office_info.get('OFFICE_WEB_APP_CLIENT_CERT', '')
|
||||
OFFICE_WEB_APP_CLIENT_KEY = office_info.get('OFFICE_WEB_APP_CLIENT_KEY', '')
|
||||
OFFICE_WEB_APP_CLIENT_PEM = office_info.get('OFFICE_WEB_APP_CLIENT_PEM', '')
|
||||
OFFICE_WEB_APP_SERVER_CA = office_info.get('OFFICE_WEB_APP_SERVER_CA', '')
|
||||
ENABLE_OFFICE_WEB_APP_EDIT = office_info.get('ENABLE_OFFICE_WEB_APP_EDIT', False)
|
||||
OFFICE_WEB_APP_FILE_EXTENSION = settings.OFFICE_SUITE_ENABLED_FILE_TYPES
|
||||
OFFICE_WEB_APP_EDIT_FILE_EXTENSION = settings.OFFICE_SUITE_ENABLED_EDIT_FILE_TYPES
|
||||
|
||||
|
||||
|
@ -11,4 +11,4 @@ class UtilsTest(BaseTestCase):
|
||||
assert DEFAULT_USER in get_available_roles()
|
||||
|
||||
def test_get_enabled_role_permissions_by_role(self):
|
||||
assert len(list(get_enabled_role_permissions_by_role(DEFAULT_USER).keys())) == 23
|
||||
assert len(list(get_enabled_role_permissions_by_role(DEFAULT_USER).keys())) == 24
|
||||
|
Loading…
Reference in New Issue
Block a user