This is an automated email from the ASF dual-hosted git repository.

east pushed a commit to branch cluster
in repository https://gitbox.apache.org/repos/asf/incubator-iotdb.git


The following commit(s) were added to refs/heads/cluster by this push:
     new 358550f  init entities for Cluster
     new 3f1cdb3  Merge remote-tracking branch 'origin/cluster' into cluster
358550f is described below

commit 358550f944bcae6c7e83b7c847f1f0b44d029fb3
Author: mdf369 <[email protected]>
AuthorDate: Mon Mar 25 20:06:05 2019 +0800

    init entities for Cluster
---
 .../main/java/org/apache/iotdb/cluster/App.java    |  25 +++-
 .../main/java/org/apache/iotdb/cluster/Utils.java  |  45 +++++++
 .../apache/iotdb/cluster/config/ClusterConfig.java | 150 +++++++++++++++++++++
 .../iotdb/cluster/config/ClusterConstant.java      |  27 ++++
 .../iotdb/cluster/config/ClusterDescriptor.java    | 127 +++++++++++++++++
 .../org/apache/iotdb/cluster/entity/Server.java    |  69 ++++++++++
 .../cluster/entity/data/DataPartitionHolder.java   |  41 ++++++
 .../cluster/entity/data/IPartitionHolder.java      |  25 ++++
 .../iotdb/cluster/entity/metadata/IHolder.java     |  25 ++++
 .../cluster/entity/metadata/MetadataHolder.java    |  41 ++++++
 .../entity/raft/DataPartitionRaftHolder.java       |  35 +++++
 .../cluster/entity/raft/DataStateMachine.java      |  36 +++++
 .../cluster/entity/raft/MetadataRaftHolder.java    |  33 +++++
 .../cluster/entity/raft/MetadataStateManchine.java |  80 +++++++++++
 .../apache/iotdb/cluster/entity/raft/RaftNode.java |  95 +++++++++++++
 .../iotdb/cluster/entity/raft/RaftService.java     |  67 +++++++++
 .../iotdb/cluster/entity/service/IService.java     |  25 ++++
 17 files changed, 943 insertions(+), 3 deletions(-)

diff --git a/cluster/src/main/java/org/apache/iotdb/cluster/App.java 
b/cluster/src/main/java/org/apache/iotdb/cluster/App.java
index 9750baa..56429f9 100644
--- a/cluster/src/main/java/org/apache/iotdb/cluster/App.java
+++ b/cluster/src/main/java/org/apache/iotdb/cluster/App.java
@@ -1,10 +1,29 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you 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 org.apache.iotdb.cluster;
 
+import org.apache.iotdb.cluster.entity.Server;
+
 public class App {
-  public App(){
-  }
 
   public static void main(String[] args){
-    System.out.println(123);
+    Server server = new Server();
+    server.start();
   }
 }
