| // Copyright 2021 The Fuchsia Authors. All rights reserved. |
| // Use of this source code is governed by a BSD-style license that can be |
| // found in the LICENSE file. |
| library fuchsia.developer.ffx; |
| |
| using fuchsia.developer.remotecontrol as rc; |
| using fuchsia.net; |
| |
| const MAX_NAME uint64 = 255; |
| const MAX_PATH uint64 = 4095; |
| const MAX_REPOS uint64 = 512; |
| const MAX_ALIASES uint64 = 32; |
| |
| /// Describes all the possible repositories that could be managed by this service. |
| type RepositorySpec = flexible union { |
| 1: file_system FileSystemRepositorySpec; |
| 2: pm PmRepositorySpec; |
| 3: http HttpRepositorySpec; |
| 4: gcs GcsRepositorySpec; |
| }; |
| |
| /// A configuration for a package repository on the local file system. |
| type FileSystemRepositorySpec = table { |
| /// File system path to the location of the metadata repository. |
| 1: metadata_repo_path string:MAX_PATH; |
| |
| /// File system path to the location of the blob repository. |
| 2: blob_repo_path string:MAX_PATH; |
| |
| /// An optional list of repository hostname aliases. A rewrite rule will be added for each |
| /// hostname in this list to resolve to this repository. |
| 3: aliases vector<string:MAX_NAME>:MAX_ALIASES; |
| }; |
| |
| /// A configuration for a package repository on the local file system. |
| /// |
| /// This is similar to [FileSystemRepositorySpec], where the metadata |
| /// repository path is `$path/repository`, and the blob repository path is |
| /// `$path/repository/blobs`. |
| type PmRepositorySpec = table { |
| /// File system path to the location of the pm repository. |
| 1: path string:MAX_PATH; |
| |
| /// An optional list of repository hostname aliases. A rewrite rule will be added for each |
| /// hostname in this list to resolve to this repository. |
| 2: aliases vector<string:MAX_NAME>:MAX_ALIASES; |
| }; |
| |
| /// A configuration for a package repository found on a web server. |
| type HttpRepositorySpec = table { |
| /// URL of the TUF repository. |
| 1: metadata_repo_url string:MAX_PATH; |
| |
| /// URL of the Blob Server. |
| 2: blob_repo_url string:MAX_PATH; |
| |
| /// An optional list of repository hostname aliases. A rewrite rule will be added for each |
| /// hostname in this list to resolve to this repository. |
| 3: aliases vector<string:MAX_NAME>:MAX_ALIASES; |
| }; |
| |
| /// A configuration for a package repository found in Google Cloud Storage. |
| /// |
| /// This is distinct from [HttpRepositorySpec] to allow it to grow GCS-specific |
| /// functionality, such as specifying which service account we should use when |
| /// authenticating requests. |
| type GcsRepositorySpec = table { |
| /// URL of the TUF repository. This must use the gs:// URL scheme. |
| 1: metadata_repo_url string:MAX_PATH; |
| |
| /// URL of the Blob Server. This must use the gs:// URL scheme. |
| 2: blob_repo_url string:MAX_PATH; |
| |
| /// An optional list of repository hostname aliases. A rewrite rule will be added for each |
| /// hostname in this list to resolve to this repository. |
| 3: aliases vector<string:MAX_NAME>:MAX_ALIASES; |
| }; |
| |
| /// Current state of the package repository server. |
| type ServerStatus = strict union { |
| /// The repository server is actively running. |
| 1: running struct { |
| /// The server is listening on this address. |
| address fuchsia.net.SocketAddress; |
| }; |
| |
| /// The repository is stopped, but is capable of being started. |
| 2: stopped struct {}; |
| |
| /// The repository is disabled. |
| 3: disabled struct {}; |
| }; |
| |
| @discoverable |
| closed protocol RepositoryRegistry { |
| /// Start the repository server if it is not already running. Returns the local socket address |
| /// the server is listening upon. |
| /// |
| /// `address`: local socket address that the server will listen on to run package repository. |
| /// This param is optional and if not provided will rely on ffx config. |
| strict ServerStart(struct { |
| address fuchsia.net.SocketAddress:optional; |
| }) -> (struct { |
| address fuchsia.net.SocketAddress; |
| }) error RepositoryError; |
| |
| /// Stop the repository server. |
| /// |
| /// * error `RepositoryError.SERVER_NOT_RUNNING` if the server is not running. |
| strict ServerStop() -> () error RepositoryError; |
| |
| /// Query status of the package repository server. |
| /// |
| /// Note: this may race with other channels calling `ServerStart()` or `ServerStop()`, |
| /// but it will not race with calls on the same channel. |
| strict ServerStatus() -> (struct { |
| status ServerStatus; |
| }); |
| |
| /// Add a repository named `name` that has the following [RepositorySpec]. |
| strict AddRepository(struct { |
| name string:MAX_NAME; |
| repository RepositorySpec; |
| }) -> () error RepositoryError; |
| |
| /// Returns true if the repository was removed, or false if there is no |
| /// repository named `name`. |
| strict RemoveRepository(struct { |
| name string:MAX_NAME; |
| }) -> (struct { |
| found bool; |
| }); |
| |
| strict ListRepositories(resource struct { |
| iterator server_end:RepositoryIterator; |
| }); |
| |
| /// Registers a repository on a target. |
| /// |
| /// `target_info`: Metadata describing the repository registration. |
| /// `alias_conflict_mode`: Resolution mode if alias conflicts present. |
| strict RegisterTarget(struct { |
| target_info RepositoryTarget; |
| alias_conflict_mode RepositoryRegistrationAliasConflictMode; |
| }) -> () error RepositoryError; |
| |
| /// Deregisters a repository from a target. |
| /// |
| /// `repo_name`: The configured name of the repository. |
| /// `target_identifier`: The target from which to deregister this repository. |
| strict DeregisterTarget(struct { |
| repository_name string:MAX_NAME; |
| target_identifier string:<rc.NODE_NAME_MAX, optional>; |
| }) -> () error RepositoryError; |
| |
| /// Get a list associating repositories with the targets they have been registered to. |
| strict ListRegisteredTargets(resource struct { |
| iterator server_end:RepositoryTargetsIterator; |
| }); |
| }; |
| |
| type RepositoryConfig = struct { |
| name string:MAX_NAME; |
| spec RepositorySpec; |
| }; |
| |
| closed protocol RepositoryIterator { |
| strict Next() -> (struct { |
| repos vector<RepositoryConfig>:MAX_REPOS; |
| }); |
| }; |
| |
| closed protocol RepositoryTargetsIterator { |
| strict Next() -> (struct { |
| registrations vector<RepositoryTarget>:MAX; |
| }); |
| }; |
| |
| type RepositoryTarget = table { |
| /// The configured name of the repository |
| 1: repo_name string:MAX_NAME; |
| /// The target on which to configure this repository |
| 2: target_identifier string:rc.NODE_NAME_MAX; |
| /// An optional list of hostnames. A rewrite rule will be added |
| /// for each hostname in this list to resolve to this repository. |
| 3: aliases vector<string:MAX_NAME>:MAX_ALIASES; |
| /// Controls how repository metadata is persisted across reboots. Optional, if absent presumed |
| /// to be EPHEMERAL. |
| 4: storage_type RepositoryStorageType; |
| }; |
| |
| /// Where the repository storage is written to. |
| type RepositoryStorageType = strict enum { |
| /// Ephemeral, or in-memory storage. This repository metadata will be lost |
| /// when the process or device is restarted. The default type. |
| EPHEMERAL = 1; |
| |
| /// Persistent, where the repository metadata is written to mutable storage |
| /// and is available after a reboot. |
| PERSISTENT = 2; |
| }; |
| |
| /// How to resolve alias conflicts. |
| type RepositoryRegistrationAliasConflictMode = strict enum { |
| /// When encountering an alias conflict, error out immediately. |
| ERROR_OUT = 1; |
| |
| /// When encountering an alias conflict, overwrite the alias with |
| /// whatever is being currently registrated. |
| REPLACE = 2; |
| }; |
| |
| type RepositoryError = strict enum : uint32 { |
| /// Repository "name" is missing in an API where it is required. |
| MISSING_REPOSITORY_NAME = 1; |
| /// No repository matches the provided name. |
| NO_MATCHING_REPOSITORY = 2; |
| /// There was an error communicating with the target. This may mean that |
| /// the target does not exist, is down or unreachable, or that there was an |
| /// error communicating with a proxy on target. |
| /// TODO(https://fxbug.dev/42157971) make this more specific when we have more specific |
| /// errors from the underlying API. |
| TARGET_COMMUNICATION_FAILURE = 3; |
| /// There was an error from the fuchsia.pkg.RepositoryRegistry. |
| REPOSITORY_MANAGER_ERROR = 4; |
| /// There was a error from fuchsia.pkg.rewrite.Engine. |
| REWRITE_ENGINE_ERROR = 5; |
| /// Unknown repository spec type. |
| UNKNOWN_REPOSITORY_SPEC = 6; |
| /// Repository spec is missing a required field. |
| MISSING_REPOSITORY_SPEC_FIELD = 7; |
| /// Some unspecified error occurred during I/O. |
| IO_ERROR = 8; |
| /// Some unspecified internal error occurred. |
| INTERNAL_ERROR = 9; |
| /// Repository metadata is expired. |
| EXPIRED_REPOSITORY_METADATA = 10; |
| /// No repository registration matches the provided repository and target. |
| NO_MATCHING_REGISTRATION = 11; |
| /// The server is not running. |
| SERVER_NOT_RUNNING = 12; |
| /// The provided URL was invalid. |
| INVALID_URL = 13; |
| /// The repository server address is already in use. |
| SERVER_ADDRESS_ALREADY_IN_USE = 14; |
| /// No package matches the provided name. |
| NO_MATCHING_PACKAGE = 15; |
| /// The repository registration has a conflicting alias. |
| CONFLICTING_REGISTRATION = 16; |
| /// The repository metadata cannot be found. |
| REPOSITORY_METADATA_NOT_FOUND = 17; |
| }; |