we want to manage the credentials of the actions of the backend from
the backend.
How to get the list of the actions of an app? After that we could show
the credential of each one through getCredential().
2nd question: i found the function to get the credential of an action
(getCredential()), but how to set the credentials? I didn't find any
setCredential() function...
Javi
I agree with much of what has already been said regarding whether or not this is a good idea.
Regardless, to do what I think you are asking:
Credentials needed for an action come from this method in sfAction:
public function getCredential()
{
return $this->getSecurityValue('credentials');
}
You can overload that in your actions (or extend it in a new subclass of sfActions and have all your actions extend that) if you want to do something more complicated, like pull credentials from a database or some other source.
Getting a list of actions of an app has nothing to do with credentials. It's a matter of convention how the credentials are named or organized. Actions and credentials are independent. You could have one credential per whole application or define one credential per action. Still, you manage credential separately.
If you really want to get list of actions you could parse the routing file.
You could also use PHP's Reflection mechanism to get methods out of the action classes.
However, sfDoctrineGuardPlugin/sfGuardPlugin offers you sufficient credential management for most of the applications. I'd rather go with this approach.
2n question: There's no setCredential() method but there is an addCredential().
Let's start with your second question first, to firm up our grasp of how credentials in Symfony work.
Credentials in Symfony are set via the security.yml file the config directory of the module. A security.yml file might look like this:
all:
is_secure: true #makes all methods on this action require user's to be authenticated
edit:
credentials: [admin]
show:
is_secure: false #don't require authentication for this one
You cannot change the security settings of an action from the backend unless you want to actually write a new YAML file and clear the old one from the cache (not recommended). If you really needed dynamic credentials on an action, I would store some sort of switch (lock file, APC, database) and use a filter to dynamically set the credentials required (also, not really recommended).
Can't you do whatever you're trying to do with a standard user/group/permission setup?
Related
I am creating an apigility project where we will be hosting all of our APIs. We need to be able to use OAuth2 for authentication but we cannot figure out how to control access to certain APIs, it seems like once a client authenticates, they can use any of our APIs but we want to limit them to use only specific ones that we define. After reading about the OAuth2 library that apigility uses, I saw that there are scopes that can be defined but I have not found any documentation about how to check a user's scope to see if they have access. I want to find out if this is the best way to restrict access to certain APIs and how to set it up if it is, or is there a better way to control access?
Just implemented this functionality using the following recipe ...
https://github.com/remiq/apigility-zfc-rbac-recipe
It worked really well and only took a few hours to get it all working.
Alternatively you can just do the checking in the Controller Action (Resource method)
$identity = $this->getIdentity()->getAuthenticationIdentity();
$scope = $identity["scope"]
if (! in_array('admin', $scope)) {
return new ApiProblem(Response::STATUS_CODE_401, 'No Auth');
}
The above code is untested but should get you on the right path if you wanted to do it that way
I'm working on a Grails application and want to integrate with a custom single-sign-on service (not CAS, but similar). I'm struggling to find all the pieces that I need to customize to make this happen. Can someone explain to me a general outline as to what I need to use to accomplish this? I've read the documentation on the plugin, but it assumes I know which beans to override and where to put all the needed files.
I've block-quoted what I think needs to be done based on my research below each point.
Order of Operations
1- The user requests secure content (everything is secure in the application for now)
I believe this setting is in the Config.groovy file:
grails.plugins.springsecurity.rejectIfNoRule = true
grails.plugins.springsecurity.securityConfigType = "InterceptUrlMap"
grails.plugins.springsecurity.interceptUrlMap = [
'/**':['ROLE_ADMIN']
]
2- Spring Security checks to see if the user has a specific value set in a cookie provided by the authentication service
I'm guessing I need to create an authentication filter, but I don't know where to put it or what it should look like.
If they don't, the user is redirected to this custom SSO service, they login, once authenticated, the user is redirected back to my application (with a new cookie set)
3- Spring security checks for the cookie value and validates it against the custom service (via HTTP POST)
From some research, I think that I need to use PreAuthenticatedProcessingFilter, but I haven't been able to find any examples of how to do this.
4- The custom service returns a series of name/value pairs, a user then needs to be created in the local application database (or the timestamp of "lastLoggedIn" is updated if they user's data is already in the database)
I believe this is done in the same PreAuthenticatedProcessingFilter as number 3 or in a GrailsUserDetailsService
5- The user's authentication is cached in the session for a period of time (6-8 hours) so that re-validation against the SSO service doesn't need to occur every time the user requests a new resource.
I'm not sure if this is something that's done inherently or if I need to add code to do this (and also set the session timeout)
We are designing an application that will use Rails and Wordpress to interact with each other. We would like to have a universal logout where you could logout from either application and it would delete cookies from the other app. They will share the same host and toplevel domain. Is there a way to do this?
Access to a cookie is dependent on the domain of the server attempting to read the request -- and potentially the domain specified in the cookie. So assuming the domains match (e.g. www.example.com and www.example.com on both blog and Rails app) either should have access to a cookie set by the other.
If this is not the case (e.g. blog.example.com, www.example.com), you'll need to make sure when the cookie is set in either place, it's set for the entire domain (e.g. .example.com). But this doesn't help: while Rails can delete WP's cookie, and vice-versa, the method for creating (and using) them needs to be mutually understood.
So there's a twist here, since this is a session cookie; in this case, the cookie (which either app should have access to) is setting a value that is used and interpreted on the server side, where sessions are managed. WordPress and Rails both different methods and look for different cookies.
A solution (idea) would be to have one or the other subsystem catch incoming requests (most likely WP, and probably through some .htaccess RewriteRule, assuming you're using Apache) and create an intermediate cookie that the other could check that provides sufficient proof that the user has logged in correctly. WP's PHP for this is pretty good, and easily extended -- you just need to create some token that's a shared secret between the two apps (one of the values in wp-config.php such as LOGGED_IN_KEY might be a good option).
Maybe a solution would be to take the publicly available value from the WP cookie for username, and append the shared secret value and (in both systems) create an MD5 hash to store in a cookie. In this case, Rails' authentication would subordinate to WP's, so you would need to make sure Rails knew to delegate things like forgotten password, changed password, etc, to WP's mechanisms.
Obviously I am thinking aloud, but maybe this is a path to consider.
In any case, this is preferable to having both systems know how to trust the other's authentication.
Fiddling with cookie deletion appears to be dirty and error prone.
You might rather want to have a look at auth providers and the according plugins such as:
OAuth (WP - Rails; maybe make either side an OAuth provider)
CAS (WP - Rails)
LDAP (WP - Rails)
...
Maybe it's an option to switch from WP to one of Rail's CMS like:
Refinery CMS
Typo
...
My website does not require login. And actions that the user takes end in calling ASP.NET MVC Controller Action Methods. Any other company can call those endpoints at this time and use my APIs in this way. I want to make sure that only users who are on my site can access these APIs.
How do I achieve that?
Adding clarification:
Say my site is consoto.com. I want my methods to work only if the end user is on consoto.com. Now if another company or hacker builds a site say hackland.com and in their javascript calls my methods, I want it to fail because their users are not on consoto.com and instead are on hackLand.com.
Many sites these days offer paid official API access to their core functionality. If they don't implement a mechanism like this, others will have the option to call the methods the actual site uses instead of going through the paid API. What would prevent a hackland.com to just use the methods used by consoto.com and end up not paying for the service?
I'm not %100 sure I understand you but, it seems like you only want to give active users on your website the ability to call certain action methods. If that is the case you can decorate the action methods with [ChildActionOnly]. This will force ASP to only allow actions that are called with HTML.Action() in the view code.
controller code
[ChildActionOnly]
public ActionResult someAction()
{
//return whatever you need
}
view code
Html.Action("someAction")
That should prevent people that aren't actively viewing the site from calling an action on the server.
There's no reliable way to achieve that if you don't require authentication on your site a then allow only authenticated users to call server side actions.
One way to do it would be to use some sort of time sensitive token that the client must supply to your Controller.
Implement a web service that takes some credentials from the user, and if the credentials are valid, return a time sensitive token that is hashed based on your server clock. This service should be called through SSL so the credentials are protected in transit.
Each of your protected controllers will expect this token in addition to whatever other inputs they currently expect. You will then validate the token by de-hashing it to obtain the time stored within. Here you can decide how long you want the token to be valid for and choose a time interval to accept. For tokens that do not de-hash property or are expired, return some error result. For tokens that are valid, return the correct result. Rather than the tokens being time sensitive, you can also implement a use count scenario, but the time sensitive approach is easier.
This way, your API controllers will not require login or SSL. Your valid users will just need to obtain the token from you before hand and then use it to call your services. Anyone else can intercept these tokens but they won't be any good after a possibly very short period of time.
I am writing a small app to allow users to update their personal information online.
I get them to Authenticate at the start of the process, but would like also to ask them again for their password just before I submit any changes back to the database.
This is the way Amazon works before allowing you to see your basket and checkout.
Is there a sensible way of doing this?
It kind of depends what your using as a membership provider...
Lets assume you are using System.Web.Security.MembershipProvider then you need to use the
ValidateUser method....
MembershipProvider _provider = Membership.Provider;
if (_provider.ValidateUser(username,password)){
...the test has passed
}
I'm also assuming SSL is in place....which would be good practise.