Sfoglia il codice sorgente

Z991239-385 #comment 1.将SpReqAnsContext改成可继承(虽然不太愿意);2.在非测试模式下屏蔽Test_Examine的发送;3.修改测试接口的使用示例(见mod_SampleEntity.h)

gifur 5 anni fa
parent
commit
5d9a325934
4 ha cambiato i file con 95 aggiunte e 24 eliminazioni
  1. 5 3
      Common/SpHelper.h
  2. 47 2
      Common/SpTest.h
  3. 35 18
      module/mod_sample/mod_SampleEntity.h
  4. 8 1
      spbase/SpEntityPrivilege.cpp

+ 5 - 3
Common/SpHelper.h

@@ -199,10 +199,12 @@ struct SpReqAnsContext
 	SpReqAnsContext(CSmartPointer<ITransactionContext> &pTransactionContext) 
 		: m_spTransactionContext(pTransactionContext) {}
 
+	virtual ~SpReqAnsContext() {}
+
 	TReq Req;
 	TAns Ans;
 
-	ErrorCodeEnum Answer(ErrorCodeEnum Error = Error_Succeed)
+	virtual ErrorCodeEnum Answer(ErrorCodeEnum Error = Error_Succeed)
 	{
 		if (Error == Error_Succeed) {
 			CAutoBuffer Buf = SpObject2Buffer<TAns>(Ans);
@@ -212,7 +214,7 @@ struct SpReqAnsContext
 		}
 	}
 
-	ErrorCodeEnum Answer(ErrorCodeEnum eSysError, DWORD dwUserError)
+	virtual ErrorCodeEnum Answer(ErrorCodeEnum eSysError, DWORD dwUserError)
 	{
 		return m_spTransactionContext->SendAnswer(eSysError, dwUserError);
 	}
@@ -222,7 +224,7 @@ struct SpReqAnsContext
 		return m_spTransactionContext->GetRequestID();
 	}
 
-	DWORD GetExpireLeftTime()
+	virtual DWORD GetExpireLeftTime()
 	{
 		// this method content is invalid, TODO: get the real ExpireLeftTime. [3/20/2020 17:27 Gifur]
 		DWORD dwWholeTime = 0;

+ 47 - 2
Common/SpTest.h

@@ -172,6 +172,7 @@ public:
 
 		MethodTestCaseT(CEntityBase* ent, ToTestFuncProto testFunc)
 			:SpReqAnsContext(m_spMockTransactionContext),m_enti(ent), m_testFunc(testFunc)
+			,m_errorCode(Error_IgnoreAll),m_dwUserCode(0)
 			{ }
 
 		virtual void PreTest() {/*To Set member Req value*/}
@@ -196,10 +197,12 @@ public:
 				TestObjectPointer that = static_cast<TestObjectPointer>(m_enti);
 				
 				(that->*m_testFunc)(GetCtx());
-
+#if 0
 				DWORD dwUserCode = 0, dwNoUsed = 0;
 				ErrorCodeEnum result = m_spMockTransactionContext->GetExpireTime(dwUserCode, dwNoUsed);
-
+#else
+				ErrorCodeEnum result = m_errorCode;
+#endif
 				Dbg("errorCode: %s", SpStrError(result));
 				
 				return (((result == Error_Succeed) ?  PostTest() : result));
@@ -208,6 +211,23 @@ public:
 			return Error_IgnoreAll;
 		}
 
+		ErrorCodeEnum Answer(ErrorCodeEnum Error = Error_Succeed) 
+		{
+			LOG_FUNCTION();
+			m_errorCode = Error;
+
+			return Error_Succeed;
+		}
+
+		ErrorCodeEnum Answer(ErrorCodeEnum eSysError, DWORD dwUserError)
+		{
+			LOG_FUNCTION();
+			m_errorCode = eSysError;
+			m_dwUserCode = dwUserError;
+
+			return Error_Succeed;
+		}
+
 	private:
 		Pointer GetCtx() 
 		{
@@ -221,6 +241,9 @@ public:
 		CEntityBase* m_enti;
 		ToTestFuncProto m_testFunc;
 
+		ErrorCodeEnum m_errorCode;
+		DWORD m_dwUserCode;
+
 	};
 
 	typedef std::vector<TestCaseEntry> TestCaseSet;
