Skip to content

SSO 및 OAuth 인증

Potato에서 Google OAuth, GitHub OAuth, 일반 OIDC를 설정합니다. 이메일 도메인이나 GitHub 조직으로 접근을 제한하고, 비밀번호를 사용한 혼합 모드 로그인을 활성화할 수 있습니다.

v2.3.0의 새로운 기능

기본적으로 Potato는 어노테이터가 아무 사용자 이름이나 입력해 로그인하는 간단한 사용자 이름 기반 로그인을 사용합니다. 이는 로컬 개발과 소규모 프로젝트에는 편리하지만, 운영 환경 배포에서는 무단 접근을 막고 어노테이터의 신원을 확인하며 기관 요구 사항을 준수하기 위해 제대로 된 인증이 필요합니다.

Potato 2.3은 세 가지 인증 방식을 지원합니다:

  1. Google OAuth -- Google 계정으로 로그인하며, 도메인 제한을 선택적으로 적용할 수 있습니다
  2. GitHub OAuth -- GitHub 계정으로 로그인하며, 조직 제한을 선택적으로 적용할 수 있습니다
  3. 일반 OIDC -- 모든 OpenID Connect 공급자(Okta, Azure AD, Auth0, Keycloak 등)에 연결합니다

모든 방식은 Potato의 기존 사용자 이름 로그인과 결합하여 혼합 모드로 구성할 수 있습니다.

Google OAuth

사전 준비

  1. Google Cloud Console에서 프로젝트를 생성합니다
  2. "Google Identity" API를 활성화합니다
  3. OAuth 2.0 자격 증명(웹 애플리케이션 유형)을 생성합니다
  4. "승인된 리디렉션 URI"에 Potato 서버 URL을 추가합니다: https://your-server.com/auth/google/callback

설정

yaml
authentication:
  method: google_oauth
 
  google_oauth:
    client_id: ${GOOGLE_CLIENT_ID}
    client_secret: ${GOOGLE_CLIENT_SECRET}
    redirect_uri: "https://your-server.com/auth/google/callback"
 
    # Optional: restrict to specific domain(s)
    allowed_domains:
      - "umich.edu"
      - "research-lab.org"
 
    # Optional: auto-register new users on first login
    auto_register: true
 
    # Optional: map Google profile fields to Potato user fields
    field_mapping:
      username: email            # use email as Potato username
      display_name: name         # show Google display name

도메인 제한

allowed_domains가 설정되면 해당 도메인의 이메일 주소를 가진 사용자만 로그인할 수 있습니다. 그 외 사용자는 오류 메시지를 보게 됩니다:

yaml
authentication:
  method: google_oauth
  google_oauth:
    client_id: ${GOOGLE_CLIENT_ID}
    client_secret: ${GOOGLE_CLIENT_SECRET}
    allowed_domains:
      - "umich.edu"
    domain_error_message: "This annotation task is restricted to University of Michigan accounts."

GitHub OAuth

사전 준비

  1. GitHub Settings > Developer settings > OAuth Apps > New OAuth App으로 이동합니다
  2. "Authorization callback URL"을 https://your-server.com/auth/github/callback로 설정합니다
  3. Client ID를 기록하고 Client Secret을 생성합니다

설정

yaml
authentication:
  method: github_oauth
 
  github_oauth:
    client_id: ${GITHUB_CLIENT_ID}
    client_secret: ${GITHUB_CLIENT_SECRET}
    redirect_uri: "https://your-server.com/auth/github/callback"
 
    # Optional: restrict to members of specific GitHub organizations
    allowed_organizations:
      - "my-research-lab"
      - "university-nlp-group"
 
    # Optional: restrict to specific teams within an organization
    allowed_teams:
      - "my-research-lab/annotators"
 
    # Scopes to request
    scopes:
      - "read:user"
      - "read:org"             # needed for organization restriction
 
    auto_register: true
 
    field_mapping:
      username: login            # GitHub username
      display_name: name

조직 제한

GitHub OAuth는 특정 조직의 구성원으로 접근을 제한할 수 있습니다. 이를 위해서는 read:org 범위가 필요합니다:

