def test_reshare_to_user_group_after_transfer_repo(self):

        tmp_user = '******'
        User.objects.create_user(tmp_user)

        # add admin user to group
        ccnet_api.group_add_member(self.group_id, self.user_name, self.admin.username)

        # share user's repo to tmp_user with 'rw' permission
        seafile_api.share_repo(self.user_repo_id, self.user.username,
                tmp_user, 'rw')

        # share user's repo to group with 'r' permission
        seafile_api.set_group_repo(self.user_repo_id, self.group_id,
                self.user_name, 'r')
        group_repos = seafile_api.get_repos_by_group(self.group_id)

        assert group_repos[0].permission == 'r'
        assert seafile_api.check_permission_by_path(self.user_repo_id,
                '/', tmp_user) == 'rw'

        self.login_as(self.user)

        url = reverse("api2-repo-owner", args=[self.user_repo_id])
        data = 'owner=%s' % self.admin.email

        # transfer repo to admin
        resp = self.client.put(url, data, 'application/x-www-form-urlencoded')
        self.assertEqual(200, resp.status_code)

        group_repos = seafile_api.get_repos_by_group(self.group_id)
        assert group_repos[0].permission == 'r'
        assert seafile_api.check_permission_by_path(self.user_repo_id,
                '/', tmp_user) == 'rw'
Beispiel #2
0
    def test_can_update_user_share_perm(self):
        self.share_repo_to_user()

        assert seafile_api.check_permission_by_path(
                self.repo_id, '/', self.admin_name) == 'rw'

        self.login_as(self.user)

        url = reverse('api-v2.1-shared-repo', args=[self.repo_id])
        data = 'permission=r&share_type=personal&user=%s' % self.admin_name
        resp = self.client.put(url, data, 'application/x-www-form-urlencoded')

        self.assertEqual(200, resp.status_code)
        assert seafile_api.check_permission_by_path(
                self.repo_id, '/', self.admin_name) == 'r'
    def handleMove(self, destPath):
        if self.provider.readonly:
            raise DAVError(HTTP_FORBIDDEN)

        parts = destPath.strip("/").split("/", 1)
        if len(parts) <= 1:
            raise DAVError(HTTP_BAD_REQUEST)
        repo_name = parts[0]
        rel_path = parts[1]

        dest_dir, dest_file = os.path.split(rel_path)
        dest_repo = getRepoByName(repo_name, self.username, self.org_id, self.is_guest)

        if seafile_api.check_permission_by_path(dest_repo.id, self.rel_path, self.username) != "rw":
            raise DAVError(HTTP_FORBIDDEN)

        src_dir, src_file = os.path.split(self.rel_path)
        if not src_file:
            raise DAVError(HTTP_BAD_REQUEST)

        if not seafile_api.is_valid_filename(dest_repo.id, dest_file):
            raise DAVError(HTTP_BAD_REQUEST)

        # some clients such as GoodReader requires "overwrite" semantics
        file_id_dest = seafile_api.get_file_id_by_path(dest_repo.id, rel_path)
        if file_id_dest != None:
            seafile_api.del_file(dest_repo.id, dest_dir, dest_file, self.username)

        seafile_api.move_file(self.repo.id, src_dir, src_file,
                              dest_repo.id, dest_dir, dest_file, self.username, NEED_PROGRESS, SYNCHRONOUS)

        return True
Beispiel #4
0
    def test_create_file_with_invalid_folder_perm(self):

        if not LOCAL_PRO_DEV_ENV:
            return

        # share user's repo to admin with 'rw' permission
        seafile_api.share_repo(self.repo_id, self.user_name, self.admin_name,
                               'rw')

        # set sub-folder permisson as 'r' for admin
        seafile_api.add_folder_user_perm(self.repo_id, self.folder_path, 'r',
                                         self.admin_name)

        # admin can visit sub-folder with 'r' permission
        assert seafile_api.check_permission_by_path(self.repo_id,
                                                    self.folder_path,
                                                    self.admin_name) == 'r'

        # login as admin, then create file in a 'r' permission folder
        self.login_as(self.admin)

        new_name = randstring(6)
        new_file_path = posixpath.join(self.folder_path, new_name)
        data = {
            'operation': 'create',
        }

        resp = self.client.post(self.url + '?p=' + new_file_path, data)
        self.assertEqual(403, resp.status_code)
Beispiel #5
0
    def test_rename_file_with_invalid_folder_perm(self):

        if not LOCAL_PRO_DEV_ENV:
            return

        # create a file as old file in user repo sub-folder
        old_file_name = randstring(6)
        seafile_api.post_empty_file(repo_id=self.repo_id,
                parent_dir=self.folder_path, filename=old_file_name,
                username=self.user_name)

        # share user's repo to admin with 'rw' permission
        seafile_api.share_repo(self.repo_id, self.user_name,
                self.admin_name, 'rw')

        # set sub-folder permisson as 'r' for admin
        seafile_api.add_folder_user_perm(self.repo_id,
                self.folder_path, 'r', self.admin_name)

        # admin can visit old file with 'r' permission
        old_file_path = posixpath.join(self.folder_path, old_file_name)
        assert seafile_api.check_permission_by_path(self.repo_id,
                old_file_path, self.admin_name) == 'r'

        # login as admin, then rename a 'r' permission old file
        self.login_as(self.admin)

        new_name = randstring(6)
        data = {'operation': 'rename', 'newname': new_name}

        resp = self.client.post(self.url + '?p=' + old_file_path, data)
        self.assertEqual(403, resp.status_code)
