diff --git a/src/test/java/org/folio/TestUtils.java b/src/test/java/org/folio/TestUtils.java
index d36af03dc..ba9216596 100644
--- a/src/test/java/org/folio/TestUtils.java
+++ b/src/test/java/org/folio/TestUtils.java
@@ -256,4 +256,13 @@ public static void validateSavedPoLines() {
         poline.mapTo(PoLine.class);
       });
   }
+
+  public static List<Location> getLocationPhysicalCopies(int n) {
+    return List.of(new Location()
+      .withLocationId(UUID.randomUUID().toString())
+      .withQuantityElectronic(0)
+      .withQuantityPhysical(n)
+      .withQuantity(n));
+  }
+
 }
diff --git a/src/test/java/org/folio/rest/impl/RoutingListsApiTest.java b/src/test/java/org/folio/rest/impl/RoutingListsApiTest.java
index be11fcafc..fd345a961 100644
--- a/src/test/java/org/folio/rest/impl/RoutingListsApiTest.java
+++ b/src/test/java/org/folio/rest/impl/RoutingListsApiTest.java
@@ -17,17 +17,9 @@
 import org.junit.jupiter.api.AfterAll;
 import org.junit.jupiter.api.AfterEach;
 import org.junit.jupiter.api.BeforeAll;
-import org.junit.jupiter.api.BeforeEach;
 import org.junit.jupiter.api.Test;
-import org.junit.jupiter.api.extension.ExtendWith;
-import org.junit.runner.RunWith;
-import org.mockito.MockitoAnnotations;
-import org.mockito.Spy;
-import org.springframework.test.context.junit.jupiter.SpringExtension;
-import org.springframework.test.context.junit4.SpringRunner;
 
 import java.util.List;
-import java.util.UUID;
 import java.util.concurrent.ExecutionException;
 import java.util.concurrent.TimeoutException;
 
@@ -45,6 +37,7 @@
 import static org.folio.TestConstants.ID_DOES_NOT_EXIST;
 import static org.folio.TestConstants.X_OKAPI_USER_ID;
 import static org.folio.TestConstants.X_OKAPI_USER_ID_WITH_ACQ_UNITS;
+import static org.folio.TestUtils.getLocationPhysicalCopies;
 import static org.folio.TestUtils.getMinimalContentPoLine;
 import static org.folio.TestUtils.getMockAsJson;
 import static org.folio.orders.utils.ResourcePathResolver.PO_LINES_STORAGE;
@@ -55,9 +48,6 @@
 import static org.hamcrest.MatcherAssert.assertThat;
 import static org.hamcrest.Matchers.equalTo;
 import static org.junit.jupiter.api.Assertions.assertEquals;
