Skip to content

Commit 9a2f814

Browse files
committed
Rework Confluence and Jira commands
1 parent 2a92c34 commit 9a2f814

File tree

14 files changed

+392
-113
lines changed

14 files changed

+392
-113
lines changed

plugin/confluence/confluence.go

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -19,9 +19,9 @@ package confluence
1919
import (
2020
"fmt"
2121
"io"
22+
"net/http/cookiejar"
2223
"strings"
2324
"time"
24-
"net/http/cookiejar"
2525

2626
"github.com/abc-inc/heimdall/cli"
2727
"github.com/abc-inc/heimdall/internal"

plugin/confluence/create.go

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -67,7 +67,7 @@ func create(cfg confluenceUpdateCfg) *goconfluence.Content {
6767
s := search(confluenceSearchCfg{
6868
confluenceCfg: cfg.confluenceCfg,
6969
limit: 2,
70-
start: 0,
70+
offset: 0,
7171
cql: cfg.cql,
7272
expand: cfg.expand,
7373
})

plugin/confluence/edit.go

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -74,7 +74,7 @@ func update(cfg confluenceUpdateCfg) *goconfluence.Content {
7474
s := search(confluenceSearchCfg{
7575
confluenceCfg: cfg.confluenceCfg,
7676
limit: 2,
77-
start: 0,
77+
offset: 0,
7878
cql: cfg.cql,
7979
expand: cfg.expand,
8080
})

plugin/confluence/search.go

Lines changed: 70 additions & 29 deletions
Original file line numberDiff line numberDiff line change
@@ -17,10 +17,11 @@
1717
package confluence
1818

1919
import (
20+
"io"
2021
"net/http"
22+
"net/url"
2123
"os"
2224
"time"
23-
"net/url"
2425

2526
"github.com/abc-inc/heimdall/cli"
2627
"github.com/abc-inc/heimdall/internal"
@@ -31,20 +32,20 @@ import (
3132

3233
type confluenceSearchCfg struct {
3334
confluenceCfg
34-
limit int
35-
start int
36-
cql string
37-
expand string
38-
exportAsPDF bool
35+
limit int
36+
offset int
37+
cql string
38+
expand string
39+
export string
40+
file string
3941
}
4042

4143
func NewSearchCmd() *cobra.Command {
4244
cfg := confluenceSearchCfg{confluenceCfg: confluenceCfg{
4345
baseURL: os.Getenv("CONFLUENCE_API_URL"),
4446
timeout: 30 * time.Second},
45-
expand: "content.body.storage",
46-
limit: 1,
47-
exportAsPDF: false,
47+
expand: "content.body.storage",
48+
limit: 10,
4849
}
4950

5051
cmd := &cobra.Command{
@@ -60,28 +61,30 @@ func NewSearchCmd() *cobra.Command {
6061
if zerolog.GlobalLevel() == zerolog.TraceLevel || zerolog.GlobalLevel() == zerolog.DebugLevel {
6162
goconfluence.SetDebug(true)
6263
}
64+
if cfg.export == "html" {
65+
cfg.expand = "content.body.view," + cfg.expand
66+
}
6367
s := search(cfg)
64-
if cfg.exportAsPDF {
65-
exportToPDF(s, cfg)
66-
} else if cfg.limit == 1 && len(s.Results) == 1 {
67-
cli.Fmtln(s.Results[0])
68+
if cfg.export != "" {
69+
export(s, cfg)
6870
} else {
69-
cli.Fmtln(s.Results)
71+
cli.Fmtln(s)
7072
}
7173
},
7274
}
7375

7476
cmd.Flags().StringVar(&cfg.expand, "expand", cfg.expand, "Expand specific entities in the returned list")
77+
cmd.Flags().StringVarP(&cfg.file, "file", "O", cfg.file, "File to save the page to (use '-' for standard output)")
7578
cmd.Flags().StringVar(&cfg.cql, "filter", cfg.cql, "CQL query for searching")
76-
cmd.Flags().IntVar(&cfg.limit, "limit", cfg.limit, "Maximum items to return")
77-
cmd.Flags().IntVar(&cfg.start, "start", cfg.start, "Starting index of the returned list")
78-
cmd.Flags().BoolVar(&cfg.exportAsPDF, "export-as-pdf", cfg.exportAsPDF, "Export search result to a PDF file which will be output to stdout")
79+
cmd.Flags().IntVar(&cfg.limit, "limit", cfg.limit, "Maximum number of items to return")
80+
cmd.Flags().IntVar(&cfg.offset, "offset", cfg.offset, "Starting index of the returned list")
81+
cmd.Flags().StringVar(&cfg.export, "export", cfg.export, "Export page (supported modes: pdf, html)")
7982
addCommonFlags(cmd, &cfg.confluenceCfg)
8083

8184
cli.AddOutputFlags(cmd, &cfg.OutCfg)
8285
internal.MustNoErr(cmd.MarkFlagRequired("filter"))
83-
cmd.MarkFlagsMutuallyExclusive("export-as-pdf", "limit")
84-
cmd.MarkFlagsMutuallyExclusive("export-as-pdf", "output")
86+
cmd.MarkFlagsMutuallyExclusive("export", "limit")
87+
cmd.MarkFlagsMutuallyExclusive("export", "output")
8588
return cmd
8689
}
8790

@@ -90,26 +93,64 @@ func search(cfg confluenceSearchCfg) *goconfluence.Search {
9093
s := internal.Must(api.Search(goconfluence.SearchQuery{
9194
CQL: cfg.cql,
9295
Limit: cfg.limit,
93-
Start: cfg.start,
96+
Start: cfg.offset,
9497
Expand: []string{cfg.expand},
9598
}))
9699

97100
return s
98101
}
99102

100-
func exportToPDF(s *goconfluence.Search, cfg confluenceSearchCfg) {
101-
internal.MustOkMsgf(1, len(s.Results) == 1, "Error: The result of the search is expected to be 1 result, found %d: PDF not exported.", len(s.Results))
102-
page := s.Results[0].Content.ID
103-
pdfExportURL := createPDFExportURL(cfg.baseURL, page)
104-
req := internal.Must(http.NewRequest("GET", pdfExportURL, nil))
103+
func export(s *goconfluence.Search, cfg confluenceSearchCfg) {
104+
internal.MustOkMsgf(1, len(s.Results) == 1, "expected 1 page, but found %d", len(s.Results))
105+
106+
switch cfg.export {
107+
case "html":
108+
exportHTML(cfg, s.Results[0])
109+
case "pdf":
110+
exportPDF(cfg, s.Results[0])
111+
default:
112+
internal.MustOkMsgf(cfg.export, false, "invalid export format: %s", cfg.export)
113+
}
114+
}
115+
116+
func exportPDF(cfg confluenceSearchCfg, page goconfluence.Results) {
117+
u := createPDFExportURL(cfg.baseURL, page.Content.ID)
118+
req := internal.Must(http.NewRequest("GET", u, nil))
105119
api := internal.Must(newClient(cfg.baseURL, cfg.token))
106-
resp := internal.Must(api.Request(req))
107-
internal.Must(os.Stdout.Write(resp))
120+
data := internal.Must(api.Request(req))
121+
122+
if cfg.file == "-" {
123+
internal.Must(os.Stdout.Write(data))
124+
return
125+
}
126+
127+
if cfg.file == "" {
128+
cfg.file = page.Content.Title + ".pdf"
129+
}
130+
131+
internal.MustNoErr(os.WriteFile(cfg.file, data, 0640))
132+
}
133+
134+
func exportHTML(cfg confluenceSearchCfg, page goconfluence.Results) {
135+
data := page.Content.Body.View.Value
136+
137+
if cfg.file == "-" {
138+
internal.Must(os.Stdout.WriteString(data))
139+
return
140+
}
141+
142+
if cfg.file == "" {
143+
cfg.file = page.Content.Title + ".html"
144+
}
145+
146+
f := internal.Must(os.OpenFile(cfg.file, os.O_RDWR|os.O_CREATE|os.O_TRUNC, 0640))
147+
defer func() { _ = f.Close() }()
148+
_ = internal.Must(io.WriteString(f, data))
108149
}
109150

110151
func createPDFExportURL(baseURL string, pageID string) string {
111-
u := internal.Must(url.Parse(baseURL))
152+
u := internal.Must(url.Parse(baseURL))
112153
u = u.JoinPath("../../spaces/flyingpdf/pdfpageexport.action")
113154
u.RawQuery = "pageId=" + pageID
114-
return u.String()
155+
return u.String()
115156
}

plugin/eval/eval.go

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -203,8 +203,8 @@ func load(i parse.Input, envMap map[string]any) {
203203
r := internal.Must(res.Open(i.File))
204204
defer func() { _ = r.Close() }()
205205

206-
if d, ok := parse.Decoders[i.Typ]; ok {
207-
log.Debug().Str("type", i.Typ).Msg("Using decoder")
206+
if d, ok := parse.Decoders[i.Type]; ok {
207+
log.Debug().Str("type", i.Type).Msg("Using decoder")
208208
v := internal.Must[any](d(r))
209209
if reflect.TypeOf(v).Kind() == reflect.Map {
210210
merge(envMap, i.Alias, v.(map[string]any))

0 commit comments

Comments
 (0)