Beispiel #6
0
    def handle_copy(self, dest_path, depth_infinity):
        if self.provider.readonly:
            raise DAVError(HTTP_FORBIDDEN)

        parts = dest_path.strip("/").split("/", 1)
        if len(parts) <= 1:
            raise DAVError(HTTP_BAD_REQUEST)
        repo_name = parts[0]
        rel_path = parts[1]

        dest_dir, dest_file = os.path.split(rel_path)
        dest_repo = getRepoByName(repo_name, self.username, self.org_id,
                                  self.is_guest)

        if seafile_api.check_permission_by_path(dest_repo.id, self.rel_path,
                                                self.username) != "rw":
            raise DAVError(HTTP_FORBIDDEN)

        src_dir, src_file = os.path.split(self.rel_path)
        if not src_file:
            raise DAVError(HTTP_BAD_REQUEST)

        if not seafile_api.is_valid_filename(dest_repo.id, dest_file):
            raise DAVError(HTTP_BAD_REQUEST)

        seafile_api.copy_file(self.repo.id, src_dir, src_file, dest_repo.id,
                              dest_dir, dest_file, self.username,
                              NEED_PROGRESS, SYNCHRONOUS)

        return True
    def handleCopy(self, destPath, depthInfinity):
        if self.provider.readonly:
            raise DAVError(HTTP_FORBIDDEN)

        parts = destPath.strip("/").split("/", 1)
        if len(parts) <= 1:
            raise DAVError(HTTP_BAD_REQUEST)
        repo_name = parts[0]
        rel_path = parts[1]

        dest_dir, dest_file = os.path.split(rel_path)
        dest_repo = getRepoByName(repo_name, self.username, self.org_id, self.is_guest)

        if seafile_api.check_permission_by_path(dest_repo.id, self.rel_path, self.username) != "rw":
            raise DAVError(HTTP_FORBIDDEN)

        src_dir, src_file = os.path.split(self.rel_path)
        if not src_file:
            raise DAVError(HTTP_BAD_REQUEST)

        if not seafile_api.is_valid_filename(dest_repo.id, dest_file):
            raise DAVError(HTTP_BAD_REQUEST)

        seafile_api.copy_file(self.repo.id, src_dir, src_file,
                              dest_repo.id, dest_dir, dest_file, self.username, NEED_PROGRESS, SYNCHRONOUS)

        return True
    def create_empty_resource(self, name):
        """Create an empty (length-0) resource.

        See DAVResource.createEmptyResource()
        """
        assert not "/" in name
        if self.provider.readonly:
            raise DAVError(HTTP_FORBIDDEN)

        if seafile_api.check_permission_by_path(self.repo.id, self.rel_path, self.username) != "rw":
            raise DAVError(HTTP_FORBIDDEN)

        if seafile_api.check_quota(self.repo.id) < 0:
            raise DAVError(HTTP_FORBIDDEN, "The quota of the repo owner is exceeded")

        try:
            seafile_api.post_empty_file(self.repo.id, self.rel_path, name, self.username)
        except SearpcError as e:
            if e.msg == 'Invalid file name':
                raise DAVError(HTTP_BAD_REQUEST)
            raise

        # Repo was updated, can't use self.repo
        repo = seafile_api.get_repo(self.repo.id)
        if not repo:
            raise DAVError(HTTP_INTERNAL_ERROR)

        member_rel_path = "/".join([self.rel_path, name])
        member_path = "/".join([self.path, name])
        obj = resolveRepoPath(repo, member_rel_path)
        if not obj or not isinstance(obj, SeafFile):
            raise DAVError(HTTP_INTERNAL_ERROR)

        return SeafileResource(member_path, repo, member_rel_path, obj, self.environ)
Beispiel #9
0
    def test_rename_folder_with_invalid_folder_perm(self):

        if not LOCAL_PRO_DEV_ENV:
            return

        # share user's repo to admin with 'rw' permission
        seafile_api.share_repo(self.repo_id, self.user_name,
                self.admin_name, 'rw')

        # set sub-folder permisson as 'r' for admin
        seafile_api.add_folder_user_perm(self.repo_id,
                self.folder_path, 'r', self.admin_name)

        # admin can visit sub-folder with 'r' permission
        assert seafile_api.check_permission_by_path(self.repo_id,
                self.folder_path, self.admin_name) == 'r'

        # login as admin, then rename a 'r' permission folder
        self.login_as(self.admin)

        new_name = randstring(6)
        data = {'operation': 'rename', 'newname': new_name}

        resp = self.client.post(self.url + '?p=' + self.folder_path, data)
        self.assertEqual(403, resp.status_code)
Beispiel #10
0
def group_wiki_pages(request, group):
    """
    List wiki pages in group.
    """
    username = request.user.username
    try:
        repo = get_group_wiki_repo(group, username)
        pages = get_wiki_pages(repo)
    except SearpcError:
        return render_error(request, _('Internal Server Error'))
    except WikiDoesNotExist:
        return render_error(request, _('Wiki does not exists.'))

    if is_registered_user(username):
        repo_perm = seafile_api.check_permission_by_path(
            repo.id, '/', username)
    else:
        # when anonymous user visit public group wiki, set permission as 'r'
        repo_perm = 'r'

    mods_available = get_available_mods_by_group(group.id)
    mods_enabled = get_enabled_mods_by_group(group.id)

    return render_to_response("group/group_wiki_pages.html", {
        "group": group,
        "pages": pages,
        "is_staff": group.is_staff,
        "repo_id": repo.id,
        "search_repo_id": repo.id,
        "search_wiki": True,
        "repo_perm": repo_perm,
        "mods_enabled": mods_enabled,
        "mods_available": mods_available,
    },
                              context_instance=RequestContext(request))
    def handle_move(self, dest_path):
        if self.provider.readonly:
            raise DAVError(HTTP_FORBIDDEN)

        parts = dest_path.strip("/").split("/", 1)
        if len(parts) <= 1:
            raise DAVError(HTTP_BAD_REQUEST)
        repo_name = parts[0]
        rel_path = parts[1]

        dest_dir, dest_file = os.path.split(rel_path)
        dest_repo = getRepoByName(repo_name, self.username, self.org_id, self.is_guest)

        if seafile_api.check_permission_by_path(dest_repo.id, self.rel_path, self.username) != "rw":
            raise DAVError(HTTP_FORBIDDEN)

        src_dir, src_file = os.path.split(self.rel_path)
        if not src_file:
            raise DAVError(HTTP_BAD_REQUEST)

        if not seafile_api.is_valid_filename(dest_repo.id, dest_file):
            raise DAVError(HTTP_BAD_REQUEST)

        # some clients such as GoodReader requires "overwrite" semantics
        file_id_dest = seafile_api.get_file_id_by_path(dest_repo.id, rel_path)
        if file_id_dest != None:
            seafile_api.del_file(dest_repo.id, dest_dir, dest_file, self.username)

        seafile_api.move_file(self.repo.id, src_dir, src_file,
                              dest_repo.id, dest_dir, dest_file, 1, self.username, NEED_PROGRESS, SYNCHRONOUS)

        return True
Beispiel #12
0
def group_wiki_pages(request, group):
    """
    List wiki pages in group.
    """
    username = request.user.username
    try:
        repo = get_group_wiki_repo(group, username)
        pages = get_wiki_pages(repo)
    except SearpcError:
        return render_error(request, _('Internal Server Error'))
    except WikiDoesNotExist:
        return render_error(request, _('Wiki does not exists.'))

    if is_registered_user(username):
        repo_perm = seafile_api.check_permission_by_path(repo.id, '/', username)
    else:
        # when anonymous user visit public group wiki, set permission as 'r'
        repo_perm = 'r'

    mods_available = get_available_mods_by_group(group.id)
    mods_enabled = get_enabled_mods_by_group(group.id)

    return render_to_response("group/group_wiki_pages.html", {
            "group": group,
            "pages": pages,
            "is_staff": group.is_staff,
            "repo_id": repo.id,
            "search_repo_id": repo.id,
            "search_wiki": True,
            "repo_perm": repo_perm,
            "mods_enabled": mods_enabled,
            "mods_available": mods_available,
            }, context_instance=RequestContext(request))
Beispiel #13
0
    def test_delete_file_with_invalid_folder_perm(self):

        if not LOCAL_PRO_DEV_ENV:
            return

        # create a file in user repo sub-folder
        file_name = randstring(6)
        seafile_api.post_empty_file(repo_id=self.repo_id,
                parent_dir=self.folder_path, filename=file_name,
                username=self.user_name)

        # share user's repo to admin with 'rw' permission
        seafile_api.share_repo(self.repo_id, self.user_name,
                self.admin_name, 'rw')

        # set sub-folder permisson as 'r' for admin
        seafile_api.add_folder_user_perm(self.repo_id,
                self.folder_path, 'r', self.admin_name)

        # admin can visit file with 'r' permission
        file_path = posixpath.join(self.folder_path, file_name)
        assert seafile_api.check_permission_by_path(self.repo_id,
                file_path, self.admin_name) == 'r'

        # login as admin, then delete a 'r' permission file
        self.login_as(self.admin)

        resp = self.client.delete(self.url + '?p=' + file_path,
                {}, 'application/x-www-form-urlencoded')
        self.assertEqual(403, resp.status_code)
