diff --git a/ci-scripts/cls_containerize.py b/ci-scripts/cls_containerize.py
index ecf0b3d0f396471ab3c987cf90006e8854a1076e..a7a80521afe982dbd7cf443aab8944f844d8ac44 100644
--- a/ci-scripts/cls_containerize.py
+++ b/ci-scripts/cls_containerize.py
@@ -84,7 +84,6 @@ def CreateWorkspace(sshSession, sourcePath, ranRepository, ranCommitID, ranTarge
 	if sshSession.getBefore().count(f'HEAD is now at {ranCommitID[:6]}') != 1:
 		sshSession.command('git log --oneline | head -n5', '\$', 5)
 		logging.error(f'problems during checkout, is at: {sshSession.getBefore()}')
-		self.exitStatus = 1
 		return False
 	else:
 		logging.debug('successful checkout')
@@ -319,7 +318,6 @@ class Containerize():
 		self.yamlPath = ['', '', '']
 		self.services = ['', '', '']
 		self.nb_healthy = [0, 0, 0]
-		self.exitStatus = 0
 		self.eNB_logFile = ['', '', '']
 
 		self.testCase_id = ''
@@ -991,7 +989,6 @@ class Containerize():
 		deployStatus,allServices = DeployServices(mySSH,self.services[self.eNB_instance])
 		if deployStatus != 0:
 			mySSH.close()
-			self.exitStatus = 1
 			logging.error('Could not deploy')
 			HTML.CreateHtmlTestRow('Could not deploy', 'KO', CONST.ALL_PROCESSES_OK)
 			return False
@@ -1014,7 +1011,6 @@ class Containerize():
 			imagesInfo += ("Healthy deployment!")
 			HTML.CreateHtmlTestRowQueue('N/A', 'OK', [(imagesInfo)])
 		else:
-			self.exitStatus = 1
 			imagesInfo += ("Unhealthy deployment! -- Check logs for reason!")
 			HTML.CreateHtmlTestRowQueue('N/A', 'KO', [(imagesInfo)])
 		return status
@@ -1035,14 +1031,16 @@ class Containerize():
 		if not copyin_res:
 			HTML.htmleNBFailureMsg='Could not copy logfile(s) to analyze it!'
 			HTML.CreateHtmlTestRow('N/A', 'KO', CONST.ENB_PROCESS_NOLOGFILE_TO_ANALYZE)
-			self.exitStatus = 1
 			return False
 		else:
 			log_results = [CheckLogs(self, mySSH, self.yamlPath[0].split('/'), service_name, HTML, RAN) for service_name, _ in services]
-			self.exitStatus = 1 if any(log_results) else 0
-			logging.info('\u001B[1m Undeploying OAI Object Pass\u001B[0m') if self.exitStatus == 0 else logging.error('\u001B[1m Undeploying OAI Object Failed\u001B[0m')
+			success = any(log_results)
 		mySSH.close()
-		return self.exitStatus == 0
+		if success:
+			logging.info('\u001B[1m Undeploying OAI Object Pass\u001B[0m')
+		else:
+			logging.error('\u001B[1m Undeploying OAI Object Failed\u001B[0m')
+		return success
 
 	def CheckAndAddRoute(self, svrName, ipAddr, userName, password):
 		logging.debug('Checking IP routing on ' + svrName)
diff --git a/ci-scripts/cls_oai_html.py b/ci-scripts/cls_oai_html.py
index dc2c3bf5c6be46549f959e4a474c394d9ce3f5a7..93176d1375228d623320215f2d15b507d308ed31 100644
--- a/ci-scripts/cls_oai_html.py
+++ b/ci-scripts/cls_oai_html.py
@@ -446,6 +446,8 @@ class HTMLManagement():
 				self.htmlFile.write(f'        <td bgcolor = "lightgreen" >{status}</td>\n')
 			elif (str(status) == 'KO'):
 				self.htmlFile.write(f'        <td bgcolor = "lightcoral" >{status}</td>\n')
+			elif str(status) == 'SKIP':
+				self.htmlFile.write(f'        <td bgcolor = "lightgray" >{status}</td>\n')
 			else:
 				addOrangeBK = True
 				self.htmlFile.write(f'        <td bgcolor = "orange" >{status}</td>\n')
diff --git a/ci-scripts/cls_oaicitest.py b/ci-scripts/cls_oaicitest.py
index 58ae8366b6586a2e56e639e3ea0680514b853d7f..8ec97c2e6e0660186e4fd0af1ae0946ddc7293c1 100644
--- a/ci-scripts/cls_oaicitest.py
+++ b/ci-scripts/cls_oaicitest.py
@@ -900,7 +900,6 @@ class OaiCiTest():
 						CONTAINERS.UndeployObject(HTML,RAN)
 					else:
 						CONTAINERS.UndeployGenObject(HTML,RAN, self)
-		RAN.prematureExit=True
 
 	#this function is called only if eNB/gNB fails to start
 	#RH to be re-factored
@@ -930,7 +929,6 @@ class OaiCiTest():
 						CONTAINERS.UndeployObject(HTML,RAN)
 					else:
 						CONTAINERS.UndeployGenObject(HTML,RAN,self)
-		RAN.prematureExit=True
 
 	def LogCollectBuild(self,RAN):
 		# Some pipelines are using "none" IP / Credentials
diff --git a/ci-scripts/cls_physim.py b/ci-scripts/cls_physim.py
index 9d2e85ff41c28d3bce144bb4517293540e328ce3..7d4dd7d33a6baf70a6bb0e3448019c688dbeed42 100644
--- a/ci-scripts/cls_physim.py
+++ b/ci-scripts/cls_physim.py
@@ -52,7 +52,6 @@ class PhySim:
 		self.ranCommitID= ""
 		self.ranAllowMerge= ""
 		self.ranTargetBranch= ""
-		self.exitStatus=0
 		self.forced_workspace_cleanup=False
 		#private attributes
 		self.__workSpacePath=''
@@ -111,7 +110,6 @@ class PhySim:
 		if res_enc is None and res_dec is None:
 			logging.error(f'no statistics: res_enc {res_enc} res_dec {res_dec}')
 			HTML.CreateHtmlTestRowQueue(self.runargs, 'KO', ['no statistics'])
-			self.exitStatus = 1
 			os.system(f'mv {self.__runLogFile} {self.__runLogPath}/.')
 			return False
 
@@ -124,7 +122,6 @@ class PhySim:
 			error_msg = f'Processing time exceeds a limit of {thrs_KO} us'
 			logging.error(error_msg)
 			HTML.CreateHtmlTestRowQueue(self.runargs, 'KO', [info + '\n' + error_msg])
-			self.exitStatus = 1
 		return success
 
 	def __CheckResults_NRulsimTest(self, HTML, CONST, testcase_id):
@@ -136,7 +133,6 @@ class PhySim:
 			error_msg = f'could not recover test result file {filename}'
 			logging.error(error_msg)
 			HTML.CreateHtmlTestRowQueue("could not recover results", 'KO', [error_msg])
-			self.exitStatus = 1
 			return False
 
 		PUSCH_OK = False
@@ -153,7 +149,6 @@ class PhySim:
 			error_msg = 'error: no "PUSCH test OK"'
 			logging.error(error_msg)
 			HTML.CreateHtmlTestRowQueue(self.runargs, 'KO', 1, [error_msg])
-			self.exitStatus = 1
 		return PUSCH_OK
 
 	def __CheckBuild_PhySim(self, HTML, CONST):
@@ -169,13 +164,10 @@ class PhySim:
 		with open(self.__buildLogFile) as f:
 			if 'BUILD SHOULD BE SUCCESSFUL' in f.read():
 				HTML.CreateHtmlTestRow(self.buildargs, 'OK', CONST.ALL_PROCESSES_OK, 'PhySim')
-				self.exitStatus=0
 				return True
 		logging.error('\u001B[1m Building Physical Simulators Failed\u001B[0m')
 		HTML.CreateHtmlTestRow(self.buildargs, 'KO', CONST.ALL_PROCESSES_OK, 'LDPC')
 		HTML.CreateHtmlTabFooter(False)
-		#exitStatus=1 will do a sys.exit in main
-		self.exitStatus = 1
 		return False
 
 
diff --git a/ci-scripts/cls_physim1.py b/ci-scripts/cls_physim1.py
index e3a24f5fc1a2aab862061069c044cf29e3eed371..0fa88aff32eea09b837ffe692d280a1013d9dc80 100644
--- a/ci-scripts/cls_physim1.py
+++ b/ci-scripts/cls_physim1.py
@@ -65,7 +65,7 @@ class PhySim:
 #PUBLIC Methods$
 #-----------------$
 
-	def Deploy_PhySim(self, HTML, RAN):
+	def Deploy_PhySim(self, HTML):
 		if self.ranRepository == '' or self.ranBranch == '' or self.ranCommitID == '':
 			HELP.GenericHelp(CONST.Version)
 			sys.exit('Insufficient Parameter')
@@ -123,7 +123,6 @@ class PhySim:
 			logging.error('\u001B[1m OC Cluster Login Failed\u001B[0m')
 			mySSH.close()
 			HTML.CreateHtmlTestRow('N/A', 'KO', CONST.OC_LOGIN_FAIL)
-			RAN.prematureExit = True
 			return False
 		else:
 			logging.debug('\u001B[1m   Login to OC Cluster Successfully\u001B[0m')
@@ -133,7 +132,6 @@ class PhySim:
 			mySSH.command('oc logout', '\$', 30)
 			mySSH.close()
 			HTML.CreateHtmlTestRow('N/A', 'KO', CONST.OC_PROJECT_FAIL)
-			RAN.prematureExit = True
 			return False
 		else:
 			logging.debug(f'\u001B[1m   Now using project {ocProjectName}\u001B[0m')
@@ -154,7 +152,6 @@ class PhySim:
 			mySSH.command('oc logout', '\$', 30)
 			mySSH.close()
 			self.AnalyzeLogFile_phySim()
-			RAN.prematureExit = True
 			return False
 		else:
 			logging.debug('\u001B[1m   Deployed PhySim Successfully using helm chart\u001B[0m')
@@ -186,7 +183,6 @@ class PhySim:
 			mySSH.command('oc logout', '\$', 30)
 			HTML.CreateHtmlTestRow('N/A', 'KO', CONST.OC_PHYSIM_DEPLOY_FAIL)
 			HTML.CreateHtmlTestRowPhySimTestResult(self.testSummary,self.testResult)
-			RAN.prematureExit = True
 			return False
 		# Waiting to complete the running test
 		count = 0
@@ -248,7 +244,6 @@ class PhySim:
 			HTML.CreateHtmlTestRowPhySimTestResult(self.testSummary,self.testResult)
 			logging.info('\u001B[1m Physical Simulator Pass\u001B[0m')
 		else:
-			RAN.prematureExit = True
 			if isFinished:
 				HTML.CreateHtmlTestRow('N/A', 'KO', CONST.ALL_PROCESSES_OK)
 			else:
diff --git a/ci-scripts/main.py b/ci-scripts/main.py
index 0fdf0f2f07425b7c40304b8ed7c0b0a07d94724b..b6f59950ecad104421b454bdbb69c34daa39fb6a 100644
--- a/ci-scripts/main.py
+++ b/ci-scripts/main.py
@@ -149,22 +149,15 @@ def ExecuteActionWithParam(action):
 		if proxy_commit is not None:
 			CONTAINERS.proxyCommit = proxy_commit
 		if action == 'Build_eNB':
-			RAN.BuildeNB(HTML)
+			success = RAN.BuildeNB(HTML)
 		elif action == 'Build_Image':
 			success = CONTAINERS.BuildImage(HTML)
-			if not success:
-				RAN.prematureExit = True
 		elif action == 'Build_Proxy':
 			success = CONTAINERS.BuildProxy(HTML)
-			if not success:
-				RAN.prematureExit = True
 		elif action == 'Build_Cluster_Image':
-			if not CLUSTER.BuildClusterImage(HTML):
-				RAN.prematureExit = True
+			success = CLUSTER.BuildClusterImage(HTML)
 		elif action == 'Build_Run_Tests':
 			success = CONTAINERS.BuildRunTests(HTML)
-			if not success:
-				RAN.prematureExit = True
 
 	elif action == 'Initialize_eNB':
 		RAN.eNB_Trace=test.findtext('eNB_Trace')
@@ -200,7 +193,7 @@ def ExecuteActionWithParam(action):
 
 		cmd_prefix = test.findtext('cmd_prefix')
 		if cmd_prefix is not None: RAN.cmd_prefix = cmd_prefix
-		RAN.InitializeeNB(HTML, EPC)
+		success = RAN.InitializeeNB(HTML, EPC)
 
 	elif action == 'Terminate_eNB':
 		eNB_instance=test.findtext('eNB_instance')
@@ -228,7 +221,7 @@ def ExecuteActionWithParam(action):
 			RAN.air_interface[RAN.eNB_instance] = 'lte-softmodem'
 		else:
 			RAN.air_interface[RAN.eNB_instance] = air_interface.lower() +'-softmodem'
-		RAN.TerminateeNB(HTML, EPC)
+		success = RAN.TerminateeNB(HTML, EPC)
 
 	elif action == 'Initialize_UE' or action == 'Attach_UE' or action == 'Detach_UE' or action == 'Terminate_UE' or action == 'CheckStatusUE' or action == 'DataEnable_UE' or action == 'DataDisable_UE':
 		CiTestObj.ue_ids = test.findtext('id').split(' ')
@@ -240,19 +233,19 @@ def ExecuteActionWithParam(action):
 		else:
 			CiTestObj.nodes = [None] * len(CiTestObj.ue_ids)
 		if action == 'Initialize_UE':
-			CiTestObj.InitializeUE(HTML)
+			success = CiTestObj.InitializeUE(HTML)
 		elif action == 'Attach_UE':
-			CiTestObj.AttachUE(HTML, RAN, EPC, CONTAINERS)
+			success = CiTestObj.AttachUE(HTML, RAN, EPC, CONTAINERS)
 		elif action == 'Detach_UE':
-			CiTestObj.DetachUE(HTML)
+			success = CiTestObj.DetachUE(HTML)
 		elif action == 'Terminate_UE':
-			CiTestObj.TerminateUE(HTML)
+			success = CiTestObj.TerminateUE(HTML)
 		elif action == 'CheckStatusUE':
-			CiTestObj.CheckStatusUE(HTML)
+			success = CiTestObj.CheckStatusUE(HTML)
 		elif action == 'DataEnable_UE':
-			CiTestObj.DataEnableUE(HTML)
+			success = CiTestObj.DataEnableUE(HTML)
 		elif action == 'DataDisable_UE':
-			CiTestObj.DataDisableUE(HTML)
+			success = CiTestObj.DataDisableUE(HTML)
 
 	elif action == 'Ping':
 		CiTestObj.ping_args = test.findtext('ping_args')
@@ -266,7 +259,7 @@ def ExecuteActionWithParam(action):
 		else:
 			CiTestObj.nodes = [None] * len(CiTestObj.ue_ids)
 		ping_rttavg_threshold = test.findtext('ping_rttavg_threshold') or ''
-		CiTestObj.Ping(HTML,RAN,EPC,CONTAINERS)
+		success = CiTestObj.Ping(HTML,RAN,EPC,CONTAINERS)
 
 	elif action == 'Iperf' or action == 'Iperf2_Unidir':
 		CiTestObj.iperf_args = test.findtext('iperf_args')
@@ -293,13 +286,13 @@ def ExecuteActionWithParam(action):
 			logging.error('test-case has wrong option ' + CiTestObj.iperf_options)
 			CiTestObj.iperf_options = 'check'
 		if action == 'Iperf':
-			CiTestObj.Iperf(HTML,RAN,EPC,CONTAINERS)
+			success = CiTestObj.Iperf(HTML,RAN,EPC,CONTAINERS)
 		elif action == 'Iperf2_Unidir':
-			CiTestObj.Iperf2_Unidir(HTML,RAN,EPC,CONTAINERS)
+			success = CiTestObj.Iperf2_Unidir(HTML,RAN,EPC,CONTAINERS)
 
 	elif action == 'IdleSleep':
 		st = test.findtext('idle_sleep_time_in_sec') or "5"
-		cls_oaicitest.IdleSleep(HTML, int(st))
+		success = cls_oaicitest.IdleSleep(HTML, int(st))
 
 	elif action == 'Build_PhySim':
 		ldpc.buildargs  = test.findtext('physim_build_args')
@@ -311,54 +304,52 @@ def ExecuteActionWithParam(action):
 				ldpc.forced_workspace_cleanup=True
 			else:
 				ldpc.forced_workspace_cleanup=False
-		HTML=ldpc.Build_PhySim(HTML,CONST)
-		if ldpc.exitStatus==1:
-			RAN.prematureExit = True
+		success = ldpc.Build_PhySim(HTML,CONST)
 
 	elif action == 'Deploy_Run_PhySim':
-		PHYSIM.Deploy_PhySim(HTML, RAN)
+		success = PHYSIM.Deploy_PhySim(HTML)
 
 	elif action == 'Initialize_MME':
 		string_field = test.findtext('option')
 		if (string_field is not None):
 			EPC.mmeConfFile = string_field
-		EPC.InitializeMME(HTML)
+		success = EPC.InitializeMME(HTML)
 
 	elif action == 'Initialize_HSS' or action == 'Initialize_SPGW':
 		if action == 'Initialize_HSS':
-			EPC.InitializeHSS(HTML)
+			success = EPC.InitializeHSS(HTML)
 		elif action == 'Initialize_SPGW':
-			EPC.InitializeSPGW(HTML)
+			success = EPC.InitializeSPGW(HTML)
 	elif action == 'Terminate_HSS' or action == 'Terminate_MME' or action == 'Terminate_SPGW':
 		if action == 'Terminate_HSS':
-			EPC.TerminateHSS(HTML)
+			success = EPC.TerminateHSS(HTML)
 		elif action == 'Terminate_MME':
-			EPC.TerminateMME(HTML)
+			success = EPC.TerminateMME(HTML)
 		elif action == 'Terminate_SPGW':
-			EPC.TerminateSPGW(HTML)
+			success = EPC.TerminateSPGW(HTML)
 
 	elif action == 'Deploy_EPC':
 		string_field = test.findtext('parameters')
 		if (string_field is not None):
 			EPC.yamlPath = string_field
-		EPC.DeployEpc(HTML)
+		success = EPC.DeployEpc(HTML)
 
 	elif action == 'Undeploy_EPC':
-		EPC.UndeployEpc(HTML)
+		success = EPC.UndeployEpc(HTML)
 
 	elif action == 'Initialize_5GCN':
 		string_field = test.findtext('args')
 		if (string_field is not None):
 			EPC.cfgDeploy = string_field	
 		EPC.cnID = test.findtext('cn_id')
-		EPC.Initialize5GCN(HTML)
+		success = EPC.Initialize5GCN(HTML)
 
 	elif action == 'Terminate_5GCN':
 		string_field = test.findtext('args')
 		if (string_field is not None):
 			EPC.cfgUnDeploy = string_field	
 		EPC.cnID = test.findtext('cn_id')
-		EPC.Terminate5GCN(HTML)
+		success = EPC.Terminate5GCN(HTML)
 
 	elif action == 'Deploy_Object' or action == 'Undeploy_Object' or action == "Create_Workspace":
 		eNB_instance=test.findtext('eNB_instance')
@@ -384,46 +375,38 @@ def ExecuteActionWithParam(action):
 		if string_field is not None:
 			CONTAINERS.services[CONTAINERS.eNB_instance] = string_field
 		if action == 'Deploy_Object':
-			CONTAINERS.DeployObject(HTML)
-			if CONTAINERS.exitStatus==1:
+			success = CONTAINERS.DeployObject(HTML)
+			if not success:
 				CiTestObj.AutoTerminateeNB(HTML,RAN,EPC,CONTAINERS)
-				RAN.prematureExit = True
 		elif action == 'Undeploy_Object':
-			CONTAINERS.UndeployObject(HTML, RAN)
-			if CONTAINERS.exitStatus == 1:
+			success = CONTAINERS.UndeployObject(HTML, RAN)
+			if not success:
 				CiTestObj.AutoTerminateeNB(HTML,RAN,EPC,CONTAINERS)
-				RAN.prematureExit = True
 		elif action == 'Create_Workspace':
-			CONTAINERS.Create_Workspace(HTML)
+			success = CONTAINERS.Create_Workspace(HTML)
 
 	elif action == 'Run_CUDATest' or action == 'Run_NRulsimTest' or action == 'Run_T2Test':
 		ldpc.runargs = test.findtext('physim_run_args')
 		ldpc.runsim = test.findtext('physim_run')
 		ldpc.timethrs = test.findtext('physim_time_threshold')
 		if action == 'Run_CUDATest':
-			HTML=ldpc.Run_CUDATest(HTML,CONST,id)
+			success = ldpc.Run_CUDATest(HTML,CONST,id)
 		elif action == 'Run_NRulsimTest':
-			HTML=ldpc.Run_NRulsimTest(HTML,CONST,id)
+			success = ldpc.Run_NRulsimTest(HTML,CONST,id)
 		elif action == 'Run_T2Test':
-			HTML=ldpc.Run_T2Test(HTML,CONST,id)
-		if ldpc.exitStatus==1:
-			RAN.prematureExit = True
+			success = ldpc.Run_T2Test(HTML,CONST,id)
 
 	elif action == 'LicenceAndFormattingCheck':
-		ret = SCA.LicenceAndFormattingCheck(HTML)
-		if ret != 0:
-			RAN.prematureExit = True
+		success = SCA.LicenceAndFormattingCheck(HTML)
 
 	elif action == 'Cppcheck_Analysis':
-		SCA.CppCheckAnalysis(HTML)
+		success = SCA.CppCheckAnalysis(HTML)
 
 	elif action == 'Push_Local_Registry':
 		string_field = test.findtext('registry_svr_id')
 		if (string_field is not None):
 			CONTAINERS.registrySvrId = string_field
 		success = CONTAINERS.Push_Image_to_Local_Registry(HTML)
-		if not success:
-			RAN.prematureExit = True
 
 	elif action == 'Pull_Local_Registry':
 		string_field = test.findtext('test_svr_id')
@@ -434,22 +417,18 @@ def ExecuteActionWithParam(action):
 		if (string_field is not None):
 			CONTAINERS.imageToPull = string_field.split()
 		success = CONTAINERS.Pull_Image_from_Local_Registry(HTML)
-		if not success:
-			RAN.prematureExit = True
 
 	elif action == 'Clean_Test_Server_Images':
 		string_field = test.findtext('test_svr_id')
 		if (string_field is not None):
 			CONTAINERS.testSvrId = string_field
 		success = CONTAINERS.Clean_Test_Server_Images(HTML)
-		if not success:
-			RAN.prematureExit = True
 
 	elif action == 'Custom_Command':
 		node = test.findtext('node')
 		command = test.findtext('command')
 		command_fail = test.findtext('command_fail') in ['True', 'true', 'Yes', 'yes']
-		cls_oaicitest.Custom_Command(HTML, node, command, command_fail)
+		success = cls_oaicitest.Custom_Command(HTML, node, command, command_fail)
 
 	elif action == 'Pull_Cluster_Image':
 		string_field = test.findtext('images_to_pull')
@@ -458,12 +437,13 @@ def ExecuteActionWithParam(action):
 		string_field = test.findtext('test_svr_id')
 		if (string_field is not None):
 			CLUSTER.testSvrId = string_field
-		if not CLUSTER.PullClusterImage(HTML,RAN):
-			RAN.prematureExit = True
+		success = CLUSTER.PullClusterImage(HTML, RAN)
 
 	else:
 		logging.warning(f"unknown action {action}, skip step")
+		success = True # by default, we skip the step and print a warning
 
+	return success
 
 #check if given test is in list
 #it is in list if one of the strings in 'list' is at the beginning of 'test'
@@ -738,13 +718,11 @@ elif re.match('^TesteNB$', mode, re.IGNORECASE) or re.match('^TestUE$', mode, re
 	if CONTAINERS.eNB1IPAddress == '172.21.16.137':
 		CONTAINERS.CheckAndAddRoute('nepes', CONTAINERS.eNB1IPAddress, CONTAINERS.eNB1UserName, CONTAINERS.eNB1Password)
 
-	RAN.prematureExit=False
+	task_set_succeeded = True
 	HTML.startTime=int(round(time.time() * 1000))
 
 	for test_case_id in todo_tests:
 		for test in all_tests:
-			if RAN.prematureExit:
-				break
 			id = test.get('id')
 			if test_case_id != id:
 				continue
@@ -752,23 +730,31 @@ elif re.match('^TesteNB$', mode, re.IGNORECASE) or re.match('^TestUE$', mode, re
 			HTML.testCase_id=CiTestObj.testCase_id
 			EPC.testCase_id=CiTestObj.testCase_id
 			CiTestObj.desc = test.findtext('desc')
+			always_exec = test.findtext('always_exec') in ['True', 'true', 'Yes', 'yes']
 			HTML.desc=CiTestObj.desc
 			action = test.findtext('class')
 			if (CheckClassValidity(xml_class_list, action, id) == False):
 				continue
 			CiTestObj.ShowTestID()
+			if not task_set_succeeded and not always_exec:
+				msg = f"skipping test due to prior error"
+				logging.warning(msg)
+				HTML.CreateHtmlTestRowQueue(msg, "SKIP", [])
+				break
 			try:
-				ExecuteActionWithParam(action)
-				if RAN.prematureExit:
+				test_succeeded = ExecuteActionWithParam(action)
+				if not test_succeeded:
+					logging.error(f"test ID {test_case_id} action {action} failed ({test_succeeded}), skipping next tests")
+					task_set_succeeded = False
 					CiTestObj.AutoTerminateeNB(HTML,RAN,EPC,CONTAINERS)
 			except Exception as e:
 				s = traceback.format_exc()
 				logging.error(f'while running CI, an exception occurred:\n{s}')
 				HTML.CreateHtmlTestRowQueue("N/A", 'KO', [f"CI test code encountered an exception:\n{s}"])
-				RAN.prematureExit = True
+				task_set_succeeded = False
 				break
 
-	if RAN.prematureExit:
+	if not task_set_succeeded:
 		logging.error('\u001B[1;37;41mScenario failed\u001B[0m')
 		HTML.CreateHtmlTabFooter(False)
 		sys.exit('Failed Scenario')
diff --git a/ci-scripts/ran.py b/ci-scripts/ran.py
index d02b927ea65fb3df5e00e51a459eff816b6616b3..9fc62eadd4ef62288cfadaa648aa03bb638dd149 100644
--- a/ci-scripts/ran.py
+++ b/ci-scripts/ran.py
@@ -55,7 +55,6 @@ class RANManagement():
 
 	def __init__(self):
 		
-		self.prematureExit = False
 		self.ranRepository = ''
 		self.ranBranch = ''
 		self.ranAllowMerge = False
@@ -1269,7 +1268,6 @@ class RANManagement():
 					rruMsg = 'Slave RRU DID NOT receive the RRU_frame_resynch command from RAU'
 					logging.debug('\u001B[1;37;41m ' + rruMsg + ' \u001B[0m')
 					htmleNBFailureMsg += rruMsg + '\n'
-					self.prematureExit = True
 					global_status = CONST.ENB_PROCESS_SLAVE_RRU_NOT_SYNCED
 		if foundSegFault:
 			logging.debug('\u001B[1;37;41m ' + nodeB_prefix + 'NB ended with a Segmentation Fault! \u001B[0m')
diff --git a/ci-scripts/tests/test-runner/test.xml b/ci-scripts/tests/test-runner/test.xml
index e1aadffb9eae1e0c37f1d68f5f60d919d51df5db..d5efacfdae9df7bd873d53fec7eabda094c2309b 100644
--- a/ci-scripts/tests/test-runner/test.xml
+++ b/ci-scripts/tests/test-runner/test.xml
@@ -27,6 +27,9 @@
         <htmlTabIcon>wrench</htmlTabIcon>
         <TestCaseRequestedList>
  000001
+ 000002
+ 000003
+ 000004
         </TestCaseRequestedList>
         <TestCaseExclusionList></TestCaseExclusionList>
 
@@ -37,4 +40,29 @@
                 <command>true</command>
                 <command_fail>yes</command_fail>
         </testCase>
+
+        <testCase id="000002">
+                <class>Custom_Command</class>
+                <desc>This should fail</desc>
+                <node>localhost</node>
+                <command>false</command>
+                <command_fail>yes</command_fail>
+        </testCase>
+
+        <testCase id="000003">
+                <class>Custom_Command</class>
+                <desc>This should be skipped</desc>
+                <node>localhost</node>
+                <command>true</command>
+                <command_fail>yes</command_fail>
+        </testCase>
+
+        <testCase id="000004">
+                <class>Custom_Command</class>
+                <desc>This should be executed because marked so</desc>
+                <always_exec>true</always_exec>
+                <node>localhost</node>
+                <command>true</command>
+                <command_fail>yes</command_fail>
+        </testCase>
 </testCaseList>