yaml
authentication:
  method: github_oauth
  github_oauth:
    client_id: ${GITHUB_CLIENT_ID}
    client_secret: ${GITHUB_CLIENT_SECRET}
    allowed_organizations:
      - "my-research-lab"
    scopes:
      - "read:user"
      - "read:org"
    org_error_message: "You must be a member of the my-research-lab GitHub organization."

일반 OIDC

엔터프라이즈 SSO 공급자(Okta, Azure AD, Auth0, Keycloak 등)의 경우 일반 OpenID Connect 통합을 사용합니다.

설정

yaml
authentication:
  method: oidc
 
  oidc:
    # Discovery URL (provider's .well-known endpoint)
    discovery_url: "https://accounts.example.com/.well-known/openid-configuration"
 
    # Or specify endpoints manually
    # authorization_endpoint: "https://accounts.example.com/authorize"
    # token_endpoint: "https://accounts.example.com/token"
    # userinfo_endpoint: "https://accounts.example.com/userinfo"
    # jwks_uri: "https://accounts.example.com/.well-known/jwks.json"
 
    client_id: ${OIDC_CLIENT_ID}
    client_secret: ${OIDC_CLIENT_SECRET}
    redirect_uri: "https://your-server.com/auth/oidc/callback"
 
    scopes:
      - "openid"
      - "profile"
      - "email"
 
    auto_register: true
 
    field_mapping:
      username: preferred_username
      display_name: name
      email: email

Azure AD 예시

yaml
authentication:
  method: oidc
 
  oidc:
    discovery_url: "https://login.microsoftonline.com/${AZURE_TENANT_ID}/v2.0/.well-known/openid-configuration"
    client_id: ${AZURE_CLIENT_ID}
    client_secret: ${AZURE_CLIENT_SECRET}
    redirect_uri: "https://your-server.com/auth/oidc/callback"
    scopes:
      - "openid"
      - "profile"
      - "email"
    auto_register: true
    field_mapping:
      username: preferred_username
      display_name: name

Okta 예시

yaml
authentication:
  method: oidc
 
  oidc:
    discovery_url: "https://your-org.okta.com/.well-known/openid-configuration"
    client_id: ${OKTA_CLIENT_ID}
    client_secret: ${OKTA_CLIENT_SECRET}
    redirect_uri: "https://your-server.com/auth/oidc/callback"
    scopes:
      - "openid"
      - "profile"
      - "email"
      - "groups"               # request group membership
    auto_register: true
 
    # Restrict to specific groups
    allowed_groups:
      - "annotation-team"
 
    field_mapping:
      username: preferred_username
      display_name: name
      groups: groups

Keycloak 예시

yaml
authentication:
  method: oidc
 
  oidc:
    discovery_url: "https://keycloak.example.com/realms/annotation/.well-known/openid-configuration"
    client_id: ${KEYCLOAK_CLIENT_ID}
    client_secret: ${KEYCLOAK_CLIENT_SECRET}
    redirect_uri: "https://your-server.com/auth/oidc/callback"
    scopes:
      - "openid"
      - "profile"
      - "email"
    auto_register: true
    field_mapping:
      username: preferred_username
      display_name: name

도메인 제한

모든 OAuth 방식은 이메일 주소를 기준으로 한 도메인 제한을 지원합니다. 특정 기관의 모든 계정을 허용하려는 경우에 유용합니다:

yaml
authentication:
  method: google_oauth          # or github_oauth, oidc
 
  domain_restriction:
    enabled: true
    allowed_domains:
      - "umich.edu"
      - "stanford.edu"
    error_message: "Access is restricted to university accounts."

email 클레임을 포함하는 OIDC 공급자의 경우 도메인 제한이 자동으로 작동합니다. 이메일을 포함하지 않는 공급자의 경우 email 범위를 명시적으로 요청해야 할 수 있습니다.

자동 등록

기본적으로 사용자는 어노테이션을 하기 전에 Potato에 미리 등록되어 있어야 합니다. auto_register: true를 사용하면 인증에 성공한 모든 사용자가 첫 로그인 시 Potato에 자동으로 생성됩니다.

yaml
authentication:
  auto_register: true
  auto_register_role: annotator   # annotator or admin

특정 사용자를 사전 승인하면서 나머지를 차단하려면:

