Skip to content

RestControllers

U-LPT00135\sumeetc edited this page Jan 2, 2016 · 2 revisions

REST Controller

REST Controllers provide custom execution logic for configured HTTP requests over specific HTTP methods. Request URI's and HTTP Verbs (GET,PUT,POST,DELETE etc) are mapped to configured C++ class methods.

All Serializable POCO objects can be mapped as request and response entities in a given rest controller.

We will consider a REST controller having the following functions

  1. Add 2 numbers

  2. Given base b and exponent n return the Exponentiation bn

  3. Read a vector of integers and return the same as response

  4. Read an Object and return the same

  5. Read a vector of Objects and return the same

  6. Upload a multipart form with one file and one parameter

  7. Upload a multipart form with 3 files and one parameter

  8. Upload a multipart form with a vector of files and one parameter

    XML Based

    (Headers)

    Test.h

     #ifndef TEST_H_
     #define TEST_H_
     #include "string"
     using namespace std;
     
     class Test {
     	int id;
     	string name;
     public:
     	Test();
     	virtual ~Test();
         int getId() const;
         void setId(int);
         string getName() const;
         void setName(string);
         bool operator<(Test t) const;
     };
     
     #endif
    

    TestMany.h

     #ifndef TESTMANY_H_
     #define TESTMANY_H_
     #include "Test.h"
     #include "vector"
     #include "YObject.h"
     #include "queue"
     #include "list"
     class TestMany {
     	vector<int> vpi;
     public:
     	Test t;
     	int y;
     	vector<int> vi;
     	vector<string> vs;
     	vector<double> vd;
     	vector<long> vl;
     	vector<bool> vb;
     	vector<short> vsh;
     	vector<YObject> vyo;
     	list<int> li;
     	std::queue<short> qsh;
     public:
     	void setVpi(vector<int> vpi)
     	{
     		this->vpi = vpi;
     	}
     	vector<int> getVpi()
     	{
     		return vpi;
     	}
     	TestMany();
     	virtual ~TestMany();
     };
     
     #endif
    

    YObject.h

     #ifndef YOBJECT_H_
     #define YOBJECT_H_
     #include "string"
     using namespace std;
     class YObject
     {
     	public:
     		int i;
     		string j;
     		float c;
     };
     
     #endif
    

    DefaultRestController.h

     #ifndef DEFAULTRESTCONTROLLER_H_
     #define DEFAULTRESTCONTROLLER_H_
     
     #include <math.h>
     #include <iostream>
     #include "vector"
     #include "TestMany.h"
     #include <fstream>
     #include "CastUtil.h"
     
     class DefaultRestController {
     public:
     	int addNumbers(int,int);
     	double power(int,int);
     	vector<int> testVector(vector<int>);
     	TestMany testObject(TestMany);
     	vector<TestMany> testVectorObject(vector<TestMany> param);
     	string testUploadFile(ifstream* ifs, string param);
     	string testUploadFileMulti1(ifstream* ifs1, ifstream* ifs2, ifstream* ifs3, string param);
     	string testUploadFileMulti2(vector<ifstream*> vifs, string param);
     };
     
     #endif
    

    (Source)

     #include "DefaultRestController.h"
     
     int DefaultRestController::addNumbers(int a, int b)
     {
     	cout << "Processed input request inside DefaultRestController for addNumbers..." << endl;
     	return a + b;
     }
     
     double DefaultRestController::power(int base, int exponent)
     {
     	cout << "Processed input request inside DefaultRestController for power..." << endl;
     	return pow((double)base, (double)exponent);
     }
     
     vector<int> DefaultRestController::testVector(vector<int> param)
     {
     	cout << "Processed input request inside DefaultRestController for testVector..." << endl;
     	return param;
     }
     
     TestMany DefaultRestController::testObject(TestMany testMany)
     {
     	cout << "Processed input request inside DefaultRestController for testObject..." << endl;
     	return testMany;
     }		
     
     vector<TestMany> DefaultRestController::testVectorObject(vector<TestMany> param)
     {
     	cout << "Processed input request inside DefaultRestController for testVectorObject..." << endl;
     	return param;
     }
     
     string DefaultRestController::testUploadFile(ifstream* ifs, string param)
     {
     	string vals;
     	unsigned int siz = 0;
     	if (ifs!=NULL && ifs->is_open())
     	{
     		ifs->seekg(0, ios::end);
     		siz = ifs->tellg();
     	}
     	vals = "Uploaded File Size = " + CastUtil::lexical_cast<string>(siz);
     	vals += "\nField value passed = " + param;
     	cout << "Processed input request inside DefaultRestController for testUploadFile..." << endl;
     	return vals;
     }
     
     string DefaultRestController::testUploadFileMulti1(ifstream* ifs1, ifstream* ifs2, ifstream* ifs3, string param)
     {
     	string vals;
     	unsigned int siz = 0;
     	if (ifs1!=NULL && ifs1->is_open())
     	{
     		ifs1->seekg(0, ios::end);
     		siz = ifs1->tellg();
     	}
     	vals = "Uploaded File1 Size = " + CastUtil::lexical_cast<string>(siz);
     	siz = 0;
     	if (ifs2!=NULL && ifs2->is_open())
     	{
     		ifs2->seekg(0, ios::end);
     		siz = ifs2->tellg();
     	}
     	vals += "\nUploaded File2 Size = " + CastUtil::lexical_cast<string>(siz);
     	siz = 0;
     	if (ifs3!=NULL && ifs3->is_open())
     	{
     		ifs3->seekg(0, ios::end);
     		siz = ifs3->tellg();
     	}
     	vals += "\nUploaded File3 Size = " + CastUtil::lexical_cast<string>(siz);
     	vals += "\nField value passed = " + param;
     	cout << "Processed input request inside DefaultRestController for testUploadFileMulti1..." << endl;
     	return vals;
     }
     
     string DefaultRestController::testUploadFileMulti2(vector<ifstream*> vifs, string param)
     {
     	string vals;
     	for(int i=0;i<(int)vifs.size();++i) {
     		ifstream* ifs = vifs.at(i);
     		unsigned int siz = 0;
     		if (ifs!=NULL && ifs->is_open())
     		{
     			ifs->seekg(0, ios::end);
     			siz = ifs->tellg();
     		}
     		vals += "Uploaded File" + CastUtil::lexical_cast<string>(i) + " Size = " + CastUtil::lexical_cast<string>(siz) + "\n";
     	}
     	vals += "Field value passed = " + param;
     	cout << "Processed input request inside DefaultRestController for testUploadFileMulti2..." << endl;
     	return vals;
     }
    

    (Configuration)

     <app>
     	<restcontrollers>
     		<restcontroller class="DefaultRestController" path="/rest/path/rest1/">
     			<restfunction name="addNumbers" path="add/{1}/{2}" meth="GET"
     				statusCode="200">
     				<param type="int" name="1" from="path" />
     				<param type="int" name="2" from="path" />
     			</restfunction>
     		</restcontroller>
     		<restcontroller class="DefaultRestController" path="/rest/reqparam/rest1/">
     			<restfunction name="addNumbers" path="add" meth="GET"
     				statusCode="200">
     				<param type="int" name="1" from="reqparam" />
     				<param type="int" name="2" from="reqparam" />
     			</restfunction>
     		</restcontroller>
     		<restcontroller class="DefaultRestController" path="/rest/postparam/rest1/">
     			<restfunction name="addNumbers" path="add" meth="POST"
     				statusCode="200">
     				<param type="int" name="1" from="postparam" />
     				<param type="int" name="2" from="postparam" />
     			</restfunction>
     		</restcontroller>
     		<restcontroller class="DefaultRestController" path="/rest/header/rest1/">
     			<restfunction name="addNumbers" path="add" meth="GET"
     				statusCode="200">
     				<param type="int" name="a" from="header" />
     				<param type="int" name="b" from="header" />
     			</restfunction>
     		</restcontroller>
     		<restcontroller class="DefaultRestController" path="/rest/path1/rest2">
     			<restfunction name="addNumbers" path="+/{1}/{2}" meth="GET"
     				statusCode="200">
     				<param type="int" name="1" from="path" />
     				<param type="int" name="2" from="path" />
     			</restfunction>
     		</restcontroller>
     		<restcontroller class="DefaultRestController" path="/rest3">
     			<restfunction name="addNumbers" path="ad/{1}/{2}" meth="GET"
     				statusCode="200">
     				<param type="int" name="1" from="path" />
     				<param type="int" name="2" from="path" />
     			</restfunction>
     		</restcontroller>
     		<restcontroller class="DefaultRestController">
     			<restfunction name="power" meth="GET"
     				path="/rest/controller/base{1}/power/exp{2}" statusCode="200">
     				<param type="int" name="1" from="path" />
     				<param type="int" name="2" from="path" />
     			</restfunction>
     		</restcontroller>
     		<restcontroller class="DefaultRestController">
     			<restfunction name="addNumbers" meth="GET"
     				path="/addNumbers/{1}/{2}" statusCode="200">
     				<param type="int" name="1" from="path" />
     				<param type="int" name="2" from="path" />
     			</restfunction>
     		</restcontroller>
     		<restcontroller class="DefaultRestController" path="/restvec">
     			<restfunction name="testVector" path="tstvec" meth="POST"
     				statusCode="200">
     				<param type="vector-of-int" from="body" />
     			</restfunction>
     		</restcontroller>
     		<restcontroller class="DefaultRestController" path="/restvecobj">
     			<restfunction name="testVectorObject" path="tstvecobj"
     				meth="POST" icontentType="application/json" statusCode="200">
     				<param type="vector-of-TestMany" from="body" />
     			</restfunction>
     		</restcontroller>
     		<restcontroller class="DefaultRestController" path="/restobj">
     			<restfunction name="testObject" path="tstobj" meth="POST"
     				icontentType="application/json" ocontentType="application/json"
     				statusCode="200">
     				<param type="TestMany" from="body" />
     			</restfunction>
     		</restcontroller>
     		<restcontroller class="DefaultRestController" path="/restvecobj">
     			<restfunction name="testVectorObject" path="tstvecobj.xml"
     				meth="POST" icontentType="application/xml" statusCode="200">
     				<param type="vector-of-TestMany" from="body" />
     			</restfunction>
     		</restcontroller>
     		<restcontroller class="DefaultRestController" path="/restobj">
     			<restfunction name="testObject" path="tstobj.xml" meth="POST"
     				icontentType="application/xml" statusCode="200">
     				<param type="TestMany" from="body" />
     			</restfunction>
     		</restcontroller>
     		<restcontroller class="DefaultRestController" path="/restupload">
     			<restfunction name="testUploadFile" path="uploadFile"
     				meth="POST" icontentType="multipart/form-data" statusCode="200">
     				<param type="filestream" name="file" from="multipart-content" />
     				<param type="string" name="field" from="multipart-content" />
     			</restfunction>
     		</restcontroller>
     		<restcontroller class="DefaultRestController" path="/restupload">
     			<restfunction name="testUploadFileMulti1" path="uploadFileMulti1"
     				meth="POST" icontentType="multipart/form-data" statusCode="200">
     				<param type="filestream" name="file1" from="multipart-content" />
     				<param type="filestream" name="file2" from="multipart-content" />
     				<param type="filestream" name="file3" from="multipart-content" />
     				<param type="string" name="field" from="multipart-content" />
     			</restfunction>
     		</restcontroller>
     		<restcontroller class="DefaultRestController" path="/restupload">
     			<restfunction name="testUploadFileMulti2" path="uploadFileMulti2"
     				meth="POST" icontentType="multipart/form-data" statusCode="200">
     				<param type="vector-of-filestream" name="files" from="multipart-content" />
     				<param type="string" name="field" from="multipart-content" />
     			</restfunction>
     		</restcontroller>
     	</restcontrollers>
     </app>
    

    Marker Based

    (Header)

     #ifndef DEFAULTRESTCONTROLLER_H_
     #define DEFAULTRESTCONTROLLER_H_
     
     #include <math.h>
     #include <iostream>
     #include "vector"
     #include "TestMany.h"
     #include <fstream>
     #include "CastUtil.h"
     
     #pragma @RestController path="/restful"
     class DefaultRestController {
     public:
     	#pragma @GET path="/add" statusCode="200"
     	int addNumbers(
     		#pragma @QueryParam name="a"
     		int,
     		#pragma @QueryParam name="b"
     		int);
    
     	#pragma @GET path="/{b}/power/{n}" statusCode="200"
     	double power(
     		#pragma @PathParam name="b"
     		int,
     		#pragma @PathParam name="n"
     		int);
    
     	#pragma @POST path="/vectorI" statusCode="200"
     	vector<int> testVector(
     		#pragma @Body
     		vector<int>);
    
     	#pragma @POST path="/object" statusCode="200"
     	TestMany testObject(
     		#pragma @Body
     		TestMany);
    
     	#pragma @POST path="/vectorObject" statusCode="200"
     	vector<TestMany> testVectorObject(
     		#pragma @Body
     		vector<TestMany> param);
    
     	#pragma @POST path="/uploadOne" statusCode="200"
     	string testUploadFile(
     		#pragma @MultipartContent name="file"
     		ifstream* ifs, 
     		#pragma @MultipartContent name="field"
     		string param);
     	
     	#pragma @POST path="/uploadMulti" statusCode="200"
     	string testUploadFileMulti1(
     		#pragma @MultipartContent name="file1"
     		ifstream* ifs1, 
     		#pragma @MultipartContent name="file2"
     		ifstream* ifs2, 
     		#pragma @MultipartContent name="file3"
     		ifstream* ifs3, 
     		#pragma @MultipartContent name="field"
     		string param);
    
     	#pragma @POST path="/uploadVecFiles" statusCode="200"
     	string testUploadFileMulti2(
     		#pragma @MultipartContent name="files"
     		vector<ifstream*> vifs, 
     		#pragma @MultipartContent name="field"
     		string param);
     };
     
     #endif
    

    (Source)

     Same as above
    
Clone this wiki locally