您好,登錄后才能下訂單哦!
如何使用ACM實現(xiàn)zookeeper依賴服務(wù)的透明Failover遷移,很多新手對此不是很清楚,為了幫助大家解決這個難題,下面小編將為大家詳細講解,有這方面需求的人可以來學(xué)習(xí)下,希望你能有所收獲。
在一個數(shù)據(jù)中心里,一個zookeeper集群常常會服務(wù)多條業(yè)務(wù)線或者業(yè)務(wù)系統(tǒng),每個業(yè)務(wù)線或者業(yè)務(wù)系統(tǒng)有自己的開發(fā)團隊,而zookeeper這類公共服務(wù)則會有專門的運維或者團隊負責(zé)保障其服務(wù)可用性和連續(xù)性。
業(yè)務(wù)應(yīng)用通過Apache Curator客戶端或者原生的zookeeper客戶端訪問zookeeper服務(wù),在這個過程中,必須在應(yīng)用程序里指定connectString,即zookeeper服務(wù)所在的機器的ip列表, 代碼示例如下:
final String connectString = "192.168.1.151:2181,192.168.1.152:2181,192.168.1.153:2181,192.168.1.154:2181,192.168.1.155:2181"; final int sessionTimeoutInMs = 15000; final int connectionTimeoutInMs = 1000; final String appNs = "app1"; CuratorFrameworkFactory.Builder builder = CuratorFrameworkFactory.builder(); CuratorFramework zkClient = builder .connectString(connectString) .connectionTimeoutMs(connectionTimeoutInMs) .sessionTimeoutMs(sessionTimeoutInMs) .namespace(appNs) .retryPolicy(new RetryNTimes(6, 100)) .build(); zkClient.start();
但在zookeeper的生產(chǎn)運行過程中,zookeeper服務(wù)集群可能會遇到機器故障,機器遷移等情況,這個過程則需要zookeeper運維人員替換節(jié)點,將服務(wù)遷移到新的ip節(jié)點,整個流程,如下圖所示,
該方案如圖所示:
在這個方案中,可以將zk服務(wù)ip掛在一個dns域名或者vip上. 這樣在zookeeper替換節(jié)點時,應(yīng)用無感知,這個方案即服務(wù)發(fā)現(xiàn)方案。
優(yōu)點
簡單易理解,但因DNS ttl緩存失效問題,會有收斂時間。
缺點
想針對zookeeper集群同時設(shè)置超時時間,應(yīng)用使用zookeeper的chroot/namespace,用于連接zookeeper服務(wù)的用戶名,密碼等配置項,并根據(jù)負載等情況動態(tài)變更這些連接相關(guān)配置無法通過DNS,VIP系統(tǒng)做到。
我們將zookeeper集群的服務(wù)ip列表,連接超時,session超時參數(shù),chroot,當(dāng)前的用戶名,密碼等放在一個ACM配置里。
然后通過ACM SDK監(jiān)聽這個配置的變更,這里我們可以使用curator client提供的EnsembleProvider功能來結(jié)合ACM達到動態(tài)監(jiān)聽配置服務(wù)ip列表變更的效果。
示例代碼如下
import java.io.IOException; import java.io.StringReader; import java.util.Properties; import java.util.concurrent.Executor; import java.util.concurrent.Executors; import java.util.concurrent.atomic.AtomicReference; import org.apache.curator.ensemble.EnsembleProvider; import com.alibaba.edas.acm.listener.ConfigChangeListener; import com.alibaba.edas.acm.ConfigService; import com.alibaba.edas.acm.exception.ConfigException; public class ACMEnsembleProvider implements EnsembleProvider { private static final String ACM_ZK_CFG_DATAID = "com.taobao.zookeeper.connCfg"; private static final String ACM_ZK_CFG_GROUP = "zookeeper"; private static final int ACM_TIME_OUT_MS = 3000; private final static Executor acmCallBackExecutor = Executors.newSingleThreadScheduledExecutor(); private ConfigChangeListener configChangeListener; private final AtomicReference<String> connectionString = new AtomicReference<String>(""); private Properties cfg = new Properties(); public String getZkHosts() { // 從ACM控制臺該配置的"示例代碼"中拷貝對應(yīng)的值 ConfigService.init("${domain}", "${namespace}", "${accessKey}", "${secretKey}"); try { String zkServiceCfg = ConfigService.getConfig(ACM_ZK_CFG_DATAID, ACM_ZK_CFG_GROUP, ACM_TIME_OUT_MS); cfg.load(new StringReader(zkServiceCfg)); String connectString = cfg.getProperty("connectString"); connectionString.set(connectString); return connectString; } catch (ConfigException e1) { // logger.warn("acm.getConfig error with dataId : " + // dataIdZkHosts, e); e1.printStackTrace(); return null; } catch (IOException e) { e.printStackTrace(); return null; } } public void start() throws Exception { configChangeListener = new ConfigChangeListener() { public Executor getExecutor() { return acmCallBackExecutor; } public void receiveConfigInfo(String configInfo) { // logger.warn("receive zkHosts change in diamond, dataId : " + // dataIdZkHosts + ", changed zkHosts : " // + configInfo); try { cfg.load(new StringReader(configInfo)); } catch (IOException e) { // process exception e.printStackTrace(); } String connectString = cfg.getProperty("connectString"); connectionString.set(connectString); } }; ConfigService.addListener(ACM_ZK_CFG_DATAID, ACM_ZK_CFG_GROUP, configChangeListener); } public String getConnectionString() { return connectionString.get(); } public void close() throws IOException { // ConfigService.removeListener(ACM_ZK_CFG_DATAID, ACM_ZK_CFG_GROUP, // configChangeListener); } }
當(dāng)zookeeper集群的節(jié)點掛掉,需要更換ip列表或者修改超時參數(shù),應(yīng)用的znode配額quota時,zookeeper運維人員只需要在ACM上修改相關(guān)的配置項,ACM將自動分發(fā)變更到所有的應(yīng)用系統(tǒng)。
該方案如圖所示:
在上例中,我們可以看到,應(yīng)用系統(tǒng)開發(fā)人員(Dev)和運維人員(Ops)之間省去了溝通成本,應(yīng)用系統(tǒng)也省去了因連接相關(guān)的配置變更導(dǎo)致的應(yīng)用重新啟動或者發(fā)布應(yīng)用的變更成本。
看完上述內(nèi)容是否對您有幫助呢?如果還想對相關(guān)知識有進一步的了解或閱讀更多相關(guān)文章,請關(guān)注億速云行業(yè)資訊頻道,感謝您對億速云的支持。
免責(zé)聲明:本站發(fā)布的內(nèi)容(圖片、視頻和文字)以原創(chuàng)、轉(zhuǎn)載和分享為主,文章觀點不代表本網(wǎng)站立場,如果涉及侵權(quán)請聯(lián)系站長郵箱:is@yisu.com進行舉報,并提供相關(guān)證據(jù),一經(jīng)查實,將立刻刪除涉嫌侵權(quán)內(nèi)容。