Active Directory, LDAP UserPrincipal - active-directory

Got this information when I wrote out the DistinguishedName property on UserPrincipal class.
CN=Test Testie, OU=123,OU=Company,OU=Accounts,DC=myServer,DC=local
And im woundering if there is a property to get the nr 123 from OU. Is there any other property to get that or is this the best way to filter out my information?

\No. There is no "Parent" property.
Every object bellow the root has a parent being either an organizational unit (OU=) on a container (CN=). So just parse what is between the first two commas and remove OU= and CN=. That way you have the Name property.
Beware that it is possible to have objects with commas in their names. It then look like this:
Great OU, The
CN=Test Testie,OU=Great OU\,The,OU=Company,OU=Accounts,DC=myServer,DC=local
Testie, Test
CN=Testie\, Test
,OU=123,The,OU=Company,OU=Accounts,DC=myServer,DC=local
So you need to check for a backslah before parsing! If found, you then need to parse, between the first and the third comma.
Here is a link about "special" characters in Distinguished Names.

Ok, it's working but it doesn't feels like the best practice to do like this:
var ctx = new PrincipalContext(ContextType.Domain, "myDomain.local");
var user = UserPrincipal.FindByIdentity(ctx, "myUser");
var auth = user.GetAuthorizationGroups().Any(x => x.Name.Contains("myGroup"));
Because the thing is that I need to use contains because the group could look like this:
myGroup.xxxx.111
Any better way to soulve this?

Related

ControlPath equivalent from DotNetNuke DnnApiController ActiveModule

Is there a way to get the module root folder (folder under DesktopModules) of the ActiveModule from a DnnApiController?
In PortalModuleBase I would use the ControlPath property to get to the same root folder I'm looking for.
As #MitchelSellers points out, it doesn't appear to be in the API so you have to figure it out yourself.
Since the API gives us the ActiveModule which is a ModuleInfo that's probably the best way to get at it.
If your modules use a pretty standard consistent naming then the following "best guess" method should work pretty well
public static string ControlPath(ModuleInfo mi, bool isMvc = false)
{
return isMvc
? $"/DesktopModules/MVC/{mi.DesktopModule.FolderName}"
: $"/DesktopModules/{mi.DesktopModule.FolderName}";
}
The other way is to look at the ModuleDefinitions of our module and grab the first ModuleControl and look at it's ControlSrc to see it's path.
public static string ControlPath(ModuleInfo mi)
{
var mdi = mi.DesktopModule.ModuleDefinitions.First().Value;
var mci = mdi.ModuleControls.First().Value; // 1st ModuleControl
return Path.GetDirectoryName(mci.ControlSrc);
}
The second method is really messy (and untested) but should give you the actual folder path where the controls are installed, over the other best guess method above.
From the API's it doesn't appear so, you should know the path for this though since you are inside of your module, the only concern is if you are inside of a child portal you need the prefix, which you should be able to get. I'd just use Server.ResolveClientUrl() to get it.

How do I remove a member from a large ldap-ad group with over >1500 members

I'm trying to remove a member from a large ldap Active Directory (AD) group. The below code will remove the member if the group is small. However it won't work if it's larger since AD splits the members into multiple range related attributes.
group.removeMember(person.getFullDn());
ldapTemplate.update(group);
I've tried to access those attributes directly using something like the below. IncrementalAttributesMapper allows me to get the list of range related member attributes ie member;Range=0-1499 and I attempt to delete the person from each, but no good. I don't get an error, but the person isn't removed from the group either
DirContextOperations ctx = ldapTemplate.lookupContext(group.getDn());
IncrementalAttributesMapper<?> attributesMapper = new DefaultIncrementalAttributesMapper("member");
while (attributesMapper.hasMore()) {
String[] attributes = attributesMapper.getAttributesForLookup();
for (String attribute: attributes ) {
ldapTemplate.lookup(group.getDn(), attributesMapper.getAttributesForLookup(), attributesMapper);
ctx.removeAttributeValue(attribute, person.getDn() );
ldapTemplate.modifyAttributes(ctx);
}
}
Hopefully someone has had more success with this. Thanks in advance!
I've got the solution as posted
I was getting a malformed attribute error until I just realised that the BasicAttribute is expecting String parameters. I was incorrectly passing in a Name object to it.
ldapTemplate.modifyAttributes(group.getDn(), new ModificationItem[] {
new ModificationItem(
DirContext.REMOVE_ATTRIBUTE,
new BasicAttribute("member", person.getFullDn().toString() ))
});

