Is there a way to do an LDAP query to get records where a particular attribute is the same? - ldap

I am trying to find an example LDAP query where I can find records where a particular attribute matches one or more other records. For instance, a user object where the userid is different, but the employee ids are the same. Is this even possible?

From a single LDAP query no. Unless you know the emplyeeID value you are looking for.
We created an LDAP tool, Duplicate Attribute Value Locater Tool, that will do this.
-jim

It's not possible to do sub queries within the filter itself. In this case, as long as I understand correctly, you'd like to find users that match :
objectClass of User
match on the value of employeeID
Out of the above subset, find all with a DISTINCT 'userid'
If you knew what userid to look for, or NOT look for, you could expand the inital AND clause to include finding, or not finding, that attribute :
userid not equal to 12345 :
(&(objectClass=person)(employeeID=JSmith)(!(userid=12345)))
userid equal to 12345 :
(&(objectClass=person)(employeeID=JSmith)(userid=12345)

I found this example for 'myattribute'. Needs some polish, and depending on the size of your directory, it could take a while to run. If that's the case, I'd break it up by attribute sections {attr=aa*, attr=ab*, attr=ac*, etc.}.
ldapsearch -x -h ldapserver.domain.com -b ou=myldap,o=mydomain.com "(&(myattribute=aa*))" myattribute | grep '^myattribute:' | sort | uniq -c| sort -n|awk '$1 > 1 { print }'

Related

LDAP Filter Syntax Query

What would be the syntax for LDAP for the below scenario:
Where sAMAccountName = GRA-* without $. I want the records which are highlighted in green.
This is my current LADP Filter for your reference:
(&(objectClass=user)sAMAccountName=GRA-*))
Anyone, Please help with the correct syntax.
Your filter can work, but you're missing a ( in front of sAMAccountName:
(&(objectClass=user)(sAMAccountName=GRA-*))
But you may be able to do better. If those ones that end in $ are computer objects (which always have sAMAccountNames that end in $, but also have an objectClass of user), then you can make sure you only get user objects by including (objectCategory=person):
(&(objectClass=user)(objectCategory=person)(sAMAccountName=GRA-*))
If, for whatever reason, those $ objects are actually user accounts, then you can exclude them with (!sAMAccountName=*$):
(&(objectClass=user)(objectCategory=person)(sAMAccountName=GRA-*)(!sAMAccountName=*$))

user wants to apply a quite complex "User Search Filter" in his LDAP Configuration

