728x90

파티션을 고려하지 못한 부분과 index_id 비교를 잘못해서 인덱스 크기 잘못 계산된 부분 재공유 합니다.
파티션을 이루는 파티션의 개수와 압축을 이용한 파티션의 개수를 같이 보여 줍니다.
SQL Server 2008 Enterprise Edition이 아니면 압축 관련 부분은 주석 처리하시면 됩니다.

select    object_name(max(object_id))

,        max(b.PartitionCnt) as 'PartitionCnt'

,        max(b.CompressionCnt) as 'CompressionPartitionCnt'

,        sum(used_page_count) * 8 as 'Total Used(KB)'

,        sum(reserved_page_count) * 8 as 'Total Reserved(KB)'

,        sum(case when index_id = 0 then used_page_count else 0 end) * 8 as 'Heap(KB)'

,        sum(case when index_id = 1 then used_page_count else 0 end) * 8 as 'Cluster(KB)'

,        sum(case when index_id >= 2 then used_page_count else 0 end) * 8 as 'Index(KB)'

,        max(row_count) as 'RowCount'

,        sum(in_row_used_page_count) * 8 as 'Row Used(KB)'

,        sum(in_row_reserved_page_count) * 8 as 'Row Reserved(KB)'

,        sum(lob_used_page_count) * 8 as 'LOB Used(KB)'

,        sum(lob_reserved_page_count) * 8 as 'LOB Reserved(KB)'

,        sum(row_overflow_used_page_count) * 8 as 'Overflow Used(KB)'

,        sum(row_overflow_reserved_page_count) * 8 as 'Overflow Reserved(KB)'

from    (    select    object_id

            ,        index_id

            ,        sum(used_page_count) as used_page_count

            ,        sum(reserved_page_count) as reserved_page_count

            ,        sum(row_count) as row_count

            ,        sum(in_row_used_page_count) as in_row_used_page_count

            ,        sum(in_row_reserved_page_count) as in_row_reserved_page_count

            ,        sum(lob_used_page_count) as lob_used_page_count

            ,        sum(lob_reserved_page_count) as lob_reserved_page_count

            ,        sum(row_overflow_used_page_count) as row_overflow_used_page_count

            ,        sum(row_overflow_reserved_page_count) as row_overflow_reserved_page_count

            from sys.dm_db_partition_stats with(nolock)

            where object_name(object_id) not like 'sys%'

            group by object_id, index_id

        ) as a

        cross apply (    select    count(aa.object_id) as 'PartitionCnt'

                        ,        sum(case when aa.data_compression > 0 then 1 else 0 end) as 'CompressionCnt'

                        from sys.partitions aa

                        where aa.object_id = a.object_id and aa.index_id = a.index_id

                        group by aa.object_id, aa.index_id

                    ) b

group by object_id

order by 'Total Used(KB)' desc

728x90
728x90

파티션 구성 정보를 조회하면서 파티션의 사이즈 및 압축 정보까지 한꺼 번에 볼 수 있도록 수정 하였음.

select
    a.PartitionName, a.FuncName, a.PartitionCount, a.Type, a.Value, a.Equality, a.Destnation_id, c.name as 'FileGroupName'

,        object_name(d.object_id) as 'ObjectName'

,        d.used_page_count * 8 as 'Total Used(KB)'

,        d.reserved_page_count * 8 as 'Total Reserved(KB)'

,        row_count as 'RowCount'

,        data_compression_desc

