File: modulemd.h

package info (click to toggle)
libmodulemd 2.15.2-1
  • links: PTS, VCS
  • area: main
  • in suites: forky, sid
  • size: 5,180 kB
  • sloc: ansic: 37,927; python: 3,233; xml: 1,739; sh: 389; makefile: 42
file content (444 lines) | stat: -rw-r--r-- 17,284 bytes parent folder | download | duplicates (3)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
/*
 * This file is part of libmodulemd
 * Copyright (C) 2018-2020 Red Hat, Inc.
 *
 * Fedora-License-Identifier: MIT
 * SPDX-2.0-License-Identifier: MIT
 * SPDX-3.0-License-Identifier: MIT
 *
 * This program is free software.
 * For more information on the license, see COPYING.
 * For more information on free software, see <https://www.gnu.org/philosophy/free-sw.en.html>.
 */

#pragma once

#include "modulemd-build-config.h"
#include "modulemd-buildopts.h"
#include "modulemd-component-module.h"
#include "modulemd-component-rpm.h"
#include "modulemd-component.h"
#include "modulemd-compression.h"
#include "modulemd-defaults-v1.h"
#include "modulemd-defaults.h"
#include "modulemd-dependencies.h"
#include "modulemd-deprecated.h"
#include "modulemd-errors.h"
#include "modulemd-module-index-merger.h"
#include "modulemd-module-index.h"
#include "modulemd-module-stream-v1.h"
#include "modulemd-module-stream-v2.h"
#include "modulemd-module-stream.h"
#include "modulemd-module.h"
#include "modulemd-packager-v3.h"
#include "modulemd-profile.h"
#include "modulemd-rpm-map-entry.h"
#include "modulemd-service-level.h"
#include "modulemd-subdocument-info.h"
#include "modulemd-translation-entry.h"
#include "modulemd-translation.h"

G_BEGIN_DECLS


