Skip to content

Commit 529cb89

Browse files
committed
Added SetSketchDefaults gRPC call
This allows to finally remove wrong access to `sketch.Sketch` from `cli` package.
1 parent 063ca1c commit 529cb89

File tree

9 files changed

+836
-470
lines changed

9 files changed

+836
-470
lines changed

arduino/errors.go

+13
Original file line numberDiff line numberDiff line change
@@ -516,6 +516,19 @@ func (e *CantCreateSketchError) Unwrap() error {
516516
return e.Cause
517517
}
518518

519+
// CantUpdateSketchError is returned when the sketch cannot be updated
520+
type CantUpdateSketchError struct {
521+
Cause error
522+
}
523+
524+
func (e *CantUpdateSketchError) Error() string {
525+
return composeErrorMsg(tr("Can't update sketch"), e.Cause)
526+
}
527+
528+
func (e *CantUpdateSketchError) Unwrap() error {
529+
return e.Cause
530+
}
531+
519532
// CantOpenSketchError is returned when the sketch is not found or cannot be opened
520533
type CantOpenSketchError struct {
521534
Cause error

commands/daemon/daemon.go

+6
Original file line numberDiff line numberDiff line change
@@ -202,6 +202,12 @@ func (s *ArduinoCoreServerImpl) LoadSketch(ctx context.Context, req *rpc.LoadSke
202202
return resp, convertErrorToRPCStatus(err)
203203
}
204204

205+
// SetSketchDefaults FIXMEDOC
206+
func (s *ArduinoCoreServerImpl) SetSketchDefaults(ctx context.Context, req *rpc.SetSketchDefaultsRequest) (*rpc.SetSketchDefaultsResponse, error) {
207+
resp, err := sketch.SetSketchDefaults(ctx, req)
208+
return resp, convertErrorToRPCStatus(err)
209+
}
210+
205211
// Compile FIXMEDOC
206212
func (s *ArduinoCoreServerImpl) Compile(req *rpc.CompileRequest, stream rpc.ArduinoCoreService_CompileServer) error {
207213
syncSend := NewSynchronizedSend(stream.Send)

commands/sketch/set_defaults.go

+57
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,57 @@
1+
// This file is part of arduino-cli.
2+
//
3+
// Copyright 2020 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 sketch
17+
18+
import (
19+
"context"
20+
21+
"github.com/arduino/arduino-cli/arduino"
22+
"github.com/arduino/arduino-cli/arduino/sketch"
23+
rpc "github.com/arduino/arduino-cli/rpc/cc/arduino/cli/commands/v1"
24+
paths "github.com/arduino/go-paths-helper"
25+
)
26+
27+
// SetSketchDefaults updates the sketch project file (sketch.yaml) with the given defaults
28+
// for the values `default_fqbn`, `default_port`, and `default_protocol`.
29+
func SetSketchDefaults(ctx context.Context, req *rpc.SetSketchDefaultsRequest) (*rpc.SetSketchDefaultsResponse, error) {
30+
sk, err := sketch.New(paths.New(req.SketchPath))
31+
if err != nil {
32+
return nil, &arduino.CantOpenSketchError{Cause: err}
33+
}
34+
35+
oldAddress, oldProtocol := sk.GetDefaultPortAddressAndProtocol()
36+
res := &rpc.SetSketchDefaultsResponse{
37+
DefaultFqbn: sk.GetDefaultFQBN(),
38+
DefaultPortAddress: oldAddress,
39+
DefaultPortProtocol: oldProtocol,
40+
}
41+
42+
if fqbn := req.GetDefaultFqbn(); fqbn != "" {
43+
if err := sk.SetDefaultFQBN(fqbn); err != nil {
44+
return nil, &arduino.CantUpdateSketchError{Cause: err}
45+
}
46+
res.DefaultFqbn = fqbn
47+
}
48+
if newAddress, newProtocol := req.GetDefaultPortAddress(), req.GetDefaultPortProtocol(); newAddress != "" {
49+
if err := sk.SetDefaultPort(newAddress, newProtocol); err != nil {
50+
return nil, &arduino.CantUpdateSketchError{Cause: err}
51+
}
52+
res.DefaultPortAddress = newAddress
53+
res.DefaultPortProtocol = newProtocol
54+
}
55+
56+
return res, nil
57+
}

internal/cli/arguments/sketch.go

-10
Original file line numberDiff line numberDiff line change
@@ -42,16 +42,6 @@ func InitSketchPath(path string) (sketchPath *paths.Path) {
4242
return sketchPath
4343
}
4444

45-
// NewSketch is a helper function useful to create a sketch instance
46-
// TODO: Remove this function, we should not access sketch:Sketch directly
47-
func NewSketch(sketchPath *paths.Path) *sketch.Sketch {
48-
sketch, err := sketch.New(sketchPath)
49-
if err != nil {
50-
feedback.Fatal(tr("Error opening sketch: %v", err), feedback.ErrGeneric)
51-
}
52-
return sketch
53-
}
54-
5545
// WarnDeprecatedFiles warns the user that a type of sketch files are deprecated
5646
func WarnDeprecatedFiles(sketchPath *paths.Path) {
5747
// .pde files are still supported but deprecated, this warning urges the user to rename them

internal/cli/board/attach.go

+19-27
Original file line numberDiff line numberDiff line change
@@ -16,11 +16,14 @@
1616
package board
1717

1818
import (
19+
"context"
1920
"fmt"
2021
"os"
2122

23+
"github.com/arduino/arduino-cli/commands/sketch"
2224
"github.com/arduino/arduino-cli/internal/cli/arguments"
2325
"github.com/arduino/arduino-cli/internal/cli/feedback"
26+
rpc "github.com/arduino/arduino-cli/rpc/cc/arduino/cli/commands/v1"
2427
"github.com/spf13/cobra"
2528
)
2629

@@ -51,39 +54,28 @@ func initAttachCommand() *cobra.Command {
5154

5255
func runAttachCommand(path string, port *arguments.Port, fqbn string) {
5356
sketchPath := arguments.InitSketchPath(path)
54-
sk := arguments.NewSketch(sketchPath)
5557

56-
var currentPort *boardAttachPortResult
57-
if currentAddress, currentProtocol := sk.GetDefaultPortAddressAndProtocol(); currentAddress != "" {
58-
currentPort = &boardAttachPortResult{
59-
Address: currentAddress,
60-
Protocol: currentProtocol,
61-
}
62-
}
63-
current := &boardAttachResult{
64-
Port: currentPort,
65-
Fqbn: sk.GetDefaultFQBN(),
58+
portAddress, portProtocol, _ := port.GetPortAddressAndProtocol(nil, "", "")
59+
newDefaults, err := sketch.SetSketchDefaults(context.Background(), &rpc.SetSketchDefaultsRequest{
60+
SketchPath: sketchPath.String(),
61+
DefaultFqbn: fqbn,
62+
DefaultPortAddress: portAddress,
63+
DefaultPortProtocol: portProtocol,
64+
})
65+
if err != nil {
66+
feedback.FatalError(err, feedback.ErrGeneric)
6667
}
6768

68-
defaultAddress, defaultProtocol := sk.GetDefaultPortAddressAndProtocol()
69-
address, protocol, _ := port.GetPortAddressAndProtocol(nil, defaultAddress, defaultProtocol)
70-
if address != "" {
71-
if err := sk.SetDefaultPort(address, protocol); err != nil {
72-
feedback.Fatal(fmt.Sprintf("%s: %s", tr("Error saving sketch metadata"), err), feedback.ErrGeneric)
73-
}
74-
current.Port = &boardAttachPortResult{
75-
Address: address,
76-
Protocol: protocol,
77-
}
69+
res := &boardAttachResult{
70+
Fqbn: newDefaults.GetDefaultFqbn(),
7871
}
79-
if fqbn != "" {
80-
if err := sk.SetDefaultFQBN(fqbn); err != nil {
81-
feedback.Fatal(fmt.Sprintf("%s: %s", tr("Error saving sketch metadata"), err), feedback.ErrGeneric)
72+
if newDefaults.GetDefaultPortAddress() != "" {
73+
res.Port = &boardAttachPortResult{
74+
Address: newDefaults.GetDefaultPortAddress(),
75+
Protocol: newDefaults.GetDefaultPortProtocol(),
8276
}
83-
current.Fqbn = fqbn
8477
}
85-
86-
feedback.PrintResult(current)
78+
feedback.PrintResult(res)
8779
}
8880

8981
type boardAttachPortResult struct {

internal/integrationtest/board/board_test.go

+41-9
Original file line numberDiff line numberDiff line change
@@ -510,23 +510,55 @@ func TestBoardSearch(t *testing.T) {
510510
]`)
511511
}
512512

513-
func TestBoardAttachWithoutSketchJson(t *testing.T) {
513+
func TestBoardAttach(t *testing.T) {
514514
env, cli := integrationtest.CreateArduinoCLIWithEnvironment(t)
515515
defer env.CleanUp()
516516

517-
_, _, err := cli.Run("update")
518-
require.NoError(t, err)
519-
520-
sketchName := "BoardAttachWithoutSketchJson"
517+
sketchName := "BoardAttach"
521518
sketchPath := cli.SketchbookDir().Join(sketchName)
522-
fqbn := "arduino:avr:uno"
519+
sketchProjectFlie := sketchPath.Join("sketch.yaml")
523520

524521
// Create a test sketch
525-
_, _, err = cli.Run("sketch", "new", sketchPath.String())
522+
_, _, err := cli.Run("sketch", "new", sketchPath.String())
526523
require.NoError(t, err)
527524

528-
_, _, err = cli.Run("board", "attach", "-b", fqbn, sketchPath.String())
529-
require.NoError(t, err)
525+
{
526+
stdout, _, err := cli.Run("board", "attach", "-b", "arduino:avr:uno", sketchPath.String(), "--format", "json")
527+
require.NoError(t, err)
528+
requirejson.Query(t, stdout, ".fqbn", `"arduino:avr:uno"`)
529+
530+
yamlData, err := sketchProjectFlie.ReadFile()
531+
require.NoError(t, err)
532+
require.Contains(t, string(yamlData), "default_fqbn: arduino:avr:uno")
533+
require.NotContains(t, string(yamlData), "default_port:")
534+
require.NotContains(t, string(yamlData), "default_protocol:")
535+
}
536+
{
537+
stdout, _, err := cli.Run("board", "attach", "-p", "/dev/ttyACM0", "-l", "serial", sketchPath.String(), "--format", "json")
538+
require.NoError(t, err)
539+
requirejson.Query(t, stdout, ".fqbn", `"arduino:avr:uno"`)
540+
requirejson.Query(t, stdout, ".port.address", `"/dev/ttyACM0"`)
541+
requirejson.Query(t, stdout, ".port.protocol", `"serial"`)
542+
543+
yamlData, err := sketchProjectFlie.ReadFile()
544+
require.NoError(t, err)
545+
require.Contains(t, string(yamlData), "default_fqbn: arduino:avr:uno")
546+
require.Contains(t, string(yamlData), "default_port: /dev/ttyACM0")
547+
require.Contains(t, string(yamlData), "default_protocol: serial")
548+
}
549+
{
550+
stdout, _, err := cli.Run("board", "attach", "-p", "/dev/ttyACM0", sketchPath.String(), "--format", "json")
551+
require.NoError(t, err)
552+
requirejson.Query(t, stdout, ".fqbn", `"arduino:avr:uno"`)
553+
requirejson.Query(t, stdout, ".port.address", `"/dev/ttyACM0"`)
554+
requirejson.Query(t, stdout, ".port.protocol", `null`)
555+
556+
yamlData, err := sketchProjectFlie.ReadFile()
557+
require.NoError(t, err)
558+
require.Contains(t, string(yamlData), "default_fqbn: arduino:avr:uno")
559+
require.Contains(t, string(yamlData), "default_port: /dev/ttyACM0")
560+
require.NotContains(t, string(yamlData), "default_protocol:")
561+
}
530562
}
531563

532564
func TestBoardSearchWithOutdatedCore(t *testing.T) {

0 commit comments

Comments
 (0)