From 049642e894f93d8eda1ff533e79ded6feaaf4b49 Mon Sep 17 00:00:00 2001 From: Wenkai Yin Date: Thu, 2 Nov 2017 18:22:06 +0800 Subject: [PATCH] Implement filter chain --- .../source/default_filter_chain.go | 57 ++++++++++++++ .../source/default_filter_chain_test.go | 75 +++++++++++++++++++ 2 files changed, 132 insertions(+) create mode 100644 src/replication/source/default_filter_chain.go create mode 100644 src/replication/source/default_filter_chain_test.go diff --git a/src/replication/source/default_filter_chain.go b/src/replication/source/default_filter_chain.go new file mode 100644 index 000000000..1acd29bf8 --- /dev/null +++ b/src/replication/source/default_filter_chain.go @@ -0,0 +1,57 @@ +// Copyright (c) 2017 VMware, Inc. All Rights Reserved. +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +package source + +import ( + "github.com/vmware/harbor/src/replication/models" +) + +// DefaultFilterChain provides a default implement for interface FilterChain +type DefaultFilterChain struct { + filters []Filter +} + +// NewDefaultFilterChain returns an instance of DefaultFilterChain +func NewDefaultFilterChain(filters []Filter) *DefaultFilterChain { + return &DefaultFilterChain{ + filters: filters, + } +} + +// Build nil implement now +func (d *DefaultFilterChain) Build(filters []Filter) error { + return nil +} + +// Filters returns the filter list +func (d *DefaultFilterChain) Filters() []Filter { + return d.filters +} + +// DoFilter does the filter works for filterItems +func (d *DefaultFilterChain) DoFilter(filterItems []models.FilterItem) []models.FilterItem { + if len(filterItems) == 0 { + return []models.FilterItem{} + } + + for _, filter := range d.filters { + convertor := filter.GetConvertor() + if convertor != nil { + filterItems = convertor.Convert(filterItems) + } + filterItems = filter.DoFilter(filterItems) + } + return filterItems +} diff --git a/src/replication/source/default_filter_chain_test.go b/src/replication/source/default_filter_chain_test.go new file mode 100644 index 000000000..ee1eec79a --- /dev/null +++ b/src/replication/source/default_filter_chain_test.go @@ -0,0 +1,75 @@ +// Copyright (c) 2017 VMware, Inc. All Rights Reserved. +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +package source + +import ( + "testing" + + "github.com/stretchr/testify/assert" + "github.com/stretchr/testify/require" + "github.com/vmware/harbor/src/replication" + "github.com/vmware/harbor/src/replication/models" +) + +func TestBuild(t *testing.T) { + chain := NewDefaultFilterChain(nil) + require.Nil(t, chain.Build(nil)) +} + +func TestFilters(t *testing.T) { + filters := []Filter{NewPatternFilter("project", "*")} + chain := NewDefaultFilterChain(filters) + assert.EqualValues(t, filters, chain.Filters()) +} + +func TestDoFilter(t *testing.T) { + projectFilter := NewPatternFilter(replication.FilterItemKindProject, "library*") + repositoryFilter := NewPatternFilter(replication.FilterItemKindRepository, + "library/ubuntu*", &fakeRepositoryConvertor{}) + filters := []Filter{projectFilter, repositoryFilter} + + items := []models.FilterItem{ + models.FilterItem{ + Kind: replication.FilterItemKindProject, + Value: "library", + }, + models.FilterItem{ + Kind: replication.FilterItemKindProject, + Value: "test", + }, + } + chain := NewDefaultFilterChain(filters) + items = chain.DoFilter(items) + assert.EqualValues(t, []models.FilterItem{ + models.FilterItem{ + Kind: replication.FilterItemKindRepository, + Value: "library/ubuntu", + }, + }, items) + +} + +type fakeRepositoryConvertor struct{} + +func (f *fakeRepositoryConvertor) Convert(items []models.FilterItem) []models.FilterItem { + result := []models.FilterItem{} + for _, item := range items { + result = append(result, models.FilterItem{ + Kind: replication.FilterItemKindRepository, + Value: item.Value + "/ubuntu", + }) + } + return result +}