from            (    select    a.name as 'PartitionName', b.name as 'FuncName', b.fanout as 'PartitionCount'

                    ,        case when boundary_value_on_right = 1 then 'Right' else 'Left' end as 'Type'

                    ,        d.value, case when boundary_value_on_right = 1 then '<=' else '>=' end as 'Equality'

                    ,        case when boundary_value_on_right = 1 then d.boundary_id + 1 else d.boundary_id end as 'destnation_id'

                    ,        a.data_space_id

                    from            sys.partition_schemes a with(nolock)

                        inner join    sys.partition_functions b with(nolock) on a.function_id = b.function_id

                        inner join    sys.partition_parameters c with(nolock) on b.function_id = c.function_id

                        inner join    sys.partition_range_values d with(nolock) on c.function_id = d.function_id and c.parameter_id = d.parameter_id

                    union all

                    select    a.name as 'PartitionName', b.name as 'FuncName', b.fanout as 'PartitionCount', 'Right' as 'Type', d.value, '>', 1, a.data_space_id

                    from            sys.partition_schemes a with(nolock)

                        inner join    sys.partition_functions b with(nolock) on a.function_id = b.function_id

                        inner join    sys.partition_parameters c with(nolock) on b.function_id = c.function_id

                        inner join    (    select function_id, parameter_id, min(value) as 'value'

                                        from sys.partition_range_values with(nolock)

                                        group by function_id, parameter_id

                                    ) d on c.function_id = d.function_id and c.parameter_id = d.parameter_id

                    where b.boundary_value_on_right = 1

                    union all

                    select    a.name as 'PartitionName', b.name as 'FuncName', b.fanout as 'PartitionCount', 'Left' as 'Type', d.value, '<', d.boundary_id, a.data_space_id

                    from            sys.partition_schemes a with(nolock)

                        inner join    sys.partition_functions b with(nolock) on a.function_id = b.function_id

                        inner join    sys.partition_parameters c with(nolock) on b.function_id = c.function_id

                        inner join    (    select function_id, parameter_id, max(value) as 'value', max(boundary_id) + 1 as 'boundary_id'

                                        from sys.partition_range_values with(nolock)

                                        group by function_id, parameter_id

                                    ) d on c.function_id = d.function_id and c.parameter_id = d.parameter_id

                    where b.boundary_value_on_right = 0

                ) a

    inner join    sys.destination_data_spaces b with(nolock) on a.data_space_id = b.partition_scheme_id and a.destnation_id = b.destination_id

    inner join    sys.data_spaces c with(nolock) on b.data_space_id = c.data_space_id

    cross apply (    select    bb.object_id, bb.used_page_count, bb.reserved_page_count, bb.row_count, cc.data_compression_desc

                    from            sys.indexes aa with(nolock)

                        inner join    sys.dm_db_partition_stats bb with(nolock) on aa.object_id = bb.object_id and aa.index_id = bb.index_id

                        inner join    sys.partitions cc with(nolock) on aa.object_id = cc.object_id and aa.index_id = cc.index_id

                    where aa.data_space_id = a.data_space_id

                      and a.destnation_id = bb.partition_number and a.destnation_id = cc.partition_number

                ) d

order by a.PartitionName, a.Destnation_id

728x90
728x90

SQL Server 트랜잭션 로그 읽기 

 

-       Version : SQL Server 2005, 2008, 2008R2, 2012 

 

데이터베이스에서 발생하는 행위는 트랜잭션 로그 라는 곳에 기록된다. 문서화되지 않은 기능 fn_dblog 함수를 사용하여 트랜잭션 로그의 정보를 읽어보자. 

 

Fn_dblog는 트랜잭션의 시작 LSN과 종료 LSN을 필요로 한다. NULL은 기본값으로 트랜잭션 로그 파일의 모든 로그 레코드를 반환한다. 

 

실습을 위해 데이터베이스를 생성한다. 

--Create DB. 

USE [master]; 

GO 

CREATE DATABASE ReadingDBLog; 

GO 

-- Create tables. 

USE ReadingDBLog; 

GO 

CREATE TABLE [Location] ( 

    [Sr.No] INT IDENTITY, 

    [Date] DATETIME DEFAULT GETDATE (), 

    [City] CHAR (25) DEFAULT 'Seoul'); 

 

다음 스크립트를 실행하여 데이터베이스 및 테이블을 작성하는데 걸린 어떤 과정과 단계를 확인할 수 있다. 

USE ReadingDBLog; 

GO 

select COUNT(*) from fn_dblog(null,null) 

 

 

 

데이터베이스 생성과 테이블을 생성하는데 총 176행의 정보가 생성된 것을 확인 할 수 있다. 다음 스크립트를 통해 데이터베이스 생성, 테이블 생성에 기록된 트랜잭션 로그 파일 데이터를 확인하여 보자. 

USE ReadingDBLog; 

GO 

select [Current LSN], 

       [Operation], 

       [Transaction Name], 

       [Transaction ID], 

       [Transaction SID], 

       [SPID], 

       [Begin Time] 

