def test_txlog_when_renaming_a_directory(self):
        user = self.factory.make_user()
        current_parent = self.factory.make_directory(owner=user,
                                                     name='current-parent')
        dir1 = self.factory.make_directory(name='dir1', parent=current_parent)
        f = self.factory.make_file(name='f.jpg',
                                   parent=dir1,
                                   mimetype=self.mimetype)
        self.clear_txlogs()
        dir1_orig_path = dir1.full_path
        f_orig_path = f.full_path
        dir1.move(dir1.parent, 'new-name')

        # All TransactionLog entries created will have the moved directory's
        # generation because in a move() we only update the directory's
        # generation and not the generation of its descendants.
        f_expected_attrs = self._get_dict_with_txlog_attrs_from(
            f,
            TransactionLog.OP_MOVE,
            old_path=f_orig_path,
            generation=dir1.generation,
            extra_data_dict=TransactionLog.extra_data_new_node(f))
        dir_expected_attrs = self._get_dict_with_txlog_attrs_from(
            dir1,
            TransactionLog.OP_MOVE,
            old_path=dir1_orig_path,
            extra_data_dict=TransactionLog.extra_data_new_node(dir1))
        self.assertTransactionLogsMatch([f_expected_attrs, dir_expected_attrs])
    def test_bootstrap_picks_up_user(self):
        user = self.make_user_without_txlog()

        TransactionLog.bootstrap(user)

        txlog = TransactionLog.objects.get(
            op_type=TransactionLog.OP_USER_CREATED)
        self.assertTxLogDetailsMatchesUserDetails(user, txlog)
    def test_bootstrap_picks_up_user(self):
        user = self.make_user_without_txlog()

        TransactionLog.bootstrap(user)

        txlog = TransactionLog.objects.get(
            op_type=TransactionLog.OP_USER_CREATED)
        self.assertTxLogDetailsMatchesUserDetails(user, txlog)
    def test_bootstrap_picks_up_only_live_files(self):
        user = self.factory.make_user()
        photos = self._create_files_for_user(user, 'image/jpeg')
        # Even though all files in this second UDF are dead, the UDF itself is
        # alive so we will have a txlog for it.
        self._create_files_for_user(user, 'image/jpeg', status=STATUS_DEAD)

        TransactionLog.bootstrap(user)

        self.assertBootstrappingPickedUpFiles(user, photos)
    def test_bootstrap_picks_up_only_files_owned_by_the_given_user(self):
        user = self.factory.make_user()
        photos = self._create_files_for_user(user, 'image/jpeg')
        # These files do not belong to the user we're bootstrapping now, so
        # they won't show up on the TXLog.
        self._create_files_for_user(self.factory.make_user(), 'image/jpeg')

        TransactionLog.bootstrap(user)

        self.assertBootstrappingPickedUpFiles(user, photos)
    def test_bootstrap_picks_up_only_live_files(self):
        user = self.factory.make_user()
        photos = self._create_files_for_user(user, 'image/jpeg')
        # Even though all files in this second UDF are dead, the UDF itself is
        # alive so we will have a txlog for it.
        self._create_files_for_user(user, 'image/jpeg', status=STATUS_DEAD)

        TransactionLog.bootstrap(user)

        self.assertBootstrappingPickedUpFiles(user, photos)
    def test_bootstrap_picks_up_only_files_owned_by_the_given_user(self):
        user = self.factory.make_user()
        photos = self._create_files_for_user(user, 'image/jpeg')
        # These files do not belong to the user we're bootstrapping now, so
        # they won't show up on the TXLog.
        self._create_files_for_user(self.factory.make_user(), 'image/jpeg')

        TransactionLog.bootstrap(user)

        self.assertBootstrappingPickedUpFiles(user, photos)
    def test_bootstrap_picks_up_only_live_udfs(self):
        user = self.factory.make_user()
        live_udf = self.factory.make_user_volume(owner=user)
        live_udf2 = self.factory.make_user_volume(owner=user)
        self.factory.make_user_volume(owner=user, status=STATUS_DEAD)
        self.clear_txlogs()

        TransactionLog.bootstrap(user)

        self.assertBootstrappingPickedUpUDFs(
            user, [user.root_node.volume, live_udf, live_udf2])
    def test_bootstrap_picks_up_only_live_udfs(self):
        user = self.factory.make_user()
        live_udf = self.factory.make_user_volume(owner=user)
        live_udf2 = self.factory.make_user_volume(owner=user)
        self.factory.make_user_volume(owner=user, status=STATUS_DEAD)
        self.clear_txlogs()

        TransactionLog.bootstrap(user)

        self.assertBootstrappingPickedUpUDFs(
            user, [user.root_node.volume, live_udf, live_udf2])
    def test_bootstrap_picks_up_public_folders(self):
        user = self.factory.make_user()
        public_dir = self.factory.make_directory(user, public=True)
        self.factory.make_directory(user)
        self.clear_txlogs()
        public_url = public_dir.public_url
        self.assertIsNotNone(public_url)

        TransactionLog.bootstrap(user)

        self.assertBootstrappingPickedUpFolders(user, [public_dir])
    def test_bootstrap_picks_up_public_folders(self):
        user = self.factory.make_user()
        public_dir = self.factory.make_directory(user, public=True)
        self.factory.make_directory(user)
        self.clear_txlogs()
        public_url = public_dir.public_url
        self.assertIsNotNone(public_url)

        TransactionLog.bootstrap(user)

        self.assertBootstrappingPickedUpFolders(user, [public_dir])
    def test_bootstrap_picks_up_shares(self):
        user = self.factory.make_user()
        directory = self.factory.make_directory(user)
        share = self.factory.make_share(subtree=directory)
        self.clear_txlogs()

        TransactionLog.bootstrap(user)

        txlog = TransactionLog.objects.get(
            op_type=TransactionLog.OP_SHARE_ACCEPTED)
        expected_attrs = self._get_dict_with_txlog_attrs_from_share(
            share, TransactionLog.OP_SHARE_ACCEPTED)
        self.assert_txlog_correct(txlog, expected_attrs)
    def test_bootstrap_picks_up_shares(self):
        user = self.factory.make_user()
        directory = self.factory.make_directory(user)
        share = self.factory.make_share(subtree=directory)
        self.clear_txlogs()

        TransactionLog.bootstrap(user)

        txlog = TransactionLog.objects.get(
            op_type=TransactionLog.OP_SHARE_ACCEPTED)
        expected_attrs = self._get_dict_with_txlog_attrs_from_share(
            share, TransactionLog.OP_SHARE_ACCEPTED)
        self.assert_txlog_correct(txlog, expected_attrs)
    def test_bootstrap_picks_up_only_folders_in_live_udfs(self):
        user = self.factory.make_user()
        folder_in_root = self.factory.make_directory(
            owner=user, parent=user.root_node, name='folder1', public=True)
        dead_udf = self.factory.make_user_volume(owner=user)
        self.factory.make_directory(
            owner=user, parent=dead_udf.root_node, name='folder2', public=True)
        dead_udf.kill()
        self.clear_txlogs()

        TransactionLog.bootstrap(user)

        self.assertBootstrappingPickedUpFolders(user, [folder_in_root])
    def test_bootstrap_picks_up_only_files_in_live_udfs(self):
        user = self.factory.make_user()
        photo_in_root = self.factory.make_file(
            owner=user, parent=user.root_node, name='foo.jpg',
            mimetype='image/jpeg')
        dead_udf = self.factory.make_user_volume(owner=user)
        self.factory.make_file(
            owner=user, parent=dead_udf.root_node,
            name='foo-in-dead-udf.jpg', mimetype='image/jpeg')
        dead_udf.kill()
        self.clear_txlogs()

        TransactionLog.bootstrap(user)

        self.assertBootstrappingPickedUpFiles(user, [photo_in_root])
    def test_record_move_for_directory_with_indirect_children(self):
        # Create the following file structure:
        # root
        # |-- new-parent
        # |-- current-parent
        #     |-- dir1
        #         |-- f1.jpg
        #         |-- dir1.1
        #             |-- f11.jpg
        user = self.factory.make_user()
        parent = self.factory.make_directory(owner=user, name='current-parent')
        dir1 = self.factory.make_directory(name='dir1', parent=parent)
        dir11 = self.factory.make_directory(name='dir1.1', parent=dir1)
        f1 = self.factory.make_file(
            name='f1.jpg', parent=dir1, mimetype=self.mimetype)
        f11 = self.factory.make_file(
            name='f11.jpg', parent=dir11, mimetype=self.mimetype)
        nodes = [(dir1, dir1.full_path), (dir11, dir11.full_path),
                 (f1, f1.full_path), (f11, f11.full_path)]

        # Now move dir1 to new_parent.
        new_parent = self.factory.make_directory(owner=user, name='new-parent')
        self.clear_txlogs()

        dir1.move(new_parent, dir1.name)

        expected = [
            self._get_dict_with_txlog_attrs_from(
                node, TransactionLog.OP_MOVE,
                old_path=old_path, generation=dir1.generation,
                extra_data_dict=TransactionLog.extra_data_new_node(node))
            for node, old_path in nodes]
        self.assertTransactionLogsMatch(expected)
    def test_bootstrap_picks_up_only_files_in_live_udfs(self):
        user = self.factory.make_user()
        photo_in_root = self.factory.make_file(owner=user,
                                               parent=user.root_node,
                                               name='foo.jpg',
                                               mimetype='image/jpeg')
        dead_udf = self.factory.make_user_volume(owner=user)
        self.factory.make_file(owner=user,
                               parent=dead_udf.root_node,
                               name='foo-in-dead-udf.jpg',
                               mimetype='image/jpeg')
        dead_udf.kill()
        self.clear_txlogs()

        TransactionLog.bootstrap(user)

        self.assertBootstrappingPickedUpFiles(user, [photo_in_root])
    def test_bootstrap_picks_up_only_folders_in_live_udfs(self):
        user = self.factory.make_user()
        folder_in_root = self.factory.make_directory(owner=user,
                                                     parent=user.root_node,
                                                     name='folder1',
                                                     public=True)
        dead_udf = self.factory.make_user_volume(owner=user)
        self.factory.make_directory(owner=user,
                                    parent=dead_udf.root_node,
                                    name='folder2',
                                    public=True)
        dead_udf.kill()
        self.clear_txlogs()

        TransactionLog.bootstrap(user)

        self.assertBootstrappingPickedUpFolders(user, [folder_in_root])
    def test_txlog_for_content_change(self):
        node = self.factory.make_file(mimetype=self.mimetype)
        new_content = self.factory.make_content_blob()
        self.clear_txlogs()

        node.content = new_content

        extra_data = TransactionLog.extra_data_new_node(node)
        expected_attrs = self._get_dict_with_txlog_attrs_from(
            node, TransactionLog.OP_PUT_CONTENT, extra_data_dict=extra_data)
        self.assertTransactionLogsMatch([expected_attrs])
 def test_extra_data_new_node(self):
     """Check that extra_data_new_node includes all we need."""
     f = self.factory.make_file()
     f_extra_data = dict(
         size=f.content.size, storage_key=unicode(f.content.storage_key),
         public_uuid=None, content_hash=f.content_hash,
         when_created=get_epoch_secs(f.when_created),
         last_modified=get_epoch_secs(f.when_last_modified),
         kind=f.kind, volume_path=f.volume.path)
     expected = TransactionLog.extra_data_new_node(f)
     self.assertEqual(expected, f_extra_data)
    def test_txlog_for_content_change(self):
        node = self.factory.make_file(mimetype=self.mimetype)
        new_content = self.factory.make_content_blob()
        self.clear_txlogs()

        node.content = new_content

        extra_data = TransactionLog.extra_data_new_node(node)
        expected_attrs = self._get_dict_with_txlog_attrs_from(
            node, TransactionLog.OP_PUT_CONTENT, extra_data_dict=extra_data)
        self.assertTransactionLogsMatch([expected_attrs])
 def assertBootstrappingPickedUpFiles(self, user, files):
     """Check there are TXLog bootstrapping entries for the given files."""
     file_txlogs = TransactionLog.objects.filter(
         owner_id=user.id, op_type=TransactionLog.OP_PUT_CONTENT)
     expected = []
     for node in files:
         extra_data = TransactionLog.extra_data_new_node(node)
         expected.append(
             self._get_dict_with_txlog_attrs_from(
                 node, TransactionLog.OP_PUT_CONTENT,
                 generation=node.generation, extra_data_dict=extra_data))
     self.assertTransactionLogsMatch(expected, txlogs=file_txlogs)
 def assertBootstrappingPickedUpFolders(self, user, folders):
     """Check there are TXLog entries for the given folders."""
     folder_txlogs = TransactionLog.objects.filter(
         owner_id=user.id, op_type=TransactionLog.OP_PUBLIC_ACCESS_CHANGED)
     expected = []
     for folder in folders:
         extra_data = TransactionLog.extra_data_new_node(folder)
         expected.append(
             self._get_dict_with_txlog_attrs_from(
                 folder, TransactionLog.OP_PUBLIC_ACCESS_CHANGED,
                 extra_data_dict=extra_data))
     self.assertTransactionLogsMatch(expected, txlogs=folder_txlogs)
 def assertBootstrappingPickedUpFolders(self, user, folders):
     """Check there are TXLog entries for the given folders."""
     folder_txlogs = TransactionLog.objects.filter(
         owner_id=user.id, op_type=TransactionLog.OP_PUBLIC_ACCESS_CHANGED)
     expected = []
     for folder in folders:
         extra_data = TransactionLog.extra_data_new_node(folder)
         expected.append(
             self._get_dict_with_txlog_attrs_from(
                 folder,
                 TransactionLog.OP_PUBLIC_ACCESS_CHANGED,
                 extra_data_dict=extra_data))
     self.assertTransactionLogsMatch(expected, txlogs=folder_txlogs)
 def test_extra_data_new_node(self):
     """Check that extra_data_new_node includes all we need."""
     f = self.factory.make_file()
     f_extra_data = dict(size=f.content.size,
                         storage_key=unicode(f.content.storage_key),
                         public_uuid=None,
                         content_hash=f.content_hash,
                         when_created=get_epoch_secs(f.when_created),
                         last_modified=get_epoch_secs(f.when_last_modified),
                         kind=f.kind,
                         volume_path=f.volume.path)
     expected = TransactionLog.extra_data_new_node(f)
     self.assertEqual(expected, f_extra_data)
    def test_txlog_when_unpublishing_directory(self):
        directory = self.factory.make_directory(public=True)
        self.assertIsNotNone(directory.public_uuid)
        self.assertTrue(directory.is_public)
        self.clear_txlogs()

        directory.make_private()

        extra_data = TransactionLog.extra_data_new_node(directory)
        expected_attrs = self._get_dict_with_txlog_attrs_from(
            directory, TransactionLog.OP_PUBLIC_ACCESS_CHANGED,
            extra_data_dict=extra_data)
        self.assertTransactionLogsMatch([expected_attrs])
    def test_txlog_for_public_access_change_on_interesting_file(self):
        node = self.factory.make_file(mimetype=self.mimetype)
        self.clear_txlogs()

        node.make_public()

        public_url = node.public_url
        self.assertIsNotNone(public_url)
        extra_data = TransactionLog.extra_data_new_node(node)
        expected_attrs = self._get_dict_with_txlog_attrs_from(
            node, TransactionLog.OP_PUBLIC_ACCESS_CHANGED,
            extra_data_dict=extra_data)
        self.assertTransactionLogsMatch([expected_attrs])
 def assertBootstrappingPickedUpFiles(self, user, files):
     """Check there are TXLog bootstrapping entries for the given files."""
     file_txlogs = TransactionLog.objects.filter(
         owner_id=user.id, op_type=TransactionLog.OP_PUT_CONTENT)
     expected = []
     for node in files:
         extra_data = TransactionLog.extra_data_new_node(node)
         expected.append(
             self._get_dict_with_txlog_attrs_from(
                 node,
                 TransactionLog.OP_PUT_CONTENT,
                 generation=node.generation,
                 extra_data_dict=extra_data))
     self.assertTransactionLogsMatch(expected, txlogs=file_txlogs)
    def test_txlog_when_unpublishing_directory(self):
        directory = self.factory.make_directory(public=True)
        self.assertIsNotNone(directory.public_uuid)
        self.assertTrue(directory.is_public)
        self.clear_txlogs()

        directory.make_private()

        extra_data = TransactionLog.extra_data_new_node(directory)
        expected_attrs = self._get_dict_with_txlog_attrs_from(
            directory,
            TransactionLog.OP_PUBLIC_ACCESS_CHANGED,
            extra_data_dict=extra_data)
        self.assertTransactionLogsMatch([expected_attrs])
    def test_txlog_for_public_access_change_on_interesting_file(self):
        node = self.factory.make_file(mimetype=self.mimetype)
        self.clear_txlogs()

        node.make_public()

        public_url = node.public_url
        self.assertIsNotNone(public_url)
        extra_data = TransactionLog.extra_data_new_node(node)
        expected_attrs = self._get_dict_with_txlog_attrs_from(
            node,
            TransactionLog.OP_PUBLIC_ACCESS_CHANGED,
            extra_data_dict=extra_data)
        self.assertTransactionLogsMatch([expected_attrs])
    def test_txlog_when_moving_file(self):
        user = self.factory.make_user()
        dir1 = self.factory.make_directory(owner=user)
        dir2 = self.factory.make_directory(owner=user)
        f = self.factory.make_file(parent=dir1, mimetype=self.mimetype)
        orig_path = f.full_path
        self.clear_txlogs()

        f.move(dir2, f.name)

        expected_attrs = self._get_dict_with_txlog_attrs_from(
            f, TransactionLog.OP_MOVE, old_path=orig_path,
            extra_data_dict=TransactionLog.extra_data_new_node(f))
        self.assertTransactionLogsMatch([expected_attrs])
    def test_txlog_when_renaming_a_directory(self):
        user = self.factory.make_user()
        current_parent = self.factory.make_directory(
            owner=user, name='current-parent')
        dir1 = self.factory.make_directory(name='dir1', parent=current_parent)
        f = self.factory.make_file(
            name='f.jpg', parent=dir1, mimetype=self.mimetype)
        self.clear_txlogs()
        dir1_orig_path = dir1.full_path
        f_orig_path = f.full_path
        dir1.move(dir1.parent, 'new-name')

        # All TransactionLog entries created will have the moved directory's
        # generation because in a move() we only update the directory's
        # generation and not the generation of its descendants.
        f_expected_attrs = self._get_dict_with_txlog_attrs_from(
            f, TransactionLog.OP_MOVE, old_path=f_orig_path,
            generation=dir1.generation,
            extra_data_dict=TransactionLog.extra_data_new_node(f))
        dir_expected_attrs = self._get_dict_with_txlog_attrs_from(
            dir1, TransactionLog.OP_MOVE, old_path=dir1_orig_path,
            extra_data_dict=TransactionLog.extra_data_new_node(dir1))
        self.assertTransactionLogsMatch(
            [f_expected_attrs, dir_expected_attrs])
    def test_txlog_when_moving_file(self):
        user = self.factory.make_user()
        dir1 = self.factory.make_directory(owner=user)
        dir2 = self.factory.make_directory(owner=user)
        f = self.factory.make_file(parent=dir1, mimetype=self.mimetype)
        orig_path = f.full_path
        self.clear_txlogs()

        f.move(dir2, f.name)

        expected_attrs = self._get_dict_with_txlog_attrs_from(
            f,
            TransactionLog.OP_MOVE,
            old_path=orig_path,
            extra_data_dict=TransactionLog.extra_data_new_node(f))
        self.assertTransactionLogsMatch([expected_attrs])
    def test_record_move_for_directory_with_indirect_children(self):
        # Create the following file structure:
        # root
        # |-- new-parent
        # |-- current-parent
        #     |-- dir1
        #         |-- f1.jpg
        #         |-- dir1.1
        #             |-- f11.jpg
        user = self.factory.make_user()
        parent = self.factory.make_directory(owner=user, name='current-parent')
        dir1 = self.factory.make_directory(name='dir1', parent=parent)
        dir11 = self.factory.make_directory(name='dir1.1', parent=dir1)
        f1 = self.factory.make_file(name='f1.jpg',
                                    parent=dir1,
                                    mimetype=self.mimetype)
        f11 = self.factory.make_file(name='f11.jpg',
                                     parent=dir11,
                                     mimetype=self.mimetype)
        nodes = [(dir1, dir1.full_path), (dir11, dir11.full_path),
                 (f1, f1.full_path), (f11, f11.full_path)]

        # Now move dir1 to new_parent.
        new_parent = self.factory.make_directory(owner=user, name='new-parent')
        self.clear_txlogs()

        dir1.move(new_parent, dir1.name)

        expected = [
            self._get_dict_with_txlog_attrs_from(
                node,
                TransactionLog.OP_MOVE,
                old_path=old_path,
                generation=dir1.generation,
                extra_data_dict=TransactionLog.extra_data_new_node(node))
            for node, old_path in nodes
        ]
        self.assertTransactionLogsMatch(expected)