다음을 통해 공유


Databricks 앱에서 권한 부여 구성

Databricks Apps는 Azure Databricks에서 보안 애플리케이션 개발을 지원합니다. 앱은 작업 영역 내의 데이터 및 서비스에 액세스할 때 데이터 액세스 제어를 적용하고 사용자 권한을 존중하는 인증 및 권한 부여 메커니즘을 사용해야 합니다. Databricks Apps 권한 부여 모델은 OAuth 2.0을 기반으로 하며 앱에 할당된 사용 권한을 액세스하는 사용자의 권한과 결합합니다.

이 프레임워크를 지원하기 위해 Databricks 앱은 두 가지 보완 ID 모델을 사용합니다.

  • 앱 권한 부여 는 일관된 권한 집합을 사용하여 앱 자체 ID를 제공합니다.
  • 사용자 권한 부여 를 통해 앱은 상호 작용하는 사용자의 ID 및 권한을 사용할 수 있습니다.

앱 권한 부여

각 Azure Databricks 앱에는 Azure Databricks 리소스에 액세스할 때 ID 역할을 하는 전용 서비스 주체 가 있습니다. 이 서비스 주체는 앱 인스턴스에 고유하며 앱 간에 다시 사용할 수 없습니다. 앱에 할당된 서비스 주체를 변경하거나 앱을 만드는 동안 기존 서비스 주체를 지정할 수 없습니다. Azure Databricks는 이 ID를 사용하여 모든 사용자와 독립적으로 앱의 권한을 평가하므로 앱이 사용자 상호 작용 컨텍스트 외부에서도 명시적으로 부여된 리소스에만 액세스할 수 있습니다.

이러한 분리는 보안 경계를 적용하는 데 도움이 되며, 이를 통해 앱 활동을 감사할 수 있으며 백그라운드 처리 또는 자동화된 작업과 같은 시나리오를 지원합니다.

서비스 주체는 고유 ID로 표시됩니다. 앱의 권한 부여 탭에서 복사합니다.

Databricks 앱에서 서비스 주체 보기

앱을 만들 때 Azure Databricks는 앱에 대한 전용 서비스 주체를 자동으로 프로비전합니다. 서비스 주체는 앱의 모든 배포에서 동일하게 유지됩니다. 앱을 삭제하면 Azure Databricks가 서비스 주체를 삭제합니다.

개별 사용자의 컨텍스트를 요구하지 않고 앱이 자체적으로 수행하는 작업에 서비스 주체를 사용합니다. 일반적인 사용 사례는 다음과 같습니다.

  • 백그라운드 작업 실행
  • 공유 구성 또는 메타데이터 읽기 또는 쓰기
  • 로깅 활동 또는 사용 메트릭
  • 보안 엔드포인트를 통해 외부 서비스 호출

앱에서 시작한 모든 작업은 서비스 주체의 권한을 사용합니다. 표준 권한 할당을 사용하여 서비스 주체에게 특정 리소스에 대한 액세스 권한을 부여합니다. 그러나 사용자 수준 액세스 제어는 지원하지 않습니다. 앱과 상호 작용하는 모든 사용자는 서비스 주체에 대해 정의된 동일한 권한을 공유하므로 앱이 개별 사용자 ID에 따라 세분화된 정책을 적용할 수 없습니다.

다음 예제에서는 앱이 서비스 주체를 사용하여 Unity 카탈로그의 데이터를 쿼리하는 방법을 보여줍니다.

서비스 주체가 앱에서 인증하는 방법 보기

이 경우 서비스 주체는 SQL 웨어하우스와 쿼리하는 Unity 카탈로그 테이블에 모두 명시적으로 액세스해야 합니다.

이 모델은 앱의 모든 사용자가 동일한 데이터를 보도록 하거나 앱이 사용자별 액세스 제어에 연결되지 않은 공유 작업을 수행할 때 잘 작동합니다.

