(원문: https://developers.google.com/web/updates/2019/03/kv-storage#browser-support)
(현재 일부만 번역된 상태입니다.)
브라우저 제조사들과 웹 성능 전문가들은 근래에 localStorage의 느린 속도를 대체할 무언가가 필요하다, 웹 개발자들은 이것을 더 이상 사용하지 않는 것이 좋다고 지적해왔습니다.
이 말은 틀리지 않았습니다. localStorage
는 메인 스레드를 멈추게 만드는 동기적(synchronous) API를 갖고 있으며, 여기에 접근함으로써 웹 페이지가 멈추는 현상을 겪게될 수 있습니다.
문제의 핵심은 다음과 같습니다. localStorage
는 굉장히 쉬운 API를 갖고 있는 반면, 비슷한 기능을 하면서도 비동기식 API를 갖고 있는 대체재는 indexedDB가 유일한데 이 API는 사용하기 그다지 편하지 않습니다.
그래서 개발자들은 쓰기 어려운 것, 혹은 성능이 좋지 않은 것 중에 하나를 선택할 수 밖에 없습니다. 물론 localStorage
만큼 사용하기 편한 API를 제공하면서도 그 내부에서는 비동기식 스토리지 API를 사용하는 라이브러리들이 있습니다만, 이런 라이브러리들을 앱에 포함시키는 것 역시 파일 사이즈와 성능 예산을 갉아먹습니다.
만약 성능 좋고 비동기식 API를 쓰면서도 localStorage 만큼 쓰기 쉽고, 파일 크기가 늘어날 걱정을 하지 않아도 된다면 어떨까요?
곧 그럴게 될 겁니다. Chrome은 내장(built-in) 모듈이라는 새 기능을 시험 중이며, 처음으로 탑재할 예정인 모듈이 KV Storage라 불리는 비동기식 키/값 스토리지 모듈입니다.
KV Storage 모듈에 대해 자세히 설명하기 전에, 내장 모듈에 설명하겠습니다.
내장 모듈은 일반적인 JavaScript 모듈과 비슷하지만, 브라우저에 이미 내장되어 있으므로 다운로드를 할 필요가 없다는 차이점이 있습니다.
전통적인 웹 API와 마찬가지로, 내장 모듈은 표준화 과정을 거쳐야 합니다. 이 과정에는 각각의 명세에 대한 설계 리뷰, 그리고 브라우저 개발사들과 웹 개발자들에게 긍정적인 피드백을 받는 과정이 포함됩니다. (Chrome에서는, 내장 모듈이 다른 모든 신규 API에 적용되는 런칭 과정을 따릅니다.)
전통적인 웹 API와는 다르게, 내장 모듈은 전역 스코프에 노출되지 않습니다. 대신 import를 해야 사용할 수 있습니다.
내장 모듈을 전역 스코프에 노출시키지 않음으로써 여러 이점을 얻을 수 있습니다. 새로운 JavaScript 런타임(새 탭, 워커, 서비스 워커 등)을 띄울 때의 오버헤드가 줄어듭니다. 그리고 import가 되지 않으면 메모리와 CPU를 전혀 소비하지 않습니다. 더해서, 여러분의 코드에 정의되어 있는 변수 이름과 충돌할 일도 없습니다.
내장 모듈을 import 하려면 내장 모듈 이름 앞에 std:
접두사를 사용하세요. 예를 들어, 아래 코드와 같이 KV Storage 모듈을 import 할 수 있습니다.
import {storage, StorageArea} from 'std:kv-storage';
KV Storage 모듈은 localStorage
API 수준의 단순함을 갖고 있지만, API의 실질적인 사용법은 JavaScript Map에 가깝습니다. getItem()
, setItem()
, removeItem()
대신에 get()
, set()
, delete()
를 사용합니다. 또한 localStorage
가 제공하지 않는 유사 Map API도 제공합니다. keys()
, values()
, entries()
같은 것들 말이죠. 또한 Map
과 유사하게, 키가 문자열일 필요가 없습니다. 어떤 structured-serializable 타입도 키가 될 수 있습니다.
Map
과 다른 점은, 모든 KV Storage 메소드가 promise 또는 async iterator를 반환한다는 것입니다. (비동기식으로 동작해야 한다는 것이 이 모듈의 핵심 요구사항이기 때문이죠) 전체 API를 자세히 알고 싶다면, 명세를 참고하세요.
위의 예제코드에서도 살펴봤다시피, KV Storage 모듈은 두 개의 named export를 갖습니다. storage
와 StorageArea
가 그것입니다.
storage
는 StorageArea
의 인스턴스로 'default'
라는 이름을 갖습니다. 그리고 대부분의 어플리케이션 코드에서 이 인스턴스를 사용하게 될 것입니다. StorageArea
클래스는 추가적인 격리가 필요할 때 사용할 수 있습니다. (e.g. 외부 라이브러리에서 데이터를 저장할 때, 기본 storage
인스턴스에 저장되어 있는 데이터와 충돌이 나는 것을 방지하고 싶을 때) StorageArea
데이터는 IndexedDB 데이터베이스에 kv-storage:${name}
이라는 이름으로 저장됩니다.
KV Storage 모듈을 사용하는 예제코드입니다.
import {storage} from 'std:kv-storage';
const main = async () => {
const oldPreferences = await storage.get('preferences');
document.querySelector('form').addEventListener('submit', async () => {
const newPreferences = Object.assign({}, oldPreferences, {
// Updated preferences go here...
});
await storage.set('preferences', newPreferences);
});
};
main();
주의: KV Storage 모듈은 현재 Chrome 74 버전에서 experimental web platform features flag
를 활성화했을 때만 사용 가능합니다.