/**
 * SECTION: modulemd
 * @title: Modulemd
 * @stability: stable
 * @short_description: User's Guide for libmodulemd
 *
 * # Working with repodata (DNF use-case)
 * The libmodulemd API provides a number of convenience tools for interacting
 * with repodata (that is, streams of YAML that contains information on multiple
 * streams, default data and translations). The documentation will use two
 * repositories, called "fedora" and "updates" for demonstrative purposes. It
 * will assume that the content of the YAML module metadata from those two
 * repositories have been loaded into string variables `fedora_yaml` and
 * `updates_yaml`, respectively.
 *
 * Tools such as DNF that are consuming data from a repository should always
 * set `strict=False`, so that it can safely handle minor,
 * backwards-compatible changes to the modulemd format.
 *
 * First step is to load the metadata from these two repositories into
 * #ModulemdModuleIndex objects. This is done as follows:
 *
 * In C:
 * |[<!-- language="C" -->
 * ModulemdModuleIndex *fedora_index = modulemd_module_index_new ();
 * gboolean ret = modulemd_module_index_update_from_string (
 *   fedora_index, fedora_yaml, FALSE, &failures, &error);
 *
 * ModulemdModuleIndex *updates_index = modulemd_module_index_new ();
 * gboolean ret2 = modulemd_module_index_update_from_string (
 *   updates_index, updates_yaml, FALSE, &failures, &error);
 * ]|
 *
 * In Python:
 * |[<!-- language="Python" -->
 * fedora_index = Modulemd.ModuleIndex.new()
 * ret, failures = fedora_index.update_from_string(fedora_yaml, False)
 *
 * updates_index = Modulemd.ModuleIndex.new()
 * ret, failures = updates_index.update_from_string(updates_yaml, False)
 * ]|
 *
 * The @failures are a list of subdocuments in the YAML that failed parsing,
 * along with the reason they failed. Hence, by checking the return value of
 * @failures we will know if the YAML parsing was successful or not.
 *
 * Since it doesn't really make sense to view the contents from separate
 * repositories in isolation (in most cases), the next step is to merge the two
 * indexes into a combined one:
 *
 * In C:
 * |[<!-- language="C" -->
 * ModulemdModuleIndexMerger *merger = modulemd_module_index_merger_new ();
 *
 * modulemd_module_index_merger_associate_index (merger, fedora_index, 0);
 * modulemd_module_index_merger_associate_index (merger, updates_index, 0);
 *
 * ModulemdModuleIndex *merged_index =
 *   modulemd_module_index_merger_resolve (merger, &error);
 * ]|
 *
 * In Python:
 * |[<!-- language="Python" -->
 * merger = Modulemd.ModuleIndexMerger.new()
 *
 * merger.associate_index(fedora_index, 0)
 * merger.associate_index(updates_index, 0)
 *
 * merged_index = merger.resolve()
 * ]|
 *
 * At this point, you now have either a complete view of the merged repodata,
 * or else have received an error describing why the merge was unable to
 * complete successfully. Additionally, it should be noted that the combined
 * metadata in any #ModulemdModuleIndex will have all of its component parts
 * upgraded to match the highest version of those objects seen. So for example
 * if the repodata has a mix of v1 and v2 #ModulemdModuleStream objects, the
 * index will contain only v2 objects (with the v1 objects automatically
 * upgraded internally).
 *
 * Now, we can start operating on the retrieved data. This guide will
 * give only a brief overview of the most common operations. See the API
 * specification for a full list of information that can be retrieved.
 *
 * ## Discover the default stream for a particular module.
 *
 * In C:
 * |[<!-- language="C" -->
 * ModulemdModule *module =
 *   modulemd_module_index_get_module (merged_index, "modulename");
 * ModulemdDefaults *defaults = modulemd_module_get_defaults (module);
 * if (defaults)
 *   {
 *     printf ("Default stream for modulename is %s\n",
 *             modulemd_defaults_v1_get_default_stream (
 *               MODULEMD_DEFAULTS_V1 (defaults), NULL));
 *   }
 * ]|
 *
 * In Python:
 * |[<!-- language="Python" -->
 * module = merged_index.get_module("modulename")
 * defaults = module.get_defaults()
 * print("Default stream for modulename is %s" % defaults.get_default_stream())
 * ]|
 *
 * ## Get the list of RPMs defining the public API for a particular module NSVCA
 * First, query the #ModulemdModuleIndex for the module with a given name.
 *
 * In C:
 * |[<!-- language="C" -->
 * ModulemdModule *module =
 *   modulemd_module_index_get_module (merged_index, "modulename");
 * ]|
 *
 * In Python:
 * |[<!-- language="Python" -->
 * module = merged_index.get_module("modulename")
 * ]|
 *
 * Then, query the #ModulemdModule for the #ModulemdModuleStream associated with the
 * provided NSVCA (name-stream-version-context-architecture identifier).
 *
 * In C:
 * |[<!-- language="C" -->
 * ModulemdModuleStream *stream = modulemd_module_get_stream_by_NSVCA (
 *   module, "modulestream", 0, "deadbeef", "coolarch", &error);
 * ]|
 *
 * In Python:
 * |[<!-- language="Python" -->
 * stream = module.get_stream_by_NSVCA("modulestream", 0, "deadbeef", "coolarch")
 * ]|
 *
 * Lastly, read the RPM API from the #ModulemdModuleStream. Here, `api_list` is
 * a list of strings containing package names.
 *
 * In C:
 * |[<!-- language="C" -->
 * GStrv api_list = modulemd_module_stream_v2_get_rpm_api_as_strv (
 *   MODULEMD_MODULE_STREAM_V2 (stream));
 * ]|
 *
 * In Python:
 * |[<!-- language="Python" -->
 * api_list = stream.get_rpm_api()
 * ]|
 *
 * Also note that in addition to accessor API methods, many objects also have
 * properties that can be accessed directly.
 *
 * In C:
 * |[<!-- language="C" -->
 * printf ("Documentation for module stream is at %s\n",
 *         modulemd_module_stream_v2_get_documentation (
 *           MODULEMD_MODULE_STREAM_V2 (stream)));
 * g_autofree gchar *doc;
 * g_object_get (MODULEMD_MODULE_STREAM_V2 (stream), "documentation", &doc, NULL);
 * printf ("Documentation for module stream is at %s\n", doc);
 * ]|
 *
 * In Python:
 * |[<!-- language="Python" -->
 * print("Documentation for module stream is at %s" % stream.get_documentation())
 * print("Documentation for module stream is at %s" % stream.props.documentation)
 * ]|
 *
 * ## Retrieve the modular runtime dependencies for a particular module NSVCA
 *
 * In C:
 * |[<!-- language="C" -->
 * ModulemdModule *module =
 *   modulemd_module_index_get_module (merged_index, "modulename");
 * ModulemdModuleStream *stream = modulemd_module_get_stream_by_NSVCA (
 *   module, "modulestream", 0, "deadbeef", "coolarch", &error);
 * GPtrArray *deps_list = modulemd_module_stream_v2_get_dependencies (
 *   MODULEMD_MODULE_STREAM_V2 (stream));
 *
 * for (gint i = 0; i < deps_list->len; i++)
 *   {
 *     GStrv depmodules_list =
 *      modulemd_dependencies_get_runtime_modules_as_strv (
 *        g_ptr_array_index (deps_list, i));
 *
 *     for (gint j = 0; j < g_strv_length (depmodules_list); j++)
 *       {
 *         GStrv depstreams_list =
 *           modulemd_dependencies_get_runtime_streams_as_strv (
 *             g_ptr_array_index (deps_list, i), depmodules_list[j]);
 *
 *         for (gint k = 0; k < g_strv_length (depstreams_list); k++)
 *           {
 *             // do stuff with depmodules_list[j], depstreams_list[k]
 *           }
 *       }
 *   }
 * ]|
 *
 * In Python:
 * |[<!-- language="Python" -->
 * module = merged_index.get_module("modulename")
 * stream = module.get_stream_by_NSVCA("modulestream", 0, "deadbeef", "coolarch")
 * deps_list = stream.get_dependencies()
 * for dep in deps_list:
 *     depmodules_list = dep.get_runtime_modules()
 *     for depmod in depmodules_list:
 *         depstream_list = dep.get_runtime_streams(depmod)
 *         for depstream in depstream_list:
 *             # do stuff with depmod, depstream
 * ]|
 *
 * # Working with a single module stream (Packager/MBS use-case)
 * One limitation of the #ModulemdModuleIndex format is that it requires that
 * all module streams loaded into it have both a name and a stream name.
 * This however is not possible when dealing with streams such as a packager
 * would be using (since the build-system auto-generates the module name and
 * stream name from the git repository information. In this case, we need to
 * work with a single module stream document at a time. For this, we will
 * use the #ModulemdModuleStream interface.
 *
 * This example will assume that the module name and stream name have
 * already been determined from the repodata and that they are stored in
 * string variables named `module_name` and `stream_name`, respectively.
 *
 * In Python:
 * |[<!-- language="Python" -->
 * stream = Modulemd.ModuleStream.read_file(
 *     "/path/to/module_name.yaml", True, module_name, stream_name
 * )
 * v2_stream = stream.upgrade(Modulemd.ModuleStreamVersionEnum.TWO)
 * v2_stream.validate()
 * ]|
 * In the example above, we upgraded the stream to v2, in case we were reading
 * from v1 metadata. This will allow us to avoid having to manage multiple
 * code-paths and support only the latest we understand. After that, it calls
 * validate() to ensure that the content that was read in was valid both
 * syntactically and referentially.
 *
 * Also available is `Modulemd.ModuleStreamVersionEnum.LATEST` which will
 * always represent the highest-supported version of the
 * #ModulemdModuleStream metadata format. This may change at any time.
 */


