Client Storage

Many of the web browsers allow you to store data, this data can be login information, cookies, etc, Originally cookies were the only data you could store however with WebStorage you can now store session data outside of the cookie, also you can store long term data in a local Storage area as well and now there is a IndexDB that can store Javascript objects, all of these i will cover in this section.

Cookies

Cookies were the original data storage and was intended to store session data on the client, they are tied to a sepcific domain and have a number of restrictions, 300 in total, 4K byes per cookie, 20 cookies per domain and 81k per domain, despite this developers used the cookies to store information. The cookie is made up of the following

The pieces of cookie information is sent via the set-cookie header

Cookie
Set-Cookie: name=value; expires=Mon, 01-Jan-20 00:00:01 GMT; domain=.datadisk.co.uk; path=/; secure

You can use the BOM document.cookie is used however you have to decode it as it contains a string of all the cookies for that page, and as there is not a good interface for handling cookies you need to create one via functions.

Web Storage

Web Storage is used when you want to store data outside of a cookie, it overcomes the limiations of cookies and has a interface making it easy to use, there are limitations and this is down to the specific browser. The Storage-Type handles key/value pairs upto a maximin defined by the browser, it has methods the following methods

There are two methods which you use to store the Storage object, sessionStorage which stores data for only the session, and localStorage which persists data until Javascript removes it our the browser clears it.

sessionStorage example
// store data using method
sessionStorage.setItem("login", "pvalle");

// store data using property
sessionStorage.title = "Mr";

// get data using method
let name = sessionStorage.getItem("login");

// get data using property
let title = sessionStorage.title;

// use delete to remove a value
delete sessionStorage.login;
localStorage example
// store data using method
localStorage.setItem("login", "pvalle");

// store data using property
localStorage.title = "Mr";

// get data using method
let name = localStorage.getItem("login");

// get data using property
let title = localStorage.title;
storage event
window.addEventListener("storage", (event) => alert('Storage changed for ${event.domain}'));

IndexDB

IndexDB is a structured data store in the browser, it allows you store store Javascript objects and you can query the database, it is accessed asynchronously and you can attached events handlers onsuccess and onerror to handle the query. IndexDB is similar to other databses like MySQL but it stored objects, you first open a databse using the method open() giving it a name, theer are many methods that can create, remove objects from/to the db

Create db
let db, request, version = 1;

request = indexedDB.open("admin", version);

request.onerror = (event) =>
    alert(`Failed to open: ${event.target.errorCode}`);
request.onsuccess = (event) => {
    db = event.target.result;
};
Object store
let user = {
username: "007",
firstName: "James",
lastName: "Bond",
password: "foo"
};

request.onupgradeneeded = (event) => {
    const db = event.target.result;

    // Delete the current objectStore if it exists. This is useful for testing,
    // but this will wipe existing data each time this event handler executes.
    if (db.objectStoreNames.contains("users")) {
        db.deleteObjectStore("users");
    }
    
    db.createObjectStore("users", { keyPath: "username" });
};
Transactions
let transaction = db.transaction("users");

let transaction = db.transaction(["users", "anotherStore"]);


const transaction = db.transaction("users");
const store = transaction.objectStore("users");
const request = store.get("007");

request.onerror = (event) => alert("Did not get the object!");
request.onsuccess = (event) => alert(event.target.result.firstName);

// add to the store
store.add(anotherUser);
Querying db
const transaction = db.transaction("users");
const store = transaction.objectStore("users");

request = store.openCursor();

request.onsuccess = (event) => {
   const cursor = event.target.result;
   let value, updateRequest;
   
   if (cursor) { 							// always check
	if (cursor.key == "foo") {
		value = cursor.value; 					// get current value
		value.password = "magic!"; 				// update the password
		updateRequest = cursor.update(value); 	                // request the update be saved
		
		updateRequest.onsuccess = () => {
			// handle success;
		};

		updateRequest.onfailure = () => {
			// handle failure
		};
	}
  }
};

request.onfailure = (event) => {
	// handle failure
};
Delete item
request.onsuccess = (event) => {
    const cursor = event.target.result;
    let value,deleteRequest;

    if (cursor) { // always check
        if (cursor.key == "foo") {
            deleteRequest = cursor.delete(); // request the value be deleted
            deleteRequest.onsuccess = () => {
                // handle success;
            };
            deleteRequest.onfailure = () => {
                // handle failure
            };
        }
    }
};
Create index
const transaction = db.transaction("users");
const store = transaction.objectStore("users");
index = store.createIndex("username", "username", { unique: true });

Note: you can use the index to query index.openCursor()