Ejemplo n.º 1
0
        private async Task DownloadProjectWorkbooksAsync(TableauProject sourceProject, TableauProject destProject)
        {
            _logger?.Debug($"Downloading workbooks for project {sourceProject.Name}");

            var sourceWorkbookService = _tableauServiceFactorySource.GetService <TableauWorkbookService>();

            var sourceWorkbooks = await GetProjectWorkbooksAsync(
                sourceProject.Id, _tableauServiceFactorySource
                ).ConfigureAwait(false);

            if (!Directory.Exists(_settingsMonitor.CurrentValue.workbookDownloadPath))
            {
                Directory.CreateDirectory(_settingsMonitor.CurrentValue.workbookDownloadPath);
            }

            foreach (var sourceWorkbook in sourceWorkbooks.Values)
            {
                _logger?.Debug($"Downloading workbook '{sourceWorkbook.Name}'");
                if (!_settingsMonitor.CurrentValue.DryRun)
                {
                    var fileName = VizDatasourceService.GetValidFileName(sourceWorkbook.Name) + ".twb";
                    var fileInfo = await sourceWorkbookService.DownloadWorkbookAsync(
                        sourceWorkbook.Id,
                        _settingsMonitor.CurrentValue.workbookDownloadPath,
                        fileName
                        ).ConfigureAwait(false);

                    _logger?.Debug($"Downloaded workbook '{sourceWorkbook.Name}' to '{fileInfo.FullName}'");
                }
            }

            _logger?.Debug($"Downloaded workbooks for project {sourceProject.Name}");
        }
Ejemplo n.º 2
0
        /// <summary>
        /// <see cref="ITableauProjectService.CreateProjectAsync"/>
        /// </summary>
        public async Task <TableauProject> CreateProjectAsync(
            string name,
            string description     = null,
            string parentProjectId = null
            )
        {
            _logger?.Debug($"Creating project {name}");

            var url = _tableauApiService.SiteUrl.AppendUri("projects");

            var project = new TableauProject()
            {
                Name            = name,
                Description     = description,
                ParentProjectId = parentProjectId
            };

            var requestJson = new JObject();

            requestJson["project"] = JToken.Parse(project.ToRequestString());

            var responseString = await _tableauApiService.SendPostAsync(
                url, requestJson.ToString()
                ).ConfigureAwait(false);

            var responseJson = JToken.Parse(responseString);

            project = JsonConvert.DeserializeObject <TableauProject>(
                responseJson.Value <JObject>("project").ToString()
                );

            _logger?.Debug($"Project {name} created with id {project.Id}");

            return(project);
        }
Ejemplo n.º 3
0
        private async Task MigrateProjectDatasourcesAsync(TableauProject sourceProject, TableauProject destProject)
        {
            _logger?.Debug($"Migrating datasources for project {sourceProject.Name}");

            var sourceDatasourceService = _tableauServiceFactorySource.GetService <TableauDatasourceService>();
            var destDatasourceService   = _tableauServiceFactoryDest.GetService <TableauDatasourceService>();

            var sourceDatasources = await GetProjectDatasourcesAsync(
                sourceProject.Id, _tableauServiceFactorySource
                ).ConfigureAwait(false);

            await _vizDatasourceService.LoadVizDatasourceReportAsync().ConfigureAwait(false);

            foreach (var sourceDatasource in sourceDatasources.Values)
            {
                await MigrateDatasourceAsync(sourceDatasource.Id, destProject.Id).ConfigureAwait(false);
            }
        }