앱 권한 부여 자격 증명 검색

앱 권한 부여를 위해 Azure Databricks는 자동으로 서비스 주체 자격 증명을 앱의 환경에 삽입합니다. 다음 환경 변수에는 필요한 OAuth 클라이언트 값이 있습니다.

Variable Description
DATABRICKS_CLIENT_ID 서비스 주체 OAuth 클라이언트 ID
DATABRICKS_CLIENT_SECRET 서비스 주체 OAuth 클라이언트 암호

Azure Databricks는 앱 런타임에서 환경 변수를 자동으로 설정합니다. 앱은 자체 인증 시 이러한 변수를 사용합니다.

Python

import os

client_id = os.getenv('DATABRICKS_CLIENT_ID')
client_secret = os.getenv('DATABRICKS_CLIENT_SECRET')

JavaScript

const clientId = process.env.DATABRICKS_CLIENT_ID;
const clientSecret = process.env.DATABRICKS_CLIENT_SECRET;

Note

Azure Databricks SDK를 사용하는 경우 일반적으로 이러한 환경 변수에 수동으로 액세스할 필요가 없습니다. SDK는 통합 인증을 따르고 환경에서 자격 증명을 자동으로 검색합니다.

예: 앱 권한 부여를 사용하여 쿼리

Python

이 예제에서는 환경 변수에서 서비스 주체 자격 증명을 가져오고 OAuth 권한 부여를 수행하는 SDK Config 개체를 사용합니다.

from databricks import sql
from databricks.sdk.core import Config

cfg = Config()

conn = sql.connect(
    server_hostname=cfg.host,
    http_path="<your-warehouse-http-path>",
    credentials_provider=lambda: cfg.authenticate,
)

query = "SELECT * FROM main.sandbox.sales_customers LIMIT 1000"

with conn.cursor() as cursor:
    cursor.execute(query)
    df = cursor.fetchall_arrow().to_pandas()
    print(df.head())

conn.close()
JavaScript

이 예제에서는 환경 변수를 사용하여 OAuth를 사용하여 서비스 주체로 인증하고 databricks SQL Driver for Node.js사용하여 쿼리를 실행합니다.

import { DBSQLClient } from '@databricks/sql';

const client = new DBSQLClient();

const connection = await client.connect({
  authType: 'databricks-oauth',
  host: process.env.DATABRICKS_SERVER_HOSTNAME,
  path: process.env.DATABRICKS_HTTP_PATH,
  oauthClientId: process.env.DATABRICKS_CLIENT_ID,
  oauthClientSecret: process.env.DATABRICKS_CLIENT_SECRET,
});

const query = 'SELECT * FROM main.sandbox.sales_customers LIMIT 1000';
const cursor = await connection.cursor(query);

const rows = [];
for await (const row of cursor) {
  rows.push(row);
}

console.log(rows.slice(0, 5)); // Like df.head()

await connection.close();

사용자 권한 부여

Important

사용자 권한 부여는 공개 미리 보기로 제공됩니다.

사용자 권한 부여라고도 하는 사용자 권한 부여를 사용하면 Databricks Apps 앱이 앱 사용자의 ID로 작동할 수 있습니다. Azure Databricks는 토큰을 사용하여 사용자를 대신하여 리소스에 액세스하는 앱에 사용자의 액세스 토큰을 전달합니다. Azure Databricks는 사용자의 기존 Unity 카탈로그 정책에 따라 모든 권한을 적용합니다.

사용자를 대신하여 작동하는 앱의 보안 위험을 관리하기 위해 Azure Databricks는 범위를 사용하여 앱이 사용자 권한 부여를 통해 수행할 수 있는 작업을 제한합니다.

앱이 개별 사용자 권한을 준수해야 하는 경우 사용자 권한 부여를 적용합니다. 일반적인 사용 사례는 다음과 같습니다.

  • 테이블 또는 볼륨 쿼리
  • SQL 웨어하우스 또는 컴퓨팅에 액세스
  • 사용자 작업에 연결된 작업 또는 워크플로 실행

