Updating properties for multiple users - active-directory

How do I update a list of different Telephone, IPPhone using this
static void Main(string[] args)
{
Console.Write("Enter userid : "); // I would pass this in from the first
//Field in the .csv file 2439009
String username = Console.ReadLine();
try
{
DirectoryEntry myLdapConnection = createDirectoryEntry();
DirectorySearcher search = new DirectorySearcher(myLdapConnection);
search.Filter = "(cn=" + uid + ")";
search.PropertiesToLoad.Add("Telephone","IPPhone");
SearchResult result = search.FindOne();
if (result != null)
{
// create new object from search result
DirectoryEntry entryToUpdate = result.GetDirectoryEntry();
// show existing title
Console.WriteLine("Current title : " + entryToUpdate.Properties["Telephone][0].ToString());
Console.Write("\n\nEnter new title : ");
// get new title and write to AD
String newTitle = Console.ReadLine();
entryToUpdate.Properties["Telephone"].Value = newTelePhone;
entryToUpdate.Properties["IPPhone"].Value = newIPPhone;
entryToUpdate.CommitChanges();
Console.WriteLine("\n\n...new title saved");
}
else Console.WriteLine("User not found!");
}
catch (Exception e)
{
Console.WriteLine("Exception caught:\n\n" + e.ToString());
}
}
static DirectoryEntry createDirectoryEntry()
{
// create and return new LDAP connection with desired settings
DirectoryEntry ldapConnection = new DirectoryEntry("mydomain.dm.com");
ldapConnection.Path = "LDAP://OU=myusers,DC=sales,DC=US,DC=US";
ldapConnection.AuthenticationType = AuthenticationTypes.Secure;
return ldapConnection;
}

I'm guessing you've grabbed someone else's code and don't know how to use it?
You should understand that this code can (will?) cause serious server problems as the DirectoryEntry resources are not closed correctly.
Every DirectoryEntry variable in your Main method should be wrapped in a using(){} statement.

Try something like this:
You define a class CSVRecord which holds your data from the CSV - read that in using FileHelpers. The class looks like this:
public class CSVRecord
{
public string EmployeeNumber { get; set; }
public string TelephoneNumber { get; set; }
public string IPPhoneNumber { get; set; }
}
Once you've read that class in, you need to iterate over its elements, and do the update for each of them.
CSVRecord[] listOfEmployees = (read in via FileHelpers)
// define root for searching your user accounts
using (DirectoryEntry root = new DirectoryEntry("LDAP://dc=yourcompany,dc=com"))
{
// set up directory searcher to find users by employeeId
using (DirectorySearcher searcher = new DirectorySearcher(root))
{
searcher.SearchScope = SearchScope.Subtree;
// iterate over all entries in your list of employees
foreach (CSVRecord csvEntry in listOfEmployees)
{
searcher.Filter = string.Format("(&(objectCategory=user)(employeeId={0}))", csvEntry.EmployeeNumber);
// search for that employee
SearchResult result = searcher.FindOne();
// if found - access the DirectoryEntry
if (result != null)
{
DirectoryEntry foundUser = result.GetDirectoryEntry();
// update properties from values in CSV
foundUser.Properties["telephoneNumber"].Value = csvEntry.TelephoneNumber;
foundUser.Properties["ipPhone"].Value = csvEntry.IPPhoneNumber;
// save changes back to directory
foundUser.CommitChanges();
}
}
}
}
Does that work for you??

Related

SalesForce: Classic to Lighting

Apologies if my question my be so dumb but my programming skills are really limited and I'm on a hurry for a PoC.
I have the apex class below which was developed for Classic. I would like to make it work with lighting and I'm not sure if the only thing I need to replace are the url's. I have created a developer account for my PoC and everytime I launch the class I'm redirected to Classic.
public class LookupByUrlParamController {
String accountName;
String accountNumber;
String phone;
String website;
String email;
String socialhandle;
public LookupByUrlParamController () { }
public String redirectToAccount() {
Account account;
Map<String,String> params = ApexPages.currentPage().getParameters();
if(params.size() > 0) {
accountName = params.get('account_name');
accountNumber = params.get('account_number');
phone = params.get('phone');
website = params.get('website');
email = params.get('email');
socialhandle = params.get('SocialHandle');
}
try {
if(accountName != null) {
account = [select ID from Account where name = :accountName limit 1];
}
} catch (System.queryException e) {//no entry found for lookup item, display empty account page
return 'https://na7.salesforce.com/001/e';
}
try {
if(accountNumber != null) {
account = [select ID from Account where AccountNumber = :accountNumber limit 1];
}
} catch (System.queryException e) {//no entry found for lookup item, display empty account page
return 'https://na7.salesforce.com/001/e';
}
try {
if(phone != null) {
String npa;
String nnx;
String extension;
// Added logic for NA phone numbers
if (phone.length() == 10) {
npa = phone.substring(0,3);
nnx = phone.substring(3,6);
extension = phone.substring(6,10);
phone = '(' + npa + ') ' + nnx + '-' + extension;
}
account = [select ID from Account where phone = :phone limit 1];
}
} catch (System.queryException e) {//no entry found for lookup item, display empty account page
return 'https://na7.salesforce.com/001/e';
}
try {
if(website != null) {
account = [select ID from Account where website = :website limit 1];
}
} catch (System.queryException e) {//no entry found for lookup item, display empty account page
return 'https://na7.salesforce.com/001/e';
}
try {
if(email != null) {
account = [select ID from Account where email__c = :email limit 1];
}
} catch (System.queryException e) {//no entry found for lookup item, display empty account page
return 'https://na7.salesforce.com/001/e';
}
try {
if(socialhandle != null) {
account = [select ID from Account where SocialHandle__c = :socialhandle limit 1];
}
} catch (System.queryException e) {//no entry found for twitter handle lookup item, display empty account page
return 'https://na7.salesforce.com/001/e';
}
String accountUrl;
if(account != null) {
accountUrl = '/' + account.Id;
} else {
accountUrl = '/';
}
return accountUrl;
}
public static testMethod void testLookupByUrlParamAccount() {
LookupByUrlParamController controller = new LookupByUrlParamController();
controller.accountName = 'Avaya';
String redirectUrl = controller.redirectToAccount();
System.assertEquals(redirectUrl, '/001A0000007UkkFIAS');
}
public static testMethod void testLookupByUrlParamInvalidAccount() {
LookupByUrlParamController controller = new LookupByUrlParamController();
controller.accountName = '';
String redirectUrl = controller.redirectToAccount();
System.assertEquals(redirectUrl, 'https://na7.salesforce.com/001/e');
}
public static testMethod void testLookupByUrlParamPhone() {
LookupByUrlParamController controller = new LookupByUrlParamController();
controller.phone = '1234';
String redirectUrl = controller.redirectToAccount();
System.assertEquals(redirectUrl, '/001A0000007UkkFIAS');
}
public static testMethod void testLookupByUrlParamWherePhoneNumberIs10Chars() {
LookupByUrlParamController controller = new LookupByUrlParamController();
controller.phone = '1234567891';
String redirectUrl = controller.redirectToAccount();
System.assertEquals(redirectUrl, 'https://na7.salesforce.com/001/e');//no record found
}
public static testMethod void testLookupByUrlParamInvalidPhoneNumber() {
LookupByUrlParamController controller = new LookupByUrlParamController();
controller.phone = '';
String redirectUrl = controller.redirectToAccount();
System.assertEquals(redirectUrl, '/001A0000015EKVPIA4');
}
public static testMethod void testLookupByUrlParamAccountNumber() {
LookupByUrlParamController controller = new LookupByUrlParamController();
controller.accountNumber = '4321';
String redirectUrl = controller.redirectToAccount();
System.assertEquals(redirectUrl, '/001A0000007UkkFIAS');
}
public static testMethod void testLookupByUrlParam() {
LookupByUrlParamController controller = new LookupByUrlParamController();
String redirectUrl = controller.redirectToAccount();
System.assertEquals(redirectUrl, '/');
}
}
In addition if anyone can tell where to being looking in the documentation to simply launch to new customer record form, or what are the redirect URLS?
It's not quite clear what you mean by
everytime I launch the class I'm redirected to Classic
However, this code appears not to have been touched in quite a number of years and there's several things you ought to change.
You are hard-coding non-My Domain Salesforce instance URLs (na7.salesforce.com). You should instead use URL.getSalesforceBaseUrl().toExternalForm(), and you'll need to turn on My Domain sooner or later.
You are using Classic-format URLs, which still work but will result in additional redirects. The Lightning equivalent for the "Create new Account" URL is lightning/o/Account/new and for a specific record is lightning/r/Account/<Id>/view. When you build Lightning components, you can use the navigation service to get these URLs dynamically.
You have inline test methods, which haven't been allowed since an API version well before I started on the platform. Break those out into a separate test class.

Read data from Firebase

I'm using Firebase for my Android app, I want read datas. In particular I want to select an user with a specific id. When I use the debugger it seems that the code doesn't execute the onDataChange() instruction.
private User readUserById(){
final User u = new User("","","");
Query query = mDatabaseReferences.child("users").orderByChild("id").equalTo(id);
query.addListenerForSingleValueEvent(new ValueEventListener() {
#Override
public void onDataChange(DataSnapshot dataSnapshot) {
for(DataSnapshot ds : dataSnapshot.getChildren()){
u.setId(ds.child("id").getValue(User.class).getId());
u.setNumber((ds.child("number").getValue(User.class).getNumber()));
}
}
#Override
public void onCancelled(DatabaseError databaseError) {
}
});
return u;
}
private void initFirebase() {
FirebaseApp.initializeApp(this);
mFirebaseDatabase = FirebaseDatabase.getInstance();
mDatabaseReferences = mFirebaseDatabase.getReference();
}
public void sendCode(View v){
id= id.getText().toString();
readUserById();
phoneNumber = phoneText.getText().toString();
if (phoneNumber.equals("") || id.equals("")) {
Toast t = Toast.makeText(this, "Please insert a nickname and a valid phone number", Toast.LENGTH_LONG);
t.show();
} else {
setUpVerificationCallbacks();
PhoneAuthProvider.getInstance().verifyPhoneNumber(
phoneNumber,
60,
TimeUnit.SECONDS,
this,
verificationCallbacks
);
}
// }
}
Using the debugger I've seen that the 'id' value is correct.
I used Firebase documentation for sendCode(), the user registration works correctly, just like the sms sending. I want to check if the nickname already exists, and the value is in the 'id' Textview. I call the sendCode() through a button.
I've tried in this way but doesn't work. Running with the debugger the result of user is null
private User readUserByName(){
final User[] user = {new User()};
DatabaseReference ref = FirebaseDatabase.getInstance().getReference();
ref.child("users").child(nick).addListenerForSingleValueEvent(new ValueEventListener() {
#Override
public void onDataChange(DataSnapshot dataSnapshot) {
if(dataSnapshot.exists()){
user[0] = dataSnapshot.getValue(User.class);
Log.d("Tag", user[0].toString());
}
else
Log.e("Tag","No such user exists");
}
#Override
public void onCancelled(DatabaseError databaseError) {
}
});
return user[0];
}
This is how I save the User
I've launched the app with the debugger
Assuming that users node is a direct child of your Firebase root, please use the following code:
DatabaseReference rootRef = FirebaseDatabase.getInstance().getReference();
DatabaseReference testRef = rootRef.child("users").child("test");
ValueEventListener eventListener = new ValueEventListener() {
#Override
public void onDataChange(DataSnapshot dataSnapshot) {
String id = dataSnapshot.child("id").getValue(String.class);
String idName = dataSnapshot.child("idName").getValue(String.class);
String number = dataSnapshot.child("number").getValue(String.class);
Log.d("TAG", id + " / " + idName + " / " + number);
}
#Override
public void onCancelled(DatabaseError databaseError) {}
};
testRef.addListenerForSingleValueEvent(eventListener);
The output will be:
test / f70eb... / number
Assumed that :
node "users" directly under root node.
You already know the id of the user and this id contains all the information under User.class
You only want to read a user, if exists in database.
All the getters and setter exists in User.class and a Public empty constructor exists
Here is how you should do it
DatabaseReference ref = FirebaseDatabase.getInstance().getReference();
ref.child("users").ref(id).addListenerforSingleValueEvent(listener);
And in Listener's OnDataChange(DataSnapshot snap);
if(snap.exists()){
user = snap.getValue(User.class);
Log.d("Tag",user.toString());
}
else
Log.e("Tag","No such user exists");

Can't get Novell.Directory.Ldap.NETStandard library to query

I need to let the user query an Active Directory for names in .Net Core.
So I am building an Active Directory Search Web API Service.
I am able to connect with the bind statement.
But I am not able to get any results back with my query although there is no error.
Another programmer sent me some code he uses in other applications. But it uses the DirectoryEntry object which is not available in .Net Core.
So I am trying to use the Novell.Directory.Ldap.NetStandard library.
Here is the code the other developer sent me:
public static List<UserProfileModel> GetADUsers(string alias)
{
List<UserProfileModel> users = new List<UserProfileModel>();
if (alias == null || alias.Trim().Equals(""))
{
return users;
}
try
{
// Ad path LDAP://ourOrg.gov/CN=Users,DC=ourOrg,DC=gov
DirectoryEntry de2 = new DirectoryEntry(ConfigurationManager.AppSettings["AD_Path"], ConfigurationManager.AppSettings["AD_User"], ConfigurationManager.AppSettings["AD_Password"]);
de2.Path = ConfigurationManager.AppSettings["AD_Path"];
de2.AuthenticationType = AuthenticationTypes.Secure;
DirectorySearcher deSearch = new DirectorySearcher();
deSearch.SearchRoot = de2;
deSearch.Filter = "(samaccountname=*" + alias + "*)";
LOGGER.Debug(String.Format("Active Directory Search Filter {0}", deSearch.Filter));
SearchResultCollection results = deSearch.FindAll();
String raw = "";
LOGGER.Debug(String.Format("Active Directory Search Result Counts {0}", results.Count));
if (results.Count > 0)
{
foreach (SearchResult item in results)
{
UserProfileModel userProfileModel = new UserProfileModel();
userProfileModel.Name = GetADProperty("name", item);
userProfileModel.email = GetADProperty("mail", item);
userProfileModel.identity = GetADProperty("userPrincipalName", item);
userProfileModel.first_name = GetADProperty("givenName", item);
userProfileModel.last_name = GetADProperty("sn", item);
users.Add(userProfileModel);
raw = String.Format("{0}/n{1}", raw, userProfileModel.ToString());
}
LOGGER.Debug(String.Format("Active Directory Search Resuts ToString: {0}", raw));
}
}
catch (Exception e)
{
LOGGER.Error("Unable to Query Active Directory", e);
}
return users;
}
I need to translate this into Novell's LDAP library.
Here is my attempt:
[HttpGet]
public async Task<List<UserProfileModel>> GetByName(string alias)
{
int ldapPort = LdapConnection.DEFAULT_PORT;
string ldapHost = "ourOrg.gov";
string loginDn = #"ourOrg\myName";
string password = "myPass";
List<UserProfileModel> users = new List<UserProfileModel>();
if (alias == null || alias.Trim().Equals(""))
{
return users;
}
try
{
using (var con = new LdapConnection())
{
con.Connect(ldapHost, ldapPort);
con.Bind(loginDn, password);
LdapSearchResults results = con.Search(
"cn=users,dc=ourOrg,dc=gov",
LdapConnection.SCOPE_ONE,
"samaccountname=*",
null,
false);
// NO RESULTS:(
}
return users;
}
catch(Exception ex)
{
throw ex;
}
}
I don't get an error.
But there are 0 results.
I originally had this part:
"samaccountname=*",
like:
"samaccountname={alias}",
but I'm just trying to get back results at this point.
I got this working:
using System;
using System.Collections.Generic;
using System.Threading.Tasks;
using Microsoft.AspNetCore.Mvc;
using Microsoft.Extensions.Options;
using Hrsa.Core.Web.App.Models.ViewModels;
using Novell.Directory.Ldap;
// For more information on enabling Web API for empty projects, visit http://go.microsoft.com/fwlink/?LinkID=397860
namespace Hrsa.Core.Web.App.Controllers.Api
{
[Route("api/[controller]")]
public class ActiveDirectoryController : Controller
{
private readonly AppSettings _appSettings;
public ActiveDirectoryController(IOptions<AppSettings> appSettings)
{
_appSettings = appSettings.Value;
}
[HttpGet]
public async Task<List<UserProfileModel>> GetByName(string alias)
{
int ldapPort = LdapConnection.DEFAULT_PORT;
string ldapHost = _appSettings.HrsaLdapHost; // ourOrgName.gov
string loginDn = _appSettings.AdUser;
string password = _appSettings.AdPassword;
string searchBase = _appSettings.HrsaAdSearchBase;
string searchFilter = $"(samaccountname=*{alias}*)";
string[] attributes = new string[] { "cn", "userPrincipalName", "st", "givenname", "samaccountname",
"description", "telephonenumber", "department", "displayname", "name", "mail", "givenName", "sn" };
List<UserProfileModel> users = new List<UserProfileModel>();
if (alias == null || alias.Trim().Equals(""))
{
return users;
}
try
{
using (var con = new LdapConnection())
{
con.Connect(ldapHost, ldapPort);
con.Bind(loginDn, password);
LdapSearchQueue queue = con.Search(
searchBase,
LdapConnection.SCOPE_SUB,
searchFilter,
attributes,
false,
(LdapSearchQueue)null,
(LdapSearchConstraints)null);
LdapMessage message;
while ((message = queue.getResponse()) != null)
{
if (message is LdapSearchResult)
{
LdapEntry entry = ((LdapSearchResult)message).Entry;
LdapAttributeSet attributeSet = entry.getAttributeSet();
users.Add(new UserProfileModel
{
Cn = attributeSet.getAttribute("cn")?.StringValue,
UserPrincipalName = attributeSet.getAttribute("userPrincipalName")?.StringValue,
St = attributeSet.getAttribute("st")?.StringValue,
Givenname = attributeSet.getAttribute("givenname")?.StringValue,
Samaccountname = attributeSet.getAttribute("samaccountname")?.StringValue,
Description = attributeSet.getAttribute("description")?.StringValue,
Telephonenumber = attributeSet.getAttribute("telephonenumber")?.StringValue,
Department = attributeSet.getAttribute("department")?.StringValue,
Displayname = attributeSet.getAttribute("displayname")?.StringValue,
Name = attributeSet.getAttribute("name")?.StringValue,
Mail = attributeSet.getAttribute("mail")?.StringValue,
GivenName = attributeSet.getAttribute("givenName")?.StringValue,
Sn = attributeSet.getAttribute("sn")?.StringValue
});
}
}
}
return users;
}
catch(Exception ex)
{
throw ex;
}
}
}
}

GWT Restlet Parameters Always Null

I am brand new to both REST and RESTlet- I got everything up and communicating last night but what I found this morning is that everything I pass into the server is always becoming null.
just as a sample app i have the following - a User Objectify entity (id, emailAddress, and version), and a RESTUserProxy object (id, emailAddress) - I wasn't originally sure if i could pass Objectify Entities back and after not being able to see anything switched it to the Proxy object - if i can get it to work this way I will try switching it back
the front end is as follows:
public interface RESTUserResourceProxy extends ClientProxy {
#Get
public void find(String emailAddress, Result<RESTUserProxy> callback);
#Put
public void persist(RESTUserProxy user, Result<Void> callback);
#Delete
public void delete(RESTUserProxy user, Result<Void> callback);
}
the backend code is as follows (this is currently extremely ugly - i got a little frustrated just trying to see something and put in a ton of sysouts)
public class RESTUserServerResource extends ServerResource implements RESTUserResource {
private final UserDao userDao;
public RESTUserServerResource() {
System.out.println("CREATED USER RESOURCE IMPL");
userDao = new UserDao();
}
#Override
#Get
public RESTUserProxy find() {
System.out.println("reference = " + getReference());
Form queryParams = getReference().getQueryAsForm();
System.out.println("query params = " + queryParams);
System.out.println("query = " + getQuery());
System.out.println("query string = " + getQuery().getQueryString());
String searchQuery = (String) getRequest().getAttributes().get("searchQuery");
System.out.println("search query = " + searchQuery) ;
return null;
// if (emailAddress == null) {
// return null;
// }
// System.out.println("user resource impl find [" + emailAddress + "]");
// final User user = userDao.find(emailAddress.getText());
// if (user != null) {
// System.out.println("found user ");
// return new RESTUserProxy(user.getId(), user.getEmailAddress());
// } else {
// System.out.println("found absolutely nothing");
// return null;
// }
}
#Override
#Put
public void persist(RESTUserProxy userProxy) {
System.out.println("user proxy = " + userProxy);
if (userProxy == null) {
return;
}
final User user = userDao.find(userProxy.getId());
user.setEmailAddress(userProxy.getEmailAddress());
user.setId(userProxy.getId());
userDao.persist(user);
}
#Override
#Delete
public void delete(RESTUserProxy userProxy) {
final User user = userDao.find(userProxy.getId());
userDao.delete(user);
}
}
what im having problems with is that eerythings coming through as null - a lot of other answers on here said to get the query to get the params - but here the query is null
below is the output of calling find and persist
reference = http://127.0.0.1:8888/users/123
query params = []
query = []
query string =
search query = null
i'm sure i'm doing something stupid here i just have no idea how to proceed right now. Any help as to what i'm doing wrong would be greatly appreciated.
This is due to GAE not supporting chunked encoding. See workaround here:
http://wiki.restlet.org/docs_2.1/13-restlet/21-restlet/318-restlet/303-restlet.html#dsy303-restlet_gwt

No Viable Alternative at character ' '

Hi i am getting the following error in this code
/*
Class : CreateMobileChatterCntrl
Description : Post Chatter on Contact.
Developed by : Harish Khatri(Appirio Offshore)
Created Date : June 2, 2012
*/
public without sharing class CreateMobileChatterCntrl {
public final Id ContactID{get;set;}
public String message{get;set;}
public boolean isSuccess{get;set;}
public boolean throwError{get;set;}
public String deviceType{get;set;}
//----------------------------------------------------------------------------
//constructor
//----------------------------------------------------------------------------
public CreateMobileChatterCntrl() {
throwError = false;
isSuccess = false;
if( ApexPages.CurrentPage().getParameters().get('id') != null){
ContactID = ApexPages.CurrentPage().getParameters().get('id');
}
String userAgent = ApexPages.currentPage().getHeaders().get('USER-AGENT');
if(userAgent.contains('iPhone'))
deviceType = 'iPhone';
//else if(userAgent.contains('Android')) deviceType = 'Android';
}
//----------------------------------------------------------------------------
// Post the chatter on contact
//----------------------------------------------------------------------------
public Pagereference save() {
if(message == null || message ==''){
throwError = true;
return null;
}
FeedItem feedItem = new FeedItem();
feedItem.ParentId = ContactID;
feedItem.Body = message;
try {
insert feedItem;
isSuccess = true;
} catch(Exception e){}
return null;//new PageReference('/' + ContactID);
}
public Pagereference cancel() {
return new PageReference('/' + ContactID);
}
}
public final Id ContactID{get;set;} at this line i am getting the error No Viable Alternative at character ' '.can any one please help why i am getting this error??
Some of the single quote characters in your class file are invalid --- perhaps because you copied and pasted the code from somewhere else. I've had this happen many times before when I've copied code from elsewhere. Starting with the quotes in: message == '' , i'd delete the single quotes, retype them, and resave your file. Repeat for all single quotes (or do a find and replace).

Resources