2 * ============LICENSE_START=======================================================
3 * Copyright (C) 2016-2018 Ericsson. All rights reserved.
4 * ================================================================================
5 * Licensed under the Apache License, Version 2.0 (the "License");
6 * you may not use this file except in compliance with the License.
7 * You may obtain a copy of the License at
9 * http://www.apache.org/licenses/LICENSE-2.0
11 * Unless required by applicable law or agreed to in writing, software
12 * distributed under the License is distributed on an "AS IS" BASIS,
13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 * See the License for the specific language governing permissions and
15 * limitations under the License.
17 * SPDX-License-Identifier: Apache-2.0
18 * ============LICENSE_END=========================================================
21 package org.onap.policy.apex.plugins.context.locking.curator;
23 import java.util.concurrent.TimeUnit;
24 import java.util.concurrent.locks.ReadWriteLock;
26 import org.apache.curator.framework.CuratorFramework;
27 import org.apache.curator.framework.CuratorFrameworkFactory;
28 import org.apache.curator.framework.state.ConnectionState;
29 import org.apache.curator.framework.state.ConnectionStateListener;
30 import org.apache.curator.retry.ExponentialBackoffRetry;
31 import org.apache.curator.utils.CloseableUtils;
32 import org.apache.zookeeper.CreateMode;
33 import org.onap.policy.apex.context.ContextException;
34 import org.onap.policy.apex.context.impl.locking.AbstractLockManager;
35 import org.onap.policy.apex.model.basicmodel.concepts.AxArtifactKey;
36 import org.onap.policy.common.parameters.ParameterService;
37 import org.slf4j.ext.XLogger;
38 import org.slf4j.ext.XLoggerFactory;
41 * The Class CuratorLockManager manages the Curator interface towards Zookeeper for administering the Apex Context Album
44 public class CuratorLockManager extends AbstractLockManager {
45 // Logger for this class
46 private static final XLogger LOGGER = XLoggerFactory.getXLogger(CuratorLockManager.class);
48 // The Curator framework used for locking
49 private CuratorFramework curatorFramework;
51 // The address of the Zookeeper server
52 private String curatorZookeeperAddress;
55 * Constructor, set up a lock manager that uses Curator locking.
57 * @throws ContextException On errors connecting to Curator
59 public CuratorLockManager() throws ContextException {
60 LOGGER.entry("CuratorLockManager(): setting up the Curator lock manager . . .");
62 LOGGER.exit("CuratorLockManager(): Curator lock manager set up");
68 * @see org.onap.policy.apex.context.impl.locking.AbstractLockManager#init(org.onap.policy.apex. model.
69 * basicmodel.concepts.AxArtifactKey)
72 public void init(final AxArtifactKey key) throws ContextException {
73 LOGGER.entry("init(" + key + ")");
77 // Get the lock manager parameters
78 final CuratorLockManagerParameters lockParameters = ParameterService
79 .get(CuratorLockManagerParameters.class.getSimpleName());
81 // Check if the curator address has been set
82 curatorZookeeperAddress = lockParameters.getZookeeperAddress();
83 if (curatorZookeeperAddress == null || curatorZookeeperAddress.trim().length() == 0) {
84 LOGGER.warn("could not set up Curator locking, check if the curator Zookeeper address parameter is set correctly");
85 throw new ContextException(
86 "could not set up Curator locking, check if the curator Zookeeper address parameter is set correctly");
89 // Set up the curator framework we'll use
90 curatorFramework = CuratorFrameworkFactory.builder().connectString(curatorZookeeperAddress)
91 .retryPolicy(new ExponentialBackoffRetry(lockParameters.getZookeeperConnectSleepTime(),
92 lockParameters.getZookeeperContextRetries()))
95 // Listen for changes on the Curator connection
96 curatorFramework.getConnectionStateListenable().addListener(new CuratorManagerConnectionStateListener());
98 // Start the framework and specify Ephemeral nodes
99 curatorFramework.start();
101 // Wait for the connection to be made
103 curatorFramework.blockUntilConnected(
104 lockParameters.getZookeeperConnectSleepTime() * lockParameters.getZookeeperContextRetries(),
105 TimeUnit.MILLISECONDS);
106 } catch (final InterruptedException e) {
107 // restore the interrupt status
108 Thread.currentThread().interrupt();
109 String message = "error connecting to Zookeeper server at \"" + curatorZookeeperAddress
110 + "\", wait for connection timed out";
111 LOGGER.warn(message);
112 throw new ContextException(message);
115 if (!curatorFramework.getZookeeperClient().isConnected()) {
116 String message = "could not connect to Zookeeper server at \"" + curatorZookeeperAddress
117 + "\", see error log for details";
118 LOGGER.warn(message);
119 throw new ContextException(message);
122 // We'll use Ephemeral nodes for locks on the Zookeeper server
123 curatorFramework.create().withMode(CreateMode.EPHEMERAL_SEQUENTIAL);
125 LOGGER.exit("init(" + key + "," + lockParameters + ")");
131 * @see org.onap.policy.apex.core.context.impl.locking.AbstractLockManager#getReentrantReadWriteLock(
135 public ReadWriteLock getReentrantReadWriteLock(final String lockId) throws ContextException {
136 // Check if the framework is active
137 if (curatorFramework != null && curatorFramework.getZookeeperClient().isConnected()) {
138 return new CuratorReentrantReadWriteLock(curatorFramework, "/" + lockId);
140 throw new ContextException("creation of lock using Zookeeper server at \"" + curatorZookeeperAddress
141 + "\", failed, see error log for details");
148 * @see org.onap.policy.apex.core.context.LockManager#shutdown()
151 public void shutdown() {
152 if (curatorFramework == null) {
155 CloseableUtils.closeQuietly(curatorFramework);
156 curatorFramework = null;
160 * This class is a callback class for state changes on the curator to Zookeeper connection.
162 private class CuratorManagerConnectionStateListener implements ConnectionStateListener {
167 * @see org.apache.curator.framework.state.ConnectionStateListener#stateChanged(org.apache.
168 * curator.framework.CuratorFramework, org.apache.curator.framework.state.ConnectionState)
171 public void stateChanged(final CuratorFramework incomngCuratorFramework, final ConnectionState newState) {
172 // Is the state changed for this curator framework?
173 if (!incomngCuratorFramework.equals(curatorFramework)) {
177 LOGGER.info("curator state of client \"{}\" connected to \"{}\" changed to {}", curatorFramework,
178 curatorZookeeperAddress, newState);
180 if (newState != ConnectionState.CONNECTED) {