• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

UiPath / uipathcli / 14470109638

15 Apr 2025 01:02PM UTC coverage: 90.371% (+0.003%) from 90.368%
14470109638

push

github

thschmitt
Move each command into separate subfolder

112 of 128 new or added lines in 11 files covered. (87.5%)

43 existing lines in 6 files now uncovered.

6138 of 6792 relevant lines covered (90.37%)

1.01 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

94.44
/plugin/studio/pack/package_pack_command.go
1
package pack
2

3
import (
4
        "bytes"
5
        "encoding/json"
6
        "fmt"
7
        "os"
8
        "path/filepath"
9
        "slices"
10
        "strings"
11
        "time"
12

13
        "github.com/UiPath/uipathcli/log"
14
        "github.com/UiPath/uipathcli/output"
15
        "github.com/UiPath/uipathcli/plugin"
16
        "github.com/UiPath/uipathcli/plugin/studio"
17
        "github.com/UiPath/uipathcli/utils/process"
18
        "github.com/UiPath/uipathcli/utils/visualization"
19
)
20

21
var OutputTypeAllowedValues = []string{"Process", "Library", "Tests", "Objects"}
22

23
// The PackagePackCommand packs a project into a single NuGet package
24
type PackagePackCommand struct {
25
        Exec process.ExecProcess
26
}
27

28
func (c PackagePackCommand) Command() plugin.Command {
1✔
29
        return *plugin.NewCommand("studio").
1✔
30
                WithCategory("package", "Package", "UiPath Studio package-related actions").
1✔
31
                WithOperation("pack", "Package Project", "Packs a project into a single package").
1✔
32
                WithParameter("source", plugin.ParameterTypeString, "Path to a project.json file or a folder containing project.json file (default: .)", false).
1✔
33
                WithParameter("destination", plugin.ParameterTypeString, "The output folder (default .)", false).
1✔
34
                WithParameter("package-version", plugin.ParameterTypeString, "The package version", false).
1✔
35
                WithParameter("auto-version", plugin.ParameterTypeBoolean, "Auto-generate package version", false).
1✔
36
                WithParameter("output-type", plugin.ParameterTypeString, "Force the output to a specific type."+c.formatAllowedValues(OutputTypeAllowedValues), false).
1✔
37
                WithParameter("split-output", plugin.ParameterTypeBoolean, "Enables the output split to runtime and design libraries", false).
1✔
38
                WithParameter("release-notes", plugin.ParameterTypeString, "Add release notes", false)
1✔
39
}
1✔
40

41
func (c PackagePackCommand) Execute(ctx plugin.ExecutionContext, writer output.OutputWriter, logger log.Logger) error {
1✔
42
        source, err := c.getSource(ctx)
1✔
43
        if err != nil {
2✔
44
                return err
1✔
45
        }
1✔
46
        destination := c.getDestination(ctx)
1✔
47
        packageVersion := c.getParameter("package-version", "", ctx.Parameters)
1✔
48
        autoVersion := c.getBoolParameter("auto-version", ctx.Parameters)
1✔
49
        outputType := c.getParameter("output-type", "", ctx.Parameters)
1✔
50
        if outputType != "" && !slices.Contains(OutputTypeAllowedValues, outputType) {
2✔
51
                return fmt.Errorf("Invalid output type '%s', allowed values: %s", outputType, strings.Join(OutputTypeAllowedValues, ", "))
1✔
52
        }
1✔
53
        splitOutput := c.getBoolParameter("split-output", ctx.Parameters)
1✔
54
        releaseNotes := c.getParameter("release-notes", "", ctx.Parameters)
1✔
55
        params := newPackagePackParams(
1✔
56
                ctx.Organization,
1✔
57
                ctx.Tenant,
1✔
58
                ctx.BaseUri,
1✔
59
                ctx.Auth.Token,
1✔
60
                ctx.IdentityUri,
1✔
61
                source,
1✔
62
                destination,
1✔
63
                packageVersion,
1✔
64
                autoVersion,
1✔
65
                outputType,
1✔
66
                splitOutput,
1✔
67
                releaseNotes)
1✔
68

1✔
69
        result, err := c.execute(*params, ctx.Debug, logger)
1✔
70
        if err != nil {
2✔
71
                return err
1✔
72
        }
1✔
73

74
        json, err := json.Marshal(result)
1✔
75
        if err != nil {
1✔
76
                return fmt.Errorf("pack command failed: %v", err)
×
UNCOV
77
        }
×
78
        return writer.WriteResponse(*output.NewResponseInfo(200, "200 OK", "HTTP/1.1", map[string][]string{}, bytes.NewReader(json)))
1✔
79
}
80

