1

I have a <div id="populated"> element on the page which receives dynamically created content, including populated DIVs, text areas, input texts and check boxes. Moreover, there are some elements with addEventListener.

My question is: how to save this "populated" DIV and reload it when a user returns to the page?

What I've tried, by using localStorage:

  • Save the entire DIV as a serialised object (got tips from here). Problem: "Uncaught TypeError: Accessing selectionDirection on an input element that cannot have a selection."

  • Save the entire DIV as innerHTML. Problems: 1) bind events are lost 2) already entered data in textareas/inputs is lost.

I can rebind the events, but parsing the DIV structure and storing/restoring .value for each element seemed too complicated.

I'm using "pure" JavaScript (no frameworks) and without AJAX. Any ideas, keywords?

Community
  • 1
  • 1
marw
  • 2,939
  • 4
  • 28
  • 37
  • Is there any reason to use pure Javascript, and without AJAX? – Hidde May 29 '12 at 19:15
  • It's my 2nd week learning JS, so I'm trying to make it as less complicated as possible. But, in essence, no reason at all. – marw May 29 '12 at 19:16
  • OK, that I suggest learning jQuery. It seems strange to start with a library, but it makes Javascript a lot easier and actually a lot more fun. http://jquery.com/ has great examples, and I'd suggest just trying it out. A lot of the thing people try nowadays with JS, are very hard and complicated, and jQuery solves so many of the little problems people run into. Good luck, if you need any help post some code, and we (I) will try! – Hidde May 29 '12 at 19:19

2 Answers2

1

There are basically three ways to persist data on the web:

  1. Server-Side
  2. Local Storage
  3. Cookies

Now cookies have a finite limit to how much they can store (and IIRC that limit varies by browser), so if your DIV has a decent amount of stuff in it, cookies won't cut it. Local storage works for newer browsers ... if it works at all that is (you should really post your storage error as a separate SO post of its own).

As for what to store, you can basically give up on storing bound events ... unless you want to convert every one to an in-line attribute (eg. "onclick='...") and save all the HTML ... but that would be a terrible idea because inline events quickly become a nightmare. (If you only have one or two this might be an option ... but I wince at suggesting it.)

What is commonly done instead is that you serialize your data in to an structure that just contains the data (no DOM, no events, etc.). You store that (however you choose), and then when you want to "load" it you deserialize it, building any DOM elements you need and hooking up any events you want at that point. JSON.stringify (present in newer browser's, or available via Crockford's JSON library if you want to support older ones) is one option for doing this serialization, as is jQuery's serialize and serializeArray methods. Or you can roll your own solution.

So in short:

  1. Serialize just the data you want to save (via JSON.stringify, $.serialize or $.serializeArray, or your own function)
  2. Choose from server-side (the common approach), cookies (limited space) or local storage (only on newer browsers and you'll have to solve your error) to store it
  3. When you get it out of storage, deserialize it, building DOM elements and binding events to those elements as needed.

Hope that helps.

machineghost
  • 33,529
  • 30
  • 159
  • 234
  • Thanks for the overview. However, I was familiar with serialisation, which did not work in my case (the first approach). I also discovered that binding is not saved. – marw May 30 '12 at 10:25
0

It took some redesign, but I managed to solve the problem:

  1. The structure of the DIV is stored as innerHTML on onpageonload in localStorage.
  2. The values of the fields inside the DIV are serialised and stored in localStorage.
  3. The binding function is independent and can be called so it parses the whole DIV.

On onbeforeunload the scrips goes through the DIV as saves the "inner HTML" and the values. While loading, the scripts checks if localStorage is empty: if not, populates the DIV, loads the values and rebind the events.

marw
  • 2,939
  • 4
  • 28
  • 37