Beispiel #14
0
    def test_rename_file_with_invalid_folder_perm(self):

        if not LOCAL_PRO_DEV_ENV:
            return

        # create a file as old file in user repo sub-folder
        old_file_name = randstring(6)
        seafile_api.post_empty_file(repo_id=self.repo_id,
                                    parent_dir=self.folder_path,
                                    filename=old_file_name,
                                    username=self.user_name)

        # share user's repo to admin with 'rw' permission
        seafile_api.share_repo(self.repo_id, self.user_name, self.admin_name,
                               'rw')

        # set sub-folder permisson as 'r' for admin
        seafile_api.add_folder_user_perm(self.repo_id, self.folder_path, 'r',
                                         self.admin_name)

        # admin can visit old file with 'r' permission
        old_file_path = posixpath.join(self.folder_path, old_file_name)
        assert seafile_api.check_permission_by_path(self.repo_id,
                                                    old_file_path,
                                                    self.admin_name) == 'r'

        # login as admin, then rename a 'r' permission old file
        self.login_as(self.admin)

        new_name = randstring(6)
        data = {'operation': 'rename', 'newname': new_name}

        resp = self.client.post(self.url + '?p=' + old_file_path, data)
        self.assertEqual(403, resp.status_code)
Beispiel #15
0
def group_wiki_pages(request, group):
    """
    List wiki pages in group.
    """
    username = request.user.username
    try:
        repo = get_group_wiki_repo(group, username)
        pages = get_wiki_pages(repo)
    except SearpcError:
        return render_error(request, _("Internal Server Error"))
    except WikiDoesNotExist:
        return render_error(request, _("Wiki does not exists."))

    repo_perm = seafile_api.check_permission_by_path(repo.id, "/", username)
    mods_available = get_available_mods_by_group(group.id)
    mods_enabled = get_enabled_mods_by_group(group.id)

    return render_to_response(
        "group/group_wiki_pages.html",
        {
            "group": group,
            "pages": pages,
            "is_staff": group.is_staff,
            "repo_id": repo.id,
            "search_repo_id": repo.id,
            "search_wiki": True,
            "repo_perm": repo_perm,
            "mods_enabled": mods_enabled,
            "mods_available": mods_available,
        },
        context_instance=RequestContext(request),
    )
Beispiel #16
0
    def test_delete_file_with_invalid_folder_perm(self):

        if not LOCAL_PRO_DEV_ENV:
            return

        # create a file in user repo sub-folder
        file_name = randstring(6)
        seafile_api.post_empty_file(repo_id=self.repo_id,
                                    parent_dir=self.folder_path,
                                    filename=file_name,
                                    username=self.user_name)

        # share user's repo to admin with 'rw' permission
        seafile_api.share_repo(self.repo_id, self.user_name, self.admin_name,
                               'rw')

        # set sub-folder permisson as 'r' for admin
        seafile_api.add_folder_user_perm(self.repo_id, self.folder_path, 'r',
                                         self.admin_name)

        # admin can visit file with 'r' permission
        file_path = posixpath.join(self.folder_path, file_name)
        assert seafile_api.check_permission_by_path(self.repo_id, file_path,
                                                    self.admin_name) == 'r'

        # login as admin, then delete a 'r' permission file
        self.login_as(self.admin)

        resp = self.client.delete(self.url + '?p=' + file_path, {},
                                  'application/x-www-form-urlencoded')
        self.assertEqual(403, resp.status_code)
Beispiel #17
0
    def test_delete_user_share(self):
        self.share_repo_to_user()

        # admin user can view repo
        assert seafile_api.check_permission_by_path(
                self.repo_id, '/', self.admin_name) == 'rw'

        self.login_as(self.user)

        args = '?share_type=personal&user=%s' % self.admin_name
        url = reverse('api-v2.1-shared-repo', args=[self.repo_id]) + args
        resp = self.client.delete(url, {}, 'application/x-www-form-urlencoded')

        self.assertEqual(200, resp.status_code)

        # admin user can NOT view repo
        assert seafile_api.check_permission_by_path(
                self.repo_id, '/', self.admin_name) == None
Beispiel #18
0
    def test_delete_user_share(self):
        self.share_repo_to_user()

        # admin user can view repo
        assert seafile_api.check_permission_by_path(self.repo_id, '/',
                                                    self.admin_name) == 'rw'

        self.login_as(self.user)

        args = '?share_type=personal&user=%s' % self.admin_name
        url = reverse('api-v2.1-shared-repo', args=[self.repo_id]) + args
        resp = self.client.delete(url, {}, 'application/x-www-form-urlencoded')

        self.assertEqual(200, resp.status_code)

        # admin user can NOT view repo
        assert seafile_api.check_permission_by_path(self.repo_id, '/',
                                                    self.admin_name) == None
Beispiel #19
0
    def test_delete_repo_user_share_permission(self):

        # user share repo to tmp user
        init_permission = 'rw'
        seafile_api.share_repo(self.repo_id,
                self.user_name, self.tmp_user_email, init_permission)

        assert seafile_api.check_permission_by_path(self.repo_id, \
                '/', self.tmp_user_email) == init_permission

        self.login_as(self.admin)

        data = 'repo_id=%s&share_type=%s&share_to=%s' % \
                (self.repo_id, 'user', self.tmp_user_email)
        resp = self.client.delete(self.url, data, 'application/x-www-form-urlencoded')
        self.assertEqual(200, resp.status_code)

        assert seafile_api.check_permission_by_path(self.repo_id, \
                '/', self.tmp_user_email) is None
Beispiel #20
0
    def test_delete_repo_user_share_permission(self):

        # user share repo to tmp user
        init_permission = 'rw'
        seafile_api.share_repo(self.repo_id,
                self.user_name, self.tmp_user_email, init_permission)

        assert seafile_api.check_permission_by_path(self.repo_id, \
                '/', self.tmp_user_email) == init_permission

        self.login_as(self.admin)

        data = 'repo_id=%s&share_type=%s&share_to=%s' % \
                (self.repo_id, 'user', self.tmp_user_email)
        resp = self.client.delete(self.url, data, 'application/x-www-form-urlencoded')
        self.assertEqual(200, resp.status_code)

        assert seafile_api.check_permission_by_path(self.repo_id, \
                '/', self.tmp_user_email) is None
