Skip to content

Commit 6c4f006

Browse files
Feat/bundle from raw (#101)
### Description Add an endpoint for creating a Batch from (in-memory) raw content. This is a pre-requisite for [AIBOM-55](https://snyksec.atlassian.net/browse/AIBOM-55), wherein the objective is to have the [aibom cli extension](https://github.com/snyk/cli-extension-ai-bom/) upload dep graphs from memory without writing them to file (as we currently do). The unit tests have also been updated to test this new method. ### Checklist - [✅] Tests added and all succeed - [✅] Linted - ~~README.md updated, if user-facing~~ (not user-facing) [AIBOM-55]: https://snyksec.atlassian.net/browse/AIBOM-55?atlOrigin=eyJpIjoiNWRkNTljNzYxNjVmNDY3MDlhMDU5Y2ZhYzA5YTRkZjUiLCJwIjoiZ2l0aHViLWNvbS1KU1cifQ
2 parents d8776ec + b75803d commit 6c4f006

File tree

2 files changed

+67
-0
lines changed

2 files changed

+67
-0
lines changed

bundle/bundle.go

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,7 @@ package bundle
1818

1919
import (
2020
"context"
21+
"fmt"
2122

2223
"github.com/rs/zerolog"
2324

@@ -134,6 +135,23 @@ func NewBatch(documents map[string]deepcode.BundleFile) *Batch {
134135
}
135136
}
136137

138+
func NewBatchFromRawContent(documents map[string][]byte) (*Batch, error) {
139+
bundleFiles := make(map[string]deepcode.BundleFile)
140+
141+
for key, rawData := range documents {
142+
bundleFile, err := deepcode.BundleFileFrom(rawData)
143+
if err != nil {
144+
return nil, fmt.Errorf("failed to create file from raw data: %v", err)
145+
}
146+
147+
bundleFiles[key] = bundleFile
148+
}
149+
150+
return &Batch{
151+
documents: bundleFiles,
152+
}, nil
153+
}
154+
137155
// todo simplify the size computation
138156
// maybe consider an addFile / canFitFile interface with proper error handling
139157
func (b *Batch) canFitFile(uri string, content []byte) bool {

bundle/bundle_test.go

Lines changed: 49 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,7 @@ import (
2020
"context"
2121
"crypto/sha256"
2222
"encoding/hex"
23+
"fmt"
2324
"os"
2425
"testing"
2526

@@ -39,6 +40,29 @@ var bundleWithMultipleFiles = bundle.NewBatch(map[string]deepcode.BundleFile{
3940
"file": {},
4041
"another": {},
4142
})
43+
var bundleFromRawContent, batchErr = bundle.NewBatchFromRawContent(map[string][]byte{"hello": []byte("world")})
44+
45+
// Matcher for BundleFile that matches on key and content (ignores hash)
46+
type bundleFilePartialMatcher struct {
47+
expectedKey string
48+
expectedContent string
49+
}
50+
51+
func (m bundleFilePartialMatcher) Matches(x interface{}) bool {
52+
files, ok := x.(map[string]deepcode.BundleFile)
53+
if !ok {
54+
return false
55+
}
56+
file, exists := files[m.expectedKey]
57+
if !exists {
58+
return false
59+
}
60+
return file.Content == m.expectedContent
61+
}
62+
63+
func (m bundleFilePartialMatcher) String() string {
64+
return fmt.Sprintf("{ Key : '%s', Content : '%s' }", m.expectedKey, m.expectedContent)
65+
}
4266

4367
func Test_UploadBatch(t *testing.T) {
4468
testLogger := zerolog.Nop()
@@ -108,6 +132,31 @@ func Test_UploadBatch(t *testing.T) {
108132
})
109133
}
110134

135+
func Test_RawContentBatch(t *testing.T) {
136+
testLogger := zerolog.Nop()
137+
138+
t.Run("create a batch from raw content and upload the bundle", func(t *testing.T) {
139+
ctrl := gomock.NewController(t)
140+
mockSnykCodeClient := deepcodeMocks.NewMockDeepcodeClient(ctrl)
141+
mockSnykCodeClient.EXPECT().ExtendBundle(gomock.Any(), "testBundleHash", bundleFilePartialMatcher{expectedKey: "hello", expectedContent: "world"}, []string{}).Return("newBundleHash", []string{}, nil).Times(1)
142+
143+
mockSpan := mocks.NewMockSpan(ctrl)
144+
mockSpan.EXPECT().Context().AnyTimes()
145+
mockInstrumentor := mocks.NewMockInstrumentor(ctrl)
146+
mockInstrumentor.EXPECT().StartSpan(gomock.Any(), gomock.Any()).Return(mockSpan).AnyTimes()
147+
mockInstrumentor.EXPECT().Finish(gomock.Any()).AnyTimes()
148+
mockErrorReporter := mocks.NewMockErrorReporter(ctrl)
149+
b := bundle.NewBundle(mockSnykCodeClient, mockInstrumentor, mockErrorReporter, &testLogger, "testRootPath", "testBundleHash", map[string]deepcode.BundleFile{}, []string{}, []string{})
150+
151+
require.NoError(t, batchErr)
152+
oldHash := b.GetBundleHash()
153+
err := b.UploadBatch(context.Background(), "testRequestId", bundleFromRawContent)
154+
require.NoError(t, err)
155+
newHash := b.GetBundleHash()
156+
assert.NotEqual(t, oldHash, newHash)
157+
})
158+
}
159+
111160
func Test_BundleEncoding(t *testing.T) {
112161
t.Run("utf-8 encoded content", func(t *testing.T) {
113162
content := []byte("hello")

0 commit comments

Comments
 (0)