| # Define an index of components which use storage |
| |
| Note: This guide uses the [components v1](/docs/glossary.md#components-v1) |
| architecture. |
| |
| ## Terminology |
| |
| - [Component Moniker](/docs/glossary.md#moniker) |
| - [Component Instance ID](/docs/glossary.md#component-instance-id) |
| |
| ## Scope |
| |
| This document describes how to define an index that maps instance ids to |
| monikers for components which use isolated-persistent-storage. |
| |
| ## Overview |
| |
| The goal of an index of component instance IDs is to assign stable identifiers |
| to component instances. This is done by mapping an instance ID to a moniker. |
| When a component instance is assigned an ID, its persistent resources are |
| identified on disk using this instance ID. This allows the component's URL or |
| realm to be changed while its resources still remain attributed to it, so long |
| as this index is also updated. |
| |
| When the component runtime discovers an instance ID -> moniker mapping, it |
| automatically moves the component instance's existing storage directory to be |
| keyed under its instance ID. |
| |
| Only components which use storage capabilities must to be included in the |
| index. The following class of components should not be included in the |
| index: |
| |
| * Test components |
| * Components whose storage is not managed by appmgr. |
| |
| ## Define a new index |
| |
| An index file is a JSON5 formatted file, mapping a component's instance ID to |
| its moniker. There may be multiple index files in a build tree, but they will |
| be merged together into a single index file, and this merged file will be made |
| available to the component runtime. This merged index file is immutable, and |
| can only be updated through another system update. |
| |
| The schema for an index file is described in the following example: |
| |
| ```json5 |
| // Index files are written in JSON5, so you may use comments! |
| { |
| // A list of entries, where each entry maps an instance ID to a moniker. |
| instances: [ |
| // An entry, mapping an instance ID to a moniker. |
| { |
| // Instance IDs are randomly generated, 256-bits of base-16 encoded |
| // strings (in lower case). To generate a new instance ID, omit this |
| // field and run the build; the build will fail and suggest a new |
| // instance ID which you can copy-paste here. |
| instance_id: "11601233aef81741f7251907d4d2a1a33aa6fec6b2e54abffc21bec29f95fec2", |
| // The `instance_id` above is associated to the following moniker: |
| appmgr_moniker: { |
| // This the URL of the component. |
| url: "fuchsia-pkg://example.com/my_package#meta/my_component.cmx", |
| |
| // This is the realm path where this component runs. |
| realm_path: [ |
| "sys", // This the parent realm of "session" |
| "session" // This is the realm the component runs under |
| ] |
| } |
| }, |
| |
| // More than one entry can be included. However, all entries must be distinct: |
| // * Two entries cannot reference the same `instance_id` |
| // * Two entries cannot reference the same `realm` |
| { |
| instance_id: "644a7f0f66f8994d894c5f78b5b879911fee6c185c6aadd29d52888812d20ac4", |
| appmgr_moniker: { |
| url: "fuchsia-pkg://example.com/my_other_package#meta/my_other_component.cmx", |
| realm_path: [ |
| "sys" |
| ] |
| } |
| } |
| ] |
| } |
| ``` |
| |
| To supply an index file to the build, use the |
| [component_id_index()](/build/component/component_id_index.gni) GN template: |
| |
| ```gn |
| component_id_index("my_component_id_index") { |
| source = "my_component_id_index.json" |
| } |
| ``` |
| |
| ## Add a component to the index {#add-to-index} |
| |
| ### Locate the appropriate index file |
| |
| In order to add a component to the index, you must insert an entry into the |
| appropriate index file. Currently, `fuchsia.git`'s components are listed in the |
| [core_component_id_index.json](/src/sys/appmgr/config/core_component_id_index.json) |
| index. Components outside `fuchsia.git` are listed in a separate index file, |
| probably located under a `//vendor` repository where the relevant product is |
| defined. |
| |
| ### Add an entry to the index |
| Append an entry to the `instances` list with the component's moniker. You may |
| omit the `instance_id` field to have the build fail and suggest a new one you |
| can use. |
| |
| #### Example |
| |
| Add `fuchsia-pkg://example.com/my_other_package#meta/my_other_component.cmx` to |
| the index by appending this entry to [core_component_id_index.json](/src/sys/appmgr/config/core_component_id_index.json)'s |
| `instances` list: |
| |
| ```json5 |
| { |
| appmgr_moniker: { |
| // The component's URL |
| url: "fuchsia-pkg://example.com/my_other_package#meta/my_other_component.cmx", |
| // The realm the component is run under. |
| realm_path: [ |
| "app", |
| "sys" |
| ] |
| } |
| } |
| ``` |
| |
| Now run the build. The build should fail, suggesting a new instance ID: |
| |
| ```bash |
| $ fx build |
| . |
| . |
| Error: Could not merge index file ../../src/sys/appmgr/config/core_component_id_index.json |
| |
| Caused by: |
| Some entries are missing `instance_id` fields. Here are some generated IDs for you: |
| [ |
| { |
| instance_id: "47c3bf08f3e560c4dee659c28fa8d863dbdc0b1dbb74065e6cb1f38441ac759c", |
| appmgr_moniker: { |
| url: "fuchsia-pkg://example.com/my_other_package#meta/my_other_component.cmx", |
| realm_path: [ |
| "app", |
| "sys" |
| ] |
| } |
| } |
| ] |
| ``` |
| |
| Update the entry you've added by copying the suggested `instance_id` field. The |
| build should now pass. |
| |
| ## Include a Component ID Index in a system assembly {#system-assembly} |
| |
| _The target audience for this section are product owners who are |
| setting up a system assembly_ |
| |
| This section describes how to include the component ID index in a system |
| assembly. |
| |
| A system assembly should include a component ID index if it contains components |
| which use isolated storage. Any product which builds on top of the |
| `core` product already includes a component ID index, so the following |
| instructions are not necessary. |
| |
| ### `component_id_index_config_package()` |
| All component_id_index()s in a system |
| build are merged together using the `component_id_index_config_package()` |
| template, which produces a `config_data(for_pkg=appmgr)`. `appmgr` then |
| consumes the merged index using this mechanism. |
| |
| To include a `component_id_index_config_package()` target in a system assembly: |
| |
| **a)** Define it with a dependency on any `component_id_index()` targets which you |
| want included in the system. For example, //build/images:universe_packages is a |
| good dependency candidate because it transitively includes all |
| `component_id_index()` specified in the build. |
| |
| **b)** Add your `component_id_index_config_package()` target to the system assembly. |
| Currently, a good method is to include your `component_id_index_config_package()` |
| target as a dependency to your system assembly's `config_package()`. |