FROM   fn_dblog(null,null) 

 

 

 

LOP_BEGIN_XACT는 트랜잭션의 시작을 의미한다. 작업 열은 우리가 삽입, 업데이트, 삭제, 축소, 잠금, 페이지 할당 등과 같이 수행되는 작업을 알려준다.  

 

데이터의 삽입, 업데이트, 삭제 등의 DML 스크립트를 사용하여 트랜잭션 로그 파일에 기록하는 방법을 확인하여 보자. 이 작업을 수행하는 동안 페이지가 할당 또는 해제되는 방법을 추적할 수 있다. 

USE ReadingDBLog 

go 

INSERT INTO Location DEFAULT VALUES ; 

GO 100 

GO 

UPDATE Location 

SET City='New Delhi' 

WHERE [Sr.No]<5 

GO 

DELETE Location  

WHERE [Sr.No]>90 

Go 

 

데이터 입력 수정, 삭제가 완료되었으면 트랜잭션 로그 파일을 확인해 보자.  

USE ReadingDBLog 

go 

SELECT 

 [Current LSN], 

 [Transaction ID], 

 [Operation], 

  [Transaction Name], 

 [CONTEXT], 

 [AllocUnitName], 

 [Page ID], 

 [Slot ID], 

 [Begin Time], 

 [End Time], 

 [Number of Locks], 

 [Lock Information] 

FROM sys.fn_dblog(NULL,NULL) 

WHERE Operation IN  

   ('LOP_INSERT_ROWS','LOP_MODIFY_ROW', 

    'LOP_DELETE_ROWS','LOP_BEGIN_XACT','LOP_COMMIT_XACT')   

 

 

 

트랜잭션을 시작하고 힙테이블 dbo.location 에 데이터를 입력하고 트랜잭션을 완료하는 것을 확인 할 수 있다. UPDATE문과 DELETE 구문도 확인 할 수 있다. 

 

트랜잭션 로그에서 SQL Server의 페이지 분할이나 페이지 분할 횟수 등 내부 동작도 확인할 수 있다. 

 

다음 스크립트를 실행하여 스플릿 정보를 확인한다. 

USE ReadingDBLog 

go 

--Get how many times page split occurs. 

SELECT  

 [Current LSN], 

 [Transaction ID], 

 [Operation], 

  [Transaction Name], 

 [CONTEXT], 

 [AllocUnitName], 

 [Page ID], 

 [Slot ID], 

 [Begin Time], 

 [End Time], 

 [Number of Locks], 

 [Lock Information] 

FROM sys.fn_dblog(NULL,NULL) 

WHERE [Transaction Name]='SplitPage'  

GO 

 

 

 

위에서 확인된 스플릿의 트랜잭션ID를 사용하여 추적할 수 있다. 

--Get what all steps SQL Server performs during a single Page Split occurrence. 

SELECT  

 [Current LSN], 

 [Transaction ID], 

 [Operation], 

  [Transaction Name], 

 [CONTEXT], 

 [AllocUnitName], 

 [Page ID], 

 [Slot ID], 

 [Begin Time], 

 [End Time], 

 [Number of Locks], 

 [Lock Information] 

FROM sys.fn_dblog(NULL,NULL) 

WHERE [Transaction ID]='0000:000002dd'   

 

 

 

 

트랜잭션 로그는 백업의 상호 관계에서는 백업을 진행 할 경우 트랜잭션 로그가 잘리게되어 로그 파일을 축소 할 수 있다. 

다음 스크립트를 통하여 백업 후 트랜잭션 로그의 행 숫자가 줄어든 것을 확인 할 수 있다. 

SELECT COUNT(*) 

FROM fn_dblog(null,null) 

GO 

 

BACKUP DATABASE ReadingDBLog TO DISK = 'c:\SQL_DATA\ReadingDBLog_Full.bak' 

GO 

 

SELECT COUNT(*) 

FROM fn_dblog(null,null) 

GO 

 

 

 

 

[참고자료] 

http://www.mssqltips.com/sqlservertip/3076/how-to-read-the-sql-server-database-transaction-log/ 

 

728x90
728x90

