브라우저, 사용자 설정, 저장용량 파티셔닝의 서드 파티 쿠키 차단은 인증과 같은 사용자 여정을 위해 삽입된 컨텍스트에서 쿠키 및 기타 저장용량을 사용하는 사이트와 서비스에 문제를 야기합니다. Storage Access API (SAA)를 사용하면 이러한 사용 사례가 계속 작동하면서 교차 사이트 추적이 최대한 제한됩니다.
구현 상태
Storage Access API는 모든 주요 브라우저에서 사용할 수 있지만 브라우저 간에 약간의 구현 차이가 있습니다. 이러한 차이점은 이 게시물의 관련 섹션에서 강조 표시되어 있습니다.
API를 표준화하기 전에 남아 있는 모든 차단 문제를 해결하기 위한 작업이 계속 진행되고 있습니다.
Storage Access API란 무엇인가요?
Storage Access API는 브라우저 설정에 따라 액세스가 거부되는 경우에도 iframe이 스토리지 액세스 권한을 요청할 수 있는 JavaScript API입니다. 교차 사이트 리소스 로드에 종속된 사용 사례가 있는 삽입은 API를 사용하여 필요에 따라 사용자에게 액세스 권한을 요청할 수 있습니다.
스토리지 요청이 승인되면 iframe은 파티션되지 않은 쿠키와 스토리지에 액세스할 수 있으며, 이는 사용자가 최상위 사이트로 방문할 때도 사용할 수 있습니다.
Storage Access API를 사용하면 최종 사용자에게 최소한의 부담으로 특정 파티션되지 않은 쿠키 및 저장소 액세스를 제공하면서도 사용자 추적에 자주 사용되는 일반적인 파티션되지 않은 쿠키 및 저장소 액세스는 방지할 수 있습니다.
사용 사례
일부 서드 파티 삽입에는 사용자에게 더 나은 환경을 제공하기 위해 파티션되지 않은 쿠키 또는 저장소에 대한 액세스가 필요합니다. 서드 파티 쿠키가 제한되고 저장소 파티셔닝이 사용 설정된 경우에는 이러한 액세스가 불가능합니다.
사용 사례는 다음과 같습니다.
- 로그인 세션 세부정보가 필요한 댓글 작성 위젯이 삽입되었습니다.
- 로그인 세션 세부정보가 필요한 소셜 미디어 '좋아요' 버튼
- 로그인 세션 세부정보가 필요한 삽입된 문서
- 동영상 삽입에 제공되는 프리미엄 환경 (예: 로그인한 사용자에게 광고를 표시하지 않거나 자막에 대한 사용자의 환경설정을 파악하거나 특정 동영상 유형을 제한하는 기능)
- 삽입된 결제 시스템
이러한 사용 사례의 대부분은 삽입된 iframe에서 로그인 액세스를 유지하는 것과 관련이 있습니다.
다른 API보다 Storage Access API를 사용해야 하는 경우
Storage Access API는 파티션되지 않은 쿠키와 저장소를 사용하는 대안 중 하나이므로 이 API를 다른 API와 비교하여 언제 사용해야 하는지 이해하는 것이 중요합니다. 다음 두 가지가 모두 해당하는 사용 사례에 적합합니다.
- 사용자가 삽입된 콘텐츠와 상호작용합니다. 즉, 수동 iframe 또는 숨겨진 iframe이 아닙니다.
- 사용자가 최상위 컨텍스트에서 삽입된 출처를 방문했습니다. 즉, 해당 출처가 다른 사이트에 삽입되지 않은 경우입니다.
다양한 사용 사례에 사용할 수 있는 대체 API가 있습니다.
- Cookies Having Independent Partitioned State (CHIPS)를 사용하면 개발자가 최상위 사이트별로 별도의 쿠키 저장소를 사용하여 '분할된' 스토리지에 쿠키를 선택할 수 있습니다. 예를 들어 서드 파티 웹 채팅 위젯은 쿠키 설정을 사용하여 세션 정보를 저장할 수 있습니다. 세션 정보는 사이트별로 저장되므로 위젯에서 설정한 쿠키가 삽입된 다른 웹사이트에서 액세스할 필요가 없습니다. Storage Access API는 삽입된 서드 파티 위젯이 여러 출처에서 동일한 정보를 공유하는 데 종속되는 경우에 유용합니다 (예: 로그인한 세션 세부정보 또는 환경설정).
- 저장소 파티션은 교차 사이트 iframe이 기존 JavaScript 저장소 메커니즘을 사용하는 동시에 기본 저장소를 사이트별로 분할하는 방법입니다. 이렇게 하면 한 웹사이트의 삽입된 저장소에 다른 웹사이트의 동일한 삽입이 액세스하지 못합니다.
- 관련 웹사이트 세트 (RWS)는 조직이 사이트 간의 관계를 선언하는 방식으로, 브라우저에서 특정한 목적으로 제한된 파티션되지 않은 쿠키 및 스토리지 액세스를 허용합니다. 사이트는 Storage Access API로 액세스를 요청해야 하지만, 집합에 포함된 사이트의 경우 사용자 메시지 없이 액세스가 부여될 수 있습니다.
- Federated Credential Management (FedCM)는 제휴 ID 서비스에 대한 개인 정보 보호 접근 방식입니다. Storage Access API는 로그인 후 파티션되지 않은 쿠키 및 스토리지에 대한 액세스를 처리합니다. 일부 사용 사례에서는 FedCM이 Storage Access API의 대체 솔루션을 제공하며, 로그인 중심의 브라우저 프롬프트를 제공하므로 FedCM이 더 적합할 수 있습니다. 그러나 FedCM을 채택하려면 일반적으로 HTTP 엔드포인트를 지원하는 등 코드를 추가로 변경해야 합니다.
- 사기 방지, 광고 관련, 측정 API도 있지만 Storage Access API는 이러한 문제를 해결하기 위한 것이 아닙니다.
Storage Access API 사용
Storage Access API에는 두 가지 약속 기반 메서드가 있습니다.
Document.hasStorageAccess()
(Chrome 125부터는 새 이름인Document.hasUnpartitionedCookieAccess()
으로도 사용 가능)Document.requestStorageAccess()
Permissions API와도 통합됩니다. 이렇게 하면 서드 파티 컨텍스트에서 저장용량 액세스 권한의 상태를 확인할 수 있으며, 이 상태는 document.requestStorageAccess()
호출이 자동으로 부여될지 여부를 나타냅니다.
hasStorageAccess()
메서드 사용
사이트가 처음 로드될 때 hasStorageAccess()
메서드를 사용하여 서드 파티 쿠키에 대한 액세스 권한이 이미 부여되었는지 확인할 수 있습니다.
// Set a hasAccess boolean variable which defaults to false.
let hasAccess = false;
async function handleCookieAccessInit() {
if (!document.hasStorageAccess) {
// Storage Access API is not supported so best we can do is
// hope it's an older browser that doesn't block 3P cookies.
hasAccess = true;
} else {
// Check whether access has been granted using the Storage Access API.
// Note on page load this will always be false initially so we could be
// skipped in this example, but including for completeness for when this
// is not so obvious.
hasAccess = await document.hasStorageAccess();
if (!hasAccess) {
// Handle the lack of access (covered later)
}
}
if (hasAccess) {
// Use the cookies.
}
}
handleCookieAccessInit();
저장소 액세스 권한은 requestStorageAccess(),
를 호출한 후에만 iframe 문서에 부여되므로 동일한 iframe의 다른 동일한 출처 문서에 이미 액세스 권한이 부여된 경우를 제외하고 hasStorageAccess()
는 처음에는 항상 false를 반환합니다. 특히 HTML 문서의 초기 요청에 쿠키가 있어야 하는 페이지에 대한 액세스 권한을 부여한 후 새로고침을 허용하기 위해 iframe 내의 동일 출처 탐색 전반에서 부여가 보존됩니다.
requestStorageAccess()
사용
iframe에 액세스 권한이 없는 경우 requestStorageAccess()
메서드를 사용하여 액세스 권한을 요청해야 할 수 있습니다.
if (!hasAccess) {
try {
await document.requestStorageAccess();
} catch (err) {
// Access was not granted and it may be gated behind an interaction
return;
}
}
이 요청이 처음으로 이루어지면 사용자는 브라우저 메시지를 통해 이 액세스를 승인해야 할 수 있으며, 그 후 프로미스가 해결되거나 거부되어 await
가 사용되는 경우 예외가 발생합니다.
악용을 방지하기 위해 이 브라우저 메시지는 사용자 상호작용 후에만 표시됩니다. 따라서 requestStorageAccess()
는 iframe이 로드되는 즉시가 아니라 사용자 활성화 이벤트 핸들러에서 처음 호출해야 합니다.
async function doClick() {
// Only do this extra check if access hasn't already been given
// based on the hasAccess variable.
if (!hasAccess) {
try {
await document.requestStorageAccess();
hasAccess = true; // Can assume this was true if requestStorageAccess() did not reject.
} catch (err) {
// Access was not granted.
return;
}
}
if (hasAccess) {
// Use the cookies
}
}
document.querySelector('#my-button').addEventListener('click', doClick);
쿠키 대신 로컬 저장소를 사용해야 하는 경우 다음을 실행할 수 있습니다.
let handle = null;
async function doClick() {
if (!handle) {
try {
handle = await document.requestStorageAccess({localStorage: true});
} catch (err) {
// Access was not granted.
return;
}
}
// Use handle to access unpartitioned local storage.
handle.localStorage.setItem('foo', 'bar');
}
document.querySelector('#my-button').addEventListener('click', doClick);
권한 메시지
사용자가 버튼을 처음 클릭하면 대부분의 경우 브라우저 메시지가 자동으로 표시됩니다(일반적으로 주소 표시줄에 표시됨). 다음 스크린샷은 Chrome의 메시지 예를 보여주지만 다른 브라우저에도 유사한 UI가 있습니다.
특정 상황에서는 브라우저에서 메시지를 건너뛰고 권한이 자동으로 제공될 수 있습니다.
- 메시지를 수락한 후 지난 30일 동안 페이지와 iframe이 사용된 경우
- 삽입된 iframe이 관련 웹사이트 세트의 일부인 경우
- FedCM이 저장소 액세스의 신뢰 신호로 사용되는 경우
- Firefox에서는 알려진 웹사이트 (최상위 수준에서 상호작용한 웹사이트)의 경우에도 처음 5번의 시도에서는 프롬프트가 건너뜁니다.
또는 특정 상황에서 메시지를 표시하지 않고 메서드가 자동으로 거부될 수도 있습니다.
- 사용자가 이전에 iframe이 아닌 최상위 문서로 iframe을 소유한 사이트를 방문하고 상호작용하지 않은 경우 즉, Storage Access API는 사용자가 이전에 퍼스트 파티 컨텍스트에서 방문한 삽입된 사이트에만 유용합니다.
- 상호작용 후 메시지의 사전 승인 없이 사용자 상호작용 이벤트 외부에서
requestStorageAccess()
메서드가 호출되는 경우
사용자에게 처음 사용 시 메시지가 표시되지만 이후 방문 시에는 Chrome 및 Firefox에서 메시지가 표시되지 않고 사용자 상호작용 없이도 requestStorageAccess()
를 해결할 수 있습니다. Safari에서는 항상 사용자 상호작용이 필요합니다.
메시지 또는 사용자 상호작용 없이 쿠키 및 저장소 액세스가 부여될 수 있으므로 이를 지원하는 브라우저 (Chrome 및 Firefox)에서 페이지 로드 시 requestStorageAccess()
를 호출하여 사용자 상호작용 전에 파티션되지 않은 쿠키 또는 저장소 액세스를 얻을 수 있습니다. 이렇게 하면 사용자가 iframe과 상호작용하기 전이라도 파티션되지 않은 쿠키와 저장소에 즉시 액세스하여 더 완전한 환경을 제공할 수 있습니다. 이는 사용자 상호작용을 기다리는 것보다 어떤 상황에서는 더 나은 사용자 환경을 제공할 수 있습니다.
FedCM이 SAA의 신뢰 신호로 사용됨
FedCM (제휴 사용자 인증 정보 관리)은 서드 파티 쿠키 또는 탐색 리디렉션을 사용하지 않는 제휴 ID 서비스 (예: '다음으로 로그인')에 대한 개인 정보 보호 접근 방식입니다.
사용자가 FedCM이 적용된 서드 파티 ID 공급업체 (IdP)의 일부 삽입된 콘텐츠가 있는 신뢰 당사자 (RP)에 로그인하면 삽입된 IdP 콘텐츠가 자체 최상위 파티션되지 않은 쿠키에 대한 저장소 액세스 권한을 자동으로 가져올 수 있습니다. FedCM으로 자동 스토리지 액세스를 사용 설정하려면 다음 조건을 충족해야 합니다.
- FedCM 인증 (사용자 로그인 상태)이 활성 상태여야 합니다.
- RP가
identity-credentials-get
권한을 설정하여 선택했습니다. 예를 들면 다음과 같습니다.
<iframe src="https://idp.example" allow="identity-credentials-get"></iframe>
예를 들어 idp.example
iframe이 rp.example
에 삽입됩니다. 사용자가 FedCM으로 로그인하면 idp.example
iframe은 자체 최상위 쿠키의 저장소 액세스를 요청할 수 있습니다.
rp.example
는 FedCM을 호출하여 ID 제공업체 idp.example
로 사용자를 로그인합니다.
// The user will be asked to grant FedCM permission.
const cred = await navigator.credentials.get({
identity: {
providers: [{
configURL: 'https://idp.example/fedcm.json',
clientId: '123',
}],
},
});
사용자가 로그인한 후 RP가 권한 정책으로 이를 명시적으로 허용한 경우 IdP는 idp.example
iframe 내에서 requestStorageAccess()
을 호출할 수 있습니다.
삽입에는 사용자 활성화나 다른 권한 메시지가 필요하지 않고 자체 최상위 쿠키에 대한 저장소 액세스 권한이 자동으로 부여됩니다.
// Make this call within the embedded IdP iframe:
// No user gesture is needed, and the storage access will be auto-granted.
await document.requestStorageAccess();
// This returns `true`.
const hasAccess = await document.hasStorageAccess();
이 권한은 사용자가 FedCM으로 로그인되어 있는 동안만 자동으로 부여됩니다. 인증이 비활성화되면 표준 SAA 요구사항이 적용되어 스토리지 액세스 권한이 부여됩니다.
storage-access
권한 쿼리 사용
사용자 상호작용 없이 액세스를 부여할 수 있는지 확인하려면 storage-access
권한의 상태를 확인하고 상호작용이 필요한 경우 requestStoreAccess()
를 호출하고 실패하게 하는 대신 사용자 작업이 필요하지 않은 경우에만 requestStoreAccess()
를 조기에 호출하면 됩니다.
이렇게 하면 로그인 버튼과 같은 다른 콘텐츠를 표시하여 메시지를 미리 표시할 필요가 있을 때 이를 처리할 수도 있습니다.
다음 코드는 이전 예에 storage-access
권한 확인을 추가합니다.
// Set a hasAccess boolean variable which defaults to false except for
// browsers which don't support the API - where we assume
// such browsers also don't block third-party cookies.
let hasAccess = false;
async function hasCookieAccess() {
// Check if Storage Access API is supported
if (!document.requestStorageAccess) {
// Storage Access API is not supported so best we can do is
// hope it's an older browser that doesn't block 3P cookies.
return true;
}
// Check if access has already been granted
if (await document.hasStorageAccess()) {
return true;
}
// Check the storage-access permission
// Wrap this in a try/catch for browsers that support the
// Storage Access API but not this permission check
// (e.g. Safari and earlier versions of Firefox).
let permission;
try {
permission = await navigator.permissions.query(
{name: 'storage-access'}
);
} catch (error) {
// storage-access permission not supported. Assume no cookie access.
return false;
}
if (permission) {
if (permission.state === 'granted') {
// Permission has previously been granted so can just call
// requestStorageAccess() without a user interaction and
// it will resolve automatically.
try {
await document.requestStorageAccess();
return true;
} catch (error) {
// This shouldn't really fail if access is granted, but return false
// if it does.
return false;
}
} else if (permission.state === 'prompt') {
// Need to call requestStorageAccess() after a user interaction
// (potentially with a prompt). Can't do anything further here,
// so handle this in the click handler.
return false;
} else if (permission.state === 'denied') {
// Not used: see https://github.com/privacycg/storage-access/issues/149
return false;
}
}
// By default return false, though should really be caught by earlier tests.
return false;
}
async function handleCookieAccessInit() {
hasAccess = await hasCookieAccess();
if (hasAccess) {
// Use the cookies.
}
}
handleCookieAccessInit();
샌드박스 처리된 iframe
샌드박스 처리된 iframe에서 Storage Access API를 사용하는 경우 다음 샌드박스 권한이 필요합니다.
- Storage Access API에 대한 액세스를 허용하려면
allow-storage-access-by-user-activation
가 필요합니다. - JavaScript를 사용하여 API를 호출하도록 허용하려면
allow-scripts
가 필요합니다. - 동일 출처 쿠키 및 기타 저장소에 대한 액세스를 허용하려면
allow-same-origin
가 필요합니다.
예를 들면 다음과 같습니다.
<iframe sandbox="allow-storage-access-by-user-activation
allow-scripts
allow-same-origin"
src="..."></iframe>
쿠키 요구사항
Chrome에서 Storage Access API로 액세스하려면 크로스 사이트 쿠키를 다음 두 속성으로 설정해야 합니다.
SameSite=None
- 쿠키를 크로스 사이트로 표시하는 데 필요합니다.Secure
: HTTPS 사이트에서 설정한 쿠키에만 액세스할 수 있습니다.
Firefox 및 Safari에서는 쿠키가 기본적으로 SameSite=None
로 설정되며 SAA를 Secure
쿠키로 제한하지 않으므로 이러한 속성은 필요하지 않습니다. SameSite
속성을 명시하고 항상 Secure
쿠키를 사용하는 것이 좋습니다.
최상위 페이지 액세스
Storage Access API는 삽입된 iframe 내에서 서드 파티 쿠키에 대한 액세스를 사용 설정하기 위한 것입니다.
최상위 페이지에 서드 파티 쿠키에 대한 액세스가 필요한 다른 사용 사례도 있습니다. 예를 들어 쿠키로 제한된 이미지나 스크립트는 사이트 소유자가 iframe이 아닌 최상위 문서에 직접 포함하고 싶을 수 있습니다. 이 사용 사례를 해결하기 위해 Chrome은 requestStorageAccessFor()
메서드를 추가하는 Storage Access API 확장 프로그램을 제안했습니다.
requestStorageAccessFor()
메서드
requestStorageAccessFor()
메서드는 requestStorageAccess()
와 비슷한 방식으로 작동하지만 최상위 리소스에 적용됩니다. 서드 파티 쿠키에 대한 일반 액세스 권한을 부여하지 않도록 관련 웹사이트 세트 내 사이트에만 사용할 수 있습니다.
requestStorageAccessFor()
사용 방법에 관한 자세한 내용은 관련 웹사이트 세트: 개발자 가이드를 참고하세요.
top-level-storage-access
권한 쿼리
브라우저 지원
storage-access
권한과 마찬가지로 requestStorageAccessFor()
에 대한 액세스 권한을 부여할 수 있는지 확인하는 top-level-storage-access
권한이 있습니다.
RWS와 함께 사용할 때 Storage Access API는 어떻게 다른가요?
Storage Access API와 함께 관련 웹사이트 세트를 사용하면 다음 표에 설명된 특정 추가 기능을 사용할 수 있습니다.
RWS 없음 | RWS 포함 | |
---|---|---|
저장소 액세스 요청을 시작하려면 사용자 동작이 필요함 | ||
액세스 권한을 부여하기 전에 사용자가 최상위 컨텍스트에서 요청된 저장소 출처를 방문해야 함 | ||
최초 사용자 메시지를 건너뛸 수 있음 | ||
이전에 액세스 권한이 부여된 경우 requestStorageAccess 를 호출할 필요가 없음 |
||
관련 웹사이트 사이트의 다른 도메인에 대한 액세스 권한을 자동으로 부여합니다. | ||
최상위 페이지 액세스를 위한 requestStorageAccessFor 지원 |
데모: 쿠키 설정 및 액세스
다음 데모에서는 데모의 첫 번째 화면에서 직접 설정한 쿠키에 데모의 두 번째 사이트에 삽입된 프레임에서 액세스하는 방법을 보여줍니다.
storage-access-api-demo.glitch.me
데모를 사용하려면 서드 파티 쿠키가 사용 중지된 브라우저가 필요합니다.
chrome://flags/#test-third-party-cookie-phaseout
플래그가 설정되고 브라우저가 다시 시작된 Chrome 118 이상- Firefox
- Safari
데모: 로컬 스토리지 설정
다음 데모에서는 Storage Access API를 사용하여 서드 파티 iframe에서 파티션되지 않은 브로드캐스트 채널에 액세스하는 방법을 보여줍니다.
https://saa-beyond-cookies.glitch.me/
이 데모를 사용하려면 test-third-party-cookie-phaseout 플래그가 사용 설정된 Chrome 125 이상이 필요합니다.