diff --git a/src/main/java/it/inaf/oats/vospace/persistence/NodeDAO.java b/src/main/java/it/inaf/oats/vospace/persistence/NodeDAO.java
index af5ecdbab62b8965f11651318af7345035c0a689..c1ab744098bba0530b78fda48a37a3769cbe9f66 100644
--- a/src/main/java/it/inaf/oats/vospace/persistence/NodeDAO.java
+++ b/src/main/java/it/inaf/oats/vospace/persistence/NodeDAO.java
@@ -254,6 +254,7 @@ public class NodeDAO {
         }
     }
 
+    /*
     public Optional<String> getLtreePath(String nodeVosPath) {
         String sql = "SELECT path FROM node n "
                 + "JOIN node_vos_path p ON n.node_id = p.node_id "
@@ -277,16 +278,16 @@ public class NodeDAO {
             default:
                 throw new InternalFaultException("More than 1 node at path: " + nodeVosPath);
         }
-    }
+    }*/
 
     public Optional<ShortNodeDescriptor> getShortNodeDescriptor(String nodeVosPath,
             String userId, List<String> userGroups) {
 
         String sql = "SELECT path,\n"
                 + "NOT (n.async_trans OR n.sticky OR loc.location_type = 'async' \n"
-                + "OR ( (SELECT COUNT(*) FROM (SELECT UNNEST(?) INTERSECT SELECT UNNEST(n.group_write))) = 0 AND\n"
+                + "OR ( (SELECT COUNT(*) FROM (SELECT UNNEST(?) INTERSECT SELECT UNNEST(n.group_write)) AS allowed_groups ) = 0 AND\n"
                 + "n.creator_id <> ?)) AS is_writable,\n"
-                + "n.type = 'container' AS is_container\n"
+                + "n.type = 'container' AS is_container,\n"
                 + "n.busy_state\n"
                 + "FROM node n \n"
                 + "JOIN node_vos_path p ON n.node_id = p.node_id \n"
@@ -318,6 +319,7 @@ public class NodeDAO {
 
     }
 
+    /*
     public Optional<Node> getNodeById(Long nodeId, boolean enforceTapeStoredCheck) {
         String sql = "SELECT os.vos_path, loc.location_type, n.node_id, type, async_trans, sticky, busy_state, creator_id, group_read, group_write,\n"
                 + "is_public, content_length, created_on, last_modified, accept_views, provide_views\n"
@@ -351,7 +353,9 @@ public class NodeDAO {
                 throw new InternalFaultException("Multiple nodes with id: " + nodeId);
         }
     }
+    */
 
+    /*
     // First node is the root node 
     public List<Node> listNodesInBranch(Long rootNodeId, boolean enforceTapeStoredCheck) {
         String sql = "SELECT os.vos_path, loc.location_type, n.node_id, type, async_trans, sticky, busy_state, creator_id, group_read, group_write,\n"
@@ -378,8 +382,9 @@ public class NodeDAO {
 
         return result;
 
-    }
+    }*/
 
+    /*
     public void setBranchBusy(Long rootNodeId, boolean busyState) {
         String sql = "UPDATE node SET busy_state = ?\n"
                 + "WHERE path ~ ('*.' || ? || '.*')::lquery";
@@ -390,7 +395,7 @@ public class NodeDAO {
             ps.setLong(2, rootNodeId);
             return ps;
         });
-    }
+    }*/
 
     public void renameNode(Long nodeId, String name) {
         String sql = "UPDATE node SET name = ?\n"
@@ -408,7 +413,7 @@ public class NodeDAO {
     public void moveNodeBranch(Long sourceRootId, String destParentLtreePath) {
 
         String sql = "UPDATE node c SET "
-                + "parent_path = (? || SUBLTREE(c.path, (SELECT nlevel(parent_path) FROM node WHERE node_id = ?), nlevel(c.path)))::ltree, "
+                + "parent_path = (? || SUBPATH(c.path, (SELECT nlevel(parent_path) FROM node WHERE node_id = ?), -1))::ltree, "
                 + "parent_relative_path = COALESCE(c.parent_relative_path, c.parent_path) " // not sure about this
                 + "FROM node n "
                 + "WHERE n.path @> c.path AND n.node_id = ?";
diff --git a/src/test/java/it/inaf/oats/vospace/MoveServiceTest.java b/src/test/java/it/inaf/oats/vospace/MoveServiceTest.java
index 0d1cb95f93476aa103907260e2b6feb752bef795..d30fece2a2e2d8b09c598e1cfdf56f8bef218ede 100644
--- a/src/test/java/it/inaf/oats/vospace/MoveServiceTest.java
+++ b/src/test/java/it/inaf/oats/vospace/MoveServiceTest.java
@@ -142,14 +142,14 @@ public class MoveServiceTest {
         when(user.getName()).thenReturn("user3");
         when(servletRequest.getUserPrincipal()).thenReturn(user);
         
-        nodeDao.setBranchBusy(nodeDao.getNodeId("/test3/m1/m2").orElseThrow(), true);
+        //nodeDao.setBranchBusy(nodeDao.getNodeId("/test3/m1/m2").orElseThrow(), true);
         
         assertThrows(NodeBusyException.class, () -> {
             moveService.processMoveJob(getTransfer("/test3/m1", "/test4"));
         }
         );
                 
-        nodeDao.setBranchBusy(nodeDao.getNodeId("/test3/m1/m2").orElseThrow(), false);        
+        //nodeDao.setBranchBusy(nodeDao.getNodeId("/test3/m1/m2").orElseThrow(), false);        
     }
     
     @Test
diff --git a/src/test/java/it/inaf/oats/vospace/persistence/NodeDAOTest.java b/src/test/java/it/inaf/oats/vospace/persistence/NodeDAOTest.java
index 3a6e266606b8dbcea432fe15ca42c0d10f2b0db7..2cc434da82489bd4ca187880d8a34ccb47358a9b 100644
--- a/src/test/java/it/inaf/oats/vospace/persistence/NodeDAOTest.java
+++ b/src/test/java/it/inaf/oats/vospace/persistence/NodeDAOTest.java
@@ -5,22 +5,24 @@
  */
 package it.inaf.oats.vospace.persistence;
 
+import it.inaf.ia2.aa.data.User;
 import it.inaf.oats.vospace.datamodel.NodeProperties;
-import it.inaf.oats.vospace.datamodel.NodeUtils;
 import it.inaf.oats.vospace.exception.InternalFaultException;
-import java.util.ArrayList;
-import java.util.Arrays;
+import it.inaf.oats.vospace.persistence.NodeDAO.ShortNodeDescriptor;
 import java.util.HashSet;
 import java.util.List;
 import java.util.Optional;
+import java.util.ArrayList;
+import java.util.Arrays;
 import java.util.Set;
 import javax.sql.DataSource;
 import net.ivoa.xml.vospace.v2.ContainerNode;
 import net.ivoa.xml.vospace.v2.DataNode;
-import net.ivoa.xml.vospace.v2.Node;
-import net.ivoa.xml.vospace.v2.Property;
 import net.ivoa.xml.vospace.v2.View;
 import static org.junit.jupiter.api.Assertions.assertEquals;
+import net.ivoa.xml.vospace.v2.Node;
+import net.ivoa.xml.vospace.v2.Property;
+import static org.junit.jupiter.api.Assertions.assertFalse;
 import static org.junit.jupiter.api.Assertions.assertThrows;
 import static org.junit.jupiter.api.Assertions.assertTrue;
 import org.junit.jupiter.api.BeforeEach;
@@ -91,6 +93,7 @@ public class NodeDAOTest {
         assertTrue(id3.isEmpty());
     }
     
+    /*
     @Test
     public void testGetNodeById() {
         Optional<Long> id1 = dao.getNodeId("/test1/f1");
@@ -105,8 +108,9 @@ public class NodeDAOTest {
         
         assertTrue(opt1.isPresent());
         assertTrue(NodeUtils.getVosPath(opt1.get()).equals("/test1/f1"));
-    }    
+    }*/    
 
+    /*
     @Test
     public void testListNodesInBranch() {
         Optional<Long> id1 = dao.getNodeId("/test1/f1");
@@ -123,8 +127,9 @@ public class NodeDAOTest {
                     dao.listNodesInBranch(id1.get(), true);
                 });
 
-    }
+    }*/
 
+    /*
     @Test
     public void testSetBranchBusy() {
         Optional<Long> rootId = dao.getNodeId("/test1/f1");
@@ -157,7 +162,135 @@ public class NodeDAOTest {
         );
 
         assertTrue(busyFalse);
+    } */
+    
+    @Test
+    public void testGetShortNodeDescriptor(){
+        String userName = "user3";
+        List<String> userGroups = List.of();
+        
+        Optional<ShortNodeDescriptor> snd1Opt = 
+                dao.getShortNodeDescriptor("/test3/mstick", userName, userGroups);
+        
+        assertTrue(snd1Opt.isPresent());
+        ShortNodeDescriptor snd1 = snd1Opt.get();
+        assertTrue(snd1.isContainer());
+        assertFalse(snd1.isWritable());
+        assertFalse(snd1.isBusy());        
+        
+        assertEquals("9.13", snd1.getDestinationNodeLtreePath());        
+        
+        snd1Opt = 
+                dao.getShortNodeDescriptor("/test3/mbusy", userName, userGroups);
+        assertTrue(snd1Opt.isPresent());
+        snd1 = snd1Opt.get();        
+        assertTrue(snd1.isWritable());
+        assertTrue(snd1.isBusy());
+        
+        snd1Opt = 
+                dao.getShortNodeDescriptor("/test3/masynctrans", userName, userGroups);
+        assertTrue(snd1Opt.isPresent());
+        snd1 = snd1Opt.get();        
+        assertFalse(snd1.isWritable());
+        assertFalse(snd1.isBusy());
+        
+        snd1Opt = 
+                dao.getShortNodeDescriptor("/test3/asyncloc", userName, userGroups);
+        assertTrue(snd1Opt.isPresent());
+        snd1 = snd1Opt.get();        
+        assertFalse(snd1.isWritable());
+        assertFalse(snd1.isBusy());
+        
+        snd1Opt = 
+                dao.getShortNodeDescriptor("/test1/f1/f2_renamed/f3", "user1", userGroups);
+        assertTrue(snd1Opt.isPresent());
+        snd1 = snd1Opt.get();        
+        assertFalse(snd1.isContainer());
+        assertFalse(snd1.isWritable());
+        assertFalse(snd1.isBusy());
+        
+        snd1Opt = 
+                dao.getShortNodeDescriptor("/test3/group1", "user1", userGroups);
+        assertTrue(snd1Opt.isPresent());
+        snd1 = snd1Opt.get();                
+        assertFalse(snd1.isWritable());
+        
+        snd1Opt = 
+                dao.getShortNodeDescriptor("/test3/group1", "user3", List.of("group99"));
+        assertTrue(snd1Opt.isPresent());
+        snd1 = snd1Opt.get();                
+        assertTrue(snd1.isWritable());
+        
+        snd1Opt = 
+                dao.getShortNodeDescriptor("/test3/group1", "user1", List.of("group1", "group2"));
+        assertTrue(snd1Opt.isPresent());
+        snd1 = snd1Opt.get();                
+        assertTrue(snd1.isWritable());      
+    }
+    
+    @Test
+    public void testIsBranchBusy() {
+        Optional<Long> optId = dao.getNodeId("/test3/m1");
+        assertTrue(optId.isPresent());
+        
+        assertFalse(dao.isBranchBusy(optId.get()));
+        
+        optId = dao.getNodeId("/test3");
+        assertTrue(optId.isPresent());
+        
+        assertTrue(dao.isBranchBusy(optId.get()));
+        
     }
+    
+    @Test
+    public void testIsBranchWritable() {
+        
+        List<String> userGroups = List.of("group1");
+        Optional<Long> optId = dao.getNodeId("/test3/m1");
+        assertTrue(optId.isPresent());        
+        assertTrue(dao.isBranchWritable(optId.get(), "user3", userGroups));
+        
+        optId = dao.getNodeId("/test3");
+        assertTrue(optId.isPresent());        
+        assertFalse(dao.isBranchWritable(optId.get(), "user3", userGroups));
+        
+        optId = dao.getNodeId("/test3/group1");
+        assertTrue(optId.isPresent());        
+        assertTrue(dao.isBranchWritable(optId.get(), "user3", userGroups));
+        
+        optId = dao.getNodeId("/test3/group1");
+        assertTrue(optId.isPresent());        
+        assertFalse(dao.isBranchWritable(optId.get(), "user1", List.of("group99")));      
+    }
+    
+    @Test
+    public void testMoveNodeBranch() {
+        // Let's move /test3/m1 to /test3/group1
+        Optional<Long> optSourceId = dao.getNodeId("/test3/m1");
+        assertTrue(optSourceId.isPresent());
+        
+        Optional<ShortNodeDescriptor> optSnd 
+                = dao.getShortNodeDescriptor("/test3/group1", "user3", List.of("group1"));
+        
+        assertTrue(optSnd.isPresent());
+        ShortNodeDescriptor snd = optSnd.get();
+                
+        assertEquals("9.17", snd.getDestinationNodeLtreePath());
+        dao.moveNodeBranch(optSourceId.get(), snd.getDestinationNodeLtreePath());
+        
+        Optional<Long> optResultId = dao.getNodeId("/test3/group1/m1");        
+        assertTrue(optSourceId.isPresent());
+        optSnd = dao.getShortNodeDescriptor("/test3/group1/m1", "user3", List.of("group1"));
+        assertEquals("9.17.10", optSnd.get().getDestinationNodeLtreePath());
+        
+        
+        Optional<Long> optResultIdChild = dao.getNodeId("/test3/group1/m1/m2");
+        optSnd = dao.getShortNodeDescriptor("/test3/group1/m1/m2", "user3", List.of("group1"));
+        assertEquals("9.17.10.11", optSnd.get().getDestinationNodeLtreePath());
+        assertTrue(optResultIdChild.isPresent());
+        
+    }
+            
 
     @Test
     public void testRenameNode() {
@@ -181,40 +314,7 @@ public class NodeDAOTest {
         assertTrue(dao.listNode(newPathChild).isPresent());
 
     }
-    
-    @Test
-    public void testMoveNodeBranch() {
-        Optional<Long> optSourceId = dao.getNodeId("/test1/f1");
-        assertTrue(optSourceId.isPresent());        
-        
-        Optional<Long> optSourceId1 = dao.getNodeId("/test1/f1/f2_renamed");
-        assertTrue(optSourceId1.isPresent());
-        
-        Optional<Long> optSourceId2 = dao.getNodeId("/test1/f1/f2_renamed/f3");
-        assertTrue(optSourceId2.isPresent());
-        
-        Optional<Long> optDestId = dao.getNodeId("/test2/f4");
-        assertTrue(optDestId.isPresent());
-        
-        // dao.moveNodeBranch(optSourceId.get(), optDestId.get());
-
-        Optional<Long> newOptSourceId = dao.getNodeId("/test1/f1");
-        assertTrue(newOptSourceId.isEmpty());
-                       
-        Optional<Long> dest = dao.getNodeId("/test2/f4/f1");
-        assertTrue(dest.isPresent());
-        assertEquals(dest.get(), optSourceId.get());
-        
-        Optional<Long> dest1 = dao.getNodeId("/test2/f4/f1/f2_renamed");        
-        assertTrue(dest1.isPresent());
-        assertEquals(dest1.get(), optSourceId1.get());
-        
-        Optional<Long> dest2 = dao.getNodeId("/test2/f4/f1/f2_renamed/f3");
-        assertTrue(dest2.isPresent());
-        assertEquals(dest2.get(), optSourceId2.get());
-        
-    }
-
+ 
     @Test
     public void testCountNodeWithPath() {
         assertEquals(1, dao.countNodesWithPath("/"));
diff --git a/src/test/resources/test-data.sql b/src/test/resources/test-data.sql
index adf89ffc32789671643f0ee3dff4190533043f90..ec04c997a261a61d4d9f7eabfbc764dd2be722bb 100644
--- a/src/test/resources/test-data.sql
+++ b/src/test/resources/test-data.sql
@@ -30,6 +30,11 @@ INSERT INTO node (parent_path, parent_relative_path, name, type, creator_id, is_
 INSERT INTO node (parent_path, parent_relative_path, name, type, creator_id, is_public, location_id) VALUES ('', NULL, 'test4', 'container', 'user3', false, 3);      -- /test4
 
 INSERT INTO node (parent_path, parent_relative_path, name, sticky, type, creator_id, is_public, location_id) VALUES ('9', '', 'mstick', true, 'container', 'user3', false, 3);      -- /test3/mstick
+INSERT INTO node (parent_path, parent_relative_path, name, busy_state, type, creator_id, is_public, location_id) VALUES ('9', '', 'mbusy', true, 'container', 'user3', false, 3);      -- /test3/mbusy
+INSERT INTO node (parent_path, parent_relative_path, name, async_trans, type, creator_id, is_public, location_id) VALUES ('9', '', 'masynctrans', true, 'container', 'user3', false, 3);      -- /test3/masynctrans
+INSERT INTO node (parent_path, parent_relative_path, name, type, creator_id, is_public, location_id) VALUES ('9', '', 'asyncloc', 'container', 'user3', false, 1);      -- /test3/asyncloc
+INSERT INTO node (parent_path, parent_relative_path, name, type, creator_id, group_write, is_public, location_id) VALUES ('9', '', 'group1', 'container', 'user3','{"group1"}', false, 3);      -- /test3/group1
+
 
 DELETE FROM job;