Skype for Business Server 2015 provide In-Place upgrade option which can be relevant for Lync Server 2013 customers. Microsoft didn’t make any changes in hardware profile for Skype for Business Server 2015, therefore customer can adopt SfB easily to get the latest enhancements. In this post, I will cover step by step in-place upgrade for SfB standard edition. In my setup, I have one Lync Server 2013 Standard Edition with Mediation server collocated and one SQL server for Archiving and Monitoring databases.

In-place upgrade is available in two mode:

1. Migrate user mode (No user downtime)

2. Offline-mode (User downtime)

To know more about in-place upgrade paths, read Planning for In-Place upgrade with Skype for Business

In this post, I am using offline-mode as I have one Lync Server 2013 Standard Edition pool.

I will start first thing first:

1. Must update your operating system with latest updates.

2. Download and Install Hotfix

Windows Server 2012 R2: https://support.microsoft.com/en-us/kb/2982006

Windows Server 2012: https://support.microsoft.com/en-us/kb/2858668

Windows Server 2008 R2: https://support.microsoft.com/en-us/kb/2533623

3. Update Lync Server 2013 with minimum CU5 (Feb 2015)

Follow below KB article to download and install updates step by step. (Make sure update process completes successfully without any error and all given steps are covered)

https://support.microsoft.com/en-us/kb/2809243

4. Stop Lync Services on Standard Edition Server

5. Update SQL Server Express Edition on Lync Standard Edition Server. (Download and install SQL Server 2012 SP1)

6. Update SQL Server 2012 archiving & monitoring database server. (Download and install SQL Server 2012 SP1)

Reboot the servers after SP1 installation.

7. Check the Standard Edition pool status for upgrade readiness state.

Make sure: IsReadyForUpgrade: True

8. Go to any one of the domain joined Windows server in your environemnt and run Skype for Business Server 2015 intial setup to install Skype for Business Server 2015, Topology Builder and Management Shell.

9. Open topology builder and download topology from existing deployment.

10. Go to the Lync Server 2013 Standard Edition and right click to select “Upgrade to Skype for Business Server 2015…”

11. Click on Yes.

12. Now, you can observe Lync Server 2013 SE has been moved under Skype for Business Server 2015.

13. Now publish the topology.

14. Check readiness state one more time.

15. Stop Lync Server services gracefully.

16. Go to the services.msc and make sure all services are stopped, any Lync service should not be in paused or running state.

17. Run Setup.exe on Standard Edition server from Skype for Business Server 2015 media and follow the steps.

 

 

Note: If you are getting below prompt to restart the server, don’t worry just reboot the server and run the setup wizard once server comes up.

 

 

 

Once upgrade process has completed successfully you can review the logs.

 

18. Open Skype for Business Server 2015 Management Shell and run Start-Cspool… (you can also use –Force switch)

Once SE pool started successfully, go to the Skype for Business Server Control Panel.

 

19. If you open monitoring reports on upgraded server, you will still find Lync Server 2013.

20. To upgrade the monitoring reports, go to the deployment wizard and run “Deploy Monitoring Reports”

Once deployment process is completed successfully, open monitoring reports for Skype for Business Server.

 

728x90
728x90

Licensing is not an easy part for everyone but this post will help you a bit to understand the Skype for Business licensing. To design or implement any solution makes more sense if solution cost justify the ROI. Skype for Business has different types of licensing.

  • Server License: Skype for Business Server 2015 has same licensing concept as it was with Lync Server 2013. There is only one type of server license which means there is no separate license for Standard Edition or Enterprise edition. License only applicable to Front End Servers. If you have 4 Standard Edition Server, you need 4 server license or if you have 1 Enterprise Edition Front End pool with 4 Front End server then also you need only 4 server license. Apart from Front End server role, none of the Skype for Business Server roles need license.
  • Client License: Skype for Business 2015 has three different types of client licenses.
    • Skype for Business Standalone client
    • Skype for Business with Office pro plus
    • Skype for Business Basic client (free).
  • Client Access License (CALs): Skype for Business Server CALs are required to use Skype for Business Server. Skype for Business has three different types of CALs which provides different kind of functionalities. Standard CALs are basic requirement for other CALs.
    • Standard CALs: Standard CALs are basic client access license which enable users or devices to connect Skype for Business Server and provides basic features such as IM/Presence, peer-to-peer VOIP and HD Video, and skype connectivity.
    • Enterprise CALs: Enterprise CALs provide additional features to Standard CALs and Standard CALs are prerequisite for Enterprise CALs. It provides scheduled and impromptu meetings with audio and video calling, desktop and application sharing, and dial-in conferencing on mobile phones, tablets, PC and Mac.
    • Plus CALs: Plus CALs are additional CALs and required only for Enterprise Voice features, and Standard CALs are prerequisite for Plus CALs. It enables PSTN in/out, emergency calling, and other enterprise-grade phone features.