모든 작업은 사용자의 기존 Unity 카탈로그 권한을 사용합니다.

사용자가 앱에서 인증하는 방법 보기

사용자 권한 부여를 사용하면 행 수준 필터 및 열 마스크와 같은 Unity 카탈로그 기능을 앱 활동에 적용하여 세분화된 액세스 제어를 수행할 수 있습니다. 이 방법은 액세스 제어를 작업 영역 거버넌스와 일관되게 유지하고 앱에 대한 권한 논리를 하드 코딩하지 않도록 방지합니다.

정밀한 권한 설정과 사용자 권한 부여

앱에 사용자 권한 부여를 추가하면 다음을 비롯한 사용자의 기존 Unity 카탈로그 권한이 적용됩니다.

  • 표시되는 행을 제한하는 행 수준 필터
  • 중요한 데이터를 수정하거나 변환하는 열 마스크

Azure Databricks는 사용자 ID를 사용하여 사용자 권한 부여 요청을 평가하므로 앱이 데이터에 액세스할 때 이러한 정책이 자동으로 적용됩니다. 예를 들어 테이블에 지역별 가시성을 제한하는 행 필터가 포함된 경우 앱은 사용자가 쿼리할 수 있는 행만 반환합니다. 앱에는 추가 필터링 논리가 필요하지 않습니다.

이 방법은 애플리케이션 코드에서 액세스 제어 논리가 중복되는 것을 방지하고 작업 영역 수준 거버넌스와의 일관성을 보장합니다. 관리자가 Unity 카탈로그 정책을 업데이트하면 앱은 이러한 변경 내용을 자동으로 적용합니다.

범위 기반 보안 및 권한 에스컬레이션

사용자 권한 부여를 사용하는 앱은 사용자를 대신하여 앱이 수행할 수 있는 작업을 제한하기 위해 특정 권한 부여 범위를 선언해야 합니다. 범위는 다음과 같은 특정 API 또는 리소스 유형에 대한 액세스를 제한합니다.

  • sql SQL 웨어하우스 쿼리용
  • dashboards.genie 지니 공간 관리
  • files.files 파일 및 디렉터리 관리

범위를 선택하지 않으면 Azure Databricks는 앱에서 기본 사용자 ID 정보를 검색할 수 있는 기본 집합을 할당합니다.

  • iam.access-control:read
  • iam.current-user:read

이러한 기본값은 사용자 권한 부여 기능을 지원하는 데 필요하지만 데이터 또는 컴퓨팅 리소스에 대한 액세스를 허용하지 않습니다. 앱을 만들거나 편집할 때 범위를 더 추가합니다.

범위는 최소 권한 원칙을 적용합니다. 필요한 범위만 요청하도록 앱을 구성해야 합니다. Azure Databricks는 사용자에게 권한이 있더라도 승인된 범위 외부의 모든 기능에 대한 액세스를 차단합니다. 예를 들어 앱이 sql 범위만 요청한다면, 사용자가 앱 외부에서 엔드포인트를 제공하는 모델에 액세스할 수 있더라도 앱 내에서는 액세스할 수 없습니다.

사용자가 앱에 처음 액세스하면 Azure Databricks는 요청된 범위 내에서 작동하도록 앱에 명시적으로 권한을 부여하라는 메시지를 표시합니다. 관리자는 필요에 따라 사용자 대신 동의를 부여하여 조직 정책에 맞게 액세스를 정렬할 수 있습니다.

앱에 범위 추가

Important

사용자 권한 부여는 공개 미리 보기로 제공됩니다. 앱에 범위를 추가하려면 먼저 작업 영역 관리자가 사용하도록 설정해야 합니다.