@@ -235,6 +258,10 @@ protected:
 
 	virtual ErrorCodeEnum RunTestCase();
 
+	/** user can override this function to add any other test, but do not
+	     invoke 'AddTestCaseEntry' and 'AddTestMethodEntry' method at this scope!!!!*/
+	virtual ErrorCodeEnum CustomTestCase() { return Error_Succeed; }
+
 private:
 
 	TestCaseSet m_testCases;
@@ -254,6 +281,7 @@ private:
  *     hook it to mock real test result without changing any functional code which I really unwill to see it!
  * 2. subclass MethodTestCaseT inherited from SpReqAnsContext cannot initialize earlier than SpReqAnsContext as children class, so we
  *     cannot declare a 'CSmartPointer<ITransactionContext>' type member and initialze it first then convey it to SpReqAnsContext.
+ * 3. multi-thead unsafe !!!
  */
 template<typename TClass>
 CSmartPointer<ITransactionContext> ITestCaseSuite<TClass>::m_spMockTransactionContext = CreateMockTransactionContext(nullptr);
@@ -269,6 +297,9 @@ ITestCaseSuite<T>::~ITestCaseSuite()
 	}
 }
 
+/** 'TestCaseEntry' Prototype:  void Entity::Function(CSmartPointer<ITransactionContext> pTransactionContext)
+   * User should declare and implement it.
+   */
 template<typename TClass>
 void ITestCaseSuite<TClass>::AddTestCaseEntry(TestCaseEntry entry)
 {
@@ -341,6 +372,20 @@ ErrorCodeEnum ITestCaseSuite<TClass>::RunTestCase()
 }
 
 
+#define TESTCASE_OVERRIDE_ON_EXAM_AND_IMPLEMENT()	\
+void OnExam(CSmartPointer<ITransactionContext> pTransactionContext) override	\
+{	\
+	LOG_FUNCTION();	\
+	ErrorCodeEnum testResult = RunTestCase();	\
+	if (testResult == Error_Succeed || testResult == Error_IgnoreAll) {	\
+        testResult =  CustomTestCase();	\
+		pTransactionContext->SendAnswer(testResult);	\
+	} else {	\
+		pTransactionContext->SendAnswer(testResult);	\
+	}	\
+}
+
+
 #define TESTCASE_DECLARE_BEGIN(serviceName, testFuncName)	\
 	void Test_##testFuncName(CSmartPointer<ITransactionContext> pTransactionContext) {\
 		SpReqAnsContext< serviceName##_##testFuncName##_Req, serviceName##_##testFuncName##_Ans>::Pointer ctx =	\

+ 35 - 18
module/mod_sample/mod_SampleEntity.h

@@ -29,7 +29,6 @@ public:
 			ec = Error_InvalidState;
 		}
 
-		//MessageBoxA(NULL, "", "", MB_OK);
 		AddTestCaseEntry(&CSampleEntity::TestTwoWayFuncNormal);
 		pTransactionContext->SendAnswer(ec);
 	}
@@ -68,9 +67,32 @@ public:
 		CHECK(Error_NoPrivilege == GetFunction()->SetSysVar("PrivilegeState", "1", true));
 		CHECK(Error_NoPrivilege == GetFunction()->SetSysVar("PrivilegeState", "1"));
 
