Skip to content

Commit cb58ab9

Browse files
committed
Add device list command (#21)
This PR introduces the device list command, useful to retrieve devices of arduino iot cloud. To list devices, no flags or arguments are needed, the command is simply: $ iot-cloud-cli device list maybe worth doing in the future: list command could accept a list of IDs that should be retrieved from the cloud edit: a new show command might be better commits log: * Add device list command * Add comments * Update readme
1 parent bcf3965 commit cb58ab9

File tree

5 files changed

+124
-66
lines changed

5 files changed

+124
-66
lines changed

Diff for: README.md

+4-66
Original file line numberDiff line numberDiff line change
@@ -1,18 +1,13 @@
11
# iot-cloud-cli
22

3-
iot-cloud-cli is a command line interface that allows to exploit the features of Arduino IoT Cloud. As of now, it is possible to provision a device and to simulate a device to be connected to the cloud using MQTT for troubleshooting purposes.
3+
iot-cloud-cli is a command line interface that allows to exploit the features of Arduino IoT Cloud. As of now, it is possible to provision a device.
44

55
### Requirements
66

77
This is all you need to use iot-cloud-cli for device **provisioning**:
88
* A client ID and a secret ID, retrievable from the [cloud](https://create.arduino.cc/iot/integrations) by creating a new API key
99
* The folder containing the precompiled provisioning firmwares (`binaries`) needs to be in the same location you run the command from
1010

11-
This is all you need to use iot-cloud-cli as a **virtual device**:
12-
* A "Generic ESP8266 Module" or "Generic ESP32 Module" device in IoT Cloud (requires a Maker plan)
13-
* A thing with a `counter` property connected to the "Generic ESP8266/ESP32 Module" device
14-
15-
1611
## Set a configuration
1712

1813
iot-cloud-cli needs to be configured before being used. In particular a client ID and the corresponding secret ID should be set.
@@ -38,64 +33,7 @@ Use this command to provision a device:
3833
3934
`$ iot-cloud-cli device create --name <deviceName> --port <port> --fqbn <deviceFqbn>`
4035

36+
## Device commands
4137

42-
## Use iot-cloud-cli as a virtual device
43-
44-
The iot-cloud-cli can be used as a virtual device for Arduino IoT Cloud for testing.
45-
46-
```
47-
$ iot-cloud-cli ping -u "<deviceId>" -p "<secret>" -t <thing ID>>
48-
Connected to Arduino IoT Cloud
49-
Subscribed true
50-
Property value sent successfully 81
51-
Property value sent successfully 87
52-
```
53-
54-
### How to set up the device and thing in IoT Cloud
55-
56-
#### Device
57-
58-
* Visit https://create.arduino.cc/iot/devices and select "Add device".
59-
* Select "Set up a 3rd party device".
60-
* Select "ESP8266".
61-
* From the drop down select "Generic ESP8266 Module", and click "Continue".
62-
* Pick a nice and friendly device name.
63-
* Save the "Device ID" and "Secret Key" in a safe place (1Password, KeepassXC, a piece of paper in your vault) , because you will not be able to see them anymore.
64-
65-
#### Thing ID
66-
67-
* Visit https://create.arduino.cc/iot/things and select "Create Thing".
68-
* Select "Add Variable".
69-
* Give the variable the name "counter", type "Integer Number" and leave the variable permission the value "Read & Write".
70-
* Press the "Add Variable" button to confirm.
71-
* Copy the "Thing ID" from the bottom right of the page.
72-
73-
#### Connect the device and the thing
74-
75-
You should connect the new device to the new thing.
76-
77-
#### Testing
78-
79-
##### Connect to the PROD environment
80-
81-
```shell
82-
$ iot-cloud-cli ping -u "<Device ID>" -p "<Secret Key>" -t <Thing ID>>
83-
```
84-
85-
If every works as expected you should see something similar to this output:
86-
```
87-
Connected to Arduino IoT Cloud
88-
Subscribed true
89-
Property value sent successfully 81
90-
Property value sent successfully 87
91-
```
92-
93-
If you visit https://create.arduino.cc/iot/devices the "Generic ESP8266 Module" device status should be "Online".
94-
95-
##### Connect to the DEV environment
96-
97-
The DEV environment is using a different broker, so you need to add the option `--host`:
98-
99-
```shell
100-
$ iot-cloud-cli ping --host tcps://mqtts-sa.iot.oniudra.cc:8884 -u "<Device ID>" -p "<Secret Key>" -t "<thing-id>"
101-
```
38+
Devices currently present on Arduino IoT Cloud can be retrieved by using this command:
39+
`$ iot-cloud-cli device list`

Diff for: cli/device/device.go

+1
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,7 @@ func NewCommand() *cobra.Command {
1212
}
1313

1414
deviceCommand.AddCommand(initCreateCommand())
15+
deviceCommand.AddCommand(initListCommand())
1516

1617
return deviceCommand
1718
}

Diff for: cli/device/list.go

+59
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,59 @@
1+
package device
2+
3+
import (
4+
"fmt"
5+
6+
"github.com/arduino/arduino-cli/cli/feedback"
7+
"github.com/arduino/arduino-cli/table"
8+
"github.com/arduino/iot-cloud-cli/command/device"
9+
"github.com/spf13/cobra"
10+
)
11+
12+
func initListCommand() *cobra.Command {
13+
listCommand := &cobra.Command{
14+
Use: "list",
15+
Short: "List devices",
16+
Long: "List devices on Arduino IoT Cloud",
17+
RunE: runListCommand,
18+
}
19+
return listCommand
20+
}
21+
22+
func runListCommand(cmd *cobra.Command, args []string) error {
23+
fmt.Println("Listing devices")
24+
25+
devs, err := device.List()
26+
if err != nil {
27+
return err
28+
}
29+
30+
feedback.PrintResult(result{devs})
31+
32+
return nil
33+
}
34+
35+
type result struct {
36+
devices []device.DeviceInfo
37+
}
38+
39+
func (r result) Data() interface{} {
40+
return r.devices
41+
}
42+
43+
func (r result) String() string {
44+
if len(r.devices) == 0 {
45+
return "No devices found."
46+
}
47+
t := table.New()
48+
t.SetHeader("Name", "ID", "Board", "FQBN", "SerialNumber")
49+
for _, device := range r.devices {
50+
t.AddRow(
51+
device.Name,
52+
device.ID,
53+
device.Board,
54+
device.FQBN,
55+
device.Serial,
56+
)
57+
}
58+
return t.Render()
59+
}

Diff for: command/device/list.go

+48
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,48 @@
1+
package device
2+
3+
import (
4+
"github.com/arduino/iot-cloud-cli/internal/config"
5+
"github.com/arduino/iot-cloud-cli/internal/iot"
6+
)
7+
8+
// DeviceInfo contains the most interesting
9+
// parameters of an Arduino IoT Cloud device.
10+
type DeviceInfo struct {
11+
Name string
12+
ID string
13+
Board string
14+
Serial string
15+
FQBN string
16+
}
17+
18+
// List command is used to list
19+
// the devices of Arduino IoT Cloud.
20+
func List() ([]DeviceInfo, error) {
21+
conf, err := config.Retrieve()
22+
if err != nil {
23+
return nil, err
24+
}
25+
iotClient, err := iot.NewClient(conf.Client, conf.Secret)
26+
if err != nil {
27+
return nil, err
28+
}
29+
30+
foundDevices, err := iotClient.ListDevices()
31+
if err != nil {
32+
return nil, err
33+
}
34+
35+
var devices []DeviceInfo
36+
for _, foundDev := range foundDevices {
37+
dev := DeviceInfo{
38+
Name: foundDev.Name,
39+
ID: foundDev.Id,
40+
Board: foundDev.Type,
41+
Serial: foundDev.Serial,
42+
FQBN: foundDev.Fqbn,
43+
}
44+
devices = append(devices, dev)
45+
}
46+
47+
return devices, nil
48+
}

Diff for: internal/iot/client.go

+12
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@ import (
1010
// Client can be used to perform actions on the arduino iot cloud.
1111
type Client interface {
1212
AddDevice(fqbn, name, serial, devType string) (string, error)
13+
ListDevices() ([]iotclient.ArduinoDevicev2, error)
1314
AddCertificate(id, csr string) (*iotclient.ArduinoCompressedv2, error)
1415
}
1516

@@ -47,6 +48,17 @@ func (cl *client) AddDevice(fqbn, name, serial, dType string) (string, error) {
4748
return dev.Id, nil
4849
}
4950

51+
// ListDevices retrieves and returns a list of all Arduino IoT Cloud devices
52+
// belonging to the user performing the request.
53+
func (cl *client) ListDevices() ([]iotclient.ArduinoDevicev2, error) {
54+
devices, _, err := cl.api.DevicesV2Api.DevicesV2List(cl.ctx, nil)
55+
if err != nil {
56+
err = fmt.Errorf("listing devices: %w", err)
57+
return nil, err
58+
}
59+
return devices, nil
60+
}
61+
5062
// AddCertifcate allows to upload a certificate on arduino iot cloud.
5163
// It returns the certificate parameters populated by the cloud.
5264
func (cl *client) AddCertificate(id, csr string) (*iotclient.ArduinoCompressedv2, error) {

0 commit comments

Comments
 (0)