Self-Made DesignStudio SDK Dashboard Comments
Dear all,
Have you been wondering when you would finally be able to put comments on your Design Studio dashboards in a decent and tremendously customizable way for free? Well, that day is today!
In the following sections I will showcase my new component ConVista EasyComment which is published open-source on GitHub, talk about the backend integration, comment saving & loading and the overall commentary architecture involved.
What do you get?
Obviously to put some comments you need a place where you can do that. I decided to use a WYSIWYG (What You See Is What You Get) HTML editor. There are a couple of libraries out there providing editors like that. My choice was CKEditor because of a well documented API, a suitable developer license and the ability to Paste from MS Word. You could also look into tinymce and Froala just to mention a few more.
You can extend gracefully by implementing your own editor plugins by the way.
Fig.1 Demo dashboard
My SDK component ConVista EasyComment comes with lots of built in functionality like spell-checking, multi-language support, the ability to add images, an option to adjust the reading direction and many more. These features are provided by the CKEditor library out of the box.
The save button (icon on the bottom right of the toolbars) exposes its functionality to the DesignStudio SDK component event On Save Button Clicked. You can also extract/modify HTML content on the editor using the scripting methods getHTMLString and setHTMLString.
You can customize the toolbars to be shown through the component property Toolbar Settings. I used the new SDK 1.6 feature that allows to put complex objects on the contribution file for that. That way DesignStudio creates a table like input window:
Fig 2 Properties
You can activate/deactivate the toolbars one by one. For the Document section which contains the save button you can decide even on item level (but you can’t hide the save button ;-). Let’s put false on every item except for Editing and see what we get.
Fig 3 Reduced editor toolbar view
If you need more fine grained customization you will need to get back to me or adjust the coding on the SDK component yourself. Now let’s jump to the fun part.
On Saving and Loading
At first I am going to tell you about the frontend part which is covered by the EasyComment component and how to model a data structure to store our DesignStudio comments before actually moving over to the backend part to show you possible starting points to implement your individual solution.
To be able to actually persist and successfully load a comment for a specific DesignStudio object you need to identify the object itself and maybe its filter state. For static content this very easy and straightforward. We could just take the technical name of the targeted object as key and save our HTML-string along with it on a table on our backend. For dynamic content like charts with arbitrary complex filter possibilities this can be a very complicated task.
Some of the commercial DesignStudio commentary components approach this topic on the SAP backend by evaluating for example BEx query state and learn the object state from there. That way they can identify the right comment to load or with what key to store it. To get this done for all of the possible DesignStudio data sources like BEx queries, BW cubes, Universes, Custom SDK data sources, CSV files and HANA views is quite a lengthy task for an ABAP developer.
Don’t make this harder as it needs to be!
My approach is not going to cover all kinds of complex scenarios but it will be as easy as it gets and get the job done for many cases. At first I make the assumption that it is sufficient to store only a limited number of characteristics values to successfully identify the breakdown of a value on a component like a DesignStudio chart, crosstab, KPI-View or Scorecard. Let’s differentiate two cases:
- Static only content like DesignStudio texts or objects themselves and
- dynamic content like data breakdowns and key figures on Crosstabs or Charts.
All of the static content can be covered by its technical object name and the dashboard they are on for example:
Key Fields |
HTML Content |
|
DashboardID |
Object Technical Name |
|
MYDASH_1 |
Demo_dashboard |
<h1>This a comment for a dashboard itself</h1> |
MYDASH_1 |
SOME_QUERY |
<i>This is a general comment on a query</i> |
MYDASH_2 |
TEXT_TITLE |
<h2><b>This is a comment for a standard text</b></h2> |
Table 1 Static objects comment saving
Now on the dynamic stuff. From my experience many cases that need comments for key figure release processes for example, there is only a limited number of filter values involved. Often you can get away with an accounting basis, an accounting entity and a key date (single date, date ranges and etc.).
Key Fields |
HTML Content |
|||||
DashboardID |
Obj tech. Name |
Acc. Basis |
Acc. Entity |
Key date |
||
MYDASH_1 |
QUERY1 |
GAAP |
COMP1 |
10.03.2016 |
<p>some html content</p> |
|
MYDASH_1 |
HANA_CALC_VIEW |
GAAP |
COMP1 |
01.01.2016 |
<p>year end forecasts are looking good</p> |
|
MYDASH_1 |
CHART_1 |
|
COMP2 |
10.03.2016 |
<p> Please check the spike! </p> |
Table 2 Dynamic objects comment saving
How do you provide this data to the WebService?
DesignStudio offers lots of scripting methods that already provide what we need:
- DashboardID: Accessible through APPLICATION.getInfo().name
- Object technical Name: All SAP data sources (except SDK data sources) provide the method getInfo() which gives you access to the underlying meta data. The technical name is part of it.
- Accounting Basis, Accounting Entity and Key date: Data sources offer methods to retrieve key-value pairs for given dimensions and DesignStudio components like the Dimension Filter give the user the ability to filter certain values on demand. When working with filter variables you can for example use the following script to learn their current setting influenced by the user input during runtime:
var vars = DS_1.getVariables();
vars.forEach(function(element, index) {
if(element.inputEnabled){
DS_1.getVariableValueExt(element.name);
}
});
You could save the values for later usage with the ConVista EasyComment using the SCN community SDK component ARRAY.
Now that we learned how to retrieve keys to identify our data sets, we are ready to send some HTML-strings to the backend. Exciting, isn’t it!? Let me give you a simplified example.
As I already told you before, there is an event provided by the EasyComment component which gets triggered when you click the save button on the editor. Here is a script from a demo application:
//cache busting
var ccid = APPLICATION.getTickCount();
//retrieve an accounting entity
var bukrs = DROPDOWN_1.getSelectedValue();
//set http request method
me.setHttpMethod(“POST”);
me.setServerUrl(
“http://<sap backend>:<port>/sap/bc/<WebService Endpoint>?bukrs=”+bukrs+“&ccid=”+ccid
);
//Actually Trigger the save
me.saveHTMLOnServer();
This DesignStudio script sets up the HTTP parameters and sends a POST request to the server. The method saveHTMLOnServer internally retrieves the current HTML-string from the editor on execution. If everything on the backend went good, you just saved your first comment!
To retrieve it again you need some more scripting and an approach how to expose that functionality. Usually people go for selection events in some sort of way. Let’s check out an example with a Dropdown.
Fig 4 Editor full cycle interaction
Once the user selects an entity from the dropdown, the components On Select method fires. In there I put the following scripting:
//Get the currently selected entity
var bukrs = me.getSelectedValue();
//Cache busting
var ccid = APPLICATION.getTickCount();
COMMENT_1.setServerUrl(
“http://<sap backend>:<port>/sap/bc/<WebService Endpoint>?bukrs=”+bukrs+“&ccid=”+ccid
);
//Set HTTP request method
COMMENT_1.setHttpMethod(“GET”);
//Actually trigger the load
COMMENT_1.loadHTMLFromServer();
The above script loads the saved comment into the editor according to the selection on the dropdown. If you need to more than just an accounting entity to select your comment, like in my example, you will have to enrich this scripting slightly (e.g. put some more URL parameters etc.).
In light of above you can easily imagine how to extend this approach to serve your specific needs without aiming for a general solution for every possible scenario and putting hundreds of hours. Now let’s have a look at a possible SAP backend WebService class implementation to take care of the saving and loading of our precious HTML-strings.
Integration of the SDK component with a server
In order to be able to save the HTML content you add to the editor, I implemented the DesignStudio SDK component to be ready to integrate with a RESTful Web Service. I am using the standard JavaScript object XMLHttpRequest to manage the communication from the browser to the backend. Of course Cross-Origin Resource Sharing (CORS) problems might apply at this point if you are hosting your dashboard on a different server than the backend. To overcome that browser security problem you have to setup your backend code to supply two HTTP headers on the HTTP response:
Access-Control-Allow-Origin: true
Access-Control-Allow–Credentials: true
I will show an easy ABAP example below. At first you have to provide an ABAP class which will serve as the handler for the WebService communication.
- ABAP class setup
Create a standard class and put it on your local objects or a development package.
Put the following two interfaces to provide your custom implementation for the SAP standard HTTP interfaces.
Once you save, the class structure will immediately be generated and look something like this:
In order to put your custom WebService behavior you will have to implement the method HANDLE_REQUEST. Before that there is one more step. We need to register this class with an ICF node. To do so, call transaction SICF and create a new node under default_host > sap > bc.
Put your class under the handler list and save. Go back and activate the ICF node. Hit test to learn your WebService endpoint URL and check if the registration worked. You will need that URL for the DesignStudio scripting and also for easy testing purposes with your browser.
Note that every user induced URL call on a browser is basically an HTTP GET request.
- HTTP CORS setup and HANDLE_REQUEST implementation
Now I am going to show you the essential ABAP code to get started. You need to be able to retrieve URL parameters from the HTTP requests, put CORS headers on your response and send the response to the client. This is done using SAP standard interface methods:
constants:
lc_header_mimetype_name type string value ‘Content-Type’,
lc_header_mimetype_value_html type string value ‘text/HTML; charset=utf-8’,
lc_header_aca_origin type string value ‘Access-Control-Allow-Origin’,
lc_header_aca_credentials type string value ‘Access-Control-Allow-Credentials’,
lc_true type string value ‘true’.
data: _request_method type string,
lt_inputparams type tihttpnvp,
ls_inputparams like line of lt_inputparams,
ld_bukrs type i,
ld_html_string type string,
ld_cors_callee type string,
ld_request_payload type string.
“Get passed parameters
call method server->request->get_form_fields
changing
fields = lt_inputparams.
“Get passed payload, HTML data
call method server->request->get_cdata
receiving
data = ld_request_payload.
“ CORS setup
ld_cors_callee = ‘http://<server hosting DesignStudio>:<port>’.
“Translate Input Parameters to Uppercase
loop at lt_inputparams assigning <ls_inputparams>.
translate: <ls_inputparams>–name to upper case.
case <ls_inputparams>–name.
when ‘BUKRS’.
ld_bukrs = <ls_inputparams>–value.
endcase.
endloop.
_request_method = server->request->get_header_field( name = ‘~request_method’ ).
“Determine if method is get or post.
if _request_method = ‘GET’.
“set the response mimetype to HTML
server->response->set_header_field
( name = lc_header_mimetype_name
value = lc_header_mimetype_value_html ).
“Set CORS access control to avoid browser policy restrictions
server->response->set_header_field
( name = lc_header_aca_origin
value = ld_cors_callee ).
server->response->set_header_field
( name = lc_header_aca_credentials
value = lc_true ).
“Do your table loading implementation here and assign to ld_html_string
“set the cdata response to the text
server->response->set_cdata( data = ld_html_string ).
elseif _request_method = ‘POST’ .
“set the response mimetype to HTML
server->response->set_header_field
( name = lc_header_mimetype_name
value = lc_header_mimetype_value_html ).
“Set CORS access control to avoid browser policy restrictions
server->response->set_header_field( name = lc_header_aca_origin
value = ld_cors_callee).
server->response->set_header_field
( name = lc_header_aca_credentials
value = lc_true ).
“Do your table saving implementation here and send given html back to have a graceful answer since the SDK component is “assigning back the data coming from the server to the editor “right away
“set the cdata response to the text
server->response->set_cdata( data = ld_request_payload ).
endif.
Make sure you send the send HTML-string back on POST requests because the EasyComment component relies on setting the HTML response to the editor as assurance that the saving worked. You could write a message here if something is wrong too. Further error handling is not implemented yet.
- Tables
To get you started have a look at the table examples in the previous section. Put the table coding at the sections highlighted in red above on the ABAP code.
Once all of that is done, put an example value on your table and make a browser GET request using the URL we remembered before. If that works, your WebService is ready to serve and you can start integrating with EasyComment. Now start saving some comments even with images attached! 🙂
Fig 5 EasyComponent editor with image on comment
Commentary Lifecycle (Commentary Solution Architecture)
To sum up the technical part I would like to provide a high level view on what I showed you in detail before.
Fig 6 Commentary Lifecycle Deployment View
In DesignStudio you need to put some logic to trigger the RESTful WebService and think about how to make that accessible to the user during runtime. On the backend you need to provide the communication endpoint for the RESTful WebService to deal with the HTTP requests. In my case that was SAP BW but the implementation is by no means limited to that. You could call any other system.
Fig 7 Commentary Lifecycle Implementation View
This sequence diagram visualizes the function calls on the involved software instances. DesignStudio scripting and events trigger internal methods on the EasyComment SDK component. As a result the component communicates with the backend to actually save and load HTML content. The callbacks deliver the content to the frontend.
What’s next?
As a next step I want to implement, what I call “Live-Commentary”. This means you no longer need to save your html content actively by hitting the save button but just start typing and save immediately. This will be achieved using WebSockets which enable full-duplex communication. User-Authorization at a side, this will allow users to edit comments even in parallel, seeing what their colleague does right away. Some of you might be familiar with that behavior from google docs or similar applications. I will keep you posted as development progresses.
Final Words
You are now able to enrich your DesignStudio dashboards with shiny comments up to a complexity that suits your needs. The frontend technology to get you started is already setup and implemented. The only open task is to decide how to store your HTML content. I have shown you a possible starting point to get this done quick and easy. Now find yourself an ABAP developer or roll up your own sleeves and have fun commenting.
You can get the component by installing the ConVista SDK components package which is available on GitHub:
ConVista-ds-sdk-visualizations by MartinPankraz
As always feel free to leave comments and ask lots of follow up questions.
Yours
Martin
Hi Martin,
thank you for sharing! this is really helpfull.
one very slight comment on ABAP code:
insert line
field-symbols: <ls_inputparams> type ihttpnvp.
data definition of ls_inputparams is obsolete.
otherwise it´s plug and play.
design studio test app + sicf service on Netweaver was set up in ~30 min on sandbox systems (without persisting data).
thank you,
Andreas
I am able to set the HTML text in commentary box i.e. setHTMLString() is working but getHTMLString() is not working.
Could you please let me the cause.
Hi Amardip,
So far you get only the current value on clicking the save button on the commentary component. Do you have a use case for retrieving it beforehand?
Kind regards
Martin
Hi Martin ,
I am also unable to fetch the content which is written by user . I have attached the screenshot of the code .Please let me know in case I need to do any modifications .
Hi Suraj,
Like I said before, the html text is only updated on saving it. In the meantime you cannot retrieve it using that script function. What would be the use case of reading the value without saving it?
Kind regards
Martin
Hi Martin,
Thanks for the reply.The code is written itself on the click of Save button .So upon clicking the Save button it should fetch the comments from clipboard .If possible I will try to share the code snippet along with screenshot .
Regards,
Suraj Grewal
Hi Suraj,
You are right. In the scenario you describe the internal html string is not update. The component only sends the correct string to the backend. I just fixed that. You can update the component from my GitHub repository as usual.
Kind regards
Martin
Hi Martin ,
Thanks a lot for your quick replies and quick fix .I will update the component from Github and will let you know in case of any concerns.
Regards,
Suraj Grewal
Hi Martin ,
Thanks a lot for the blog . There are few points in which I need your help .We have the requirement where we have to add comment for every cell of the report just like the Excel functionality.Our query is a cell based query .So for storing comment for every cell we need to define a key from which we can identify different cells .So for these we are reading the UID of selections for getting the exact location where user in trying to insert the comment in query as our query has more than 200 cells.Below is the code for fetching the UID.
var a=CROSSTAB_1.getSelection();
a.forEach(function(value, key) {
APPLICATION.alert(key);
value.forEach(function(element, index) {
APPLICATION.alert(element);
});
});
With the above code I will be getting 4 UIDs as my query is built on 2 structures so 1 alert will show the UID of structure and then UID of selection inside that structure .Same will continue for the second structure and second selection .
Just like excel I have added 2 custom option in context menu i.e. Show comment and insert comment .The issue which I am facing is it will read UID only at the time of clicking on insert comment .I cannot fetch values at the time of clicking on save button which is embedded on the comment component.
So either I need to create some global variable which I can access from JS of save button or I need to call webservice when I click on insert button then by ABAP code I need to update a Z table which will hold the current user logged in and the combination of UIDs . Once it will get updated I will get the comment component infront of me .Now I will write any content and will click on save button .
Now my concern is once save button is clicked how I can identify which UID I need to pick from Z table and corresponding to that ID only I need to place the comment?
Do I need to call the webservice 3 times for posting the comment ?
1.While fetching the UIDs from cell and store it in a Z table , POST method has to be called.
2.Once we will click on save button firstly we need to use GET method to read the UID from table
How we will read the UID from Z Table as we don't have UID stored anywhere in Design Studio when we click on save button ?
then call POST method to post the comment in Z table .
It will be very helpful to me . 🙂
Kind Regards,
Suraj Grewal
Hi Suraj,
Since you need to wait for the user to write a comment for a particular cell, you definitely need to remember the ids somewhere. I would suggest to keep it on the client for performance and maintenance reasons. You could either use global script variables or use the communities JSON object to store those values during runtime. That way there is only server call for actually storing the comment.
Kind regards
Martin
Hi Martin,
Good day!!
Thanks for the reply . The approach which I am trying to follow is
1. I will create 1 Textbox and will capture the UIDs as I am getting the UIDs with the above code .This operation will be performed when I will click on insert comment in context menu. We will set the visibility of textbox to false .
2.In the second step I will write the comment in comment box and will click on save button .Upon clicking on save button I will read the text of the textbox and will pass as a parameter in the URL in order to update the table .
Please let me know in case it will be a better option or not ?
Regards,
Suraj Grewal
Hi Suraj,
Your approach is as sound as the options I suggested. I'd say this is only a question of application design philosophy. If you favor the functionality of the text box over the other components, go for it.
Kind regards
Martin
Hi Martin,
I am trying to set the text on text box using getHTMLString() method,but it is not working.
Kindly have look over following script :
On save button clicked : OVERVIEW.setText(COMMENT_1.getHTMLString());
Hi Amardip,
Please see my comments above. There was a small bug regarding the method getHTMLString and you need to make sure to only call it after you hit save on the commentary box (for example on the on Save button event).
You can update the component from my GitHub repository as usual.
Kind regards
Martin
Hi Martin,
Yes,I have written the script OVERVIEW.setText(COMMENT_1.getHTMLString()); on save button event.
When I type something in commentary box and hit on save,it pass null values and shows blank "Overview" text.
Can you please provide your contact details,so that we can discus further.Thanks in advance.
Hi Amardip,
You can click on my profile and follow me. That way you are able to write private messages.
Did you make sure the SDK component is updated? I just tested again without any problems.
Kind regards
Martin
Hi Amardip,
I was also facing the same issue but after updating the SDK now I am getting Strings in HTML tags .
HI Martin,
I have started following you but I am unable to find you in chat room 🙁
Thanks & Regards,
Suraj Grewal
Hi Martin ,
Could you please suggest some idea where I can differentiate between the NW portal links as in the GET and POST both methods we need to put the URL .The initial part of the URL will be hardcoded .
“http://<sap backend>:<port>/sap/bc/<WebService Endpoint>?bukrs=”+bukrs+“&ccid=”+ccid.
Since normally we have 3 boxes , Dev, Quality and production so how to distinguish it in Design Studio level ?
Thanks & Regards,
Suraj Grewal
Hi Suraj,
you can use the component's method setServerUrl in combination with global script variables containing the server addresses. To determine on which system you are you can for example do the following:
var cuid = DS_1.getInfo().system;
if(cuid === g_sys_dev){
}else if (cuid === g_sys_qual)...
The CUID's of your systems should be different. I have seen environments however where that was not the case.
Let me know if that solves your problem.
Kind regards
Martin
Hi Martin,
I have followed your Blog, after updating latest version, now I can save comments successfully in backend system.
But, I have a requirement to display existing comments initially.
for that, I have created a button and written below code in "On click"
var BUKRS = INPUTFIELD_1.getValue();
var ccid = APPLICATION.getTickCount();
COMMENT_1.setServerUrl("<Webservice endpoint>?sap-client=100?sap-bukrs="+BUKRS+"&ccid="+ccid+"?");
COMMENT_1.setHttpMethod("GET");
COMMENT_1.loadHTMLFromServer();
My backend system has entries for the combination.
Backend code:
SPAN {
font-family: "Courier New";
font-size: 10pt;
color: #000000;
background: #FFFFFF;
}
.L0S33 {
color: #4DA619;
}
.L0S52 {
color: #0000FF;
}
.L0S55 {
color: #800080;
}
IF _request_method = 'GET' .
ld_cors_callee = "*".
SPAN {
font-family: "Courier New";
font-size: 10pt;
color: #000000;
background: #FFFFFF;
}
.L0S31 {
font-style: italic;
color: #808080;
}
.L0S33 {
color: #4DA619;
}
.L0S52 {
color: #0000FF;
}
.L0S55 {
color: #800080;
}
.L0S70 {
color: #808080;
}
"set the response mimetype to html
server->response->set_header_field( name = lc_header_mimetype_name
value = lc_header_mimetype_value_html ).
"set cors access control to avoid browser policy restrictions
server->response->set_header_field( name = lc_header_aca_origin
value = ld_cors_callee ).
server->response->set_header_field( name = lc_header_aca_credentials
value = lc_true ).
ld_html_string = 'testing'.
server->response->set_cdata( data = ld_html_string ).
Endif.
I don't get comments displayed in commentary box. Could you advise what is missing in my code.
Thanks.
Regards,
Venkatesan
Hi Venkatesan,
First of all, did you check on abap if you receive a call at all? You can use external breakpoints for example. Judging from the code snippet, the URL you are calling is wrong. Check the question marks. There should only be one at the end of the url. The query string itself should not contain any. Change your URL like so:
COMMENT_1.setServerUrl(“<Webservice endpoint>?sap-client=100&sap-bukrs=”+BUKRS+”&ccid=”+ccid);
Let me know.
Kind regards
Martin
Hi Martin,
Thanks for your reply. I have tried with external breakpoints. I can get into debugging. All statements working correctly.
I have simplified code in class, just to display "Testing" irrespective of any input passed.
If I execute it in browser, I can get response in browser and it is correctly displaying "testng". I have also tried it with SOAPUI, it does get response as per code.
It doesn't work only with our component. I have tried by executing it locally and also by deploying it in BI Platform it is not working to display.
To tell you more, BO and BW are in two different servers. Cross domain policy is correctly set. And also We already having working Xcelcius dashboard with webservice connection.
For this REST API, I am suspecting in CORS area and Proxy setting. I am not very familiar with CORS. Is there any setting need to be done for Proxy related.
Sample Code:
_request_method = server->request->get_header_field( name = '~request_method' ).
"determine if method is get or post.
IF _request_method = 'GET' OR _request_method = 'get'.
"set the response mimetype to html
server->response->set_header_field( name = lc_header_mimetype_name
value = lc_header_mimetype_value_html ).
"set cors access control to avoid browser policy restrictions
server->response->set_header_field( name = lc_header_aca_origin
value = ld_cors_callee ).
server->response->set_header_field( name = lc_header_aca_credentials
value = lc_true ).
ld_html_string = 'testing'.
server->response->set_cdata( data = ld_html_string ).
ENDIF
Hi Venkatesan,
obviously communication is correct if you can save comments, catch backend breakpoints and display values afterwards. You should always check the browser’s developer console to troubleshoot (hit f12, navigate to console tab and refresh your page to see possible errors). Let me know what you find there.
You are still trying to load the comment from a button click, right? Did you also check the URL for the initial load like I asked?
Kind regards
Martin
Hello Venkatesan,
I am having exactly the same issue. When i load the URL from brower, everything works fine. However the same URL does not display the HTML text within the component.
Have you been able to solve the issue?
Regards,
Nitish.
Hi Martin ,
Good Day!!!
We have installed the component in the SAP Netweaver platform as well but we are unable to see the comment component . Could you please suggest what might be the issue ?
Regards,
Suraj Grewal
Hi Suraj,
Communication is a little scattered on this thread. Did you solve this by now?
Kind regards
Martin
Hi Martin, your blog its awesome.
Great idea.
I have a question: this functionality, works fine on ipad with SAP BI?
thanks!
Hi Ariel,
I have never tested that but I don't see why there should be a problem.
Kind regards
Martin
Hi Martin,
i've implemented your solution(thanks for sharing) and everything works fine except of one thing:
The cors implementation only works when i manualy make a request to the webservice(abap) through webbrowser(only then the cors headers are transferred).
When i start it from the Design Studio App(portal) directly, without making the manual request - i get a cross site error. Shouldn't the cors implemantation be somehow on the Portal side, or did i miss something? I'm quite new to the cors topic so any help would be appreciated.
Hi Carsten,
Calling the web service URL From the webbrowser will always work because this cannot be a cross domain problem by design 😉
Please check with an external breakpoint on abap if the web service is reached. Secondly check if the http response contains the http headers. Lastly check the cross site domain error message. Maybe you can already derive from the message if you missed the protocol, out in a wrong domain or forgot the port. Keep in mind that you allow the java side to call abap. One last hint: If you run local mode in DesignStudio and you didn't fix your port you get a different port on every execution, which will get you into trouble with the cors implementation.
The cors implementation is on my abap example.
Kind regards
Martin
Hi Martin,
thanks for your answer.
I've set a breakpoint - the service isn't called. In the error console i see the url to the webservice. I can open it manually - the service ist called and then the cors headers are transferred.
How can the cors headers be set from the abap part, when the application runs on the portal and the browser prohibits callling the abap url from within java script?
It seems i'm just missing a tiny piece to make it work...
Carsten
Hi Carsten,
that is the core of CORS. You tell the browser to accept responses from domains other than your own. So DesignStudio running on your portal may receive calls from abap. It should look like the following:
Make sure to use an external breakpoint. From your description it seems there is a problem even calling your webservice class. Make sure you have the inital call correct.
To circumvent CORS entirely you would need a web dispatcher that routes request to the corresponding machines (Java and ABAP) but exposing both under the same domain to the browser satisfying the CORS restriction.
Kind regards
Martin
Hi Martin,
we're successfully using your comment SDK with DesignStudio 1.6 and it works great. Thank you for this.
Currently we've updated our test environment to Lumira 2.0. Now commentare commands result in a script error.
Do you know of any issues with your component with Lumira 2.0? Is an upgrade planned?
Thx,
Alexander Oertel
Hi Alexander,
Thanks for reaching out. I fixed the error for Lumira 2.0 this week. Let me know how it goes. In case you have further problems please contact my colleague. He will be mentioned on my leave notice.
Kind regards
Martin
Hi Martin,
I’ve just downloaded latest version of the component and trying to use “setHTMLstring” to pass an HTML from formatted text view. However nothing happens. getHTMLstring works just fine.
I’m using text editor component on a popup window and have realized that when1st time popup editor comes up it comes with all settings set in the properties.
2nd and thereafter – only with base elements (like bold, italics, etc.) and no save button at all. However that is very random and in most the cases popup with editor comes up just fine.
Thank you in advance,
Alex
Just realized that setHTMLstring works if beforehand you press "save" button, then HTML string is passed as normal from another element or variable.
Is there something I'm missing or there is a bug and setHTMLstring doesn't have an attribute to save to until "save" button is clicked?
Thank you,
Alex
Hi Alex,
I am finally back from my trip. I haven't checked the component in a while. In general it was designed to save data only on "save" button click. Could you describe your case so I can understand where you expect different behavior?
Thanks for reaching out.
Kind regards
Martin
Hi Martin,
First of all Thanks a lot providing this component. It provides the required functionality which was expected by Users.
Few queries for you,
Thanks
Swapnil
Hi Swapnil,
Thanks for reaching out. I just updated the repository. You can now hide/show the save button using the properties or api method setSaveButtonVisible. Also I made all of the editor setting groups customizable through the properties. So now you can hide everything.
Please update from the new Lumira link. That should also work for your DS16 installation. Also note that there is standard support for commentary as of Lumira Designer 2.1.
Let me know what you think.
Kind regards
Martin
Hi Martin,
I did updated the extension and checked the same. Its working :).
Thanks you so much for the lightning Fast response.
Thanks and Regards,
Swapnil K
Hi Martin,
Thank you for providing this component.
Can you please explain, how to integrate the back end web service to write comments back to Oracle database.
Hi Dheeray,
my blog post specifically targets an ABAP backend implementation but of course you are not limited to that. In general SAP application server support Oracle as database as well. But I assume you mean integrating a webserver other than SAP ABAP, like BusinessObjects for example.
No matter what approach you take, you always have to code a web service endpoint, which can be integrated with the DesignStudio SDK component. Make sure you can expose the REST interface methods GET and POST and you should be good to go.
Kind regards
Martin
Thank you Matin
Hello Martin,
When I execute the application on the BI platform, i do not find the EasyComment CommentBox. I can only find it on local. Is there any else that needs to be done on BI platform?
Regards,
Nitish.
Hello Nitish,
you need to deploy the sdk components to your BO server. You can do that on your Designer Client (Menu -> Tools).
Kind regards
Martin