1 package org.apache.archiva.metadata.repository.cassandra;
4 * Licensed to the Apache Software Foundation (ASF) under one
5 * or more contributor license agreements. See the NOTICE file
6 * distributed with this work for additional information
7 * regarding copyright ownership. The ASF licenses this file
8 * to you under the Apache License, Version 2.0 (the
9 * "License"); you may not use this file except in compliance
10 * with the License. You may obtain a copy of the License at
12 * http://www.apache.org/licenses/LICENSE-2.0
14 * Unless required by applicable law or agreed to in writing,
15 * software distributed under the License is distributed on an
16 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
17 * KIND, either express or implied. See the License for the
18 * specific language governing permissions and limitations
22 import static org.apache.archiva.metadata.repository.cassandra.model.ColumnNames.*;
24 import me.prettyprint.cassandra.model.BasicColumnDefinition;
25 import me.prettyprint.cassandra.model.ConfigurableConsistencyLevel;
26 import me.prettyprint.cassandra.serializers.StringSerializer;
27 import me.prettyprint.cassandra.service.CassandraHostConfigurator;
28 import me.prettyprint.cassandra.service.ThriftKsDef;
29 import me.prettyprint.hector.api.Cluster;
30 import me.prettyprint.hector.api.HConsistencyLevel;
31 import me.prettyprint.hector.api.Keyspace;
32 import me.prettyprint.hector.api.ddl.ColumnFamilyDefinition;
33 import me.prettyprint.hector.api.ddl.ColumnIndexType;
34 import me.prettyprint.hector.api.ddl.ComparatorType;
35 import me.prettyprint.hector.api.factory.HFactory;
36 import org.apache.archiva.metadata.repository.RepositorySessionFactoryBean;
37 import org.apache.commons.lang.StringUtils;
38 import org.slf4j.Logger;
39 import org.slf4j.LoggerFactory;
40 import org.springframework.beans.factory.annotation.Value;
41 import org.springframework.context.ApplicationContext;
42 import org.springframework.stereotype.Service;
44 import javax.annotation.PostConstruct;
45 import javax.annotation.PreDestroy;
46 import javax.inject.Inject;
47 import java.util.ArrayList;
48 import java.util.List;
51 * FIXME make all configuration not hardcoded :-)
53 * @author Olivier Lamy
56 @Service("archivaEntityManagerFactory#cassandra")
57 public class DefaultCassandraArchivaManager
58 implements CassandraArchivaManager
61 private Logger logger = LoggerFactory.getLogger( getClass() );
64 private ApplicationContext applicationContext;
66 private static final String CLUSTER_NAME = "archiva";
68 private static final String KEYSPACE_NAME = "ArchivaKeySpace";
70 private boolean started;
72 private Cluster cluster;
74 private Keyspace keyspace;
77 private String repositoryFamilyName = "repository";
79 private String namespaceFamilyName = "namespace";
81 private String projectFamilyName = PROJECT.toString();
83 private String projectVersionMetadataFamilyName = "projectversionmetadata";
85 private String artifactMetadataFamilyName = "artifactmetadata";
87 private String metadataFacetFamilyName = "metadatafacet";
89 private String mailingListFamilyName = "mailinglist";
91 private String licenseFamilyName = "license";
93 private String dependencyFamilyName = "dependency";
95 @Value("${cassandra.host}")
96 private String cassandraHost;
98 @Value("${cassandra.port}")
99 private String cassandraPort;
101 @Value("${cassandra.maxActive}")
102 private int maxActive;
104 @Value("${cassandra.readConsistencyLevel}")
105 private String readConsistencyLevel;
107 @Value("${cassandra.writeConsistencyLevel}")
108 private String writeConsistencyLevel;
110 @Value("${cassandra.replicationFactor}")
111 private int replicationFactor;
113 @Value("${cassandra.keyspace.name}")
114 private String keyspaceName;
116 @Value("${cassandra.cluster.name}")
117 private String clusterName;
120 private RepositorySessionFactoryBean repositorySessionFactoryBean;
123 public void initialize()
125 // skip initialisation if not cassandra
126 if ( !StringUtils.equals( repositorySessionFactoryBean.getId(), "cassandra" ) )
130 final CassandraHostConfigurator configurator =
131 new CassandraHostConfigurator( cassandraHost + ":" + cassandraPort );
132 configurator.setMaxActive( maxActive );
133 //configurator.setCassandraThriftSocketTimeout( );
135 cluster = HFactory.getOrCreateCluster( clusterName, configurator );
137 final ConfigurableConsistencyLevel consistencyLevelPolicy = new ConfigurableConsistencyLevel();
138 consistencyLevelPolicy.setDefaultReadConsistencyLevel( HConsistencyLevel.valueOf( readConsistencyLevel ) );
139 consistencyLevelPolicy.setDefaultWriteConsistencyLevel( HConsistencyLevel.valueOf( writeConsistencyLevel ) );
140 keyspace = HFactory.createKeyspace( keyspaceName, cluster, consistencyLevelPolicy );
142 List<ColumnFamilyDefinition> cfds = new ArrayList<>();
147 final ColumnFamilyDefinition namespace =
148 HFactory.createColumnFamilyDefinition( keyspace.getKeyspaceName(), //
149 getNamespaceFamilyName(), //
150 ComparatorType.UTF8TYPE );
151 cfds.add( namespace );
153 // creating indexes for cql query
155 BasicColumnDefinition nameColumn = new BasicColumnDefinition();
156 nameColumn.setName( StringSerializer.get().toByteBuffer( NAME.toString() ) );
157 nameColumn.setIndexName( NAME.toString() );
158 nameColumn.setIndexType( ColumnIndexType.KEYS );
159 nameColumn.setValidationClass( ComparatorType.UTF8TYPE.getClassName() );
160 namespace.addColumnDefinition( nameColumn );
162 BasicColumnDefinition repositoryIdColumn = new BasicColumnDefinition();
163 repositoryIdColumn.setName( StringSerializer.get().toByteBuffer( REPOSITORY_NAME.toString() ) );
164 repositoryIdColumn.setIndexName( REPOSITORY_NAME.toString() );
165 repositoryIdColumn.setIndexType( ColumnIndexType.KEYS );
166 repositoryIdColumn.setValidationClass( ComparatorType.UTF8TYPE.getClassName() );
167 namespace.addColumnDefinition( repositoryIdColumn );
172 final ColumnFamilyDefinition repository =
173 HFactory.createColumnFamilyDefinition( keyspace.getKeyspaceName(), //
174 getRepositoryFamilyName(), //
175 ComparatorType.UTF8TYPE );
177 cfds.add( repository );
179 BasicColumnDefinition nameColumn = new BasicColumnDefinition();
180 nameColumn.setName( StringSerializer.get().toByteBuffer( REPOSITORY_NAME.toString() ) );
181 nameColumn.setIndexName( REPOSITORY_NAME.toString() );
182 nameColumn.setIndexType( ColumnIndexType.KEYS );
183 nameColumn.setValidationClass( ComparatorType.UTF8TYPE.getClassName() );
184 repository.addColumnDefinition( nameColumn );
190 final ColumnFamilyDefinition project = HFactory.createColumnFamilyDefinition( keyspace.getKeyspaceName(), //
191 getProjectFamilyName(), //
192 ComparatorType.UTF8TYPE );
195 // creating indexes for cql query
197 BasicColumnDefinition projectIdColumn = new BasicColumnDefinition();
198 projectIdColumn.setName( StringSerializer.get().toByteBuffer( PROJECT_ID.toString() ) );
199 projectIdColumn.setIndexName( PROJECT_ID.toString() );
200 projectIdColumn.setIndexType( ColumnIndexType.KEYS );
201 projectIdColumn.setValidationClass( ComparatorType.UTF8TYPE.getClassName() );
202 project.addColumnDefinition( projectIdColumn );
204 BasicColumnDefinition repositoryIdColumn = new BasicColumnDefinition();
205 repositoryIdColumn.setName( StringSerializer.get().toByteBuffer( REPOSITORY_NAME.toString() ) );
206 repositoryIdColumn.setIndexName( REPOSITORY_NAME.toString() );
207 repositoryIdColumn.setIndexType( ColumnIndexType.KEYS );
208 repositoryIdColumn.setValidationClass( ComparatorType.UTF8TYPE.getClassName() );
209 project.addColumnDefinition( repositoryIdColumn );
211 BasicColumnDefinition namespaceIdColumn = new BasicColumnDefinition();
212 namespaceIdColumn.setName( StringSerializer.get().toByteBuffer( NAMESPACE_ID.toString() ) );
213 namespaceIdColumn.setIndexName( NAMESPACE_ID.toString() );
214 namespaceIdColumn.setIndexType( ColumnIndexType.KEYS );
215 namespaceIdColumn.setValidationClass( ComparatorType.UTF8TYPE.getClassName() );
216 project.addColumnDefinition( namespaceIdColumn );
219 //projectversionmetadatamodel
222 final ColumnFamilyDefinition projectVersionMetadataModel =
223 HFactory.createColumnFamilyDefinition( keyspace.getKeyspaceName(), //
224 getProjectVersionMetadataFamilyName(), //
225 ComparatorType.UTF8TYPE );
226 cfds.add( projectVersionMetadataModel );
228 // creating indexes for cql query
230 BasicColumnDefinition namespaceIdColumn = new BasicColumnDefinition();
231 namespaceIdColumn.setName( StringSerializer.get().toByteBuffer( NAMESPACE_ID.toString() ) );
232 namespaceIdColumn.setIndexName( NAMESPACE_ID.toString() );
233 namespaceIdColumn.setIndexType( ColumnIndexType.KEYS );
234 namespaceIdColumn.setValidationClass( ComparatorType.UTF8TYPE.getClassName() );
235 projectVersionMetadataModel.addColumnDefinition( namespaceIdColumn );
237 BasicColumnDefinition repositoryNameColumn = new BasicColumnDefinition();
238 repositoryNameColumn.setName( StringSerializer.get().toByteBuffer( REPOSITORY_NAME.toString() ) );
239 repositoryNameColumn.setIndexName( REPOSITORY_NAME.toString() );
240 repositoryNameColumn.setIndexType( ColumnIndexType.KEYS );
241 repositoryNameColumn.setValidationClass( ComparatorType.UTF8TYPE.getClassName() );
242 projectVersionMetadataModel.addColumnDefinition( repositoryNameColumn );
244 BasicColumnDefinition idColumn = new BasicColumnDefinition();
245 idColumn.setName( StringSerializer.get().toByteBuffer( ID.toString() ) );
246 idColumn.setIndexName( ID.toString() );
247 idColumn.setIndexType( ColumnIndexType.KEYS );
248 idColumn.setValidationClass( ComparatorType.UTF8TYPE.getClassName() );
249 projectVersionMetadataModel.addColumnDefinition( idColumn );
251 BasicColumnDefinition projectIdColumn = new BasicColumnDefinition();
252 projectIdColumn.setName( StringSerializer.get().toByteBuffer( PROJECT_ID.toString() ) );
253 projectIdColumn.setIndexName( PROJECT_ID.toString() );
254 projectIdColumn.setIndexType( ColumnIndexType.KEYS );
255 projectIdColumn.setValidationClass( ComparatorType.UTF8TYPE.getClassName() );
256 projectVersionMetadataModel.addColumnDefinition( projectIdColumn );
260 // artifactmetadatamodel table
263 final ColumnFamilyDefinition artifactMetadataModel =
264 HFactory.createColumnFamilyDefinition( keyspace.getKeyspaceName(), //
265 getArtifactMetadataFamilyName(), //
266 ComparatorType.UTF8TYPE );
267 cfds.add( artifactMetadataModel );
269 // creating indexes for cql query
271 BasicColumnDefinition idColumn = new BasicColumnDefinition();
272 idColumn.setName( StringSerializer.get().toByteBuffer( ID.toString() ) );
273 idColumn.setIndexName( ID.toString() );
274 idColumn.setIndexType( ColumnIndexType.KEYS );
275 idColumn.setValidationClass( ComparatorType.UTF8TYPE.getClassName() );
276 artifactMetadataModel.addColumnDefinition( idColumn );
278 BasicColumnDefinition repositoryNameColumn = new BasicColumnDefinition();
279 repositoryNameColumn.setName( StringSerializer.get().toByteBuffer( REPOSITORY_NAME.toString() ) );
280 repositoryNameColumn.setIndexName( REPOSITORY_NAME.toString() );
281 repositoryNameColumn.setIndexType( ColumnIndexType.KEYS );
282 repositoryNameColumn.setValidationClass( ComparatorType.UTF8TYPE.getClassName() );
283 artifactMetadataModel.addColumnDefinition( repositoryNameColumn );
285 BasicColumnDefinition namespaceIdColumn = new BasicColumnDefinition();
286 namespaceIdColumn.setName( StringSerializer.get().toByteBuffer( NAMESPACE_ID.toString() ) );
287 namespaceIdColumn.setIndexName( NAMESPACE_ID.toString() );
288 namespaceIdColumn.setIndexType( ColumnIndexType.KEYS );
289 namespaceIdColumn.setValidationClass( ComparatorType.UTF8TYPE.getClassName() );
290 artifactMetadataModel.addColumnDefinition( namespaceIdColumn );
292 BasicColumnDefinition projectColumn = new BasicColumnDefinition();
293 projectColumn.setName( StringSerializer.get().toByteBuffer( PROJECT.toString() ) );
294 projectColumn.setIndexName( PROJECT.toString() );
295 projectColumn.setIndexType( ColumnIndexType.KEYS );
296 projectColumn.setValidationClass( ComparatorType.UTF8TYPE.getClassName() );
297 artifactMetadataModel.addColumnDefinition( projectColumn );
299 BasicColumnDefinition projectVersionColumn = new BasicColumnDefinition();
300 projectVersionColumn.setName( StringSerializer.get().toByteBuffer( PROJECT_VERSION.toString() ) );
301 projectVersionColumn.setIndexName( PROJECT_VERSION.toString() );
302 projectVersionColumn.setIndexType( ColumnIndexType.KEYS );
303 projectVersionColumn.setValidationClass( ComparatorType.UTF8TYPE.getClassName() );
304 artifactMetadataModel.addColumnDefinition( projectVersionColumn );
306 BasicColumnDefinition versionColumn = new BasicColumnDefinition();
307 versionColumn.setName( StringSerializer.get().toByteBuffer( VERSION.toString() ) );
308 versionColumn.setIndexName( VERSION.toString() );
309 versionColumn.setIndexType( ColumnIndexType.KEYS );
310 versionColumn.setValidationClass( ComparatorType.UTF8TYPE.getClassName() );
311 artifactMetadataModel.addColumnDefinition( versionColumn );
313 BasicColumnDefinition whenGatheredColumn = new BasicColumnDefinition();
314 whenGatheredColumn.setName( StringSerializer.get().toByteBuffer( WHEN_GATHERED.toString() ) );
315 whenGatheredColumn.setIndexName( WHEN_GATHERED.toString() );
316 whenGatheredColumn.setIndexType( ColumnIndexType.KEYS );
317 whenGatheredColumn.setValidationClass( ComparatorType.LONGTYPE.getClassName() );
318 artifactMetadataModel.addColumnDefinition( whenGatheredColumn );
320 BasicColumnDefinition sha1Column = new BasicColumnDefinition();
321 sha1Column.setName( StringSerializer.get().toByteBuffer( SHA1.toString() ) );
322 sha1Column.setIndexName( SHA1.toString() );
323 sha1Column.setIndexType( ColumnIndexType.KEYS );
324 sha1Column.setValidationClass( ComparatorType.UTF8TYPE.getClassName() );
325 artifactMetadataModel.addColumnDefinition( sha1Column );
327 BasicColumnDefinition md5Column = new BasicColumnDefinition();
328 md5Column.setName( StringSerializer.get().toByteBuffer( MD5.toString() ) );
329 md5Column.setIndexName( MD5.toString() );
330 md5Column.setIndexType( ColumnIndexType.KEYS );
331 md5Column.setValidationClass( ComparatorType.UTF8TYPE.getClassName() );
332 artifactMetadataModel.addColumnDefinition( md5Column );
337 // metadatafacetmodel table
339 final ColumnFamilyDefinition metadataFacetModel =
340 HFactory.createColumnFamilyDefinition( keyspace.getKeyspaceName(), //
341 getMetadataFacetFamilyName(), //
342 ComparatorType.UTF8TYPE );
343 cfds.add( metadataFacetModel );
345 // creating indexes for cql query
347 BasicColumnDefinition facetIdColumn = new BasicColumnDefinition();
348 facetIdColumn.setName( StringSerializer.get().toByteBuffer( FACET_ID.toString() ) );
349 facetIdColumn.setIndexName( FACET_ID.toString() );
350 facetIdColumn.setIndexType( ColumnIndexType.KEYS );
351 facetIdColumn.setValidationClass( ComparatorType.UTF8TYPE.getClassName() );
352 metadataFacetModel.addColumnDefinition( facetIdColumn );
354 BasicColumnDefinition repositoryNameColumn = new BasicColumnDefinition();
355 repositoryNameColumn.setName( StringSerializer.get().toByteBuffer( REPOSITORY_NAME.toString() ) );
356 repositoryNameColumn.setIndexName( REPOSITORY_NAME.toString() );
357 repositoryNameColumn.setIndexType( ColumnIndexType.KEYS );
358 repositoryNameColumn.setValidationClass( ComparatorType.UTF8TYPE.getClassName() );
359 metadataFacetModel.addColumnDefinition( repositoryNameColumn );
361 BasicColumnDefinition nameColumn = new BasicColumnDefinition();
362 nameColumn.setName( StringSerializer.get().toByteBuffer( NAME.toString() ) );
363 nameColumn.setIndexName( NAME.toString() );
364 nameColumn.setIndexType( ColumnIndexType.KEYS );
365 nameColumn.setValidationClass( ComparatorType.UTF8TYPE.getClassName() );
366 metadataFacetModel.addColumnDefinition( nameColumn );
368 BasicColumnDefinition namespaceColumn = new BasicColumnDefinition();
369 namespaceColumn.setName( StringSerializer.get().toByteBuffer( NAMESPACE_ID.toString() ) );
370 namespaceColumn.setIndexName( NAMESPACE_ID.toString() );
371 namespaceColumn.setIndexType( ColumnIndexType.KEYS );
372 namespaceColumn.setValidationClass( ComparatorType.UTF8TYPE.getClassName() );
373 metadataFacetModel.addColumnDefinition( namespaceColumn );
375 BasicColumnDefinition projectIdColumn = new BasicColumnDefinition();
376 projectIdColumn.setName( StringSerializer.get().toByteBuffer( PROJECT_ID.toString() ) );
377 projectIdColumn.setIndexName( PROJECT_ID.toString() );
378 projectIdColumn.setIndexType( ColumnIndexType.KEYS );
379 projectIdColumn.setValidationClass( ComparatorType.UTF8TYPE.getClassName() );
380 metadataFacetModel.addColumnDefinition( projectIdColumn );
382 BasicColumnDefinition projectVersionColumn = new BasicColumnDefinition();
383 projectVersionColumn.setName( StringSerializer.get().toByteBuffer( PROJECT_VERSION.toString() ) );
384 projectVersionColumn.setIndexName( PROJECT_VERSION.toString() );
385 projectVersionColumn.setIndexType( ColumnIndexType.KEYS );
386 projectVersionColumn.setValidationClass( ComparatorType.UTF8TYPE.getClassName() );
387 metadataFacetModel.addColumnDefinition( projectVersionColumn );
393 final ColumnFamilyDefinition mailingListCf =
394 HFactory.createColumnFamilyDefinition( keyspace.getKeyspaceName(), //
395 getMailingListFamilyName(), //
396 ComparatorType.UTF8TYPE );
398 BasicColumnDefinition projectVersionMetadataModel_key = new BasicColumnDefinition();
399 projectVersionMetadataModel_key.setName( StringSerializer.get().toByteBuffer( "projectVersionMetadataModel.key" ) );
400 projectVersionMetadataModel_key.setIndexName( "projectVersionMetadataModel_key" );
401 projectVersionMetadataModel_key.setIndexType( ColumnIndexType.KEYS );
402 projectVersionMetadataModel_key.setValidationClass( ComparatorType.UTF8TYPE.getClassName() );
403 mailingListCf.addColumnDefinition( projectVersionMetadataModel_key );
405 cfds.add( mailingListCf );
407 // creating indexes for cql query
413 final ColumnFamilyDefinition licenseCf =
414 HFactory.createColumnFamilyDefinition( keyspace.getKeyspaceName(), //
415 getLicenseFamilyName(), //
416 ComparatorType.UTF8TYPE );
418 BasicColumnDefinition projectVersionMetadataModel_key = new BasicColumnDefinition();
419 projectVersionMetadataModel_key.setName( StringSerializer.get().toByteBuffer( "projectVersionMetadataModel.key" ) );
420 projectVersionMetadataModel_key.setIndexName( "projectVersionMetadataModel_key" );
421 projectVersionMetadataModel_key.setIndexType( ColumnIndexType.KEYS );
422 projectVersionMetadataModel_key.setValidationClass( ComparatorType.UTF8TYPE.getClassName() );
423 licenseCf.addColumnDefinition( projectVersionMetadataModel_key );
425 cfds.add( licenseCf );
427 // creating indexes for cql query
433 final ColumnFamilyDefinition dependencyCf =
434 HFactory.createColumnFamilyDefinition( keyspace.getKeyspaceName(), //
435 getDependencyFamilyName(), //
436 ComparatorType.UTF8TYPE );
437 cfds.add( dependencyCf );
439 // creating indexes for cql query
441 BasicColumnDefinition groupIdColumn = new BasicColumnDefinition();
442 groupIdColumn.setName( StringSerializer.get().toByteBuffer( GROUP_ID.toString() ) );
443 groupIdColumn.setIndexName( "groupIdIdx" );
444 groupIdColumn.setIndexType( ColumnIndexType.KEYS );
445 groupIdColumn.setValidationClass( ComparatorType.UTF8TYPE.getClassName() );
446 dependencyCf.addColumnDefinition( groupIdColumn );
448 BasicColumnDefinition projectVersionMetadataModel_key = new BasicColumnDefinition();
449 projectVersionMetadataModel_key.setName( StringSerializer.get().toByteBuffer( "projectVersionMetadataModel.key" ) );
450 projectVersionMetadataModel_key.setIndexName( "projectVersionMetadataModel_key" );
451 projectVersionMetadataModel_key.setIndexType( ColumnIndexType.KEYS );
452 projectVersionMetadataModel_key.setValidationClass( ComparatorType.UTF8TYPE.getClassName() );
453 dependencyCf.addColumnDefinition( projectVersionMetadataModel_key );
457 // TODO take care of update new table!!
458 { // ensure keyspace exists, here if the keyspace doesn't exist we suppose nothing exist
459 if ( cluster.describeKeyspace( keyspaceName ) == null )
461 logger.info( "Creating Archiva Cassandra '" + keyspaceName + "' keyspace." );
462 cluster.addKeyspace( HFactory.createKeyspaceDefinition( keyspaceName, //
463 ThriftKsDef.DEF_STRATEGY_CLASS, //
464 replicationFactor, //
479 public void shutdown()
485 public boolean started()
492 public Keyspace getKeyspace()
498 public Cluster getCluster()
504 public String getRepositoryFamilyName()
506 return repositoryFamilyName;
510 public String getNamespaceFamilyName()
512 return namespaceFamilyName;
516 public String getProjectFamilyName()
518 return projectFamilyName;
522 public String getProjectVersionMetadataFamilyName()
524 return projectVersionMetadataFamilyName;
528 public String getArtifactMetadataFamilyName()
530 return artifactMetadataFamilyName;
534 public String getMetadataFacetFamilyName()
536 return metadataFacetFamilyName;
540 public String getMailingListFamilyName()
542 return mailingListFamilyName;
546 public String getLicenseFamilyName()
548 return licenseFamilyName;
552 public String getDependencyFamilyName()
554 return dependencyFamilyName;