Functions are
Custom operations exposed by an OData service that must always return data and must never modify data on the backend so that there are no observable side effects.
That is they're always GET HTTP operations.
In this blog post, we will look into how to implement Custom Functions in the
SAP Cloud Application Programming (CAP) model by leveraging
CAP Java SDK Maven Plugin.
Create a CAP Java Application using SAP Business Application Studio (BAS)
Step1: Generate a Java project
- Create a Dev Space in BAS with any name, select "Full Stack Cloud Application". Start the DevSpace.
- Open a terminal in the Development space and run the below command in the directory:
/home/user/projects
to create an initial java project.
mvn -B archetype:generate -DarchetypeArtifactId=cds-services-archetype -DarchetypeGroupId=com.sap.cds \
-DarchetypeVersion=RELEASE \
-DgroupId=com.sap.cap -DartifactId=function-import-service -Dpackage=com.sap.cap.functionimport
From the main menu, choose
File >
Open Workspace to open the project.
Step2: Create a CDS Service and define your Function
In
srv folder, create a file named "customfunctions.cds".
Add the following service definition to the file -
service CustomFunctionService {
function getCurrentDateTime() returns Timestamp;
}
This creates an OData Function with the name
getCurrentDateTime
.
Step3: Compile the Service definition
In the terminal, run the following command to compile the project -
mvn clean install
During compilation, the
CAP Java SDK Maven Plugin automatically generates
Event Context objects for Functions defined in the CDS model, which provide
type-safe access to the function parameters and
allow to set the return values.
Check under
srv/src/gen/java/cds/gen
for the generated Event Context files. We would be utilizing the below-highlighted fields for implementing Event Handler in our next step.
Step4: Implement a Custom Event Handler
In SAP Cloud Application Programming Model, Functions are implemented through Event Handlers. For each function, an
On phase is defined, which implements
- Business Logic
- Provides return value
Create a Java file "CustomFunctionsHandler.java" under
srv/src/main/java/com/sap/cap/functionimport
with the following content -
package com.sap.cap.functionimport;
import java.time.Instant;
import com.sap.cds.services.handler.EventHandler;
import com.sap.cds.services.handler.annotations.On;
import com.sap.cds.services.handler.annotations.ServiceName;
import org.springframework.stereotype.Component;
import cds.gen.customfunctionservice.CustomFunctionService_;
import cds.gen.customfunctionservice.GetCurrentDateTimeContext;
@Component
@ServiceName(CustomFunctionService_.CDS_NAME)
public class CustomFunctionsHandler implements EventHandler {
@On(event = GetCurrentDateTimeContext.CDS_NAME)
public void onGetCurrentDateTime(GetCurrentDateTimeContext context) {
context.setResult(Instant.now());
}
}
Step5: Run the Application
Start the application with the below command in terminal -
mvn clean spring-boot:run
A notification saying "A service is listening to port 8080" will appear at the bottom right, choose
Expose and Open. The application will be started at default port: 8080
Step6: Check OData metadata and Custom Function Response
Click on
$metadata from the welcome page
- $metadata of the CustomFunctionService returns the Function name
getCurrentDateTime
we defined in the CDS file
2. Replace the
$metadata in the URL with the Function name
getCurrentDateTime()
.
Response of the Custom Function is returned as shown below
Custom Functions with Parameters
Please follow the same steps as mentioned above, just replace the content as follows
- Define a function with parameters in the CDS service file.
service CustomFunctionService {
function displayUserName(userName: String) returns String;
}
2. Compile the project which auto-generates the following Event Context files. Notice the auto-generated
getter and setter methods for the parameter
userName
.
3. Create an Event Handler file with the following content -
package com.sap.cap.functionimport;
import com.sap.cds.services.handler.EventHandler;
import com.sap.cds.services.handler.annotations.On;
import com.sap.cds.services.handler.annotations.ServiceName;
import org.springframework.stereotype.Component;
import cds.gen.customfunctionservice.CustomFunctionService_;
import cds.gen.customfunctionservice.DisplayUserNameContext;
@Component
@ServiceName(CustomFunctionService_.CDS_NAME)
public class CustomFunctionsHandler implements EventHandler {
@On(event = DisplayUserNameContext.CDS_NAME)
public void onDisplayName(DisplayUserNameContext context) {
String name = context.getUserName();
context.setResult("Hello "+name);
}
}
4. Start the application as done before, and open the
$metadata endpoint.
The function
displayUserName
and the parameter
userName
is visible as shown below
5. Replace
$metadata in the URL with the Function and parameter name as
/displayUserName(userName='Harry%20Potter')
Conclusion
- In this blog post, we've talked about how to implement OData (V4) Custom Functions along with parameters in SAP Cloud Application Programming Model.
- If you have any questions please submit them here in the relevant tag Q&A area. I will be happy to answer.
- You're welcome to provide feedback in the comment section.