sql >> Base de Datos >  >> RDS >> Mysql

SQL:selección de columnas según el valor de la columna de otra tabla

La respuesta depende de sus requisitos para el resultado. ¿Necesita un resultado con un conjunto coherente de columnas, independientemente de los privilegios del usuario? Si es así, puede establecer los valores no permitidos en nulo (o algún otro valor especial) usando una cláusula IF, por ejemplo,

SELECT IF (p.col1 = 0 THEN NULL ELSE d.col1) AS col1, 
       IF (p.col2 = 0 THEN NULL ELSE d.col2) AS col2,
       IF (p.col3 = 0 THEN NULL ELSE d.col3) AS col3
FROM Data d, 
     UserPrivileges p
WHERE p.userId = '#' 
  AND d.DataId = '#'

Por supuesto, el "valor especial" podría ser un problema, ya que necesita un valor que nunca aparecería en los datos. Si necesita saber la diferencia entre nulo porque el valor real es nulo y nulo porque es una columna prohibida, entonces no puede usar nulo.

Otro enfoque sería simplemente incluir el indicador de privilegio para cada columna que aparece en el resultado y dejar que su lógica comercial lo use para determinar qué valores son visibles para el usuario.

Un enfoque muy diferente tendría el conjunto de resultados para contener solo las columnas permitidas. En este caso, deberá crear su declaración sql de forma dinámica. No sé si está haciendo esto en un procedimiento almacenado o en un idioma host, pero la idea básica es algo como esto:

string sqlCmd = "SELECT " 
    + (SELECT (FIELDS_NAME_QUERY(UserID='#') 
       FROM USER_PRIVILEGES 
       WHERE userid='#') 
    + FROM data d 
execute sqlCmd

"ejecutar" significa lo que tenga disponible para ejecutar una cadena como un comando sql.

más después de la aclaración de OP:

Bien, necesita la función sql que devuelve una cadena que se parece a "colname1, colname2, ...". Lo siguiente se asemeja a cómo se vería en el servidor sql. sintaxis

create function   
FIELDS_NAME_QUERY (@userid int)  
begin  
select col1, col2, col3... INTO @col1priv, @col2priv, @col3priv FROM userPrivileges WHERE UserId = @UserId  
declare @result varhcar(60)  
set @result = ''  
if (@col1priv = 1) @result = 'col1'  
if (@col2priv = 1) @result = @result + ' ,col2'  
if (@col3priv = 1) @result = @result + ' ,col3'  
return @result  
end