yaml
authentication:
  auto_register: false
  allowed_users:
    - "researcher@umich.edu"
    - "student1@umich.edu"
    - "student2@umich.edu"
  user_not_found_message: "Your account has not been approved. Contact the project administrator."

혼합 모드

여러 인증 방식을 동시에 활성화할 수 있습니다. 로그인 페이지에는 활성화된 각 방식의 버튼과 선택적인 사용자 이름 입력란이 표시됩니다.

yaml
authentication:
  methods:
    - google_oauth
    - github_oauth
    - username                   # keep simple username login as fallback
 
  google_oauth:
    client_id: ${GOOGLE_CLIENT_ID}
    client_secret: ${GOOGLE_CLIENT_SECRET}
    redirect_uri: "https://your-server.com/auth/google/callback"
 
  github_oauth:
    client_id: ${GITHUB_CLIENT_ID}
    client_secret: ${GITHUB_CLIENT_SECRET}
    redirect_uri: "https://your-server.com/auth/github/callback"
 
  # Username login settings
  username:
    enabled: true
    require_password: true       # require a password for username login
    password_file: "auth/passwords.yaml"

혼합 모드는 마이그레이션 중에 유용합니다. 사용자 이름 로그인과 함께 OAuth를 활성화한 다음, 모든 어노테이터가 OAuth 계정을 연결한 후에 사용자 이름 로그인을 비활성화하면 됩니다.

세션 관리

인증된 사용자의 세션 동작을 설정합니다:

yaml
authentication:
  session:
    lifetime_hours: 24           # session duration
    refresh: true                # refresh session on activity
    cookie_secure: true          # require HTTPS for cookies
    cookie_samesite: "Lax"       # SameSite cookie attribute

관리자 인증

관리자 계정은 동일한 OAuth 흐름을 사용하거나 별도의 인증 방식을 사용할 수 있습니다:

yaml
authentication:
  method: google_oauth
  google_oauth:
    client_id: ${GOOGLE_CLIENT_ID}
    client_secret: ${GOOGLE_CLIENT_SECRET}
 
  admin:
    # Admins must match these emails
    admin_emails:
      - "pi@umich.edu"
      - "lead-ra@umich.edu"
 
    # Or use a separate API key for admin access
    api_key: ${ADMIN_API_KEY}

HTTPS 요구 사항

OAuth 공급자는 운영 환경에서 리디렉션 URI에 HTTPS를 요구합니다. 로컬 개발에서는 localhost로 HTTP를 사용할 수 있습니다:

yaml
# Development (HTTP allowed)
authentication:
  google_oauth:
    redirect_uri: "http://localhost:8000/auth/google/callback"
 
# Production (HTTPS required)
authentication:
  google_oauth:
    redirect_uri: "https://annotation.example.com/auth/google/callback"

리버스 프록시(nginx, Caddy) 뒤에서 운영 환경에 배포하는 경우, 프록시가 올바른 X-Forwarded-Proto 헤더를 전달하는지 확인하십시오:

nginx
# nginx example
location / {
    proxy_pass http://localhost:8000;
    proxy_set_header X-Forwarded-Proto $scheme;
    proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
    proxy_set_header Host $host;
}

전체 예시

Google OAuth, 도메인 제한, 관리자 API 키를 사용한 완전한 운영 환경 인증 설정:

yaml
task_name: "Annotation Project"
task_dir: "."
 
authentication:
  method: google_oauth
 
  google_oauth:
    client_id: ${GOOGLE_CLIENT_ID}
    client_secret: ${GOOGLE_CLIENT_SECRET}
    redirect_uri: "https://annotation.umich.edu/auth/google/callback"
    allowed_domains:
      - "umich.edu"
    auto_register: true
    field_mapping:
      username: email
      display_name: name
 
  session:
    lifetime_hours: 48
    cookie_secure: true
 
  admin:
    admin_emails:
      - "pi@umich.edu"
    api_key: ${ADMIN_API_KEY}
 
data_files:
  - "data/instances.jsonl"
 
annotation_schemes:
  - annotation_type: radio
    name: sentiment
    labels: [Positive, Neutral, Negative]
 
output_annotation_dir: "output/"
output_annotation_format: "jsonl"

더 읽어보기

구현 세부 정보는 원본 문서를 참고하십시오.