/**
 * modulemd_get_version:
 *
 * Returns: (transfer none): A string describing the version of libmodulemd.
 *
 * Since: 2.0
 */
const gchar *
modulemd_get_version (void);


/**
 * modulemd_load_file:
 * @yaml_file: (in): A YAML file containing the module metadata and other
 * related information such as default streams.
 * @error: (out): A #GError containing additional information if this function
 * fails in a way that prevents program continuation.
 *
 * This is a convenience function that is a wrapper around
 * modulemd_module_index_new() and modulemd_module_index_update_from_file()
 * with `strict=False`.
 *
 * It will return the imported module metadata if all subdocuments are
 * parseable and valid. If any part of the document is unreadable or fails
 * validation, it will return NULL and set @error appropriately. If you need
 * more detail about which parts of the document failed, use the lower-level
 * functions.
 *
 * Returns: (transfer full): A newly-allocated #ModulemdModuleIndex object
 * initialized with the content from @yaml_file. Returns NULL and sets @error
 * if the file is not completely valid.
 *
 * Since: 2.10
 */
ModulemdModuleIndex *
modulemd_load_file (const gchar *yaml_file, GError **error);


/**
 * modulemd_load_string:
 * @yaml_string: (in): A YAML string containing the module metadata and other
 * related information such as default streams.
 * @error: (out): A #GError containing additional information if this function
 * fails in a way that prevents program continuation.
 *
 * This is a convenience function that is a wrapper around
 * modulemd_module_index_new() and modulemd_module_index_update_from_string()
 * with `strict=False`.
 *
 * It will return the imported module metadata if all subdocuments are
 * parseable and valid. If any part of the document is unreadable or fails
 * validation, it will return NULL and set @error appropriately. If you need
 * more detail about which parts of the document failed, use the lower-level
 * functions.
 *
 * Returns: (transfer full): A newly-allocated #ModulemdModuleIndex object
 * initialized with the content from @yaml_string. Returns NULL and sets @error
 * if the metadata is not completely valid.
 *
 * Since: 2.10
 */
