Seguridad con PowerShell

Haremos uso de 3 ficheros:

  • El script principal de ejecución: PS_Lab03_Seguridad.ps1.
  • Fichero de módulo de script con diferentes funciones que usaremos en el script principal: Funciones.psm1.
  • Un fichero de configuración donde están la seguridad: Seguridad.cfg.

Nuestro fichero de configuración tendrá el siguiente contenido:

SQL_SERVER = SRVPRO
SQL_Database = BD
SQL_Table = SECURITY

La gestión de la seguridad la tenemos registrada en tablas de BD, en el script principal consultaremos las tablas y obtendremos la información de usuarios y países para este ejemplo, de tal forma que el roleado del cubo lo gestionaremos en base a esta información.

Veamos ahora paso por paso el fichero principal:

Establecemos variables de inicio (Parámetros).

$pRutaFicheroParam = "C:\Users\Administrador\Documents\PowerShell\Config\Seguridad.cfg"

Cargamos un array con los datos de los parametros del fichero pRutaFicheroParam:

$ConfigParam = @{} # Tabla de hash para guardar los pares Parametro - Valor
Get-Content $pRutaFicheroParam | foreach {
  $line = $_.split("=")
  $ConfigParam.($line[0].Trim()) = $line[1]
  }

Establecemos rutas donde leer los ficheros:

$FicheroModulo="C:\Users\Administrador\Documents\PowerShell\Funciones.psm1"

Cargamos el modulo que contiene las funciones auxiliares:

$LoadedModule = Import-Module  $FicheroModulo -PassThru -force -DisableNameChecking

Cargamos la libreria de funciones de analysis services:

ImportModulesAndAssemblies

Creamos un objeto de tipo Server:

$ASObj = New-Object Microsoft.AnalysisServices.Server

Creamos los objetos de base de datos SSAS:

    $ASObj.Connect($ConfigParam.SSAS_Server)
    $ASDataBase = $ASObj.Databases.Find($ConfigParam.SSAS_Database)
#-----------------------------------------------------------------------------
LogWriteSeparador
LogWrite -Text "Conexion establecida con el servidor de analysis services:........." , ($ConfigParam.SSAS_Server + " --> " + $ASDataBase.name), "  [Ok]" -Color White, Yellow, Green

Conectamos con el sql server donde se almacena la relación de permisos:

    $dataSource = $ConfigParam.SQL_SERVER
    $database = $ConfigParam.SQL_Database
    $connectionString = “Server=$dataSource;Database=$database;Integrated Security=True;”
    $connection = New-Object System.Data.SqlClient.SqlConnection
    $connection.ConnectionString = $connectionString
    $connection.Open()
LogWrite -Text "Conexion establecida con el servidor de SQl Server:................" , ($ConfigParam.SQL_SERVER + " --> " + $connection.DataBase.ToString()), "  [Ok]" -Color White, Yellow, Green
LogWriteSeparador

Cargamos los datos de la tabla que contiene la información de seguridad:

    $queryCountries = “SELECT [Country] FROM [dbo].[" + $ConfigParam.SQL_Table + "] Group by [Country]”
    $queryUsers = "SELECT [UserName] ,[Country] ,[MemberUN] FROM [dbo].[" + $ConfigParam.SQL_Table + "]"

    #Paises
    $commandCountries = $connection.CreateCommand()
    $commandCountries.CommandText = $queryCountries
    $result = $commandCountries.ExecuteReader()
    $tableCountries = new-object System.Data.DataTable
    $tableCountries.Load($result)

    #Usuarios
    $commandUsers = $connection.CreateCommand()
    $commandUsers.CommandText = $queryUsers
    $result = $commandUsers.ExecuteReader()
    $tableUsers = new-object System.Data.DataTable
    $tableUsers.Load($result)

LogWrite -Text "Se han leido correctamente los datos de seguridad, se comprobaran los siguientes roles: " , ($tableCountries.Rows | ForEach-Object {"[" + $_.Country + "] "}) -Color White, Yellow
LogWriteSeparador