사용자 권한 부여를 사용하도록 설정한 후에는 기존 앱을 다시 시작해야 범위를 추가할 수 있습니다. 사용자 권한 부여를 사용하지 않도록 설정하는 경우 현재 사용자의 액세스 토큰 사용을 중지하여 리소스에 액세스하려면 기존 앱을 다시 시작해야 합니다.

Azure Databricks UI에서 앱을 만들거나 편집할 때 사용자 권한 부여를 구성합니다.

구성 단계에서 +범위 추가를 클릭하고 앱이 사용자를 대신하여 액세스할 수 있는 Azure Databricks API 또는 리소스를 정의하는 범위를 선택합니다. Azure Databricks는 런타임에 이러한 범위를 적용하고 액세스 권한을 부여하기 전에 사용자 또는 관리자 동의가 필요합니다.

Databricks 앱에 사용자 권한 부여 범위 추가

전체 예제는 GitHub의 Databricks Apps 권한 부여 데모를 참조하세요. 예제 앱은 앱 및 사용자 권한 부여 모델을 모두 사용하는 방법을 보여 줍니다. 여기에는 사용자 권한 부여가 포함된 설정 지침 및 예제 쿼리가 포함되어 있습니다.

사용자 권한 부여 자격 증명 검색

사용자 권한 부여를 위해 Azure Databricks는 사용자의 ID 및 액세스 토큰을 HTTP 헤더의 앱에 전달합니다. 앱은 사용자를 대신하여 작동하려면 이러한 헤더를 추출해야 합니다.

이러한 헤더를 검색하는 방법은 사용하는 프레임워크에 따라 달라집니다.

Streamlit

import streamlit as st
user_access_token = st.context.headers.get('x-forwarded-access-token')

Gradio

import gradio as gr

def query_fn(message, history, request: gr.Request):
    access_token = request.headers.get("x-forwarded-access-token")
    ...

매개 변수로 선언하는 경우 Gradio는 요청 개체를 앱의 함수에 자동으로 삽입합니다. 요청을 수동으로 생성하거나 가져올 필요가 없습니다.

대시 및 플라스크

from flask import request

headers = request.headers
user_token = headers.get('x-forwarded-access-token')

Shiny

user_token = session.http_conn.headers.get('x-forwarded-access-token')

Express

import express from 'express';

const userAccessToken = req.header('x-forwarded-access-token');

예: 사용자 권한 부여를 사용하여 쿼리

이 경우 앱은 사용자의 액세스 토큰을 커넥터에 직접 전달하고 Azure Databricks는 사용자의 권한을 쿼리에 적용합니다.

Python
from databricks import sql
from databricks.sdk.core import Config
from flask import request

cfg = Config()
user_token = request.headers.get("x-forwarded-access-token")

conn = sql.connect(
    server_hostname=cfg.host,
    http_path="<your-warehouse-http-path>",
    access_token=user_token
)

query = "SELECT * FROM main.sandbox.sales_customers LIMIT 1000"

with conn.cursor() as cursor:
    cursor.execute(query)
    df = cursor.fetchall_arrow().to_pandas()
    print(df.head())

conn.close()
JavaScript
import { DBSQLClient } from '@databricks/sql';
import express from 'express';

const app = express();

app.get('/', async (req, res) => {
  const userToken = req.header('x-forwarded-access-token');

  const client = new DBSQLClient();
  const connection = await client.connect({
    authType: 'access-token',
    host: process.env.DATABRICKS_SERVER_HOSTNAME,
    path: process.env.DATABRICKS_HTTP_PATH,
    token: userToken,
  });

  const query = 'SELECT * FROM main.sandbox.sales_customers LIMIT 1000';
  const cursor = await connection.cursor(query);

  const rows = [];
  for await (const row of cursor) {
    rows.push(row);
  }

  console.log(rows.slice(0, 5));
  await connection.close();

  res.send('Query complete');
});

app.listen(3000);

사용자 권한 부여 모범 사례

