compose: Move txn+ref to toplevel, out of postprocess/commit code

Prep for `compose tree --ex-jigdo`; basically we want to generate the jigdoRPM
and only then set the ref to help bind the two things together.  The main
thing to achieve is that if generating the jigdoRPM fails, the ref isn't
updated.

Closes: #1161
Approved by: jlebon
This commit is contained in:
Colin Walters 2017-12-15 12:13:08 -05:00 committed by Atomic Bot
parent 2e3ff041c7
commit 07bb4339c3
3 changed files with 94 additions and 87 deletions

View File

@ -28,6 +28,9 @@
#include <libdnf/dnf-repo.h>
#include <sys/mount.h>
#include <stdio.h>
#include <linux/magic.h>
#include <sys/statvfs.h>
#include <sys/vfs.h>
#include <libglnx.h>
#include <rpm/rpmmacro.h>
@ -1091,6 +1094,18 @@ impl_install_tree (RpmOstreeTreeComposeContext *self,
return TRUE;
}
/* https://pagure.io/atomic-wg/issue/387 */
static gboolean
repo_is_on_netfs (OstreeRepo *repo)
{
int dfd = ostree_repo_get_dfd (repo);
struct statfs stbuf;
if (fstatfs (dfd, &stbuf) != 0)
return FALSE;
return stbuf.f_type == NFS_SUPER_MAGIC;
}
/* Perform required postprocessing, and invoke rpmostree_compose_commit(). */
static gboolean
impl_commit_tree (RpmOstreeTreeComposeContext *self,
GCancellable *cancellable,
@ -1153,15 +1168,64 @@ impl_commit_tree (RpmOstreeTreeComposeContext *self,
glnx_prefix_error (error, "Handling group db");
}
/* See comment above */
const gboolean use_txn = (getenv ("RPMOSTREE_COMMIT_NO_TXN") == NULL &&
!repo_is_on_netfs (self->repo));
if (use_txn)
{
if (!ostree_repo_prepare_transaction (self->repo, NULL, cancellable, error))
return FALSE;
}
g_autofree char *parent_revision = NULL;
if (self->ref)
{
if (!ostree_repo_resolve_rev (self->repo, self->ref, TRUE, &parent_revision, error))
return FALSE;
}
/* The penultimate step, just basically `ostree commit` */
g_autofree char *new_revision = NULL;
if (!rpmostree_commit (self->rootfs_dfd, self->repo, self->ref, opt_write_commitid_to,
metadata, gpgkey, selinux, self->devino_cache,
&new_revision,
cancellable, error))
if (!rpmostree_compose_commit (self->rootfs_dfd, self->repo, parent_revision,
metadata, gpgkey, selinux, self->devino_cache,
&new_revision, cancellable, error))
return FALSE;
g_print ("%s => %s\n", self->ref, new_revision);
/* --write-commitid-to overrides writing the ref */
if (self->ref && !opt_write_commitid_to)
{
if (use_txn)
ostree_repo_transaction_set_ref (self->repo, NULL, self->ref, new_revision);
else
{
if (!ostree_repo_set_ref_immediate (self->repo, NULL, self->ref, new_revision,
cancellable, error))
return FALSE;
}
}
if (use_txn)
{
OstreeRepoTransactionStats stats = { 0, };
if (!ostree_repo_commit_transaction (self->repo, &stats, cancellable, error))
return glnx_prefix_error (error, "Commit");
g_print ("Metadata Total: %u\n", stats.metadata_objects_total);
g_print ("Metadata Written: %u\n", stats.metadata_objects_written);
g_print ("Content Total: %u\n", stats.content_objects_total);
g_print ("Content Written: %u\n", stats.content_objects_written);
g_print ("Content Bytes Written: %" G_GUINT64_FORMAT "\n", stats.content_bytes_written);
}
g_print ("Wrote commit: %s\n", new_revision);
if (opt_write_commitid_to)
{
if (!g_file_set_contents (opt_write_commitid_to, new_revision, -1, error))
return glnx_prefix_error (error, "While writing to '%s'", opt_write_commitid_to);
}
else if (self->ref)
g_print ("%s => %s\n", self->ref, new_revision);
return TRUE;
}

View File