Beispiel #21
0
    def put(self, request, token):
        """ This api only used for refresh OnlineOffice lock
        when user edit office file via share link.

        Permission checking:
        1, If enable SHARE_LINK_LOGIN_REQUIRED, user must have been authenticated.
        2, Share link should have can_edit permission.
        3, File must have been locked by OnlineOffice.
        """

        if SHARE_LINK_LOGIN_REQUIRED and \
                not request.user.is_authenticated():
            error_msg = 'Permission denied.'
            return api_error(status.HTTP_403_FORBIDDEN, error_msg)

        try:
            share_link = FileShare.objects.get(token=token)
        except FileShare.DoesNotExist:
            error_msg = 'Share link %s not found.' % token
            return api_error(status.HTTP_404_NOT_FOUND, error_msg)

        if share_link.is_expired():
            error_msg = 'Share link %s is expired.' % token
            return api_error(status.HTTP_400_BAD_REQUEST, error_msg)

        shared_by = share_link.username
        repo_id = share_link.repo_id
        path = normalize_file_path(share_link.path)
        parent_dir = os.path.dirname(path)
        if seafile_api.check_permission_by_path(
                repo_id, parent_dir, shared_by) != PERMISSION_READ_WRITE:
            error_msg = 'Permission denied.'
            return api_error(status.HTTP_403_FORBIDDEN, error_msg)

        permissions = share_link.get_permissions()
        can_edit = permissions['can_edit']
        if not can_edit:
            error_msg = 'Share link %s has no edit permission.' % token
            return api_error(status.HTTP_403_FORBIDDEN, error_msg)

        locked_by_online_office = if_locked_by_online_office(repo_id, path)
        if locked_by_online_office:
            # refresh lock file
            try:
                seafile_api.refresh_file_lock(repo_id, path)
            except SearpcError as e:
                logger.error(e)
                error_msg = 'Internal Server Error'
                return api_error(status.HTTP_500_INTERNAL_SERVER_ERROR,
                                 error_msg)
        else:
            error_msg = _("You can not refresh this file's lock.")
            return api_error(status.HTTP_403_FORBIDDEN, error_msg)

        return Response({'success': True})
    def handle_delete(self):
        if self.provider.readonly:
            raise DAVError(HTTP_FORBIDDEN)

        if seafile_api.check_permission_by_path(self.repo.id, self.rel_path, self.username) != "rw":
            raise DAVError(HTTP_FORBIDDEN)

        parent, filename = os.path.split(self.rel_path)
        seafile_api.del_file(self.repo.id, parent, filename, self.username)

        return True
    def handleDelete(self):
        if self.provider.readonly:
            raise DAVError(HTTP_FORBIDDEN)

        if seafile_api.check_permission_by_path(self.repo.id, self.rel_path, self.username) != "rw":
            raise DAVError(HTTP_FORBIDDEN)

        parent, filename = os.path.split(self.rel_path)
        seafile_api.del_file(self.repo.id, parent, filename, self.username)

        return True
Beispiel #24
0
    def get(self, request, repo_id, format=None):
        # list dir
        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)

        path = request.GET.get('p', '/')
        if path[-1] != '/':
            path = path + '/'

        try:
            dir_id = seafile_api.get_dir_id_by_path(repo_id, path)
        except SearpcError as e:
            logger.error(e)
            error_msg = 'Internal Server Error'
            return api_error(status.HTTP_500_INTERNAL_SERVER_ERROR, error_msg)

        if not dir_id:
            error_msg = 'Folder %s not found.' % path
            return api_error(status.HTTP_404_NOT_FOUND, error_msg)

        if check_folder_permission(request, repo_id, path) is None:
            error_msg = 'Permission denied.'
            return api_error(status.HTTP_403_FORBIDDEN, error_msg)

        old_oid = request.GET.get('oid', None)
        if old_oid and old_oid == dir_id:
            resp = Response({'success': True})
            resp["oid"] = dir_id
            return resp
        else:
            request_type = request.GET.get('t', None)
            if request_type and request_type not in ('f', 'd'):
                error_msg = "'t'(type) should be 'f' or 'd'."
                return api_error(status.HTTP_400_BAD_REQUEST, error_msg)

            if request_type == 'd':
                recursive = request.GET.get('recursive', '0')
                if recursive not in ('1', '0'):
                    error_msg = "If you want to get recursive dir entries, you should set 'recursive' argument as '1'."
                    return api_error(status.HTTP_400_BAD_REQUEST, error_msg)

                if recursive == '1':
                    username = request.user.username
                    dir_list = get_dir_recursively(username, repo_id, path, [])
                    dir_list.sort(lambda x, y: cmp(x['name'].lower(), y['name'].lower()))

                    resp = Response(dir_list)
                    resp["oid"] = dir_id
                    resp["dir_perm"] = seafile_api.check_permission_by_path(repo_id, path, username)
                    return resp

            return get_dir_entrys_by_id(request, repo, path, dir_id, request_type)
Beispiel #25
0
    def test_reshare_to_user_after_transfer_repo(self):

        tmp_user = '******'
        User.objects.create_user(tmp_user)

        # share user's repo to tmp_user with 'rw' permission
        seafile_api.share_repo(self.user_repo_id, self.user.username,
                tmp_user, 'rw')

        assert seafile_api.check_permission_by_path(self.user_repo_id,
                '/', tmp_user) == 'rw'

        self.login_as(self.user)

        url = reverse("api2-repo-owner", args=[self.user_repo_id])
        data = 'owner=%s' % self.admin.email

        resp = self.client.put(url, data, 'application/x-www-form-urlencoded')
        self.assertEqual(200, resp.status_code)

        assert seafile_api.check_permission_by_path(self.user_repo_id,
                '/', tmp_user) == 'rw'
Beispiel #26
0
    def test_reshare_to_user_after_transfer_repo(self):

        tmp_user = '******'
        User.objects.create_user(tmp_user)

        # share user's repo to tmp_user with 'rw' permission
        seafile_api.share_repo(self.user_repo_id, self.user.username,
                tmp_user, 'rw')

        assert seafile_api.check_permission_by_path(self.user_repo_id,
                '/', tmp_user) == 'rw'

        self.login_as(self.user)

        url = reverse("api2-repo-owner", args=[self.user_repo_id])
        data = 'owner=%s' % self.admin.email

        resp = self.client.put(url, data, 'application/x-www-form-urlencoded')
        self.assertEqual(200, resp.status_code)

        assert seafile_api.check_permission_by_path(self.user_repo_id,
                '/', tmp_user) == 'rw'
Beispiel #27
0
    def set_user_folder_rw_permission_to_admin(self):

        # share user's repo to admin with 'r' permission
        seafile_api.share_repo(self.repo.id, self.user.username,
                self.admin.username, 'r')

        # set user sub-folder 'rw' permisson to admin
        seafile_api.add_folder_user_perm(self.repo.id,
                self.folder, 'rw', self.admin.username)

        # admin can visit user sub-folder with 'rw' permission
        assert seafile_api.check_permission_by_path(self.repo.id,
                self.folder, self.admin.username) == 'rw'