Ejemplo n.º 4
0
        private async Task MigrateProjectUsersAsync(TableauProject sourceProject, TableauProject destProject)
        {
            _logger?.Debug($"Migrating users for project {sourceProject.Name}");

            var destUserService = _tableauServiceFactoryDest.GetService <TableauUserService>();
            var sourceUsers     = await GetProjectUsersWithDomain(
                sourceProject.Id, _tableauServiceFactorySource
                ).ConfigureAwait(false);

            foreach (var sourceUser in sourceUsers.Values)
            {
                var destUser = await destUserService.FindUserAsync(
                    sourceUser.Name, sourceUser.Domain?.Name
                    ).ConfigureAwait(false);

                if (destUser != null)
                {
                    _logger?.Debug($"User {sourceUser.UserPrincipalName} found in destination site");
                    continue;
                }

                _logger?.Debug($"Creating user {sourceUser.UserPrincipalName}");

                if (!_settingsMonitor.CurrentValue.DryRun)
                {
                    try
                    {
                        var newUser = await destUserService.AddUserToSiteAsync(
                            sourceUser.DownLevelLogonName, sourceUser.SiteRole
                            ).ConfigureAwait(false);

                        _logger?.Debug($"Created user {newUser.UserPrincipalName} ({newUser.Id})");
                    }
                    catch (Exception ex)
                    {
                        _logger?.Error($"Unable to create user: {ex.Message}");
                    }
                }
            }

            // allow Tableau api to catch up to db changes
            await Task.Delay(1000).ConfigureAwait(false);
        }
Ejemplo n.º 5
0
        private async Task MigrateProjectWorkbooksAsync(
            TableauProject sourceProject,
            TableauProject destProject,
            IEnumerable <string> workbooksToMigrate = null
            )
        {
            _logger?.Debug(
                "Migrating workbooks for project '{0}': '{1}'",
                sourceProject.Name,
                String.Join(", ", workbooksToMigrate)
                );

            var sourceWorkbookService = _tableauServiceFactorySource.GetService <TableauWorkbookService>();
            var destWorkbookService   = _tableauServiceFactoryDest.GetService <TableauWorkbookService>();

            var sourceUserService = _tableauServiceFactorySource.GetService <TableauUserService>();
            var destUserService   = _tableauServiceFactoryDest.GetService <TableauUserService>();

            var sourceWorkbooks = await GetProjectWorkbooksAsync(
                sourceProject.Id, _tableauServiceFactorySource
                ).ConfigureAwait(false);

            workbooksToMigrate = workbooksToMigrate ?? Enumerable.Empty <string>();

            var workbooksToSkip = _settingsMonitor.CurrentValue.WorkbooksToSkip ?? Enumerable.Empty <string>();

            foreach (var sourceWorkbook in sourceWorkbooks.Values)
            {
                if (
                    workbooksToSkip.Contains(sourceWorkbook.Name.Trim(), StringComparer.OrdinalIgnoreCase) ||
                    (
                        !workbooksToMigrate.Contains("*") &&
                        !workbooksToMigrate.Any(w => w.EqualsIgnoreCase(sourceWorkbook.Name.Trim()))
                    )
                    )
                {
                    _logger?.Debug($"Skipping workbook {sourceWorkbook.Name}");
                    continue;
                }

                _logger?.Debug($"Publishing workbook '{sourceWorkbook.Name}'");
                // get workbook metadata
                var workbook = await sourceWorkbookService.GetWorkbookAsync(
                    sourceWorkbook.Id, true
                    ).ConfigureAwait(false);

                var destWorkbook = await destWorkbookService.FindWorkbookAsync(
                    sourceWorkbook.Name, false
                    ).ConfigureAwait(false);

                if (destWorkbook != null)
                {
                    if (destWorkbook.Project?.Id == sourceWorkbook.Project?.Id)
                    {
                        _logger?.Debug($"Workbook '{sourceWorkbook.Name}' already exists in destination, skipping");
                        continue;
                    }
                    else
                    {
                        _logger?.Warning(
                            $"Workbook '{sourceWorkbook.Name}' found in project {destWorkbook.Project?.Id}"
                            );
                    }
                }

                var defaultDestUsername       = "";
                var defaultDestDomain         = "";
                var defaultDestUsernameTokens = _settingsMonitor.CurrentValue.DefaultOwnerUsername.Split('@', '\\');

                if (_settingsMonitor.CurrentValue.DefaultOwnerUsername.Contains("@"))
                {
                    defaultDestUsername = defaultDestUsernameTokens.First();
                    defaultDestDomain   = defaultDestUsernameTokens.Last();
                }
                else if (_settingsMonitor.CurrentValue.DefaultOwnerUsername.Contains("\\"))
                {
                    defaultDestUsername = defaultDestUsernameTokens.Last();
                    defaultDestDomain   = defaultDestUsernameTokens.First();
                }
                else
                {
                    defaultDestUsername = _settingsMonitor.CurrentValue.DefaultOwnerUsername;
                }

                var defaultDestUser = !String.IsNullOrWhiteSpace(defaultDestUsername)
                    ? await destUserService.FindUserAsync(defaultDestUsername, defaultDestDomain).ConfigureAwait(false)
                    : null;

                if (defaultDestUser == null)
                {
                    _logger?.Warning(
                        $"Default owner '{_settingsMonitor.CurrentValue.DefaultOwnerUsername}' not found in destination"
                        );
                }

                var sourceUser = await sourceUserService.GetUserAsync(workbook.Owner.Id).ConfigureAwait(false);

                var destUser = await destUserService.FindUserAsync(
                    sourceUser.Name, sourceUser.Domain?.Name
                    ).ConfigureAwait(false) ?? defaultDestUser;

                if (destUser == null)
                {
                    _logger?.Error($"Error, owner {sourceUser.DownLevelLogonName} not found in destination");
                    throw new Exception($"Error, owner {sourceUser.DownLevelLogonName} not found in destination");
                }

                if (!_settingsMonitor.CurrentValue.DryRun)
                {
                    try
                    {
                        _logger?.Debug($"Publishing workbook '{sourceWorkbook.Name}'");
                        var newWorkbook = await MigrateWorkbookAsync(
                            sourceWorkbook.Id, destProject.Id, destUser.Id
                            ).ConfigureAwait(false);

                        _logger?.Debug($"Published workbook '{sourceWorkbook.Name}'");
                    }
                    catch (Exception ex)
                    {
                        _logger?.Error($"Error publishing workbook {sourceWorkbook.Name}: {ex.Message}");
                    }
                }
            }
        }