@ -29,10 +29,7 @@
#include <utime.h>
#include <err.h>
#include <sys/types.h>
#include <sys/statvfs.h>
#include <sys/vfs.h>
#include <sys/stat.h>
#include <linux/magic.h>
#include <pwd.h>
#include <grp.h>
#include <unistd.h>
@ -1896,29 +1893,21 @@ on_progress_timeout (gpointer datap)
return TRUE;
}
/* https://pagure.io/atomic-wg/issue/387 */
static gboolean
repo_is_on_netfs (OstreeRepo *repo)
{
int dfd = ostree_repo_get_dfd (repo);
struct statfs stbuf;
if (fstatfs (dfd, &stbuf) != 0)
return FALSE;
return stbuf.f_type == NFS_SUPER_MAGIC;
}
/* This is the server-side-only variant; see also the code in rpmostree-core.c
* for all the other cases like client side layering and `ex container` for
* buildroots.
*/
gboolean
rpmostree_commit (int rootfs_fd,
OstreeRepo *repo,
const char *refname,
const char *write_commitid_to,
GVariant *metadata,
const char *gpg_keyid,
gboolean enable_selinux,
OstreeRepoDevInoCache *devino_cache,
char **out_new_revision,
GCancellable *cancellable,
GError **error)
rpmostree_compose_commit (int rootfs_fd,
OstreeRepo *repo,
const char *parent_revision,
GVariant *metadata,
const char *gpg_keyid,
gboolean enable_selinux,
OstreeRepoDevInoCache *devino_cache,
char **out_new_revision,
GCancellable *cancellable,
GError **error)
{
g_autoptr(OstreeSePolicy) sepolicy = NULL;
if (enable_selinux)
@ -1928,16 +1917,6 @@ rpmostree_commit (int rootfs_fd,
return FALSE;
}
/* See comment above */
const gboolean use_txn = (getenv ("RPMOSTREE_COMMIT_NO_TXN") == NULL &&
!repo_is_on_netfs (repo));
if (use_txn)
{
if (!ostree_repo_prepare_transaction (repo, NULL, cancellable, error))
return FALSE;
}
g_autoptr(OstreeMutableTree) mtree = ostree_mutable_tree_new ();
/* We may make this configurable if someone complains about including some
* unlabeled content, but I think the fix for that is to ensure that policy is
@ -2002,13 +1981,6 @@ rpmostree_commit (int rootfs_fd,
if (!ostree_repo_write_mtree (repo, mtree, &root_tree, cancellable, error))
return glnx_prefix_error (error, "While writing tree");
g_autofree char *parent_revision = NULL;
if (refname)
{
if (!ostree_repo_resolve_rev (repo, refname, TRUE, &parent_revision, error))
return FALSE;
}
g_autofree char *new_revision = NULL;
if (!ostree_repo_write_commit (repo, parent_revision, "", "", metadata,
(OstreeRepoFile*)root_tree, &new_revision,
@ -2022,36 +1994,8 @@ rpmostree_commit (int rootfs_fd,
return glnx_prefix_error (error, "While signing commit");
}
if (write_commitid_to)
{
if (!g_file_set_contents (write_commitid_to, new_revision, -1, error))
return glnx_prefix_error (error, "While writing to '%s'", write_commitid_to);
}
else if (refname)
{
if (use_txn)
ostree_repo_transaction_set_ref (repo, NULL, refname, new_revision);
else
{
if (!ostree_repo_set_ref_immediate (repo, NULL, refname, new_revision,
cancellable, error))
return FALSE;
}
}
if (use_txn)
{
OstreeRepoTransactionStats stats = { 0, };
if (!ostree_repo_commit_transaction (repo, &stats, cancellable, error))
return glnx_prefix_error (error, "Commit");
g_print ("Metadata Total: %u\n", stats.metadata_objects_total);
g_print ("Metadata Written: %u\n", stats.metadata_objects_written);
g_print ("Content Total: %u\n", stats.content_objects_total);
g_print ("Content Written: %u\n", stats.content_objects_written);
g_print ("Content Bytes Written: %" G_GUINT64_FORMAT "\n", stats.content_bytes_written);
}
if (out_new_revision)
*out_new_revision = g_steal_pointer (&new_revision);
return TRUE;
}

View File

@ -79,14 +79,13 @@ rpmostree_postprocess_final (int rootfs_dfd,
GError **error);
gboolean
rpmostree_commit (int rootfs_dfd,
OstreeRepo *repo,
const char *refname,
const char *write_commitid_to,
GVariant *metadata,
const char *gpg_keyid,
gboolean enable_selinux,
OstreeRepoDevInoCache *devino_cache,
char **out_new_revision,
GCancellable *cancellable,
GError **error);
rpmostree_compose_commit (int rootfs_dfd,
OstreeRepo *repo,
const char *parent,
GVariant *metadata,
const char *gpg_keyid,
gboolean enable_selinux,
OstreeRepoDevInoCache *devino_cache,
char **out_new_revision,
GCancellable *cancellable,
GError **error);