1//  Copyright (c) 2014 Couchbase, Inc.
2//
3// Licensed under the Apache License, Version 2.0 (the "License");
4// you may not use this file except in compliance with the License.
5// You may obtain a copy of the License at
6//
7// 		http://www.apache.org/licenses/LICENSE-2.0
8//
9// Unless required by applicable law or agreed to in writing, software
10// distributed under the License is distributed on an "AS IS" BASIS,
11// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12// See the License for the specific language governing permissions and
13// limitations under the License.
14
15package http
16
17import (
18	"fmt"
19	"sync"
20
21	"github.com/blevesearch/bleve"
22)
23
24var indexNameMapping map[string]bleve.Index
25var indexNameMappingLock sync.RWMutex
26
27func RegisterIndexName(name string, idx bleve.Index) {
28	indexNameMappingLock.Lock()
29	defer indexNameMappingLock.Unlock()
30
31	if indexNameMapping == nil {
32		indexNameMapping = make(map[string]bleve.Index)
33	}
34	indexNameMapping[name] = idx
35}
36
37func UnregisterIndexByName(name string) bleve.Index {
38	indexNameMappingLock.Lock()
39	defer indexNameMappingLock.Unlock()
40
41	if indexNameMapping == nil {
42		return nil
43	}
44	rv := indexNameMapping[name]
45	if rv != nil {
46		delete(indexNameMapping, name)
47	}
48	return rv
49}
50
51func IndexByName(name string) bleve.Index {
52	indexNameMappingLock.RLock()
53	defer indexNameMappingLock.RUnlock()
54
55	return indexNameMapping[name]
56}
57
58func IndexNames() []string {
59	indexNameMappingLock.RLock()
60	defer indexNameMappingLock.RUnlock()
61
62	rv := make([]string, len(indexNameMapping))
63	count := 0
64	for k := range indexNameMapping {
65		rv[count] = k
66		count++
67	}
68	return rv
69}
70
71func UpdateAlias(alias string, add, remove []string) error {
72	indexNameMappingLock.Lock()
73	defer indexNameMappingLock.Unlock()
74
75	index, exists := indexNameMapping[alias]
76	if !exists {
77		// new alias
78		if len(remove) > 0 {
79			return fmt.Errorf("cannot remove indexes from a new alias")
80		}
81		indexes := make([]bleve.Index, len(add))
82		for i, addIndexName := range add {
83			addIndex, indexExists := indexNameMapping[addIndexName]
84			if !indexExists {
85				return fmt.Errorf("index named '%s' does not exist", addIndexName)
86			}
87			indexes[i] = addIndex
88		}
89		indexAlias := bleve.NewIndexAlias(indexes...)
90		indexNameMapping[alias] = indexAlias
91	} else {
92		// something with this name already exists
93		indexAlias, isAlias := index.(bleve.IndexAlias)
94		if !isAlias {
95			return fmt.Errorf("'%s' is not an alias", alias)
96		}
97		// build list of add indexes
98		addIndexes := make([]bleve.Index, len(add))
99		for i, addIndexName := range add {
100			addIndex, indexExists := indexNameMapping[addIndexName]
101			if !indexExists {
102				return fmt.Errorf("index named '%s' does not exist", addIndexName)
103			}
104			addIndexes[i] = addIndex
105		}
106		// build list of remove indexes
107		removeIndexes := make([]bleve.Index, len(remove))
108		for i, removeIndexName := range remove {
109			removeIndex, indexExists := indexNameMapping[removeIndexName]
110			if !indexExists {
111				return fmt.Errorf("index named '%s' does not exist", removeIndexName)
112			}
113			removeIndexes[i] = removeIndex
114		}
115		indexAlias.Swap(addIndexes, removeIndexes)
116	}
117	return nil
118}
119