81
func (c PackagePackCommand) formatAllowedValues(allowed []string) string {
1✔
82
        return "\n\nAllowed Values:\n- " + strings.Join(allowed, "\n- ")
1✔
83
}
1✔
84

85
func (c PackagePackCommand) execute(params packagePackParams, debug bool, logger log.Logger) (*packagePackResult, error) {
1✔
86
        projectReader := studio.NewStudioProjectReader(params.Source)
1✔
87
        project, err := projectReader.ReadMetadata()
1✔
88
        if err != nil {
1✔
89
                return nil, err
×
UNCOV
90
        }
×
91
        supported, err := project.TargetFramework.IsSupported()
1✔
92
        if !supported {
2✔
93
                return nil, err
1✔
94
        }
1✔
95
        _ = projectReader.AddToIgnoredFiles(project.NupkgIgnoreFilePattern())
1✔
96

1✔
97
        uipcli := studio.NewUipcli(c.Exec, logger)
1✔
98
        err = uipcli.Initialize(project.TargetFramework)
1✔
99
        if err != nil {
1✔
100
                return nil, err
×
UNCOV
101
        }
×
102

103
        if !debug {
2✔
104
                bar := c.newPackagingProgressBar(logger)
1✔
105
                defer close(bar)
1✔
106
        }
1✔
107
        args := c.preparePackArguments(params)
1✔
108
        exitCode, stdErr, err := uipcli.ExecuteAndWait(args...)
1✔
109
        if err != nil {
1✔
110
                return nil, err
×
UNCOV
111
        }
×
112

113
        var result *packagePackResult
1✔
114
        if exitCode == 0 {
2✔
115
                nupkgPath := studio.FindLatestNupkg(params.Destination)
1✔
116
                nupkgReader := studio.NewNupkgReader(nupkgPath)
1✔
117
                nuspec, err := nupkgReader.ReadNuspec()
1✔
118
                if err != nil {
2✔
119
                        return nil, err
1✔
120
                }
1✔
121
                result = newSucceededPackagePackResult(
1✔
122
                        nupkgPath,
1✔
123
                        project.Name,
1✔
124
                        project.Description,
1✔
125
                        project.ProjectId,
1✔
126
                        nuspec.Version)
1✔
127
        } else {
1✔
128
                result = newFailedPackagePackResult(
1✔
129
                        stdErr,
1✔
130
                        &project.Name,
1✔
131
                        &project.Description,
1✔
132
                        &project.ProjectId)
1✔
133
        }
1✔
134
        return result, nil
1✔
135
}
136

