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

qiaojialin pushed a commit to branch new_sync
in repository https://gitbox.apache.org/repos/asf/iotdb.git


The following commit(s) were added to refs/heads/new_sync by this push:
     new 8e630e4  [To new_sync][IOTDB-2700] Sync transfer adaption to receiver 
(#5200)
8e630e4 is described below

commit 8e630e45beb5ec55bc465a7b46c61c01bccc4c92
Author: Chen YZ <[email protected]>
AuthorDate: Wed Mar 16 11:01:36 2022 +0800

    [To new_sync][IOTDB-2700] Sync transfer adaption to receiver (#5200)
---
 .../sync/IoTDBSyncReceiverCollectorIT.java         |  10 +-
 .../apache/iotdb/db/newsync/conf/SyncPathUtil.java |   5 +
 .../iotdb/db/newsync/pipedata/TsFilePipeData.java  |  52 +++--
 .../pipedata/queue/PipeDataQueueFactory.java       |  45 +++++
 .../iotdb/db/newsync/receiver/ReceiverService.java |  29 +--
 .../db/newsync/receiver/collector/Collector.java   |  15 +-
 .../db/newsync/receiver/recovery/ReceiverLog.java  |  10 +-
 .../iotdb/db/newsync/transfer/SyncRequest.java     |  64 ------
 .../iotdb/db/newsync/transfer/SyncResponse.java    |  25 ---
 .../newsync/transport/client/ITransportClient.java |  19 ++
 .../newsync/transport/client/TransportClient.java  | 134 +++++--------
 .../db/newsync/transport/conf/TransportConfig.java |  19 ++
 .../newsync/transport/conf/TransportConstant.java  |  19 ++
 .../transport/server/TransportServerManager.java   |  31 ++-
 .../server/TransportServerManagerMBean.java        |  19 ++
 .../server/TransportServerThriftHandler.java       |  21 +-
 .../transport/server/TransportServiceImpl.java     | 219 +++++++++++++--------
 .../pipedata/BufferedPipeDataQueueTest.java        |  12 +-
 .../db/newsync/transport/TransportServiceTest.java | 196 ++++++++++++++++++
 thrift-sync/src/main/thrift/transport.thrift       |  28 ++-
 20 files changed, 649 insertions(+), 323 deletions(-)

diff --git 
a/integration/src/test/java/org/apache/iotdb/db/integration/sync/IoTDBSyncReceiverCollectorIT.java
 
b/integration/src/test/java/org/apache/iotdb/db/integration/sync/IoTDBSyncReceiverCollectorIT.java
index b6f75e9..d64aef7 100644
--- 
a/integration/src/test/java/org/apache/iotdb/db/integration/sync/IoTDBSyncReceiverCollectorIT.java
+++ 
b/integration/src/test/java/org/apache/iotdb/db/integration/sync/IoTDBSyncReceiverCollectorIT.java
@@ -29,6 +29,7 @@ import org.apache.iotdb.db.newsync.pipedata.PipeData;
 import org.apache.iotdb.db.newsync.pipedata.SchemaPipeData;
 import org.apache.iotdb.db.newsync.pipedata.TsFilePipeData;
 import org.apache.iotdb.db.newsync.pipedata.queue.BufferedPipeDataQueue;
+import org.apache.iotdb.db.newsync.pipedata.queue.PipeDataQueueFactory;
 import org.apache.iotdb.db.newsync.receiver.collector.Collector;
 import org.apache.iotdb.db.qp.physical.PhysicalPlan;
 import org.apache.iotdb.db.qp.physical.sys.CreateAlignedTimeSeriesPlan;
@@ -189,7 +190,7 @@ public class IoTDBSyncReceiverCollectorIT {
     Deletion deletion = new Deletion(new PartialPath("root.vehicle.**"), 0, 
33, 38);
     PipeData pipeData = new DeletionPipeData(deletion, serialNum++);
     BufferedPipeDataQueue pipeDataQueue =
-        Collector.getPipeDataQueue(
+        PipeDataQueueFactory.getBufferedPipeDataQueue(
             SyncPathUtil.getReceiverPipeLogDir(pipeName1, remoteIp1, 
createdTime1));
     pipeDataQueue.offer(pipeData);
 
@@ -275,6 +276,7 @@ public class IoTDBSyncReceiverCollectorIT {
         Assert.fail();
       }
     }
+    pipeDataQueue.clear();
   }
 
   @Test
@@ -399,10 +401,10 @@ public class IoTDBSyncReceiverCollectorIT {
 
     // 3. create and start collector
     BufferedPipeDataQueue pipeDataQueue1 =
-        Collector.getPipeDataQueue(
+        PipeDataQueueFactory.getBufferedPipeDataQueue(
             SyncPathUtil.getReceiverPipeLogDir(pipeName1, remoteIp1, 
createdTime1));
     BufferedPipeDataQueue pipeDataQueue2 =
-        Collector.getPipeDataQueue(
+        PipeDataQueueFactory.getBufferedPipeDataQueue(
             SyncPathUtil.getReceiverPipeLogDir(pipeName2, remoteIp2, 
createdTime2));
     Collector collector = new Collector();
     collector.startCollect();
@@ -499,5 +501,7 @@ public class IoTDBSyncReceiverCollectorIT {
         Assert.fail();
       }
     }
+    pipeDataQueue2.clear();
+    pipeDataQueue1.clear();
   }
 }
diff --git 
a/server/src/main/java/org/apache/iotdb/db/newsync/conf/SyncPathUtil.java 
b/server/src/main/java/org/apache/iotdb/db/newsync/conf/SyncPathUtil.java
index 50f024e..143a7f9 100644
--- a/server/src/main/java/org/apache/iotdb/db/newsync/conf/SyncPathUtil.java
+++ b/server/src/main/java/org/apache/iotdb/db/newsync/conf/SyncPathUtil.java
@@ -24,6 +24,11 @@ import java.io.File;
 
 /** Util for path generation in sync module */
 public class SyncPathUtil {
+
+  private SyncPathUtil() {
+    // forbidding instantiation
+  }
+
   /** sender */
   public static String getSenderPipeDir(String pipeName, long createTime) {
     return IoTDBDescriptor.getInstance().getConfig().getNewSyncDir()
diff --git 
a/server/src/main/java/org/apache/iotdb/db/newsync/pipedata/TsFilePipeData.java 
b/server/src/main/java/org/apache/iotdb/db/newsync/pipedata/TsFilePipeData.java
index aec255d..115af1a 100644
--- 
a/server/src/main/java/org/apache/iotdb/db/newsync/pipedata/TsFilePipeData.java
+++ 
b/server/src/main/java/org/apache/iotdb/db/newsync/pipedata/TsFilePipeData.java
@@ -41,15 +41,33 @@ import java.util.Objects;
 public class TsFilePipeData extends PipeData {
   private static final Logger logger = 
LoggerFactory.getLogger(TsFilePipeData.class);
 
-  private String tsFilePath;
+  private String parentDirPath;
+  private String tsFileName;
 
   public TsFilePipeData(String tsFilePath, long serialNumber) {
     super(serialNumber);
-    this.tsFilePath = tsFilePath;
+    String sep = File.separator.equals("\\") ? "\\\\" : File.separator;
+    String[] paths = tsFilePath.split(sep);
+    tsFileName = paths[paths.length - 1];
+    parentDirPath = tsFilePath.substring(0, tsFilePath.length() - 
tsFileName.length());
   }
 
-  public void setTsFilePath(String tsFilePath) {
-    this.tsFilePath = tsFilePath;
+  public TsFilePipeData(String parentDirPath, String tsFileName, long 
serialNumber) {
+    super(serialNumber);
+    this.parentDirPath = parentDirPath;
+    this.tsFileName = tsFileName;
+  }
+
+  public void setParentDirPath(String parentDirPath) {
+    this.parentDirPath = parentDirPath;
+  }
+
+  public String getTsFileName() {
+    return tsFileName;
+  }
+
+  public String getTsFilePath() {
+    return parentDirPath + File.separator + tsFileName;
   }
 
   @Override
@@ -59,18 +77,21 @@ public class TsFilePipeData extends PipeData {
 
   @Override
   public long serialize(DataOutputStream stream) throws IOException {
-    return super.serialize(stream) + ReadWriteIOUtils.write(tsFilePath, 
stream);
+    return super.serialize(stream)
+        + ReadWriteIOUtils.write(parentDirPath, stream)
+        + ReadWriteIOUtils.write(tsFileName, stream);
   }
 
   public static TsFilePipeData deserialize(DataInputStream stream) throws 
IOException {
     long serialNumber = stream.readLong();
-    String tsFilePath = ReadWriteIOUtils.readString(stream);
-    return new TsFilePipeData(tsFilePath, serialNumber);
+    String parentDirPath = ReadWriteIOUtils.readString(stream);
+    String tsFileName = ReadWriteIOUtils.readString(stream);
+    return new TsFilePipeData(parentDirPath == null ? "" : parentDirPath, 
tsFileName, serialNumber);
   }
 
   @Override
   public ILoader createLoader() {
-    return new TsFileLoader(new File(tsFilePath));
+    return new TsFileLoader(new File(getTsFilePath()));
   }
 
   @Override
@@ -82,7 +103,7 @@ public class TsFilePipeData extends PipeData {
   }
 
   public List<File> getTsFiles() throws FileNotFoundException {
-    File tsFile = new File(tsFilePath).getAbsoluteFile();
+    File tsFile = new File(getTsFilePath()).getAbsoluteFile();
     File resource = new File(tsFile.getAbsolutePath() + 
TsFileResource.RESOURCE_SUFFIX);
     File mods = new File(tsFile.getAbsolutePath() + 
ModificationFile.FILE_SUFFIX);
 
@@ -108,18 +129,18 @@ public class TsFilePipeData extends PipeData {
       try {
         
Thread.sleep(SyncConstant.DEFAULT_WAITING_FOR_TSFILE_CLOSE_MILLISECONDS);
       } catch (InterruptedException e) {
-        logger.warn(String.format("Be Interrupted when waiting for tsfile %s 
closed", tsFilePath));
+        logger.warn(String.format("Be Interrupted when waiting for tsfile %s 
closed", tsFileName));
       }
       logger.info(
           String.format(
               "Waiting for tsfile %s close, retry %d / %d.",
-              tsFilePath, (i + 1), 
SyncConstant.DEFAULT_WAITING_FOR_TSFILE_RETRY_NUMBER));
+              tsFileName, (i + 1), 
SyncConstant.DEFAULT_WAITING_FOR_TSFILE_RETRY_NUMBER));
     }
     return false;
   }
 
   private boolean isTsFileClosed() {
-    File tsFile = new File(tsFilePath).getAbsoluteFile();
+    File tsFile = new File(getTsFilePath()).getAbsoluteFile();
     File resource = new File(tsFile.getAbsolutePath() + 
TsFileResource.RESOURCE_SUFFIX);
     return resource.exists();
   }
@@ -130,7 +151,7 @@ public class TsFilePipeData extends PipeData {
         + "serialNumber="
         + serialNumber
         + ", tsFilePath='"
-        + tsFilePath
+        + getTsFilePath()
         + '\''
         + '}';
   }
@@ -140,12 +161,13 @@ public class TsFilePipeData extends PipeData {
     if (this == o) return true;
     if (o == null || getClass() != o.getClass()) return false;
     TsFilePipeData pipeData = (TsFilePipeData) o;
-    return Objects.equals(tsFilePath, pipeData.tsFilePath)
+    return Objects.equals(parentDirPath, pipeData.parentDirPath)
+        && Objects.equals(tsFileName, pipeData.tsFileName)
         && Objects.equals(serialNumber, pipeData.serialNumber);
   }
 
   @Override
   public int hashCode() {
-    return Objects.hash(tsFilePath, serialNumber);
+    return Objects.hash(parentDirPath, tsFileName, serialNumber);
   }
 }
diff --git 
a/server/src/main/java/org/apache/iotdb/db/newsync/pipedata/queue/PipeDataQueueFactory.java
 
b/server/src/main/java/org/apache/iotdb/db/newsync/pipedata/queue/PipeDataQueueFactory.java
new file mode 100644
index 0000000..92d1f70
--- /dev/null
+++ 
b/server/src/main/java/org/apache/iotdb/db/newsync/pipedata/queue/PipeDataQueueFactory.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.db.newsync.pipedata.queue;
+
+import java.util.Map;
+import java.util.concurrent.ConcurrentHashMap;
+
+public class PipeDataQueueFactory {
+
+  // TODO: try use weakReference to avoid memory leak
+  private static final Map<String, BufferedPipeDataQueue> 
bufferedPipeDataQueueMap =
+      new ConcurrentHashMap<>();
+  /**
+   * get or create BufferedPipeDataQueue identified by key
+   *
+   * @param pipeLogDir using path of pipe-log dir as key
+   * @return BufferedPipeDataQueue
+   */
+  public static BufferedPipeDataQueue getBufferedPipeDataQueue(String 
pipeLogDir) {
+    return bufferedPipeDataQueueMap.computeIfAbsent(
+        pipeLogDir, i -> new BufferedPipeDataQueue(pipeLogDir));
+  }
+
+  public static void removeBufferedPipeDataQueue(String pipeLogDir) {
+    BufferedPipeDataQueue queue = bufferedPipeDataQueueMap.remove(pipeLogDir);
+    queue.clear();
+  }
+}
diff --git 
a/server/src/main/java/org/apache/iotdb/db/newsync/receiver/ReceiverService.java
 
b/server/src/main/java/org/apache/iotdb/db/newsync/receiver/ReceiverService.java
index bfdb672..983f17c 100644
--- 
a/server/src/main/java/org/apache/iotdb/db/newsync/receiver/ReceiverService.java
+++ 
b/server/src/main/java/org/apache/iotdb/db/newsync/receiver/ReceiverService.java
@@ -21,18 +21,20 @@ package org.apache.iotdb.db.newsync.receiver;
 import org.apache.iotdb.db.exception.StartupException;
 import org.apache.iotdb.db.metadata.path.PartialPath;
 import org.apache.iotdb.db.newsync.conf.SyncPathUtil;
+import org.apache.iotdb.db.newsync.pipedata.queue.PipeDataQueueFactory;
 import org.apache.iotdb.db.newsync.receiver.collector.Collector;
 import org.apache.iotdb.db.newsync.receiver.manager.PipeInfo;
 import org.apache.iotdb.db.newsync.receiver.manager.PipeMessage;
 import org.apache.iotdb.db.newsync.receiver.manager.PipeStatus;
 import org.apache.iotdb.db.newsync.receiver.manager.ReceiverManager;
-import org.apache.iotdb.db.newsync.transfer.SyncRequest;
-import org.apache.iotdb.db.newsync.transfer.SyncResponse;
+import org.apache.iotdb.db.newsync.transport.server.TransportServerManager;
 import org.apache.iotdb.db.qp.physical.sys.ShowPipeServerPlan;
 import org.apache.iotdb.db.qp.utils.DatetimeUtils;
 import org.apache.iotdb.db.query.dataset.ListDataSet;
 import org.apache.iotdb.db.service.IService;
 import org.apache.iotdb.db.service.ServiceType;
+import org.apache.iotdb.service.transport.thrift.SyncRequest;
+import org.apache.iotdb.service.transport.thrift.SyncResponse;
 import org.apache.iotdb.tsfile.file.metadata.enums.TSDataType;
 import org.apache.iotdb.tsfile.read.common.Field;
 import org.apache.iotdb.tsfile.read.common.RowRecord;
@@ -69,8 +71,8 @@ public class ReceiverService implements IService {
               pipeInfo.getPipeName(), pipeInfo.getRemoteIp(), 
pipeInfo.getCreateTime());
         }
       }
-      // TODO: start socket
-    } catch (IOException e) {
+      TransportServerManager.getInstance().startService();
+    } catch (IOException | StartupException e) {
       logger.error(e.getMessage());
       return false;
     }
@@ -82,7 +84,8 @@ public class ReceiverService implements IService {
     try {
       receiverManager.stopServer();
       collector.stopCollect();
-      // TODO: stop socket and collector
+      // todo: how to stop?
+      TransportServerManager.getInstance().stopService();
     } catch (IOException e) {
       logger.error(e.getMessage());
       return false;
@@ -94,22 +97,22 @@ public class ReceiverService implements IService {
   // TODO: define exception
   // TODO: this is a mock interface
   public SyncResponse recMsg(SyncRequest request) throws IOException {
-    switch (request.getCode()) {
-      case SyncRequest.HEARTBEAT:
+    switch (request.getType()) {
+      case HEARTBEAT:
         List<PipeMessage> messages =
             receiverManager.getPipeMessages(
                 request.getPipeName(), request.getRemoteIp(), 
request.getCreateTime());
         break;
-      case SyncRequest.CREATE:
+      case CREATE:
         createPipe(request.getPipeName(), request.getRemoteIp(), 
request.getCreateTime());
         break;
-      case SyncRequest.START:
+      case START:
         startPipe(request.getPipeName(), request.getRemoteIp(), 
request.getCreateTime());
         break;
-      case SyncRequest.STOP:
+      case STOP:
         stopPipe(request.getPipeName(), request.getRemoteIp(), 
request.getCreateTime());
         break;
-      case SyncRequest.DROP:
+      case DROP:
         dropPipe(request.getPipeName(), request.getRemoteIp(), 
request.getCreateTime());
         break;
     }
@@ -142,6 +145,8 @@ public class ReceiverService implements IService {
     collector.stopPipe(pipeName, remoteIp, createTime);
     File dir = new File(SyncPathUtil.getReceiverPipeDir(pipeName, remoteIp, 
createTime));
     FileUtils.deleteDirectory(dir);
+    PipeDataQueueFactory.removeBufferedPipeDataQueue(
+        SyncPathUtil.getReceiverPipeLogDir(pipeName, remoteIp, createTime));
   }
 
   private void createDir(String pipeName, String remoteIp, long createTime) {
@@ -218,9 +223,9 @@ public class ReceiverService implements IService {
 
   @Override
   public void stop() {
-    stopPipeServer();
     try {
       receiverManager.close();
+      collector.stopCollect();
     } catch (IOException e) {
       logger.error(e.getMessage());
     }
diff --git 
a/server/src/main/java/org/apache/iotdb/db/newsync/receiver/collector/Collector.java
 
b/server/src/main/java/org/apache/iotdb/db/newsync/receiver/collector/Collector.java
index 6d85631..3c5b309 100644
--- 
a/server/src/main/java/org/apache/iotdb/db/newsync/receiver/collector/Collector.java
+++ 
b/server/src/main/java/org/apache/iotdb/db/newsync/receiver/collector/Collector.java
@@ -24,11 +24,10 @@ import org.apache.iotdb.db.concurrent.ThreadName;
 import org.apache.iotdb.db.exception.metadata.StorageGroupAlreadySetException;
 import org.apache.iotdb.db.newsync.conf.SyncPathUtil;
 import org.apache.iotdb.db.newsync.pipedata.PipeData;
-import org.apache.iotdb.db.newsync.pipedata.queue.BufferedPipeDataQueue;
 import org.apache.iotdb.db.newsync.pipedata.queue.PipeDataQueue;
+import org.apache.iotdb.db.newsync.pipedata.queue.PipeDataQueueFactory;
 import org.apache.iotdb.db.newsync.receiver.manager.PipeMessage;
 import org.apache.iotdb.db.newsync.receiver.manager.ReceiverManager;
-import org.apache.iotdb.db.utils.TestOnly;
 
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
@@ -51,15 +50,6 @@ public class Collector {
     taskFutures = new ConcurrentHashMap<>();
   }
 
-  private static Map<String, BufferedPipeDataQueue> bufferedPipeDataQueueMap =
-      new ConcurrentHashMap<>();
-
-  @TestOnly
-  public static BufferedPipeDataQueue getPipeDataQueue(String pipeLogDir) {
-    return bufferedPipeDataQueueMap.computeIfAbsent(
-        pipeLogDir, i -> new BufferedPipeDataQueue(pipeLogDir));
-  }
-
   public void startCollect() {
     this.executorService =
         
IoTDBThreadPoolFactory.newCachedThreadPool(ThreadName.SYNC_RECEIVER_COLLECTOR.getName());
@@ -118,7 +108,8 @@ public class Collector {
     @Override
     public void run() {
       PipeDataQueue pipeDataQueue =
-          getPipeDataQueue(SyncPathUtil.getReceiverPipeLogDir(pipeName, 
remoteIp, createTime));
+          PipeDataQueueFactory.getBufferedPipeDataQueue(
+              SyncPathUtil.getReceiverPipeLogDir(pipeName, remoteIp, 
createTime));
       while (!Thread.interrupted()) {
         PipeData pipeData = null;
         try {
diff --git 
a/server/src/main/java/org/apache/iotdb/db/newsync/receiver/recovery/ReceiverLog.java
 
b/server/src/main/java/org/apache/iotdb/db/newsync/receiver/recovery/ReceiverLog.java
index abbc710..03ec25a 100644
--- 
a/server/src/main/java/org/apache/iotdb/db/newsync/receiver/recovery/ReceiverLog.java
+++ 
b/server/src/main/java/org/apache/iotdb/db/newsync/receiver/recovery/ReceiverLog.java
@@ -115,7 +115,13 @@ public class ReceiverLog {
   }
 
   public void close() throws IOException {
-    bw.close();
-    msg.close();
+    if (bw != null) {
+      bw.close();
+      bw = null;
+    }
+    if (msg != null) {
+      msg.close();
+      msg = null;
+    }
   }
 }
diff --git 
a/server/src/main/java/org/apache/iotdb/db/newsync/transfer/SyncRequest.java 
b/server/src/main/java/org/apache/iotdb/db/newsync/transfer/SyncRequest.java
deleted file mode 100644
index c49355c..0000000
--- a/server/src/main/java/org/apache/iotdb/db/newsync/transfer/SyncRequest.java
+++ /dev/null
@@ -1,64 +0,0 @@
-/*
- * 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.db.newsync.transfer;
-
-public class SyncRequest {
-  public static final int CREATE = 0;
-  public static final int START = 1;
-  public static final int STOP = 2;
-  public static final int DROP = 3;
-  public static final int HEARTBEAT = 4;
-
-  private int code;
-  private String pipeName;
-  private String remoteIp;
-  private long createTime;
-
-  public int getCode() {
-    return code;
-  }
-
-  public void setCode(int code) {
-    this.code = code;
-  }
-
-  public String getPipeName() {
-    return pipeName;
-  }
-
-  public void setPipeName(String pipeName) {
-    this.pipeName = pipeName;
-  }
-
-  public String getRemoteIp() {
-    return remoteIp;
-  }
-
-  public void setRemoteIp(String remoteIp) {
-    this.remoteIp = remoteIp;
-  }
-
-  public long getCreateTime() {
-    return createTime;
-  }
-
-  public void setCreateTime(long createTime) {
-    this.createTime = createTime;
-  }
-}
diff --git 
a/server/src/main/java/org/apache/iotdb/db/newsync/transfer/SyncResponse.java 
b/server/src/main/java/org/apache/iotdb/db/newsync/transfer/SyncResponse.java
deleted file mode 100644
index 5f5eb1e..0000000
--- 
a/server/src/main/java/org/apache/iotdb/db/newsync/transfer/SyncResponse.java
+++ /dev/null
@@ -1,25 +0,0 @@
-/*
- * 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.db.newsync.transfer;
-
-public class SyncResponse {
-  public static final int SUCCESS = 0;
-  public static final int WARN = 1;
-  public static final int ERROR = 2;
-}
diff --git 
a/server/src/main/java/org/apache/iotdb/db/newsync/transport/client/ITransportClient.java
 
b/server/src/main/java/org/apache/iotdb/db/newsync/transport/client/ITransportClient.java
index 0499fb1..1376dcc 100644
--- 
a/server/src/main/java/org/apache/iotdb/db/newsync/transport/client/ITransportClient.java
+++ 
b/server/src/main/java/org/apache/iotdb/db/newsync/transport/client/ITransportClient.java
@@ -1,3 +1,22 @@
+/*
+ * 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.db.newsync.transport.client;
 
 public interface ITransportClient {}
diff --git 
a/server/src/main/java/org/apache/iotdb/db/newsync/transport/client/TransportClient.java
 
b/server/src/main/java/org/apache/iotdb/db/newsync/transport/client/TransportClient.java
index 037543b..0179656 100644
--- 
a/server/src/main/java/org/apache/iotdb/db/newsync/transport/client/TransportClient.java
+++ 
b/server/src/main/java/org/apache/iotdb/db/newsync/transport/client/TransportClient.java
@@ -1,3 +1,22 @@
+/*
+ * 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.db.newsync.transport.client;
 
 import org.apache.iotdb.db.concurrent.ThreadName;
@@ -8,10 +27,8 @@ import org.apache.iotdb.db.newsync.pipedata.PipeData;
 import org.apache.iotdb.db.newsync.pipedata.TsFilePipeData;
 import org.apache.iotdb.db.newsync.sender.pipe.Pipe;
 import org.apache.iotdb.db.newsync.transport.conf.TransportConstant;
-import org.apache.iotdb.db.sync.conf.SyncConstant;
 import org.apache.iotdb.db.sync.conf.SyncSenderConfig;
 import org.apache.iotdb.db.sync.conf.SyncSenderDescriptor;
-import org.apache.iotdb.db.sync.sender.transfer.SyncClient;
 import org.apache.iotdb.db.utils.TestOnly;
 import org.apache.iotdb.rpc.RpcTransportFactory;
 import org.apache.iotdb.service.transport.thrift.IdentityInfo;
@@ -31,13 +48,8 @@ import org.apache.thrift.transport.TTransportException;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 
-import java.io.BufferedReader;
-import java.io.ByteArrayOutputStream;
-import java.io.DataOutputStream;
 import java.io.File;
 import java.io.FileInputStream;
-import java.io.FileOutputStream;
-import java.io.FileReader;
 import java.io.IOException;
 import java.io.InputStream;
 import java.io.RandomAccessFile;
@@ -45,7 +57,6 @@ import java.net.Socket;
 import java.nio.ByteBuffer;
 import java.security.MessageDigest;
 import java.security.NoSuchAlgorithmException;
-import java.util.UUID;
 
 import static 
org.apache.iotdb.db.newsync.transport.conf.TransportConfig.isCheckFileDegistAgain;
 import static 
org.apache.iotdb.db.newsync.transport.conf.TransportConstant.REBASE_CODE;
@@ -54,7 +65,7 @@ import static 
org.apache.iotdb.db.newsync.transport.conf.TransportConstant.SUCCE
 
 public class TransportClient implements ITransportClient, Runnable {
 
-  private static final Logger logger = 
LoggerFactory.getLogger(SyncClient.class);
+  private static final Logger logger = 
LoggerFactory.getLogger(TransportClient.class);
 
   // TODO: Need to change to transport config
   private static SyncSenderConfig config = 
SyncSenderDescriptor.getInstance().getConfig();
@@ -71,8 +82,6 @@ public class TransportClient implements ITransportClient, 
Runnable {
 
   private int port = -1;
 
-  private String uuid = null;
-
   private IdentityInfo identityInfo = null;
 
   private Pipe pipe = null;
@@ -91,7 +100,6 @@ public class TransportClient implements ITransportClient, 
Runnable {
   public void setServerConfig(String ipAddress, int port) throws IOException {
     this.ipAddress = ipAddress;
     this.port = port;
-    this.uuid = getOrCreateUUID(getUuidFile());
   }
 
   public TransportClient(Pipe pipe, String ipAddress, int port) throws 
IOException {
@@ -101,7 +109,6 @@ public class TransportClient implements ITransportClient, 
Runnable {
     this.pipe = pipe;
     this.ipAddress = ipAddress;
     this.port = port;
-    this.uuid = getOrCreateUUID(getUuidFile());
 
     handshake();
   }
@@ -146,7 +153,8 @@ public class TransportClient implements ITransportClient, 
Runnable {
       identityInfo =
           new IdentityInfo(
               socket.getLocalAddress().getHostAddress(),
-              this.uuid,
+              pipe.getName(),
+              pipe.getCreateTime(),
               ioTDBConfig.getIoTDBMajorVersion());
       TransportStatus status = serviceClient.handshake(identityInfo);
       if (status.code != SUCCESS_CODE) {
@@ -165,7 +173,7 @@ public class TransportClient implements ITransportClient, 
Runnable {
     return true;
   }
 
-  private boolean senderTransport(PipeData pipeData) {
+  public boolean senderTransport(PipeData pipeData) {
 
     int retryCount = 0;
 
@@ -272,17 +280,15 @@ public class TransportClient implements ITransportClient, 
Runnable {
       }
 
       int dataLength;
-      try (RandomAccessFile randomAccessFile = new RandomAccessFile(file, "r");
-          ByteArrayOutputStream byteArrayOutputStream =
-              new ByteArrayOutputStream(TransportConstant.DATA_CHUNK_SIZE)) {
-
+      try (RandomAccessFile randomAccessFile = new RandomAccessFile(file, 
"r")) {
+        if (randomAccessFile.length() <= position) {
+          break;
+        }
         randomAccessFile.seek(position);
         while ((dataLength = randomAccessFile.read(buffer)) != -1) {
           messageDigest.reset();
-          byteArrayOutputStream.write(buffer, 0, dataLength);
           messageDigest.update(buffer, 0, dataLength);
-          ByteBuffer buffToSend = 
ByteBuffer.wrap(byteArrayOutputStream.toByteArray());
-          byteArrayOutputStream.reset();
+          ByteBuffer buffToSend = ByteBuffer.wrap(buffer, 0, dataLength);
           MetaInfo metaInfo = new MetaInfo(Type.FILE, file.getName(), 
position);
 
           TransportStatus status = null;
@@ -351,16 +357,11 @@ public class TransportClient implements ITransportClient, 
Runnable {
                 "Can not sync pipe data after %s tries.", 
config.getMaxNumOfSyncFileRetry()));
       }
 
-      try (ByteArrayOutputStream byteArrayOutputStream = new 
ByteArrayOutputStream();
-          DataOutputStream dataOutputStream = new 
DataOutputStream(byteArrayOutputStream)) {
-        int dataLength = new 
Long(pipeData.serialize(dataOutputStream)).intValue();
-        byte[] buffer = new byte[dataLength];
-
-        byteArrayOutputStream.write(buffer, 0, dataLength);
+      try {
+        byte[] buffer = pipeData.serialize();
         messageDigest.reset();
-        messageDigest.update(buffer, 0, dataLength);
-        ByteBuffer buffToSend = 
ByteBuffer.wrap(byteArrayOutputStream.toByteArray());
-        byteArrayOutputStream.reset();
+        messageDigest.update(buffer);
+        ByteBuffer buffToSend = ByteBuffer.wrap(buffer);
 
         MetaInfo metaInfo =
             new MetaInfo(Type.findByValue(pipeData.getType().ordinal()), 
"fileName", 0);
@@ -380,49 +381,6 @@ public class TransportClient implements ITransportClient, 
Runnable {
     }
   }
 
-  /** UUID marks the identity of sender for receiver. */
-  private String getOrCreateUUID(File uuidFile) throws IOException {
-    if (!uuidFile.getParentFile().exists()) {
-      uuidFile.getParentFile().mkdirs();
-    }
-
-    String uuid;
-    if (uuidFile.exists()) {
-      try (BufferedReader bf = new BufferedReader((new FileReader(uuidFile)))) 
{
-        uuid = bf.readLine();
-      } catch (IOException e) {
-        logger.error("Cannot read UUID from file {}", uuidFile.getPath());
-        throw new IOException(e);
-      }
-
-      if ((uuid == null) || (uuid.length() == 0)) {
-        logger.warn("UUID in file {} is empty.", uuidFile.getPath());
-        uuidFile.delete();
-      } else {
-        return uuid;
-      }
-    }
-
-    // uuidFile not exist or uuid in uuidFile is invalid
-    try (FileOutputStream out = new FileOutputStream(uuidFile)) {
-      uuid = generateUUID();
-      out.write(uuid.getBytes());
-    } catch (IOException e) {
-      logger.error("Cannot insert UUID to file {}", uuidFile.getPath());
-      throw new IOException(e);
-    }
-
-    return uuid;
-  }
-
-  private String generateUUID() {
-    return UUID.randomUUID().toString().replaceAll("-", "");
-  }
-
-  private File getUuidFile() {
-    return new File(ioTDBConfig.getSyncDir(), SyncConstant.UUID_FILE_NAME);
-  }
-
   /**
    * When an object implementing interface <code>Runnable</code> is used to 
create a thread,
    * starting the thread causes the object's <code>run</code> method to be 
called in that separately
@@ -471,21 +429,25 @@ public class TransportClient implements ITransportClient, 
Runnable {
       return;
     }
 
-    // Example 1. Send TSFILE.
-    //    List<File> files = new ArrayList<>();
-    //    files.add(new File(System.getProperty(IoTDBConstant.IOTDB_HOME) + 
"/files/test1"));
-    //    files.add(new File(System.getProperty(IoTDBConstant.IOTDB_HOME) + 
"/files/test2"));
-    //    files.add(new File(System.getProperty(IoTDBConstant.IOTDB_HOME) + 
"/files/test3"));
+    //     Example 1. Send TSFILE.
+    //        List<File> files = new ArrayList<>();
+    //        files.add(new File(System.getProperty(IoTDBConstant.IOTDB_HOME) 
+ "/files/test1"));
+    //        files.add(new File(System.getProperty(IoTDBConstant.IOTDB_HOME) 
+ "/files/test2"));
+    //        files.add(new File(System.getProperty(IoTDBConstant.IOTDB_HOME) 
+ "/files/test3"));
+
+    //     if (!TransportClient.getInstance().senderTransport()) {
+    //     Deal with the error here.
+    //     }
 
-    // if (!TransportClient.getInstance().senderTransport()) {
-    // Deal with the error here.
-    // }
+    //     Example 2. Send DELETION
+    //     TsFilePipeData.Type.DELETION.name();
 
-    // Example 2. Send DELETION
-    // TsFilePipeData.Type.DELETION.name();
+    //     Example 3. Send PHYSICALPLAN
+    //     TsFilePipeData.Type.PHYSICALPLAN.name();
+  }
 
-    // Example 3. Send PHYSICALPLAN
-    // TsFilePipeData.Type.PHYSICALPLAN.name();
+  public void close() {
+    transport.close();
   }
 
   private static class InstanceHolder {
diff --git 
a/server/src/main/java/org/apache/iotdb/db/newsync/transport/conf/TransportConfig.java
 
b/server/src/main/java/org/apache/iotdb/db/newsync/transport/conf/TransportConfig.java
index 316f6f5..e9af083 100644
--- 
a/server/src/main/java/org/apache/iotdb/db/newsync/transport/conf/TransportConfig.java
+++ 
b/server/src/main/java/org/apache/iotdb/db/newsync/transport/conf/TransportConfig.java
@@ -1,3 +1,22 @@
+/*
+ * 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.db.newsync.transport.conf;
 
 import org.apache.iotdb.db.conf.IoTDBConstant;
diff --git 
a/server/src/main/java/org/apache/iotdb/db/newsync/transport/conf/TransportConstant.java
 
b/server/src/main/java/org/apache/iotdb/db/newsync/transport/conf/TransportConstant.java
index daf1d0d..7d575c7 100644
--- 
a/server/src/main/java/org/apache/iotdb/db/newsync/transport/conf/TransportConstant.java
+++ 
b/server/src/main/java/org/apache/iotdb/db/newsync/transport/conf/TransportConstant.java
@@ -1,3 +1,22 @@
+/*
+ * 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.db.newsync.transport.conf;
 
 import org.apache.iotdb.rpc.RpcUtils;
diff --git 
a/server/src/main/java/org/apache/iotdb/db/newsync/transport/server/TransportServerManager.java
 
b/server/src/main/java/org/apache/iotdb/db/newsync/transport/server/TransportServerManager.java
index 7f9a540..c9d8c64 100644
--- 
a/server/src/main/java/org/apache/iotdb/db/newsync/transport/server/TransportServerManager.java
+++ 
b/server/src/main/java/org/apache/iotdb/db/newsync/transport/server/TransportServerManager.java
@@ -1,3 +1,22 @@
+/*
+ * 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.db.newsync.transport.server;
 
 import org.apache.iotdb.db.concurrent.ThreadName;
@@ -92,18 +111,18 @@ public class TransportServerManager extends ThriftService
   @Override
   public void startService() throws StartupException {
     // TODO: Whether to change this config here
-    if (!IoTDBDescriptor.getInstance().getConfig().isSyncEnable()) {
-      return;
-    }
+    //    if (!IoTDBDescriptor.getInstance().getConfig().isSyncEnable()) {
+    //      return;
+    //    }
     super.startService();
   }
 
   @Override
   public void stopService() {
     // TODO: Whether to change this config here
-    if (IoTDBDescriptor.getInstance().getConfig().isSyncEnable()) {
-      super.stopService();
-    }
+    //    if (IoTDBDescriptor.getInstance().getConfig().isSyncEnable()) {
+    super.stopService();
+    //    }
   }
 
   @TestOnly
diff --git 
a/server/src/main/java/org/apache/iotdb/db/newsync/transport/server/TransportServerManagerMBean.java
 
b/server/src/main/java/org/apache/iotdb/db/newsync/transport/server/TransportServerManagerMBean.java
index fec1947..ebb892b 100644
--- 
a/server/src/main/java/org/apache/iotdb/db/newsync/transport/server/TransportServerManagerMBean.java
+++ 
b/server/src/main/java/org/apache/iotdb/db/newsync/transport/server/TransportServerManagerMBean.java
@@ -1,3 +1,22 @@
+/*
+ * 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.db.newsync.transport.server;
 
 import org.apache.iotdb.db.exception.StartupException;
diff --git 
a/server/src/main/java/org/apache/iotdb/db/newsync/transport/server/TransportServerThriftHandler.java
 
b/server/src/main/java/org/apache/iotdb/db/newsync/transport/server/TransportServerThriftHandler.java
index 8a3898c..5815317 100644
--- 
a/server/src/main/java/org/apache/iotdb/db/newsync/transport/server/TransportServerThriftHandler.java
+++ 
b/server/src/main/java/org/apache/iotdb/db/newsync/transport/server/TransportServerThriftHandler.java
@@ -1,3 +1,22 @@
+/*
+ * 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.db.newsync.transport.server;
 
 import org.apache.thrift.protocol.TProtocol;
@@ -9,7 +28,7 @@ public class TransportServerThriftHandler implements 
TServerEventHandler {
 
   private TransportServiceImpl serviceImpl;
 
-  TransportServerThriftHandler(TransportServiceImpl serviceImpl) {
+  public TransportServerThriftHandler(TransportServiceImpl serviceImpl) {
     this.serviceImpl = serviceImpl;
   }
 
diff --git 
a/server/src/main/java/org/apache/iotdb/db/newsync/transport/server/TransportServiceImpl.java
 
b/server/src/main/java/org/apache/iotdb/db/newsync/transport/server/TransportServiceImpl.java
index 0160cf3..cdfa9db 100644
--- 
a/server/src/main/java/org/apache/iotdb/db/newsync/transport/server/TransportServiceImpl.java
+++ 
b/server/src/main/java/org/apache/iotdb/db/newsync/transport/server/TransportServiceImpl.java
@@ -1,9 +1,31 @@
+/*
+ * 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.db.newsync.transport.server;
 
 import org.apache.iotdb.db.conf.IoTDBConfig;
 import org.apache.iotdb.db.conf.IoTDBDescriptor;
 import org.apache.iotdb.db.exception.metadata.IllegalPathException;
+import org.apache.iotdb.db.newsync.conf.SyncPathUtil;
 import org.apache.iotdb.db.newsync.pipedata.PipeData;
+import org.apache.iotdb.db.newsync.pipedata.TsFilePipeData;
+import org.apache.iotdb.db.newsync.pipedata.queue.PipeDataQueueFactory;
 import org.apache.iotdb.service.transport.thrift.IdentityInfo;
 import org.apache.iotdb.service.transport.thrift.MetaInfo;
 import org.apache.iotdb.service.transport.thrift.SyncRequest;
@@ -16,16 +38,7 @@ import org.apache.thrift.TException;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 
-import java.io.BufferedReader;
-import java.io.ByteArrayInputStream;
-import java.io.DataInputStream;
-import java.io.File;
-import java.io.FileInputStream;
-import java.io.FileWriter;
-import java.io.IOException;
-import java.io.InputStream;
-import java.io.InputStreamReader;
-import java.io.RandomAccessFile;
+import java.io.*;
 import java.math.BigInteger;
 import java.nio.ByteBuffer;
 import java.nio.file.Files;
@@ -34,7 +47,6 @@ import java.security.MessageDigest;
 import java.security.NoSuchAlgorithmException;
 import java.util.Arrays;
 
-import static 
org.apache.iotdb.db.newsync.transport.conf.TransportConfig.getSyncedDir;
 import static 
org.apache.iotdb.db.newsync.transport.conf.TransportConstant.CONFLICT_CODE;
 import static 
org.apache.iotdb.db.newsync.transport.conf.TransportConstant.ERROR_CODE;
 import static 
org.apache.iotdb.db.newsync.transport.conf.TransportConstant.REBASE_CODE;
@@ -46,6 +58,8 @@ public class TransportServiceImpl implements 
TransportService.Iface {
   private static Logger logger = 
LoggerFactory.getLogger(TransportServiceImpl.class);
 
   private IoTDBConfig config = IoTDBDescriptor.getInstance().getConfig();
+  private static final String RECORD_SUFFIX = ".record";
+  private static final String PATCH_SUFFIX = ".patch";
 
   private class CheckResult {
     boolean result;
@@ -66,7 +80,7 @@ public class TransportServiceImpl implements 
TransportService.Iface {
   }
 
   private CheckResult checkStartIndexValid(File file, long startIndex) throws 
IOException {
-    File recordFile = new File(file.getAbsolutePath() + ".record");
+    File recordFile = new File(file.getAbsolutePath() + RECORD_SUFFIX);
 
     if (!recordFile.exists() && startIndex != 0) {
       logger.error(
@@ -121,8 +135,8 @@ public class TransportServiceImpl implements 
TransportService.Iface {
               identityInfo.version, config.getIoTDBVersion()));
     }
 
-    if (!new File(getSyncedDir(identityInfo.getAddress(), 
identityInfo.getUuid())).exists()) {
-      new File(getSyncedDir(identityInfo.getAddress(), 
identityInfo.getUuid())).mkdirs();
+    if (!new File(getFileDataDirPath(identityInfo)).exists()) {
+      new File(getFileDataDirPath(identityInfo)).mkdirs();
     }
     return new TransportStatus(SUCCESS_CODE, "");
   }
@@ -132,82 +146,79 @@ public class TransportServiceImpl implements 
TransportService.Iface {
       IdentityInfo identityInfo, MetaInfo metaInfo, ByteBuffer buff, 
ByteBuffer digest) {
     logger.debug("Invoke transportData method from client ip = {}", 
identityInfo.address);
 
-    String ipAddress = identityInfo.address;
-    String uuid = identityInfo.uuid;
-    synchronized (uuid.intern()) {
-      Type type = metaInfo.type;
-      String fileName = metaInfo.fileName;
-      long startIndex = metaInfo.startIndex;
-
-      // Check file start index valid
-      if (type == Type.FILE) {
-        try {
-          CheckResult result =
-              checkStartIndexValid(new File(getSyncedDir(ipAddress, uuid), 
fileName), startIndex);
-          if (!result.isResult()) {
-            return new TransportStatus(REBASE_CODE, result.getIndex());
-          }
-        } catch (IOException e) {
-          logger.error(e.getMessage());
-          return new TransportStatus(ERROR_CODE, e.getMessage());
-        }
-      }
+    String fileDir = getFileDataDirPath(identityInfo);
+    Type type = metaInfo.type;
+    String fileName = metaInfo.fileName;
+    long startIndex = metaInfo.startIndex;
 
-      // Check buff digest
-      int pos = buff.position();
-      MessageDigest messageDigest = null;
+    // Check file start index valid
+    if (type == Type.FILE) {
       try {
-        messageDigest = MessageDigest.getInstance("SHA-256");
-      } catch (NoSuchAlgorithmException e) {
+        CheckResult result = checkStartIndexValid(new File(fileDir, fileName), 
startIndex);
+        if (!result.isResult()) {
+          return new TransportStatus(REBASE_CODE, result.getIndex());
+        }
+      } catch (IOException e) {
         logger.error(e.getMessage());
         return new TransportStatus(ERROR_CODE, e.getMessage());
       }
-      messageDigest.update(buff);
-      byte[] digestBytes = new byte[digest.capacity()];
-      digest.get(digestBytes);
-      if (!Arrays.equals(messageDigest.digest(), digestBytes)) {
-        return new TransportStatus(RETRY_CODE, "Data digest check error, 
retry.");
-      }
+    }
 
-      if (type != Type.FILE) {
+    // Check buff digest
+    int pos = buff.position();
+    MessageDigest messageDigest = null;
+    try {
+      messageDigest = MessageDigest.getInstance("SHA-256");
+    } catch (NoSuchAlgorithmException e) {
+      logger.error(e.getMessage());
+      return new TransportStatus(ERROR_CODE, e.getMessage());
+    }
+    messageDigest.update(buff);
+    byte[] digestBytes = new byte[digest.capacity()];
+    digest.get(digestBytes);
+    if (!Arrays.equals(messageDigest.digest(), digestBytes)) {
+      return new TransportStatus(RETRY_CODE, "Data digest check error, 
retry.");
+    }
 
-        buff.position(pos);
+    if (type != Type.FILE) {
+      buff.position(pos);
+      int length = buff.capacity();
+      byte[] byteArray = new byte[length];
+      buff.get(byteArray);
+      try {
+        PipeData pipeData = PipeData.deserialize(byteArray);
+        if (type == Type.TSFILE) {
+          // Do with file
+          handleTsFilePipeData((TsFilePipeData) pipeData, fileDir);
+        }
+        
PipeDataQueueFactory.getBufferedPipeDataQueue(getPipeLogDirPath(identityInfo))
+            .offer(pipeData);
+      } catch (IOException | IllegalPathException e) {
+        logger.error("Pipe data transport error, {}", e.getMessage());
+        return new TransportStatus(RETRY_CODE, "Data digest transport error " 
+ e.getMessage());
+      }
+    } else {
+      // Write buff to {file}.patch
+      buff.position(pos);
+      File file = new File(fileDir, fileName + PATCH_SUFFIX);
+      try (RandomAccessFile randomAccessFile = new RandomAccessFile(file, 
"rw")) {
+        randomAccessFile.seek(startIndex);
         int length = buff.capacity();
         byte[] byteArray = new byte[length];
         buff.get(byteArray);
-        try (InputStream inputStream = new ByteArrayInputStream(byteArray);
-            DataInputStream dataInputStream = new 
DataInputStream(inputStream)) {
-          PipeData pipeData = PipeData.deserialize(dataInputStream);
-          // Do with file
-          // BufferedPipeDataQueue.offer(pipeData);
-        } catch (IOException | IllegalPathException e) {
-          e.printStackTrace();
-        }
-      } else {
-        // Write buff to {file}.patch
-        buff.position(pos);
-        File file = new File(getSyncedDir(ipAddress, uuid), fileName + 
".patch");
-        try (RandomAccessFile randomAccessFile = new RandomAccessFile(file, 
"rw")) {
-          randomAccessFile.seek(startIndex);
-          int length = buff.capacity();
-          byte[] byteArray = new byte[length];
-          buff.get(byteArray);
-          randomAccessFile.write(byteArray);
-          writeRecordFile(
-              new File(getSyncedDir(ipAddress, uuid), fileName + ".record"), 
startIndex + length);
-          logger.debug(
-              "Sync "
-                  + fileName
-                  + " start at "
-                  + startIndex
-                  + " to "
-                  + (startIndex + length)
-                  + " is done.");
-        } catch (IOException e) {
-          logger.error(e.getMessage());
-          e.printStackTrace();
-          return new TransportStatus(ERROR_CODE, e.getMessage());
-        }
+        randomAccessFile.write(byteArray);
+        writeRecordFile(new File(fileDir, fileName + RECORD_SUFFIX), 
startIndex + length);
+        logger.debug(
+            "Sync "
+                + fileName
+                + " start at "
+                + startIndex
+                + " to "
+                + (startIndex + length)
+                + " is done.");
+      } catch (IOException e) {
+        logger.error(e.getMessage());
+        return new TransportStatus(ERROR_CODE, e.getMessage());
       }
     }
     return new TransportStatus(SUCCESS_CODE, "");
@@ -218,9 +229,8 @@ public class TransportServiceImpl implements 
TransportService.Iface {
       IdentityInfo identityInfo, MetaInfo metaInfo, ByteBuffer digest) throws 
TException {
     logger.debug("Invoke checkFileDigest method from client ip = {}", 
identityInfo.address);
 
-    String ipAddress = identityInfo.getAddress();
-    String uuid = identityInfo.getUuid();
-    synchronized (uuid.intern()) {
+    String fileDir = getFileDataDirPath(identityInfo);
+    synchronized (fileDir.intern()) {
       String fileName = metaInfo.fileName;
       MessageDigest messageDigest = null;
       try {
@@ -231,7 +241,7 @@ public class TransportServiceImpl implements 
TransportService.Iface {
       }
 
       try (InputStream inputStream =
-          new FileInputStream(new File(getSyncedDir(ipAddress, uuid), fileName 
+ ".patch"))) {
+          new FileInputStream(new File(fileDir, fileName + PATCH_SUFFIX))) {
         byte[] block = new byte[DATA_CHUNK_SIZE];
         int length;
         while ((length = inputStream.read(block)) > 0) {
@@ -248,11 +258,11 @@ public class TransportServiceImpl implements 
TransportService.Iface {
               fileName,
               localDigest,
               digest);
-          new File(getSyncedDir(ipAddress, uuid), fileName + 
".record").delete();
+          new File(fileDir, fileName + RECORD_SUFFIX).delete();
           return new TransportStatus(CONFLICT_CODE, "File digest check 
error.");
         }
       } catch (IOException e) {
-        e.printStackTrace();
+        logger.error(e.getMessage());
         return new TransportStatus(ERROR_CODE, e.getMessage());
       }
 
@@ -283,4 +293,41 @@ public class TransportServiceImpl implements 
TransportService.Iface {
     // TODO: Handle client exit here.
     // do nothing now
   }
+
+  /**
+   * handle when successfully receive tsFilePipeData. Rename .patch file and 
reset tsFilePipeData's
+   * path.
+   *
+   * @param tsFilePipeData pipeData
+   * @param fileDir path of file data dir
+   */
+  private void handleTsFilePipeData(TsFilePipeData tsFilePipeData, String 
fileDir) {
+    String tsFileName = tsFilePipeData.getTsFileName();
+    File dir = new File(fileDir);
+    File[] targetFiles =
+        dir.listFiles((dir1, name) -> name.startsWith(tsFileName) && 
name.endsWith(PATCH_SUFFIX));
+    // TODO: same name ?
+    if (targetFiles != null) {
+      for (File targetFile : targetFiles) {
+        File newFile =
+            new File(
+                dir,
+                targetFile
+                    .getName()
+                    .substring(0, targetFile.getName().length() - 
PATCH_SUFFIX.length()));
+        targetFile.renameTo(newFile);
+      }
+    }
+    tsFilePipeData.setParentDirPath(dir.getAbsolutePath());
+  }
+
+  private String getFileDataDirPath(IdentityInfo identityInfo) {
+    return SyncPathUtil.getReceiverFileDataDir(
+        identityInfo.getPipeName(), identityInfo.getAddress(), 
identityInfo.getCreateTime());
+  }
+
+  private String getPipeLogDirPath(IdentityInfo identityInfo) {
+    return SyncPathUtil.getReceiverPipeLogDir(
+        identityInfo.getPipeName(), identityInfo.getAddress(), 
identityInfo.getCreateTime());
+  }
 }
diff --git 
a/server/src/test/java/org/apache/iotdb/db/newsync/pipedata/BufferedPipeDataQueueTest.java
 
b/server/src/test/java/org/apache/iotdb/db/newsync/pipedata/BufferedPipeDataQueueTest.java
index 33afae8..e187cce 100644
--- 
a/server/src/test/java/org/apache/iotdb/db/newsync/pipedata/BufferedPipeDataQueueTest.java
+++ 
b/server/src/test/java/org/apache/iotdb/db/newsync/pipedata/BufferedPipeDataQueueTest.java
@@ -74,7 +74,7 @@ public class BufferedPipeDataQueueTest {
               new FileOutputStream(
                   new File(pipeLogDir.getPath(), 
SyncConstant.getPipeLogName(0)), false));
       for (int i = 0; i < 4; i++) {
-        new TsFilePipeData(null, i).serialize(pipeLogOutput1);
+        new TsFilePipeData("", i).serialize(pipeLogOutput1);
       }
       pipeLogOutput1.close();
       // pipelog2: 4~10
@@ -83,7 +83,7 @@ public class BufferedPipeDataQueueTest {
               new FileOutputStream(
                   new File(pipeLogDir.getPath(), 
SyncConstant.getPipeLogName(4)), false));
       for (int i = 4; i < 11; i++) {
-        new TsFilePipeData(null, i).serialize(pipeLogOutput2);
+        new TsFilePipeData("", i).serialize(pipeLogOutput2);
       }
       pipeLogOutput2.close();
       // pipelog3: 11 without pipedata
@@ -99,12 +99,12 @@ public class BufferedPipeDataQueueTest {
       pipeDataQueue.clear();
       Assert.assertFalse(pipeLogDir.exists());
     } catch (Exception e) {
-      Assert.fail();
+      e.printStackTrace();
+      Assert.fail(e.getMessage());
     }
   }
 
   /** Try to take data from a new pipe. Expect to wait indefinitely if no data 
offer. */
-  // TODO: 抛出NPE
   @Test
   public void testTake() {
     BufferedPipeDataQueue pipeDataQueue = new 
BufferedPipeDataQueue(pipeLogDir.getPath());
@@ -142,7 +142,7 @@ public class BufferedPipeDataQueueTest {
             Thread.currentThread().interrupt();
           }
         });
-    pipeDataQueue.offer(new TsFilePipeData(null, 0));
+    pipeDataQueue.offer(new TsFilePipeData("", 0));
     try {
       Thread.sleep(3000);
     } catch (InterruptedException e) {
@@ -244,7 +244,7 @@ public class BufferedPipeDataQueueTest {
       BufferedPipeDataQueue pipeDataQueue = new 
BufferedPipeDataQueue(pipeLogDir.getPath());
       Assert.assertEquals(1, pipeDataQueue.getCommitSerialNumber());
       Assert.assertEquals(10, pipeDataQueue.getLastMaxSerialNumber());
-      PipeData offerPipeData = new TsFilePipeData(null, 11);
+      PipeData offerPipeData = new TsFilePipeData("", 11);
       pipeDataList.add(offerPipeData);
       pipeDataQueue.offer(offerPipeData);
 
diff --git 
a/server/src/test/java/org/apache/iotdb/db/newsync/transport/TransportServiceTest.java
 
b/server/src/test/java/org/apache/iotdb/db/newsync/transport/TransportServiceTest.java
new file mode 100644
index 0000000..8e4d4d0
--- /dev/null
+++ 
b/server/src/test/java/org/apache/iotdb/db/newsync/transport/TransportServiceTest.java
@@ -0,0 +1,196 @@
+/*
+ * 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.db.newsync.transport;
+
+import org.apache.iotdb.db.engine.modification.Deletion;
+import org.apache.iotdb.db.engine.modification.ModificationFile;
+import org.apache.iotdb.db.engine.storagegroup.TsFileResource;
+import org.apache.iotdb.db.metadata.path.PartialPath;
+import org.apache.iotdb.db.newsync.conf.SyncPathUtil;
+import org.apache.iotdb.db.newsync.pipedata.DeletionPipeData;
+import org.apache.iotdb.db.newsync.pipedata.PipeData;
+import org.apache.iotdb.db.newsync.pipedata.SchemaPipeData;
+import org.apache.iotdb.db.newsync.pipedata.TsFilePipeData;
+import org.apache.iotdb.db.newsync.pipedata.queue.PipeDataQueue;
+import org.apache.iotdb.db.newsync.pipedata.queue.PipeDataQueueFactory;
+import org.apache.iotdb.db.newsync.sender.pipe.Pipe;
+import org.apache.iotdb.db.newsync.sender.pipe.TsFilePipe;
+import org.apache.iotdb.db.newsync.transport.client.TransportClient;
+import org.apache.iotdb.db.newsync.transport.server.TransportServerManager;
+import org.apache.iotdb.db.qp.physical.sys.CreateTimeSeriesPlan;
+import org.apache.iotdb.db.qp.physical.sys.SetStorageGroupPlan;
+import org.apache.iotdb.db.utils.EnvironmentUtils;
+import org.apache.iotdb.tsfile.file.metadata.enums.TSDataType;
+import org.apache.iotdb.tsfile.file.metadata.enums.TSEncoding;
+import org.apache.iotdb.tsfile.write.schema.MeasurementSchema;
+
+import org.apache.commons.io.FileUtils;
+import org.junit.After;
+import org.junit.Assert;
+import org.junit.Before;
+import org.junit.Test;
+
+import java.io.*;
+import java.security.MessageDigest;
+import java.util.ArrayList;
+import java.util.List;
+import java.util.concurrent.ExecutorService;
+import java.util.concurrent.Executors;
+
+public class TransportServiceTest {
+  /** create tsfile and move to tmpDir for sync test */
+  File tmpDir = new File("target/synctest");
+
+  String pipeName1 = "pipe1";
+  String remoteIp1 = "127.0.0.1";
+  long createdTime1 = System.currentTimeMillis();
+  File fileDir = new File(SyncPathUtil.getReceiverFileDataDir(pipeName1, 
remoteIp1, createdTime1));
+  PipeDataQueue pipeDataQueue =
+      PipeDataQueueFactory.getBufferedPipeDataQueue(
+          SyncPathUtil.getReceiverPipeLogDir(pipeName1, remoteIp1, 
createdTime1));
+
+  @Before
+  public void setUp() throws Exception {
+    EnvironmentUtils.envSetUp();
+    if (!tmpDir.exists()) {
+      tmpDir.mkdirs();
+    }
+  }
+
+  @After
+  public void tearDown() throws Exception {
+    pipeDataQueue.clear();
+    FileUtils.deleteDirectory(tmpDir);
+    EnvironmentUtils.cleanEnv();
+  }
+
+  @Test
+  public void test() throws Exception {
+    // 1. prepare fake file
+    File tsfile = new File(tmpDir, "test.tsfile");
+    File resourceFile = new File(tsfile.getAbsoluteFile() + 
TsFileResource.RESOURCE_SUFFIX);
+    File modsFile = new File(tsfile.getAbsoluteFile() + 
ModificationFile.FILE_SUFFIX);
+    FileWriter out = new FileWriter(tsfile);
+    out.write("tsfile");
+    out.flush();
+    out.close();
+    out = new FileWriter(resourceFile);
+    out.write("resource");
+    out.flush();
+    out.close();
+    out = new FileWriter(modsFile);
+    out.write("mods");
+    out.flush();
+    out.close();
+
+    // 2. prepare pipelog and pipeDataQueue
+    int serialNum = 0;
+    List<PipeData> pipeDataList = new ArrayList<>();
+    pipeDataList.add(
+        new SchemaPipeData(new SetStorageGroupPlan(new 
PartialPath("root.vehicle")), serialNum++));
+    pipeDataList.add(
+        new SchemaPipeData(
+            new CreateTimeSeriesPlan(
+                new PartialPath("root.vehicle.d0.s0"),
+                new MeasurementSchema("s0", TSDataType.INT32, TSEncoding.RLE)),
+            serialNum++));
+    TsFilePipeData tsFilePipeData = new TsFilePipeData(tsfile.getPath(), 
serialNum++);
+    pipeDataList.add(tsFilePipeData);
+    Deletion deletion = new Deletion(new PartialPath("root.vehicle.**"), 0, 
33, 38);
+    pipeDataList.add(new DeletionPipeData(deletion, serialNum++));
+
+    // 3. start server
+    TransportServerManager.getInstance().startService();
+
+    // 4. start client
+    Pipe pipe = new TsFilePipe(createdTime1, pipeName1, null, 0, false);
+    TransportClient client = new TransportClient(pipe, "127.0.0.1", 5555);
+    for (PipeData pipeData : pipeDataList) {
+      client.senderTransport(pipeData);
+    }
+
+    // 5. check file
+    Thread.sleep(1000);
+    client.close();
+    TransportServerManager.getInstance().stopService();
+    File[] targetFiles = fileDir.listFiles((dir1, name) -> 
name.equals(tsfile.getName()));
+    Assert.assertNotNull(targetFiles);
+    Assert.assertEquals(1, targetFiles.length);
+    compareFile(targetFiles[0], tsfile);
+    File[] resourceFiles = fileDir.listFiles((dir1, name) -> 
name.equals(resourceFile.getName()));
+    Assert.assertNotNull(resourceFiles);
+    Assert.assertEquals(1, resourceFiles.length);
+    compareFile(resourceFiles[0], resourceFile);
+    File[] modsFiles = fileDir.listFiles((dir1, name) -> 
name.equals(modsFile.getName()));
+    Assert.assertNotNull(modsFiles);
+    Assert.assertEquals(1, modsFiles.length);
+    compareFile(modsFiles[0], modsFile);
+
+    // 6. check pipedata
+    tsFilePipeData.setParentDirPath(fileDir.getAbsolutePath());
+    ExecutorService es1 = Executors.newSingleThreadExecutor();
+    List<PipeData> resPipeData = new ArrayList<>();
+    es1.execute(
+        () -> {
+          for (int i = 0; i < pipeDataList.size(); i++) {
+            try {
+              resPipeData.add(pipeDataQueue.take());
+              pipeDataQueue.commit();
+            } catch (InterruptedException e) {
+              Thread.currentThread().interrupt();
+            }
+          }
+        });
+    try {
+      Thread.sleep(500);
+    } catch (InterruptedException e) {
+      e.printStackTrace();
+    }
+    es1.shutdownNow();
+    Assert.assertEquals(pipeDataList.size(), resPipeData.size());
+    for (int i = 0; i < resPipeData.size(); i++) {
+      Assert.assertEquals(pipeDataList.get(i), resPipeData.get(i));
+    }
+  }
+
+  private void compareFile(File firFile, File secFile) {
+    try {
+      MessageDigest messageDigest1 = MessageDigest.getInstance("SHA-256");
+      MessageDigest messageDigest2 = MessageDigest.getInstance("SHA-256");
+      BufferedInputStream fir = new BufferedInputStream(new 
FileInputStream(firFile));
+      BufferedInputStream sec = new BufferedInputStream(new 
FileInputStream(secFile));
+      // To compare the length and hash of the files.
+      Assert.assertEquals(fir.available(), sec.available());
+      byte[] firstBytes = new byte[1024];
+      byte[] secondBytes = new byte[1024];
+      int length = -1;
+      while ((length = fir.read(firstBytes)) != -1) {
+        Assert.assertEquals(length, sec.read(secondBytes));
+        messageDigest1.update(firstBytes, 0, length);
+        messageDigest2.update(secondBytes, 0, length);
+      }
+      fir.close();
+      sec.close();
+      Assert.assertArrayEquals(messageDigest1.digest(), 
messageDigest2.digest());
+    } catch (Exception e) {
+      Assert.fail(e.getMessage());
+    }
+  }
+}
diff --git a/thrift-sync/src/main/thrift/transport.thrift 
b/thrift-sync/src/main/thrift/transport.thrift
index 3eccde3..c84452c 100644
--- a/thrift-sync/src/main/thrift/transport.thrift
+++ b/thrift-sync/src/main/thrift/transport.thrift
@@ -30,10 +30,12 @@ struct IdentityInfo{
   1:required string address
 
   // Sender needs to tell receiver its identity.
-  2:required string uuid
+  2:required string pipeName
+  3:required i64 createTime
 
   // The version of sender and receiver need to be the same.
-  3:required string version
+  4:required string version
+
 }
 
 enum Type {
@@ -43,6 +45,20 @@ enum Type {
   FILE
 }
 
+enum RequestType {
+  CREATE,
+  START,
+  STOP,
+  DROP,
+  HEARTBEAT
+}
+
+enum ResponseType {
+  INFO,
+  WARN,
+  ERROR
+}
+
 struct MetaInfo{
   // The type of the pipeData in sending.
   1:required Type type
@@ -55,12 +71,14 @@ struct MetaInfo{
 }
 
 struct SyncRequest{
-  1:required i32 code
-  2:required string msg
+  1:required RequestType type
+  2:required string pipeName
+  3:required string remoteIp
+  4:required i64 createTime
 }
 
 struct SyncResponse{
-  1:required i32 code
+  1:required ResponseType type
   2:required string msg
 }
 

Reply via email to