728x90
728x90

For example: I have common name between all the users. You can have common “Department”, “OU” or something else which can be used to filter the users.

Get-CsAduser -LDAPFilter “(name=sfb*)” | Enable-CsUser -RegistrarPool “poolfqdn” -SipAddressType EmailAddress

728x90
728x90

Let me start by saying that I am NOT even half as good as the great Mr. Pat Richard when it comes to PowerShell.  If he is the major league of PowerShell, on my best day I’m a solid backup player for a little league team.  Therefore the PowerShell that I’m about to share could be a lot better but think of it as a first step to something better in the future.  If you have any improvements feel free to add them to the comments.

Over the last few weeks I’ve been thinking about a way to assist a client in the draining of their servers for the purposes of patching.  As it is well documented, the draining process will leave services up and running in a paused state until all active conversations are completed.  The issue I’ve ran into a few times however is that I’ve waited over 24 hours and some services (typically the IM MCU) are still up and running.  Often times, this is just a random person who left a conference IM window open on their computer but none the less I don’t want to bounce the box if there is a legitimate conference going on.

So I started digging around the database (because that is where all the cool stuff happens in Lync) and knowing exactly where all of the active conference are happening decided to start looking for a way to display that information via PowerShell.  I decided the simplest way was to prompt for a pool, look-up the members of that pool and loop through each of the front-end servers.

The SQL is the easy part:

SELECT ActiveConference.ConfId AS ‘Conference ID’, ActiveConference.Locked, Participant.UserAtHost AS ‘Participant’, Participant.JoinTime, Participant.EnterpriseId, ActiveConference.IsLargeMeeting AS ‘Large Meeting’ FROM ActiveConference INNER JOIN Participant ON ActiveConference.ConfId = Participant.ConfId

Each front-end server in the RTCDYN database has an ActiveConference table which contains all of the active conferences running on that particular server.

pic2

And the Participants table contains all of the active participants for the call with a corresponding conference ID.  Therefore all we need to do is join the two tables together and we have a complete list.  Using this information I went ahead and created this short script:

pic3

Download Here: Get-CSActiveConferences

You will need to rename the script to .ps1 from .txt.  Once you have renamed the file, go ahead and run .Get-CsActiveConferences from the Lync Management Shell.  It will prompt you for the name of the pool you want get results from.  Your results will look like:

pic1

NOTE: You may need to adjust firewall rules if you don’t allow your local SQL databases to be accessible remotely.  Port 1433 is the default SQL port.

All meetings will be grouped by Conference ID.  By default I’m showing the Participant, Join Time and if it is a Large Meeting.  You can always edit the PowerShell file to display other information if needed.  If you have any good requests or changes please just pass them along and I’ll post them.

 

http://masteringlync.com/2013/11/19/list-all-active-conferences-via-powershell/

728x90
728x90

Howdy,

I had free time in the holidays that I spent playing around with databases of Lync and took notes of what I found and learned and decided to put them in an article to be used as a…let’s say Lync databases anatomy, I’ll be talking about a simple Lync pool installation and databases included with it.


Overview of Lync database architecture