-import static org.mockito.ArgumentMatchers.any;
-import static org.mockito.Mockito.doReturn;
-import static org.mockito.Mockito.spy;
 
 public class RoutingListsApiTest {
   private static final Logger logger = LogManager.getLogger();
@@ -99,7 +89,7 @@ void testPostRoutingList() {
     PoLine poLine = getMinimalContentPoLine()
       .withId(PO_LINE_UUID)
       .withOrderFormat(PoLine.OrderFormat.PHYSICAL_RESOURCE)
-      .withLocations(getLocation(1));
+      .withLocations(getLocationPhysicalCopies(1));
     addMockEntry(PO_LINES_STORAGE, JsonObject.mapFrom(poLine));
 
     RoutingList rListRq = routingListJsonReqData.mapTo(RoutingList.class)
@@ -136,7 +126,7 @@ void testPostRoutingListShouldFailForLimitReached() {
     PoLine poLine = getMinimalContentPoLine()
       .withId(PO_LINE_UUID)
       .withOrderFormat(PoLine.OrderFormat.PHYSICAL_RESOURCE)
-      .withLocations(getLocation(0));
+      .withLocations(getLocationPhysicalCopies(0));
     addMockEntry(PO_LINES_STORAGE, JsonObject.mapFrom(poLine));
 
     RoutingList rListRq = routingListJsonReqData.mapTo(RoutingList.class)
@@ -218,12 +208,4 @@ void deleteNotExistentRoutingListTest() {
     verifyDeleteResponse(String.format(ROUTING_LISTS_ID_PATH, ID_DOES_NOT_EXIST), APPLICATION_JSON, 404);
   }
 
-  private List<Location> getLocation(int n) {
-    return List.of(new Location()
-      .withLocationId(UUID.randomUUID().toString())
-      .withQuantityElectronic(0)
-      .withQuantityPhysical(n)
-      .withQuantity(n));
-  }
-
 }
diff --git a/src/test/java/org/folio/service/routinglists/RoutingListValidatorTest.java b/src/test/java/org/folio/service/routinglists/RoutingListValidatorTest.java
new file mode 100644
index 000000000..7afbc8029
--- /dev/null
+++ b/src/test/java/org/folio/service/routinglists/RoutingListValidatorTest.java
@@ -0,0 +1,74 @@
+package org.folio.service.routinglists;
+
+import org.folio.rest.jaxrs.model.Error;
+import org.folio.rest.jaxrs.model.PoLine;
+import org.folio.rest.jaxrs.model.RoutingList;
+import org.folio.rest.jaxrs.model.RoutingListCollection;
+import org.folio.service.routinglists.validators.RoutingListValidatorUtil;
+import org.junit.jupiter.api.BeforeEach;
+import org.junit.jupiter.api.Test;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import static org.folio.TestUtils.getLocationPhysicalCopies;
+import static org.folio.TestUtils.getMinimalContentPoLine;
+import static org.folio.TestUtils.getMockAsJson;
+import static org.folio.rest.core.exceptions.ErrorCodes.INVALID_ROUTING_LIST_FOR_PO_LINE_FORMAT;
+import static org.folio.rest.core.exceptions.ErrorCodes.ROUTING_LIST_LIMIT_REACHED_FOR_PO_LINE;
+import static org.folio.rest.impl.MockServer.ROUTING_LISTS_MOCK_DATA_PATH;
+import static org.junit.jupiter.api.Assertions.assertEquals;
+
+public class RoutingListValidatorTest {
+
+  private static final String ROUTING_LIST_SAMPLE = ROUTING_LISTS_MOCK_DATA_PATH + "routing-list.json";
+
+  private static final String PO_LINE_UUID = "0009662b-8b80-4001-b704-ca10971f222d";
+
+  private PoLine samplePoLine;
+  private RoutingList sampleRoutingList;
+
+  @BeforeEach
+  void before() {
+    sampleRoutingList = getMockAsJson(ROUTING_LIST_SAMPLE).mapTo(RoutingList.class);
+    samplePoLine = getMinimalContentPoLine()
+      .withId(PO_LINE_UUID)
+      .withOrderFormat(PoLine.OrderFormat.PHYSICAL_RESOURCE)
+      .withLocations(getLocationPhysicalCopies(1));
+  }
+
+  @Test
+  void testValidateRoutingList() {
+    RoutingListCollection collection = getRoutingListCollection(0);
+    List<Error> errorList = RoutingListValidatorUtil.validateRoutingList(collection, samplePoLine);
+    assertEquals(errorList.size(), 0);
+  }
+
+  @Test
+  void testValidateRoutingListWithPOLineLimitReached() {
+    RoutingListCollection collection = getRoutingListCollection(1);
+    List<Error> errors = RoutingListValidatorUtil.validateRoutingList(collection, samplePoLine);
+    assertEquals(errors.size(), 1);
+    assertEquals(errors.get(0).getMessage(), ROUTING_LIST_LIMIT_REACHED_FOR_PO_LINE.getDescription());
+  }
+
+  @Test
+  void testValidateRoutingListWithPOLineInvalidOrderFormat() {
+    samplePoLine.setOrderFormat(PoLine.OrderFormat.ELECTRONIC_RESOURCE);
+    RoutingListCollection collection = getRoutingListCollection(1);
+    List<Error> errors = RoutingListValidatorUtil.validateRoutingList(collection, samplePoLine);
+    assertEquals(errors.size(), 1);
+    assertEquals(errors.get(0).getMessage(), INVALID_ROUTING_LIST_FOR_PO_LINE_FORMAT.getDescription());
+  }
+
+  private RoutingListCollection getRoutingListCollection(int n) {
+    List<RoutingList> lists = new ArrayList<>();
+    for (int i = 0; i < n; i++) {
+      lists.add(sampleRoutingList);
+    }
+    return new RoutingListCollection()
+      .withRoutingLists(lists)
+      .withTotalRecords(n);
+  }
+
+}