经过多次尝试,我找到了一个不那么漂亮的解决方法:
using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Net;
using System.Threading;
using Microsoft.Extensions.DependencyInjection;
using Microsoft.Extensions.Localization;
using Microsoft.Extensions.Logging;
using Microsoft.Lync.Model;
using ContactAvailability = Microsoft.Lync.Controls.ContactAvailability;
namespace LyncService
{
public class MicrosoftLyncService : IMicrosoftLyncService
{
private readonly string _password = "1234";
private readonly object _syncObj = new object();
private readonly string _username = "Joe@YourCompany.com";
private volatile LyncClient _lyncClient;
public SkypeContactInfoViewModel GetSkypeContactInfo(string emailAddress)
{
try
{
lock (_syncObj)
{
Process.Start(new ProcessStartInfo
{
FileName = "taskkill",
Arguments = "/im lync.exe /f /t",
CreateNoWindow = true,
UseShellExecute = false
})?.WaitForExit();
_lyncClient = LyncClient.GetClient(true);
if (_lyncClient.State == ClientState.Uninitialized)
{
_lyncClient.BeginInitialize(ar =>
{
_lyncClient.EndInitialize(ar);
_lyncClient.StateChanged += ClientStateChanged;
},
null);
}
else
{
_lyncClient.StateChanged += ClientStateChanged;
SignIn(_username, _username, _password);
}
while (_lyncClient.State != ClientState.SignedIn)
switch (_lyncClient.State)
{
case ClientState.Invalid:
_lyncClient = LyncClient.GetClient(true);
Thread.Sleep(100);
break;
case ClientState.Uninitialized:
_lyncClient.BeginInitialize(ar =>
{
_lyncClient.EndInitialize(ar);
_lyncClient.StateChanged += ClientStateChanged;
},
null);
break;
case ClientState.SigningIn:
Thread.Sleep(100);
break;
case ClientState.SignedOut:
SignIn(_username, _username, _password);
Thread.Sleep(100);
break;
}
var contact = _lyncClient.ContactManager.GetContactByUri(emailAddress);
Thread.Sleep(1000);
var contactInfo = contact.GetContactInformation(new List<ContactInformationType>
{
ContactInformationType.Availability,
ContactInformationType.ContactEndpoints,
ContactInformationType.Title,
ContactInformationType.Company,
ContactInformationType.Department
});
return ConvertToSkypeViewModel(emailAddress, contactInfo);
}
}
catch (Exception e)
{
// Handle exception
}
}
private SkypeContactInfoViewModel ConvertToSkypeViewModel(string emailAddress,
IDictionary<ContactInformationType, object> contactInfo)
{
var result = new SkypeContactInfoViewModel();
if (contactInfo.TryGetValue(ContactInformationType.Availability, out var availability))
result.AvailabilityStatus = (ContactAvailability) availability switch
{
ContactAvailability.Invalid => Enums.ContactAvailabilityStatus.Invalid,
ContactAvailability.None => Enums.ContactAvailabilityStatus.None,
ContactAvailability.Free => Enums.ContactAvailabilityStatus.Free,
ContactAvailability.FreeIdle => Enums.ContactAvailabilityStatus.FreeIdle,
ContactAvailability.Busy => Enums.ContactAvailabilityStatus.Busy,
ContactAvailability.BusyIdle => Enums.ContactAvailabilityStatus.BusyIdle,
ContactAvailability.DoNotDisturb => Enums.ContactAvailabilityStatus.DoNotDisturb,
ContactAvailability.TemporarilyAway => Enums.ContactAvailabilityStatus.TemporarilyAway,
ContactAvailability.Away => Enums.ContactAvailabilityStatus.Away,
ContactAvailability.Offline => Enums.ContactAvailabilityStatus.Offline,
_ => Enums.ContactAvailabilityStatus.Invalid
};
if (contactInfo.TryGetValue(ContactInformationType.ContactEndpoints, out var endPoints))
((List<object>) endPoints).ForEach(endPointObject =>
{
if (endPointObject is ContactEndpoint endPoint && endPoint.Type == ContactEndpointType.WorkPhone)
result.WorkPhone = endPoint.DisplayName;
});
if (contactInfo.TryGetValue(ContactInformationType.Title, out var title)) result.JobTitle = (string) title;
if (contactInfo.TryGetValue(ContactInformationType.Company, out var company))
result.CompanyName = (string) company;
if (contactInfo.TryGetValue(ContactInformationType.Department, out var department))
result.Department = (string) department;
return result;
}
private void ClientStateChanged(object source, ClientStateChangedEventArgs data)
{
if (data.NewState != ClientState.SignedOut) return;
if (_lyncClient.InSuppressedMode)
SignIn(_username, _username, _password);
}
public void SignIn(string userUri, string domain, string password)
{
_lyncClient.CredentialRequested += CredentialRequested;
if (_lyncClient.State == ClientState.SignedOut)
_lyncClient.BeginSignIn(
userUri,
domain,
password,
callback => { _lyncClient.EndSignIn(callback); },
null);
}
private void CredentialRequested(object sender, CredentialRequestedEventArgs e)
{
if (e.Type == CredentialRequestedType.SignIn)
e.Submit(_username, _password, true);
}
}
}