OIDC 싱글 사인온 커스텀 도메인 교체 절차 (배포 플랜 URL 주소 교체 방안, 더 이상 권장하지 않음)¶
소개¶
Guance 배포 플랜은 OIDC 프로토콜 기반의 커스텀 도메인 주소 교체를 통한 싱글 사인온을 지원하며, 워크스페이스 커스텀 도메인 방식으로 OIDC 로그인을 연동할 수 있습니다.
!!! warning
이 방안은 새로운 연동 시나리오에는 더 이상 권장되지 않습니다.
현재는 [커스텀 OIDC 연동 (배포 플랜)](./oidc-custom-access.md)을 사용하여 Func에서 로그인 주소, `redirect_uri`, 콜백 주소 및 사용자 정보 포맷팅 로직을 통합하는 방식을 권장합니다. 이 방식은 단일 IDP, 다중 IDP 및 다양한 비표준 OIDC 호환 시나리오에 더 적합합니다.
본 문서는 기존 환경 유지보수 또는 레거시 구성 호환을 위해 보관됩니다.
개념¶
| 용어 | 설명 |
|---|---|
| loginUrl | Guance OIDC 로그인 진입 주소입니다. 일반적인 형식: http://도메인/oidc/login 또는 주소에 쿼리 매개변수가 포함된 형태입니다. |
| authUrl | 계정 인증 주소입니다. |
| callbackURL | 계정 인증 성공 후 Guance으로 콜백되는 주소입니다. 일반적인 형식: http://도메인/oidc/callback |
| redirect_uri | authUrl에 포함된 콜백 주소 매개변수명입니다. |
절차¶
1. OIDC 기본 구성¶
1) Guance Launcher 네임스페이스: forethought-core > core에서 OIDCClientSet 구성 항목에 하위 구성 항목 requestSet을 추가합니다.
# OIDC 클라이언트 구성 (해당 구성에 wellKnowURL이 설정된 경우 KeyCloakPassSet 구성 항목이 자동으로 비활성화됨)
OIDCClientSet:
# OIDC Endpoints 구성 주소, 즉 전체 `https://xxx.xxx.com/xx/.well-known/openid-configuration` 주소입니다.
wellKnowURL: https://xxx.xxx.com/xx/.well-known/openid-configuration
# 인증 서비스에서 제공하는 클라이언트 ID
clientId: xxx
# 클라이언트 시크릿 키
clientSecret: xxxx
# 다음은 사용자 정의 구성 부분입니다 (oidc 프로세스의 다양한 주소를 사용자 정의하는 데 사용). 바로 복사 가능합니다.
requestSet:
login:
redirectUriFormatRequest:
# 스위치 활성화
isOpen: true
url: "func의 함수 요청 주소 (아래 redirect_uri_format 함수 외부 링크에 해당)"
urlFormatRequest:
# 스위치, 기본값 비활성화
isOpen: true
url: "func의 함수 요청 주소 (아래 login_auth_url_format 함수 외부 링크에 해당)"
callback:
redirectUriFormatRequest:
# 스위치, 기본값 비활성화
isOpen: true
description: "login 하위의 redirectUriFormatRequest 구성 설명과 동일"
url: "func의 함수 요청 주소 (아래 redirect_uri_format 함수 외부 링크에 해당)"
urlFormatRequest:
# 스위치, 기본값 비활성화
isOpen: true
url: "func의 함수 요청 주소 (아래 callback_url_format 함수 외부 링크에 해당)"
추가 설명:
- 신규 연동 시나리오의 경우 커스텀 OIDC 연동 (배포 플랜)을 사용하여 주소 포맷팅 로직을 Func에서 처리하는 것을 권장합니다.
OIDCClientSet.clientSecret은 구성에 직접 입력하는 것 외에도 Func 측의 비밀번호 유형 환경 변수를 통해 안전하게 관리할 수 있으므로, 스크립트나 예제 코드에 민감한 정보를 평문으로 작성하지 않는 것이 좋습니다.
1. redirect_uri_format 함수 설명¶
OIDC 프로세스에서 비표준적인 redirect_uri 변경이 발생하는 경우, 외부 함수에서 포맷팅을 수행해야 합니다. login 및 callback 요청 시 oidc client의 redirect_uri가 일관되도록 보장해야 합니다. 그렇지 않으면 클라이언트의 state 및 code 검증이 실패합니다.
python
# 요청 메서드: post
# 요청 본문 내용:
{
"type": "login", # 변경이 login인지 callback 프로세스인지 나타냄
"redirect_uri": "원래 redirect_uri 주소",
"args": {
# oidc/login 요청에서 수신한 쿼리 매개변수
},
"headers": {
# oidc/login 요청에서 수신한 요청 헤더 데이터
}
}
# 응답 내용:
{
"redirect_uri": "변경된 redirect_uri",
}
2. login_auth_url_format 함수 설명¶
oidc/login의 리디렉션 주소를 외부 함수로 전달하여 재구성한 후 리디렉션을 수행합니다.
python
# 요청 메서드: post
# 요청 본문 내용:
{
"type": "login", # 로그인 유형, login은 로그인, callback은 콜백 요청
"url": "원래 OIDC 로그인 주소",
"args": {
# oidc/login 요청에서 수신한 쿼리 매개변수
},
"headers": {
# oidc/login 요청에서 수신한 요청 헤더 데이터
}
}
# 응답 내용:
{
"url": "포맷팅된 auth_url",
}
3. callback_url_format 함수 설명¶
oidc/callback의 리디렉션 주소를 외부 함수로 전달하여 재구성한 후 리디렉션을 수행합니다.
python
# 요청 메서드: post
# 요청 본문 내용:
{
"type": "callback", # 로그인 유형, callback 프로세스 요청
"url": "원래 생성된 리디렉션 주소",
"args": {
# oidc/login 요청에서 수신한 쿼리 매개변수
},
"headers": {
# oidc/login 요청에서 수신한 요청 헤더 데이터
}
}
# 응답 내용:
{
"url": "포맷팅된 url",
}
2. 내장 Func에 스크립트 추가¶
참고: 이 스크립트를 바로 복사할 수 있습니다.
!!! warning
아래 스크립트는 주소 포맷팅 처리 로직을 설명하기 위한 예시입니다.
스크립트에 `clientSecret`, Token 또는 기타 민감한 자격 증명을 직접 하드코딩하지 않는 것이 좋습니다. 키 정보가 필요한 경우 Func 측의 비밀번호 유형 환경 변수를 통해 주입 및 읽기하는 것을 우선적으로 사용하세요.
import json
import copy
import requests
from urllib.parse import urlparse, parse_qs, urlencode, urlunparse
from collections import OrderedDict
def parse_url(url):
'''
url을 파싱하여 통합된 url 파싱 객체와 쿼리 매개변수 딕셔너리 데이터를 반환합니다.
'''
# url 정보 파싱
parsed_url = urlparse(url)
# 도메인 전달은 url 매개변수에 배치
query_params = parse_qs(parsed_url.query)
# OrderedDict를 사용하여 매개변수의 원래 순서 유지
ordered_params = OrderedDict(query_params)
return parsed_url, ordered_params
def __make_redirect_uri(url, headers):
'''
요청 헤더에서 요청 출처 주소를 추출합니다. 이 주소는 X-Forwarded-Host 헤더에서 추출합니다.
'''
# redirect_uri 파싱
parsed_url, ordered_params = parse_url(url)
x_host = headers.get("X-Forwarded-Host")
x_port = headers.get("X-Forwarded-Port")
x_scheme = headers.get("X-Forwarded-Scheme", "").lower()
if not x_scheme:
x_scheme = copy.deepcopy(parsed_url.scheme)
netloc = copy.deepcopy(parsed_url.netloc)
if x_host:
if (x_scheme == "http" and x_port == "80") or (x_scheme == "https" and x_port == "443"):
netloc = x_host
else:
netloc = f"{x_host}:{x_port}" if x_port else x_host
parsed_url = parsed_url._replace(scheme=x_scheme, netloc=netloc)
new_url = urlunparse(parsed_url)
return new_url
@DFF.API('redirectUriFormatRequest 함수에 해당 - oidc client의 redirect_uri 정보 포맷팅')
def redirect_uri_format(**kwargs):
'''
Guance OIDC 프로세스 연동 시, 비표준 프로세스로 인해 redirect_uri 매개변수명 또는 매개변수 값이 변경되는 경우, 현재 함수를 통해 처리해야 합니다.
Parameters:
type {str} 현재 작업이 oidc 프로세스에서 해당하는 유형, login은 oidc/login 요청의 주소 변경, callback은 oidc/callback 프로세스 요청
redirect_uri {str} 원래 redirect_uri 주소
args {json} 프로세스에 해당하는 요청의 쿼리 매개변수
headers {json} 프로세스에 해당하는 요청 헤더 정보
return {"redirect_uri": "변경된 redirect_uri 주소"}
'''
print("kwargs--->>>", json.dumps(kwargs))
# 원래 redirect_uri 주소와 요청 헤더 정보 추출
redirect_uri = kwargs.get("redirect_uri", "")
headers = kwargs.get("headers", {})
# 새로운 redirect_uri 주소 생성
new_url = __make_redirect_uri(redirect_uri, headers)
result = {
# 이 주소는 원래의 로그인 인증 코드 획득 주소를 제공
"redirect_uri": new_url,
}
print("result-->>", result)
return result
@DFF.API('urlFormatRequest 함수에 해당 - login의 리디렉션 주소 정보 포맷팅')
def login_auth_url_format(**kwargs):
'''
Guance OIDC 프로세스 연동 시, 비표준 프로세스로 인해 login 주소의 매개변수를 변경해야 하는 경우, 현재 함수에서 처리할 수 있습니다.
Parameters:
type {str} 현재 작업이 oidc 프로세스에서 해당하는 유형, login은 oidc/login 요청의 주소 변경, callback은 oidc/callback 프로세스 요청
url {str} 원래 url 주소
args {json} 프로세스에 해당하는 요청의 쿼리 매개변수
headers {json} 프로세스에 해당하는 요청 헤더 정보
return {"url": "변경된 url 주소"}
'''
print("kwargs--->>>", json.dumps(kwargs))
url = kwargs.get("url")
new_url = None
args = kwargs.get("args")
headers = kwargs.get("headers")
new_host = headers.get("X-From")
if new_host:
# url 정보 파싱
parsed_url = urlparse(url)
parsed_url = parsed_url._replace(netloc=new_host)
new_url = urlunparse(parsed_url)
result = {
# 이 주소는 원래의 로그인 인증 코드 획득 주소를 제공
"url": new_url or url
}
print("result-->>", result)
return result
@DFF.API('urlFormatRequest 함수에 해당 - callback의 리디렉션 주소 정보 포맷팅')
def callback_url_format(**kwargs):
'''
Guance OIDC 프로세스 연동 시, 비표준 프로세스로 인해 callback 후 Guance 워크스페이스 로그인 주소의 매개변수를 변경해야 하는 경우, 현재 함수에서 처리할 수 있습니다.
Parameters:
type {str} 현재 작업이 oidc 프로세스에서 해당하는 유형, login은 oidc/login 요청의 주소 변경, callback은 oidc/callback 프로세스 요청
url {str} 원래 url 주소
args {json} 프로세스에 해당하는 요청의 쿼리 매개변수
headers {json} 프로세스에 해당하는 요청 헤더 정보
return {"url": "변경된 url 주소"}
'''
print("kwargs--->>>", json.dumps(kwargs))
type = kwargs.get("type")
url = kwargs.get("url")
args = kwargs.get("args") or {}
headers = kwargs.get("headers") or {}
new_url = None
from_v = args.get("from")
if from_v:
# url 파싱
parsed_url, ordered_params = parse_url(url)
ordered_params["from"] = from_v
# 쿼리 문자열 재구성, 원래 순서 유지
new_query_string = urlencode(ordered_params, doseq=True)
parsed_url = parsed_url._replace(query=new_query_string)
new_url = urlunparse(parsed_url)
result = {
# 이 주소는 callback 성공 후 프런트엔드로 로그인하는 주소 조정을 제공
"url": new_url or url,
}
return result
참고: redirect_uri_format, login_auth_url_format, callback_url_format 세 함수에 대해 권한 링크를 활성화해야 합니다.