Beispiel #28
0
    def post(self, request, repo_id, format=None):
        """Post a participant of a file.
        """
        # argument check
        path = request.data.get('path')
        if not path:
            return api_error(status.HTTP_400_BAD_REQUEST, 'path invalid.')
        path = normalize_file_path(path)

        email = request.data.get('email')
        if not email or not is_valid_username(email):
            return api_error(status.HTTP_400_BAD_REQUEST, 'email invalid.')

        # resource check
        file_id = seafile_api.get_file_id_by_path(repo_id, path)
        if not file_id:
            return api_error(status.HTTP_404_NOT_FOUND,
                             'File %s not found.' % path)

        try:
            user = User.objects.get(email=email)
        except User.DoesNotExist:
            return api_error(status.HTTP_404_NOT_FOUND,
                             'User %s not found.' % email)

        # permission check
        if not check_folder_permission(request, repo_id, '/'):
            return api_error(status.HTTP_403_FORBIDDEN, 'Permission denied.')

        if not seafile_api.check_permission_by_path(repo_id, '/',
                                                    user.username):
            return api_error(status.HTTP_403_FORBIDDEN,
                             _('%s Permission denied.') % email)

        # main
        try:
            file_uuid = FileUUIDMap.objects.get_or_create_fileuuidmap_by_path(
                repo_id, path, False)

            if FileParticipant.objects.get_participant(file_uuid, email):
                return api_error(status.HTTP_409_CONFLICT,
                                 _('Participant %s already exists.') % email)

            FileParticipant.objects.add_participant(file_uuid, email)
            participant = get_user_common_info(email)
        except Exception as e:
            logger.error(e)
            return api_error(status.HTTP_500_INTERNAL_SERVER_ERROR,
                             'Internal Server Error.')

        return Response(participant, status=201)
Beispiel #29
0
def check_folder_permission(request, repo_id, path):
    """Check repo/folder/file access permission of a user, always return 'rw'
    when repo is system repo and user is admin.

    Arguments:
    - `request`:
    - `repo_id`:
    - `path`:
    """
    username = request.user.username
    if request.user.is_staff and get_system_default_repo_id() == repo_id:
        return 'rw'

    return seafile_api.check_permission_by_path(repo_id, path, username)
Beispiel #30
0
    def test_update_perm_if_not_owner(self):
        self.share_repo_to_user()

        # admin can view repo but NOT owner
        assert seafile_api.check_permission_by_path(self.repo_id, '/',
                                                    self.admin_name) == 'rw'

        self.login_as(self.admin)

        url = reverse('api-v2.1-shared-repo', args=[self.repo_id])
        data = 'permission=r&share_type=personal'
        resp = self.client.put(url, data, 'application/x-www-form-urlencoded')

        self.assertEqual(403, resp.status_code)
Beispiel #31
0
    def test_update_perm_if_not_owner(self):
        self.share_repo_to_user()

        # admin can view repo but NOT owner
        assert seafile_api.check_permission_by_path(
                self.repo_id, '/', self.admin_name) == 'rw'

        self.login_as(self.admin)

        url = reverse('api-v2.1-shared-repo', args=[self.repo_id])
        data = 'permission=r&share_type=personal'
        resp = self.client.put(url, data, 'application/x-www-form-urlencoded')

        self.assertEqual(403, resp.status_code)
Beispiel #32
0
def check_folder_permission(request, repo_id, path):
    """Check repo/folder/file access permission of a user, always return 'rw'
    when repo is system repo and user is admin.

    Arguments:
    - `request`:
    - `repo_id`:
    - `path`:
    """
    username = request.user.username
    if request.user.is_staff and get_system_default_repo_id() == repo_id:
        return 'rw'

    return seafile_api.check_permission_by_path(repo_id, path, username)
Beispiel #33
0
def view_shared_upload_link(request, uploadlink):
    token = uploadlink.token

    password_check_passed, err_msg = check_share_link_common(request,
                                                             uploadlink,
                                                             is_upload_link=True)
    if not password_check_passed:
        d = {'token': token, 'view_name': 'view_shared_upload_link', 'err_msg': err_msg}
        return render(request, 'share_access_validation.html', d)

    username = uploadlink.username
    repo_id = uploadlink.repo_id
    repo = get_repo(repo_id)
    if not repo:
        raise Http404

    path = uploadlink.path
    if path == '/':
        # use repo name as dir name if share whole library
        dir_name = repo.name
    else:
        dir_name = os.path.basename(path[:-1])

    repo = get_repo(repo_id)
    if not repo:
        raise Http404

    if repo.encrypted or \
            seafile_api.check_permission_by_path(repo_id, '/', username) != 'rw':
        return render_error(request, _('Permission denied'))

    uploadlink.view_cnt = F('view_cnt') + 1
    uploadlink.save()

    no_quota = True if seaserv.check_quota(repo_id) < 0 else False

    return render(request, 'view_shared_upload_link_react.html', {
    #return render(request, 'view_shared_upload_link.html', {
            'repo': repo,
            'path': path,
            'username': username,
            'dir_name': dir_name,
            'max_upload_file_size': seaserv.MAX_UPLOAD_FILE_SIZE,
            'no_quota': no_quota,
            'uploadlink': uploadlink,
            'enable_upload_folder': ENABLE_UPLOAD_FOLDER,
            'enable_resumable_fileupload': ENABLE_RESUMABLE_FILEUPLOAD,
            'max_number_of_files_for_fileupload': MAX_NUMBER_OF_FILES_FOR_FILEUPLOAD,
            })
Beispiel #34
0
    def put(self, request, token):
        """ This api only used for refresh OnlineOffice lock
        when user edit office file via share link.

        Permission checking:
        1, If enable SHARE_LINK_LOGIN_REQUIRED, user must have been authenticated.
        2, Share link should have can_edit permission.
        3, File must have been locked by OnlineOffice.
        """

        if SHARE_LINK_LOGIN_REQUIRED and \
                not request.user.is_authenticated():
            error_msg = 'Permission denied.'
            return api_error(status.HTTP_403_FORBIDDEN, error_msg)

        try:
            share_link = FileShare.objects.get(token=token)
        except FileShare.DoesNotExist:
            error_msg = 'Share link %s not found.' % token
            return api_error(status.HTTP_404_NOT_FOUND, error_msg)

        if share_link.is_expired():
            error_msg = 'Share link %s is expired.' % token
            return api_error(status.HTTP_400_BAD_REQUEST, error_msg)

        shared_by = share_link.username
        repo_id = share_link.repo_id
        path = normalize_file_path(share_link.path)
        parent_dir = os.path.dirname(path)
        if seafile_api.check_permission_by_path(repo_id,
                parent_dir, shared_by) != PERMISSION_READ_WRITE:
            error_msg = 'Permission denied.'
            return api_error(status.HTTP_403_FORBIDDEN, error_msg)

        permissions = share_link.get_permissions()
        can_edit = permissions['can_edit']
        if not can_edit:
            error_msg = 'Share link %s has no edit permission.' % token
            return api_error(status.HTTP_403_FORBIDDEN, error_msg)

        locked_by_online_office = if_locked_by_online_office(repo_id, path)
        if locked_by_online_office:
            # refresh lock file
            try:
                seafile_api.refresh_file_lock(repo_id, path)
            except SearpcError, e:
                logger.error(e)
                error_msg = 'Internal Server Error'
                return api_error(status.HTTP_500_INTERNAL_SERVER_ERROR, error_msg)