ModulemdModuleIndex *
modulemd_load_string (const gchar *yaml_string, GError **error);

/**
 * modulemd_read_packager_file: (skip)
 * @yaml_path: (in): A path to a YAML file containing a packager document.
 * @object: (out): (transfer full): A newly allocated #ModulemdModuleStreamV2 or
 * #ModulemdPackagerV3 object initialized with the content from @yaml_path.
 * @error: (out): A #GError containing additional information if this function
 * fails in a way that prevents program continuation.
 *
 * Returns: @MODULEMD_TYPE_MODULE_STREAM_V2, @MODULEMD_TYPE_PACKAGER_V3, or
 * @G_TYPE_INVALID. Returns the matching GObject through the @object parameter.
 * If the return value is @G_TYPE_INVALID, returns the reason as @error.
 *
 * Since: 2.11
 */
GType
modulemd_read_packager_file (const gchar *yaml_path,
                             GObject **object,
                             GError **error);

/**
 * modulemd_read_packager_file_ext: (rename-to modulemd_read_packager_file)
 * @yaml_path: (in): A path to a YAML file containing a packager document.
 * @object: (out): (transfer full): A newly allocated #ModulemdModuleStreamV2 or
 * #ModulemdPackagerV3 object initialized with the content from @yaml_path.
 * @module_name: (in) (nullable): An optional module name to override the
 * document on disk. Mostly useful in cases where the name is being
 * auto-detected from git.
 * @module_stream: (in) (nullable): An optional module stream name to override
 * the document on disk. Mostly useful in cases where the name is being
 * auto-detected from git.
 * @error: (out): A #GError containing additional information if this function
 * fails in a way that prevents program continuation.
 *
 * Returns: @MODULEMD_TYPE_MODULE_STREAM_V2, @MODULEMD_TYPE_PACKAGER_V3, or
 * @G_TYPE_INVALID. Returns the matching GObject through the @object parameter.
 * If the return value is @G_TYPE_INVALID, returns the reason as @error.
 *
 * Since: 2.11
 */
GType
modulemd_read_packager_file_ext (const gchar *yaml_path,
                                 GObject **object,
                                 const gchar *module_name,
                                 const gchar *module_stream,
                                 GError **error);

/**
 * modulemd_read_packager_string: (skip)
 * @yaml_string: (in): A YAML string containing a packager document.
 * @object: (out): (transfer full): A newly allocated #ModulemdModuleStreamV2 or
 * #ModulemdPackagerV3 object initialized with the content from @yaml_string.
 * @error: (out): A #GError containing additional information if this function
 * fails in a way that prevents program continuation.
 *
 * Returns: @MODULEMD_TYPE_MODULE_STREAM_V2, @MODULEMD_TYPE_PACKAGER_V3, or
 * @G_TYPE_INVALID. Returns the matching GObject through the @object parameter.
 * If the return value is @G_TYPE_INVALID, returns the reason as @error.
 *
 * Since: 2.11
 */
GType
modulemd_read_packager_string (const gchar *yaml_string,
                               GObject **object,
                               GError **error);

/**
 * modulemd_read_packager_string_ext: (rename-to modulemd_read_packager_string)
 * @yaml_string: (in): A YAML string containing a packager document.
 * @object: (out): (transfer full): A newly allocated #ModulemdModuleStreamV2 or
 * #ModulemdPackagerV3 object initialized with the content from @yaml_string.
 * @module_name: (in) (nullable): An optional module name to override the
 * document on disk. Mostly useful in cases where the name is being
 * auto-detected from git.
 * @module_stream: (in) (nullable): An optional module stream name to override
 * the document on disk. Mostly useful in cases where the name is being
 * auto-detected from git.
 * @error: (out): A #GError containing additional information if this function
 * fails in a way that prevents program continuation.
 *
 * Returns: @MODULEMD_TYPE_MODULE_STREAM_V2, @MODULEMD_TYPE_PACKAGER_V3, or
 * @G_TYPE_INVALID. Returns the matching GObject through the @object parameter.
 * If the return value is @G_TYPE_INVALID, returns the reason as @error.
 *
 * Since: 2.11
 */
GType
modulemd_read_packager_string_ext (const gchar *yaml_string,
                                   GObject **object,
                                   const gchar *module_name,
                                   const gchar *module_stream,
                                   GError **error);

G_END_DECLS