Skip to content

Commit baa2ab0

Browse files
committed
Added integration-test to check handling of multiple discovery instances
1 parent 9522f68 commit baa2ab0

File tree

3 files changed

+117
-4
lines changed

3 files changed

+117
-4
lines changed

internal/integrationtest/arduino-cli.go

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -506,6 +506,13 @@ func (cli *ArduinoCLI) Create() *ArduinoCLIInstance {
506506
}
507507
}
508508

509+
// Destroy calls the "Destroy" gRPC method.
510+
func (inst *ArduinoCLIInstance) Destroy(ctx context.Context) error {
511+
logCallf(">>> Destroy(%v)\n", inst.instance.GetId())
512+
_, err := inst.cli.daemonClient.Destroy(ctx, &commands.DestroyRequest{Instance: inst.instance})
513+
return err
514+
}
515+
509516
// SetValue calls the "SetValue" gRPC method.
510517
func (cli *ArduinoCLI) SetValue(key, jsonData string) error {
511518
req := &commands.SettingsSetValueRequest{
Lines changed: 86 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,86 @@
1+
// This file is part of arduino-cli.
2+
//
3+
// Copyright 2025 ARDUINO SA (http://www.arduino.cc/)
4+
//
5+
// This software is released under the GNU General Public License version 3,
6+
// which covers the main part of arduino-cli.
7+
// The terms of this license can be found at:
8+
// https://www.gnu.org/licenses/gpl-3.0.en.html
9+
//
10+
// You can be released from the requirements of the above licenses by purchasing
11+
// a commercial license. Buying such a license is mandatory if you want to
12+
// modify or otherwise use the software for commercial activities involving the
13+
// Arduino software without disclosing the source code of your own applications.
14+
// To purchase a commercial license, send an email to [email protected].
15+
16+
package daemon
17+
18+
import (
19+
"fmt"
20+
"testing"
21+
"time"
22+
23+
"github.com/arduino/arduino-cli/internal/integrationtest"
24+
"github.com/arduino/arduino-cli/rpc/cc/arduino/cli/commands/v1"
25+
"github.com/stretchr/testify/require"
26+
)
27+
28+
func TestBoardListMock(t *testing.T) {
29+
env, cli := integrationtest.CreateEnvForDaemon(t)
30+
defer env.CleanUp()
31+
32+
_, _, err := cli.Run("core", "update-index")
33+
require.NoError(t, err)
34+
35+
cli.InstallMockedSerialDiscovery(t)
36+
37+
var tmp1, tmp2 string
38+
39+
{
40+
// Create a new instance of the daemon
41+
grpcInst := cli.Create()
42+
require.NoError(t, grpcInst.Init("", "", func(ir *commands.InitResponse) {
43+
fmt.Printf("INIT> %v\n", ir.GetMessage())
44+
}))
45+
46+
// Run a BoardList
47+
resp, err := grpcInst.BoardList(time.Second)
48+
require.NoError(t, err)
49+
require.NotEmpty(t, resp.Ports)
50+
for _, port := range resp.Ports {
51+
if port.GetPort().GetProtocol() == "serial" {
52+
tmp1 = port.Port.GetProperties()["discovery_tmp"]
53+
}
54+
}
55+
require.NotEmpty(t, tmp1)
56+
57+
// Close instance
58+
require.NoError(t, grpcInst.Destroy(t.Context()))
59+
}
60+
61+
{
62+
// Create a second instance of the daemon
63+
grpcInst := cli.Create()
64+
require.NoError(t, grpcInst.Init("", "", func(ir *commands.InitResponse) {
65+
fmt.Printf("INIT> %v\n", ir.GetMessage())
66+
}))
67+
68+
// Run a BoardList
69+
resp, err := grpcInst.BoardList(time.Second)
70+
require.NoError(t, err)
71+
require.NotEmpty(t, resp.Ports)
72+
for _, port := range resp.Ports {
73+
if port.GetPort().GetProtocol() == "serial" {
74+
tmp2 = port.Port.GetProperties()["discovery_tmp"]
75+
}
76+
}
77+
require.NotEmpty(t, tmp2)
78+
79+
// Close instance
80+
require.NoError(t, grpcInst.Destroy(t.Context()))
81+
}
82+
83+
// Check if the discoveries have been successfully close
84+
require.NoFileExists(t, tmp1, "discovery has not been closed")
85+
require.NoFileExists(t, tmp2, "discovery has not been closed")
86+
}

internal/mock_serial_discovery/main.go

Lines changed: 24 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -19,20 +19,39 @@ package main
1919

2020
import (
2121
"errors"
22+
"fmt"
2223
"os"
2324
"time"
2425

26+
"github.com/arduino/go-paths-helper"
2527
"github.com/arduino/go-properties-orderedmap"
2628
discovery "github.com/arduino/pluggable-discovery-protocol-handler/v2"
2729
)
2830

2931
type mockSerialDiscovery struct {
3032
startSyncCount int
3133
closeChan chan<- bool
34+
tmpFile string
3235
}
3336

3437
func main() {
35-
dummy := &mockSerialDiscovery{}
38+
// Write a file in a $TMP/mock_serial_discovery folder.
39+
// This file will be used by the integration tests to detect if the discovery is running.
40+
tmpDir := paths.TempDir().Join("mock_serial_discovery")
41+
if err := tmpDir.MkdirAll(); err != nil {
42+
fmt.Fprintf(os.Stderr, "Error creating temp dir: %v\n", err)
43+
os.Exit(1)
44+
}
45+
tmpFile, err := paths.MkTempFile(tmpDir, "")
46+
if err != nil {
47+
fmt.Fprintf(os.Stderr, "Error creating temp file: %v\n", err)
48+
os.Exit(1)
49+
}
50+
tmpFile.Close()
51+
defer os.Remove(tmpFile.Name())
52+
53+
// Run mock discovery
54+
dummy := &mockSerialDiscovery{tmpFile: tmpFile.Name()}
3655
server := discovery.NewServer(dummy)
3756
if err := server.Run(os.Stdin, os.Stdout); err != nil {
3857
os.Exit(1)
@@ -80,9 +99,10 @@ func (d *mockSerialDiscovery) StartSync(eventCB discovery.EventCallback, errorCB
8099
ProtocolLabel: "Serial",
81100
HardwareID: "123456",
82101
Properties: properties.NewFromHashmap(map[string]string{
83-
"vid": "0x2341",
84-
"pid": "0x0041",
85-
"serial": "123456",
102+
"vid": "0x2341",
103+
"pid": "0x0041",
104+
"serial": "123456",
105+
"discovery_tmp": d.tmpFile,
86106
}),
87107
})
88108

0 commit comments

Comments
 (0)