Beispiel #35
0
    def get(self, request, token):
        """ Get file upload url according to upload link token.

        Permission checking:
        1. anyone has the upload link token can perform this action;
        """

        try:
            uls = UploadLinkShare.objects.get(token=token)
        except UploadLinkShare.DoesNotExist:
            error_msg = 'token %s not found.' % token
            return api_error(status.HTTP_404_NOT_FOUND, error_msg)

        # currently not support encrypted upload link
        if uls.is_encrypted():
            error_msg = 'Upload link %s is encrypted.' % token
            return api_error(status.HTTP_403_FORBIDDEN, error_msg)

        repo_id = uls.repo_id
        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)

        path = uls.path
        dir_id = seafile_api.get_dir_id_by_path(repo_id, path)
        if not dir_id:
            error_msg = 'Folder %s not found.' % path
            return api_error(status.HTTP_404_NOT_FOUND, error_msg)

        if repo.encrypted or \
                seafile_api.check_permission_by_path(repo_id, '/', uls.username) != 'rw':
            error_msg = 'Permission denied.'
            return api_error(status.HTTP_403_FORBIDDEN, error_msg)

        obj_id = json.dumps({'parent_dir': path})
        token = seafile_api.get_fileserver_access_token(repo_id,
                                                        obj_id,
                                                        'upload-link',
                                                        uls.username,
                                                        use_onetime=False)

        if not token:
            error_msg = 'Internal Server Error'
            return api_error(status.HTTP_500_INTERNAL_SERVER_ERROR, error_msg)

        result = {}
        result['upload_link'] = gen_file_upload_url(token, 'upload-api')
        return Response(result)
    def test_unshare_with_invalid_ownership(self):

        self.share_repo_to_user_and_group()

        # admin can visit user sub-folder with 'rw' permission
        assert seafile_api.check_permission_by_path(self.repo.id,
                '/', self.admin.username) == 'rw'

        self.login_as(self.admin)

        resp = self.client.delete('/api2/repos/%s/dir/shared_items/?p=/&share_type=user&username=%s' % (
            self.repo.id,
            self.admin.username
        ))
        self.assertEqual(403, resp.status_code)
Beispiel #37
0
def get_folder_permission_recursively(username, repo_id, path):
    """ Get folder permission recursively

    Ger permission from the innermost layer of subdirectories to root
    directory.
    """
    if not path or not isinstance(path, basestring):
        raise Exception('path invalid.')

    if not seafile_api.get_dir_id_by_path(repo_id, path):
        # get current folder's parent directory
        path = os.path.dirname(path.rstrip('/'))
        return get_folder_permission_recursively(username, repo_id, path)
    else:
        return seafile_api.check_permission_by_path(repo_id, path, username)
Beispiel #38
0
def view_shared_upload_link(request, uploadlink):
    token = uploadlink.token

    password_check_passed, err_msg = check_share_link_common(request,
                                                             uploadlink,
                                                             is_upload_link=True)
    if not password_check_passed:
        d = {'token': token, 'view_name': 'view_shared_upload_link', 'err_msg': err_msg}
        return render(request, 'share_access_validation.html', d)

    username = uploadlink.username
    repo_id = uploadlink.repo_id
    repo = get_repo(repo_id)
    if not repo:
        raise Http404

    path = uploadlink.path
    if path == '/':
        # use repo name as dir name if share whole library
        dir_name = repo.name
    else:
        dir_name = os.path.basename(path[:-1])

    repo = get_repo(repo_id)
    if not repo:
        raise Http404

    if repo.encrypted or \
            seafile_api.check_permission_by_path(repo_id, '/', username) != 'rw':
        return render_error(request, _(u'Permission denied'))

    uploadlink.view_cnt = F('view_cnt') + 1
    uploadlink.save()

    no_quota = True if seaserv.check_quota(repo_id) < 0 else False

    return render(request, 'view_shared_upload_link.html', {
            'repo': repo,
            'path': path,
            'username': username,
            'dir_name': dir_name,
            'max_upload_file_size': seaserv.MAX_UPLOAD_FILE_SIZE,
            'no_quota': no_quota,
            'uploadlink': uploadlink,
            'enable_upload_folder': ENABLE_UPLOAD_FOLDER,
            'enable_resumable_fileupload': ENABLE_RESUMABLE_FILEUPLOAD,
            'max_number_of_files_for_fileupload': MAX_NUMBER_OF_FILES_FOR_FILEUPLOAD,
            })
    def test_share_with_invalid_ownership(self):

        self.share_repo_to_user_and_group()

        # admin can visit user sub-folder with 'rw' permission
        assert seafile_api.check_permission_by_path(self.repo.id,
                '/', self.admin.username) == 'rw'

        self.login_as(self.admin)

        resp = self.client.put(
            '/api2/repos/%s/dir/shared_items/?p=/' % self.repo.id,
            "share_type=user&username=%s" % self.admin.username,
            'application/x-www-form-urlencoded',
        )
        self.assertEqual(403, resp.status_code)
    def create_collection(self, name):
        """Create a new collection as member of self.

        See DAVResource.createCollection()
        """
        assert not "/" in name
        if self.provider.readonly:
            raise DAVError(HTTP_FORBIDDEN)

        if seafile_api.check_permission_by_path(self.repo.id, self.rel_path, self.username) != "rw":
            raise DAVError(HTTP_FORBIDDEN)

        if not seafile_api.is_valid_filename(self.repo.id, name):
            raise DAVError(HTTP_BAD_REQUEST)

        seafile_api.post_dir(self.repo.id, self.rel_path, name, self.username)
    def createCollection(self, name):
        """Create a new collection as member of self.

        See DAVResource.createCollection()
        """
        assert not "/" in name
        if self.provider.readonly:
            raise DAVError(HTTP_FORBIDDEN)

        if seafile_api.check_permission_by_path(self.repo.id, self.rel_path, self.username) != "rw":
            raise DAVError(HTTP_FORBIDDEN)

        if not seafile_api.is_valid_filename(self.repo.id, name):
            raise DAVError(HTTP_BAD_REQUEST)

        seafile_api.post_dir(self.repo.id, self.rel_path, name, self.username)