사용자를 대신하여 작업을 수행하는 앱을 빌드하는 경우 다음 모범 사례를 따라 안전하고 감사 가능한 액세스를 보장합니다.

  • 앱 소유자 또는 소수의 신뢰할 수 있는 사용자만 액세스할 수 있는 폴더에 앱 코드를 저장합니다.
  • 앱 유지 관리 및 검토를 담당하는 신뢰할 수 있는 선임 개발자에게만 권한을 부여 CAN MANAGE 합니다. 앱을 실행하도록 승인된 특정 사용자 또는 그룹에만 사용 권한을 부여 CAN USE 합니다.
  • 토큰이 파일에 출력, 기록되거나 저장되지 않았는지 확인합니다. 이는 모든 로깅 문, 디버깅 도구 및 오류 처리기에 적용됩니다. 예를 들어 print(f"User token: {token}") 대신 headers = {"Authorization": f"Bearer {token}"}를 사용하십시오.
  • 해당 기능에 필요한 최소 권한 부여 범위만 요청하도록 각 앱을 구성합니다.
  • 코드를 검토하는 동안 범위 및 권한 설정이 보안 요구 사항에 부합하고 불필요한 액세스 권한을 부여하지 않는지 확인합니다.
  • 프로덕션 환경에 배포하기 전에 모든 앱 코드에 대한 피어 검토를 적용합니다.
  • 앱 코드가 사용자 ID, 작업 유형, 대상 리소스 및 상태를 포함하여 사용자를 대신하여 수행되는 모든 작업에 대해 구조화된 감사 로그를 기록해야 합니다.

인증 방법

Databricks 앱에 대한 토큰을 가져오기 위해 사용자와 서비스 주체는 모두 표준 OAuth 2.0 흐름을 사용하여 인증합니다. 이 메서드는 호출자가 사용자인지 자동화된 워크로드인지에 따라 달라집니다.

작업 영역 로그인의 경우(사용자만 해당):

  • SSO(Single Sign-On): 사용자는 SSO(Single Sign-On)가 구성된 경우 ID 공급자를 통해 인증합니다.
  • OTP(일회성 암호): SSO가 구성되지 않은 경우 사용자는 임시 암호를 받습니다.

OAuth 플로우(앱과 워크로드의 경우):

  • U2M(사용자-컴퓨터) OAuth: 사용자가 인증하고, 결과 토큰은 앱이 사용자를 대신하여 작동할 수 있도록 사용자 권한 부여를 사용하도록 설정합니다.
  • M2M(컴퓨터-컴퓨터) OAuth: 서비스 주체는 클라이언트 자격 증명 또는 페더레이션을 사용하여 인증합니다. 이러한 토큰은 앱이 사용자 대신 자체 역할을 하는 앱 권한 부여를 뒷받침합니다.

토큰 인증을 사용하여 Databricks 앱을 호출하는 지침은 토큰 인증 을 사용하여 API Databricks 앱에 연결을 참조하세요.

모델 비교 및 결합

Databricks 앱은 앱과 사용자 권한 부여를 독립적으로 또는 함께 사용할 수 있습니다. 이러한 모델은 다양한 용도로 사용되며 병렬로 작동하도록 설계되었습니다.

인증 모델 사용 시기 사용 사례 예
앱 권한 부여 앱이 사용자의 ID에 의존하지 않는 작업을 수행하는 경우 로그 작성, 공유 구성 액세스, 외부 서비스 호출
사용자 권한 부여 앱이 현재 사용자의 컨텍스트에서 리소스에 액세스해야 하는 경우 Unity 카탈로그 데이터 쿼리, 컴퓨팅 시작, 행 수준 권한 적용
둘다 앱이 공유 작업과 사용자별 작업을 모두 수행하는 경우 앱 ID를 사용하여 메트릭 로깅, 사용자 ID를 사용하여 필터링된 데이터 쿼리