From 075ba12cc537dbc9fcfd2420fe580ee7bedaa686 Mon Sep 17 00:00:00 2001 From: HollererJ Date: Tue, 5 Dec 2023 09:12:48 +0100 Subject: [PATCH 01/19] Add: added README.md for configReader --- pkg/configReader/README.md | 71 ++++++++++++++++++++++++++++++++++++++ 1 file changed, 71 insertions(+) create mode 100644 pkg/configReader/README.md diff --git a/pkg/configReader/README.md b/pkg/configReader/README.md new file mode 100644 index 0000000..3a82ca0 --- /dev/null +++ b/pkg/configReader/README.md @@ -0,0 +1,71 @@ +# Config Reader + +The `configReader` package provides a function `ReadEnvVarsIntoStruct` that can be used to read environment variables or config files into a struct. + +## Usage + +To use the `configReader` package, first create a struct that you want to read environment variables into: + +```go +type Config struct { + Port int `viperEnv:"port"` + Host string `viperEnV:"host" default:"localhost"` + LogLevel string `viperEnv:"LOG_LEVEL" default:"info"` +} +``` + +Then, in your code, you can use the `ReadEnvVarsIntoStruct` function to read environment variables into the struct: + +```go +package main + +import ( + "github.com/greenbone/opensight-golang-libraries/configReader" +) + +func main() { + var config Config + err := configReader.ReadEnvVarsIntoStruct(&config) + if err != nil { + panic(err) + } + // use the config +} +``` + +Any environment variables that match the struct fields will be read into the struct. The following environment variables will be read into the `Config` struct: + +``` +PORT=8080 +HOST=localhost +LOG_LEVEL=debug +``` + +If a field in the struct has a `viperEnv` tag, the environment variable will be matched to that tag. Otherwise, the field name will be used as the tag. + +If a field in the struct has a `default` tag, a default value will be used if the environment variable is not set. + +The `configReader` package uses [Viper](https://github.com/spf13/viper) for reading environment variables, and [Zerolog](https://github.com/rs/zerolog) for logging. + +## Maintainer + +This project is maintained by [Greenbone AG][Greenbone AG] + +## Contributing + +Your contributions are highly appreciated. Please +[create a pull request](https://github.com/greenbone/asset-management-backend/pulls) +on GitHub. Bigger changes need to be discussed with the development team via the +[issues section at GitHub](https://github.com/greenbone/asset-management-backend/issues) +first. + +## License + +Copyright (C) 2022-2023 [Greenbone AG][Greenbone AG] + +Licensed under the [GNU General Public License v3.0 or later](LICENSE). + +[Greenbone AG]: https://www.greenbone.net/ +[poetry]: https://python-poetry.org/ +[pip]: https://pip.pypa.io/ +[autohooks]: https://github.com/greenbone/autohooks \ No newline at end of file From b754b80c991cfab0ec11c2151059659104c752c8 Mon Sep 17 00:00:00 2001 From: Tim Steffens Date: Thu, 7 Dec 2023 20:12:18 +0100 Subject: [PATCH 02/19] use explicit initialization instead of indirect global variable --- .../open_search_query/aggregation_test.go | 2 +- .../open_search_query/boolQueryBuilder.go | 118 ++++++++++++------ .../boolQueryBuilder_test.go | 89 ++----------- .../open_search_query/compareHandler.go | 72 +++++------ .../open_search_query/compareHandler_test.go | 8 +- pkg/openSearch/open_search_query/filter.go | 20 +-- pkg/openSearch/open_search_query/sort_test.go | 2 +- 7 files changed, 147 insertions(+), 164 deletions(-) diff --git a/pkg/openSearch/open_search_query/aggregation_test.go b/pkg/openSearch/open_search_query/aggregation_test.go index 5471f95..5de7d96 100644 --- a/pkg/openSearch/open_search_query/aggregation_test.go +++ b/pkg/openSearch/open_search_query/aggregation_test.go @@ -13,7 +13,7 @@ import ( func TestAggregation(t *testing.T) { t.Run("shouldCreateJsonForNestedAggregations", func(t *testing.T) { - query := NewBoolQueryBuilder() + query := NewBoolQueryBuilder(&QuerySettings{}) query.AddAggregation( TermsAgg("aggNameOne", "hostname"). Aggs( diff --git a/pkg/openSearch/open_search_query/boolQueryBuilder.go b/pkg/openSearch/open_search_query/boolQueryBuilder.go index 9d48abf..b35505f 100644 --- a/pkg/openSearch/open_search_query/boolQueryBuilder.go +++ b/pkg/openSearch/open_search_query/boolQueryBuilder.go @@ -10,9 +10,22 @@ import ( "github.com/pkg/errors" ) +type boolQueryBuilder struct { + querySettings *QuerySettings + compareOperators []CompareOperator + size uint64 + query *esquery.BoolQuery + // aggregations aggregation of this search request. + // Deprecated: Better create custom implementation for more verbosity. + aggregations []Aggregation + Must []esquery.Mappable + MustNot []esquery.Mappable +} + type ( QueryAppender func(fieldName string, fieldKeys []string, fieldValue any) - CompareOperatorHandler func(fieldName string, fieldKeys []string, fieldValue any) esquery.Mappable + CompareOperatorHandler func(fieldName string, fieldKeys []string, fieldValue any, + querySettings *QuerySettings) esquery.Mappable ) type QuerySettings struct { @@ -20,7 +33,6 @@ type QuerySettings struct { IsEqualToKeywordFields map[string]bool UseNestedMatchQueryFields map[string]bool UseMatchPhrase map[string]bool - CompareOperators []CompareOperator NestedQueryFieldDefinitions []NestedQueryFieldDefinition FilterFieldMapping map[string]string } @@ -37,28 +49,34 @@ type CompareOperator struct { MustCondition bool } -var actualBoolQuerySettings QuerySettings +func NewBoolQueryBuilder(querySettings *QuerySettings) *boolQueryBuilder { + return NewBoolQueryBuilderWith(esquery.Bool(), querySettings) +} -func SetQuerySettings(settings QuerySettings) { - actualBoolQuerySettings = settings +func NewBoolQueryBuilderWith(query *esquery.BoolQuery, querySettings *QuerySettings) *boolQueryBuilder { + return &boolQueryBuilder{ + querySettings: querySettings, + compareOperators: defaultCompareOperators(), + query: query, + } } -type BoolQueryBuilder struct { - size uint64 - query *esquery.BoolQuery - // aggregations aggregation of this search request. - // Deprecated: Better create custom implementation for more verbosity. - aggregations []Aggregation - Must []esquery.Mappable - MustNot []esquery.Mappable +func (q *boolQueryBuilder) ReplaceCompareOperators(operators []CompareOperator) *boolQueryBuilder { + q.compareOperators = operators + return q +} + +func (q *boolQueryBuilder) AddCompareOperators(operators ...CompareOperator) *boolQueryBuilder { + q.compareOperators = append(q.compareOperators, operators...) + return q } -func (q *BoolQueryBuilder) AddTermsFilter(fieldName string, values ...interface{}) *BoolQueryBuilder { +func (q *boolQueryBuilder) AddTermsFilter(fieldName string, values ...interface{}) *boolQueryBuilder { q.query = q.query.Filter(esquery.Terms(fieldName, values...)) return q } -func (q *BoolQueryBuilder) AddTermFilter(fieldName string, value interface{}) *BoolQueryBuilder { +func (q *boolQueryBuilder) AddTermFilter(fieldName string, value interface{}) *boolQueryBuilder { q.query = q.query.Filter(esquery.Term(fieldName, value)) return q } @@ -66,38 +84,38 @@ func (q *BoolQueryBuilder) AddTermFilter(fieldName string, value interface{}) *B // AddAggregation adds an aggregation to this search request. // // Deprecated: Better create custom implementation for more verbosity. -func (q *BoolQueryBuilder) AddAggregation(aggregation Aggregation) *BoolQueryBuilder { +func (q *boolQueryBuilder) AddAggregation(aggregation Aggregation) *boolQueryBuilder { q.aggregations = append(q.aggregations, aggregation) return q } -func (q *BoolQueryBuilder) Size(size uint64) *BoolQueryBuilder { +func (q *boolQueryBuilder) Size(size uint64) *boolQueryBuilder { q.size = size return q } -func (q *BoolQueryBuilder) AddToMust(call CompareOperatorHandler) QueryAppender { +func (q *boolQueryBuilder) AddToMust(call CompareOperatorHandler) QueryAppender { return func(fieldName string, fieldKeys []string, fieldValue any) { - value := call(fieldName, fieldKeys, fieldValue) + value := call(fieldName, fieldKeys, fieldValue, q.querySettings) if value != nil { q.Must = append(q.Must, value) } } } -func (q *BoolQueryBuilder) AddToMustNot(call CompareOperatorHandler) QueryAppender { +func (q *boolQueryBuilder) AddToMustNot(call CompareOperatorHandler) QueryAppender { return func(fieldName string, fieldKeys []string, fieldValue any) { - value := call(fieldName, fieldKeys, fieldValue) + value := call(fieldName, fieldKeys, fieldValue, q.querySettings) if value != nil { q.MustNot = append(q.MustNot, value) } } } -func (q *BoolQueryBuilder) createOperatorMapping() map[filter.CompareOperator]QueryAppender { +func (q *boolQueryBuilder) createOperatorMapping() map[filter.CompareOperator]QueryAppender { operatorMapping := make(map[filter.CompareOperator]QueryAppender, - len(actualBoolQuerySettings.CompareOperators)) - for _, setting := range actualBoolQuerySettings.CompareOperators { + len(q.compareOperators)) + for _, setting := range q.compareOperators { if setting.MustCondition { operatorMapping[setting.Operator] = q.AddToMust(setting.Handler) } else { @@ -107,12 +125,12 @@ func (q *BoolQueryBuilder) createOperatorMapping() map[filter.CompareOperator]Qu return operatorMapping } -func (q *BoolQueryBuilder) AddFilterRequest(request *filter.Request) error { +func (q *boolQueryBuilder) AddFilterRequest(request *filter.Request) error { if request == nil { return nil } - effectiveRequest, err := EffectiveFilterFields(*request) + effectiveRequest, err := EffectiveFilterFields(*request, q.querySettings.FilterFieldMapping) if err != nil { return errors.WithStack(err) } @@ -153,14 +171,14 @@ func (q *BoolQueryBuilder) AddFilterRequest(request *filter.Request) error { } } -func (q *BoolQueryBuilder) Build() *esquery.BoolQuery { +func (q *boolQueryBuilder) Build() *esquery.BoolQuery { return q.query } // ToJson returns a json representation of the search request // // Deprecated: do not use due to dubious size setting. Better create custom implementation. -func (q *BoolQueryBuilder) ToJson() (json string, err error) { +func (q *boolQueryBuilder) ToJson() (json string, err error) { size := q.size if size == 0 { // TODO: 15.08.2022 stolksdorf - current default size is 100 until we get paging @@ -193,14 +211,40 @@ func (q *BoolQueryBuilder) ToJson() (json string, err error) { return string(jsonByte), nil } -func NewBoolQueryBuilder() *BoolQueryBuilder { - return &BoolQueryBuilder{ - query: esquery.Bool(), - } -} - -func NewBoolQueryBuilderWith(query *esquery.BoolQuery) *BoolQueryBuilder { - return &BoolQueryBuilder{ - query: query, +func defaultCompareOperators() []CompareOperator { + return []CompareOperator{ + {Operator: filter.CompareOperatorIsEqualTo, Handler: HandleCompareOperatorIsEqualTo, MustCondition: true}, + {Operator: filter.CompareOperatorIsNotEqualTo, Handler: HandleCompareOperatorIsEqualTo, MustCondition: false}, + {Operator: filter.CompareOperatorIsNumberEqualTo, Handler: HandleCompareOperatorIsEqualTo, MustCondition: true}, + { + Operator: filter.CompareOperatorIsNumberNotEqualTo, + Handler: HandleCompareOperatorIsEqualTo, MustCondition: false, + }, + {Operator: filter.CompareOperatorIsIpEqualTo, Handler: HandleCompareOperatorIsKeywordEqualTo, MustCondition: true}, + {Operator: filter.CompareOperatorIsIpNotEqualTo, Handler: HandleCompareOperatorIsKeywordEqualTo, MustCondition: false}, + {Operator: filter.CompareOperatorIsStringEqualTo, Handler: HandleCompareOperatorIsKeywordEqualTo, MustCondition: true}, + { + Operator: filter.CompareOperatorIsStringNotEqualTo, + Handler: HandleCompareOperatorIsKeywordEqualTo, MustCondition: false, + }, + {Operator: filter.CompareOperatorContains, Handler: HandleCompareOperatorContains, MustCondition: true}, + {Operator: filter.CompareOperatorDoesNotContain, Handler: HandleCompareOperatorContains, MustCondition: false}, + {Operator: filter.CompareOperatorBeginsWith, Handler: HandleCompareOperatorBeginsWith, MustCondition: true}, + { + Operator: filter.CompareOperatorDoesNotBeginWith, + Handler: HandleCompareOperatorNotBeginsWith, MustCondition: true, + }, + { + Operator: filter.CompareOperatorIsLessThanOrEqualTo, + Handler: HandleCompareOperatorIsLessThanOrEqualTo, MustCondition: true, + }, + { + Operator: filter.CompareOperatorIsGreaterThanOrEqualTo, + Handler: HandleCompareOperatorIsGreaterThanOrEqualTo, MustCondition: true, + }, + {Operator: filter.CompareOperatorIsGreaterThan, Handler: HandleCompareOperatorIsGreaterThan, MustCondition: true}, + {Operator: filter.CompareOperatorIsLessThan, Handler: HandleCompareOperatorIsLessThan, MustCondition: true}, + {Operator: filter.CompareOperatorAfterDate, Handler: HandleCompareOperatorIsGreaterThan, MustCondition: true}, + {Operator: filter.CompareOperatorBeforeDate, Handler: HandleCompareOperatorIsLessThan, MustCondition: true}, } } diff --git a/pkg/openSearch/open_search_query/boolQueryBuilder_test.go b/pkg/openSearch/open_search_query/boolQueryBuilder_test.go index 41853ce..fef5db6 100644 --- a/pkg/openSearch/open_search_query/boolQueryBuilder_test.go +++ b/pkg/openSearch/open_search_query/boolQueryBuilder_test.go @@ -16,12 +16,15 @@ import ( // TODO free from JSON generation for easier testing? func TestBoolQueryBuilder(t *testing.T) { var ( - query *BoolQueryBuilder + query *boolQueryBuilder folder testFolder.TestFolder ) setup := func(t *testing.T) { - query = NewBoolQueryBuilder() + querySettings := QuerySettings{ + FilterFieldMapping: map[string]string{"testName": "testName"}, + } + query = NewBoolQueryBuilder(&querySettings) folder = testFolder.NewTestFolder() } @@ -46,16 +49,6 @@ func TestBoolQueryBuilder(t *testing.T) { t.Run("shouldReturnJsonForFilterTermWithFilterRequest", func(t *testing.T) { setup(t) - SetQuerySettings(QuerySettings{ - CompareOperators: []CompareOperator{ - { - Operator: filter.CompareOperatorBeginsWith, - Handler: HandleCompareOperatorBeginsWith, MustCondition: true, - }, - }, - FilterFieldMapping: map[string]string{"testName": "testName"}, - }) - query.AddTermFilter("foo", "bar") err := query.AddFilterRequest(&filter.Request{ Operator: filter.LogicOperatorAnd, @@ -76,36 +69,9 @@ func TestBoolQueryBuilder(t *testing.T) { } func TestFilterQueryOperatorAnd(t *testing.T) { - SetQuerySettings(QuerySettings{ - CompareOperators: []CompareOperator{ - { - Operator: filter.CompareOperatorIsStringEqualTo, - Handler: HandleCompareOperatorIsKeywordEqualTo, MustCondition: true, - }, - { - Operator: filter.CompareOperatorIsStringNotEqualTo, - Handler: HandleCompareOperatorIsKeywordEqualTo, MustCondition: false, - }, - {Operator: filter.CompareOperatorContains, Handler: HandleCompareOperatorContains, MustCondition: true}, - {Operator: filter.CompareOperatorDoesNotContain, Handler: HandleCompareOperatorContains, MustCondition: false}, - {Operator: filter.CompareOperatorBeginsWith, Handler: HandleCompareOperatorBeginsWith, MustCondition: true}, - { - Operator: filter.CompareOperatorDoesNotBeginWith, - Handler: HandleCompareOperatorNotBeginsWith, MustCondition: true, - }, - { - Operator: filter.CompareOperatorIsLessThanOrEqualTo, - Handler: HandleCompareOperatorIsLessThanOrEqualTo, MustCondition: true, - }, - { - Operator: filter.CompareOperatorIsGreaterThanOrEqualTo, - Handler: HandleCompareOperatorIsGreaterThanOrEqualTo, MustCondition: true, - }, - {Operator: filter.CompareOperatorIsGreaterThan, Handler: HandleCompareOperatorIsGreaterThan, MustCondition: true}, - {Operator: filter.CompareOperatorIsLessThan, Handler: HandleCompareOperatorIsLessThan, MustCondition: true}, - }, + querySettings := QuerySettings{ FilterFieldMapping: map[string]string{"testName": "testName"}, - }) + } mixedTests := map[string]struct { file string @@ -162,7 +128,7 @@ func TestFilterQueryOperatorAnd(t *testing.T) { } for name, tc := range mixedTests { t.Run(name, func(t *testing.T) { - query := NewBoolQueryBuilder() + query := NewBoolQueryBuilder(&querySettings) err := query.AddFilterRequest(&filter.Request{ Operator: filter.LogicOperatorAnd, Fields: []filter.RequestField{ @@ -206,7 +172,7 @@ func TestFilterQueryOperatorAnd(t *testing.T) { } for name, tc := range singleValueTests { t.Run(name, func(t *testing.T) { - query := NewBoolQueryBuilder() + query := NewBoolQueryBuilder(&querySettings) err := query.AddFilterRequest(&filter.Request{ Operator: filter.LogicOperatorAnd, Fields: []filter.RequestField{ @@ -228,38 +194,9 @@ func TestFilterQueryOperatorAnd(t *testing.T) { } func TestFilterQueryOperatorOr(t *testing.T) { - SetQuerySettings(QuerySettings{ - CompareOperators: []CompareOperator{ - {Operator: filter.CompareOperatorIsEqualTo, Handler: HandleCompareOperatorIsEqualTo, MustCondition: true}, - {Operator: filter.CompareOperatorIsNotEqualTo, Handler: HandleCompareOperatorIsEqualTo, MustCondition: false}, - { - Operator: filter.CompareOperatorIsStringEqualTo, - Handler: HandleCompareOperatorIsKeywordEqualTo, MustCondition: true, - }, - { - Operator: filter.CompareOperatorIsStringNotEqualTo, - Handler: HandleCompareOperatorIsKeywordEqualTo, MustCondition: false, - }, - {Operator: filter.CompareOperatorContains, Handler: HandleCompareOperatorContains, MustCondition: true}, - {Operator: filter.CompareOperatorDoesNotContain, Handler: HandleCompareOperatorContains, MustCondition: false}, - {Operator: filter.CompareOperatorBeginsWith, Handler: HandleCompareOperatorBeginsWith, MustCondition: true}, - { - Operator: filter.CompareOperatorDoesNotBeginWith, - Handler: HandleCompareOperatorNotBeginsWith, MustCondition: true, - }, - { - Operator: filter.CompareOperatorIsLessThanOrEqualTo, - Handler: HandleCompareOperatorIsLessThanOrEqualTo, MustCondition: true, - }, - { - Operator: filter.CompareOperatorIsGreaterThanOrEqualTo, - Handler: HandleCompareOperatorIsGreaterThanOrEqualTo, MustCondition: true, - }, - {Operator: filter.CompareOperatorIsGreaterThan, Handler: HandleCompareOperatorIsGreaterThan, MustCondition: true}, - {Operator: filter.CompareOperatorIsLessThan, Handler: HandleCompareOperatorIsLessThan, MustCondition: true}, - }, + querySettings := QuerySettings{ FilterFieldMapping: map[string]string{"testName": "testName"}, - }) + } mixedTests := map[string]struct { file string @@ -321,7 +258,7 @@ func TestFilterQueryOperatorOr(t *testing.T) { } for name, tc := range mixedTests { t.Run(name, func(t *testing.T) { - query := NewBoolQueryBuilder() + query := NewBoolQueryBuilder(&querySettings) err := query.AddFilterRequest(&filter.Request{ Operator: filter.LogicOperatorOr, Fields: []filter.RequestField{ @@ -364,7 +301,7 @@ func TestFilterQueryOperatorOr(t *testing.T) { } for name, tc := range singleValueTests { t.Run(name, func(t *testing.T) { - query := NewBoolQueryBuilder() + query := NewBoolQueryBuilder(&querySettings) err := query.AddFilterRequest(&filter.Request{ Operator: filter.LogicOperatorAnd, Fields: []filter.RequestField{ diff --git a/pkg/openSearch/open_search_query/compareHandler.go b/pkg/openSearch/open_search_query/compareHandler.go index 23eb2b7..ce285dc 100644 --- a/pkg/openSearch/open_search_query/compareHandler.go +++ b/pkg/openSearch/open_search_query/compareHandler.go @@ -13,25 +13,25 @@ import ( ) // HandleCompareOperatorIsEqualTo handles is equal to -func HandleCompareOperatorIsEqualTo(fieldName string, fieldKeys []string, fieldValue any) esquery.Mappable { - return createTermQuery(fieldName, fieldValue, fieldKeys) +func HandleCompareOperatorIsEqualTo(fieldName string, fieldKeys []string, fieldValue any, querySettings *QuerySettings) esquery.Mappable { + return createTermQuery(fieldName, fieldValue, fieldKeys, querySettings) } // HandleCompareOperatorIsKeywordEqualTo handles is keyword field equal to -func HandleCompareOperatorIsKeywordEqualTo(fieldName string, fieldKeys []string, fieldValue any) esquery.Mappable { - return createTermQuery(fieldName+".keyword", fieldValue, fieldKeys) +func HandleCompareOperatorIsKeywordEqualTo(fieldName string, fieldKeys []string, fieldValue any, querySettings *QuerySettings) esquery.Mappable { + return createTermQuery(fieldName+".keyword", fieldValue, fieldKeys, querySettings) } // HandleCompareOperatorContains handles contains -func HandleCompareOperatorContains(fieldName string, fieldKeys []string, fieldValue any) esquery.Mappable { - if actualBoolQuerySettings.UseNestedMatchQueryFields != nil && - actualBoolQuerySettings.UseNestedMatchQueryFields[fieldName] { - return nestedHandleCompareOperatorContains(fieldName, fieldKeys, fieldValue) +func HandleCompareOperatorContains(fieldName string, fieldKeys []string, fieldValue any, querySettings *QuerySettings) esquery.Mappable { + if querySettings.UseNestedMatchQueryFields != nil && + querySettings.UseNestedMatchQueryFields[fieldName] { + return nestedHandleCompareOperatorContains(fieldName, fieldKeys, fieldValue, querySettings) } // for list of values - if actualBoolQuerySettings.WildcardArrays != nil && - actualBoolQuerySettings.WildcardArrays[fieldName] { - return handleCompareOperatorContainsDifferent(fieldName, nil, fieldValue) + if querySettings.WildcardArrays != nil && + querySettings.WildcardArrays[fieldName] { + return handleCompareOperatorContainsDifferent(fieldName, nil, fieldValue, querySettings) } else { if values, ok := fieldValue.([]interface{}); ok { return esquery.Bool(). @@ -47,9 +47,9 @@ func HandleCompareOperatorContains(fieldName string, fieldKeys []string, fieldVa } } -func nestedHandleCompareOperatorContains(fieldName string, fieldKeys []string, fieldValue any) esquery.Mappable { +func nestedHandleCompareOperatorContains(fieldName string, fieldKeys []string, fieldValue any, querySettings *QuerySettings) esquery.Mappable { // Special case as now for one input we need to queries to be set (for name and value) - nestedFieldSetting := findNestedFieldByName(fieldName) + nestedFieldSetting := findNestedFieldByName(fieldName, querySettings) if nestedFieldSetting != nil && len(fieldKeys) == 1 { query1 := Nested(nestedFieldSetting.FieldKeyName, *esquery.Bool(). Must( @@ -60,7 +60,7 @@ func nestedHandleCompareOperatorContains(fieldName string, fieldKeys []string, f return nil } -func handleCompareOperatorContainsDifferent(fieldName string, fieldKeys []string, fieldValue any) esquery.Mappable { +func handleCompareOperatorContainsDifferent(fieldName string, fieldKeys []string, fieldValue any, querySettings *QuerySettings) esquery.Mappable { if values, ok := fieldValue.([]interface{}); ok { return esquery.Bool(). Should( @@ -75,7 +75,7 @@ func handleCompareOperatorContainsDifferent(fieldName string, fieldKeys []string } // HandleCompareOperatorBeginsWith handles begins with -func HandleCompareOperatorBeginsWith(fieldName string, fieldKeys []string, fieldValue any) esquery.Mappable { +func HandleCompareOperatorBeginsWith(fieldName string, fieldKeys []string, fieldValue any, querySettings *QuerySettings) esquery.Mappable { // for list of values if values, ok := fieldValue.([]interface{}); ok { return esquery.Bool(). @@ -90,7 +90,7 @@ func HandleCompareOperatorBeginsWith(fieldName string, fieldKeys []string, field } } -func HandleCompareOperatorNotBeginsWith(fieldName string, fieldKeys []string, fieldValue any) esquery.Mappable { +func HandleCompareOperatorNotBeginsWith(fieldName string, fieldKeys []string, fieldValue any, querySettings *QuerySettings) esquery.Mappable { // for list of values if values, ok := fieldValue.([]interface{}); ok { return esquery.Bool(). @@ -105,32 +105,34 @@ func HandleCompareOperatorNotBeginsWith(fieldName string, fieldKeys []string, fi } // HandleCompareOperatorIsLessThanOrEqualTo handles is less than or equal to -func HandleCompareOperatorIsLessThanOrEqualTo(fieldName string, fieldKeys []string, fieldValue any) esquery.Mappable { +func HandleCompareOperatorIsLessThanOrEqualTo(fieldName string, fieldKeys []string, fieldValue any, querySettings *QuerySettings) esquery.Mappable { return esquery.Range(fieldName). Lte(fieldValue) } // HandleCompareOperatorIsGreaterThanOrEqualTo handles is greater than or equal to -func HandleCompareOperatorIsGreaterThanOrEqualTo(fieldName string, fieldKeys []string, fieldValue any) esquery.Mappable { +func HandleCompareOperatorIsGreaterThanOrEqualTo(fieldName string, fieldKeys []string, + fieldValue any, querySettings *QuerySettings, +) esquery.Mappable { return esquery.Range(fieldName). Gte(fieldValue) } // HandleCompareOperatorIsGreaterThan handles is greater than -func HandleCompareOperatorIsGreaterThan(fieldName string, fieldKeys []string, fieldValue any) esquery.Mappable { +func HandleCompareOperatorIsGreaterThan(fieldName string, fieldKeys []string, fieldValue any, querySettings *QuerySettings) esquery.Mappable { return esquery.Range(fieldName). Gt(fieldValue) } // HandleCompareOperatorIsLessThan handles is less than -func HandleCompareOperatorIsLessThan(fieldName string, fieldKeys []string, fieldValue any) esquery.Mappable { +func HandleCompareOperatorIsLessThan(fieldName string, fieldKeys []string, fieldValue any, querySettings *QuerySettings) esquery.Mappable { return esquery.Range(fieldName). Lt(fieldValue) } -func simpleNestedMatchQuery(fieldName string, fieldKeys []string, fieldValue any) esquery.Mappable { +func simpleNestedMatchQuery(fieldName string, fieldKeys []string, fieldValue any, querySettings *QuerySettings) esquery.Mappable { // Special case as now for one input we need to queries to be set (for name and value) - nestedFieldSetting := findNestedFieldByName(fieldName) + nestedFieldSetting := findNestedFieldByName(fieldName, querySettings) if nestedFieldSetting != nil && len(fieldKeys) == 1 { query1 := Nested(nestedFieldSetting.FieldName, *esquery.Bool().Must( esquery.Match(nestedFieldSetting.FieldKeyName, fieldKeys[0]), @@ -140,10 +142,10 @@ func simpleNestedMatchQuery(fieldName string, fieldKeys []string, fieldValue any return nil } -func createTermQuery(fieldName string, fieldValue any, fieldKeys []string) esquery.Mappable { - if actualBoolQuerySettings.UseNestedMatchQueryFields != nil && - actualBoolQuerySettings.UseNestedMatchQueryFields[fieldName] { - return simpleNestedMatchQuery(fieldName, fieldKeys, fieldValue) +func createTermQuery(fieldName string, fieldValue any, fieldKeys []string, querySettings *QuerySettings) esquery.Mappable { + if querySettings.UseNestedMatchQueryFields != nil && + querySettings.UseNestedMatchQueryFields[fieldName] { + return simpleNestedMatchQuery(fieldName, fieldKeys, fieldValue, querySettings) } // for list of values if values, ok := fieldValue.([]interface{}); ok { @@ -151,18 +153,18 @@ func createTermQuery(fieldName string, fieldValue any, fieldKeys []string) esque return nil } - if actualBoolQuerySettings.IsEqualToKeywordFields != nil && - actualBoolQuerySettings.IsEqualToKeywordFields[fieldName] { + if querySettings.IsEqualToKeywordFields != nil && + querySettings.IsEqualToKeywordFields[fieldName] { fieldName = fieldName + ".keyword" } - if actualBoolQuerySettings.UseMatchPhrase != nil && - actualBoolQuerySettings.UseMatchPhrase[fieldName] { + if querySettings.UseMatchPhrase != nil && + querySettings.UseMatchPhrase[fieldName] { return esquery.MatchPhrase(fieldName, values...) } return esquery.Terms(fieldName, values...) } else { // for single values - if actualBoolQuerySettings.UseMatchPhrase != nil && - actualBoolQuerySettings.UseMatchPhrase[fieldName] { + if querySettings.UseMatchPhrase != nil && + querySettings.UseMatchPhrase[fieldName] { return esquery.MatchPhrase(fieldName, fieldValue) } return esquery.Term(fieldName, fieldValue) @@ -184,11 +186,11 @@ func valueToString(value interface{}) string { } } -func findNestedFieldByName(name string) *NestedQueryFieldDefinition { - if actualBoolQuerySettings.NestedQueryFieldDefinitions == nil { +func findNestedFieldByName(name string, querySettings *QuerySettings) *NestedQueryFieldDefinition { + if querySettings.NestedQueryFieldDefinitions == nil { return nil } - for _, field := range actualBoolQuerySettings.NestedQueryFieldDefinitions { + for _, field := range querySettings.NestedQueryFieldDefinitions { if field.FieldName == name { return &field // Gibt die Adresse des gefundenen Feldes zurück } diff --git a/pkg/openSearch/open_search_query/compareHandler_test.go b/pkg/openSearch/open_search_query/compareHandler_test.go index 53eb4c0..a6d8ac3 100644 --- a/pkg/openSearch/open_search_query/compareHandler_test.go +++ b/pkg/openSearch/open_search_query/compareHandler_test.go @@ -8,7 +8,7 @@ import ( ) func TestHandleCompareOperator(t *testing.T) { - SetQuerySettings(QuerySettings{ + querySettings := QuerySettings{ WildcardArrays: map[string]bool{ "asset.ips": true, "asset.macAddresses": true, @@ -23,11 +23,11 @@ func TestHandleCompareOperator(t *testing.T) { FieldValueName: "asset.tags.tagvalue", }, }, - }) + } tests := []struct { name string - handler func(string, []string, any) esquery.Mappable + handler CompareOperatorHandler field string keys []string value any @@ -96,7 +96,7 @@ func TestHandleCompareOperator(t *testing.T) { for _, tt := range tests { t.Run(tt.name, func(t *testing.T) { - assert.Equal(t, tt.expected, tt.handler(tt.field, tt.keys, tt.value)) + assert.Equal(t, tt.expected, tt.handler(tt.field, tt.keys, tt.value, &querySettings)) }) } } diff --git a/pkg/openSearch/open_search_query/filter.go b/pkg/openSearch/open_search_query/filter.go index c183161..2421780 100644 --- a/pkg/openSearch/open_search_query/filter.go +++ b/pkg/openSearch/open_search_query/filter.go @@ -4,31 +4,31 @@ package open_search_query -import "github.com/greenbone/opensight-golang-libraries/pkg/query/filter" +import queryFilter "github.com/greenbone/opensight-golang-libraries/pkg/query/filter" -func EffectiveFilterFields(filterRequest filter.Request) (filter.Request, error) { - var filterFields []filter.RequestField +func EffectiveFilterFields(filterRequest queryFilter.Request, fieldMapping map[string]string) (queryFilter.Request, error) { + var filterFields []queryFilter.RequestField for _, field := range filterRequest.Fields { - mappedField, err := createMappedField(field) + mappedField, err := createMappedField(field, fieldMapping) if err != nil { - return filter.Request{}, err + return queryFilter.Request{}, err } filterFields = append(filterFields, mappedField) } - return filter.Request{ + return queryFilter.Request{ Operator: filterRequest.Operator, Fields: filterFields, }, nil } -func createMappedField(dtoField filter.RequestField) (filter.RequestField, error) { - entityName, ok := actualBoolQuerySettings.FilterFieldMapping[dtoField.Name] +func createMappedField(dtoField queryFilter.RequestField, fieldMapping map[string]string) (queryFilter.RequestField, error) { + entityName, ok := fieldMapping[dtoField.Name] if !ok { - return filter.RequestField{}, filter.NewInvalidFilterFieldError( + return queryFilter.RequestField{}, queryFilter.NewInvalidFilterFieldError( "Mapping for filter field '%s' is currently not implemented.", dtoField.Name) } - return filter.RequestField{ + return queryFilter.RequestField{ Operator: dtoField.Operator, Keys: dtoField.Keys, Name: entityName, diff --git a/pkg/openSearch/open_search_query/sort_test.go b/pkg/openSearch/open_search_query/sort_test.go index 0cf2203..bd71796 100644 --- a/pkg/openSearch/open_search_query/sort_test.go +++ b/pkg/openSearch/open_search_query/sort_test.go @@ -54,7 +54,7 @@ func TestSorting(t *testing.T) { for name := range testCases { t.Run(name, func(t *testing.T) { - q := NewBoolQueryBuilder() + q := NewBoolQueryBuilder(&QuerySettings{}) subAggs := []esquery.Aggregation{} subAggs, err := AddMaxAggForSorting(subAggs, testCases[name].SortingRequest) if testCases[name].ExpectedErrorMessage != "" { From 69db91366814cdbbb3a37b7b391569cdcb35327e Mon Sep 17 00:00:00 2001 From: Tim Steffens Date: Thu, 7 Dec 2023 21:59:54 +0100 Subject: [PATCH 03/19] replace client with simpleClient --- pkg/openSearch/open_search_client/client.go | 340 ++---------------- .../open_search_client/simpleClient.go | 60 ---- 2 files changed, 33 insertions(+), 367 deletions(-) delete mode 100644 pkg/openSearch/open_search_client/simpleClient.go diff --git a/pkg/openSearch/open_search_client/client.go b/pkg/openSearch/open_search_client/client.go index 6861c9b..368481c 100644 --- a/pkg/openSearch/open_search_client/client.go +++ b/pkg/openSearch/open_search_client/client.go @@ -5,279 +5,70 @@ package open_search_client import ( - "fmt" + "bytes" "io" - "net/http" - "strings" + "time" - jsoniter "github.com/json-iterator/go" "github.com/opensearch-project/opensearch-go" "github.com/pkg/errors" "github.com/rs/zerolog/log" ) -type IndexFunctionsInterface interface { - CreateIndex(indexName string, body io.Reader) error +type simpleClient struct { + client *opensearch.Client + queue *requestQueue } -//go:generate mockery --name OpenSearchClientWithIndex --with-expecter=true -type OpenSearchClientWithIndex[T Identifiable] interface { - // Save save - Save(document T) error - - // SearchOne search one - SearchOne(body Json) (*T, error) - - // Search search - Search(body Json) (*SearchResponse[T], error) - - // UpdateById update by id - UpdateById(id string, body map[string]any) error - - // AsyncDeleteByQuery async delete by query - AsyncDeleteByQuery(body Json) error - - // DeleteByQuery delete by query - DeleteByQuery(body Json) error - - // DeleteById delete by id - DeleteById(id string) error - - // SearchString - SearchString(body string) (*SearchResponse[T], error) - - // GetClient - GetClient() *opensearch.Client - - // SaveVulnerabilitiesToIndex - SaveToIndex(indexName string, documents []T) error -} - -type openSearchClient[T Identifiable] struct { - client *opensearch.Client - indexName string -} - -func NewOpenSearchClient[T Identifiable](initClient *opensearch.Client, defaultIndexName string) *openSearchClient[T] { - return &openSearchClient[T]{ - client: initClient, - indexName: defaultIndexName, - } -} - -func (o *openSearchClient[T]) GetClient() *opensearch.Client { - return o.client -} - -func (o *openSearchClient[T]) UpdateById(id string, updateBody map[string]any) error { - jsonString, err := jsoniter.Marshal(&updateBody) - if err != nil { - return errors.Wrapf(err, "openSearch client can't marshal body with ID %q to JSON for update", id) +func NewSimpleClient(client *opensearch.Client, updateMaxRetries int, updateRetryDelay time.Duration) *simpleClient { + c := &simpleClient{ + client: client, } - - updateRequestString := `{ "doc": ` + string(jsonString) + `}` - - updateResponse, err := o.client.Update( - o.indexName, id, strings.NewReader(updateRequestString), - ) - if err != nil { - return errors.WithStack(err) - } - - resultString, err := io.ReadAll(updateResponse.Body) - if err != nil { - return errors.WithStack(err) - } - - return GetResponseError(updateResponse.StatusCode, resultString, o.indexName) + c.queue = NewRequestQueue(client, updateMaxRetries, updateRetryDelay) + return c } -func (o *openSearchClient[T]) Save(document T) error { - documentJson, err := jsoniter.Marshal(document) - if err != nil { - return errors.WithStack(err) - } - - insertResponse, err := o.client.Index( - o.indexName, - strings.NewReader(string(documentJson)), - o.client.Index.WithRefresh("true"), - o.client.Index.WithDocumentID(document.GetId()), +func (c *simpleClient) Search(indexName string, requestBody []byte) (responseBody []byte, err error) { + log.Debug().Msgf("search requestBody: %s", string(requestBody)) + searchResponse, err := c.client.Search( + c.client.Search.WithIndex(indexName), + c.client.Search.WithBody(bytes.NewReader(requestBody)), ) - if err != nil { - return errors.WithStack(err) - } - - resultString, err := io.ReadAll(insertResponse.Body) - if err != nil { - return errors.WithStack(err) - } - - err = GetResponseError(insertResponse.StatusCode, resultString, o.indexName) - if err != nil { - return errors.WithStack(err) - } - - response := &CreatedResponse{} - err = jsoniter.Unmarshal(resultString, response) - if err != nil { - return errors.WithStack(err) - } - - document.SetId(response.Id) - - return nil -} - -func (o *openSearchClient[T]) SearchOne(body Json) (*T, error) { - json, err := body.ToJson() - if err != nil { - return nil, err - } - - return o.searchOne(json) -} - -func (o *openSearchClient[T]) searchOne(jsonString string) (*T, error) { - elements, err := o.search(jsonString) if err != nil { return nil, errors.WithStack(err) } - if len(elements.Hits.SearchHits) == 0 { - return nil, NewOpenSearchResourceNotFoundWithStack( - fmt.Sprintf("Document not found '%s'", jsonString)) - } - - return &elements.Hits.SearchHits[0].Content, nil -} - -func (o *openSearchClient[T]) SearchString(body string) (*SearchResponse[T], error) { - return o.search(body) -} - -func (o *openSearchClient[T]) Search(body Json) (*SearchResponse[T], error) { - json, err := body.ToJson() - if err != nil { - return nil, err - } - return o.search(json) -} - -func (o *openSearchClient[T]) search(body string) (*SearchResponse[T], error) { - log.Trace().Msgf("search query - json:'%s'", body) - - searchResponse, err := o.client.Search( - o.client.Search.WithIndex(o.indexName), - o.client.Search.WithBody(strings.NewReader(body)), - ) + result, err := io.ReadAll(searchResponse.Body) if err != nil { return nil, errors.WithStack(err) } + log.Trace().Msgf("search response - statusCode:'%d' json:'%s'", searchResponse.StatusCode, result) - resultString, err := io.ReadAll(searchResponse.Body) + err = GetResponseError(searchResponse.StatusCode, result, indexName) if err != nil { return nil, errors.WithStack(err) } - log.Trace().Msgf("search response - statusCode:'%d' json:'%s'", searchResponse.StatusCode, resultString) - err = GetResponseError(searchResponse.StatusCode, resultString, o.indexName) - if err != nil { - return nil, errors.WithStack(err) - } - - var results SearchResponse[T] - - err = jsoniter.Unmarshal(resultString, &results) - if err != nil { - return nil, errors.WithStack(err) - } - - for _, searchHit := range results.Hits.SearchHits { - searchHit.Content.SetId(searchHit.Id) - } - - return &results, nil + return result, nil } -func (o *openSearchClient[T]) SaveAll(documents []T) error { - if len(documents) == 0 { - return nil - } - - var body strings.Builder - body.Reset() - - for _, document := range documents { - if document.GetId() != "" { - body.WriteString(fmt.Sprintf(`{"index": { "_index" : "%s", "_id": "%s"}}`, - o.indexName, document.GetId()) + "\n") - } else { - body.WriteString(fmt.Sprintf(`{"index": { "_index" : "%s"}}`, - o.indexName) + "\n") - } - - documentJson, err := jsoniter.Marshal(document) - if err != nil { - return errors.WithStack(err) - } - body.WriteString(string(documentJson) + "\n") - } - - insertResponse, err := o.client.Bulk( - strings.NewReader(body.String()), - o.client.Bulk.WithIndex(o.indexName), - o.client.Bulk.WithRefresh("true"), - ) - if err != nil { - return errors.WithStack(err) - } - - resultString, err := io.ReadAll(insertResponse.Body) - if err != nil { - return errors.WithStack(err) - } - - return GetResponseError(insertResponse.StatusCode, resultString, o.indexName) +func (c *simpleClient) Update(indexName string, requestBody []byte) (responseBody []byte, err error) { + return c.queue.Update(indexName, requestBody) } -func (o *openSearchClient[T]) AsyncDeleteByQuery(body Json) error { - return deleteByQuery(body, true, o) +func (c *simpleClient) AsyncDeleteByQuery(indexName string, requestBody []byte) error { + return c.deleteByQuery(indexName, requestBody, true) } -func (o *openSearchClient[T]) DeleteByQuery(body Json) error { - return deleteByQuery(body, false, o) +func (c *simpleClient) DeleteByQuery(indexName string, requestBody []byte) error { + return c.deleteByQuery(indexName, requestBody, false) } // deleteByQuery deletes documents by a query -func deleteByQuery[T Identifiable](body Json, isAsync bool, o *openSearchClient[T]) error { - json, err := body.ToJson() - if err != nil { - return err - } - - deleteResponse, err := o.client.DeleteByQuery( - []string{o.indexName}, - strings.NewReader(json), - o.client.DeleteByQuery.WithWaitForCompletion(!isAsync), - ) - if err != nil { - return errors.WithStack(err) - } - - resultString, err := io.ReadAll(deleteResponse.Body) - if err != nil { - return errors.WithStack(err) - } - - return GetResponseError(deleteResponse.StatusCode, resultString, o.indexName) -} - -// DeleteById deletes a document by id -func (o *openSearchClient[T]) DeleteById(id string) error { - deleteResponse, err := o.client.Delete( - o.indexName, - id, +func (c *simpleClient) deleteByQuery(indexName string, requestBody []byte, isAsync bool) error { + deleteResponse, err := c.client.DeleteByQuery( + []string{indexName}, + bytes.NewReader(requestBody), + c.client.DeleteByQuery.WithWaitForCompletion(!isAsync), ) if err != nil { return errors.WithStack(err) @@ -288,74 +79,9 @@ func (o *openSearchClient[T]) DeleteById(id string) error { return errors.WithStack(err) } - return GetResponseError(deleteResponse.StatusCode, resultString, o.indexName) + return GetResponseError(deleteResponse.StatusCode, resultString, indexName) } -func (o *openSearchClient[T]) SaveToIndex(indexName string, documents []T) error { - if len(documents) == 0 { - return nil - } - - var body strings.Builder - body.Reset() - - for _, document := range documents { - body.WriteString(fmt.Sprintf(`{"index": { "_index" : "%s"}}`, - indexName) + "\n") - documentJson, err := jsoniter.Marshal(document) - if err != nil { - return errors.WithStack(err) - } - body.WriteString(string(documentJson) + "\n") - } - - insertResponse, err := o.client.Bulk( - strings.NewReader(body.String()), - o.GetClient().Bulk.WithIndex(indexName), - o.GetClient().Bulk.WithRefresh("true"), - ) - if err != nil { - return errors.WithStack(err) - } - - resultString, err := io.ReadAll(insertResponse.Body) - if err != nil { - return errors.WithStack(err) - } - - return GetResponseError(insertResponse.StatusCode, resultString, indexName) -} - -// GetResponseError gets the error from the response -func GetResponseError(statusCode int, responseString []byte, indexName string) error { - if statusCode >= 200 && statusCode < 300 { - errorResponse := &BulkResponse{} - err := jsoniter.Unmarshal(responseString, errorResponse) - if err != nil { - return errors.WithStack(err) - } - - if errorResponse.HasError { - return errors.Errorf("request error %v", errorResponse) - } - - return nil - } - - if statusCode == http.StatusBadRequest { - openSearchErrorResponse := &OpenSearchErrorResponse{} - err := jsoniter.Unmarshal(responseString, openSearchErrorResponse) - if err != nil { - return errors.WithStack(err) - } - - if openSearchErrorResponse.Error.Type == "resource_already_exists_exception" { - return NewOpenSearchResourceAlreadyExistsWithStack( - fmt.Sprintf("Resource '%s' already exists", indexName)) - } else { - return NewOpenSearchErrorWithStack(openSearchErrorResponse.Error.Reason) - } - } else { - return NewOpenSearchErrorWithStack(string(responseString)) - } +func (c *simpleClient) Close() { + c.queue.Stop() } diff --git a/pkg/openSearch/open_search_client/simpleClient.go b/pkg/openSearch/open_search_client/simpleClient.go deleted file mode 100644 index d902faa..0000000 --- a/pkg/openSearch/open_search_client/simpleClient.go +++ /dev/null @@ -1,60 +0,0 @@ -// Copyright (C) Greenbone Networks GmbH -// -// SPDX-License-Identifier: AGPL-3.0-or-later - -package open_search_client - -import ( - "bytes" - "io" - "time" - - "github.com/opensearch-project/opensearch-go" - "github.com/pkg/errors" - "github.com/rs/zerolog/log" -) - -type simpleClient struct { - client *opensearch.Client - queue *requestQueue -} - -func NewSimpleClient(client *opensearch.Client, updateMaxRetries int, updateRetryDelay time.Duration) *simpleClient { - c := &simpleClient{ - client: client, - } - c.queue = NewRequestQueue(client, updateMaxRetries, updateRetryDelay) - return c -} - -func (c *simpleClient) Search(indexName string, requestBody []byte) (responseBody []byte, err error) { - log.Debug().Msgf("search requestBody: %s", string(requestBody)) - searchResponse, err := c.client.Search( - c.client.Search.WithIndex(indexName), - c.client.Search.WithBody(bytes.NewReader(requestBody)), - ) - if err != nil { - return nil, errors.WithStack(err) - } - - result, err := io.ReadAll(searchResponse.Body) - if err != nil { - return nil, errors.WithStack(err) - } - log.Trace().Msgf("search response - statusCode:'%d' json:'%s'", searchResponse.StatusCode, result) - - err = GetResponseError(searchResponse.StatusCode, result, indexName) - if err != nil { - return nil, errors.WithStack(err) - } - - return result, nil -} - -func (c *simpleClient) Update(indexName string, requestBody []byte) (responseBody []byte, err error) { - return c.queue.Update(indexName, requestBody) -} - -func (c *simpleClient) Close() { - c.queue.Stop() -} From 5cc14637ea4ecef7ccf97019dc6e2aa55594ef81 Mon Sep 17 00:00:00 2001 From: Tim Steffens Date: Thu, 7 Dec 2023 22:04:58 +0100 Subject: [PATCH 04/19] restore code lost by fs caching failure --- pkg/openSearch/open_search_client/client.go | 68 +++++++++++++++++++++ 1 file changed, 68 insertions(+) diff --git a/pkg/openSearch/open_search_client/client.go b/pkg/openSearch/open_search_client/client.go index 368481c..5b3012e 100644 --- a/pkg/openSearch/open_search_client/client.go +++ b/pkg/openSearch/open_search_client/client.go @@ -6,7 +6,11 @@ package open_search_client import ( "bytes" + "fmt" + jsoniter "github.com/json-iterator/go" "io" + "net/http" + "strings" "time" "github.com/opensearch-project/opensearch-go" @@ -82,6 +86,70 @@ func (c *simpleClient) deleteByQuery(indexName string, requestBody []byte, isAsy return GetResponseError(deleteResponse.StatusCode, resultString, indexName) } +func (c *simpleClient) SaveToIndex(indexName string, documents [][]byte) error { + if len(documents) == 0 { + return nil + } + + var body strings.Builder + body.Reset() + + for _, document := range documents { + body.WriteString(fmt.Sprintf(`{"index": { "_index" : "%s"}}`, + indexName) + "\n") + body.WriteString(string(document) + "\n") + } + + insertResponse, err := c.client.Bulk( + strings.NewReader(body.String()), + c.client.Bulk.WithIndex(indexName), + c.client.Bulk.WithRefresh("true"), + ) + if err != nil { + return errors.WithStack(err) + } + + resultString, err := io.ReadAll(insertResponse.Body) + if err != nil { + return errors.WithStack(err) + } + + return GetResponseError(insertResponse.StatusCode, resultString, indexName) +} + +func GetResponseError(statusCode int, responseString []byte, indexName string) error { + if statusCode >= 200 && statusCode < 300 { + errorResponse := &BulkResponse{} + err := jsoniter.Unmarshal(responseString, errorResponse) + if err != nil { + return errors.WithStack(err) + } + + if errorResponse.HasError { + return errors.Errorf("request error %v", errorResponse) + } + + return nil + } + + if statusCode == http.StatusBadRequest { + openSearchErrorResponse := &OpenSearchErrorResponse{} + err := jsoniter.Unmarshal(responseString, openSearchErrorResponse) + if err != nil { + return errors.WithStack(err) + } + + if openSearchErrorResponse.Error.Type == "resource_already_exists_exception" { + return NewOpenSearchResourceAlreadyExistsWithStack( + fmt.Sprintf("Resource '%s' already exists", indexName)) + } else { + return NewOpenSearchErrorWithStack(openSearchErrorResponse.Error.Reason) + } + } else { + return NewOpenSearchErrorWithStack(string(responseString)) + } +} + func (c *simpleClient) Close() { c.queue.Stop() } From d49300d2734db69a20f2d89930cdbc98111a9fea Mon Sep 17 00:00:00 2001 From: Tim Steffens Date: Thu, 7 Dec 2023 22:19:51 +0100 Subject: [PATCH 05/19] remove --- .../mocks/OpenSearchClientWithIndex.go | 496 ------------------ 1 file changed, 496 deletions(-) delete mode 100644 pkg/openSearch/open_search_client/mocks/OpenSearchClientWithIndex.go diff --git a/pkg/openSearch/open_search_client/mocks/OpenSearchClientWithIndex.go b/pkg/openSearch/open_search_client/mocks/OpenSearchClientWithIndex.go deleted file mode 100644 index a13a72c..0000000 --- a/pkg/openSearch/open_search_client/mocks/OpenSearchClientWithIndex.go +++ /dev/null @@ -1,496 +0,0 @@ -// Code generated by mockery v2.28.2. DO NOT EDIT. - -package mocks - -import ( - open_search_client "github.com/greenbone/opensight-golang-libraries/pkg/openSearch/open_search_client" - opensearch "github.com/opensearch-project/opensearch-go" - mock "github.com/stretchr/testify/mock" -) - -// OpenSearchClientWithIndex is an autogenerated mock type for the OpenSearchClientWithIndex type -type OpenSearchClientWithIndex[T open_search_client.Identifiable] struct { - mock.Mock -} - -type OpenSearchClientWithIndex_Expecter[T open_search_client.Identifiable] struct { - mock *mock.Mock -} - -func (_m *OpenSearchClientWithIndex[T]) EXPECT() *OpenSearchClientWithIndex_Expecter[T] { - return &OpenSearchClientWithIndex_Expecter[T]{mock: &_m.Mock} -} - -// AsyncDeleteByQuery provides a mock function with given fields: body -func (_m *OpenSearchClientWithIndex[T]) AsyncDeleteByQuery(body open_search_client.Json) error { - ret := _m.Called(body) - - var r0 error - if rf, ok := ret.Get(0).(func(open_search_client.Json) error); ok { - r0 = rf(body) - } else { - r0 = ret.Error(0) - } - - return r0 -} - -// OpenSearchClientWithIndex_AsyncDeleteByQuery_Call is a *mock.Call that shadows Run/Return methods with type explicit version for method 'AsyncDeleteByQuery' -type OpenSearchClientWithIndex_AsyncDeleteByQuery_Call[T open_search_client.Identifiable] struct { - *mock.Call -} - -// AsyncDeleteByQuery is a helper method to define mock.On call -// - body open_search_client.Json -func (_e *OpenSearchClientWithIndex_Expecter[T]) AsyncDeleteByQuery(body interface{}) *OpenSearchClientWithIndex_AsyncDeleteByQuery_Call[T] { - return &OpenSearchClientWithIndex_AsyncDeleteByQuery_Call[T]{Call: _e.mock.On("AsyncDeleteByQuery", body)} -} - -func (_c *OpenSearchClientWithIndex_AsyncDeleteByQuery_Call[T]) Run(run func(body open_search_client.Json)) *OpenSearchClientWithIndex_AsyncDeleteByQuery_Call[T] { - _c.Call.Run(func(args mock.Arguments) { - run(args[0].(open_search_client.Json)) - }) - return _c -} - -func (_c *OpenSearchClientWithIndex_AsyncDeleteByQuery_Call[T]) Return(_a0 error) *OpenSearchClientWithIndex_AsyncDeleteByQuery_Call[T] { - _c.Call.Return(_a0) - return _c -} - -func (_c *OpenSearchClientWithIndex_AsyncDeleteByQuery_Call[T]) RunAndReturn(run func(open_search_client.Json) error) *OpenSearchClientWithIndex_AsyncDeleteByQuery_Call[T] { - _c.Call.Return(run) - return _c -} - -// DeleteById provides a mock function with given fields: id -func (_m *OpenSearchClientWithIndex[T]) DeleteById(id string) error { - ret := _m.Called(id) - - var r0 error - if rf, ok := ret.Get(0).(func(string) error); ok { - r0 = rf(id) - } else { - r0 = ret.Error(0) - } - - return r0 -} - -// OpenSearchClientWithIndex_DeleteById_Call is a *mock.Call that shadows Run/Return methods with type explicit version for method 'DeleteById' -type OpenSearchClientWithIndex_DeleteById_Call[T open_search_client.Identifiable] struct { - *mock.Call -} - -// DeleteById is a helper method to define mock.On call -// - id string -func (_e *OpenSearchClientWithIndex_Expecter[T]) DeleteById(id interface{}) *OpenSearchClientWithIndex_DeleteById_Call[T] { - return &OpenSearchClientWithIndex_DeleteById_Call[T]{Call: _e.mock.On("DeleteById", id)} -} - -func (_c *OpenSearchClientWithIndex_DeleteById_Call[T]) Run(run func(id string)) *OpenSearchClientWithIndex_DeleteById_Call[T] { - _c.Call.Run(func(args mock.Arguments) { - run(args[0].(string)) - }) - return _c -} - -func (_c *OpenSearchClientWithIndex_DeleteById_Call[T]) Return(_a0 error) *OpenSearchClientWithIndex_DeleteById_Call[T] { - _c.Call.Return(_a0) - return _c -} - -func (_c *OpenSearchClientWithIndex_DeleteById_Call[T]) RunAndReturn(run func(string) error) *OpenSearchClientWithIndex_DeleteById_Call[T] { - _c.Call.Return(run) - return _c -} - -// DeleteByQuery provides a mock function with given fields: body -func (_m *OpenSearchClientWithIndex[T]) DeleteByQuery(body open_search_client.Json) error { - ret := _m.Called(body) - - var r0 error - if rf, ok := ret.Get(0).(func(open_search_client.Json) error); ok { - r0 = rf(body) - } else { - r0 = ret.Error(0) - } - - return r0 -} - -// OpenSearchClientWithIndex_DeleteByQuery_Call is a *mock.Call that shadows Run/Return methods with type explicit version for method 'DeleteByQuery' -type OpenSearchClientWithIndex_DeleteByQuery_Call[T open_search_client.Identifiable] struct { - *mock.Call -} - -// DeleteByQuery is a helper method to define mock.On call -// - body open_search_client.Json -func (_e *OpenSearchClientWithIndex_Expecter[T]) DeleteByQuery(body interface{}) *OpenSearchClientWithIndex_DeleteByQuery_Call[T] { - return &OpenSearchClientWithIndex_DeleteByQuery_Call[T]{Call: _e.mock.On("DeleteByQuery", body)} -} - -func (_c *OpenSearchClientWithIndex_DeleteByQuery_Call[T]) Run(run func(body open_search_client.Json)) *OpenSearchClientWithIndex_DeleteByQuery_Call[T] { - _c.Call.Run(func(args mock.Arguments) { - run(args[0].(open_search_client.Json)) - }) - return _c -} - -func (_c *OpenSearchClientWithIndex_DeleteByQuery_Call[T]) Return(_a0 error) *OpenSearchClientWithIndex_DeleteByQuery_Call[T] { - _c.Call.Return(_a0) - return _c -} - -func (_c *OpenSearchClientWithIndex_DeleteByQuery_Call[T]) RunAndReturn(run func(open_search_client.Json) error) *OpenSearchClientWithIndex_DeleteByQuery_Call[T] { - _c.Call.Return(run) - return _c -} - -// GetClient provides a mock function with given fields: -func (_m *OpenSearchClientWithIndex[T]) GetClient() *opensearch.Client { - ret := _m.Called() - - var r0 *opensearch.Client - if rf, ok := ret.Get(0).(func() *opensearch.Client); ok { - r0 = rf() - } else { - if ret.Get(0) != nil { - r0 = ret.Get(0).(*opensearch.Client) - } - } - - return r0 -} - -// OpenSearchClientWithIndex_GetClient_Call is a *mock.Call that shadows Run/Return methods with type explicit version for method 'GetClient' -type OpenSearchClientWithIndex_GetClient_Call[T open_search_client.Identifiable] struct { - *mock.Call -} - -// GetClient is a helper method to define mock.On call -func (_e *OpenSearchClientWithIndex_Expecter[T]) GetClient() *OpenSearchClientWithIndex_GetClient_Call[T] { - return &OpenSearchClientWithIndex_GetClient_Call[T]{Call: _e.mock.On("GetClient")} -} - -func (_c *OpenSearchClientWithIndex_GetClient_Call[T]) Run(run func()) *OpenSearchClientWithIndex_GetClient_Call[T] { - _c.Call.Run(func(args mock.Arguments) { - run() - }) - return _c -} - -func (_c *OpenSearchClientWithIndex_GetClient_Call[T]) Return(_a0 *opensearch.Client) *OpenSearchClientWithIndex_GetClient_Call[T] { - _c.Call.Return(_a0) - return _c -} - -func (_c *OpenSearchClientWithIndex_GetClient_Call[T]) RunAndReturn(run func() *opensearch.Client) *OpenSearchClientWithIndex_GetClient_Call[T] { - _c.Call.Return(run) - return _c -} - -// Save provides a mock function with given fields: document -func (_m *OpenSearchClientWithIndex[T]) Save(document T) error { - ret := _m.Called(document) - - var r0 error - if rf, ok := ret.Get(0).(func(T) error); ok { - r0 = rf(document) - } else { - r0 = ret.Error(0) - } - - return r0 -} - -// OpenSearchClientWithIndex_Save_Call is a *mock.Call that shadows Run/Return methods with type explicit version for method 'Save' -type OpenSearchClientWithIndex_Save_Call[T open_search_client.Identifiable] struct { - *mock.Call -} - -// Save is a helper method to define mock.On call -// - document T -func (_e *OpenSearchClientWithIndex_Expecter[T]) Save(document interface{}) *OpenSearchClientWithIndex_Save_Call[T] { - return &OpenSearchClientWithIndex_Save_Call[T]{Call: _e.mock.On("Save", document)} -} - -func (_c *OpenSearchClientWithIndex_Save_Call[T]) Run(run func(document T)) *OpenSearchClientWithIndex_Save_Call[T] { - _c.Call.Run(func(args mock.Arguments) { - run(args[0].(T)) - }) - return _c -} - -func (_c *OpenSearchClientWithIndex_Save_Call[T]) Return(_a0 error) *OpenSearchClientWithIndex_Save_Call[T] { - _c.Call.Return(_a0) - return _c -} - -func (_c *OpenSearchClientWithIndex_Save_Call[T]) RunAndReturn(run func(T) error) *OpenSearchClientWithIndex_Save_Call[T] { - _c.Call.Return(run) - return _c -} - -// SaveToIndex provides a mock function with given fields: indexName, documents -func (_m *OpenSearchClientWithIndex[T]) SaveToIndex(indexName string, documents []T) error { - ret := _m.Called(indexName, documents) - - var r0 error - if rf, ok := ret.Get(0).(func(string, []T) error); ok { - r0 = rf(indexName, documents) - } else { - r0 = ret.Error(0) - } - - return r0 -} - -// OpenSearchClientWithIndex_SaveToIndex_Call is a *mock.Call that shadows Run/Return methods with type explicit version for method 'SaveToIndex' -type OpenSearchClientWithIndex_SaveToIndex_Call[T open_search_client.Identifiable] struct { - *mock.Call -} - -// SaveToIndex is a helper method to define mock.On call -// - indexName string -// - documents []T -func (_e *OpenSearchClientWithIndex_Expecter[T]) SaveToIndex(indexName interface{}, documents interface{}) *OpenSearchClientWithIndex_SaveToIndex_Call[T] { - return &OpenSearchClientWithIndex_SaveToIndex_Call[T]{Call: _e.mock.On("SaveToIndex", indexName, documents)} -} - -func (_c *OpenSearchClientWithIndex_SaveToIndex_Call[T]) Run(run func(indexName string, documents []T)) *OpenSearchClientWithIndex_SaveToIndex_Call[T] { - _c.Call.Run(func(args mock.Arguments) { - run(args[0].(string), args[1].([]T)) - }) - return _c -} - -func (_c *OpenSearchClientWithIndex_SaveToIndex_Call[T]) Return(_a0 error) *OpenSearchClientWithIndex_SaveToIndex_Call[T] { - _c.Call.Return(_a0) - return _c -} - -func (_c *OpenSearchClientWithIndex_SaveToIndex_Call[T]) RunAndReturn(run func(string, []T) error) *OpenSearchClientWithIndex_SaveToIndex_Call[T] { - _c.Call.Return(run) - return _c -} - -// Search provides a mock function with given fields: body -func (_m *OpenSearchClientWithIndex[T]) Search(body open_search_client.Json) (*open_search_client.SearchResponse[T], error) { - ret := _m.Called(body) - - var r0 *open_search_client.SearchResponse[T] - var r1 error - if rf, ok := ret.Get(0).(func(open_search_client.Json) (*open_search_client.SearchResponse[T], error)); ok { - return rf(body) - } - if rf, ok := ret.Get(0).(func(open_search_client.Json) *open_search_client.SearchResponse[T]); ok { - r0 = rf(body) - } else { - if ret.Get(0) != nil { - r0 = ret.Get(0).(*open_search_client.SearchResponse[T]) - } - } - - if rf, ok := ret.Get(1).(func(open_search_client.Json) error); ok { - r1 = rf(body) - } else { - r1 = ret.Error(1) - } - - return r0, r1 -} - -// OpenSearchClientWithIndex_Search_Call is a *mock.Call that shadows Run/Return methods with type explicit version for method 'Search' -type OpenSearchClientWithIndex_Search_Call[T open_search_client.Identifiable] struct { - *mock.Call -} - -// Search is a helper method to define mock.On call -// - body open_search_client.Json -func (_e *OpenSearchClientWithIndex_Expecter[T]) Search(body interface{}) *OpenSearchClientWithIndex_Search_Call[T] { - return &OpenSearchClientWithIndex_Search_Call[T]{Call: _e.mock.On("Search", body)} -} - -func (_c *OpenSearchClientWithIndex_Search_Call[T]) Run(run func(body open_search_client.Json)) *OpenSearchClientWithIndex_Search_Call[T] { - _c.Call.Run(func(args mock.Arguments) { - run(args[0].(open_search_client.Json)) - }) - return _c -} - -func (_c *OpenSearchClientWithIndex_Search_Call[T]) Return(_a0 *open_search_client.SearchResponse[T], _a1 error) *OpenSearchClientWithIndex_Search_Call[T] { - _c.Call.Return(_a0, _a1) - return _c -} - -func (_c *OpenSearchClientWithIndex_Search_Call[T]) RunAndReturn(run func(open_search_client.Json) (*open_search_client.SearchResponse[T], error)) *OpenSearchClientWithIndex_Search_Call[T] { - _c.Call.Return(run) - return _c -} - -// SearchOne provides a mock function with given fields: body -func (_m *OpenSearchClientWithIndex[T]) SearchOne(body open_search_client.Json) (*T, error) { - ret := _m.Called(body) - - var r0 *T - var r1 error - if rf, ok := ret.Get(0).(func(open_search_client.Json) (*T, error)); ok { - return rf(body) - } - if rf, ok := ret.Get(0).(func(open_search_client.Json) *T); ok { - r0 = rf(body) - } else { - if ret.Get(0) != nil { - r0 = ret.Get(0).(*T) - } - } - - if rf, ok := ret.Get(1).(func(open_search_client.Json) error); ok { - r1 = rf(body) - } else { - r1 = ret.Error(1) - } - - return r0, r1 -} - -// OpenSearchClientWithIndex_SearchOne_Call is a *mock.Call that shadows Run/Return methods with type explicit version for method 'SearchOne' -type OpenSearchClientWithIndex_SearchOne_Call[T open_search_client.Identifiable] struct { - *mock.Call -} - -// SearchOne is a helper method to define mock.On call -// - body open_search_client.Json -func (_e *OpenSearchClientWithIndex_Expecter[T]) SearchOne(body interface{}) *OpenSearchClientWithIndex_SearchOne_Call[T] { - return &OpenSearchClientWithIndex_SearchOne_Call[T]{Call: _e.mock.On("SearchOne", body)} -} - -func (_c *OpenSearchClientWithIndex_SearchOne_Call[T]) Run(run func(body open_search_client.Json)) *OpenSearchClientWithIndex_SearchOne_Call[T] { - _c.Call.Run(func(args mock.Arguments) { - run(args[0].(open_search_client.Json)) - }) - return _c -} - -func (_c *OpenSearchClientWithIndex_SearchOne_Call[T]) Return(_a0 *T, _a1 error) *OpenSearchClientWithIndex_SearchOne_Call[T] { - _c.Call.Return(_a0, _a1) - return _c -} - -func (_c *OpenSearchClientWithIndex_SearchOne_Call[T]) RunAndReturn(run func(open_search_client.Json) (*T, error)) *OpenSearchClientWithIndex_SearchOne_Call[T] { - _c.Call.Return(run) - return _c -} - -// SearchString provides a mock function with given fields: body -func (_m *OpenSearchClientWithIndex[T]) SearchString(body string) (*open_search_client.SearchResponse[T], error) { - ret := _m.Called(body) - - var r0 *open_search_client.SearchResponse[T] - var r1 error - if rf, ok := ret.Get(0).(func(string) (*open_search_client.SearchResponse[T], error)); ok { - return rf(body) - } - if rf, ok := ret.Get(0).(func(string) *open_search_client.SearchResponse[T]); ok { - r0 = rf(body) - } else { - if ret.Get(0) != nil { - r0 = ret.Get(0).(*open_search_client.SearchResponse[T]) - } - } - - if rf, ok := ret.Get(1).(func(string) error); ok { - r1 = rf(body) - } else { - r1 = ret.Error(1) - } - - return r0, r1 -} - -// OpenSearchClientWithIndex_SearchString_Call is a *mock.Call that shadows Run/Return methods with type explicit version for method 'SearchString' -type OpenSearchClientWithIndex_SearchString_Call[T open_search_client.Identifiable] struct { - *mock.Call -} - -// SearchString is a helper method to define mock.On call -// - body string -func (_e *OpenSearchClientWithIndex_Expecter[T]) SearchString(body interface{}) *OpenSearchClientWithIndex_SearchString_Call[T] { - return &OpenSearchClientWithIndex_SearchString_Call[T]{Call: _e.mock.On("SearchString", body)} -} - -func (_c *OpenSearchClientWithIndex_SearchString_Call[T]) Run(run func(body string)) *OpenSearchClientWithIndex_SearchString_Call[T] { - _c.Call.Run(func(args mock.Arguments) { - run(args[0].(string)) - }) - return _c -} - -func (_c *OpenSearchClientWithIndex_SearchString_Call[T]) Return(_a0 *open_search_client.SearchResponse[T], _a1 error) *OpenSearchClientWithIndex_SearchString_Call[T] { - _c.Call.Return(_a0, _a1) - return _c -} - -func (_c *OpenSearchClientWithIndex_SearchString_Call[T]) RunAndReturn(run func(string) (*open_search_client.SearchResponse[T], error)) *OpenSearchClientWithIndex_SearchString_Call[T] { - _c.Call.Return(run) - return _c -} - -// UpdateById provides a mock function with given fields: id, body -func (_m *OpenSearchClientWithIndex[T]) UpdateById(id string, body map[string]interface{}) error { - ret := _m.Called(id, body) - - var r0 error - if rf, ok := ret.Get(0).(func(string, map[string]interface{}) error); ok { - r0 = rf(id, body) - } else { - r0 = ret.Error(0) - } - - return r0 -} - -// OpenSearchClientWithIndex_UpdateById_Call is a *mock.Call that shadows Run/Return methods with type explicit version for method 'UpdateById' -type OpenSearchClientWithIndex_UpdateById_Call[T open_search_client.Identifiable] struct { - *mock.Call -} - -// UpdateById is a helper method to define mock.On call -// - id string -// - body map[string]interface{} -func (_e *OpenSearchClientWithIndex_Expecter[T]) UpdateById(id interface{}, body interface{}) *OpenSearchClientWithIndex_UpdateById_Call[T] { - return &OpenSearchClientWithIndex_UpdateById_Call[T]{Call: _e.mock.On("UpdateById", id, body)} -} - -func (_c *OpenSearchClientWithIndex_UpdateById_Call[T]) Run(run func(id string, body map[string]interface{})) *OpenSearchClientWithIndex_UpdateById_Call[T] { - _c.Call.Run(func(args mock.Arguments) { - run(args[0].(string), args[1].(map[string]interface{})) - }) - return _c -} - -func (_c *OpenSearchClientWithIndex_UpdateById_Call[T]) Return(_a0 error) *OpenSearchClientWithIndex_UpdateById_Call[T] { - _c.Call.Return(_a0) - return _c -} - -func (_c *OpenSearchClientWithIndex_UpdateById_Call[T]) RunAndReturn(run func(string, map[string]interface{}) error) *OpenSearchClientWithIndex_UpdateById_Call[T] { - _c.Call.Return(run) - return _c -} - -type mockConstructorTestingTNewOpenSearchClientWithIndex interface { - mock.TestingT - Cleanup(func()) -} - -// NewOpenSearchClientWithIndex creates a new instance of OpenSearchClientWithIndex. It also registers a testing interface on the mock and a cleanup function to assert the mocks expectations. -func NewOpenSearchClientWithIndex[T open_search_client.Identifiable](t mockConstructorTestingTNewOpenSearchClientWithIndex) *OpenSearchClientWithIndex[T] { - mock := &OpenSearchClientWithIndex[T]{} - mock.Mock.Test(t) - - t.Cleanup(func() { mock.AssertExpectations(t) }) - - return mock -} From a144bbece79a5385c7c89323a674cd04f9c84f8e Mon Sep 17 00:00:00 2001 From: Tim Steffens Date: Thu, 7 Dec 2023 22:25:46 +0100 Subject: [PATCH 06/19] remove unused function --- pkg/openSearch/open_search_client/json.go | 9 --------- 1 file changed, 9 deletions(-) diff --git a/pkg/openSearch/open_search_client/json.go b/pkg/openSearch/open_search_client/json.go index a0081f0..02ddf54 100644 --- a/pkg/openSearch/open_search_client/json.go +++ b/pkg/openSearch/open_search_client/json.go @@ -82,15 +82,6 @@ func UnmarshalWithoutValidation(data []byte, v any) error { return nil } -func Marshal(v any) ([]byte, error) { - marshal, err := jsoniter.Marshal(v) - if err != nil { - return nil, errors.WithStack(err) - } - - return marshal, nil -} - func StructFields(value any) []string { typ := reflect.TypeOf(value) if typ.Kind() == reflect.Pointer { From d1ea6741266df2bac35affd1b0ea76966791e42a Mon Sep 17 00:00:00 2001 From: Tim Steffens Date: Thu, 7 Dec 2023 22:44:05 +0100 Subject: [PATCH 07/19] remove superflous code and some renamings --- pkg/openSearch/open_search_client/client.go | 3 +- .../{type.go => identifiable.go} | 12 ------ .../open_search_client/mockTransport.go | 42 ------------------- ...enSearch.go => openSearchTestContainer.go} | 0 pkg/openSearch/open_search_client/response.go | 8 ++++ .../open_search_client/searchEngine.go | 2 +- 6 files changed, 11 insertions(+), 56 deletions(-) rename pkg/openSearch/open_search_client/{type.go => identifiable.go} (52%) delete mode 100644 pkg/openSearch/open_search_client/mockTransport.go rename pkg/openSearch/open_search_client/{testOpenSearch.go => openSearchTestContainer.go} (100%) diff --git a/pkg/openSearch/open_search_client/client.go b/pkg/openSearch/open_search_client/client.go index 5b3012e..5accf49 100644 --- a/pkg/openSearch/open_search_client/client.go +++ b/pkg/openSearch/open_search_client/client.go @@ -7,12 +7,13 @@ package open_search_client import ( "bytes" "fmt" - jsoniter "github.com/json-iterator/go" "io" "net/http" "strings" "time" + jsoniter "github.com/json-iterator/go" + "github.com/opensearch-project/opensearch-go" "github.com/pkg/errors" "github.com/rs/zerolog/log" diff --git a/pkg/openSearch/open_search_client/type.go b/pkg/openSearch/open_search_client/identifiable.go similarity index 52% rename from pkg/openSearch/open_search_client/type.go rename to pkg/openSearch/open_search_client/identifiable.go index badf627..977137b 100644 --- a/pkg/openSearch/open_search_client/type.go +++ b/pkg/openSearch/open_search_client/identifiable.go @@ -9,15 +9,3 @@ type Identifiable interface { SetId(id string) } - -type Json interface { - ToJson() (string, error) -} - -type KeepJsonAsString []byte - -func (k *KeepJsonAsString) UnmarshalJSON(data []byte) error { - *k = data - - return nil -} diff --git a/pkg/openSearch/open_search_client/mockTransport.go b/pkg/openSearch/open_search_client/mockTransport.go deleted file mode 100644 index 2b09185..0000000 --- a/pkg/openSearch/open_search_client/mockTransport.go +++ /dev/null @@ -1,42 +0,0 @@ -// Copyright (C) Greenbone Networks GmbH -// -// SPDX-License-Identifier: AGPL-3.0-or-later - -package open_search_client - -import ( - "bytes" - "io" - "net/http" -) - -type MockTransport struct { - Request string - Response *http.Response - RoundTripFn func(req *http.Request) (*http.Response, error) -} - -func (t *MockTransport) RoundTrip(req *http.Request) (*http.Response, error) { - var buf bytes.Buffer - if req.Body != nil { - tee := io.TeeReader(req.Body, &buf) - - value, err := io.ReadAll(tee) - if err != nil { - return nil, err - } - t.Request = string(value) - } - - if t.RoundTripFn == nil { - t.RoundTripFn = func(req *http.Request) (*http.Response, error) { - return t.Response, nil - } - } - - response, err := t.RoundTripFn(req) - if err != nil { - return nil, err - } - return response, nil -} diff --git a/pkg/openSearch/open_search_client/testOpenSearch.go b/pkg/openSearch/open_search_client/openSearchTestContainer.go similarity index 100% rename from pkg/openSearch/open_search_client/testOpenSearch.go rename to pkg/openSearch/open_search_client/openSearchTestContainer.go diff --git a/pkg/openSearch/open_search_client/response.go b/pkg/openSearch/open_search_client/response.go index b5b253a..ebee83e 100644 --- a/pkg/openSearch/open_search_client/response.go +++ b/pkg/openSearch/open_search_client/response.go @@ -20,6 +20,14 @@ type SearchResponseHits[T Identifiable] struct { SearchHits []SearchResponseHit[T] `json:"hits"` } +type KeepJsonAsString []byte + +func (k *KeepJsonAsString) UnmarshalJSON(data []byte) error { + *k = data + + return nil +} + type DynamicAggregationHits struct { Total SearchResponseHitsTotal `json:"total"` SearchHits KeepJsonAsString `json:"hits"` diff --git a/pkg/openSearch/open_search_client/searchEngine.go b/pkg/openSearch/open_search_client/searchEngine.go index 844614d..1243be3 100644 --- a/pkg/openSearch/open_search_client/searchEngine.go +++ b/pkg/openSearch/open_search_client/searchEngine.go @@ -16,7 +16,7 @@ import ( "github.com/opensearch-project/opensearch-go/opensearchapi" ) -func NewSearchEngine(ctx context.Context) (*opensearch.Client, error) { +func NewOpensearchProjectClient(ctx context.Context) (*opensearch.Client, error) { config, confErr := config.ReadSearchEngineConfig() if confErr != nil { return nil, confErr From 036f9853cae604187a251945ee60e20a2d0f16f0 Mon Sep 17 00:00:00 2001 From: Tim Steffens Date: Thu, 7 Dec 2023 22:47:06 +0100 Subject: [PATCH 08/19] renaming for consistency --- .../{searchEngine.go => opensearchProjectClient.go} | 0 ...chTestContainer.go => opensearchTestContainer.go} | 12 ++++++------ 2 files changed, 6 insertions(+), 6 deletions(-) rename pkg/openSearch/open_search_client/{searchEngine.go => opensearchProjectClient.go} (100%) rename pkg/openSearch/open_search_client/{openSearchTestContainer.go => opensearchTestContainer.go} (80%) diff --git a/pkg/openSearch/open_search_client/searchEngine.go b/pkg/openSearch/open_search_client/opensearchProjectClient.go similarity index 100% rename from pkg/openSearch/open_search_client/searchEngine.go rename to pkg/openSearch/open_search_client/opensearchProjectClient.go diff --git a/pkg/openSearch/open_search_client/openSearchTestContainer.go b/pkg/openSearch/open_search_client/opensearchTestContainer.go similarity index 80% rename from pkg/openSearch/open_search_client/openSearchTestContainer.go rename to pkg/openSearch/open_search_client/opensearchTestContainer.go index 4959700..f961ae8 100644 --- a/pkg/openSearch/open_search_client/openSearchTestContainer.go +++ b/pkg/openSearch/open_search_client/opensearchTestContainer.go @@ -12,13 +12,13 @@ import ( ) // Container represents the opensearch container type used in the module -type OpenSearchTestContainer struct { +type OpensearchTestContainer struct { testcontainers.Container } const openSearchTestDefaultHttpPort = "9200/tcp" -func StartOpenSearchTestContainer(ctx context.Context) (testcontainers.Container, error) { +func StartOpensearchTestContainer(ctx context.Context) (testcontainers.Container, error) { req := testcontainers.ContainerRequest{ Image: "opensearchproject/opensearch:2.11.0", ExposedPorts: []string{openSearchTestDefaultHttpPort, "9300/tcp"}, @@ -28,7 +28,7 @@ func StartOpenSearchTestContainer(ctx context.Context) (testcontainers.Container "discovery.type": "single-node", }, } - openSearchContainer, err := testcontainers.GenericContainer(ctx, testcontainers.GenericContainerRequest{ + opensearchContainer, err := testcontainers.GenericContainer(ctx, testcontainers.GenericContainerRequest{ ContainerRequest: req, Started: true, }) @@ -36,13 +36,13 @@ func StartOpenSearchTestContainer(ctx context.Context) (testcontainers.Container log.Debug().Msgf("failed to create container: %s", err.Error()) } - host, _ := openSearchContainer.Host(ctx) - localPort, _ := openSearchContainer.MappedPort(ctx, openSearchTestDefaultHttpPort) + host, _ := opensearchContainer.Host(ctx) + localPort, _ := opensearchContainer.MappedPort(ctx, openSearchTestDefaultHttpPort) _ = os.Setenv("ELASTIC_HOST", host) _ = os.Setenv("ELASTIC_API_PORT", localPort.Port()) - return openSearchContainer, nil + return opensearchContainer, nil } func createWaitStrategyFor() wait.Strategy { From 4257fa61e810b8b83ad0648c74121e3d694c021f Mon Sep 17 00:00:00 2001 From: Tim Steffens Date: Thu, 7 Dec 2023 22:53:27 +0100 Subject: [PATCH 09/19] pass config explicitely --- .../open_search_client/opensearchProjectClient.go | 7 +------ 1 file changed, 1 insertion(+), 6 deletions(-) diff --git a/pkg/openSearch/open_search_client/opensearchProjectClient.go b/pkg/openSearch/open_search_client/opensearchProjectClient.go index 1243be3..1e9f5d2 100644 --- a/pkg/openSearch/open_search_client/opensearchProjectClient.go +++ b/pkg/openSearch/open_search_client/opensearchProjectClient.go @@ -16,12 +16,7 @@ import ( "github.com/opensearch-project/opensearch-go/opensearchapi" ) -func NewOpensearchProjectClient(ctx context.Context) (*opensearch.Client, error) { - config, confErr := config.ReadSearchEngineConfig() - if confErr != nil { - return nil, confErr - } - +func NewOpensearchProjectClient(config config.SearchEngineConfig, ctx context.Context) (*opensearch.Client, error) { protocol := "http" if config.Https { protocol = "https" From 34e7b793194b18911aa6760c3a709285cb5513dd Mon Sep 17 00:00:00 2001 From: Tim Steffens Date: Thu, 7 Dec 2023 22:54:49 +0100 Subject: [PATCH 10/19] move and rename --- pkg/{postgres => }/dbcrypt/config/config.go | 0 pkg/{postgres/dbcrypt/dbcryptutil.go => dbcrypt/dbcrypt.go} | 3 +-- pkg/{postgres => }/dbcrypt/dbcrypt_test.go | 0 3 files changed, 1 insertion(+), 2 deletions(-) rename pkg/{postgres => }/dbcrypt/config/config.go (100%) rename pkg/{postgres/dbcrypt/dbcryptutil.go => dbcrypt/dbcrypt.go} (98%) rename pkg/{postgres => }/dbcrypt/dbcrypt_test.go (100%) diff --git a/pkg/postgres/dbcrypt/config/config.go b/pkg/dbcrypt/config/config.go similarity index 100% rename from pkg/postgres/dbcrypt/config/config.go rename to pkg/dbcrypt/config/config.go diff --git a/pkg/postgres/dbcrypt/dbcryptutil.go b/pkg/dbcrypt/dbcrypt.go similarity index 98% rename from pkg/postgres/dbcrypt/dbcryptutil.go rename to pkg/dbcrypt/dbcrypt.go index 29e4b5d..91de513 100644 --- a/pkg/postgres/dbcrypt/dbcryptutil.go +++ b/pkg/dbcrypt/dbcrypt.go @@ -6,10 +6,9 @@ import ( "crypto/rand" "encoding/hex" "fmt" + "github.com/greenbone/opensight-golang-libraries/pkg/dbcrypt/config" "io" "reflect" - - "github.com/greenbone/opensight-golang-libraries/pkg/postgres/dbcrypt/config" ) type DBCrypt[T any] struct { diff --git a/pkg/postgres/dbcrypt/dbcrypt_test.go b/pkg/dbcrypt/dbcrypt_test.go similarity index 100% rename from pkg/postgres/dbcrypt/dbcrypt_test.go rename to pkg/dbcrypt/dbcrypt_test.go From bd0f2ba17478a6924181d1bea9c64df92917db0d Mon Sep 17 00:00:00 2001 From: Tim Steffens Date: Thu, 7 Dec 2023 22:56:08 +0100 Subject: [PATCH 11/19] remove code that was commented out --- pkg/dbcrypt/dbcrypt.go | 60 ------------------------------------------ 1 file changed, 60 deletions(-) diff --git a/pkg/dbcrypt/dbcrypt.go b/pkg/dbcrypt/dbcrypt.go index 91de513..ea3489a 100644 --- a/pkg/dbcrypt/dbcrypt.go +++ b/pkg/dbcrypt/dbcrypt.go @@ -53,12 +53,6 @@ func (d *DBCrypt[T]) DecryptStruct(data *T) error { field := value.Field(i) fieldType := valueType.Field(i) if encrypt, ok := fieldType.Tag.Lookup("encrypt"); ok && encrypt == "true" { - /* - ciphertext, err := hex.DecodeString(field.String()[4:]) - if err != nil { - return err - }*/ - plaintext, err := d.decrypt(field.String()) if err != nil { return err @@ -131,57 +125,3 @@ func (d *DBCrypt[T]) decrypt(encrypted string) (string, error) { return string(plaintext), nil } - -/* -// This function encrypts a value using AES encryption with the derived key -func (d *DBCrypt[T]) encryptValue(value string) ([]byte, error) { - key, genKeyErr := d.deriveEncryptionKey() - if genKeyErr != nil { - return nil, genKeyErr - } - block, err := aes.NewCipher(key) - if err != nil { - return nil, err - } - gcm, err := cipher.NewGCM(block) - if err != nil { - return nil, err - } - nonce := make([]byte, gcm.NonceSize()) - if _, err := rand.Read(nonce); err != nil { - return nil, err - } - ciphertext := gcm.Seal(nonce, nonce, []byte(value), nil) - return ciphertext, nil -} - -// This function decrypts a value using AES decryption with the derived key -func (d *DBCrypt[T]) decryptValue(ciphertext []byte) (string, error) { - key, genKeyErr := d.deriveEncryptionKey() - if genKeyErr != nil { - return "", genKeyErr - } - block, err := aes.NewCipher(key) - if err != nil { - return "", err - } - gcm, err := cipher.NewGCM(block) - if err != nil { - return "", err - } - nonceSize := gcm.NonceSize() - if len(ciphertext) < nonceSize { - return "", errors.New("ciphertext too short") - } - nonce, ciphertext := ciphertext[:nonceSize], ciphertext[nonceSize:] - plaintext, err := gcm.Open(nil, nonce, ciphertext, nil) - if err != nil { - return "", err - } - return string(plaintext), nil -} - -*/ - -// TODO test without DB -// TODO Test DB beforeUpdate ... From aaecc534c8a1c788392b40307dd3fdb4afe94a9c Mon Sep 17 00:00:00 2001 From: Greenbone Bot Date: Fri, 8 Dec 2023 09:56:28 +0000 Subject: [PATCH 12/19] Automatic release to 0.0.3 --- version.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/version.go b/version.go index 74779af..8b3b868 100644 --- a/version.go +++ b/version.go @@ -10,4 +10,4 @@ package opensight_golang_libraries // THIS IS AN AUTOGENERATED FILE. DO NOT TOUCH! -var Version = "0.0.3-alpha2-dev1" +var Version = "0.0.3" From 05d8a8ddf27196925686fb57bfe652a87ee8c76c Mon Sep 17 00:00:00 2001 From: Greenbone Bot Date: Fri, 8 Dec 2023 09:56:30 +0000 Subject: [PATCH 13/19] Automatic adjustments after release * Update to version 0.0.4-dev1 --- version.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/version.go b/version.go index 8b3b868..1495379 100644 --- a/version.go +++ b/version.go @@ -10,4 +10,4 @@ package opensight_golang_libraries // THIS IS AN AUTOGENERATED FILE. DO NOT TOUCH! -var Version = "0.0.3" +var Version = "0.0.4-dev1" From ac7da6b562a8329622478460ce03a12b222eadbf Mon Sep 17 00:00:00 2001 From: Roxana Meixner Date: Fri, 8 Dec 2023 11:49:50 +0100 Subject: [PATCH 14/19] change: enhance naming, rename simpleClient struct to client, rename struct field and method parameter client to opensearchProjectClient --- pkg/openSearch/open_search_client/client.go | 44 +++++++++---------- .../open_search_client/updateQueue.go | 26 +++++------ 2 files changed, 35 insertions(+), 35 deletions(-) diff --git a/pkg/openSearch/open_search_client/client.go b/pkg/openSearch/open_search_client/client.go index 5accf49..628214c 100644 --- a/pkg/openSearch/open_search_client/client.go +++ b/pkg/openSearch/open_search_client/client.go @@ -19,24 +19,24 @@ import ( "github.com/rs/zerolog/log" ) -type simpleClient struct { - client *opensearch.Client - queue *requestQueue +type client struct { + opensearchProjectClient *opensearch.Client + queue *requestQueue } -func NewSimpleClient(client *opensearch.Client, updateMaxRetries int, updateRetryDelay time.Duration) *simpleClient { - c := &simpleClient{ - client: client, +func NewClient(opensearchProjectClient *opensearch.Client, updateMaxRetries int, updateRetryDelay time.Duration) *client { + c := &client{ + opensearchProjectClient: opensearchProjectClient, } - c.queue = NewRequestQueue(client, updateMaxRetries, updateRetryDelay) + c.queue = NewRequestQueue(opensearchProjectClient, updateMaxRetries, updateRetryDelay) return c } -func (c *simpleClient) Search(indexName string, requestBody []byte) (responseBody []byte, err error) { +func (c *client) Search(indexName string, requestBody []byte) (responseBody []byte, err error) { log.Debug().Msgf("search requestBody: %s", string(requestBody)) - searchResponse, err := c.client.Search( - c.client.Search.WithIndex(indexName), - c.client.Search.WithBody(bytes.NewReader(requestBody)), + searchResponse, err := c.opensearchProjectClient.Search( + c.opensearchProjectClient.Search.WithIndex(indexName), + c.opensearchProjectClient.Search.WithBody(bytes.NewReader(requestBody)), ) if err != nil { return nil, errors.WithStack(err) @@ -56,24 +56,24 @@ func (c *simpleClient) Search(indexName string, requestBody []byte) (responseBod return result, nil } -func (c *simpleClient) Update(indexName string, requestBody []byte) (responseBody []byte, err error) { +func (c *client) Update(indexName string, requestBody []byte) (responseBody []byte, err error) { return c.queue.Update(indexName, requestBody) } -func (c *simpleClient) AsyncDeleteByQuery(indexName string, requestBody []byte) error { +func (c *client) AsyncDeleteByQuery(indexName string, requestBody []byte) error { return c.deleteByQuery(indexName, requestBody, true) } -func (c *simpleClient) DeleteByQuery(indexName string, requestBody []byte) error { +func (c *client) DeleteByQuery(indexName string, requestBody []byte) error { return c.deleteByQuery(indexName, requestBody, false) } // deleteByQuery deletes documents by a query -func (c *simpleClient) deleteByQuery(indexName string, requestBody []byte, isAsync bool) error { - deleteResponse, err := c.client.DeleteByQuery( +func (c *client) deleteByQuery(indexName string, requestBody []byte, isAsync bool) error { + deleteResponse, err := c.opensearchProjectClient.DeleteByQuery( []string{indexName}, bytes.NewReader(requestBody), - c.client.DeleteByQuery.WithWaitForCompletion(!isAsync), + c.opensearchProjectClient.DeleteByQuery.WithWaitForCompletion(!isAsync), ) if err != nil { return errors.WithStack(err) @@ -87,7 +87,7 @@ func (c *simpleClient) deleteByQuery(indexName string, requestBody []byte, isAsy return GetResponseError(deleteResponse.StatusCode, resultString, indexName) } -func (c *simpleClient) SaveToIndex(indexName string, documents [][]byte) error { +func (c *client) SaveToIndex(indexName string, documents [][]byte) error { if len(documents) == 0 { return nil } @@ -101,10 +101,10 @@ func (c *simpleClient) SaveToIndex(indexName string, documents [][]byte) error { body.WriteString(string(document) + "\n") } - insertResponse, err := c.client.Bulk( + insertResponse, err := c.opensearchProjectClient.Bulk( strings.NewReader(body.String()), - c.client.Bulk.WithIndex(indexName), - c.client.Bulk.WithRefresh("true"), + c.opensearchProjectClient.Bulk.WithIndex(indexName), + c.opensearchProjectClient.Bulk.WithRefresh("true"), ) if err != nil { return errors.WithStack(err) @@ -151,6 +151,6 @@ func GetResponseError(statusCode int, responseString []byte, indexName string) e } } -func (c *simpleClient) Close() { +func (c *client) Close() { c.queue.Stop() } diff --git a/pkg/openSearch/open_search_client/updateQueue.go b/pkg/openSearch/open_search_client/updateQueue.go index 819103d..ba2b3e3 100644 --- a/pkg/openSearch/open_search_client/updateQueue.go +++ b/pkg/openSearch/open_search_client/updateQueue.go @@ -26,21 +26,21 @@ type Request struct { } type requestQueue struct { - client *opensearch.Client - queue chan *Request - stop chan bool - wg sync.WaitGroup - updateMaxRetries int - updateRetryDelay time.Duration + opensearchProjectClient *opensearch.Client + queue chan *Request + stop chan bool + wg sync.WaitGroup + updateMaxRetries int + updateRetryDelay time.Duration } -func NewRequestQueue(client *opensearch.Client, updateMaxRetries int, updateRetryDelay time.Duration) *requestQueue { +func NewRequestQueue(opensearchProjectClient *opensearch.Client, updateMaxRetries int, updateRetryDelay time.Duration) *requestQueue { rQueue := &requestQueue{ - client: client, - queue: make(chan *Request, 10), - stop: make(chan bool), - updateMaxRetries: updateMaxRetries, - updateRetryDelay: updateRetryDelay, + opensearchProjectClient: opensearchProjectClient, + queue: make(chan *Request, 10), + stop: make(chan bool), + updateMaxRetries: updateMaxRetries, + updateRetryDelay: updateRetryDelay, } rQueue.start() return rQueue @@ -120,7 +120,7 @@ func (q *requestQueue) update(indexName string, requestBody []byte) ([]byte, err Pretty: true, } - updateResponse, err = req.Do(context.Background(), q.client) + updateResponse, err = req.Do(context.Background(), q.opensearchProjectClient) if err != nil { log.Info().Err(err).Msgf("Attempt %d: Error in req.Do", i+1) time.Sleep(q.updateRetryDelay) From 25bd21ba6e2afb273d1ac0ef301fddc518455773 Mon Sep 17 00:00:00 2001 From: Roxana Meixner Date: Fri, 8 Dec 2023 12:19:23 +0100 Subject: [PATCH 15/19] Change: refactoring of SaveToIndex method into serialization and update steps Changes by timsteffens --- pkg/openSearch/open_search_client/client.go | 15 +++++++++++---- 1 file changed, 11 insertions(+), 4 deletions(-) diff --git a/pkg/openSearch/open_search_client/client.go b/pkg/openSearch/open_search_client/client.go index 628214c..8a20ed8 100644 --- a/pkg/openSearch/open_search_client/client.go +++ b/pkg/openSearch/open_search_client/client.go @@ -87,9 +87,9 @@ func (c *client) deleteByQuery(indexName string, requestBody []byte, isAsync boo return GetResponseError(deleteResponse.StatusCode, resultString, indexName) } -func (c *client) SaveToIndex(indexName string, documents [][]byte) error { +func SerializeDocumentsForBulkUpdate[T Identifiable](indexName string, documents []T) ([]byte, error) { if len(documents) == 0 { - return nil + return nil, fmt.Errorf("no documents to serialize") } var body strings.Builder @@ -98,11 +98,18 @@ func (c *client) SaveToIndex(indexName string, documents [][]byte) error { for _, document := range documents { body.WriteString(fmt.Sprintf(`{"index": { "_index" : "%s"}}`, indexName) + "\n") - body.WriteString(string(document) + "\n") + documentJson, err := jsoniter.Marshal(document) + if err != nil { + return nil, errors.WithStack(err) + } + body.WriteString(string(documentJson) + "\n") } + return []byte(body.String()), nil +} +func (c *client) BulkUpdate(indexName string, requestBody []byte) error { insertResponse, err := c.opensearchProjectClient.Bulk( - strings.NewReader(body.String()), + bytes.NewReader(requestBody), c.opensearchProjectClient.Bulk.WithIndex(indexName), c.opensearchProjectClient.Bulk.WithRefresh("true"), ) From 818e634953296e84182c8e9b0111dfb0ab7422f7 Mon Sep 17 00:00:00 2001 From: Roxana Meixner Date: Fri, 8 Dec 2023 16:23:40 +0100 Subject: [PATCH 16/19] Change: [WIP] cleanup and simplify usage of opensight libraries, adapt and enhance unit tests Changes by timsteffens --- pkg/openSearch/open_search_client/config/config.go | 6 +++--- .../open_search_client/opensearchProjectClient.go | 2 +- .../open_search_client/opensearchTestContainer.go | 13 ++++++++----- 3 files changed, 12 insertions(+), 9 deletions(-) diff --git a/pkg/openSearch/open_search_client/config/config.go b/pkg/openSearch/open_search_client/config/config.go index bf3f3cd..334e036 100644 --- a/pkg/openSearch/open_search_client/config/config.go +++ b/pkg/openSearch/open_search_client/config/config.go @@ -9,14 +9,14 @@ import ( "github.com/rs/zerolog/log" ) -type SearchEngineConfig struct { +type OpensearchClientConfig struct { Host string `validate:"required" viperEnv:"ELASTIC_HOST"` Port int `validate:"required,min=1,max=65535" viperEnv:"ELASTIC_API_PORT"` Https bool `viperEnv:"ELASTIC_HTTPS"` } -func ReadSearchEngineConfig() (SearchEngineConfig, error) { - config := &SearchEngineConfig{} +func ReadOpensearchClientConfig() (OpensearchClientConfig, error) { + config := &OpensearchClientConfig{} _, err := configReader.ReadEnvVarsIntoStruct(config) if err != nil { return *config, err diff --git a/pkg/openSearch/open_search_client/opensearchProjectClient.go b/pkg/openSearch/open_search_client/opensearchProjectClient.go index 1e9f5d2..5314155 100644 --- a/pkg/openSearch/open_search_client/opensearchProjectClient.go +++ b/pkg/openSearch/open_search_client/opensearchProjectClient.go @@ -16,7 +16,7 @@ import ( "github.com/opensearch-project/opensearch-go/opensearchapi" ) -func NewOpensearchProjectClient(config config.SearchEngineConfig, ctx context.Context) (*opensearch.Client, error) { +func NewOpensearchProjectClient(ctx context.Context, config config.OpensearchClientConfig) (*opensearch.Client, error) { protocol := "http" if config.Https { protocol = "https" diff --git a/pkg/openSearch/open_search_client/opensearchTestContainer.go b/pkg/openSearch/open_search_client/opensearchTestContainer.go index f961ae8..6c4df6c 100644 --- a/pkg/openSearch/open_search_client/opensearchTestContainer.go +++ b/pkg/openSearch/open_search_client/opensearchTestContainer.go @@ -2,8 +2,8 @@ package open_search_client import ( "context" + "github.com/greenbone/opensight-golang-libraries/pkg/openSearch/open_search_client/config" "net/http" - "os" "time" "github.com/rs/zerolog/log" @@ -18,7 +18,7 @@ type OpensearchTestContainer struct { const openSearchTestDefaultHttpPort = "9200/tcp" -func StartOpensearchTestContainer(ctx context.Context) (testcontainers.Container, error) { +func StartOpensearchTestContainer(ctx context.Context) (testcontainers.Container, config.OpensearchClientConfig, error) { req := testcontainers.ContainerRequest{ Image: "opensearchproject/opensearch:2.11.0", ExposedPorts: []string{openSearchTestDefaultHttpPort, "9300/tcp"}, @@ -39,10 +39,13 @@ func StartOpensearchTestContainer(ctx context.Context) (testcontainers.Container host, _ := opensearchContainer.Host(ctx) localPort, _ := opensearchContainer.MappedPort(ctx, openSearchTestDefaultHttpPort) - _ = os.Setenv("ELASTIC_HOST", host) - _ = os.Setenv("ELASTIC_API_PORT", localPort.Port()) + conf := config.OpensearchClientConfig{ + Host: host, + Port: localPort.Int(), + Https: false, + } - return opensearchContainer, nil + return opensearchContainer, conf, nil } func createWaitStrategyFor() wait.Strategy { From 72e4f5132b972b8b4c0fb9f85f4201c00219826d Mon Sep 17 00:00:00 2001 From: Tim Steffens Date: Mon, 11 Dec 2023 08:31:00 +0100 Subject: [PATCH 17/19] Update pkg/configReader/README.md Co-authored-by: Roxana Meixner <146721250+larox11@users.noreply.github.com> --- pkg/configReader/README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/pkg/configReader/README.md b/pkg/configReader/README.md index 3a82ca0..79229d3 100644 --- a/pkg/configReader/README.md +++ b/pkg/configReader/README.md @@ -54,7 +54,7 @@ This project is maintained by [Greenbone AG][Greenbone AG] ## Contributing Your contributions are highly appreciated. Please -[create a pull request](https://github.com/greenbone/asset-management-backend/pulls) +[create a pull request](https://github.com/greenbone/opensight-golang-libraries/pulls) on GitHub. Bigger changes need to be discussed with the development team via the [issues section at GitHub](https://github.com/greenbone/asset-management-backend/issues) first. From 2ef3190498bad70ea45e382dc7a6ae361dfc1d35 Mon Sep 17 00:00:00 2001 From: Tim Steffens Date: Mon, 11 Dec 2023 08:31:11 +0100 Subject: [PATCH 18/19] Update pkg/configReader/README.md Co-authored-by: Roxana Meixner <146721250+larox11@users.noreply.github.com> --- pkg/configReader/README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/pkg/configReader/README.md b/pkg/configReader/README.md index 79229d3..f4f5c8f 100644 --- a/pkg/configReader/README.md +++ b/pkg/configReader/README.md @@ -56,7 +56,7 @@ This project is maintained by [Greenbone AG][Greenbone AG] Your contributions are highly appreciated. Please [create a pull request](https://github.com/greenbone/opensight-golang-libraries/pulls) on GitHub. Bigger changes need to be discussed with the development team via the -[issues section at GitHub](https://github.com/greenbone/asset-management-backend/issues) +[issues section at GitHub](https://github.com/greenbone/opensight-golang-libraries/issues) first. ## License From a45e95f12477b3507f7049c5a12817ae53661420 Mon Sep 17 00:00:00 2001 From: Tim Steffens Date: Mon, 11 Dec 2023 08:32:27 +0100 Subject: [PATCH 19/19] Update README.md --- pkg/configReader/README.md | 3 --- 1 file changed, 3 deletions(-) diff --git a/pkg/configReader/README.md b/pkg/configReader/README.md index f4f5c8f..ac07499 100644 --- a/pkg/configReader/README.md +++ b/pkg/configReader/README.md @@ -66,6 +66,3 @@ Copyright (C) 2022-2023 [Greenbone AG][Greenbone AG] Licensed under the [GNU General Public License v3.0 or later](LICENSE). [Greenbone AG]: https://www.greenbone.net/ -[poetry]: https://python-poetry.org/ -[pip]: https://pip.pypa.io/ -[autohooks]: https://github.com/greenbone/autohooks \ No newline at end of file