Beispiel #42
0
    def get(self, request, token):
        """ Get file upload url according to upload link token.

        Permission checking:
        1. anyone has the upload link token can perform this action;
        """

        try:
            uls = UploadLinkShare.objects.get(token=token)
        except UploadLinkShare.DoesNotExist:
            error_msg = 'token %s not found.' % token
            return api_error(status.HTTP_404_NOT_FOUND, error_msg)

        # currently not support encrypted upload link
        if uls.is_encrypted():
            error_msg = 'Upload link %s is encrypted.' % token
            return api_error(status.HTTP_403_FORBIDDEN, error_msg)

        repo_id = uls.repo_id
        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)

        path = uls.path
        dir_id = seafile_api.get_dir_id_by_path(repo_id, path)
        if not dir_id:
            error_msg = 'Folder %s not found.' % path
            return api_error(status.HTTP_404_NOT_FOUND, error_msg)

        if repo.encrypted or \
                seafile_api.check_permission_by_path(repo_id, '/', uls.username) != 'rw':
            error_msg = 'Permission denied.'
            return api_error(status.HTTP_403_FORBIDDEN, error_msg)

        token = seafile_api.get_fileserver_access_token(repo_id,
                dir_id, 'upload-link', uls.username, use_onetime=False)

        if not token:
            error_msg = 'Internal Server Error'
            return api_error(status.HTTP_500_INTERNAL_SERVER_ERROR, error_msg)

        result = {}
        result['upload_link'] = gen_file_upload_url(token, 'upload-api')
        return Response(result)
    def beginWrite(self, contentType=None, isnewfile=True, contentlength=-1):
        """Open content as a stream for writing.

        See DAVResource.beginWrite()
        """
        assert not self.isCollection
        if self.provider.readonly:
            raise DAVError(HTTP_FORBIDDEN)

        if seafile_api.check_permission_by_path(self.repo.id, self.rel_path, self.username) != "rw":
            raise DAVError(HTTP_FORBIDDEN)

        if not self.check_repo_owner_quota(isnewfile, contentlength):
            raise DAVError(HTTP_FORBIDDEN, "The quota of the repo owner is exceeded")

        fd, path = tempfile.mkstemp(dir=self.provider.tmpdir)
        self.tmpfile_path = path
        return os.fdopen(fd, "wb")
    def begin_write(self, content_type=None, isnewfile=True, contentlength=-1):
        """Open content as a stream for writing.

        See DAVResource.beginWrite()
        """
        assert not self.is_collection
        if self.provider.readonly:
            raise DAVError(HTTP_FORBIDDEN)

        if seafile_api.check_permission_by_path(self.repo.id, self.rel_path, self.username) != "rw":
            raise DAVError(HTTP_FORBIDDEN)

        if not self.check_repo_owner_quota(isnewfile, contentlength):
            raise DAVError(HTTP_FORBIDDEN, "The quota of the repo owner is exceeded")

        fd, path = tempfile.mkstemp(dir=self.provider.tmpdir)
        self.tmpfile_path = path
        return os.fdopen(fd, "wb")
    def createEmptyResource(self, name):
        """Create an empty (length-0) resource.

        See DAVResource.createEmptyResource()
        """
        assert not "/" in name
        if self.provider.readonly:
            raise DAVError(HTTP_FORBIDDEN)

        if seafile_api.check_permission_by_path(self.repo.id, self.rel_path, self.username) != "rw":
            raise DAVError(HTTP_FORBIDDEN)

        if check_repo_quota(self.repo.id) < 0:
            raise DAVError(HTTP_FORBIDDEN, "The quota of the repo owner is exceeded")

        try:
            seafile_api.post_empty_file(self.repo.id, self.rel_path, name, self.username)
        except SearpcError, e:
            if e.msg == 'Invalid file name':
                raise DAVError(HTTP_BAD_REQUEST)
            raise
Beispiel #46
0
    def test_modify_repo_user_share_permission_to_admin(self):

        # user share repo to tmp user
        init_permission = 'rw'
        seafile_api.share_repo(self.repo_id,
                self.user_name, self.tmp_user_email, init_permission)

        assert seafile_api.check_permission_by_path(self.repo_id, \
                '/', self.tmp_user_email) == init_permission

        self.login_as(self.admin)

        modified_perm = 'admin'
        data = 'repo_id=%s&share_type=%s&permission=%s&share_to=%s' % \
                (self.repo_id, 'user', modified_perm, self.tmp_user_email)
        resp = self.client.put(self.url, data, 'application/x-www-form-urlencoded')
        self.assertEqual(200, resp.status_code)

        json_resp = json.loads(resp.content)
        assert json_resp['permission'] == 'rw'
        assert json_resp['is_admin'] == True
        assert json_resp['user_email'] == self.tmp_user_email
Beispiel #47
0
    def test_copy_file_with_invalid_dst_folder_perm(self):

        if not LOCAL_PRO_DEV_ENV:
            return

        # share user's repo to admin with 'rw' permission
        seafile_api.share_repo(self.repo_id, self.user_name, self.admin_name,
                               'rw')

        # set sub-folder permisson as 'r' for admin
        seafile_api.add_folder_user_perm(self.repo_id, self.folder_path, 'r',
                                         self.admin_name)

        # admin can visit sub-folder with 'r' permission
        assert seafile_api.check_permission_by_path(self.repo_id,
                                                    self.folder_path,
                                                    self.admin_name) == 'r'

        # create a file for admin repo
        admin_repo_id = self.admin_create_new_repo()
        admin_file_name = randstring(6)
        seafile_api.post_empty_file(repo_id=admin_repo_id,
                                    parent_dir='/',
                                    filename=admin_file_name,
                                    username=self.admin_name)

        # login as admin, then move file to a 'r' permission folder
        self.login_as(self.admin)

        # create new repo for admin
        data = {
            'operation': 'copy',
            'dst_repo': self.repo_id,
            'dst_dir': self.folder_path,
        }

        url = reverse('api-v2.1-file-view', args=[admin_repo_id])
        resp = self.client.post(url + '?p=/' + admin_file_name, data)
        self.assertEqual(403, resp.status_code)
Beispiel #48
0
    def test_delete_folder_with_invalid_folder_perm(self):

        if not LOCAL_PRO_DEV_ENV:
            return

        # share user's repo to admin with 'rw' permission
        seafile_api.share_repo(self.repo_id, self.user_name,
                self.admin_name, 'rw')

        # set sub-folder permisson as 'r' for admin
        seafile_api.add_folder_user_perm(self.repo_id,
                self.folder_path, 'r', self.admin_name)

        # admin can visit sub-folder with 'r' permission
        assert seafile_api.check_permission_by_path(self.repo_id,
                self.folder_path, self.admin_name) == 'r'

        # login as admin, then delete a 'r' permission folder
        self.login_as(self.admin)

        resp = self.client.delete(self.url + '?p=' + self.folder_path,
                {}, 'application/x-www-form-urlencoded')
        self.assertEqual(403, resp.status_code)
