This doc will guide you through some of the features of ffx. For an overview of the design and components of ffx, see this doc.
Warning: ffx is currently in alpha. Its APIs, command-line surface, and documentation are subject to change.
If you discover possible bugs or have questions or suggestions, file a bug.
To follow the examples in this doc, you‘ll need a Fuchsia device running. If you don’t have a physical device connected, you can use an emulator with networking enabled (-N).
Tip: To start a headless emulator, run fx emu --headless --software-gpu -N.
Your device must be running a core product configuration or a product configuration which extends core (such as workstation).
Optionally, you can run fx log, which will provide some additional information about the interactions between ffx and your Fuchsia target device.
After following all the prerequisites, run the following in a terminal:
fx ffx help
This will list all of the available ffx subcommands. You'll see something like:
Usage: ffx [-c <config>] [-e <env>] [-t <target>] [<command>] [<args>] Fuchsia's developer tool Options: -c, --config override default configuration -e, --env override default environment settings -t, --target apply operations across single or multiple targets --help display usage information Commands: component Discover and manage components config View and switch default and user configurations daemon Interact with/control the ffx daemon diagnostic Run diagnostic tests on Fuchsia targets docs View suite of docs for ffx and for Fuchsia doctor Run common checks for the ffx tool and host environment emulator Start and manage Fuchsia emulators overnet Interact with the Overnet mesh package Create and publish Fuchsia packages sdk Modify or query the installed SDKs target Interact with a target device or emulator vendor Run partner plugins version Print out ffx tool and daemon versions
You can use fx ffx help <subcommand> or fx ffx <subcommand> --help to see more about any subcommand.
In a terminal, run the following:
$ fx ffx target list
You'll see a list of devices that ffx has discovered. For example, with a single emulator running, output looks like:
NAME TYPE STATE ADDRS/IP AGE RCS step-atom-yard-juicy Unknown Unknown [fe80::5054:ff:fe63:5e7a%4] 0m0s N
NOTE: Ignore the TYPE and STATE columns - they have no values besides UNKNOWN right now.
A couple columns worth explanation:
AGE: this is the time since ffx was last able to reach the device.RCS: Indicates whether there is a reachable instance of the Remote Control Service (RCS) running on the device.If you wait 10 to 15 seconds and run the same command again, you should see the value in the RCS column change to Y.
$ fx ffx target list NAME TYPE STATE ADDRS/IP AGE RCS step-atom-yard-juicy Unknown Unknown [fe80::5054:ff:fe63:5e7a%4] 0m6s Y
If you had fx log running, you should also see something like the following in the logs:
[00009.776170][28540][28542][remote-control, remote_control_bin] INFO: published remote control service to overnet
NOTE: if the RCS column remains N for an extended amount of time, reach out to the ffx team.
TODO: fill this out.
You can use the target off and target reboot subcommands to power-off or reboot a device, respectively.
TODO
Many ffx commands that interact with components or services take component selectors as a parameter. Component selectors in ffx use the same syntax as the component selectors in the diagnostics library.
Here are some example selectors, all of which select the Remote Control Service:
core/remote-control:out:fuchsia.developer.remotecontrol.RemoteControl core/*:out:fuchsia.developer.remotecontrol.RemoteControl core/*:expose:fuchsia.developer.remotecontrol.RemoteControl core/remote-control:out:* core/*:expose:fuchsia.developer.remotecontrol.R*
There are 3 constituent segments of a selector: <component moniker>:<node selector>:<property selector>. Each is discussed below. The wildcard (*) is valid in each segment of a selector.
Consider this example: core/remote-control:out:fuchsia.developer.remotecontrol.RemoteControl
core/remote-control is the component moniker. This uniquely specifies a path in the component topology.
Note: You can use * to wildcard a particular level in the topology, but * is not recursive. That is, a/*/c will match a/b/c but would not match a/b/b2/c.
out is the node selector. In ffx, this must be one of the following values, which correspond to the routing terminology used in the component manifest and defined here.
out: services offered by the component. Corresponds to offer in the component manifest.expose: services exposed by the component. Corresponds to expose in the component manifest.in: services depended upon by the component. Corresponds to use in the component manifest.fuchsia.developer.remotecontrol.RemoteControl is the property selector and is matched against fully-qualified FIDL service names in the routing directory/directories matched by the node selector.
You may optionally omit the property selector: core/remote-control:out is equivalent to core/remote-control:out:*.
You can use the component select command to inspect services in the component topology. For example, the following command will display all services offered by v1 components:
$ fx ffx component select 'core/appmgr:out:*'` core/appmgr | --out | --chromium.cast.ApplicationConfigManager --fuchsia.bluetooth.avrcp.PeerManager --fuchsia.bluetooth.avrcp.test.PeerManagerExt --fuchsia.bluetooth.bredr.Profile --fuchsia.bluetooth.control.Control --fuchsia.bluetooth.gatt.Server --fuchsia.bluetooth.le.Central --fuchsia.bluetooth.le.Peripheral --fuchsia.bluetooth.snoop.Snoop --fuchsia.bluetooth.sys.Access --fuchsia.bluetooth.sys.HostWatcher --fuchsia.boot.Arguments --fuchsia.boot.FactoryItems --fuchsia.boot.Items --fuchsia.boot.ReadOnlyLog --fuchsia.boot.RootJobForInspect --fuchsia.boot.RootResource [truncated]
Note: this command can be slow (~10-15s), especially for selectors that match a large number of services.
You can use the component knock command to verify that a service starts successfully: knock will open a channel to the service and return success if and only if the channel isn't closed.
The component framework will start the component that provides the service on-demand.
Note: the selector you pass to knock may contain a wildcard but must match exactly one service. You cannot knock on multiple services at once.
For example:
$ fx ffx component knock 'core/appmgr:out:fuchsia.hwinfo.P*' Success: service is up. Connected to 'core/appmgr:out:fuchsia.hwinfo.Product'. $ fx ffx component knock 'core/appmgr:out:not.a.real.service' Failed to connect to service: NoMatchingServices
ffx can run components on a device given their package URL and arguments. stdout and stderr will be streamed to the corresponding descriptor on the host terminal.
Only v1 components can be run: v2 components are only started on-demand by the framework. Learn more about the component lifecycle here.
Note: fx serve must be running in order to component run a package that is not in base or cached.
Here‘s an example of running the Rust hello-world component. First, you’ll need the hello-world package in your universe:
$ fx set <product>.<board> --with //examples/hello_world/rust:hello_world_rust && fx build ... $ fx ffx component run fuchsia-pkg://fuchsia.com/hello_world_rust#meta/hello_world_rust.cmx Hello, world!
If you‘re experiencing problems communicating with a target device using ffx, you can use the doctor command to diagnose and attempt to resolve them. If you file a bug that involves a target device, we’ll typically ask for the output from ffx doctor to provide information about where the problem is.
doctor will attempt to communicate with the ffx daemon, killing and restarting it if needed. If this is successful, it will attempt to SSH into a target device and start the Remote Control Service.
If you try running ffx doctor under normal circumstances, you should see:
$ fx ffx doctor Checking for a running daemon...none running. Attempting to kill any zombie daemons...killed at least one daemon. Starting a new daemon instance...success Attempting to connect to the daemon. This may take a couple seconds...success Attempting to communicate with the daemon...success Attempting to list targets...success Attempting to get an RCS connection...success Attempting to communicate with RCS...success SUCCESS. You should be able to run ffx commands now.
If doctor fails, it will try to suggest a resolution to the problem. It will also provide a link to the Monorail component in which you can file a bug if you persistently have problems. For example, if doctor is unable to start the RCS, you would see the following:
$ fx ffx doctor Checking for a running daemon...found Attempting to connect to the daemon. This may take a couple seconds...success Attempting to communicate with the daemon...success Attempting to list targets...success Attempting to get an RCS connection...success Attempting to communicate with RCS...FAILED. Timed out. Attempt 2 of 3 Attempting to list targets...success Attempting to get an RCS connection...success Attempting to communicate with RCS...FAILED. Timed out. Attempt 3 of 3 Attempting to list targets...success Attempting to get an RCS connection...success Attempting to communicate with RCS...FAILED. Timed out. Connecting to RCS failed after maximum attempts. To resolve this issue, try rebooting your device. If this persists, please file a bug at the link below and include 1) all output above and 2) device syslog if available.Bug link: ...
ffx.