user have to apply a quite complex "User Search Filter" in his LDAP Configuration.
The filter is too big and exceed the 256 allowed character. For customer business policy is not possible to modify the LDAP structure or data How can we proceed?
Here there is a sample of the filter:
(&
(|
(memberOf=CN=Applicazione_DocB_AmmApplicativo,OU=Intranet,OU=Gruppi,DC=CBMAIN,DC=CBDOM,DC=IT)
(memberOf=CN=Applicazione_DocB_AmmPiattaforma,OU=Intranet,OU=Gruppi,DC=CBMAIN,DC=CBDOM,DC=IT)
(memberOf=CN=Applicazione_DocB_ArchFIRead,OU=Intranet,OU=Gruppi,DC=CBMAIN,DC=CBDOM,DC=IT)
(memberOf=CN=Applicazione_DocB_ArchFIWrite,OU=Intranet,OU=Gruppi,DC=CBMAIN,DC=CBDOM,DC=IT)
(memberOf=CN=Applicazione_DocB_AreaFinanza,OU=Intranet,OU=Gruppi,DC=CBMAIN,DC=CBDOM,DC=IT)
(memberOf=CN=Applicazione_DocB_Arm,OU=Intranet,OU=Gruppi,DC=CBMAIN,DC=CBDOM,DC=IT)
(memberOf=CN=Applicazione_DocB_BoGestCanc,OU=Intranet,OU=Gruppi,DC=CBMAIN,DC=CBDOM,DC=IT)
(memberOf=CN=Applicazione_DocB_BoUpdDocum,OU=Intranet,OU=Gruppi,DC=CBMAIN,DC=CBDOM,DC=IT)
(memberOf=CN=Applicazione_DocB_Crif,OU=Intranet,OU=Gruppi,DC=CBMAIN,DC=CBDOM,DC=IT)
(memberOf=CN=Applicazione_DocB_VisualBase,OU=Intranet,OU=Gruppi,DC=CBMAIN,DC=CBDOM,DC=IT)
(memberOf=CN=Applicazione_DocB_VisualEsteso,OU=Intranet,OU=Gruppi,DC=CBMAIN,DC=CBDOM,DC=IT)
)(|
(userAccountControl=512)
(userAccountControl=544)
(userAccountControl=66048)
)
)
Have the customer create one single group to control access to the application, then they can add all of those groups to that one group. Then you only need to look at that one group. However, you will need to use the LDAP_MATCHING_RULE_IN_CHAIN operator so that it will look at the members of nested groups.
If the name of that new group is Applicazione_DocB, that would look something like this:
(memberOf:1.2.840.113556.1.4.1941:=CN=Applicazione_DocB,OU=Intranet,OU=Gruppi,DC=CBMAIN,DC=CBDOM,DC=IT)
Your conditions on userAccountControl can also be simplified. That attribute is a bit flag, which means that each bit in the binary value is a flag that means something. Those values are listed in the documentation for userAccountControl. The three conditions you are using are:
512: ADS_UF_NORMAL_ACCOUNT
544: ADS_UF_NORMAL_ACCOUNT | ADS_UF_PASSWD_NOTREQD (password not required)
66048: ADS_UF_NORMAL_ACCOUNT | ADS_UF_DONT_EXPIRE_PASSWD (password does not expire)
If the intent is to exclude disabled accounts (514: ADS_UF_NORMAL_ACCOUNT | ADS_UF_ACCOUNTDISABLE), then you can do that by using the LDAP_MATCHING_RULE_BIT_AND operator to check if the second bit is not set (which indicates a disabled account), like this:
(!userAccountControl:1.2.840.113556.1.4.803:=2)
Putting that all together, you get a query that is less than 256 characters:
(&(memberOf:1.2.840.113556.1.4.1941:=CN=Applicazione_DocB,OU=Intranet,OU=Gruppi,DC=CBMAIN,DC=CBDOM,DC=IT)(!userAccountControl:1.2.840.113556.1.4.803:=2))

How can I put several extracted values from a Json in an array in Kusto?