First things first, in Lync there are couple of places that databases are usually installed, depend on your Lync pool design

  • Enterprise front end Pool – Master databases installed on SQL backend server and copy database installed locally on the front end servers
  • Standard front end Pool – both master & copy databases are installed locally on the Front end server (SQL Express)
  • In My lab I have an Enterprise front end pool with a SQL backend server, so I’ll be talking about two locations where databases are installed on the SQL backend and the front end servers. In case of a standard edition front end pool those databases are installed in one location – the front end.

    image

    PowerShell command Get-CsConfigurationStoreLocation can help locating the server used as Lync Backend

    image

    RTC instance, RTC and RTCLOCAL… huh?

    for some engineers with limited understanding of SQL (like me), they might get confused when talking about too many use of the word RTC in a conversation, and if you include RTCLOCAL to the conversation they just start fade away Smile

    so let’s clear things up shall we?

  • Instance: think of a SQL Instance as a container that have Databases inside it.
  • Database: well database is where the data is actually stored
  • taking this definition and apply it to Lync databases we get the following

  • RTC Instance is used by Lync to store all the backend databases, including the master CMS, Response Groups configuration, location database…etc.
  • image

    NOTE: RTC is the default name of the Lync instance, but it can be changed during deployments.

  • RTC Database is used by Lync to store persistent user information like scheduled conferences, contact lists..etc.
  • RTCLOCAL Instance is used by Lync front end server to store a local copy of the master CMS database and other database used for some user information (presence, endpoints..etc.) explained later in this article.
  • image

    you can learn more about RTC & RTCLOCAL from my previous article Simple understanding for Lync CMS

    Lync Databases

    Now let’s talk about the type of each of those databases you see and what are they used for. In Lync there are number of database types I used the way TechNet divided them with small different (full list can be found here)

  • Application
  • Archiving & Monitoring
  • Central management
  • Lync Core
  • Users
  • Application Databases

    following databases are considered “Application” databases

    • CPsdyn: contain dynamic information used by Call Park application like “Orbits”

    image

    • RGSConfig: contain the configuration of the Response Groups, like Agents, Workflows, Queues, Holidays…etc.

    image

    • RGSDyn: contain dynamic “live” information used by the Response Groups
    Archiving & Monitoring

    I think from the name it is obvious what are they used for, just pay attention that usually those databases are installed on a different SQL instance, not the default one.

    • LCSLog: archive information about Instant messaging sessions, P2P calls and conferencing used by the archiving server.
    • LCSCdr: store the call details records used by the monitoring server.
    • QoEMetrics: store information about Quality of Experience used by the monitoring server.
    Central Management
    • XDS: this is the Lync Central management Store (CMS) database, it holds Lync topology, configuration and polices (more details: Simple understanding for Lync CMS)
    • Lis: store location information (network subnets, ports, Switches…etc.) that is used by Lync Location services for E9-1-1 feature.

    image

    Lync Core

    Following databases are usually installed on both the RTC and RTCLOCAL instances

    • RTC: as mentioned before, it store persistent user information (contact list, scheduled conferences…etc.)
    • RTCDyn: Store dynamic “live” data about users (current presence, endpoints user logged in from…etc.)
    Users
    • RTCAB: store the Lync address book information used by Lync address book services
    • RTCXDS: store a back up of user data

    that’s all, a small quick and to the point explanation of Lync Databases types and functionalities, hope you found it helpful.

    Happy New year everyone Smile

     

     

    https://lyncdude.com/2014/12/31/understand-lync-databases/#more-1863

    https://technet.microsoft.com/ko-kr/library/gg398479.aspx

    728x90
    728x90

    Update May 2015: The process below is the same for Skype for Business.

    Issues with the Lync Address book are common to all Lync admins. Troubleshooting these issues isn’t as easy as it looks. To better troubleshoot or change the information stored in the Lync Address Book, you need to be aware of all the steps it takes in creating the Lync Address Book. To simplify the explanation of how the address book ends up at the users side, I created the following flowchart of this process.

    Lync Address Book Sync

    Lync Address Book Sync

    Step 1 – User Replicator

    AbAttribute Table

    AbAttribute Table

    Information about your Users, Contacts and Groups is stored in Active Directory (AD). This information is retrieved from AD by the User Replicator and placed in the user database into the RTCab database. The table AbUserEntry is used to store this information and it contains two colums, one for the UserGUID and one for all the UserData. What kind of data is placed in the column is defined by the entries in the AbAttribute table. If this table is empty the User Replicator will skip the AbUserEntry filling process (no users in the Lync Address Book). With each attribute a flag is also present. This flag determines what happens with translation between AD and the AbUserEntry table or, if a certain AD attribute is present, to include or exclude the user from adding it to the AbUserEntry table. You can control the AbAttribute table by using the ABSConfig.exe tool (Lync 2013 Resource Kit). For more information regarding the attributes and flags see: Administering the Address Book Service, Lync 2013. After changing the AbAttribute table, make sure you run Update-CSAddressBook to regenerate the address book.

    By default all domains that are found will be replicated and will be replicated alphabetically from A to Z. If there are some domains that you don’t want to replicate to the Lync Address Book, use the ADDomainNamingContextList parameter (Set-CsUserReplicatorConfiguration) to add only the domains you want to synchronize. Use the following commands:

    # Add domains
    Set-CsUserReplicatorConfiguration -Identity global -ADDomainNamingContextList @{Add="dc=domain1,dc=local","dc=domain2,dc=local"}
    
    # Remove domain
    Set-CsUserReplicatorConfiguration -Identity global -ADDomainNamingContextList @{Remove="dc=domain2,dc=local"}

    Note: In previous versions of Lync it’s still imperative to use the Update-CSUserDatabase powershell command. In Lync 2013 this process runs at a configured interval. To retrieve how often this is done or find more settings, use Get-CsUserReplicatorConfiguration.

    Step 2 – Address Book

    Information of your users, contacts and groups is now in the Lync database. The next step is to create the actual address book files. These files are generated by the Front End with the Address Book Server task and stored in the Lync file share defined in your topology . In this share you’ll find the following subfolder: \ServerLyncShare1-WebServices-1ABFiles. When you’re in a single tenant Lync configuration you’ll only find the tenant directory 00000000-0000-0000-0000-000000000000, which is the default for the msRTCSIP-TenantId attribute in AD. This attribute stores the unique identifier of the tenant.

    In this subdirectory you’ll find all *.lsabs and *.dabs files which your clients will download. The address book files are generated by default each day at  1:30 AM. When the process starts, it uses the company_phone_number_normalization_rules.txt to translate telephone numbers to E.164 format. Remember that this file will translate all numbers, even numbers that are already in E.164 format if rules are applicable, like the msRTCSIPLine attribute. The text file is used when it’s placed in the ABFiles directory. By default this text file doesn’t exist. Numbers not being translated correctly are placed in the tenant directory in a file called Invalid_AD_Phone_Numbers.txt. Check your Lync eventviewer for information or errors regarding the Lync Address Book Server, filter on LS Address Book Server.

    Log Name:      Lync Server
    Source:        LS Address Book Server
    Event ID:      21034
    Task Category: (1008)
    Level:         Warning
    Keywords:
    Classic Description:
    One or more phone numbers failed to normalize. 300 total numbers failed to normalize.  They are listed in the text file: ‘\ServerLyncShare1-WebServices-1ABFiles0000000-0000-0000-0000-0000000000000000000-0000-0000-0000-000000000000Invalid_AD_Phone_Numbers.txt’ Cause: One or more phone number attributes in Active Directory contained text that could not be normalized.  Normalization rules are contained in the optional Company_Phone_Number_Normalization_Rules.txt file located in the output location or in the generic rules built into Address Book Server.  Refer to the documentation for a description of the built-in generic normalization rules.  Use the ABServer -dumpRules command to see all the rules that Address Book Server is currently configured with. Resolution: Either create a Company_Phone_Number_Normalization_Rules.txt file in the output location and make sure it covers all cases found in your Active Directory deployment or fix the invalid phone number(s) in the Active Directory record(s).

    Use Get-CsAddressBook to retrieve all the Address Book settings. For the use of all normalization rules make sure the UseNormalizationRules is set to True.

    You can make the Address Book files from the Lync share readable by exporting them, use the following cmd:

    abserver -dumpfile “\ServerLyncSharen-WebServices-nABFiles0000000-0000-0000-0000-0000000000000000000-0000-0000-0000-000000000000F-0ef3.lsabs” c:TempExport-ABS.txt

    Note: An un-documented feature, found by  Trevor Miller, when there is a Company_Phone_Number_Normalization_Rules.txt file placed in the installation directory of Lync (ex. C:Program FilesMicrosoft Lync Server 2013ServerCore), this file will be used.

    Step 3 – Clients

    Now that your Address Book files are ready, clients can download them, if the AddressBookAvailability is set to download the address book this is the default. Make sure you have a good reason to make the address book available locally, as the preferred method would be to set the addressbookavailability to WebSearchOnly.

    If you have set the availability to download, when a client starts it will connect to the internal or external Address Book Server URL:

    • URL Internal From Server;https://LyncpoolFQDN:443/abs/handler
    • URL External From Server;https://LyncExternalWebServiceFQDN:443/abs/handler

    Use the Test-CsAddressBookService and Test-CsAddressBookWebQuery commands to check errors regarding the configuration. The client will download the files by default within 0 to 60 minutes. You can change this by using the GalDownloadInitialDelay (DWORD) registry key. Setting this key to the value of 0 will enforce a direct download. You can find or place this key in:

    • Lync 2010 : HKLM or HKCU SoftwarePoliciesMicrosoftCommunicator
    • Lync 2013:  HKLM or HKCU SoftwarePoliciesMicrosoftOffice15.0Lync

    When Lync has downloaded the files, you will have 2 files in the userprofile, namely GalContacts.db and GalContacts.db.idx. In Lync 2013 this is a file called ABS__sipdomain.cache. The cache file is updated when the user logs into Lync or after 24 hours when the cache is valid. On a Windows 7 or higher machine these files will be located in the folder:

    Lync 2010: %userprofile%AppDataLocalMicrosoftCommunicatorsip_user@domain
    Lync 2013: %userprofile%AppDataLocalMicrosoftOffice15.0Lyncsip_user@domain

     

    Common issues

    Now that you know how the process works, here are some issues regarding the Lync Address Book.

    Lync User is not being displayed in the Lync Address Book

    You have a user who is Lync enabled. Everything is working, the user can log in, but when you search for this user on your Lync client no name is returned. The most common reason for this behaviour is based on an issue with step 1. When the User Replicator runs, it checks the attribute msExchangeHideFromAddressBook. This is the Exchange attribute for hiding users from the Global Address List (GAL). If this is set to TRUE, which indicates it doesn’t need to appear on the GAL, Lync will also ignore this user for the Address Book.

    Lync Response Group number to name

    You created a Lync Response Group, you can find it in the address book using it’s name, but when you type the phone number the Response Group isn’t resolved. Check the Invalid_AD_Phone_Numbers.txt file. See if your Response Group number is placed here. If it is, you haven’t used the E.164 format in the Display Number field. Change the field to the correct format or add a valid translation to the company_phone_number_normalization_rules.txtIf you leave the Display Number field empty, it will use the lineuri (telephone number) field to be placed as phone number in the address book. This also applies to extensions not being correctly translated to the Response Group name.

    The address book is preparing to synchronize

    If you haven’t set the GalDownloadInitialDelay registry, this will be displayed at a maximum of 0 to 60 minutes. If it keeps displaying the message try the following:

    1. Exit the Lync client
    2. Delete the local address book files (see step 3)
    3. Restart the Lync client
      Or a script to automatically delete the files (The Expta Blog).

    Try using the WebSearchOnly value in the Lync client policy. This will not use the local address book files anymore, but will only use the Address Book Web Query (ABWQ).

    Certain phone numbers from Active Directory not displayed on the contact card

    When you view a contact card in Lync, you’re missing phone numbers which you know you placed in AD.

    First make sure these numbers of the user are in E.164 format. If it’s not in E.164 format, use the Company_Phone_Number_Normalization_Rules.txt (Step 2) to normalize the numbers correctly. Run the Update-CSAddressBook command, make sure that your Lync client updates the Lync Address Book (step 3) and the numbers should now be visible in Lync.

    Something else…?

    There are a lot more questions, tools and issues regarding the address book. Feel free to contact me or drop a comment.

    And even more information about the Address Book:

    Incoming search terms:

    • ItsallabouttheLyncAddressBook-Fots-Lync/SfB
    • abwq normalized numbers
    • lync common area phone global address book
    • GET /abs/handler/F-5094 lsabs - 443
    • lync 2010 websearchonly showing wrong info
    • lync 2013 client address book sip
    • lync web based address book
    • sfb 2015 contacts not appearing
    • lync address name status common name
    • skype for business 2015 some users not showing in the address book
    728x90
    728x90

    $photo = [byte[]](Get-Content "C:\photo\test01.jpg" -Encoding byte)
    Set-ADUser 계정명 -Replace @{thumbnailPhoto=$photo}

     

    728x90

    + Recent posts