137
func (c PackagePackCommand) preparePackArguments(params packagePackParams) []string {
1✔
138
        args := []string{"package", "pack", params.Source, "--output", params.Destination}
1✔
139
        if params.PackageVersion != "" {
1✔
140
                args = append(args, "--version", params.PackageVersion)
×
UNCOV
141
        }
×
142
        if params.AutoVersion {
2✔
143
                args = append(args, "--autoVersion")
1✔
144
        }
1✔
145
        if params.OutputType != "" {
2✔
146
                args = append(args, "--outputType", params.OutputType)
1✔
147
        }
1✔
148
        if params.SplitOutput {
2✔
149
                args = append(args, "--splitOutput")
1✔
150
        }
1✔
151
        if params.ReleaseNotes != "" {
2✔
152
                args = append(args, "--releaseNotes", params.ReleaseNotes)
1✔
153
        }
1✔
154
        if params.AuthToken != nil && params.Organization != "" {
2✔
155
                args = append(args, "--libraryIdentityUrl", params.IdentityUri.String())
1✔
156
                args = append(args, "--libraryOrchestratorUrl", params.BaseUri.String())
1✔
157
                args = append(args, "--libraryOrchestratorAuthToken", params.AuthToken.Value)
1✔
158
                args = append(args, "--libraryOrchestratorAccountName", params.Organization)
1✔
159
                if params.Tenant != "" {
2✔
160
                        args = append(args, "--libraryOrchestratorTenant", params.Tenant)
1✔
161
                }
1✔
162
        }
163
        return args
1✔
164
}
165

166
func (c PackagePackCommand) newPackagingProgressBar(logger log.Logger) chan struct{} {
1✔
167
        progressBar := visualization.NewProgressBar(logger)
1✔
168
        ticker := time.NewTicker(10 * time.Millisecond)
1✔
169
        cancel := make(chan struct{})
1✔
170
        var percent float64 = 0
1✔
171
        go func() {
2✔
172
                for {
2✔
173
                        select {
1✔
174
                        case <-ticker.C:
1✔
175
                                progressBar.UpdatePercentage("packaging...  ", percent)
1✔
176
                                percent = percent + 1
1✔
177
                                if percent > 100 {
2✔
178
                                        percent = 0
1✔
179
                                }
1✔
180
                        case <-cancel:
1✔
181
                                ticker.Stop()
1✔
182
                                progressBar.Remove()
1✔
183
                                return
1✔
184
                        }
185
                }
186
        }()
187
        return cancel
1✔
188
}
189

190
func (c PackagePackCommand) getSource(ctx plugin.ExecutionContext) (string, error) {
1✔
191
        source := c.getParameter("source", ".", ctx.Parameters)
1✔
192
        source, _ = filepath.Abs(source)
1✔
193
        fileInfo, err := os.Stat(source)
1✔
194
        if err != nil {
2✔
195
                return "", fmt.Errorf("%s not found", studio.DefaultProjectJson)
1✔
196
        }
1✔
197
        if fileInfo.IsDir() {
2✔
198
                source = filepath.Join(source, studio.DefaultProjectJson)
1✔
199
        }
1✔
200
        return source, nil
1✔
201
}
202

203
func (c PackagePackCommand) getDestination(ctx plugin.ExecutionContext) string {
1✔
204
        destination := c.getParameter("destination", ".", ctx.Parameters)
1✔
205
        destination, _ = filepath.Abs(destination)
1✔
206
        return destination
1✔
207
}
1✔
208

209
func (c PackagePackCommand) getParameter(name string, defaultValue string, parameters []plugin.ExecutionParameter) string {
1✔
210
        result := defaultValue
1✔
211
        for _, p := range parameters {
2✔
212
                if p.Name == name {
2✔
213
                        if data, ok := p.Value.(string); ok {
2✔
214
                                result = data
1✔
215
                                break
1✔
216
                        }
217
                }
218
        }
219
        return result
1✔
220
}
221

222
func (c PackagePackCommand) getBoolParameter(name string, parameters []plugin.ExecutionParameter) bool {
1✔
223
        result := false
1✔
224
        for _, p := range parameters {
2✔
225
                if p.Name == name {
2✔
226
                        if data, ok := p.Value.(bool); ok {
2✔
227
                                result = data
1✔
228
                                break
1✔
229
                        }
230
                }
231
        }
232
        return result
1✔
233
}
234

235
func NewPackagePackCommand() *PackagePackCommand {
1✔
236
        return &PackagePackCommand{process.NewExecProcess()}
1✔
237
}
1✔
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2026 Coveralls, Inc