I'm trying to write a query that returns the vulnerabilities found by "Built-in Qualys vulnerability assessment" in log analytics.
It was all going smoothly I was getting the values from the properties Json and turning then into separated strings but I found out that some of the terms posses more than one value, and I need to get all of them in a single cell.
My query is like this right now
securityresources | where type =~ "microsoft.security/assessments/subassessments"
| extend assessmentKey=extract(#"(?i)providers/Microsoft.Security/assessments/([^/]*)", 1, id), IdAzure=tostring(properties.id)
| extend IdRecurso = tostring(properties.resourceDetails.id)
| extend NomeVulnerabilidade=tostring(properties.displayName),
Correcao=tostring(properties.remediation),
Categoria=tostring(properties.category),
Impacto=tostring(properties.impact),
Ameaca=tostring(properties.additionalData.threat),
severidade=tostring(properties.status.severity),
status=tostring(properties.status.code),
Referencia=tostring(properties.additionalData.vendorReferences[0].link),
CVE=tostring(properties.additionalData.cve[0].link)
| where assessmentKey == "1195afff-c881-495e-9bc5-1486211ae03f"
| where status == "Unhealthy"
| project IdRecurso, IdAzure, NomeVulnerabilidade, severidade, Categoria, CVE, Referencia, status, Impacto, Ameaca, Correcao
Ignore the awkward names of the columns, for they are in Portuguese.
As you can see in the "Referencia" and "CVE" columns, I'm able to extract the values from a specific index of the array, but I want all links of the whole array
Without sample input and expected output it's hard to understand what you need, so trying to guess here...
I think that summarize make_list(...) by ... will help you (see this to learn how to use make_list)
If this is not what you're looking for, please delete the question, and post a new one with minimal sample input (using datatable operator), and expected output, and we'll gladly help.

Search using Lookup from a single field CSV file

I have a list of usernames that I have to monitor and the list is growing every day. I read Splunk documentation and it seems like lookup is the best way to handle this situation.
The goal is for my query to leverage the lookup function and prints out all the download events from all these users in the list.
Sample logs
index=proxy123 activity="download"
{
"machine":"1.1.1.1",
"username":"ABC#xyz.com",
"activity":"download"
}
{
"machine":"2.2.2.2",
"username":"ASDF#xyz.com",
"activity":"download"
}
{
"machine":"3.3.3.3",
"username":"GGG#xyz.com",
"activity":"download"
}
Sample Lookup (username.csv)
users
ABC#xyz.com
ASDF#xyz.com
BBB#xyz.com
Current query:
index=proxy123 activity="download" | lookup username.csv users OUTPUT users | where not isnull(users)
Result: 0 (which is not correct)
I probably don't understand lookup correctly. Can someone correct me and teach me the correct way?
In the lookup file, the name of the field is users, whereas in the event, it is username. Fortunately, the lookup command has a mechanism for renaming the fields during the lookup. Try the following
index=proxy123 activity="download" | lookup username.csv users AS username OUTPUT users | where isnotnull(users)
Now, depending on the volume of data you have in your index and how much data is being discarded when not matching a username in the CSV, there may be alternate approaches you can try, for example, this one using a subsearch.
index=proxy123 activity="download" [ | inputlookup username.csv | rename users AS username | return username ]
What happens here in the subsearch (the bit in the []) is that the subsearch will be expanded first, in this case, to (username="ABC#xyz.com" OR username="ASDF#xyz.com" OR username="BBB#xyz.com"). So your main search will turn into
index=proxy123 activity="download" (username="ABC#xyz.com" OR username="ASDF#xyz.com" OR username="BBB#xyz.com")
which may be more efficient than returning all the data in the index, then discarding anything that doesn't match the list of users.
This approach assumes that you have the username field extracted in the first place. If you don't, you can try the following.
index=proxy123 activity="download" [ | inputlookup username.csv | rename users AS search | format ]
This expanded search will be
index=proxy123 activity="download" "ABC#xyz.com" OR "ASDF#xyz.com" OR "BBB#xyz.com")
which may be more suitable to your data.

How to select by elements in a UniData multivalued field

I'm trying to do an ad hoc search of records that contain duplicate values in the first and second elements of a multivalued UniData field. I was hoping something like this would work but I'm not having any luck.
LIST PERSON WITH EVAL "STATUS[1] = STATUS[2]"
After some testing it looks like I stumbled across a way of reading the field right to left that many characters. Interesting but not useful for what I need.
LIST PERSON NAME EVAL "NAME[3]" COL.HDG 'Last3'
PERSON Name Last3
0001 Smith ith
Any ideas on how to correctly select on specific field elements?
Apparently the EXTRACT function will let me specify an element but I still can't get a selection on it to work properly.
LIST PERSON STATUS EVAL "EXTRACT(STATUS,1,2,0)" COL.HDG 'Status2'
PERSON STATUS Status2
0001 Added Processed
Processed
I would use eval with #RECORD placeholder with the dynamic array notation as such (assuming that STATUS is in Attribute 11.
Edit:
Previous answer was how I would do this in UniVerse
SELECT PERSON WITH EVAL "#RECORD<11,1>" EQ EVAL "#RECORD<11,2>"
Script Wolf's more better way that works in UniVerse and UniData.
SELECT PERSON WITH EVAL "EXTRACT(#RECORD,11,1,0)" EQ EVAL "EXTRACT(#RECORD,11,2,0)"
Good Luck.