Beispiel #49
0
    def test_copy_file_with_invalid_dst_folder_perm(self):

        if not LOCAL_PRO_DEV_ENV:
            return

        # share user's repo to admin with 'rw' permission
        seafile_api.share_repo(self.repo_id, self.user_name,
                self.admin_name, 'rw')

        # set sub-folder permisson as 'r' for admin
        seafile_api.add_folder_user_perm(self.repo_id,
                self.folder_path, 'r', self.admin_name)

        # admin can visit sub-folder with 'r' permission
        assert seafile_api.check_permission_by_path(self.repo_id,
                self.folder_path, self.admin_name) == 'r'

        # create a file for admin repo
        admin_repo_id = self.admin_create_new_repo()
        admin_file_name = randstring(6)
        seafile_api.post_empty_file(repo_id=admin_repo_id,
                parent_dir='/', filename=admin_file_name,
                username=self.admin_name)

        # login as admin, then move file to a 'r' permission folder
        self.login_as(self.admin)

        # create new repo for admin
        data = {
            'operation': 'copy',
            'dst_repo': self.repo_id,
            'dst_dir': self.folder_path,
        }

        url = reverse('api-v2.1-file-view', args=[admin_repo_id])
        resp = self.client.post(url + '?p=/' + admin_file_name, data)
        self.assertEqual(403, resp.status_code)
    def delete(self, request, repo_id, format=None):
        username = request.user.username
        repo = seafile_api.get_repo(repo_id)
        if not repo:
            return api_error(status.HTTP_404_NOT_FOUND, 'Library %s not found.' % repo_id)

        path = request.GET.get('p', '/')
        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)

        if username != self.get_repo_owner(request, repo_id):
            return api_error(status.HTTP_403_FORBIDDEN, 'Permission denied.')

        shared_to_user, shared_to_group = self.handle_shared_to_args(request)

        if path == '/':
            shared_repo = repo
        else:
            try:
                sub_repo = self.get_sub_repo_by_path(request, repo, path)
                if sub_repo:
                    shared_repo = sub_repo
                else:
                    return api_error(status.HTTP_404_NOT_FOUND, 'Sub-library not found.')
            except SearpcError as e:
                logger.error(e)
                return api_error(status.HTTP_500_INTERNAL_SERVER_ERROR, 'Failed to get sub-library.')

        if shared_to_user:
            shared_to = request.GET.get('username')
            if shared_to is None or not is_valid_username(shared_to):
                return api_error(status.HTTP_400_BAD_REQUEST, 'Email %s invalid.' % shared_to)

            try:
                User.objects.get(email=shared_to)
            except User.DoesNotExist:
                return api_error(status.HTTP_400_BAD_REQUEST, 'Invalid user, should be registered')

            if is_org_context(request):
                org_id = request.user.org.org_id
                seaserv.seafserv_threaded_rpc.org_remove_share(
                    org_id, shared_repo.id, username, shared_to)
            else:
                seaserv.remove_share(shared_repo.id, username, shared_to)

            permission = seafile_api.check_permission_by_path(repo.id, path,
                                                              shared_to)
            send_perm_audit_msg('delete-repo-perm', username, shared_to,
                                repo_id, path, permission)

        if shared_to_group:
            group_id = request.GET.get('group_id')
            try:
                group_id = int(group_id)
            except ValueError:
                return api_error(status.HTTP_400_BAD_REQUEST, 'group_id %s invalid' % group_id)

            # hacky way to get group repo permission
            permission = ''
            for e in seafile_api.list_repo_shared_group_by_user(username, shared_repo.id):
                if e.group_id == group_id:
                    permission = e.perm
                    break

            if is_org_context(request):
                org_id = request.user.org.org_id
                seaserv.del_org_group_repo(shared_repo.id, org_id, group_id)
            else:
                seafile_api.unset_group_repo(shared_repo.id, group_id, username)

            send_perm_audit_msg('delete-repo-perm', username, group_id,
                                repo_id, path, permission)

        return HttpResponse(json.dumps({'success': True}), status=200,
                            content_type=json_content_type)
Beispiel #51
0
    def delete(self, request, repo_id, format=None):
        """ Unshare a repo.

        Permission checking:
        1. Only repo owner can unshare a library.
        """

        # argument check
        share_type = request.GET.get('share_type', None)
        if not share_type:
            error_msg = 'share_type invalid.'
            return api_error(status.HTTP_400_BAD_REQUEST, error_msg)

        if share_type not in ('personal', 'group', 'public'):
            error_msg = "share_type can only be 'personal' or 'group' or 'public'."
            return api_error(status.HTTP_400_BAD_REQUEST, error_msg)

        # resource 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)

        # 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:
            error_msg = 'Permission denied.'
            return api_error(status.HTTP_403_FORBIDDEN, error_msg)

        # delete share
        org_id = None
        if is_org_context(request):
            org_id = request.user.org.org_id

        if share_type == 'personal':
            user = request.GET.get('user', None)
            if not user or not is_valid_username(user):
                error_msg = 'user invalid.'
                return api_error(status.HTTP_400_BAD_REQUEST, error_msg)

            # if user not found, permission will be None
            permission = seafile_api.check_permission_by_path(
                    repo_id, '/', user)

            try:
                if org_id:
                    seafile_api.org_remove_share(org_id, repo_id,
                                                 username, user)
                else:
                    seafile_api.remove_share(repo_id, username, user)
            except Exception as e:
                logger.error(e)
                error_msg = 'Internal Server Error'
                return api_error(status.HTTP_500_INTERNAL_SERVER_ERROR, error_msg)

            send_perm_audit_msg('delete-repo-perm', username, user,
                    repo_id, '/', permission)

        if share_type == 'group':
            group_id = request.GET.get('group_id', None)
            if not group_id:
                error_msg = 'group_id invalid.'
                return api_error(status.HTTP_400_BAD_REQUEST, error_msg)

            try:
                group_id = int(group_id)
            except ValueError:
                error_msg = 'group_id must be integer.'
                return api_error(status.HTTP_400_BAD_REQUEST, error_msg)

            # hacky way to get group repo permission
            permission = ''
            if org_id:
                for e in seafile_api.list_org_repo_shared_group(
                        org_id, username, repo_id):
                    if e.group_id == group_id:
                        permission = e.perm
                        break
            else:
                for e in seafile_api.list_repo_shared_group_by_user(username, repo_id):
                    if e.group_id == group_id:
                        permission = e.perm
                        break

            try:
                if org_id:
                    seaserv.del_org_group_repo(repo_id, org_id, group_id)
                else:
                    seafile_api.unset_group_repo(repo_id, group_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)

            send_perm_audit_msg('delete-repo-perm', username, group_id,
                                repo_id, '/', permission)

        if share_type == 'public':
            pub_repos = []
            if org_id:
                pub_repos = seaserv.list_org_inner_pub_repos(org_id, username)

            if not request.cloud_mode:
                pub_repos = seaserv.list_inner_pub_repos(username)

            try:
                if org_id:
                    seaserv.seafserv_threaded_rpc.unset_org_inner_pub_repo(org_id, repo_id)
                else:
                    seafile_api.remove_inner_pub_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)

            permission = ''
            for repo in pub_repos:
                if repo.repo_id == repo_id:
                    permission = repo.permission
                    break

            if permission:
                send_perm_audit_msg('delete-repo-perm', username, 'all', repo_id, '/', permission)

        return Response({'success': True})
Beispiel #52
0
    else:
        is_owner = False

    cur_path = path
    for commit in commits:
        commit.path = cur_path
        if commit.rev_renamed_old_path:
            cur_path = '/' + commit.rev_renamed_old_path

    zipped = gen_path_link(path, repo.name)

    can_revert_file = True
    username = request.user.username

    is_locked, locked_by_me = check_file_lock(repo_id, path, username)
    if seafile_api.check_permission_by_path(repo_id, path, username) != 'rw' or \
        (is_locked and not locked_by_me):
        can_revert_file = False

    return render_to_response('file_revisions.html', {
        'repo': repo,
        'path': path,
        'u_filename': u_filename,
        'zipped': zipped,
        'commits': commits,
        'is_owner': is_owner,
        'can_compare': can_compare,
        'can_revert_file': can_revert_file,
        'days': days,
        }, context_instance=RequestContext(request))