Navigator 객체에서 제공하는 Useragent함수에는 http헤더에 포함된 User-Agent string에서 브라우저, OS, 사용자의 기기 정보 등 사용자 에이전트 정보를 얻을수 있음
이를 사용하는 큰 이유는 아래와 같다.
1. 특정 버전의 버그
2. OS의 동작 차이
3. 버전에 따른 동작차이
4. 사용자 에이전트에 따라 보여줄 컨텐츠 조작
통상 이런 다양한 이유로 User-Agent string에 담겨져 있는 정보를 사용하였지만 많은 정보량(entropy-엔트로피)이 담겨 있어 개인정보 침해 문제가 발생할수 있습니다.
이에 따라 Chrome은 개인정보 보호를 위한 샌드박스 프로젝트 중 Client Hints를 도입하였다.
Client Hint란 클라이언트 및 에이전트의 정보라고 할수 있고 가져올 정보를 명시한다.
Chrome 46 - HTTP Client Hints 실험적 도입
Chrome 77 - Freeze-User-Agent 플래그 추가
Chrome 82, 83 (2020.05) - User-Agent Client Hints 실험적 도입
Chrome 84 (2020.07) - User-Agent Client Hints 인터페이스 변경
📚UA프리징의 시작
Chrome 83부터 User-Agent Client Hints가 실험적으로 도입되었고 가장 큰 이슈는 User-Agent string의 프리징이다.
🧨다음 속성값이 고정된다.
- navigator.userAgent
- navigator.appVersion
- navigator.platform (Android Chrome에서는 Linux armv8l으로 고정)
- navigator.productSub
- navigator.vendor
🧨Chrome에서 안드로이드를 제외한 모든 운영체제는 윈도우 10으로 변한다.
🧨동기 방식으로 OS 이름, OS 버전, 모델명을 알 수 없다.
🧨navigator.userAgent 대신 navigator.userAgentData을 사용해야 한다.
- 브라우저 버전은 메이저 버전만 나타난다.
- OS 이름, 버전, 모델명, 브라우저의 풀버전은 비동기 방식으로 알 수 있다.
🌞크롬에서 제공하는 flags를 통한 ua프리징 체크 URL
chrome://flags/#enable-experimental-web-platform-features
chrome://flags/#freeze-user-agent
UA 프리징 테스트 결과 navigator.userAgent를 사용하여 얻은 User-Agent string 값은 다음과 같다.
- Galaxy Z Flip, Android 10, Chrome 85.0.4183.81
- 전: Mozila/5.0 (Linux; Android 10; SM-F700N) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/85.0.4183.81 Mobile Safari/537.36
- 후: Mozila/5.0 (Linux; Android 9; Unspecified Device) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/85.0.0.0 Mobile Safari/537.36
- Mac OS X 10.15.4, Chrome Canary 87.0.4243.0
- 전: Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_4) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/87.0.4243.0 Safari/537.36
- 후: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/87.0.0.0 Safari/537.36
🌞UA프리징이 시행되면서 OS, 브라우저 정보, 기기명에 대한 정보가 불분명해져간다. 앞으로도 더욱더 간소화 되고 보안적관점에서 제외가 필요하다면 더욱더 간소화 될것이다.
📚UA 프리징 대응 방안
UA 프리징의 대응방은으로는 User-Agent string을 세분화 하여 Object형식으로 나타낸 User-Agent Data를 사용할수 있다.
navigator객체.userAgentData에 접근하여 getHighEntropyValues 메소드를 통해서 정보를 호출할수 있다.
⭐User-Agent navigator 인터페이스
dictionary NavigatorUABrandVersion {
DOMString brand;
DOMString version;
};
dictionary UADataValues {
DOMString platform;
DOMString platformVersion;
DOMString architecture;
DOMString model;
DOMString uaFullVersion;
};
[Exposed=(Window,Worker)]
interface NavigatorUAData {
readonly attribute FrozenArray<NavigatorUABrandVersion> brands;
readonly attribute boolean mobile;
Promise<UADataValues> getHighEntropyValues(sequence<DOMString> hints);
};
interface mixin NavigatorUA {
[SecureContext] readonly attribute NavigatorUAData userAgentData;
};
Navigator includes NavigatorUA;
WorkerNavigator includes NavigatorUA;
⭐getHighEntropyValues 메소드 내
navigator.userAgentData
.getHighEntropyValues([
"architecture",
"model",
"platform",
"platformVersion",
"fullVersionList",
"uaFullVersion",
])
.then((values) => {
console.log(values);
});
📚지원부분
getHighEntropyValues 메소드는 현재 navigator객체에서 제공하는 실험적인 기능이다. ( 지원브라우저가 상이함 )
그래서 특정 디바이스 모델명을 찾아야 할때가 있다.
그래서 필자는 javascript에서 try catch를 통해서 일차적으로 getHighEntropyValues 메소드를 호출해보고 지원하지 않는 브라우저일때는 android와 IOS만 구별하였습니다.
try {
navigator.userAgentData
.getHighEntropyValues([
"architecture",
"model",
"platform",
"platformVersion",
"fullVersionList",
"uaFullVersion",
])
.then((values) => {
console.log(values);
if(values.model.indexOf("SM-") > -1 ) {
// 비동기로 호출하기때문에 결과 호출시 로직실행
}
});
// getHighEntropyValues메소드를 지원하지 않을때
} catch (error) {
if(navigator.userAgentData.indexOf("ANDROID") > -1 ) {
} else {
}
}
📚마치며
웹에서는 정말 많은 보안이슈가 업데이트가 됩니다. 크롬브라우저 80버전에서 그다음버전으로 넘어갔을때 입니다. Samesite설정이 안되어있으면 타 URL에 대한 쿠키공유가 안되어 해당 기능을 사용 못했던 적이 있습니다. 이렇듯 브라우저는 앞으로도 더욱더 보안에 대해서 제공하는 정보는 더 간소해 질것 입니다. 앞으로 소스를 구현할때 이러한 프리징으로 인한 내역을 염두하여 작성을 해야할것입니다.
Ref.https://d2.naver.com/helloworld/6532276
댓글