diff --git a/cluster/src/main/java/org/apache/iotdb/cluster/Utils.java 
b/cluster/src/main/java/org/apache/iotdb/cluster/Utils.java
new file mode 100644
index 0000000..26f0005
--- /dev/null
+++ b/cluster/src/main/java/org/apache/iotdb/cluster/Utils.java
@@ -0,0 +1,45 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you 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 org.apache.iotdb.cluster;
+
+import java.util.ArrayList;
+import java.util.List;
+import org.apache.iotdb.cluster.entity.raft.RaftNode;
+
+public class Utils {
+
+  private Utils(){}
+
+  public static List<RaftNode> convertNodesToRaftNodeList(String[] nodes) {
+    List<RaftNode> nodeList = new ArrayList<>(nodes.length);
+    for (int i = 0; i < nodes.length; i++) {
+      nodeList.add(RaftNode.parseRaftNode(nodes[i]));
+    }
+    return nodeList;
+  }
+
+  public static int getIndexOfIpFromRaftNodeList(String ip, List<RaftNode> 
nodeList) {
+    for (int i = 0; i < nodeList.size(); i++) {
+      if (nodeList.get(i).getIp().equals(ip)) {
+        return i;
+      }
+    }
+    return -1;
+  }
+}
diff --git 
a/cluster/src/main/java/org/apache/iotdb/cluster/config/ClusterConfig.java 
b/cluster/src/main/java/org/apache/iotdb/cluster/config/ClusterConfig.java
new file mode 100644
index 0000000..5c2d009
--- /dev/null
+++ b/cluster/src/main/java/org/apache/iotdb/cluster/config/ClusterConfig.java
@@ -0,0 +1,150 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you 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 org.apache.iotdb.cluster.config;
+
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+public class ClusterConfig {
+
+  public static final String CONFIG_NAME = "iotdb-cluster.properties";
+  public static final String DEFAULT_NODE_IP = "127.0.0.1:8888";
+
+  // Cluster node: {ip1,ip2,...,ipn}
+  private String[] nodes = {DEFAULT_NODE_IP};
+
+  // Replication number
+  private int replication = 3;
+
+  private String ip = null;
+  private int port = 8888;
+
+  // Path for metadata holder to store log
+  private String metadataGroupLogPath = "/tmp/metadata/log/";
+
+  // Path for metadata holder to store snapshot
+  private String metadataGroupSnapshotPath = "/tmp/metadata/snapshot/";
+
+  // Path for data partition to store log
+  private String dataGroupLogPath = "/tmp/data/log/";
+
+  // Path for data partition to store snapshot
+  private String dataGroupSnapshotPath = "/tmp/data/snapshot/";
+
+  // When the number of the difference between
+  // leader and follower log is less than this value, it is considered as 
'catch-up'
+  private int maxCatchUpLogNum = 100000;
+
+  // Whether to enable the delayed snapshot mechanism or not
+  private boolean delaySnapshot = false;
+  // Maximum allowed delay hours
+  private int delayHours = 24;
+
+  public ClusterConfig() {
+    // empty constructor
+  }
+
+  public String[] getNodes() {
+    return nodes;
+  }
+
+  public void setNodes(String[] nodes) {
+    this.nodes = nodes;
+  }
+
+  public int getReplication() {
+    return replication;
+  }
+
+  public void setReplication(int replication) {
+    this.replication = replication;
+  }
+
+  public String getIp() {
+    return ip;
+  }
+
+  public void setIp(String ip) {
+    this.ip = ip;
+  }
+
+  public int getPort() {
+    return port;
+  }
+
+  public void setPort(int port) {
+    this.port = port;
+  }
+
+  public String getMetadataGroupLogPath() {
+    return metadataGroupLogPath;
+  }
+
+  public void setMetadataGroupLogPath(String metadataGroupLogPath) {
+    this.metadataGroupLogPath = metadataGroupLogPath;
+  }
+
+  public String getMetadataGroupSnapshotPath() {
+    return metadataGroupSnapshotPath;
+  }
+
+  public void setMetadataGroupSnapshotPath(String metadataGroupSnapshotPath) {
+    this.metadataGroupSnapshotPath = metadataGroupSnapshotPath;
+  }
+
+  public String getDataGroupLogPath() {
+    return dataGroupLogPath;
+  }
+
+  public void setDataGroupLogPath(String dataGroupLogPath) {
+    this.dataGroupLogPath = dataGroupLogPath;
+  }
+
+  public String getDataGroupSnapshotPath() {
+    return dataGroupSnapshotPath;
+  }
+
+  public void setDataGroupSnapshotPath(String dataGroupSnapshotPath) {
+    this.dataGroupSnapshotPath = dataGroupSnapshotPath;
+  }
+
+  public int getMaxCatchUpLogNum() {
+    return maxCatchUpLogNum;
+  }
+
+  public void setMaxCatchUpLogNum(int maxCatchUpLogNum) {
+    this.maxCatchUpLogNum = maxCatchUpLogNum;
+  }
+
+  public boolean isDelaySnapshot() {
+    return delaySnapshot;
+  }
+
+  public void setDelaySnapshot(boolean delaySnapshot) {
+    this.delaySnapshot = delaySnapshot;
+  }
+
+  public int getDelayHours() {
+    return delayHours;
+  }
+
+  public void setDelayHours(int delayHours) {
+    this.delayHours = delayHours;
+  }
+}
diff --git 
a/cluster/src/main/java/org/apache/iotdb/cluster/config/ClusterConstant.java 
b/cluster/src/main/java/org/apache/iotdb/cluster/config/ClusterConstant.java
new file mode 100644
index 0000000..e4c0d78
--- /dev/null
+++ b/cluster/src/main/java/org/apache/iotdb/cluster/config/ClusterConstant.java
@@ -0,0 +1,27 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you 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 org.apache.iotdb.cluster.config;
+
+public class ClusterConstant {
+
+  public static final String CLUSTER_CONF = "CLUSTER_CONF";
+
+  private ClusterConstant(){
+  }
+}
diff --git 
a/cluster/src/main/java/org/apache/iotdb/cluster/config/ClusterDescriptor.java 
b/cluster/src/main/java/org/apache/iotdb/cluster/config/ClusterDescriptor.java
new file mode 100644
index 0000000..b438e2d
--- /dev/null
+++ 
b/cluster/src/main/java/org/apache/iotdb/cluster/config/ClusterDescriptor.java
@@ -0,0 +1,127 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you 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 org.apache.iotdb.cluster.config;
+
+import java.io.File;
+import java.io.FileInputStream;
+import java.io.FileNotFoundException;
+import java.io.IOException;
+import java.io.InputStream;
+import java.util.Properties;
+import org.apache.iotdb.db.conf.IoTDBConstant;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+public class ClusterDescriptor {
+
+  private static final Logger LOGGER = 
LoggerFactory.getLogger(ClusterDescriptor.class);
+  private ClusterConfig conf = new ClusterConfig();
+
+  private ClusterDescriptor() {
+    loadProps();
+  }
+
+  public static ClusterDescriptor getInstance() {
+    return ClusterDescriptorHolder.INSTANCE;
+  }
+
+  public ClusterConfig getConfig() {
+    return conf;
+  }
+
+  /**
+   * load an property file and set ClusterConfig variables.
+   */
+  private void loadProps() {
+    InputStream inputStream;
+    String url = System.getProperty(ClusterConstant.CLUSTER_CONF, null);
+    if (url == null) {
+      url = System.getProperty(IoTDBConstant.IOTDB_HOME, null);
+      if (url != null) {
+        url = url + File.separatorChar + "conf" + File.separatorChar + 
ClusterConfig.CONFIG_NAME;
+      } else {
+        LOGGER.warn(
+            "Cannot find IOTDB_HOME or CLUSTER_CONF environment variable when 
loading "
+                + "config file {}, use default configuration",
+            ClusterConfig.CONFIG_NAME);
+        return;
+      }
+    } else {
+      url += (File.separatorChar + ClusterConfig.CONFIG_NAME);
+    }
+
+    try {
+      inputStream = new FileInputStream(new File(url));
+    } catch (FileNotFoundException e) {
+      LOGGER.warn("Fail to find config file {}", url, e);
+      return;
+    }
+
+    LOGGER.info("Start to read config file {}", url);
+    Properties properties = new Properties();
+    try {
+      properties.load(inputStream);
+      conf.setNodes(properties.getProperty("nodes", 
ClusterConfig.DEFAULT_NODE_IP)
+          .split(","));
+
+      conf.setReplication(Integer
+          .parseInt(properties.getProperty("replication",
+              Integer.toString(conf.getReplication()))));
+
+      conf.setIp(properties.getProperty("ip", conf.getIp()));
+
+      conf.setPort(Integer.parseInt(properties.getProperty("port",
+          Integer.toString(conf.getPort()))));
+
+      conf.setIp(properties.getProperty("metadata_group_log_path", 
conf.getMetadataGroupLogPath()));
+
+      conf.setIp(properties.getProperty("metadata_group_snapshot_path", 
conf.getMetadataGroupSnapshotPath()));
+
+      conf.setIp(properties.getProperty("data_group_log_path", 
conf.getDataGroupLogPath()));
+
+      conf.setIp(properties.getProperty("data_group_snapshot_path", 
conf.getDataGroupSnapshotPath()));
+
+      conf.setMaxCatchUpLogNum(Integer
+          .parseInt(properties.getProperty("max_catch_up_log_num",
+              Integer.toString(conf.getMaxCatchUpLogNum()))));
+
+      conf.setDelaySnapshot(Boolean
+          .parseBoolean(properties.getProperty("delay_snapshot",
+              Boolean.toString(conf.isDelaySnapshot()))));
+
+      conf.setDelayHours(Integer
+          .parseInt(properties.getProperty("delay_hours",
+              Integer.toString(conf.getDelayHours()))));
+    } catch (IOException e) {
+      LOGGER.warn("Cannot load config file because, use default 
configuration", e);
+    } catch (Exception e) {
+      LOGGER.warn("Incorrect format in config file, use default 
configuration", e);
+    } finally {
+      try {
+        inputStream.close();
+      } catch (IOException e) {
+        LOGGER.error("Fail to close config file input stream because ", e);
+      }
+    }
+  }
+
+  private static class ClusterDescriptorHolder {
+    private static final ClusterDescriptor INSTANCE = new ClusterDescriptor();
+  }
+}
diff --git a/cluster/src/main/java/org/apache/iotdb/cluster/entity/Server.java 
b/cluster/src/main/java/org/apache/iotdb/cluster/entity/Server.java
new file mode 100644
index 0000000..b12654b
--- /dev/null
+++ b/cluster/src/main/java/org/apache/iotdb/cluster/entity/Server.java
@@ -0,0 +1,69 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you 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 org.apache.iotdb.cluster.entity;
+
+import java.util.Collections;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+import org.apache.iotdb.cluster.Utils;
+import org.apache.iotdb.cluster.config.ClusterConfig;
+import org.apache.iotdb.cluster.config.ClusterDescriptor;
+import org.apache.iotdb.cluster.entity.data.DataPartitionHolder;
+import org.apache.iotdb.cluster.entity.metadata.MetadataHolder;
+import org.apache.iotdb.cluster.entity.raft.DataPartitionRaftHolder;
+import org.apache.iotdb.cluster.entity.raft.MetadataRaftHolder;
+import org.apache.iotdb.cluster.entity.raft.RaftNode;
+import org.apache.iotdb.db.service.IoTDB;
+import org.apache.iotdb.tsfile.utils.Pair;
+
+public class Server {
+
+  private static final ClusterConfig ClusterConf = 
ClusterDescriptor.getInstance().getConfig();
+
+  private MetadataHolder metadataHolder;
+  private Map<Integer, DataPartitionHolder> dataPartitionHolderMap;
+
+  public void start() {
+    // Stand-alone version of IoTDB, be careful to replace the internal JDBC 
Server with a cluster version
+    IoTDB iotdb = new IoTDB();
+    iotdb.active();
+
+    List<RaftNode> nodeList = 
Utils.convertNodesToRaftNodeList(ClusterConf.getNodes());
+    metadataHolder = new MetadataRaftHolder(nodeList, null);
+    metadataHolder.init();
+    metadataHolder.start();
+
+    dataPartitionHolderMap = new HashMap<>();
+    int index = Utils.getIndexOfIpFromRaftNodeList(ClusterConf.getIp(), 
nodeList);
+    List<Pair<Integer, List<RaftNode>>> groupNodeList = 
getDataPartitonNodeList(index, nodeList);
+    for(int i = 0; i < groupNodeList.size(); i++) {
+      Pair<Integer, List<RaftNode>> pair = groupNodeList.get(i);
+      DataPartitionHolder dataPartitionHolder = new 
DataPartitionRaftHolder(pair.left, pair.right, null);
+      dataPartitionHolder.init();
+      dataPartitionHolder.start();
+      dataPartitionHolderMap.put(pair.left, dataPartitionHolder);
+    }
+  }
+
+  // A node belongs to multiple data groups and calculates the members of the 
i-th data group.
+  private List<Pair<Integer, List<RaftNode>>> getDataPartitonNodeList(int i, 
List<RaftNode> nodeList) {
+    return Collections.emptyList();
+  }
+}
diff --git 
a/cluster/src/main/java/org/apache/iotdb/cluster/entity/data/DataPartitionHolder.java
 
b/cluster/src/main/java/org/apache/iotdb/cluster/entity/data/DataPartitionHolder.java
new file mode 100644
index 0000000..2975cc1
--- /dev/null
+++ 
b/cluster/src/main/java/org/apache/iotdb/cluster/entity/data/DataPartitionHolder.java
@@ -0,0 +1,41 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you 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 org.apache.iotdb.cluster.entity.data;
+
+import org.apache.iotdb.cluster.entity.service.IService;
+
+public class DataPartitionHolder implements IPartitionHolder {
+
+  protected IService service;;
+
+  @Override
+  public void init() {
+    service.init();
+  }
+
+  @Override
+  public void start() {
+    service.start();
+  }
+
+  @Override
+  public void stop() {
+    service.stop();
+  }
+}
diff --git 
a/cluster/src/main/java/org/apache/iotdb/cluster/entity/data/IPartitionHolder.java
 
b/cluster/src/main/java/org/apache/iotdb/cluster/entity/data/IPartitionHolder.java
new file mode 100644
index 0000000..b658590
--- /dev/null
+++ 
b/cluster/src/main/java/org/apache/iotdb/cluster/entity/data/IPartitionHolder.java
@@ -0,0 +1,25 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you 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 org.apache.iotdb.cluster.entity.data;
+
+public interface IPartitionHolder {
+  void init();
+  void start();
+  void stop();
+}
diff --git 
a/cluster/src/main/java/org/apache/iotdb/cluster/entity/metadata/IHolder.java 
b/cluster/src/main/java/org/apache/iotdb/cluster/entity/metadata/IHolder.java
new file mode 100644
index 0000000..f8cbefc
--- /dev/null
+++ 
b/cluster/src/main/java/org/apache/iotdb/cluster/entity/metadata/IHolder.java
@@ -0,0 +1,25 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you 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 org.apache.iotdb.cluster.entity.metadata;
+
+public interface IHolder {
+  void init();
+  void start();
+  void stop();
+}
diff --git 
a/cluster/src/main/java/org/apache/iotdb/cluster/entity/metadata/MetadataHolder.java
 
b/cluster/src/main/java/org/apache/iotdb/cluster/entity/metadata/MetadataHolder.java
new file mode 100644
index 0000000..7358240
--- /dev/null
+++ 
b/cluster/src/main/java/org/apache/iotdb/cluster/entity/metadata/MetadataHolder.java
@@ -0,0 +1,41 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you 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 org.apache.iotdb.cluster.entity.metadata;
+
+import org.apache.iotdb.cluster.entity.service.IService;
+
+public abstract class MetadataHolder implements IHolder {
+
+  protected IService service;
+
+  @Override
+  public void init() {
+    service.init();
+  }
+
+  @Override
+  public void start() {
+    service.start();
+  }
+
+  @Override
+  public void stop() {
+    service.stop();
+  }
+}
diff --git 
a/cluster/src/main/java/org/apache/iotdb/cluster/entity/raft/DataPartitionRaftHolder.java
 
b/cluster/src/main/java/org/apache/iotdb/cluster/entity/raft/DataPartitionRaftHolder.java
new file mode 100644
index 0000000..8a0680f
--- /dev/null
+++ 
b/cluster/src/main/java/org/apache/iotdb/cluster/entity/raft/DataPartitionRaftHolder.java
@@ -0,0 +1,35 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you 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 org.apache.iotdb.cluster.entity.raft;
+
+import com.alipay.sofa.jraft.storage.LogStorage;
+import java.util.List;
+import org.apache.iotdb.cluster.entity.data.DataPartitionHolder;
+
+public class DataPartitionRaftHolder extends DataPartitionHolder {
+
+  private int groupId;
+  private DataStateMachine fsm;
+
+  public DataPartitionRaftHolder(int groupId, List<RaftNode> nodeList, 
LogStorage logStorage) {
+    this.groupId = groupId;
+    fsm = new DataStateMachine();
+    service = new RaftService(nodeList, logStorage);
+  }
+}
diff --git 
a/cluster/src/main/java/org/apache/iotdb/cluster/entity/raft/DataStateMachine.java
 
b/cluster/src/main/java/org/apache/iotdb/cluster/entity/raft/DataStateMachine.java
new file mode 100644
index 0000000..fc537e6
--- /dev/null
+++ 
b/cluster/src/main/java/org/apache/iotdb/cluster/entity/raft/DataStateMachine.java
@@ -0,0 +1,36 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you 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 org.apache.iotdb.cluster.entity.raft;
+
+import com.alipay.sofa.jraft.Iterator;
+import com.alipay.sofa.jraft.core.StateMachineAdapter;
+import org.apache.iotdb.db.engine.Processor;
+
+public class DataStateMachine extends StateMachineAdapter {
+  private Processor process;
+
+  public DataStateMachine() {
+    //TODO init @code{process}
+  }
+
+  @Override
+  public void onApply(Iterator iterator) {
+
+  }
+}
diff --git 
a/cluster/src/main/java/org/apache/iotdb/cluster/entity/raft/MetadataRaftHolder.java
 
b/cluster/src/main/java/org/apache/iotdb/cluster/entity/raft/MetadataRaftHolder.java
new file mode 100644
index 0000000..93bb7ce
--- /dev/null
+++ 
b/cluster/src/main/java/org/apache/iotdb/cluster/entity/raft/MetadataRaftHolder.java
@@ -0,0 +1,33 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you 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 org.apache.iotdb.cluster.entity.raft;
+
+import com.alipay.sofa.jraft.storage.LogStorage;
+import java.util.List;
+import org.apache.iotdb.cluster.entity.metadata.MetadataHolder;
+
+public class MetadataRaftHolder extends MetadataHolder {
+
+  private MetadataStateManchine fsm;
+
+  public MetadataRaftHolder(List<RaftNode> nodeList, LogStorage logStorage) {
+    fsm = new MetadataStateManchine();
+    service = new RaftService(nodeList, logStorage);
+  }
+}
diff --git 
a/cluster/src/main/java/org/apache/iotdb/cluster/entity/raft/MetadataStateManchine.java
 
b/cluster/src/main/java/org/apache/iotdb/cluster/entity/raft/MetadataStateManchine.java
new file mode 100644
index 0000000..d1b13c0
--- /dev/null
+++ 
b/cluster/src/main/java/org/apache/iotdb/cluster/entity/raft/MetadataStateManchine.java
@@ -0,0 +1,80 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you 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 org.apache.iotdb.cluster.entity.raft;
+
+import com.alipay.sofa.jraft.Iterator;
+import com.alipay.sofa.jraft.core.StateMachineAdapter;
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+public class MetadataStateManchine extends StateMachineAdapter {
+
+  // All Storage Groups in Cluster
+  private List<String> storageGroupList;
+
+  // Map<username, password>
+  Map<String, String> userProfileMap;
+
+  public MetadataStateManchine() {
+    storageGroupList = new ArrayList<>();
+    userProfileMap = new HashMap<>();
+  }
+
+  // Update StrageGroup List and userProfileMap based on Task read from raft 
log
+  @Override
+  public void onApply(Iterator iterator) {
+
+  }
+
+  public boolean isStorageGroupLegal(String sg) {
+    return storageGroupList.contains(sg);
+  }
+
+  public boolean isUerProfileLegal(String username, String password) {
+    if (userProfileMap.containsKey(username)) {
+      return password.equals(userProfileMap.get(username));
+    } else {
+      return false;
+    }
+  }
+
+  public void addStorageGroup(String sg) {
+    storageGroupList.add(sg);
+  }
+
+  public void deleteStorageGroup(String sg) {
+    storageGroupList.remove(sg);
+  }
+
+  public void addUser(String username, String password) {
+    userProfileMap.put(username, password);
+  }
+
+  public void deleteUSer(String username, String password) {
+    userProfileMap.remove(username, password);
+  }
+
+  public void updateUser(String username, String oldPassword, String 
newPassword) {
+    if (isUerProfileLegal(username, oldPassword)) {
+      userProfileMap.put(username, newPassword);
+    }
+  }
+}
diff --git 
a/cluster/src/main/java/org/apache/iotdb/cluster/entity/raft/RaftNode.java 
b/cluster/src/main/java/org/apache/iotdb/cluster/entity/raft/RaftNode.java
new file mode 100644
index 0000000..2ded0f2
--- /dev/null
+++ b/cluster/src/main/java/org/apache/iotdb/cluster/entity/raft/RaftNode.java
@@ -0,0 +1,95 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you 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 org.apache.iotdb.cluster.entity.raft;
+
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+public class RaftNode {
+
+  private static final Logger LOGGER = LoggerFactory.getLogger(RaftNode.class);
+
+  private String ip;
+  private int port;
+  private int groupId;
+
+  public RaftNode() {
+  }
+
+  public RaftNode(String ip, int port, int groupId) {
+    this.ip = ip;
+    this.port = port;
+    this.groupId = groupId;
+  }
+
+  public String getIp() {
+    return ip;
+  }
+
+  public int getPort() {
+    return port;
+  }
+
+  public int getGroupId() {
+    return groupId;
+  }
+
+  /**
+   * Parse a raft node from string in the format of "ip:port:groupId",
+   * returns null if fail to parse.
+   *
+   * @param s input string with the format of "ip:port:groupId"
+   * @return parsed peer
+   */
+  public static RaftNode parseRaftNode(String s) {
+    final RaftNode node = new RaftNode();
+    if (node.parse(s)) {
+      return node;
+    }
+    return null;
+  }
+
+  /**
+   * Parse raftNode from string that generated by {@link #toString()}
+   */
+  public boolean parse(String s) {
+    final String[] tmps = s.split(":");
+    if (tmps.length != 3 && tmps.length != 2) {
+      return false;
+    }
+    try {
+      this.ip = tmps[0];
+      this.port = Integer.valueOf(tmps[1]);
+      if (tmps.length == 3) {
+        this.groupId = Integer.valueOf(tmps[2]);
+      } else {
+        this.groupId = 0;
+      }
+      return true;
+    } catch (final Exception e) {
+      LOGGER.error("Parse raft node from string failed: {}", s, e);
+      return false;
+    }
+  }
+
+  @Override
+  public String toString() {
+    return this.ip + ":" + this.port + ":" + this.groupId;
+  }
+}
diff --git 
a/cluster/src/main/java/org/apache/iotdb/cluster/entity/raft/RaftService.java 
b/cluster/src/main/java/org/apache/iotdb/cluster/entity/raft/RaftService.java
new file mode 100644
index 0000000..ee75b1a
--- /dev/null
+++ 
b/cluster/src/main/java/org/apache/iotdb/cluster/entity/raft/RaftService.java
@@ -0,0 +1,67 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you 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 org.apache.iotdb.cluster.entity.raft;
+
+import com.alipay.sofa.jraft.storage.LogStorage;
+import java.util.List;
+import org.apache.iotdb.cluster.entity.service.IService;
+
+public class RaftService implements IService {
+
+  private List<RaftNode> nodeList;
+  private LogStorage logStorage;
+  private State state;
+  private RaftNode leader;
+
+  public RaftService(List<RaftNode> nodeList, LogStorage logStorage) {
+    this.nodeList = nodeList;
+    this.logStorage = logStorage;
+  }
+
+  @Override
+  public void init() {
+
+  }
+
+  @Override
+  public void start() {
+
+  }
+
+  @Override
+  public void stop() {
+
+  }
+
+  public void saveSnapshot() {
+
+  }
+
+  public void loadSnapshot() {
+
+  }
+
+  public void onRevice(Object message) {
+
+  }
+
+  enum State {
+    FOLLOWER, LEADER, CANIDIDATE;
+  }
+}
diff --git 
a/cluster/src/main/java/org/apache/iotdb/cluster/entity/service/IService.java 
b/cluster/src/main/java/org/apache/iotdb/cluster/entity/service/IService.java
new file mode 100644
index 0000000..57e2844
--- /dev/null
+++ 
b/cluster/src/main/java/org/apache/iotdb/cluster/entity/service/IService.java
@@ -0,0 +1,25 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you 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 org.apache.iotdb.cluster.entity.service;
+
+public interface IService {
+  void init();
+  void start();
+  void stop();
+}

Reply via email to