diff --git a/commands/instances.go b/commands/instances.go index 2ba91add4e5..838e031a1c2 100644 --- a/commands/instances.go +++ b/commands/instances.go @@ -388,6 +388,40 @@ func (s *arduinoCoreServerImpl) Init(req *rpc.InitRequest, stream rpc.ArduinoCor continue } + if libraryRef.GitURL != nil { + uid := libraryRef.InternalUniqueIdentifier() + libRoot := s.settings.ProfilesCacheDir().Join(uid) + libDir := libRoot.Join(libraryRef.Library) + + if !libDir.IsDir() { + // Clone repo and install + tmpDir, err := librariesmanager.CloneLibraryGitRepository(ctx, libraryRef.GitURL.String()) + if err != nil { + taskCallback(&rpc.TaskProgress{Name: i18n.Tr("Error downloading library %s", libraryRef)}) + e := &cmderrors.FailedLibraryInstallError{Cause: err} + responseError(e.GRPCStatus()) + continue + } + + // Install library into profile cache + copyErr := tmpDir.CopyDirTo(libDir) + _ = tmpDir.RemoveAll() + if copyErr != nil { + taskCallback(&rpc.TaskProgress{Name: i18n.Tr("Error installing library %s", libraryRef)}) + e := &cmderrors.FailedLibraryInstallError{Cause: fmt.Errorf("copying library to profile cache: %w", err)} + responseError(e.GRPCStatus()) + continue + } + } + + lmb.AddLibrariesDir(librariesmanager.LibrariesDir{ + Path: libDir, + Location: libraries.Profile, + IsSingleLibrary: true, + }) + continue + } + uid := libraryRef.InternalUniqueIdentifier() libRoot := s.settings.ProfilesCacheDir().Join(uid) libDir := libRoot.Join(libraryRef.Library) diff --git a/commands/service_library_install.go b/commands/service_library_install.go index f20b845615d..1cff02a3306 100644 --- a/commands/service_library_install.go +++ b/commands/service_library_install.go @@ -267,9 +267,8 @@ func (s *arduinoCoreServerImpl) GitLibraryInstall(req *rpc.GitLibraryInstallRequ lmi, release := lm.NewInstaller() defer release() - // TODO: pass context - // ctx := stream.Context() - if err := lmi.InstallGitLib(req.GetUrl(), req.GetOverwrite()); err != nil { + ctx := stream.Context() + if err := lmi.InstallGitLib(ctx, req.GetUrl(), req.GetOverwrite()); err != nil { return &cmderrors.FailedLibraryInstallError{Cause: err} } taskCB(&rpc.TaskProgress{Message: i18n.Tr("Library installed"), Completed: true}) diff --git a/commands/service_profile_lib_add.go b/commands/service_profile_lib_add.go index 34fa8819e76..5f5e909d326 100644 --- a/commands/service_profile_lib_add.go +++ b/commands/service_profile_lib_add.go @@ -18,6 +18,7 @@ package commands import ( "cmp" "context" + "net/url" "slices" "github.com/arduino/arduino-cli/commands/cmderrors" @@ -59,6 +60,15 @@ func (s *arduinoCoreServerImpl) ProfileLibAdd(ctx context.Context, req *rpc.Prof addedLib := &sketch.ProfileLibraryReference{InstallDir: path} profile.Libraries = append(profile.Libraries, addedLib) addedLibs = append(addedLibs, addedLib) + } else if reqGitLib := req.GetLibrary().GetGitLibrary(); reqGitLib != nil { + // Add a git library + gitURL, err := url.Parse(reqGitLib.GetUrl()) + if err != nil { + return nil, &cmderrors.InvalidURLError{Cause: err} + } + addedLib := &sketch.ProfileLibraryReference{GitURL: gitURL} + profile.Libraries = append(profile.Libraries, addedLib) + addedLibs = append(addedLibs, addedLib) } else if reqIndexLib := req.GetLibrary().GetIndexLibrary(); reqIndexLib != nil { // Obtain the library index from the manager li, err := instances.GetLibrariesIndex(req.GetInstance()) diff --git a/internal/arduino/libraries/librariesmanager/install.go b/internal/arduino/libraries/librariesmanager/install.go index 9b53910d41a..305c1eec423 100644 --- a/internal/arduino/libraries/librariesmanager/install.go +++ b/internal/arduino/libraries/librariesmanager/install.go @@ -200,54 +200,64 @@ func (lmi *Installer) InstallZipLib(ctx context.Context, archivePath *paths.Path } // InstallGitLib installs a library hosted on a git repository on the specified path. -func (lmi *Installer) InstallGitLib(argURL string, overwrite bool) error { - libraryName, gitURL, ref, err := parseGitArgURL(argURL) +func (lmi *Installer) InstallGitLib(ctx context.Context, argURL string, overwrite bool) error { + tmpInstallPath, err := CloneLibraryGitRepository(ctx, argURL) if err != nil { return err } + defer tmpInstallPath.RemoveAll() + + // Install extracted library in the destination directory + if err := lmi.importLibraryFromDirectory(tmpInstallPath, overwrite); err != nil { + return errors.New(i18n.Tr("moving extracted archive to destination dir: %s", err)) + } + + return nil +} + +// CloneLibraryGitRepository clones a git repository containing a library +// into a temporary directory and returns the path to the cloned library. +func CloneLibraryGitRepository(ctx context.Context, argURL string) (*paths.Path, error) { + libraryName, gitURL, ref, err := parseGitArgURL(argURL) + if err != nil { + return nil, err + } // Clone library in a temporary directory tmp, err := paths.MkTempDir("", "") if err != nil { - return err + return nil, err } - defer tmp.RemoveAll() tmpInstallPath := tmp.Join(libraryName) - if _, err := git.PlainClone(tmpInstallPath.String(), false, &git.CloneOptions{ + if _, err := git.PlainCloneContext(ctx, tmpInstallPath.String(), false, &git.CloneOptions{ URL: gitURL, ReferenceName: plumbing.ReferenceName(ref), }); err != nil { if err.Error() != "reference not found" { - return err + return nil, err } // We did not find the requested reference, let's do a PlainClone and use // "ResolveRevision" to find and checkout the requested revision - if repo, err := git.PlainClone(tmpInstallPath.String(), false, &git.CloneOptions{ + if repo, err := git.PlainCloneContext(ctx, tmpInstallPath.String(), false, &git.CloneOptions{ URL: gitURL, }); err != nil { - return err + return nil, err } else if h, err := repo.ResolveRevision(plumbing.Revision(ref)); err != nil { - return err + return nil, err } else if w, err := repo.Worktree(); err != nil { - return err + return nil, err } else if err := w.Checkout(&git.CheckoutOptions{ Force: true, // workaround for: https://github.com/go-git/go-git/issues/1411 Hash: plumbing.NewHash(h.String())}); err != nil { - return err + return nil, err } } // We don't want the installed library to be a git repository thus we delete this folder tmpInstallPath.Join(".git").RemoveAll() - - // Install extracted library in the destination directory - if err := lmi.importLibraryFromDirectory(tmpInstallPath, overwrite); err != nil { - return errors.New(i18n.Tr("moving extracted archive to destination dir: %s", err)) - } - - return nil + return tmpInstallPath, nil } // parseGitArgURL tries to recover a library name from a git URL. diff --git a/internal/arduino/sketch/profiles.go b/internal/arduino/sketch/profiles.go index bc74c2a2c4e..13f7911394f 100644 --- a/internal/arduino/sketch/profiles.go +++ b/internal/arduino/sketch/profiles.go @@ -21,6 +21,7 @@ import ( "errors" "fmt" "net/url" + "path/filepath" "regexp" "slices" "strings" @@ -354,6 +355,7 @@ type ProfileLibraryReference struct { Version *semver.Version IsDependency bool InstallDir *paths.Path + GitURL *url.URL } // UnmarshalYAML decodes a ProfileLibraryReference from YAML source. @@ -375,6 +377,19 @@ func (l *ProfileLibraryReference) UnmarshalYAML(unmarshal func(interface{}) erro } l.IsDependency = true // Fallback + } else if gitUrl, ok := dataMap["git"]; ok { + if gitUrlStr, ok := gitUrl.(string); !ok { + return fmt.Errorf("%s: %s", i18n.Tr("invalid library reference"), dataMap) + } else if parsedUrl, err := url.Parse(gitUrlStr); err != nil { + return fmt.Errorf("%s: %w", i18n.Tr("invalid git URL"), err) + } else { + l.GitURL = parsedUrl + if l.Library = filepath.Base(parsedUrl.Path); l.Library == "" { + l.Library = "lib" + } + l.Library = strings.TrimSuffix(l.Library, ".git") + return nil + } } else { return fmt.Errorf("%s: %s", i18n.Tr("invalid library reference"), dataMap) } @@ -401,6 +416,9 @@ func (l *ProfileLibraryReference) AsYaml() string { if l.InstallDir != nil { return fmt.Sprintf(" - dir: %s\n", l.InstallDir) } + if l.GitURL != nil { + return fmt.Sprintf(" - git: %s\n", l.GitURL) + } dep := "" if l.IsDependency { dep = "dependency: " @@ -412,6 +430,9 @@ func (l *ProfileLibraryReference) String() string { if l.InstallDir != nil { return "@dir:" + l.InstallDir.String() } + if l.GitURL != nil { + return "@git:" + l.GitURL.String() + } dep := "" if l.IsDependency { dep = " (dep)" @@ -431,6 +452,14 @@ func (l *ProfileLibraryReference) Match(other *ProfileLibraryReference) bool { if other.InstallDir != nil { return false } + + if l.GitURL != nil { + return other.GitURL != nil && l.GitURL.String() == other.GitURL.String() + } + if other.GitURL != nil { + return false + } + if l.Library != other.Library { return false } @@ -451,6 +480,15 @@ func (l *ProfileLibraryReference) ToRpc() *rpc.ProfileLibraryReference { }, } } + if l.GitURL != nil { + return &rpc.ProfileLibraryReference{ + Library: &rpc.ProfileLibraryReference_GitLibrary_{ + GitLibrary: &rpc.ProfileLibraryReference_GitLibrary{ + Url: l.GitURL.String(), + }, + }, + } + } return &rpc.ProfileLibraryReference{ Library: &rpc.ProfileLibraryReference_IndexLibrary_{ IndexLibrary: &rpc.ProfileLibraryReference_IndexLibrary{ @@ -471,6 +509,13 @@ func FromRpcProfileLibraryReference(l *rpc.ProfileLibraryReference) (*ProfileLib } return &ProfileLibraryReference{InstallDir: path}, nil } + if gitLib := l.GetGitLibrary(); gitLib != nil { + gitURL, err := url.Parse(gitLib.GetUrl()) + if err != nil { + return nil, &cmderrors.InvalidURLError{Cause: err} + } + return &ProfileLibraryReference{GitURL: gitURL}, nil + } if indexLib := l.GetIndexLibrary(); indexLib != nil { var version *semver.Version if indexLib.GetVersion() != "" { @@ -494,6 +539,15 @@ func (l *ProfileLibraryReference) InternalUniqueIdentifier() string { f.Assert(l.InstallDir == nil, "InternalUniqueIdentifier should not be called for library references with an install directory") + if l.GitURL != nil { + id := "git-" + utils.SanitizeName(l.GitURL.Host+l.GitURL.Path+"#"+l.GitURL.Fragment) + if len(id) > 50 { + id = id[:50] + } + h := sha256.Sum256([]byte(l.GitURL.String())) + return id + "-" + hex.EncodeToString(h[:])[:8] + } + id := l.Library + "@" + l.Version.String() h := sha256.Sum256([]byte(id)) res := fmt.Sprintf("%s_%s", id, hex.EncodeToString(h[:])[:16]) diff --git a/internal/arduino/sketch/profiles_test.go b/internal/arduino/sketch/profiles_test.go index c19d0b9661a..661d6810806 100644 --- a/internal/arduino/sketch/profiles_test.go +++ b/internal/arduino/sketch/profiles_test.go @@ -60,15 +60,19 @@ func TestProjectFileLibraries(t *testing.T) { require.NoError(t, err) require.Len(t, proj.Profiles, 1) prof := proj.Profiles[0] - require.Len(t, prof.Libraries, 4) + require.Len(t, prof.Libraries, 6) require.Equal(t, "FlashStorage@1.2.3", prof.Libraries[0].String()) require.Equal(t, "@dir:/path/to/system/lib", prof.Libraries[1].String()) require.Equal(t, "@dir:path/to/sketch/lib", prof.Libraries[2].String()) require.Equal(t, "DependencyLib@2.3.4 (dep)", prof.Libraries[3].String()) + require.Equal(t, "@git:https://github.com/username/HelloWorld.git#v2.13", prof.Libraries[4].String()) + require.Equal(t, "@git:https://github.com/username/HelloWorld.git#v2.14", prof.Libraries[5].String()) require.Equal(t, "FlashStorage_1.2.3_e525d7c96b27788f", prof.Libraries[0].InternalUniqueIdentifier()) require.Panics(t, func() { prof.Libraries[1].InternalUniqueIdentifier() }) require.Panics(t, func() { prof.Libraries[2].InternalUniqueIdentifier() }) require.Equal(t, "DependencyLib_2.3.4_ecde631facb47ae5", prof.Libraries[3].InternalUniqueIdentifier()) + require.Equal(t, "git-github.com_username_HelloWorld.git_v2.13-0c146203", prof.Libraries[4].InternalUniqueIdentifier()) + require.Equal(t, "git-github.com_username_HelloWorld.git_v2.14-49f5df7f", prof.Libraries[5].InternalUniqueIdentifier()) orig, err := sketchProj.ReadFile() require.NoError(t, err) diff --git a/internal/arduino/sketch/testdata/profiles/profile_with_libraries.yml b/internal/arduino/sketch/testdata/profiles/profile_with_libraries.yml index b7d2ef55216..dee566f3e80 100644 --- a/internal/arduino/sketch/testdata/profiles/profile_with_libraries.yml +++ b/internal/arduino/sketch/testdata/profiles/profile_with_libraries.yml @@ -8,5 +8,7 @@ profiles: - dir: /path/to/system/lib - dir: path/to/sketch/lib - dependency: DependencyLib (2.3.4) + - git: https://github.com/username/HelloWorld.git#v2.13 + - git: https://github.com/username/HelloWorld.git#v2.14 default_profile: giga_any diff --git a/internal/cli/feedback/result/rpc.go b/internal/cli/feedback/result/rpc.go index 31a87eb564d..9064d3170ce 100644 --- a/internal/cli/feedback/result/rpc.go +++ b/internal/cli/feedback/result/rpc.go @@ -1126,6 +1126,22 @@ func NewIndexUpdateReport_Status(r rpc.IndexUpdateReport_Status) IndexUpdateRepo } } +type ProfileLibraryReference_GitLibraryResult struct { + Url string `json:"url,omitempty"` +} + +func NewProfileLibraryReference_GitLibraryResult(resp *rpc.ProfileLibraryReference_GitLibrary) *ProfileLibraryReference_GitLibraryResult { + return &ProfileLibraryReference_GitLibraryResult{ + Url: resp.GetUrl(), + } +} + +func (*ProfileLibraryReference_GitLibraryResult) isProfileLibraryReference() {} + +func (l *ProfileLibraryReference_GitLibraryResult) String() string { + return fmt.Sprintf("git: %s", l.Url) +} + type ProfileLibraryReference_LocalLibraryResult struct { Path string `json:"path,omitempty"` } @@ -1182,6 +1198,12 @@ func NewProfileLibraryReference(resp *rpc.ProfileLibraryReference) *ProfileLibra Kind: "index", } } + if lib := resp.GetGitLibrary(); lib != nil { + return &ProfileLibraryReference{ + Library: NewProfileLibraryReference_GitLibraryResult(lib), + Kind: "git", + } + } if lib := resp.GetLocalLibrary(); lib != nil { return &ProfileLibraryReference{ Library: NewProfileLibraryReference_LocalLibraryResult(lib), diff --git a/internal/cli/feedback/result/rpc_test.go b/internal/cli/feedback/result/rpc_test.go index 1ccafb7945a..86ae34eb946 100644 --- a/internal/cli/feedback/result/rpc_test.go +++ b/internal/cli/feedback/result/rpc_test.go @@ -238,6 +238,10 @@ func TestAllFieldAreMapped(t *testing.T) { profileLibraryReference_IndexLibraryResult := result.NewProfileLibraryReference_IndexLibraryResult(profileLibraryReference_IndexLibraryRpc) mustContainsAllPropertyOfRpcStruct(t, profileLibraryReference_IndexLibraryRpc, profileLibraryReference_IndexLibraryResult) + profileLibraryReference_GitLibraryRpc := &rpc.ProfileLibraryReference_GitLibrary{} + profileLibraryReference_GitLibraryResult := result.NewProfileLibraryReference_GitLibraryResult(profileLibraryReference_GitLibraryRpc) + mustContainsAllPropertyOfRpcStruct(t, profileLibraryReference_GitLibraryRpc, profileLibraryReference_GitLibraryResult) + profileLibraryReference_LocalLibraryRpc := &rpc.ProfileLibraryReference_LocalLibrary{} profileLibraryReference_LocalLibraryResult := result.NewProfileLibraryReference_LocalLibraryResult(profileLibraryReference_LocalLibraryRpc) mustContainsAllPropertyOfRpcStruct(t, profileLibraryReference_LocalLibraryRpc, profileLibraryReference_LocalLibraryResult) diff --git a/rpc/cc/arduino/cli/commands/v1/common.pb.go b/rpc/cc/arduino/cli/commands/v1/common.pb.go index 5dd0371c21f..4135b485ab4 100644 --- a/rpc/cc/arduino/cli/commands/v1/common.pb.go +++ b/rpc/cc/arduino/cli/commands/v1/common.pb.go @@ -1446,6 +1446,7 @@ type ProfileLibraryReference struct { // // *ProfileLibraryReference_IndexLibrary_ // *ProfileLibraryReference_LocalLibrary_ + // *ProfileLibraryReference_GitLibrary_ Library isProfileLibraryReference_Library `protobuf_oneof:"library"` } @@ -1502,6 +1503,13 @@ func (x *ProfileLibraryReference) GetLocalLibrary() *ProfileLibraryReference_Loc return nil } +func (x *ProfileLibraryReference) GetGitLibrary() *ProfileLibraryReference_GitLibrary { + if x, ok := x.GetLibrary().(*ProfileLibraryReference_GitLibrary_); ok { + return x.GitLibrary + } + return nil +} + type isProfileLibraryReference_Library interface { isProfileLibraryReference_Library() } @@ -1516,10 +1524,17 @@ type ProfileLibraryReference_LocalLibrary_ struct { LocalLibrary *ProfileLibraryReference_LocalLibrary `protobuf:"bytes,2,opt,name=local_library,json=localLibrary,proto3,oneof"` } +type ProfileLibraryReference_GitLibrary_ struct { + // The library is installed from a git repository. + GitLibrary *ProfileLibraryReference_GitLibrary `protobuf:"bytes,3,opt,name=git_library,json=gitLibrary,proto3,oneof"` +} + func (*ProfileLibraryReference_IndexLibrary_) isProfileLibraryReference_Library() {} func (*ProfileLibraryReference_LocalLibrary_) isProfileLibraryReference_Library() {} +func (*ProfileLibraryReference_GitLibrary_) isProfileLibraryReference_Library() {} + type ProfileLibraryReference_IndexLibrary struct { state protoimpl.MessageState sizeCache protoimpl.SizeCache @@ -1634,6 +1649,54 @@ func (x *ProfileLibraryReference_LocalLibrary) GetPath() string { return "" } +type ProfileLibraryReference_GitLibrary struct { + state protoimpl.MessageState + sizeCache protoimpl.SizeCache + unknownFields protoimpl.UnknownFields + + // URL to the git repo (the revision reference is in the fragment part of the URL). + Url string `protobuf:"bytes,1,opt,name=url,proto3" json:"url,omitempty"` +} + +func (x *ProfileLibraryReference_GitLibrary) Reset() { + *x = ProfileLibraryReference_GitLibrary{} + if protoimpl.UnsafeEnabled { + mi := &file_cc_arduino_cli_commands_v1_common_proto_msgTypes[23] + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + ms.StoreMessageInfo(mi) + } +} + +func (x *ProfileLibraryReference_GitLibrary) String() string { + return protoimpl.X.MessageStringOf(x) +} + +func (*ProfileLibraryReference_GitLibrary) ProtoMessage() {} + +func (x *ProfileLibraryReference_GitLibrary) ProtoReflect() protoreflect.Message { + mi := &file_cc_arduino_cli_commands_v1_common_proto_msgTypes[23] + if protoimpl.UnsafeEnabled && x != nil { + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + if ms.LoadMessageInfo() == nil { + ms.StoreMessageInfo(mi) + } + return ms + } + return mi.MessageOf(x) +} + +// Deprecated: Use ProfileLibraryReference_GitLibrary.ProtoReflect.Descriptor instead. +func (*ProfileLibraryReference_GitLibrary) Descriptor() ([]byte, []int) { + return file_cc_arduino_cli_commands_v1_common_proto_rawDescGZIP(), []int{19, 2} +} + +func (x *ProfileLibraryReference_GitLibrary) GetUrl() string { + if x != nil { + return x.Url + } + return "" +} + var File_cc_arduino_cli_commands_v1_common_proto protoreflect.FileDescriptor var file_cc_arduino_cli_commands_v1_common_proto_rawDesc = []byte{ @@ -1834,7 +1897,7 @@ var file_cc_arduino_cli_commands_v1_common_proto_rawDesc = []byte{ 0x6f, 0x72, 0x74, 0x43, 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x75, 0x72, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x52, 0x0a, 0x70, 0x6f, 0x72, 0x74, 0x43, 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x12, 0x1a, 0x0a, 0x08, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x63, 0x6f, 0x6c, 0x18, 0x06, 0x20, 0x01, 0x28, 0x09, 0x52, 0x08, - 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x63, 0x6f, 0x6c, 0x22, 0xfd, 0x02, 0x0a, 0x17, 0x50, 0x72, 0x6f, + 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x63, 0x6f, 0x6c, 0x22, 0x80, 0x04, 0x0a, 0x17, 0x50, 0x72, 0x6f, 0x66, 0x69, 0x6c, 0x65, 0x4c, 0x69, 0x62, 0x72, 0x61, 0x72, 0x79, 0x52, 0x65, 0x66, 0x65, 0x72, 0x65, 0x6e, 0x63, 0x65, 0x12, 0x67, 0x0a, 0x0d, 0x69, 0x6e, 0x64, 0x65, 0x78, 0x5f, 0x6c, 0x69, 0x62, 0x72, 0x61, 0x72, 0x79, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x40, 0x2e, 0x63, 0x63, @@ -1849,21 +1912,29 @@ var file_cc_arduino_cli_commands_v1_common_proto_rawDesc = []byte{ 0x31, 0x2e, 0x50, 0x72, 0x6f, 0x66, 0x69, 0x6c, 0x65, 0x4c, 0x69, 0x62, 0x72, 0x61, 0x72, 0x79, 0x52, 0x65, 0x66, 0x65, 0x72, 0x65, 0x6e, 0x63, 0x65, 0x2e, 0x4c, 0x6f, 0x63, 0x61, 0x6c, 0x4c, 0x69, 0x62, 0x72, 0x61, 0x72, 0x79, 0x48, 0x00, 0x52, 0x0c, 0x6c, 0x6f, 0x63, 0x61, 0x6c, 0x4c, - 0x69, 0x62, 0x72, 0x61, 0x72, 0x79, 0x1a, 0x61, 0x0a, 0x0c, 0x49, 0x6e, 0x64, 0x65, 0x78, 0x4c, - 0x69, 0x62, 0x72, 0x61, 0x72, 0x79, 0x12, 0x12, 0x0a, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x18, 0x01, - 0x20, 0x01, 0x28, 0x09, 0x52, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x12, 0x18, 0x0a, 0x07, 0x76, 0x65, - 0x72, 0x73, 0x69, 0x6f, 0x6e, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x07, 0x76, 0x65, 0x72, - 0x73, 0x69, 0x6f, 0x6e, 0x12, 0x23, 0x0a, 0x0d, 0x69, 0x73, 0x5f, 0x64, 0x65, 0x70, 0x65, 0x6e, - 0x64, 0x65, 0x6e, 0x63, 0x79, 0x18, 0x03, 0x20, 0x01, 0x28, 0x08, 0x52, 0x0c, 0x69, 0x73, 0x44, - 0x65, 0x70, 0x65, 0x6e, 0x64, 0x65, 0x6e, 0x63, 0x79, 0x1a, 0x22, 0x0a, 0x0c, 0x4c, 0x6f, 0x63, - 0x61, 0x6c, 0x4c, 0x69, 0x62, 0x72, 0x61, 0x72, 0x79, 0x12, 0x12, 0x0a, 0x04, 0x70, 0x61, 0x74, - 0x68, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x04, 0x70, 0x61, 0x74, 0x68, 0x42, 0x09, 0x0a, - 0x07, 0x6c, 0x69, 0x62, 0x72, 0x61, 0x72, 0x79, 0x42, 0x48, 0x5a, 0x46, 0x67, 0x69, 0x74, 0x68, - 0x75, 0x62, 0x2e, 0x63, 0x6f, 0x6d, 0x2f, 0x61, 0x72, 0x64, 0x75, 0x69, 0x6e, 0x6f, 0x2f, 0x61, - 0x72, 0x64, 0x75, 0x69, 0x6e, 0x6f, 0x2d, 0x63, 0x6c, 0x69, 0x2f, 0x72, 0x70, 0x63, 0x2f, 0x63, - 0x63, 0x2f, 0x61, 0x72, 0x64, 0x75, 0x69, 0x6e, 0x6f, 0x2f, 0x63, 0x6c, 0x69, 0x2f, 0x63, 0x6f, - 0x6d, 0x6d, 0x61, 0x6e, 0x64, 0x73, 0x2f, 0x76, 0x31, 0x3b, 0x63, 0x6f, 0x6d, 0x6d, 0x61, 0x6e, - 0x64, 0x73, 0x62, 0x06, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x33, + 0x69, 0x62, 0x72, 0x61, 0x72, 0x79, 0x12, 0x61, 0x0a, 0x0b, 0x67, 0x69, 0x74, 0x5f, 0x6c, 0x69, + 0x62, 0x72, 0x61, 0x72, 0x79, 0x18, 0x03, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x3e, 0x2e, 0x63, 0x63, + 0x2e, 0x61, 0x72, 0x64, 0x75, 0x69, 0x6e, 0x6f, 0x2e, 0x63, 0x6c, 0x69, 0x2e, 0x63, 0x6f, 0x6d, + 0x6d, 0x61, 0x6e, 0x64, 0x73, 0x2e, 0x76, 0x31, 0x2e, 0x50, 0x72, 0x6f, 0x66, 0x69, 0x6c, 0x65, + 0x4c, 0x69, 0x62, 0x72, 0x61, 0x72, 0x79, 0x52, 0x65, 0x66, 0x65, 0x72, 0x65, 0x6e, 0x63, 0x65, + 0x2e, 0x47, 0x69, 0x74, 0x4c, 0x69, 0x62, 0x72, 0x61, 0x72, 0x79, 0x48, 0x00, 0x52, 0x0a, 0x67, + 0x69, 0x74, 0x4c, 0x69, 0x62, 0x72, 0x61, 0x72, 0x79, 0x1a, 0x61, 0x0a, 0x0c, 0x49, 0x6e, 0x64, + 0x65, 0x78, 0x4c, 0x69, 0x62, 0x72, 0x61, 0x72, 0x79, 0x12, 0x12, 0x0a, 0x04, 0x6e, 0x61, 0x6d, + 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x12, 0x18, 0x0a, + 0x07, 0x76, 0x65, 0x72, 0x73, 0x69, 0x6f, 0x6e, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x07, + 0x76, 0x65, 0x72, 0x73, 0x69, 0x6f, 0x6e, 0x12, 0x23, 0x0a, 0x0d, 0x69, 0x73, 0x5f, 0x64, 0x65, + 0x70, 0x65, 0x6e, 0x64, 0x65, 0x6e, 0x63, 0x79, 0x18, 0x03, 0x20, 0x01, 0x28, 0x08, 0x52, 0x0c, + 0x69, 0x73, 0x44, 0x65, 0x70, 0x65, 0x6e, 0x64, 0x65, 0x6e, 0x63, 0x79, 0x1a, 0x22, 0x0a, 0x0c, + 0x4c, 0x6f, 0x63, 0x61, 0x6c, 0x4c, 0x69, 0x62, 0x72, 0x61, 0x72, 0x79, 0x12, 0x12, 0x0a, 0x04, + 0x70, 0x61, 0x74, 0x68, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x04, 0x70, 0x61, 0x74, 0x68, + 0x1a, 0x1e, 0x0a, 0x0a, 0x47, 0x69, 0x74, 0x4c, 0x69, 0x62, 0x72, 0x61, 0x72, 0x79, 0x12, 0x10, + 0x0a, 0x03, 0x75, 0x72, 0x6c, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x03, 0x75, 0x72, 0x6c, + 0x42, 0x09, 0x0a, 0x07, 0x6c, 0x69, 0x62, 0x72, 0x61, 0x72, 0x79, 0x42, 0x48, 0x5a, 0x46, 0x67, + 0x69, 0x74, 0x68, 0x75, 0x62, 0x2e, 0x63, 0x6f, 0x6d, 0x2f, 0x61, 0x72, 0x64, 0x75, 0x69, 0x6e, + 0x6f, 0x2f, 0x61, 0x72, 0x64, 0x75, 0x69, 0x6e, 0x6f, 0x2d, 0x63, 0x6c, 0x69, 0x2f, 0x72, 0x70, + 0x63, 0x2f, 0x63, 0x63, 0x2f, 0x61, 0x72, 0x64, 0x75, 0x69, 0x6e, 0x6f, 0x2f, 0x63, 0x6c, 0x69, + 0x2f, 0x63, 0x6f, 0x6d, 0x6d, 0x61, 0x6e, 0x64, 0x73, 0x2f, 0x76, 0x31, 0x3b, 0x63, 0x6f, 0x6d, + 0x6d, 0x61, 0x6e, 0x64, 0x73, 0x62, 0x06, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x33, } var ( @@ -1878,7 +1949,7 @@ func file_cc_arduino_cli_commands_v1_common_proto_rawDescGZIP() []byte { return file_cc_arduino_cli_commands_v1_common_proto_rawDescData } -var file_cc_arduino_cli_commands_v1_common_proto_msgTypes = make([]protoimpl.MessageInfo, 23) +var file_cc_arduino_cli_commands_v1_common_proto_msgTypes = make([]protoimpl.MessageInfo, 24) var file_cc_arduino_cli_commands_v1_common_proto_goTypes = []any{ (*Instance)(nil), // 0: cc.arduino.cli.commands.v1.Instance (*DownloadProgress)(nil), // 1: cc.arduino.cli.commands.v1.DownloadProgress @@ -1903,6 +1974,7 @@ var file_cc_arduino_cli_commands_v1_common_proto_goTypes = []any{ nil, // 20: cc.arduino.cli.commands.v1.PlatformSummary.ReleasesEntry (*ProfileLibraryReference_IndexLibrary)(nil), // 21: cc.arduino.cli.commands.v1.ProfileLibraryReference.IndexLibrary (*ProfileLibraryReference_LocalLibrary)(nil), // 22: cc.arduino.cli.commands.v1.ProfileLibraryReference.LocalLibrary + (*ProfileLibraryReference_GitLibrary)(nil), // 23: cc.arduino.cli.commands.v1.ProfileLibraryReference.GitLibrary } var file_cc_arduino_cli_commands_v1_common_proto_depIdxs = []int32{ 2, // 0: cc.arduino.cli.commands.v1.DownloadProgress.start:type_name -> cc.arduino.cli.commands.v1.DownloadProgressStart @@ -1921,12 +1993,13 @@ var file_cc_arduino_cli_commands_v1_common_proto_depIdxs = []int32{ 16, // 13: cc.arduino.cli.commands.v1.SketchProfile.port_config:type_name -> cc.arduino.cli.commands.v1.MonitorPortConfiguration 21, // 14: cc.arduino.cli.commands.v1.ProfileLibraryReference.index_library:type_name -> cc.arduino.cli.commands.v1.ProfileLibraryReference.IndexLibrary 22, // 15: cc.arduino.cli.commands.v1.ProfileLibraryReference.local_library:type_name -> cc.arduino.cli.commands.v1.ProfileLibraryReference.LocalLibrary - 11, // 16: cc.arduino.cli.commands.v1.PlatformSummary.ReleasesEntry.value:type_name -> cc.arduino.cli.commands.v1.PlatformRelease - 17, // [17:17] is the sub-list for method output_type - 17, // [17:17] is the sub-list for method input_type - 17, // [17:17] is the sub-list for extension type_name - 17, // [17:17] is the sub-list for extension extendee - 0, // [0:17] is the sub-list for field type_name + 23, // 16: cc.arduino.cli.commands.v1.ProfileLibraryReference.git_library:type_name -> cc.arduino.cli.commands.v1.ProfileLibraryReference.GitLibrary + 11, // 17: cc.arduino.cli.commands.v1.PlatformSummary.ReleasesEntry.value:type_name -> cc.arduino.cli.commands.v1.PlatformRelease + 18, // [18:18] is the sub-list for method output_type + 18, // [18:18] is the sub-list for method input_type + 18, // [18:18] is the sub-list for extension type_name + 18, // [18:18] is the sub-list for extension extendee + 0, // [0:18] is the sub-list for field type_name } func init() { file_cc_arduino_cli_commands_v1_common_proto_init() } @@ -2199,6 +2272,18 @@ func file_cc_arduino_cli_commands_v1_common_proto_init() { return nil } } + file_cc_arduino_cli_commands_v1_common_proto_msgTypes[23].Exporter = func(v any, i int) any { + switch v := v.(*ProfileLibraryReference_GitLibrary); i { + case 0: + return &v.state + case 1: + return &v.sizeCache + case 2: + return &v.unknownFields + default: + return nil + } + } } file_cc_arduino_cli_commands_v1_common_proto_msgTypes[1].OneofWrappers = []any{ (*DownloadProgress_Start)(nil), @@ -2208,6 +2293,7 @@ func file_cc_arduino_cli_commands_v1_common_proto_init() { file_cc_arduino_cli_commands_v1_common_proto_msgTypes[19].OneofWrappers = []any{ (*ProfileLibraryReference_IndexLibrary_)(nil), (*ProfileLibraryReference_LocalLibrary_)(nil), + (*ProfileLibraryReference_GitLibrary_)(nil), } type x struct{} out := protoimpl.TypeBuilder{ @@ -2215,7 +2301,7 @@ func file_cc_arduino_cli_commands_v1_common_proto_init() { GoPackagePath: reflect.TypeOf(x{}).PkgPath(), RawDescriptor: file_cc_arduino_cli_commands_v1_common_proto_rawDesc, NumEnums: 0, - NumMessages: 23, + NumMessages: 24, NumExtensions: 0, NumServices: 0, }, diff --git a/rpc/cc/arduino/cli/commands/v1/common.proto b/rpc/cc/arduino/cli/commands/v1/common.proto index e53f7aa0390..3451ab4fe67 100644 --- a/rpc/cc/arduino/cli/commands/v1/common.proto +++ b/rpc/cc/arduino/cli/commands/v1/common.proto @@ -251,10 +251,16 @@ message ProfileLibraryReference { // Absolute path to the library. string path = 1; } + message GitLibrary { + // URL to the git repo (the revision reference is in the fragment part of the URL). + string url = 1; + } oneof library { // The library is installed from the Library Index. IndexLibrary index_library = 1; // The library is a local library. LocalLibrary local_library = 2; + // The library is installed from a git repository. + GitLibrary git_library = 3; } }