diff --git a/app/flatpak-builtins-build-bundle.c b/app/flatpak-builtins-build-bundle.c
index 6f641858..3edf3f96 100644
--- a/app/flatpak-builtins-build-bundle.c
+++ b/app/flatpak-builtins-build-bundle.c
@@ -190,7 +190,7 @@ build_bundle (OstreeRepo *repo, GFile *file,
if (flatpak_appstream_xml_migrate (xml_root, appstream_root,
full_branch, name, keyfile))
{
- g_autoptr(GBytes) xml_data = flatpak_appstream_xml_root_to_data (appstream_root, error);
+ g_autoptr(GBytes) xml_data = NULL;
int i;
g_autoptr(GFile) icons_dir =
g_file_resolve_relative_path (root,
@@ -199,7 +199,7 @@ build_bundle (OstreeRepo *repo, GFile *file,
const char *icon_sizes_key[] = { "icon-64", "icon-128" };
g_autofree char *icon_name = g_strconcat (name, ".png", NULL);
- if (xml_data == NULL)
+ if (!flatpak_appstream_xml_root_to_data (appstream_root, NULL, &xml_data, error))
return FALSE;
g_variant_builder_add (&metadata_builder, "{sv}", "appdata",
diff --git a/common/flatpak-utils.c b/common/flatpak-utils.c
index 047a4afd..ef949898 100644
--- a/common/flatpak-utils.c
+++ b/common/flatpak-utils.c
@@ -3194,8 +3194,12 @@ commit_filter (OstreeRepo *repo,
GFileInfo *file_info,
gpointer user_data)
{
+ const char *ignore_filename = user_data;
guint current_mode;
+ if (g_strcmp0 (ignore_filename, g_file_info_get_name (file_info)) == 0)
+ return OSTREE_REPO_COMMIT_FILTER_SKIP;
+
/* No user info */
g_file_info_set_attribute_uint32 (file_info, "unix::uid", 0);
g_file_info_set_attribute_uint32 (file_info, "unix::gid", 0);
@@ -3544,8 +3548,10 @@ flatpak_appstream_xml_new (void)
return appstream_root;
}
-GBytes *
+gboolean
flatpak_appstream_xml_root_to_data (FlatpakXml *appstream_root,
+ GBytes **uncompressed,
+ GBytes **compressed,
GError **error)
{
g_autoptr(GString) xml = NULL;
@@ -3558,16 +3564,25 @@ flatpak_appstream_xml_root_to_data (FlatpakXml *appstream_root,
xml = g_string_new ("");
flatpak_xml_to_string (appstream_root, xml);
- compressor = g_zlib_compressor_new (G_ZLIB_COMPRESSOR_FORMAT_GZIP, -1);
- out = g_memory_output_stream_new_resizable ();
- out2 = g_converter_output_stream_new (out, G_CONVERTER (compressor));
- if (!g_output_stream_write_all (out2, xml->str, xml->len,
- NULL, NULL, error))
- return NULL;
- if (!g_output_stream_close (out2, NULL, error))
- return NULL;
+ if (compressed)
+ {
+ compressor = g_zlib_compressor_new (G_ZLIB_COMPRESSOR_FORMAT_GZIP, -1);
+ out = g_memory_output_stream_new_resizable ();
+ out2 = g_converter_output_stream_new (out, G_CONVERTER (compressor));
+ if (!g_output_stream_write_all (out2, xml->str, xml->len,
+ NULL, NULL, error))
+ return FALSE;
+ if (!g_output_stream_close (out2, NULL, error))
+ return FALSE;
+ }
- return g_memory_output_stream_steal_as_bytes (G_MEMORY_OUTPUT_STREAM (out));
+ if (uncompressed)
+ *uncompressed = g_string_free_to_bytes (g_steal_pointer (&xml));
+
+ if (compressed)
+ *compressed = g_memory_output_stream_steal_as_bytes (G_MEMORY_OUTPUT_STREAM (out));
+
+ return TRUE;
}
gboolean
@@ -3633,19 +3648,23 @@ flatpak_repo_generate_appstream (OstreeRepo *repo,
g_autofree char *tmpdir = g_strdup ("/tmp/flatpak-appstream-XXXXXX");
g_autoptr(FlatpakTempDir) tmpdir_file = NULL;
g_autoptr(GFile) appstream_file = NULL;
- g_autoptr(GFile) root = NULL;
- g_autoptr(OstreeMutableTree) mtree = NULL;
+ g_autoptr(GFile) appstream_gz_file = NULL;
g_autofree char *commit_checksum = NULL;
OstreeRepoTransactionStats stats;
g_autoptr(OstreeRepoCommitModifier) modifier = NULL;
- g_autofree char *parent = NULL;
- g_autofree char *branch = NULL;
g_autoptr(FlatpakXml) appstream_root = NULL;
g_autoptr(GBytes) xml_data = NULL;
- gboolean skip_commit = FALSE;
+ g_autoptr(GBytes) xml_gz_data = NULL;
const char *compat_arch;
-
+ g_autoptr(FlatpakRepoTransaction) transaction = NULL;
compat_arch = flatpak_get_compat_arch (arch);
+ struct {
+ const char *ignore_filename;
+ const char *branch_prefix;
+ } branch_data[] = {
+ { "appstream.xml", "appstream" },
+ { "appstream.xml.gz", "appstream2" },
+ };
if (g_mkdtemp_full (tmpdir, 0755) == NULL)
return flatpak_fail (error, "Can't create temporary directory");
@@ -3710,12 +3729,10 @@ flatpak_repo_generate_appstream (OstreeRepo *repo,
}
}
- xml_data = flatpak_appstream_xml_root_to_data (appstream_root, error);
- if (xml_data == NULL)
+ if (!flatpak_appstream_xml_root_to_data (appstream_root, &xml_data, &xml_gz_data, error))
return FALSE;
- appstream_file = g_file_get_child (tmpdir_file, "appstream.xml.gz");
-
+ appstream_file = g_file_get_child (tmpdir_file, "appstream.xml");
if (!g_file_replace_contents (appstream_file,
g_bytes_get_data (xml_data, NULL),
g_bytes_get_size (xml_data),
@@ -3727,117 +3744,130 @@ flatpak_repo_generate_appstream (OstreeRepo *repo,
error))
return FALSE;
- if (!ostree_repo_prepare_transaction (repo, NULL, cancellable, error))
+ appstream_gz_file = g_file_get_child (tmpdir_file, "appstream.xml.gz");
+ if (!g_file_replace_contents (appstream_gz_file,
+ g_bytes_get_data (xml_gz_data, NULL),
+ g_bytes_get_size (xml_gz_data),
+ NULL,
+ FALSE,
+ G_FILE_CREATE_NONE,
+ NULL,
+ cancellable,
+ error))
return FALSE;
- branch = g_strdup_printf ("appstream/%s", arch);
+ transaction = flatpak_repo_transaction_start (repo, cancellable, error);
+ if (transaction == NULL)
+ return FALSE;
- if (!ostree_repo_resolve_rev (repo, branch, TRUE, &parent, error))
- goto out;
-
- mtree = ostree_mutable_tree_new ();
-
- modifier = ostree_repo_commit_modifier_new (OSTREE_REPO_COMMIT_MODIFIER_FLAGS_SKIP_XATTRS |
- OSTREE_REPO_COMMIT_MODIFIER_FLAGS_CANONICAL_PERMISSIONS,
- (OstreeRepoCommitFilter) commit_filter, NULL, NULL);
-
- if (!ostree_repo_write_directory_to_mtree (repo, G_FILE (tmpdir_file), mtree, modifier, cancellable, error))
- goto out;
-
- if (!ostree_repo_write_mtree (repo, mtree, &root, cancellable, error))
- goto out;
-
-
- /* No need to commit if nothing changed */
- if (parent)
+ for (i = 0; i < G_N_ELEMENTS(branch_data); i++)
{
- g_autoptr(GFile) parent_root;
+ gboolean skip_commit = FALSE;
+ const char *ignore_filename = branch_data[i].ignore_filename;
+ const char *branch_prefix = branch_data[i].branch_prefix;
+ g_autoptr(OstreeMutableTree) mtree = NULL;
+ g_autoptr(GFile) root = NULL;
+ g_autofree char *branch = NULL;
+ g_autofree char *parent = NULL;
- if (!ostree_repo_read_commit (repo, parent, &parent_root, NULL, cancellable, error))
- goto out;
+ branch = g_strdup_printf ("%s/%s", branch_prefix, arch);
+ if (!ostree_repo_resolve_rev (repo, branch, TRUE, &parent, error))
+ return FALSE;
- if (g_file_equal (root, parent_root))
+ mtree = ostree_mutable_tree_new ();
+ modifier = ostree_repo_commit_modifier_new (OSTREE_REPO_COMMIT_MODIFIER_FLAGS_SKIP_XATTRS |
+ OSTREE_REPO_COMMIT_MODIFIER_FLAGS_CANONICAL_PERMISSIONS,
+ (OstreeRepoCommitFilter) commit_filter, (gpointer)ignore_filename, NULL);
+
+ if (!ostree_repo_write_directory_to_mtree (repo, G_FILE (tmpdir_file), mtree, modifier, cancellable, error))
+ return FALSE;
+
+ if (!ostree_repo_write_mtree (repo, mtree, &root, cancellable, error))
+ return FALSE;
+
+ /* No need to commit if nothing changed */
+ if (parent)
{
- skip_commit = TRUE;
- g_debug ("Not updating %s, no change", branch);
- }
- }
+ g_autoptr(GFile) parent_root;
- if (!skip_commit)
- {
- g_autoptr(GVariantDict) metadata_dict = NULL;
- g_autoptr(GVariant) metadata = NULL;
+ if (!ostree_repo_read_commit (repo, parent, &parent_root, NULL, cancellable, error))
+ return FALSE;
- /* Add bindings to the metadata. Do this even if P2P support is not
- * enabled, as it might be enable for other flatpak builds. */
- metadata_dict = g_variant_dict_new (NULL);
- g_variant_dict_insert (metadata_dict, "ostree.collection-binding",
- "s", (collection_id != NULL) ? collection_id : "");
- g_variant_dict_insert_value (metadata_dict, "ostree.ref-binding",
- g_variant_new_strv ((const gchar * const *) &branch, 1));
- metadata = g_variant_ref_sink (g_variant_dict_end (metadata_dict));
-
- if (timestamp > 0)
- {
- if (!ostree_repo_write_commit_with_time (repo, parent, "Update", NULL, metadata,
- OSTREE_REPO_FILE (root),
- timestamp,
- &commit_checksum,
- cancellable, error))
- goto out;
- }
- else
- {
- if (!ostree_repo_write_commit (repo, parent, "Update", NULL, metadata,
- OSTREE_REPO_FILE (root),
- &commit_checksum, cancellable, error))
- goto out;
- }
-
- if (gpg_key_ids)
- {
- int i;
-
- for (i = 0; gpg_key_ids[i] != NULL; i++)
+ if (g_file_equal (root, parent_root))
{
- const char *keyid = gpg_key_ids[i];
-
- if (!ostree_repo_sign_commit (repo,
- commit_checksum,
- keyid,
- gpg_homedir,
- cancellable,
- error))
- goto out;
+ skip_commit = TRUE;
+ g_debug ("Not updating %s, no change", branch);
}
}
-#ifdef FLATPAK_ENABLE_P2P
- if (collection_id != NULL)
+ if (!skip_commit)
{
- const OstreeCollectionRef collection_ref = { (char *) collection_id, branch };
- ostree_repo_transaction_set_collection_ref (repo, &collection_ref, commit_checksum);
- }
- else
-#endif /* FLATPAK_ENABLE_P2P */
- {
- ostree_repo_transaction_set_ref (repo, NULL, branch, commit_checksum);
- }
+ g_autoptr(GVariantDict) metadata_dict = NULL;
+ g_autoptr(GVariant) metadata = NULL;
- if (!ostree_repo_commit_transaction (repo, &stats, cancellable, error))
- goto out;
- }
- else
- {
- ostree_repo_abort_transaction (repo, cancellable, NULL);
+ /* Add bindings to the metadata. Do this even if P2P support is not
+ * enabled, as it might be enable for other flatpak builds. */
+ metadata_dict = g_variant_dict_new (NULL);
+ g_variant_dict_insert (metadata_dict, "ostree.collection-binding",
+ "s", (collection_id != NULL) ? collection_id : "");
+ g_variant_dict_insert_value (metadata_dict, "ostree.ref-binding",
+ g_variant_new_strv ((const gchar * const *) &branch, 1));
+ metadata = g_variant_ref_sink (g_variant_dict_end (metadata_dict));
+
+ if (timestamp > 0)
+ {
+ if (!ostree_repo_write_commit_with_time (repo, parent, "Update", NULL, metadata,
+ OSTREE_REPO_FILE (root),
+ timestamp,
+ &commit_checksum,
+ cancellable, error))
+ return FALSE;
+ }
+ else
+ {
+ if (!ostree_repo_write_commit (repo, parent, "Update", NULL, metadata,
+ OSTREE_REPO_FILE (root),
+ &commit_checksum, cancellable, error))
+ return FALSE;
+ }
+
+ if (gpg_key_ids)
+ {
+ int i;
+
+ for (i = 0; gpg_key_ids[i] != NULL; i++)
+ {
+ const char *keyid = gpg_key_ids[i];
+
+ if (!ostree_repo_sign_commit (repo,
+ commit_checksum,
+ keyid,
+ gpg_homedir,
+ cancellable,
+ error))
+ return FALSE;
+ }
+ }
+
+#ifdef FLATPAK_ENABLE_P2P
+ if (collection_id != NULL)
+ {
+ const OstreeCollectionRef collection_ref = { (char *) collection_id, branch };
+ ostree_repo_transaction_set_collection_ref (repo, &collection_ref, commit_checksum);
+ }
+ else
+#endif /* FLATPAK_ENABLE_P2P */
+ {
+ ostree_repo_transaction_set_ref (repo, NULL, branch, commit_checksum);
+ }
+ }
}
+
+ if (!ostree_repo_commit_transaction (repo, &stats, cancellable, error))
+ return FALSE;
}
return TRUE;
-
-out:
- ostree_repo_abort_transaction (repo, cancellable, NULL);
- return FALSE;
}
void
diff --git a/common/flatpak-utils.h b/common/flatpak-utils.h
index 43fbb12d..e1ad6882 100644
--- a/common/flatpak-utils.h
+++ b/common/flatpak-utils.h
@@ -604,8 +604,10 @@ gboolean flatpak_appstream_xml_migrate (FlatpakXml *source,
const char *ref,
const char *id,
GKeyFile *metadata);
-GBytes *flatpak_appstream_xml_root_to_data (FlatpakXml *appstream_root,
- GError **error);
+gboolean flatpak_appstream_xml_root_to_data (FlatpakXml *appstream_root,
+ GBytes **uncompressed,
+ GBytes **compressed,
+ GError **error);
gboolean flatpak_repo_generate_appstream (OstreeRepo *repo,
const char **gpg_key_ids,
const char *gpg_homedir,
diff --git a/tests/test-repo.sh b/tests/test-repo.sh
index e37bff9d..e3c35c93 100755
--- a/tests/test-repo.sh
+++ b/tests/test-repo.sh
@@ -37,9 +37,15 @@ setup_repo
if ! ostree show --repo=repos/test appstream/${ARCH} > /dev/null; then
assert_not_reached "No appstream branch"
fi
+if ! ostree show --repo=repos/test appstream2/${ARCH} > /dev/null; then
+ assert_not_reached "No appstream2 branch"
+fi
ostree cat --repo=repos/test appstream/${ARCH} /appstream.xml.gz | gunzip -d > appdata.xml
assert_file_has_content appdata.xml "org.test.Hello.desktop"
+ostree cat --repo=repos/test appstream2/${ARCH} /appstream.xml > appdata2.xml
+assert_file_has_content appdata2.xml "org.test.Hello.desktop"
+
# Unsigned repo (not supported with collections; client-side use of collections requires GPG)
if [ x${USE_COLLECTIONS_IN_CLIENT-} == xyes ] ; then
if GPGPUBKEY=" " GPGARGS=" " setup_repo test-no-gpg org.test.Collection.NoGpg; then
diff --git a/tests/test-unsigned-summaries.sh b/tests/test-unsigned-summaries.sh
index 9f89cbfc..307d9561 100755
--- a/tests/test-unsigned-summaries.sh
+++ b/tests/test-unsigned-summaries.sh
@@ -60,10 +60,12 @@ ostree --repo=repos/test refs > refs
assert_file_has_content refs "^app/org.test.App/$ARCH/master$"
assert_file_has_content refs '^ostree-metadata$'
assert_file_has_content refs "^appstream/${ARCH}$"
+assert_file_has_content refs "^appstream2/${ARCH}$"
ostree --repo=repos/test refs --collections > refs-collections
assert_file_has_content refs-collections "^(org.test.Collection, app/org.test.App/$ARCH/master)$"
assert_file_has_content refs-collections '^(org.test.Collection, ostree-metadata)$'
assert_file_has_content refs-collections "^(org.test.Collection, appstream/${ARCH})$"
+assert_file_has_content refs-collections "^(org.test.Collection, appstream2/${ARCH})$"
assert_has_file repos/test/summary.sig
ostree --repo=repos/test summary --view > summary
assert_file_has_content summary '^Collection ID (ostree.summary.collection-id): org.test.Collection$'