Ejemplo n.º 6
0
        private async Task MigrateProjectDefaultPermissionsAsync(
            TableauProject sourceProject,
            TableauProject destProject,
            ResourceType resourceType
            )
        {
            _logger?.Debug($"Migrating default {resourceType.ToString()} permissions for project {sourceProject.Name}");

            var sourcePermissionService = _tableauServiceFactorySource.GetService <TableauPermissionService>();
            var destPermissionService   = _tableauServiceFactoryDest.GetService <TableauPermissionService>();
            var sourceUserService       = _tableauServiceFactorySource.GetService <TableauUserService>();
            var destUserService         = _tableauServiceFactoryDest.GetService <TableauUserService>();
            var sourceGroupService      = _tableauServiceFactorySource.GetService <TableauGroupService>();
            var destGroupService        = _tableauServiceFactoryDest.GetService <TableauGroupService>();

            var sourcePermissions = await sourcePermissionService.GetDefaultPermissionsAsync(
                sourceProject.Id, resourceType
                ).ConfigureAwait(false);

            // pre-load all destination to faciliate searching by name
            var destGroups = await destGroupService.GetGroupsAsync().ConfigureAwait(false);

            if (sourcePermissions.GranteeCapabilities == null)
            {
                _logger?.Debug("No granteee capabilities found");
                return;
            }

            foreach (var granteeCapability in sourcePermissions.GranteeCapabilities)
            {
                var destGranteeId   = "";
                var destGranteeName = "";
                if (granteeCapability.GranteeType == GranteeType.User)
                {
                    var sourceUser = await sourceUserService.GetUserAsync(
                        granteeCapability.GranteeId
                        ).ConfigureAwait(false);

                    var destUser = await destUserService.FindUserAsync(
                        sourceUser.Name, sourceUser.Domain?.Name
                        ).ConfigureAwait(false);

                    destGranteeId   = destUser.Id;
                    destGranteeName = destUser.UserPrincipalName;
                }
                else if (granteeCapability.GranteeType == GranteeType.Group)
                {
                    var sourceGroup = await sourceGroupService.GetGroupAsync(
                        granteeCapability.GranteeId
                        ).ConfigureAwait(false);

                    var destGroup = destGroups.Single(g => g.Name.EqualsIgnoreCase(sourceGroup.Name));
                    destGranteeId   = destGroup.Id;
                    destGranteeName = destGroup.Name;
                }

                foreach (var capability in granteeCapability.Capabilities.Capability)
                {
                    _logger?.Debug(
                        String.Format(
                            "Adding default permission for {0} {1}: {2} {3}",
                            granteeCapability.GranteeType.ToString(),
                            destGranteeName,
                            capability.Mode,
                            capability.Name
                            )
                        );

                    if (!_settingsMonitor.CurrentValue.DryRun)
                    {
                        await destPermissionService.AddDefaultCapabilityAsync(
                            destProject.Id,
                            resourceType,
                            granteeCapability.GranteeType,
                            destGranteeId,
                            (CapabilityName)Enum.Parse(typeof(CapabilityName), capability.Name, true),
                            (CapabilityMode)Enum.Parse(typeof(CapabilityMode), capability.Mode, true)
                            ).ConfigureAwait(false);

                        _logger?.Debug("Added default permission");
                    }
                }
            }
        }
