smarthome
smarthome copied to clipboard
Add support for conditional access based on user role
migrated from Bugzilla #423548 status NEW severity enhancement in component Core for --- Reported in version unspecified on platform PC Assigned to: Project Inbox
On 2013-12-08 15:16:18 -0500, Kai Kreuzer wrote:
Migrated from https://code.google.com/p/openhab/issues/detail?id=387
On 2015-09-25 03:52:04 -0400, Kai Kreuzer wrote:
Some input from my side what I see should be covered. There are multiple levels of access control that can be addressed:
- Global access control as it is done in openHAB 1 (see https://github.com/openhab/openhab/wiki/Security#authentication). I.e. for any access to the runtime, the user needs credentials and is then assigned a role. JAAS is probably a good option here. Note that the solution has to work in general for any OSGi HttpService, it must not be specific to Jetty (while in openHAB 2, we can add a Jetty-specific configuration for JAAS then).
- Restrict certain urls and/or http verbs for certain roles. See the example discussed in https://www.eclipse.org/forums/index.php/t/1068387/.
- Restrict access on certain data, e.g. return a HTTP 403 when my kids try to access localhost:8080/classicui/app?sitemap=admin. This could be implemented in phases, the most important resource would be sitemaps, then come items, things, rules, etc. But in general this mechanism should be available on all resources. Configuration of such restrictions should not only be by resource name, but possibly also by type/tag, e.g. do not grant access to any item that is tagged as "security".
- Filter data within requests, i.e. if I do not have rights for sitemap "admin" (see 3), the REST url /rest/sitemaps should not even list it. Sitemaps that refer to items that I am not allowed to access should filter out these widgets automatically.
- Check implications on automation rules. Normally, rules are executed by the system and not the user. But we could imagine that a trigger was caused by some user (e.g. an item state change) and thus the rule could be regarded to be executed on behalf of this user - then again, the permissions should be checked and e.g. sending commands to restricted items must be blocked.
Does anybody has further ideas/requirements?
I'd like to see a way to use my google account, so support for external OAuth2 providers.
It would also be nice to open up a guest mode if you are connected locally but not expose that externally.
+1 for Global access control as it is done in openHAB. we want to use openhab2 in an organization-wide newtork do to show control for visit points and exhibitions.
@ozel Does that mean your are volunteering for implementing it? :-)
@kaikreuzer sorry, that's way out of my skills. I come from an embedded C world with precicely defined typing etc. and struggle a lot these days in just getting my openHab java rules working relibaly... However, I follow https://community.openhab.org/t/authentication-in-oh2/1723/24 and as soon as there's something to test I'll volunteer for that
Some time ago in my fork I added few classes which could potentialy cover authentication support in ESH. Main purpose is to avoid any specific framework for handling that and letting vendors customize with their own choice. For this reason even JAAS is not enforced, however could be used to implement basic login.
Linked commit introduces following structures:
- Authentication which represents information about user and assigned roles (generaly speaking). This is simplest model which could be a starting point to more advanced policies which could let users controls who can interact with specific items.
- Credentials - generic purpose structure which can hold data needed to obtain authentication. One type of this might be UsernamePassword, another ie. OAuth token.
- AuthenticationProvider element responsible for verifying given Credentials and returning Authentication in case of successful login process.
- LoginResource - a dummy implementation of login resource which could be used from user interface level.
In perfect world internal code should utilize Authentication object to calculate access and visibility to items, that's why I put all auth-related stuff in core bundle. Authentication object should be also kept in HTTP session to avoid resending credentials with every requests (to deny usage of basic/digest scheme).
@splatch do you know how would this be enforced in the addons/bundles? I was playing around with implementing simple http based auth this morning. The only way I could successfully do this in a standard way was to create a custom HttpContext object that implements the "handleSecurity" function.
My knowledge of OSGI dependency injection is zero, it would be nice if the call to the "createDefaultHttpContext()" which all bindings with rest endpoints seem to use would return a context that does authentication (and could redirect to your bundle)
@splatch Your concept looks good to me, I think it is a good starting point for tackling this feature - so feel free to create a PR with it and a basic implementation of the providers and resources.
@digitaldan I think nothing speaks against introducing a custom HttpContext that we could provide as a service to all our JAX-RS resources and servlets. The "defaultHttpContext" could still stay the current one which does not require any authentication (we will still need this, e.g. for providing communication endpoints for UPnP, the hue emulator, etc.
@kaikreuzer sounds good to me. @splatch can't wait to see a simple implementation of this!
@digitaldan @kaikreuzer We will need custom http context anyway, over which we could delegate security checks to underlying Authorization mechanism and verify if access is granted or not. Feel free to add PR with custom context anyway.
Feel free to add PR with custom context anyway.
PR to where? I thought we are currently waiting for a PR by you here first?
PR to where? I thought we are currently waiting for a PR by you here first?
I will start putting all things together around infrastructure, any help with surroundings is welcome. Maybe @digitaldan will be able to base his PR upon my changes.
The HttpContext object is easy:
public class AuthenticatedHttpContext implements HttpContext {
@Override
public boolean handleSecurity(HttpServletRequest request, HttpServletResponse response) throws IOException {
response.sendError(HttpServletResponse.SC_UNAUTHORIZED);
return false;
}
@Override
public URL getResource(String name) {
return null;
}
@Override
public String getMimeType(String name) {
return null;
}
}
If we want to go this way,
- what package should this live in, maybe org.eclipse.smarthome.io.rest or org.eclipse.smarthome.core.auth?
- how should this look up a registered authentication provider and call it inside handleSecurity?
- this would mean we need to modify all existing bindings to use/import this new class..... is there a better way?
This approach make me a little uneasy b/c there is no global policy and I would hate to expose services accidentally, but I don't think OSGI will allow any other way.
- org.eclipse.smarthome.core.auth sounds good to me as it not only applies to the rest interface.
- Could AuthenticatedHttpContext simply be a service itself (then the auth provider would simply be a mandatory static dependency)?
- This is imho ok, but I agree that the risk to miss something (e.g. in extensions) is not nice. It would be great to be able to somehow inject this context into httpService.createDefaultHttpContext() - but this is probably only possible through very dirty hacks.
- This is imho ok, but I agree that the risk to miss something (e.g. in extensions) is not nice. It would be great to be able to somehow inject this context into httpService.createDefaultHttpContext() - but this is probably only possible through very dirty hacks.
I didn't read eclipsesource jaxrs source code too deep, however there is an example with their own security layer which requires registration of AuthenticationHandler and AuthorizationHandler: security example.
Correct, but this will only cover the REST API, but not any other servlet that might be registered by an extension.
Hello together, I'm also working on your approach while writing my master thesis at university. At the moment I'm trying to understand parts of the OpenHab/ESH Code and got stuck at the point the *.items files where read.
I noticed that at this point xtext is used to parse these files, my question is how to setup my eclipse ide to make changes to the xtext files (e.g. to add a user role/group) to the items. I already installed xtext and imported the missing projects, but they are full of errors (missing references, etc.) and once I include them in the run configuration OpenHab starts throwing exceptions. How can this be fixed?
Thanks in advance.
@neverend92 I don't think your question is really related to this issue. You ask how to setup the IDE (if I understand your comment correctly). For ESH install the Eclipse IDE as described in the ESH documentation and you should be able to change the xtext files (and see the result). For openHAB IDE use the openHAB community board.
Alright sorry for that, I will ask for help with this problem at the openHAB community board...
But then I want to ask you all if the approach to extend the *.items configuration files by user groups, etc. is good. Or if there is a better way to connect items and access control?
I don't know if there has been already some decisions how fine granular the access control should be defined (e.g. REST API access in general, things, channels, items, ...). I don't think it make sense to start with the *.items configuration as long as I can use the REST API to create another item that links to the same channel...
Could AuthenticatedHttpContext simply be a service itself
@kaikreuzer are you thinking it would be a service in an existing bundle, or be its own standalone bundle?
I think it must be a part of the core, just as it is done in here.
Why do we want to create Security concepts / Models by our own. Lets use a framework? @splatch , @digitaldan and @kaikreuzer What speaks against Apache Shiro (http://shiro.apache.org/) ? We may put shiro into a single bundle which than exports a SecurityManager as an OSGI service (other bindings could import and use it). It also fits well to Karaf... as I remember from my investigations for Authentication, there is a Karaf feature for OSGi integration. Shiro has easy API's for authentication, authorization, cryptography, and session management + can be deployed inside a OSGI container Not sure how thin shiro is, but its worth to check it out..
Thank @marziman , I'll take a look at Shiro, have not used it in the past, it would be great not to reinvent the wheel, especially with security.
@marziman I came across Shiro quite a while ago and thought that this could be interesting. So I agree that we should have a closer look. I so far cannot judge how well it integrates with Pax-Web, Java-servlets and Jersey.
Why do we want to create Security concepts / Models by our own. Lets use a framework?
My main concern on that is bringing external dependency to our more or less dependency less core artifacts. That's why I based on very similar basis as security frameworks so they could be wired in when needed. It was not intented to build everything from scrach but rather adapt existing solution in the way that anyone have freedom of choice.
it would be great not to reinvent the wheel, especially with security.
Currently in Java land there is no security standard other than JAAS. This is the simplest thing we could have, however it brings it's own set of troubles. Anything else than JAAS is in fact - reiventing the wheel. If you will take a look on all security frameworks made in Java - starting from Acegi over Spring Security up to Shiro - they all claim to provide comprehensive security framework. But if Acegi would do it properly in first place I think nobody else would start Shiro. And I'm pretty sure there are other implementations which yet we don't know. This is double edged sword.
@splatch, I think your Security Idea is good and appretiate your concept. But we really should investigate first. Iam not dogmatic and dont want to force it. I just got the feeling that this Framework will be good for our requirements. I had no time to make a prototype or sth. like that to say anything about ext. dependencies, but we may think about NOT putting it into the core and making a standalone SecurityManager bundle. We could bring it later to the core, too. Your concerns are valid, so if we know we have 2 or more Security Frameworks we want to make usable, than we could create a more general OH Interface abstracting this by e.g. your Security concept. But for the time being I cant see that. I would wait for @digitaldan and his feedback. Is that fine for you guys?
Well I'm no expert on Java security (nor OSGI), I have used JAAS in the past (years and years ago) and remember fighting it constantly every time a corner case came up. I'm sure Shiro has its own "quirks" too. IMHO authentication is becoming one of the major roadblocks to users adopting OH2, so I think this is becoming more urgent to get done soon. @splatch are you still working on submitting your proposal? I would hope there would also be a simple example implementation of it as well.
@splatch are you still working on submitting your proposal?
Any news here? I'd also be very interested to get a PR for that soon!
@kaikreuzer It should be fine to merge it, however I didn't have enought of time to attempt implementation of this SPI thus futher changes may be necessary. I think it's safer to submit complete pull request. From other hand I've done an example of smarthome rest services running together with CXF which allowed to support JAAS security out of the box.
I think it's safer to submit complete pull request.
Fine with that as long as you are still planning to work on this and create such a PR in the not too distant future :-)