Mediante un bucle vamos recorriendo la consulta de países y asignando el rol correspondiente a cada usuario, también se realiza un borrado previo de los roles en caso de que ya exista, esto lo hacemos para que si a un país se le ha modificado la asignación de usuarios que tiene, refrescamos el rol con la nueva información de la tabla:

Foreach ($RowCountry in $tableCountries.Rows)
{
    $rolename = $RowCountry.country
    
    #Borramos el rol si ya existe
    $roleToDelete = $ASDataBase.Roles.FindByName($roleName)
  if ($roleToDelete)
  {
    $roleToDelete.Drop(“AlterOrDeleteDependents”)
        LogWrite -Text "        Se ha borrado el rol ", ("[" + $roleName + "]"), " para su recreacion" -Color white, yellow, white 
  }
    
    #Creamos un objeto de tipo Rol con el nombre del pais al que concede permisos
    [Microsoft.AnalysisServices.Role] $roleToCreate = new-Object([Microsoft.AnalysisServices.Role])($rolename)

    #Le añadimos los usuarios pertenecientes a ese rol 
    $Users = $tableUsers | Where {$_.Country -eq $RowCountry.country}
    Foreach ( $User in $Users)
    {
        $ExecuteResult  = $roleToCreate.Members.Add($User.Username)
    }

    #Añadimos el rol a la base de datos y le damos permisos de lectura
    $ExecuteResult  = $ASDataBase.Roles.Add($roleToCreate)
    $roleToCreate.Update()

    $dbperm = $ASDataBase.DatabasePermissions.Add($roleToCreate.ID)
    $dbperm.Read = [Microsoft.AnalysisServices.ReadAccess]::Allowed
    $dbperm.Update()
    
    #Añadimos Permisos de lectura a los cubos de la base de datos
    foreach ($cube in $ASDataBase.Cubes)
    {
      $cubeperm = $cube.CubePermissions.Add($roleToCreate.ID)
      $cubePerm.Read = [Microsoft.AnalysisServices.ReadAccess]::Allowed
      $cubeperm.Update()
    }

    #Localizamos la dimension geografia por la que estableceremos los permisos
    $dim = $ASDataBase.Dimensions.FindByName(“Geography”)
    
    #Añadimos permisos en la dimension 
    $ExecuteResult  = $dim.DimensionPermissions.Add($roleToCreate.ID)
    $dimperm = $dim.DimensionPermissions.add($roleToCreate.ID)
    $dimperm.Read = [Microsoft.AnalysisServices.ReadAccess]::Allowed

    #Localizamos el atributo pais por el que estableceremos los permisos
    $att = $dim.Attributes.FindByName(“Country”)

    #Añadimos permisos al atributo
    $attPerm = $dimPerm.AttributePermissions.Add($att.ID)
    $attPerm.AllowedSet = “{[Geography].[Country].&[” + $RowCountry.country + “]}”

    $dimPerm.Update() 
    LogWrite -Text "        Se han ha creado el Rol: " ,("[" + $roleName + "]") , " con los siguientes usuarios asociados: " ,  ($Users | ForEach-Object {"[" + $_.UserName + "] "}) -Color White, Yellow, white, Yellow
}
LogWriteSeparador

A modo de resumen de este hilo de código, veamos una diagrama de flujo de los pasos seguidos, por supuesto lo podemos complicar tanto como deseemos:

Automatizar la gestión de SSAS con PowerShell pt. 3

Con lo visto hasta aquí tendríamos lista la parte de seguridad y damos por cerrado el post con la parte de automatización de la seguridad de SSAS.

0 Shares:
Deja una respuesta

Tu dirección de correo electrónico no será publicada. Los campos obligatorios están marcados con *

You May Also Like
Leer más

Seguimiento de métricas en tiempo real con PowerBI y PowerShell

En este artículo vamos a ver como enviar un stream de datos a PowerBi mediante un pequeño script de powershell para hacer un seguimiento en tiempo real de unos sensores (por ejemplo), también podríamos usar el script para enviar cualquier tipo de información de monitorización, como datos de un log, estadísticas de uso de una base de datos o cualquier otra métrica que queramos monitorizar en tiempo real.