Ejemplo n.º 7
0
        private async Task MigrateProjectGroupsAsync(TableauProject sourceProject, TableauProject destProject)
        {
            _logger?.Debug($"Migrating groups for project {sourceProject.Name}");

            var sourceGroups = await GetProjectGroups(
                sourceProject.Id, _tableauServiceFactorySource
                ).ConfigureAwait(false);

            var destUserService  = _tableauServiceFactoryDest.GetService <TableauUserService>();
            var destGroupService = _tableauServiceFactoryDest.GetService <TableauGroupService>();

            foreach (var sourceGroup in sourceGroups.Values)
            {
                var destGroup = await destGroupService.FindGroupAsync(sourceGroup.Name).ConfigureAwait(false);

                if (destGroup == null)
                {
                    _logger?.Debug($"Creating group {sourceGroup.Name} in destination site");

                    if (!_settingsMonitor.CurrentValue.DryRun)
                    {
                        destGroup = await destGroupService.CreateGroupAsync(sourceGroup.Name).ConfigureAwait(false);

                        await Task.Delay(1000).ConfigureAwait(false);
                    }
                }
                else
                {
                    _logger?.Warning($"Group {sourceGroup.Name} found in destination site ({destGroup.Id})");
                }
                // make sure dest group membership matches source
                var sourceGroupUsers = await GetGroupUsersWithDomain(
                    sourceGroup.Id, _tableauServiceFactorySource
                    ).ConfigureAwait(false);

                var destGroupUsers = await GetGroupUsersWithDomain(
                    destGroup.Id, _tableauServiceFactoryDest
                    ).ConfigureAwait(false);

                foreach (var sourceGroupUser in sourceGroupUsers.Values)
                {
                    if (
                        !destGroupUsers.Values.Any(
                            u => u.UserPrincipalName.EqualsIgnoreCase(sourceGroupUser.UserPrincipalName)
                            )
                        )
                    {
                        var destGroupUser = await destUserService.FindUserAsync(
                            sourceGroupUser.Name, sourceGroupUser.Domain?.Name
                            ).ConfigureAwait(false);

                        if (destGroupUser == null)
                        {
                            var destUser = await destUserService.FindUserAsync(
                                sourceGroupUser.Name, sourceGroupUser.Domain?.Name
                                ).ConfigureAwait(false);

                            if (destUser == null)
                            {
                                _logger?.Warning(
                                    "User {0} not found in destination, not added to group {1}",
                                    sourceGroupUser.DownLevelLogonName,
                                    destGroup.Name
                                    );
                                continue;
                            }
                        }

                        _logger?.Debug($"Adding user {destGroupUser.UserPrincipalName} to {destGroup.Name}");
                        if (!_settingsMonitor.CurrentValue.DryRun)
                        {
                            await destGroupService.AddUserToGroupAsync(
                                destGroup.Id, destGroupUser.Id
                                ).ConfigureAwait(false);

                            _logger?.Debug($"Added user {destGroupUser.UserPrincipalName} to {destGroup.Name}");
                        }
                    }
                }
            }
        }