Setting up the Advantage CSP API Setting up the Advantage CSP Server API for accessing any object can be straightforwardly accomplished by creating an API entry within the configuration section. This setup allows the configuration of the same object under various API names, enabling the provision of distinct authentication levels or workflows to different clients. This flexible approach ensures tailored access and functionality for diverse client needs. Advantage CSP WebAPI Configuration Creation Date: March 21, 2024 Created By: Oren Shapiro View most recent version # After logging in, you’re likely to be greeted by the admin dashboard. Look for the primary admin navigation pane, often located on the left side or at the top of the page. Here, find and select the “Configuration” option. Visualize a navigation 1. Click on Domain Management; Expanding Configuration Options: Upon selecting “Configuration,” a submenu or list of options should appear. Expanding the node reveals additional settings such as “Site,” “Social,” and “System tabs.” 2. Navigating to Configuration: 3. Accessing System Settings: From the expanded menu options under “Configuration,” click on “System.” This action will change the main admin workspace to display various system settings. You might see a grid or list layout showcasing different system settings. 4. Selecting API Settings: Within the System settings, look for “API Settings” or a similar term indicating settings related to the Application Programming Interface. There might be an icon or a pencil symbol to edit or view these settings. 5. Adding a New API Entry: In the API Settings view, there should be an option to add a new API object or entry, often labelled as “Add” or “Create New.” This could be a button or a link. This option will allow you to configure a new API endpoint or access rule. 6. Configuring API Access: After selecting “Add” to create a new API entry, you’ll have a form or fields to enter the required information for your new API object. This could include specifying the type of object, access permissions, keys, or other relevant details nec 7. Type "the name of your business object" 8. The auto-complete will reveal a dropdown for selection 9. Check Use Cache if applicable 10. Set your cache expiration 11. Select API Security, i.e. Secure read / Secure write from Permissions 12. Click on Update 13. Click on Save Advantage Server API Security This document outlines the security implementation for accessing BusinessObjects defined as "Secure" in the Advantage Server configuration. It covers the server-side implementation, client-side usage, and provides examples of API calls. Server-Side Implementation 1. AdvantageSecureContentControllerHandler To enable secure access, implement the AdvantageSecureContentControllerHandler class: In order to access BusinessObjects that have been defined as “Secure” in the configuration, an “AdvantageSecureContentControllerHandler” must be defined and added to the “AdvantageCSP.API.WebApiConfig”. Advantage-SecureContentControllerHandler namespace AdvantageCSP.WebAPI { public class SecureContentControllerHandler : AdvantageSecureContentControllerHandler { private static string myKey = "d32b2c8c-dc57-4978-bf98-7c82db7c027c"; private class AuthResponse { public string UserName { get; set; } public string Password { get; set; } public DateTime TimeStamp { get; set; } } public override AdvantageAuthResponse AuthenticateRequest(HttpRequestMessage request) { var credentials = ParseAuthorizationHeader(request); if (credentials != null) return new AdvantageAuthResponse() { Success = true }; else return new AdvantageAuthResponse() { Success = false }; } private AuthResponse ParseAuthorizationHeader(HttpRequestMessage request) { try { AuthResponse result = new AuthResponse(); string authHeader = null; var auth = request.Headers.Authorization; if (auth != null && auth.Scheme == "Basic") authHeader = auth.Parameter; if (string.IsNullOrEmpty(authHeader)) return null; authHeader = Encryption.Decrypt(Encoding.Default.GetString(Convert.FromBase64String(authHeader)), myKey); var tokens = authHeader.Split(':'); if (tokens.Length < 3) return null; result.UserName = tokens[0]; result.Password = tokens[1]; result.TimeStamp = DateTimeOffset.FromUnixTimeSeconds(Convert.ToInt64(tokens[2])).DateTime; return result; } catch { return null; } } // Sample of some authorization header for use in secure api. public static string GenerateAuthHeader() { string username = "SomeName"; string password = "SomePassword"; string datetime = DateTimeOffset.UtcNow.ToUnixTimeSeconds().ToString(); byte[] data = Encoding.ASCII.GetBytes(Encryption.Encrypt($"{username}:{password}:{datetime}", myKey)); return "{"Authorization": "Basic " + Convert.ToBase64String(data).ToString() + ""}"; } } } Global.asax Configuration Global.asax Configuration<script runat="server"> void Application_Start(object sender, EventArgs e) { AdvantageCSP.API.WebApiConfig.Register(GlobalConfiguration.Configuration, new AdvantageCSP.WebAPI.SecureContentControllerHandler()); } </script> Advantage Client API This method will return a list of objects defined as API accessible. Follow the instructions for implementation, including routing and optional security Advantage Server API Security & Client API Advantage Client API Wrapper Advantage CSP offers a client wrapper to simplify retrieving data. Reference the API wrapper JS file from the Advantage server as follows: Advantage Client API Wrapper<script src="//yourserver.com/AdvantageCMS.Resource.WebResource.axd?d=AdvantageAPI.js" type="text/javascript"></script> The `AdvantageAPI.js` file provides objects to assist in defining method calls. Here's a sample implementation: <script type="text/javascript"> function Sample() { // Create the request context for API Article, language English var tmp = new AdvContentRequest("Article", "en"); // Specify secure API access tmp.Authenticate = true; // Specify the security header (custom) tmp.Header = 'encrypted security context'; // OPTIONAL: Specify an index tmp.set_Index("Author", 'Ernest Hemingway', advDataType.String, advCompare.Like); // OPTIONAL: Specify a sort order tmp.AddSort(advDirection.Asc, 'Title'); // OPTIONAL: Specify field list (reduces payload from server) tmp.AddField("Title"); tmp.AddField("ArticleDate"); tmp.AddField("Author"); tmp.AddField("ArticleImage"); // Call function to return data advGetContent(tmp, showResult, showResult); // Get the data. } function showResult(resp) { // Show the pretty result var pretty = JSON.stringify(resp, undefined, 2); alert(pretty); } </script> POST Get All Objects Example Below is a basic list request sample for retrieving object "article" for language "en" using a secure method: POST Get All Objects Example// Endpoint: yourserver.com/advantageapi/secure/content/get/article/en // HEADERS Content-Type: application/json Accept: application/json Authorization: Basic {encrypted_credentials} // BODY (raw, application/json) { "Index": { "Key": "Author", "DataType": "string", "Comparison": "equals", "Value": "The Enginess Team" }, "FieldList": ["Author", "ArticleDate", "ArticleImage", "Title"], "SortList": [{"FieldName": "ArticleDate", "Direction": "asc"}, {"FieldName": "Title", "Direction": "desc"}], "Filter": [{"Key": "Title", "DataType": "string", "Comparison": "like", "Value": "https"}] } POST Get Filtered Objects Example An advanced list request sample for retrieving "article" for language "en" with filtering: POST Get Filtered Objects Example// Endpoint: yourserver.com/advantageapi/secure/content/get/article/en // HEADERS Content-Type: application/json Accept: application/json Authorization: Basic {encrypted_credentials} // BODY (raw, application/json) { "Index": { "Key": "Author", "DataType": "string", "Comparison": "equals", "Value": "The Enginess Team" }, "FieldList": ["Author", "ArticleDate", "ArticleImage", "Title"], "SortList Security Considerations Always use HTTPS for API communications. Regularly rotate the encryption key used for the authorization header. Implement rate limiting and monitoring for API abuse. Validate and sanitize all input on the server side. Troubleshooting If authentication fails, check the encryption key and the format of the authorization header. For performance issues, consider optimizing database queries and using caching where appropriate. Monitor server logs for any recurring errors or suspicious activity.