def get_related_users_by_repo(repo_id, org_id=None): """ Return all users who can view this library. 1. repo owner 2. users repo has been shared to 3. members of groups repo has been shared to """ users = [] if org_id: repo_owner = seafile_api.get_org_repo_owner(repo_id) user_shared_to = seafile_api.list_org_repo_shared_to(org_id, repo_owner, repo_id) else: repo_owner = seafile_api.get_repo_owner(repo_id) user_shared_to = seafile_api.list_repo_shared_to( repo_owner, repo_id) # 1. repo owner users.append(repo_owner) # 2. users repo has been shared to for user in user_shared_to: users.append(user.user) # 3. members of groups repo has been shared to groups = get_shared_groups_by_repo(repo_id, org_id) for group in groups: members = ccnet_api.get_group_members(group.id) for member in members: if member.user_name not in users: users.append(member.user_name) return users
def format_repo_share_msg(self, notice): d = json.loads(notice.detail) repo_id = d['repo_id'] repo = seafile_api.get_repo(repo_id) path = d['path'] org_id = d.get('org_id', None) if path == '/': shared_type = 'library' else: shared_type = 'folder' if org_id: owner = seafile_api.get_org_repo_owner(repo_id) repo = seafile_api.get_org_virtual_repo( org_id, repo_id, path, owner) else: owner = seafile_api.get_repo_owner(repo_id) repo = seafile_api.get_virtual_repo(repo_id, path, owner) repo_url = reverse('lib_view', args=[repo_id, repo.name, '']) notice.repo_url = repo_url notice.notice_from = escape(email2nickname(d['share_from'])) notice.repo_name = repo.name notice.avatar_src = self.get_avatar_src(d['share_from']) notice.shared_type = shared_type return notice
def is_repo_admin(username, repo_id): repo_owner = seafile_api.get_repo_owner(repo_id) try: if '@seafile_group' in repo_owner: # is group owned repo group_id = int(repo_owner.split('@')[0]) if is_group_admin(group_id, username): return True else: user_share_permission = ExtraSharePermission.objects.\ get_user_permission(repo_id, username) if user_share_permission == PERMISSION_ADMIN: return True # get all groups that repo is shared to with admin permission group_ids = ExtraGroupsSharePermission.objects.get_admin_groups_by_repo(repo_id) for group_id in group_ids: if is_group_admin(group_id, username): return True return False except Exception as e: logger.error(e) return False
def repo_history_view(request, repo_id): """View repo in history. """ repo = get_repo(repo_id) if not repo: raise Http404 username = request.user.username path = get_path_from_request(request) user_perm = check_folder_permission(request, repo.id, '/') if user_perm is None: return render_error(request, _(u'Permission denied')) try: server_crypto = UserOptions.objects.is_server_crypto(username) except CryptoOptionNotSetError: # Assume server_crypto is ``False`` if this option is not set. server_crypto = False if repo.encrypted and \ (repo.enc_version == 1 or (repo.enc_version == 2 and server_crypto)) \ and not is_password_set(repo.id, username): return render_to_response( 'decrypt_repo_form.html', { 'repo': repo, 'next': get_next_url_from_request(request) or reverse('repo', args=[repo.id]), 'force_server_crypto': FORCE_SERVER_CRYPTO, }, context_instance=RequestContext(request)) commit_id = request.GET.get('commit_id', None) if commit_id is None: return HttpResponseRedirect(reverse('repo', args=[repo.id])) current_commit = get_commit(repo.id, repo.version, commit_id) if not current_commit: current_commit = get_commit(repo.id, repo.version, repo.head_cmmt_id) file_list, dir_list, dirent_more = get_repo_dirents( request, repo, current_commit, path) zipped = get_nav_path(path, repo.name) repo_owner = seafile_api.get_repo_owner(repo.id) is_repo_owner = True if username == repo_owner else False return render_to_response( 'repo_history_view.html', { 'repo': repo, "is_repo_owner": is_repo_owner, 'user_perm': user_perm, 'current_commit': current_commit, 'dir_list': dir_list, 'file_list': file_list, 'path': path, 'zipped': zipped, }, context_instance=RequestContext(request))
def get_group_repos(username, org_id, groups): """Get repos shared to groups. """ group_repos = [] if org_id: # For each group I joined... for grp in groups: # Get group repos, and for each group repos... for r_id in seafile_api.get_org_group_repoids(org_id, grp.id): # No need to list my own repo repo_owner = seafile_api.get_org_repo_owner(r_id) if repo_owner == username: continue group_repos.append(r_id) else: # For each group I joined... for grp in groups: # Get group repos, and for each group repos... for r_id in seafile_api.get_group_repoids(grp.id): # No need to list my own repo repo_owner = seafile_api.get_repo_owner(r_id) if repo_owner == username: continue group_repos.append(r_id) return group_repos
def repo_online_gc(request, repo_id): if request.method != 'POST': raise Http404 repo = get_repo(repo_id) if not repo: raise Http404 referer = request.META.get('HTTP_REFERER', None) next = settings.SITE_ROOT if referer is None else referer username = request.user.username if is_org_context(request): repo_owner = seafile_api.get_org_repo_owner(repo.id) else: repo_owner = seafile_api.get_repo_owner(repo.id) is_repo_owner = True if repo_owner == username else False if not is_repo_owner: messages.error(request, _('Permission denied')) return HttpResponseRedirect(next) day = int(request.POST.get('day')) try: seafile_api.clean_up_repo_history(repo.id, day) except SearpcError as e: logger.error(e) messages.error(request, _('Internal server error')) return HttpResponseRedirect(next) return HttpResponseRedirect(next)
def check_repo_owner_quota(self, isnewfile=True, contentlength=-1): """Check if the upload would cause the user quota be exceeded `contentlength` is only positive when the client does not use "transfer-encode: chunking" Return True if the quota would not be exceeded, otherwise return False. """ if contentlength <= 0: # When client use "transfer-encode: chunking", the content length # is not included in the request headers if isnewfile: return check_repo_quota(self.repo.id) >= 0 else: return True if not self.owner: self.owner = seafile_api.get_repo_owner(self.repo.id) quota = seafile_api.get_user_quota(self.owner) if quota == INFINITE_QUOTA: return True self_usage = seafile_api.get_user_self_usage(self.owner) share_usage = seafile_api.get_user_share_usage(self.owner) if CALC_SHARE_USAGE else 0 remain = quota - self_usage - share_usage if not isnewfile: remain -= self.obj.size return contentlength <= remain
def repo_restored_cb(sender, **kwargs): repo_id = kwargs['repo_id'] operator = kwargs['operator'] repo = seafile_api.get_repo(repo_id) org_id = get_org_id_by_repo_id(repo_id) if org_id > 0: related_users = seafile_api.org_get_shared_users_by_repo(org_id, repo_id) repo_owner = seafile_api.get_org_repo_owner(repo_id) else: related_users = seafile_api.get_shared_users_by_repo(repo_id) repo_owner = seafile_api.get_repo_owner(repo_id) related_users.append(repo_owner) record = { 'op_type':'recover', 'obj_type':'repo', 'timestamp': datetime.datetime.utcnow(), 'repo_id': repo_id, 'repo_name': repo.repo_name, 'path': '/', 'op_user': operator, 'related_users': [related_users], 'org_id': org_id, } from utils import SeafEventsSession session = SeafEventsSession() seafevents.save_user_activity(session, record) session.close()
def sys_repo_admin(request): # Make sure page request is an int. If not, deliver first page. try: current_page = int(request.GET.get('page', '1')) per_page = int(request.GET.get('per_page', '25')) except ValueError: current_page = 1 per_page = 25 repos_all = seafile_api.get_repo_list(per_page * (current_page -1), per_page + 1) repos = repos_all[:per_page] if len(repos_all) == per_page + 1: page_next = True else: page_next = False for repo in repos: try: repo.owner = seafile_api.get_repo_owner(repo.id) except: repo.owner = "failed to get" return render_to_response( 'sysadmin/sys_repo_admin.html', { 'repos': repos, 'current_page': current_page, 'prev_page': current_page-1, 'next_page': current_page+1, 'per_page': per_page, 'page_next': page_next, }, context_instance=RequestContext(request))
def get_repo_info(repo): repo_owner = seafile_api.get_repo_owner(repo.repo_id) if not repo_owner: try: org_repo_owner = seafile_api.get_org_repo_owner(repo.repo_id) except Exception: org_repo_owner = None owner = repo_owner or org_repo_owner or '' result = {} result['id'] = repo.repo_id result['name'] = repo.repo_name result['owner'] = owner result['owner_email'] = owner result['owner_name'] = email2nickname(owner) result['owner_contact_email'] = email2contact_email(owner) result['size'] = repo.size result['size_formatted'] = filesizeformat(repo.size) result['encrypted'] = repo.encrypted result['file_count'] = repo.file_count if '@seafile_group' in owner: group_id = get_group_id_by_repo_owner(owner) result['group_name'] = group_id_to_name(group_id) return result
def get(self, request, format=None): username = request.user.username shared_repos = [] shared_repos += seafile_api.get_share_in_repo_list(username, -1, -1) joined_groups = get_personal_groups_by_user(username) for grp in joined_groups: # Get group repos, and for each group repos... for r_id in get_group_repoids(grp.id): # No need to list my own repo if seafile_api.is_repo_owner(username, r_id): continue # Convert repo properties due to the different collumns in Repo # and SharedRepo r = get_repo(r_id) if not r: continue r.repo_id = r.id r.repo_name = r.name r.repo_desc = r.desc cmmts = get_commits(r_id, 0, 1) last_commit = cmmts[0] if cmmts else None r.last_modified = last_commit.ctime if last_commit else 0 r.share_type = 'group' r.user = seafile_api.get_repo_owner(r_id) r.user_perm = check_permission(r_id, username) shared_repos.append(r) if not CLOUD_MODE: shared_repos += list_inner_pub_repos(username) return HttpResponse(json.dumps(shared_repos, cls=SearpcObjEncoder), status=200, content_type=json_content_type)
def email_repo_owner(self, repo_file): repo_id, file_path = repo_file.split(':', 1) owner = seafile_api.get_repo_owner(repo_id) if not owner: return # save current language cur_language = translation.get_language() # get and active user language user_language = self.get_user_language(owner) translation.activate(user_language) contact_email = Profile.objects.get_contact_email_by_user(owner) send_html_email_with_dj_template( contact_email, dj_template='notifications/notify_virus.html', context={'owner': owner, 'file_url': reverse('view_lib_file', args=[repo_id, file_path]), 'file_name': os.path.basename(file_path), }, subject=_('Virus detected on %s') % get_site_name(), priority=MAIL_PRIORITY.now ) # restore current language translation.activate(cur_language)
def format_repo_share_to_group_msg(self): """ Arguments: - `self`: """ try: d = json.loads(self.detail) except Exception as e: logger.error(e) return _(u"Internal error") share_from = email2nickname(d['share_from']) repo_id = d['repo_id'] group_id = d['group_id'] path = d.get('path', '/') org_id = d.get('org_id', None) repo = None try: group = ccnet_api.get_group(group_id) if path == '/': repo = seafile_api.get_repo(repo_id) else: if org_id: owner = seafile_api.get_org_repo_owner(repo_id) repo = seafile_api.get_org_virtual_repo( org_id, repo_id, path, owner) else: owner = seafile_api.get_repo_owner(repo_id) repo = seafile_api.get_virtual_repo(repo_id, path, owner) except Exception as e: logger.error(e) return None if not repo or not group: self.delete() return None if path == '/': tmpl = 'notifications/notice_msg/repo_share_to_group_msg.html' else: tmpl = 'notifications/notice_msg/folder_share_to_group_msg.html' lib_url = reverse('lib_view', args=[repo.id, repo.name, '']) group_url = reverse('group', args=[group.id]) msg = render_to_string(tmpl, { 'user': share_from, 'lib_url': lib_url, 'lib_name': repo.name, 'group_url': group_url, 'group_name': group.group_name, }) return msg
def get_repo_owner(request, repo_id): if is_org_context(request): repo_owner = seafile_api.get_org_repo_owner(repo_id) else: # for admin panel # administrator may get org repo's owner repo_owner = seafile_api.get_repo_owner(repo_id) if not repo_owner: repo_owner = seafile_api.get_org_repo_owner(repo_id) return repo_owner
def unsetinnerpub(request, repo_id): """Unshare repos in organization or in share admin page. Only system admin, organization admin or repo owner can perform this op. """ repo = get_repo(repo_id) perm = request.GET.get('permission', None) if perm is None: return render_error(request, _(u'Argument is not valid')) if not repo: messages.error(request, _('Failed to unshare the library, as it does not exist.')) return HttpResponseRedirect(reverse('share_admin')) # permission check username = request.user.username if is_org_context(request): org_id = request.user.org.org_id repo_owner = seafile_api.get_org_repo_owner(repo.id) is_repo_owner = True if repo_owner == username else False if not (request.user.org.is_staff or is_repo_owner): raise Http404 else: repo_owner = seafile_api.get_repo_owner(repo.id) is_repo_owner = True if repo_owner == username else False if not (request.user.is_staff or is_repo_owner): raise Http404 try: if is_org_context(request): org_id = request.user.org.org_id seaserv.seafserv_threaded_rpc.unset_org_inner_pub_repo(org_id, repo.id) else: seaserv.unset_inner_pub_repo(repo.id) origin_repo_id, origin_path = get_origin_repo_info(repo.id) if origin_repo_id is not None: perm_repo_id = origin_repo_id perm_path = origin_path else: perm_repo_id = repo.id perm_path = '/' send_perm_audit_msg('delete-repo-perm', username, 'all', perm_repo_id, perm_path, perm) messages.success(request, _('Unshare "%s" successfully.') % repo.name) except SearpcError: messages.error(request, _('Failed to unshare "%s".') % repo.name) referer = request.META.get('HTTP_REFERER', None) next = settings.SITE_ROOT if referer is None else referer return HttpResponseRedirect(next)
def list_repos_by_name(repo_name): repos = [] repos_all = seafile_api.get_repo_list(-1, -1) for repo in repos_all: if repo_name in repo.name: try: repo.owner = seafile_api.get_repo_owner(repo.id) except SearpcError: repo.owner = "failed to get" repos.append(repo) return repos
def render_recycle_root(request, repo_id, referer): repo = get_repo(repo_id) if not repo: raise Http404 scan_stat = request.GET.get('scan_stat', None) try: deleted_entries = seafile_api.get_deleted(repo_id, 0, '/', scan_stat) except SearpcError as e: logger.error(e) referer = request.META.get('HTTP_REFERER', None) next = settings.SITE_ROOT if referer is None else referer return HttpResponseRedirect(next) if not deleted_entries: new_scan_stat = None else: new_scan_stat = deleted_entries[-1].scan_stat trash_more = True if new_scan_stat is not None else False deleted_entries = deleted_entries[0:-1] for dirent in deleted_entries: if stat.S_ISDIR(dirent.mode): dirent.is_dir = True else: dirent.is_dir = False # Entries sort by deletion time in descending order. deleted_entries.sort(lambda x, y: cmp(y.delete_time, x.delete_time)) username = request.user.username if is_org_context(request): repo_owner = seafile_api.get_org_repo_owner(repo.id) else: repo_owner = seafile_api.get_repo_owner(repo.id) is_repo_owner = True if repo_owner == username else False enable_clean = False if is_repo_owner: enable_clean = True return render_to_response('repo_dir_recycle_view.html', { 'show_recycle_root': True, 'repo': repo, 'repo_dir_name': repo.name, 'dir_entries': deleted_entries, 'scan_stat': new_scan_stat, 'trash_more': trash_more, 'enable_clean': enable_clean, 'referer': referer, }, context_instance=RequestContext(request))
def get_repo_info(repo): result = {} result['id'] = repo.repo_id result['name'] = repo.repo_name result['owner'] = seafile_api.get_repo_owner(repo.repo_id) result['size'] = repo.size result['size_formatted'] = filesizeformat(repo.size) result['encrypted'] = repo.encrypted result['file_count'] = repo.file_count return result
def delete(self, request, repo_id, format=None): """ delete a library Permission checking: 1. only admin can perform this action. """ if get_system_default_repo_id() == repo_id: error_msg = _('System library can not be deleted.') return api_error(status.HTTP_400_BAD_REQUEST, error_msg) repo = seafile_api.get_repo(repo_id) if not repo: # for case of `seafile-data` has been damaged # no `repo object` will be returned from seafile api # delete the database record anyway try: seafile_api.remove_repo(repo_id) except Exception as e: logger.error(e) error_msg = 'Internal Server Error' return api_error(status.HTTP_500_INTERNAL_SERVER_ERROR, error_msg) return Response({'success': True}) repo_name = repo.name repo_owner = seafile_api.get_repo_owner(repo_id) if not repo_owner: repo_owner = seafile_api.get_org_repo_owner(repo_id) try: related_usernames = seaserv.get_related_users_by_repo(repo_id) seafile_api.remove_repo(repo_id) # send signal for seafevents repo_deleted.send(sender=None, org_id=-1, operator=request.user.username, usernames=related_usernames, repo_owner=repo_owner, repo_id=repo_id, repo_name=repo.name) except Exception as e: logger.error(e) error_msg = 'Internal Server Error' return api_error(status.HTTP_500_INTERNAL_SERVER_ERROR, error_msg) # send admin operation log signal admin_op_detail = { "id": repo_id, "name": repo_name, "owner": repo_owner, } admin_operation.send(sender=None, admin_name=request.user.username, operation=REPO_DELETE, detail=admin_op_detail) return Response({'success': True})
def get_group_repos(username, org_id, groups): """Get repos shared to groups. """ group_repos = [] if org_id: # For each group I joined... for grp in groups: # Get group repos, and for each group repos... for r_id in seafile_api.get_org_group_repoids(org_id, grp.id): # No need to list my own repo repo_owner = seafile_api.get_org_repo_owner(r_id) if repo_owner == username: continue # Convert repo properties due to the different collumns in Repo # and SharedRepo r = seafile_api.get_repo(r_id) if not r: continue r.repo_id = r.id r.repo_name = r.name r.repo_desc = r.desc r.last_modified = get_repo_last_modify(r) r.share_type = 'group' r.user = repo_owner r.user_perm = seafile_api.check_repo_access_permission( r_id, username) r.group = grp group_repos.append(r) else: # For each group I joined... for grp in groups: # Get group repos, and for each group repos... for r_id in seafile_api.get_group_repoids(grp.id): # No need to list my own repo repo_owner = seafile_api.get_repo_owner(r_id) if repo_owner == username: continue # Convert repo properties due to the different collumns in Repo # and SharedRepo r = seafile_api.get_repo(r_id) if not r: continue r.repo_id = r.id r.repo_name = r.name r.repo_desc = r.desc r.last_modified = get_repo_last_modify(r) r.share_type = 'group' r.user = repo_owner r.user_perm = seafile_api.check_repo_access_permission( r_id, username) r.group = grp group_repos.append(r) return group_repos
def format_repo_share_msg(self): """ Arguments: - `self`: """ try: d = json.loads(self.detail) except Exception as e: logger.error(e) return _(u"Internal error") share_from = email2nickname(d['share_from']) repo_id = d['repo_id'] path = d.get('path', '/') org_id = d.get('org_id', None) repo = None try: if path == '/': repo = seafile_api.get_repo(repo_id) else: if org_id: owner = seafile_api.get_org_repo_owner(repo_id) repo = seafile_api.get_org_virtual_repo( org_id, repo_id, path, owner) else: owner = seafile_api.get_repo_owner(repo_id) repo = seafile_api.get_virtual_repo(repo_id, path, owner) except Exception as e: logger.error(e) return None if repo is None: self.delete() return None if path == '/': tmpl = 'notifications/notice_msg/repo_share_msg.html' else: tmpl = 'notifications/notice_msg/folder_share_msg.html' msg = render_to_string( tmpl, { 'user': share_from, 'lib_url': HASH_URLS["VIEW_COMMON_LIB_DIR"] % { 'repo_id': repo.id, 'path': '' }, 'lib_name': repo.name, }) return msg
def test_can_clean_department_repo_trash(self): if not LOCAL_PRO_DEV_ENV: return # create a department group_id = ccnet_api.create_group('department_test', 'system admin', parent_group_id=-1) seafile_api.set_group_quota(group_id, -2) repo_id = seafile_api.add_group_owned_repo(group_id, 'dep_test', 'rw') repo_owner = seafile_api.get_repo_owner(repo_id) assert '@seafile_group' in repo_owner group_repos = seafile_api.get_repos_by_group(group_id) assert len(group_repos) == 1 group = ccnet_api.get_group(group_id) # department add user ccnet_api.group_add_member(group_id, group.creator_name, self.user_name) ccnet_api.group_add_member(group_id, group.creator_name, self.tmp_user.username) ccnet_api.group_set_admin(group_id, self.user_name) ccnet_api.group_unset_admin(group_id, self.tmp_user.username) assert is_group_admin(group_id, self.user_name) assert not is_group_admin(group_id, self.tmp_user.username) file_name = 'dep_test.txt' self.create_file( repo_id=repo_id, parent_dir='/', filename=file_name, username=self.user_name) # delete a file first seafile_api.del_file(repo_id, '/', file_name, self.user_name) # get trash item count self.login_as(self.user) resp = self.client.get(reverse('api-v2.1-repo-trash', args=[repo_id])) json_resp = json.loads(resp.content) assert len(json_resp['data']) > 0 # department member can not clean trash self.logout() self.login_as(self.tmp_user) resp = self.client.delete(self.url) self.assertEqual(403, resp.status_code) # department admin can clean library trash self.logout() self.login_as(self.user) ccnet_api.group_set_admin(group_id, self.user_name) resp = self.client.delete(self.url) self.assertEqual(200, resp.status_code) # get trash item count again resp = self.client.get(self.url) json_resp = json.loads(resp.content) assert len(json_resp['data']) == 0
def render_recycle_root(request, repo_id): repo = get_repo(repo_id) if not repo: raise Http404 scan_stat = request.GET.get('scan_stat', None) try: deleted_entries = seafile_api.get_deleted(repo_id, 0, '/', scan_stat) except SearpcError as e: logger.error(e) referer = request.META.get('HTTP_REFERER', None) next = settings.SITE_ROOT if referer is None else referer return HttpResponseRedirect(next) if not deleted_entries: new_scan_stat = None else: new_scan_stat = deleted_entries[-1].scan_stat trash_more = True if new_scan_stat is not None else False deleted_entries = deleted_entries[0:-1] for dirent in deleted_entries: if stat.S_ISDIR(dirent.mode): dirent.is_dir = True else: dirent.is_dir = False # Entries sort by deletion time in descending order. deleted_entries.sort(lambda x, y : cmp(y.delete_time, x.delete_time)) username = request.user.username if is_org_context(request): repo_owner = seafile_api.get_org_repo_owner(repo.id) else: repo_owner = seafile_api.get_repo_owner(repo.id) is_repo_owner = True if repo_owner == username else False enable_clean = False if is_repo_owner: enable_clean = True return render_to_response('repo_dir_recycle_view.html', { 'show_recycle_root': True, 'repo': repo, 'repo_dir_name': repo.name, 'dir_entries': deleted_entries, 'scan_stat': new_scan_stat, 'trash_more': trash_more, 'enable_clean': enable_clean, }, context_instance=RequestContext(request))
def delete(self, request, repo_id, path, share_type): """ Delete user/group share permission. Permission checking: 1. admin user. """ # current `request.user.username` is admin user, # so need to identify the repo owner specifically. repo_owner = seafile_api.get_repo_owner(repo_id) share_to = request.data.get('share_to', None) if share_type == 'user': email = share_to if not email or not is_valid_username(email): error_msg = 'email %s invalid.' % email return api_error(status.HTTP_400_BAD_REQUEST, error_msg) try: if path == '/': seafile_api.remove_share(repo_id, repo_owner, email) else: seafile_api.unshare_subdir_for_user( repo_id, path, repo_owner, email) except Exception as e: logger.error(e) error_msg = 'Internal Server Error' return api_error(status.HTTP_500_INTERNAL_SERVER_ERROR, error_msg) if share_type == 'group': group_id = share_to try: group_id = int(group_id) except ValueError: error_msg = 'group_id %s invalid' % group_id return api_error(status.HTTP_400_BAD_REQUEST, error_msg) try: if path == '/': seafile_api.unset_group_repo(repo_id, group_id, repo_owner) else: seafile_api.unshare_subdir_for_group( repo_id, path, repo_owner, group_id) except Exception as e: logger.error(e) error_msg = 'Internal Server Error' return api_error(status.HTTP_500_INTERNAL_SERVER_ERROR, error_msg) return Response({'success': True})
def permission_check_admin_owner(username, repo_id, request=None): # maybe add more complex logic in the future """ if repo is owned by user return true or check whether repo is owned by group and whether user is group's staff so finally the code is: check user == repo's owner else check user is the such group's staff """ if username == seafile_api.get_repo_owner(repo_id): return True else: return is_group_repo_staff(request, repo_id, username)
def get(self, request, repo_id, format=None): """ get all file/folder in a library """ 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) if not can_view_sys_admin_repo(repo): error_msg = 'Feature disabled.' return api_error(status.HTTP_403_FORBIDDEN, error_msg) parent_dir = request.GET.get('parent_dir', '/') if not parent_dir: error_msg = 'parent_dir invalid.' return api_error(status.HTTP_400_BAD_REQUEST, error_msg) if parent_dir[-1] != '/': parent_dir = parent_dir + '/' dir_id = seafile_api.get_dir_id_by_path(repo_id, parent_dir) if not dir_id: error_msg = 'Folder %s not found.' % parent_dir return api_error(status.HTTP_404_NOT_FOUND, error_msg) if is_org_context(request): repo_owner = seafile_api.get_org_repo_owner(repo_id) else: repo_owner = seafile_api.get_repo_owner(repo_id) try: dirs = seafserv_threaded_rpc.list_dir_with_perm( repo_id, parent_dir, dir_id, repo_owner, -1, -1) except SearpcError as e: logger.error(e) error_msg = 'Internal Server Error' return api_error(status.HTTP_500_INTERNAL_SERVER_ERROR, error_msg) return_results = {} return_results['repo_name'] = repo.repo_name return_results['repo_id'] = repo.repo_id return_results['is_system_library'] = True if \ repo.id == get_system_default_repo_id() else False return_results['dirent_list'] = [] for dirent in dirs: dirent_info = get_dirent_info(dirent) return_results['dirent_list'].append(dirent_info) return Response(return_results)
def list_group_shared_items(self, request, repo_id, path): if is_org_context(request): # when calling seafile API to share authority related functions, change the uesrname to repo owner. repo_owner = seafile_api.get_org_repo_owner(repo_id) org_id = request.user.org.org_id if path == '/': share_items = seafile_api.list_org_repo_shared_group(org_id, repo_owner, repo_id) else: share_items = seafile_api.get_org_shared_groups_for_subdir(org_id, repo_id, path, repo_owner) else: repo_owner = seafile_api.get_repo_owner(repo_id) if path == '/': share_items = seafile_api.list_repo_shared_group_by_user(repo_owner, repo_id) else: share_items = seafile_api.get_shared_groups_for_subdir(repo_id, path, repo_owner) ret = [] # change is_admin to True if user in admin groups. admin_groups = ExtraGroupsSharePermission.objects.get_admin_groups_by_repo(repo_id) for item in share_items: group_id = item.group_id group = ccnet_api.get_group(group_id) if not group: if is_org_context(request): if path == '/': seafile_api.del_org_group_repo(repo_id, org_id, group_id) else: seafile_api.org_unshare_subdir_for_group( org_id, repo_id, path, repo_owner, group_id) else: if path == '/': seafile_api.unset_group_repo(repo_id, group_id, repo_owner) else: seafile_api.unshare_subdir_for_group( repo_id, path, repo_owner, group_id) continue ret.append({ "share_type": "group", "group_info": { "id": group_id, "name": group.group_name, }, "permission": item.perm, "is_admin": group_id in admin_groups, }) return ret
def my_group_repos(request): """Return html snippet of group repos. Arguments: - `request`: """ if not request.is_ajax(): raise Http404 username = request.user.username group_repos = [] # Get all personal groups I joined. joined_groups = request.user.joined_groups # For each group I joined... for grp in joined_groups: # Get group repos, and for each group repos... for r_id in seaserv.get_group_repoids(grp.id): # No need to list my own repo repo_owner = seafile_api.get_repo_owner(r_id) if repo_owner == username: continue # Convert repo properties due to the different collumns in Repo # and SharedRepo r = seaserv.get_repo(r_id) if not r: continue r.repo_id = r.id r.repo_name = r.name r.repo_desc = r.desc r.last_modified = get_repo_last_modify(r) r.share_type = 'group' r.user = repo_owner r.user_perm = seaserv.check_permission(r_id, username) r.group = grp group_repos.append(r) group_repos.sort(key=lambda x: x.group.group_name) for i, repo in enumerate(group_repos): if i == 0: repo.show_group_name = True else: if repo.group.group_name != group_repos[i-1].group.group_name: repo.show_group_name = True ctx = { "group_repos": group_repos, } html = render_to_string('my_group_repos.html', ctx, context_instance=RequestContext(request)) return HttpResponse(html)
def get(self, request, repo_id, format=None): """ get all file/folder in a library """ 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) if not can_view_sys_admin_repo(repo): error_msg = 'Feature disabled.' return api_error(status.HTTP_403_FORBIDDEN, error_msg) parent_dir = request.GET.get('parent_dir', '/') if not parent_dir: error_msg = 'parent_dir invalid.' return api_error(status.HTTP_400_BAD_REQUEST, error_msg) if parent_dir[-1] != '/': parent_dir = parent_dir + '/' dir_id = seafile_api.get_dir_id_by_path(repo_id, parent_dir) if not dir_id: error_msg = 'Folder %s not found.' % parent_dir return api_error(status.HTTP_404_NOT_FOUND, error_msg) if is_org_context(request): repo_owner = seafile_api.get_org_repo_owner(repo_id) else: repo_owner = seafile_api.get_repo_owner(repo_id) try: dirs = seafserv_threaded_rpc.list_dir_with_perm(repo_id, parent_dir, dir_id, repo_owner, -1, -1) except SearpcError as e: logger.error(e) error_msg = 'Internal Server Error' return api_error(status.HTTP_500_INTERNAL_SERVER_ERROR, error_msg) return_results = {} return_results['repo_name'] = repo.repo_name return_results['repo_id'] = repo.repo_id return_results['is_system_library'] = True if \ repo.id == get_system_default_repo_id() else False return_results['dirent_list'] = [] for dirent in dirs: dirent_info = get_dirent_info(dirent) return_results['dirent_list'].append(dirent_info) return Response(return_results)
def repo_history_view(request, repo_id): """View repo in history. """ repo = get_repo(repo_id) if not repo: raise Http404 username = request.user.username path = get_path_from_request(request) user_perm = check_folder_permission(request, repo.id, '/') if user_perm is None: return render_error(request, _(u'Permission denied')) try: server_crypto = UserOptions.objects.is_server_crypto(username) except CryptoOptionNotSetError: # Assume server_crypto is ``False`` if this option is not set. server_crypto = False if repo.encrypted and \ (repo.enc_version == 1 or (repo.enc_version == 2 and server_crypto)) \ and not is_password_set(repo.id, username): return render_to_response('decrypt_repo_form.html', { 'repo': repo, 'next': get_next_url_from_request(request) or reverse("view_common_lib_dir", args=[repo_id, '']), }, context_instance=RequestContext(request)) commit_id = request.GET.get('commit_id', None) if commit_id is None: return HttpResponseRedirect(reverse("view_common_lib_dir", args=[repo_id, ''])) current_commit = get_commit(repo.id, repo.version, commit_id) if not current_commit: current_commit = get_commit(repo.id, repo.version, repo.head_cmmt_id) file_list, dir_list, dirent_more = get_repo_dirents(request, repo, current_commit, path) zipped = get_nav_path(path, repo.name) repo_owner = seafile_api.get_repo_owner(repo.id) is_repo_owner = True if username == repo_owner else False return render_to_response('repo_history_view.html', { 'repo': repo, "is_repo_owner": is_repo_owner, 'user_perm': user_perm, 'current_commit': current_commit, 'dir_list': dir_list, 'file_list': file_list, 'path': path, 'zipped': zipped, }, context_instance=RequestContext(request))
def put(self, request, repo_id): """ Change repo password. Permission checking: 1. repo owner """ # argument check old_password = request.POST.get('old_password', None) if not old_password: error_msg = 'old_password invalid.' return api_error(status.HTTP_400_BAD_REQUEST, error_msg) new_password = request.POST.get('new_password', None) if not new_password: error_msg = 'new_password invalid.' return api_error(status.HTTP_400_BAD_REQUEST, 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) # permission check if is_org_context(request): repo_owner = seafile_api.get_org_repo_owner(repo.id) else: repo_owner = seafile_api.get_repo_owner(repo.id) username = request.user.username if username != repo_owner: error_msg = 'Permission denied.' return api_error(status.HTTP_403_FORBIDDEN, error_msg) # change password try: seafile_api.change_repo_passwd(repo_id, old_password, new_password, username) except SearpcError as e: if e.msg == 'Incorrect password': error_msg = _(u'Wrong old password') return api_error(status.HTTP_403_FORBIDDEN, error_msg) else: logger.error(e) error_msg = 'Internal Server Error' return api_error(status.HTTP_500_INTERNAL_SERVER_ERROR, error_msg) return Response({'success': True})
def format_repo_share_to_group_msg(self): """ Arguments: - `self`: """ try: d = json.loads(self.detail) except Exception as e: logger.error(e) return _(u"Internal error") share_from = email2nickname(d['share_from']) repo_id = d['repo_id'] group_id = d['group_id'] path = d.get('path', '/') org_id = d.get('org_id', None) repo = None try: group = ccnet_api.get_group(group_id) if path == '/': repo = seafile_api.get_repo(repo_id) else: if org_id: owner = seafile_api.get_org_repo_owner(repo_id) repo = seafile_api.get_org_virtual_repo( org_id, repo_id, path, owner) else: owner = seafile_api.get_repo_owner(repo_id) repo = seafile_api.get_virtual_repo(repo_id, path, owner) except Exception as e: logger.error(e) return None if not repo or not group: self.delete() return None msg = _( u"%(user)s has shared a library named <a href='%(repo_href)s'>%(repo_name)s</a> to group <a href='%(group_href)s'>%(group_name)s</a>." ) % { 'user': escape(share_from), 'repo_href': reverse('view_common_lib_dir', args=[repo.id, '']), 'repo_name': escape(repo.name), 'group_href': reverse('group_info', args=[group.id]), 'group_name': escape(group.group_name), } return msg
def repo_snapshot(request, repo_id): """View repo in history. """ repo = get_repo(repo_id) if not repo: raise Http404 username = request.user.username user_perm = check_folder_permission(request, repo.id, '/') if user_perm is None: return render_error(request, _('Permission denied')) try: server_crypto = UserOptions.objects.is_server_crypto(username) except CryptoOptionNotSetError: # Assume server_crypto is ``False`` if this option is not set. server_crypto = False reverse_url = reverse('lib_view', args=[repo_id, repo.name, '']) if repo.encrypted and \ (repo.enc_version == 1 or (repo.enc_version == 2 and server_crypto)) \ and not is_password_set(repo.id, username): return render( request, 'decrypt_repo_form.html', { 'repo': repo, 'next': get_next_url_from_request(request) or reverse_url, }) commit_id = request.GET.get('commit_id', None) if commit_id is None: return HttpResponseRedirect(reverse_url) current_commit = get_commit(repo.id, repo.version, commit_id) if not current_commit: current_commit = get_commit(repo.id, repo.version, repo.head_cmmt_id) has_perm = is_repo_owner(request, repo.id, username) # department admin if not has_perm: repo_owner = seafile_api.get_repo_owner(repo_id) if '@seafile_group' in repo_owner: group_id = get_group_id_by_repo_owner(repo_owner) has_perm = is_group_admin(group_id, username) return render( request, 'repo_snapshot_react.html', { 'repo': repo, "can_restore_repo": has_perm, 'current_commit': current_commit, })
def get(self, request): """get virus scan records """ if not request.user.admin_permissions.other_permission(): return api_error(status.HTTP_403_FORBIDDEN, 'Permission denied.') try: page = int(request.GET.get('page', '')) except ValueError: page = 1 try: per_page = int(request.GET.get('per_page', '')) except ValueError: per_page = 25 start = (page - 1) * per_page count = per_page try: virus_records = get_virus_record(start=start, limit=count) except Exception as e: logger.error(e) error_msg = 'Internal Server Error' return api_error(status.HTTP_500_INTERNAL_SERVER_ERROR, error_msg) record_list = list() for virus_record in virus_records: try: repo = seafile_api.get_repo(virus_record.repo_id) repo_owner = seafile_api.get_repo_owner(virus_record.repo_id) except Exception as e: logger.error(e) continue if not repo: continue else: record = dict() record["repo_name"] = repo.name record["repo_owner"] = repo_owner record["file_path"] = virus_record.file_path record["has_handle"] = virus_record.has_handle record["virus_id"] = virus_record.vid record_list.append(record) return Response({"record_list": record_list}, status=status.HTTP_200_OK)
def post(self, request, repo_id, commit_id, format=None): """ revert commit in repo history Permission checking: 1. only repo owner can perform this action. """ username = request.user.username # 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) commit = seafile_api.get_commit(repo.id, repo.version, commit_id) if not commit: error_msg = 'Commit %s not found.' % commit_id return api_error(status.HTTP_404_NOT_FOUND, error_msg) # permission check has_perm = is_repo_owner(request, repo.id, username) if not has_perm: repo_owner = seafile_api.get_repo_owner(repo_id) # department admin if '@seafile_group' in repo_owner: group_id = get_group_id_by_repo_owner(repo_owner) has_perm = is_group_admin(group_id, username) if not has_perm: error_msg = 'Permission denied.' return api_error(status.HTTP_403_FORBIDDEN, error_msg) # main if repo.encrypted: ret = seafile_api.is_password_set(repo_id, username) is_decrypted = False if ret == 0 else True if not is_decrypted: error_msg = _('This library has not been decrypted.') return api_error(status.HTTP_403_FORBIDDEN, error_msg) try: seafile_api.revert_repo(repo_id, commit_id, username) except Exception as e: logger.error(e) error_msg = 'Internal Server Error' return api_error(status.HTTP_500_INTERNAL_SERVER_ERROR, error_msg) return Response({'success': True})
def delete(self, request, repo_id, format=None): """ Delete repo share invitation. """ # argument check path = request.data.get('path', None) if not path: return api_error(status.HTTP_400_BAD_REQUEST, 'path invalid.') token = request.data.get('token', None) if not token: return api_error(status.HTTP_400_BAD_REQUEST, 'token invalid.') # recourse check repo = seafile_api.get_repo(repo_id) if not repo: return api_error(status.HTTP_404_NOT_FOUND, 'Library %s not found.' % repo_id) if seafile_api.get_dir_id_by_path(repo.id, path) is None: return api_error(status.HTTP_404_NOT_FOUND, 'Folder %s not found.' % path) # permission check username = request.user.username if is_org_context(request): repo_owner = seafile_api.get_org_repo_owner(repo_id) else: repo_owner = seafile_api.get_repo_owner(repo_id) if username != repo_owner and not is_repo_admin(username, repo_id): error_msg = 'Permission denied.' return api_error(status.HTTP_403_FORBIDDEN, error_msg) # mian try: shared_obj = RepoShareInvitation.objects.get_by_token_and_path( token=token, repo_id=repo_id, path=path) if not shared_obj: error_msg = 'repo share invitation not found.' return api_error(status.HTTP_404_NOT_FOUND, error_msg) shared_obj.delete() except Exception as e: logger.error(e) error_msg = 'Internal Server Error' return api_error(status.HTTP_500_INTERNAL_SERVER_ERROR, error_msg) return Response({'success': True})
def get(self, request, repo_id, format=None): """ List repo share invitations. """ # argument check path = request.GET.get('path', None) if not path: return api_error(status.HTTP_400_BAD_REQUEST, 'path invalid.') # recourse 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) if seafile_api.get_dir_id_by_path(repo.id, path) is None: return api_error(status.HTTP_404_NOT_FOUND, 'Folder %s not found.' % path) # permission check username = request.user.username if is_org_context(request): repo_owner = seafile_api.get_org_repo_owner(repo_id) else: repo_owner = seafile_api.get_repo_owner(repo_id) if username != repo_owner and not is_repo_admin(username, repo_id): error_msg = 'Permission denied.' return api_error(status.HTTP_403_FORBIDDEN, error_msg) # main shared_list = list() try: shared_queryset = RepoShareInvitation.objects.list_by_repo_id_and_path( repo_id, path) except Exception as e: logger.error(e) error_msg = 'Internal Server Error' return api_error(status.HTTP_500_INTERNAL_SERVER_ERROR, error_msg) for obj in shared_queryset: data = obj.invitation.to_dict() data['permission'] = obj.permission data['inviter_name'] = email2nickname(obj.invitation.inviter) shared_list.append(data) return Response({'repo_share_invitation_list': shared_list})
def get_group_repos(request, groups): """Get repos shared to groups. """ group_repos = [] if is_org_context(request): org_id = request.user.org.org_id # For each group I joined... for grp in groups: # Get group repos, and for each group repos... for r_id in seafile_api.get_org_group_repoids(org_id, grp.id): repo_owner = seafile_api.get_org_repo_owner(r_id) # Convert repo properties due to the different collumns in Repo # and SharedRepo r = get_repo(r_id) if not r: continue r.repo_id = r.id r.repo_name = r.name r.repo_desc = r.desc r.last_modified = get_repo_last_modify(r) r.share_type = 'group' r.user = repo_owner r.user_perm = check_folder_permission(request, r_id, '/') r.group = grp group_repos.append(r) else: # For each group I joined... for grp in groups: # Get group repos, and for each group repos... for r_id in seafile_api.get_group_repoids(grp.id): repo_owner = seafile_api.get_repo_owner(r_id) # Convert repo properties due to the different collumns in Repo # and SharedRepo r = get_repo(r_id) if not r: continue r.repo_id = r.id r.repo_name = r.name r.repo_desc = r.desc r.last_modified = get_repo_last_modify(r) r.share_type = 'group' r.user = repo_owner r.user_perm = check_folder_permission(request, r_id, '/') r.group = grp group_repos.append(r) return group_repos
def test_can_set_department_repo(self): if not LOCAL_PRO_DEV_ENV: return # create a department group_id = ccnet_api.create_group('department_test', 'system admin', parent_group_id=-1) seafile_api.set_group_quota(group_id, -2) repo_id = seafile_api.add_group_owned_repo(group_id, 'dep_test', 'rw') repo_owner = seafile_api.get_repo_owner(repo_id) assert '@seafile_group' in repo_owner group_repos = seafile_api.get_repos_by_group(group_id) assert len(group_repos) == 1 group = ccnet_api.get_group(group_id) # department add user ccnet_api.group_add_member(group_id, group.creator_name, self.user.username) ccnet_api.group_add_member(group_id, group.creator_name, self.tmp_user.username) ccnet_api.group_set_admin(group_id, self.user.username) ccnet_api.group_unset_admin(group_id, self.tmp_user.username) assert is_group_admin(group_id, self.user.username) assert not is_group_admin(group_id, self.tmp_user.username) url = reverse("api2-repo-history-limit", args=[repo_id]) self.config.ENABLE_REPO_HISTORY_SETTING = True # department member can not set self.logout() self.login_as(self.tmp_user) data = 'keep_days=%s' % 6 resp = self.client.put(url, data, 'application/x-www-form-urlencoded') self.assertEqual(403, resp.status_code) # department admin can set self.logout() self.login_as(self.user) data = 'keep_days=%s' % 6 resp = self.client.put(url, data, 'application/x-www-form-urlencoded') self.assertEqual(200, resp.status_code) self.remove_group(group_id) self.remove_repo(repo_id)
def has_shared_to_user(repo_id, path, username, org_id=None): if is_valid_org_id(org_id): # when calling seafile API to share authority related functions, change the uesrname to repo owner. repo_owner = seafile_api.get_org_repo_owner(repo_id) if path == '/': share_items = seafile_api.list_org_repo_shared_to( org_id, repo_owner, repo_id) else: share_items = seafile_api.get_org_shared_users_for_subdir( org_id, repo_id, path, repo_owner) else: repo_owner = seafile_api.get_repo_owner(repo_id) if path == '/': share_items = seafile_api.list_repo_shared_to(repo_owner, repo_id) else: share_items = seafile_api.get_shared_users_for_subdir( repo_id, path, repo_owner) return username in [item.user for item in share_items]
def _decorated(view, request, repo_id, *args, **kwargs): 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) # check permission if is_org_context(request): repo_owner = seafile_api.get_org_repo_owner(repo_id) else: repo_owner = seafile_api.get_repo_owner(repo_id) username = request.user.username if repo.is_virtual or username != repo_owner: error_msg = 'Permission denied.' return api_error(status.HTTP_403_FORBIDDEN, error_msg) return func(view, request, repo_id, *args, **kwargs)
def upload_file_done(request): """Send a message when a file is uploaded. Arguments: - `request`: """ ct = 'application/json; charset=utf-8' result = {} filename = request.GET.get('fn', '') if not filename: result['error'] = _('Argument missing') return HttpResponse(json.dumps(result), status=400, content_type=ct) repo_id = request.GET.get('repo_id', '') if not repo_id: result['error'] = _('Argument missing') return HttpResponse(json.dumps(result), status=400, content_type=ct) path = request.GET.get('p', '') if not path: result['error'] = _('Argument missing') return HttpResponse(json.dumps(result), status=400, content_type=ct) # a few checkings if not seafile_api.get_repo(repo_id): result['error'] = _('Wrong repo id') return HttpResponse(json.dumps(result), status=400, content_type=ct) owner = seafile_api.get_repo_owner(repo_id) if not owner: result['error'] = _('Wrong repo id') return HttpResponse(json.dumps(result), status=400, content_type=ct) file_path = path.rstrip('/') + '/' + filename if seafile_api.get_file_id_by_path(repo_id, file_path) is None: result['error'] = _('File does not exist') return HttpResponse(json.dumps(result), status=400, content_type=ct) # send singal upload_file_successful.send(sender=None, repo_id=repo_id, file_path=file_path, owner=owner) return HttpResponse(json.dumps({'success': True}), content_type=ct)
def _decorated(view, request, repo_id, *args, **kwargs): 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) # check permission if is_org_context(request): repo_owner = seafile_api.get_org_repo_owner(repo_id) else: repo_owner = seafile_api.get_repo_owner(repo_id) username = request.user.username if repo.is_virtual or username != repo_owner: error_msg = 'Permission denied.' return api_error(status.HTTP_403_FORBIDDEN, error_msg) # check arguments group_id = request.data.get('group_id', None) path = request.data.get('folder_path', None) perm = request.data.get('permission', None) try: group_id = int(group_id) except ValueError: error_msg = 'group_id invalid.' return api_error(status.HTTP_400_BAD_REQUEST, error_msg) if not seaserv.get_group(group_id): error_msg = 'Group %s not found.' % group_id return api_error(status.HTTP_404_NOT_FOUND, error_msg) if path: path = path.rstrip('/') if path != '/' else path if seafile_api.get_dir_id_by_path(repo_id, path) is None: error_msg = 'Folder %s not found.' % path return api_error(status.HTTP_404_NOT_FOUND, error_msg) if request.method in ('POST', 'PUT') and perm not in ('r', 'rw'): error_msg = 'permission invalid.' return api_error(status.HTTP_400_BAD_REQUEST, error_msg) return func(view, request, repo_id, *args, **kwargs)
def can_access_repo_setting(request, repo_id, username): repo = seafile_api.get_repo(repo_id) if not repo: return (False, None) # no settings for virtual repo if ENABLE_SUB_LIBRARY and repo.is_virtual: return (False, None) # check permission if is_org_context(request): repo_owner = seafile_api.get_org_repo_owner(repo_id) else: repo_owner = seafile_api.get_repo_owner(repo_id) is_owner = True if username == repo_owner else False if not is_owner: return (False, None) return (True, repo)
def get_repo_info(repo): repo_owner = seafile_api.get_repo_owner(repo.repo_id) if not repo_owner: try: org_repo_owner = seafile_api.get_org_repo_owner(repo.repo_id) except Exception: org_repo_owner = None result = {} result['id'] = repo.repo_id result['name'] = repo.repo_name result['owner'] = repo_owner or org_repo_owner result['size'] = repo.size result['size_formatted'] = filesizeformat(repo.size) result['encrypted'] = repo.encrypted result['file_count'] = repo.file_count return result
def post(self, request, email, format=None): # migrate an account's repos and groups to an exist account if not is_valid_username(email): return api_error(status.HTTP_400_BAD_REQUEST, 'Email %s invalid.' % email) op = request.data.get('op', '').lower() if op == 'migrate': from_user = email to_user = request.data.get('to_user', '') if not is_valid_username(to_user): return api_error(status.HTTP_400_BAD_REQUEST, 'Email %s invalid.' % to_user) try: user2 = User.objects.get(email=to_user) except User.DoesNotExist: return api_error(status.HTTP_404_NOT_FOUND, 'User %s not found.' % to_user) # transfer owned repos to new user for r in seafile_api.get_owned_repo_list(from_user): seafile_api.set_repo_owner(r.id, user2.username) # transfer shared repos to new user for r in seafile_api.get_share_in_repo_list(from_user, -1, -1): owner = seafile_api.get_repo_owner(r.repo_id) seafile_api.share_repo(r.repo_id, owner, to_user, r.permission) # transfer joined groups to new user for g in ccnet_api.get_groups(from_user): if not is_group_member(g.id, user2.username): # add new user to the group on behalf of the group creator ccnet_threaded_rpc.group_add_member( g.id, g.creator_name, to_user) if from_user == g.creator_name: ccnet_threaded_rpc.set_group_creator(g.id, to_user) return Response({'success': True}) else: return api_error(status.HTTP_400_BAD_REQUEST, 'op can only be migrate.')
def format_repo_share_msg(self): """ Arguments: - `self`: """ try: d = json.loads(self.detail) except Exception as e: logger.error(e) return _(u"Internal error") share_from = email2nickname(d['share_from']) repo_id = d['repo_id'] path = d.get('path', '/') org_id = d.get('org_id', None) repo = None try: if path == '/': repo = seafile_api.get_repo(repo_id) else: if org_id: owner = seafile_api.get_org_repo_owner(repo_id) repo = seafile_api.get_org_virtual_repo( org_id, repo_id, path, owner) else: owner = seafile_api.get_repo_owner(repo_id) repo = seafile_api.get_virtual_repo(repo_id, path, owner) except Exception as e: logger.error(e) return None if repo is None: self.delete() return None msg = _(u"%(user)s has shared a library named <a href='%(href)s'>%(repo_name)s</a> to you.") % { 'user': escape(share_from), 'href': HASH_URLS["VIEW_COMMON_LIB_DIR"] % {'repo_id':repo.id, 'path': ''}, 'repo_name': escape(repo.name), } return msg
def has_shared_to_group(repo_id, path, gid, org_id=None): if is_valid_org_id(org_id): # when calling seafile API to share authority related functions, change the uesrname to repo owner. repo_owner = seafile_api.get_org_repo_owner(repo_id) if path == '/': share_items = seafile_api.list_org_repo_shared_group(org_id, repo_owner, repo_id) else: share_items = seafile_api.get_org_shared_groups_for_subdir(org_id, repo_id, path, repo_owner) else: repo_owner = seafile_api.get_repo_owner(repo_id) if path == '/': share_items = seafile_api.list_repo_shared_group_by_user(repo_owner, repo_id) else: share_items = seafile_api.get_shared_groups_for_subdir(repo_id, path, repo_owner) return gid in [item.group_id for item in share_items]
def has_shared_to_group(repo_id, path, gid, org_id=None): if org_id: # when calling seafile API to share authority related functions, change the uesrname to repo owner. repo_owner = seafile_api.get_org_repo_owner(repo_id) if path == '/': share_items = seafile_api.list_org_repo_shared_group(org_id, repo_owner, repo_id) else: share_items = seafile_api.get_org_shared_groups_for_subdir(org_id, repo_id, path, repo_owner) else: repo_owner = seafile_api.get_repo_owner(repo_id) if path == '/': share_items = seafile_api.list_repo_shared_group_by_user(repo_owner, repo_id) else: share_items = seafile_api.get_shared_groups_for_subdir(repo_id, path, repo_owner) return gid in [item.group_id for item in share_items]
def repo_revert_history(request, repo_id): next = request.META.get('HTTP_REFERER', None) if not next: next = settings.SITE_ROOT repo = get_repo(repo_id) if not repo: messages.error(request, _("Library does not exist")) return HttpResponseRedirect(next) # perm check perm = check_folder_permission(request, repo_id, '/') username = request.user.username repo_owner = seafile_api.get_repo_owner(repo.id) if perm is None or repo_owner != username: messages.error(request, _("Permission denied")) return HttpResponseRedirect(next) try: server_crypto = UserOptions.objects.is_server_crypto(username) except CryptoOptionNotSetError: # Assume server_crypto is ``False`` if this option is not set. server_crypto = False password_set = False if repo.props.encrypted and \ (repo.enc_version == 1 or (repo.enc_version == 2 and server_crypto)): try: ret = seafserv_rpc.is_passwd_set(repo_id, username) if ret == 1: password_set = True except SearpcError, e: return render_error(request, e.msg) if not password_set: return HttpResponseRedirect(reverse("view_common_lib_dir", args=[repo_id, '']))
def put(self, request, repo_id, format=None): """ Share a repo to users/groups/public. """ share_type = request.GET.get('share_type') user = request.GET.get('user') group_id = request.GET.get('group_id') permission = request.GET.get('permission') if permission !='rw' and permission != "r": return api_error(status.HTTP_400_BAD_REQUEST, 'Permission need to be rw or r.') if share_type == 'personal': if not is_registered_user(user) : return api_error(status.HTTP_400_BAD_REQUEST, 'User does not exist') try : from_email = seafile_api.get_repo_owner(repo_id) seafserv_threaded_rpc.add_share(repo_id, from_email, user, permission) except SearpcError, e: return api_error(status.HTTP_500_INTERNAL_SERVER_ERROR, "Searpc Error: " + e.msg)
def get_repo_owner(self, request, repo_id): if is_org_context(request): return seafile_api.get_org_repo_owner(repo_id) else: return seafile_api.get_repo_owner(repo_id)
def render_repo(request, repo): """Steps to show repo page: If user has permission to view repo If repo is encrypt and password is not set on server return decrypt repo page If repo is not encrypt or password is set on server Show repo direntries based on requested path If user does not have permission to view repo return permission deny page """ username = request.user.username path = get_path_from_request(request) user_perm = check_repo_access_permission(repo.id, request.user) if user_perm is None: return render_to_response('repo_access_deny.html', { 'repo': repo, }, context_instance=RequestContext(request)) sub_lib_enabled = UserOptions.objects.is_sub_lib_enabled(username) server_crypto = False if repo.encrypted: try: server_crypto = UserOptions.objects.is_server_crypto(username) except CryptoOptionNotSetError: return render_to_response('options/set_user_options.html', { }, context_instance=RequestContext(request)) if (repo.enc_version == 1 or (repo.enc_version == 2 and server_crypto)) \ and not is_password_set(repo.id, username): return render_to_response('decrypt_repo_form.html', { 'repo': repo, 'next': get_next_url_from_request(request) or \ reverse('repo', args=[repo.id]), 'force_server_crypto': FORCE_SERVER_CRYPTO, }, context_instance=RequestContext(request)) # query context args fileserver_root = get_fileserver_root() max_upload_file_size = get_max_upload_file_size() protocol = request.is_secure() and 'https' or 'http' domain = RequestSite(request).domain for g in request.user.joined_groups: g.avatar = grp_avatar(g.id, 20) head_commit = get_commit(repo.id, repo.version, repo.head_cmmt_id) if not head_commit: raise Http404 if new_merge_with_no_conflict(head_commit): info_commit = get_commit_before_new_merge(head_commit) else: info_commit = head_commit repo_size = get_repo_size(repo.id) no_quota = is_no_quota(repo.id) if is_org_context(request): repo_owner = seafile_api.get_org_repo_owner(repo.id) else: repo_owner = seafile_api.get_repo_owner(repo.id) is_repo_owner = True if repo_owner == username else False if is_repo_owner and not repo.is_virtual: show_repo_settings = True else: show_repo_settings = False more_start = None file_list, dir_list, dirent_more = get_repo_dirents(request, repo, head_commit, path, offset=0, limit=100) if dirent_more: more_start = 100 zipped = get_nav_path(path, repo.name) repo_groups = get_shared_groups_by_repo_and_user(repo.id, username) if len(repo_groups) > 1: repo_group_str = render_to_string("snippets/repo_group_list.html", {'groups': repo_groups}) else: repo_group_str = '' upload_url = get_upload_url(request, repo.id) fileshare = get_fileshare(repo.id, username, path) dir_shared_link = get_dir_share_link(fileshare) uploadlink = get_uploadlink(repo.id, username, path) dir_shared_upload_link = get_dir_shared_upload_link(uploadlink) return render_to_response('repo.html', { 'repo': repo, 'user_perm': user_perm, 'repo_owner': repo_owner, 'is_repo_owner': is_repo_owner, 'show_repo_settings': show_repo_settings, 'current_commit': head_commit, 'info_commit': info_commit, 'password_set': True, 'repo_size': repo_size, 'dir_list': dir_list, 'file_list': file_list, 'dirent_more': dirent_more, 'more_start': more_start, 'path': path, 'zipped': zipped, 'groups': repo_groups, 'repo_group_str': repo_group_str, 'no_quota': no_quota, 'max_upload_file_size': max_upload_file_size, 'upload_url': upload_url, 'fileserver_root': fileserver_root, 'protocol': protocol, 'domain': domain, 'fileshare': fileshare, 'dir_shared_link': dir_shared_link, 'uploadlink': uploadlink, 'dir_shared_upload_link': dir_shared_upload_link, 'ENABLE_SUB_LIBRARY': ENABLE_SUB_LIBRARY, 'server_crypto': server_crypto, "sub_lib_enabled": sub_lib_enabled, }, context_instance=RequestContext(request))