+		TestCaseDemo();
+	}
+
+	void TestCaseDemo()
+	{
+		/** simple test way, user declare and implement the test method*/
 		AddTestCaseEntry(&CSampleEntity::TestTwoWayFuncWithID);
 
+		/** this is meanless usage way beacause we cannot set req member*/
+		AddTestMethodEntry(
+			new MethodTestCaseT<SampleService_TwoWayFuncNotOverlap_Req, SampleService_TwoWayFuncNotOverlap_Ans>(
+				this,
+				&CSampleEntity::TwoWayFuncNotOverlap));
+
+		/** but we can change it like this.*/
+		auto methdTest1 = new MethodTestCaseT<SampleService_TwoWayFuncNotOverlap_Req, SampleService_TwoWayFuncNotOverlap_Ans>(
+			this,
+			&CSampleEntity::TwoWayFuncNotOverlap);
+
+		methdTest1->Req.req_context = "I'am Test";
+		AddTestMethodEntry(methdTest1);
 
+		/** but still, we cannot check the Ans member's validity, only one thing what we can do is 
+		      just checking the aim furncion returned 'ErrorCodeEnum' type value*/
+
+		 /** last but not lease, we can inherit MethodTestCaseT and override PreTest(to set Req) and PostTest(to check Ans)*/
 		struct TwoWayFuncOverlapTestCase :
 			public MethodTestCaseT<SampleService_TwoWayFuncOverlap_Req, SampleService_TwoWayFuncOverlap_Ans>
 		{
@@ -88,7 +110,7 @@ public:
 				LOG_FUNCTION();
 
 				if (Ans.ans_context.Compare("world", true) != 0) {
-					LOG_TRACE("Ans.ans_context.Compare");
+					LOG_TRACE("Check failed, return except Error_Succeed");
 					return Error_Unexpect;
 				}
 
@@ -97,24 +119,15 @@ public:
 		};
 
 		AddTestMethodEntry(new TwoWayFuncOverlapTestCase(this, &CSampleEntity::TwoWayFuncOverlap));
-
-		AddTestMethodEntry(
-			new MethodTestCaseT<SampleService_TwoWayFuncNotOverlap_Req, SampleService_TwoWayFuncNotOverlap_Ans>(
-				this,
-				&CSampleEntity::TwoWayFuncNotOverlap));
-
 	}
 
-	void OnExam(CSmartPointer<ITransactionContext> pTransactionContext) override
+	TESTCASE_OVERRIDE_ON_EXAM_AND_IMPLEMENT()
+
+	ErrorCodeEnum CustomTestCase() override
 	{
 		LOG_FUNCTION();
-
-		ErrorCodeEnum testResult = RunTestCase();
-		if (testResult == Error_Succeed || testResult == Error_IgnoreAll) {
-			pTransactionContext->SendAnswer(Error_Succeed);
-		} else {
-			pTransactionContext->SendAnswer(testResult);
-		}
+		/** User add any other test logical*/
+		return Error_Succeed;
 	}
 
 	ErrorCodeEnum OnewayFuncOverlap(
@@ -210,9 +223,13 @@ public:
 
 		/** Set ctx->Req*/
 
-		TwoWayFuncNormal(ctx);
+		/*The aim function you would like test.*/
+		if (Error_Succeed == TwoWayFuncNormal(ctx)) 
+		{
+			/** Check ctx->Ans*/
 
-		/** Check ctx->Req*/
+			/** Overwite the Result using pTransactionContext->SendAnswer()*/
+		}
 	}
 
 	void TestTwoWayFuncWithID(CSmartPointer<ITransactionContext> pTransactionContext)

+ 8 - 1
spbase/SpEntityPrivilege.cpp

@@ -60,8 +60,15 @@ static ErrorCodeEnum ControlEntity(
 	iobuffer_write(req_pkt, IOBUF_T_I4, &v, 0);
 	if (call_type == SHELL_CMD_REQ_ENTITY_START)
 		iobuffer_write(req_pkt, IOBUF_T_STR, cmd_line, -1);
-	else if (call_type == SHELL_CMD_REQ_ENTITY_TEST)
+	else if (call_type == SHELL_CMD_REQ_ENTITY_TEST) {
+		/** prohibit user from sending test call in the absence of test mode   [5/20/2020 Gifur] */
+		if (param1 == 1/*Test_Examine*/ && env->cfg->args->test_mode == 0) {
+			iobuffer_destroy(req_pkt);
+			return Error_NoPrivilege;
+		}
 		iobuffer_write(req_pkt, IOBUF_T_I4, &param1, 0);
+	}
+		
 
 	SpAsyncWaitRPC *pAsyncWait	= new SpAsyncWaitRPC(pEntity, &req_pkt, call_type);
 	ErrorCodeEnum Error = pAsyncWait->Begin();