pattern for updating a datastore object

I'm wondering what the right pattern should be to update an existing datastore object using endpoints-proto-datastore.
For example, given a model like the one from your GDL videos:
class Task(EndpointsModel):
detail = ndb.StringProperty(required=True)
owner = ndb.StringProperty()
imagine we'd like to update the 'detail' of a Task.
I considered something like:
#Task.method(name='task.update',
path='task/{id}',
request_fields=('id', 'detail'))
def updateTask(self, task):
pass
However, 'task' would presumably contain the previously-stored version of the object, and I'm not clear on how to access the 'new' detail variable with which to update the object and re-store it.
Put another way, I'd like to write something like this:
def updateTask(self, task_in_datastore, task_from_request):
task_in_datastore.detail = task_from_request.detail
task_in_datastore.put()
Is there a pattern for in-place updates of objects with endpoints-proto-datastore?
Thanks!
See the documentation for details on this
The property id is one of five helper properties provided by default
to help you perform common operations like this (retrieving by ID). In
addition there is an entityKey property which provides a base64
encoded version of a datastore key and can be used in a similar
fashion as id...
This means that if you use the default id property your current object will be retrieved and then any updates from the request will replace those on the current object. Hence doing the most trivial:
#Task.method(name='task.update',
path='task/{id}',
request_fields=('id', 'detail'))
def updateTask(self, task):
task.put()
return task
will perform exactly what you intended.
Task is your model, you can easily update like this:
#Task.method(name='task.update',
path='task/{id}',
request_fields=('id', 'detail'))
def updateTask(self, task):
# Task.get_by_id(task.id)
Task.detail = task.detail
Task.put()
return task

Using ADSI calls, how to get ms-TS-Allow-Logon attribute value?

I am trying to retrieve some attributes of a terminal service user(eg.ms-TS-Allow-Logon) through ADSI.
I tried something like
LPOLESTR pszPropertyList [] = {L"ms-TS-Allow-Logon"};
swprintf_s(pszSearchFilter, dwLength, L"(&(objectCategory=person)(objectClass=user)");
hr = pContainerToSearch->ExecuteSearch(pszSearchFilter,
pszPropertyList,
sizeof(pszPropertyList)/sizeof(LPOLESTR),
&hSearch
);
But it doesn't work.
Where can I get the exact attribute names to be passed to an ADSI call for all these terminal service names(like ms-TS-Allow-Logon, ms-TS-Endpoint-Type etc)
Thanks
Sunil
according to MSDN ms-TS-Allow-Logon attribute the ldap name for this attribute is msTSAllowLogon
We can get all the attribute names using the ADSI tool that gets shipped along with the activedirectory

getting the file in a sub-folder # Isolated Storage - WP7

I would like to get all the files that a sub-folder holds in a string array.
So, I have tried something like the following:
var IOstore = IsolatedStorageFile.GetUserStoreForApplication();
string searchpath = System.IO.Path.Combine("product", ProductName);
string filesInSubDirs[] = IOstore.GetFileNames(searchpath);
But I got all the files in the "product" folder. I have also tried with "productname" only as the parameter.
Thanks for your help.
The search pattern for a sub-folder needs to include "*.*" at the end to pattern match any file, which would make your code something like the following:
var IOstore = IsolatedStorageFile.GetUserStoreForApplication();
string searchpath = System.IO.Path.Combine("product", ProductName);
searchpath = string.Format("{0}\\*.*", searchpath);
string filesInSubDirs[] = IOstore.GetFileNames(searchpath);
Something you might want to try. (this is sort of a left field answer, sorry). In my dropbox client http://sharpdropbox.codeplex.com/) I have a set of facades for System.IO.File, System.IO.FileInfo, System.IO.Directory, and System.IO.DirectoryInfo. They work pretty good and I have tested them.
Basically, you add a Using or Import for System.IO.IsolatedStorage and then PSFile, PSDirectory, PSFileInfo, or PSDirectoryInfo. It's saved me from having to remember all the nuances... for instance if you are querying a directory, it knows to add a slash, etc. BTW, the "PS" prefix stands for "Persisted Storage" which is what IsolatedStorage is sometimes called (starting them with an "I" implies they are interfaces.. and having no prefix makes things even more confusing).
Anyway, you can grab the code from source or I believe the last release had the DLLs for them (it's called something like "IsolatedStorageFacade-WP7")

Resources