cancel
Showing results for 
Search instead for 
Did you mean: 

CAPM Protect CDS Service with XSUAA

Ben
Participant
1,696

Hi There

When following the tutorial https://developers.sap.com/tutorials/xsa-cap-add-uaa.html the srv-Module (srv_api) is protected when called via AppRouter.

But as far as I see, the srv-Module still can be called directly (not via AppRouter) and then, the srv is not protected.

If using a CDS oData Service based on CAPM template, it would be possible to add some annotations for access restriction, for example @(requires:'authenticated-user') --> see https://answers.sap.com/questions/784681/more-info-on-cds-requires-statement-cloud-applicat.html

But if doing so, then the srv-Module can not be called directly or via AppRouter, there will be error message "Forbidden".

Therefore I would like to know how it is possible to secure an oData srv-Module by means that it is protected if called via AppRouter or called directly on the srv-Instance.

Best regards,

Ben

Accepted Solutions (0)

Answers (4)

Answers (4)

I got the solution. If you call the service via AppRouter you will have to add an additional header parameter, called x-approuter-authorization, filled with the same information as parameter Authorization, which means: "Bearer "+Token .

gregorw
Active Contributor

Hi Ben,

if you're using the Java flavour of CAPM then the blog post Securing Cloud Platform Business Application by ivan.mirisola might be helpful for you.

Best regards
Gregor

Ben
Participant
0 Kudos

Hi Gregor

Thanks for the link you provided but I am not using the Java flavour but the Node.js flavour of the CAPM.

Here you see my srv/cat-service.cds File:

using my as my from '../db/data-model';

service CatalogService @(impl:'../cat-service.js') @(requires:'authenticated-user') {
    entity Persons as projection on my.Persons;
}

srv/cat-service.js File (in order to write user info to log):

module.exports = srv => {
	const {
		CatalogService
	} = cds.entities('my');

	srv.before('READ', 'Persons', (req) => {
		console.log('Authentication: ' + JSON.stringify(req.user));
	})
};

srv-Logfile:

GET /catalog/Persons
{ user: 'anonymous', ip: '10.0.72.5' }

Any ideas?

Ahh and to mention, I tried running from WebIDE but also deployed whole mtar to cf trial account.

Both is not working as soon as I add following annotation to CDS service:

@(requires:'authenticated-user')

Best regards,
Ben

gregorw
Active Contributor

Hi benkrencker and christian.georgi,

to make it easier to work on this issue I've created a Node.JS based project at https://github.com/gregorwolf/bookshop-nodejs. I've deployed that to my SAP CP Cloud Foundry Trial account and do face the issue that when running the UI the metadata could not be retrieved because the request reaches the backend with an anonymous user. Looking forward for some help.

Best regards
Gregor

CC: dj.adams.sap daniel.hutzel

gregorw
Active Contributor

HI benkrencker,

I have how a working version using scopes in the GitHub repository at: https://github.com/gregorwolf/bookshop-nodejs.

Best regards
Gregor

maheshpalavalli
Active Contributor
0 Kudos

Hi Gregor Wolf,

The project looks really cool... I was just going through your project and found a lot of stuff related to authentication(Passport xssec jwtstrategy). Just wanted to know if there is any standard documentation available for it and if yes, could you please provide me that link for reference.

Thanks & Regards,
Mahesh

Ben
Participant
0 Kudos

Hi Gregor Wolf

Thanks a lot for providing a solution on this issue! I am just wondering wheter this is a solution or a workaround? As far as I see, you created a express app.js and server.js in srv module and are not using the CAPM built-in cds server anymore. Is is supposed to only work when using custom express server? Maybe Christian Georgi can answer this question, because this was not part of his solution..?

One other question to Gregor Wolf: are you using the WebIDE to build the Project? When I clone your project to my WebIDE, I am not able to build db or srv module. Even when I try to "Build CDS" there is a build error (ESLINT Parsing error: the keyword "const" is reserved in File app.js Line 1 and server.js Line 1).

I am now going to create new WebIDE project from scratch and to create app.js and server.js file in this new project..

Best regards,
Ben

gregorw
Active Contributor

Hi benkrencker,

as you can see in https://github.com/gregorwolf/bookshop-nodejs/blob/master/srv/package.json#L22 I've changed back to start the srv using the CAPM built in server.

I've used my local dev environment in VS Code on Linux. The mtar was created using mbt and then deployed using the cf cli with the mta plugin.

Best regards
Gregor

Ben
Participant
0 Kudos

Hi gregorw

In the meantime I was able to build, run and deploy the project to SCP trial environment. I guess the build problems came from some WebIDE interrups (I recently had some WebIDE errors in trial environment)..

Regarding Line 22 in package.json, did you deploy the project to CF and run the example? As soon as I use the built in server (like Line 22) the authentication is not working (I get "forbidden" message in UI).

The project only works when I have following line in package.json:

	"scripts": {
		"start": "node server.js",
	},

I would be happy I you could double check if your project really works when using the built in oData server.

Best regards;

Ben

Ben
Participant
0 Kudos

Hi gregorw

Please forget my last comment 🙂

I did not see that I had implemented a role restriction into my oData Service. I can confirm that it is now working also with builtin oData Server..

What is the difference to the original project, why is it working now? Was there an update of the CAPM oData server?

Best regards,

Ben

0 Kudos

Nearby one year ago and I'm facing the same problem. As Benjamin told:

JWT token is not delivered to or recognized from the srv-Module because when I call the oData Service (srv-Module) via AppRouter, I am routed to the login page and after successful login, the oData response still is "forbidden".

Are there new ideas, solutions ? I tried a lot, but unfortunately nothing works.

gregorw
Active Contributor
0 Kudos

Hi Stefan,

maybe my debug handlers in server.js help.

Best regards
Gregor

chgeo
Advisor
Advisor
0 Kudos

Hi Ben,

I have answered to your BCP ticket for this question.

Regards,

Christian

Ben
Participant
0 Kudos

Hi Christian

I followed your recommendations (see below) but it was not working: it seems like the JWT token is not delivered to or recognized from the srv-Module because when I call the oData Service (srv-Module) via AppRouter, I am routed to the login page and after successful login, the oData response still is "forbidden".

Your recommendations:

  • Create an HTML5 module, which is run as an approuter instance -> done
  • In its xs-app.json, there should be one route to the service. Make sure you set the "authenticationMethod" to "xsuaa". -> done
  • In mta.yaml
    • Bind the HTML5 module to the XSUAA service instance -> done
    • Require the service module from the HTML5 module in its destinations -> done

Best regards,

Ben