npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2024 – Pkg Stats / Ryan Hefner

nserializejson

v1.0.32-alpha.1

Published

HTML form JSON serializer on Vanilla JS

Downloads

682

Readme

npm version npm downloads

Description

NSerializeJson is a Vanilla JS form serializer which serializes form data into JSON object.

Changes

v. 1.0.3 (2019-08-13)
  • Dot separator parsing fix.
  • Added more examples.
v. 1.0.2 (2018-11-11)

select element parsing fix.

Usage

Install

npm install nserializejson

Prepare and usage

Import:

import {NSerializeJson} from "nserializejson";

or use the scripts tag (bundle):

<script src="nserializejson.min.js"></script>

Define the HTML form:

<form id="myForm">
  <input type="text" name="title" value="Finding Loot"/>
  <input type="text" name="author[name]" value="John Smith"/>
  <input type="text" name="author[job]"  value="Legendary Pirate"/>
</form>

Then: (TypeScript)

NSerializeJson.serializeForm(document.getElementById("myForm") as HTMLFormElement);

(JavaScript, using scripts tag)

NSerializeJson.NSerializeJson.serializeForm(document.getElementById("myForm")); // In JS bundle NSerializeJson.* required, because of UMD library!

Returns:

{
  title: "Finding Loot",
  author: {
    name: "John Smith",
    job: "Legendary Pirate"
  }
}

Form input, textarea and select tags are supported. Nested attributes and arrays can be specified by using the attr[nested][nested] syntax.

HTML form:

<form id="my-profile">
  <!-- simple attribute -->
  <input type="text" name="fullName"              value="Nikolay Maev" />

  <!-- nested attributes -->
  <input type="text" name="address[city]"         value="Rostov-on-Don" />
  <input type="text" name="address[state][name]"  value="Rostov oblast'" />
  <input type="text" name="address[state][abbr]"  value="ROV" />

  <!-- array -->
  <input type="text" name="jobbies[]"             value="coding" />
  <input type="text" name="jobbies[]"             value="cycling" />

  <!-- nested arrays, textareas, checkboxes ... -->
  <textarea              name="projects[0][name]">NVal</textarea>
  <textarea              name="projects[0][language]">TypeScript</textarea>
  <input type="hidden"   name="projects[0][popular]" value="0" />
  <input type="checkbox" name="projects[0][popular]" value="1" checked />

  <textarea              name="projects[1][name]">NSerializeJson</textarea>
  <textarea              name="projects[1][language]">TypeScript</textarea>
  <input type="hidden"   name="projects[1][popular]" value="0" />
  <input type="checkbox" name="projects[1][popular]" value="1"/>

  <!-- select -->
  <select name="selectOne">
    <option value="paper">Paper</option>
    <option value="rock" selected>Rock</option>
    <option value="scissors">Scissors</option>
  </select>

  <!-- select multiple options, just name it as an array[] -->
  <select multiple name="selectMultiple[]">
    <option value="red"  selected>Red</option>
    <option value="blue" selected>Blue</option>
    <option value="yellow">Yellow</option>
	</select>
</form>

HTML form (dot separator):

<form id="my-profile">
  <!-- simple attribute -->
  <input type="text" name="fullName"              value="Nikolay Maev" />

  <!-- nested attributes -->
  <input type="text" name="address.city"         value="Rostov-on-Don" />
  <input type="text" name="address.state.name"  value="Rostov oblast'" />
  <input type="text" name="address.state.abbr"  value="ROV" />

  <!-- array -->
  <input type="text" name="jobbies[]"             value="coding" />
  <input type="text" name="jobbies[]"             value="cycling" />

  <!-- nested arrays, textareas, checkboxes ... -->
  <textarea              name="projects[0].name">NVal</textarea>
  <textarea              name="projects[0].language">TypeScript</textarea>
  <input type="hidden"   name="projects[0].popular" value="0" />
  <input type="checkbox" name="projects[0].popular" value="1" checked />

  <textarea              name="projects[1].name.">NSerializeJson</textarea>
  <textarea              name="projects[1].language">TypeScript</textarea>
  <input type="hidden"   name="projects[1].popular" value="0" />
  <input type="checkbox" name="projects[1].popular" value="1"/>

  <!-- select -->
  <select name="selectOne">
    <option value="paper">Paper</option>
    <option value="rock" selected>Rock</option>
    <option value="scissors">Scissors</option>
  </select>

  <!-- select multiple options, just name it as an array[] -->
  <select multiple name="selectMultiple[]">
    <option value="red"  selected>Red</option>
    <option value="blue" selected>Blue</option>
    <option value="yellow">Yellow</option>
	</select>
</form>

JavaScript:

NSerializeJson.serializeForm(document.getElementById("my-profile") as HTMLFormElement)

// returns =>
{
  fullName: "Nikolay Maev",

  address: {
    city: "Rostov-on-Don",
    state: {
      name: "Rostov oblast'",
      abbr: "ROV"
    }
  },

  jobbies: ["coding", "cycling"],

  projects: {
    '0': { name: "NVal", language: "TypeScript", popular: "1" },
    '1': { name: "NSerializeJson",   language: "TypeScript", popular: "0" }
  },

  selectOne: "rock",
  selectMultiple: ["red", "blue"]
}

The serializeForm function returns a JavaScript object, not a JSON String.

Parse values with :types

All attribute values are auto by default. But you can force values to be parsed with specific types by appending the type with a colon.

<form id="myForm">
  <input type="text" name="strbydefault"     value=":string is the default (implicit) type"/>
  <input type="text" name="text:string"      value=":string type can still be used to override other parsing options"/>
  <input type="text" name="excluded:skip"    value="Use :skip to not include this field in the result"/>

  <input type="text" name="numbers[0]:number"           value="0"/>
  <input type="text" name="numbers[1]:number"           value="1"/>
  
  <input type="text" name="keys[1.1]:number"         value="1.1"/>

  <input type="text" name="bools[true]:boolean"      value="true"/>
  <input type="text" name="bools[false]:boolean"     value="false"/>
  <input type="text" name="bools[zero]:boolean"         value="0"/>

  <input type="text" name="autos[string]:auto"          value="text with stuff"/>
  <input type="text" name="autos[one]:auto"               value="1"/>
  <input type="text" name="autos[two]:auto"               value="2"/>
  <input type="text" name="autos[true]:auto"            value="true"/>
  <input type="text" name="autos[false]:auto"           value="false"/>
  <input type="text" name="autos[null]:auto"            value="null"/>
  <input type="text" name="autos[list]:auto"            value='1, 2, 3, foo, bar, {"pet": "cat"}'/>
  
  <input type="text" name="arrays[empty]:array[auto]"        value=""/>
  <input type="text" name="arrays[auto]:array[auto]"         value="1, 2, 3, foo, bar"/>
  <input type="text" name="arrays[numbers]:array[number]"     value="1, 2, 3, foo, bar"/>

  <input type="text" name="json[empty]:json"       value="{}"/>
  <input type="text" name="json[not empty]:json"   value='{"my": "stuff"}'/>
</form>
NSerializeJson.serializeForm(document.getElementById("myForm") as HTMLFormElement);

// returns =>
{
	"strbydefault": ":string is the default (implicit) type",
	"text": ":string type can still be used to override other parsing options",
	"numbers": [
		0,
		1
	],
	"keys": {
		"1.1": 1.1
	},
	"bools": {
		"true": true,
		"false": false,
		"zero": false
	},
	"autos": {
		"string": "text with stuff",
		"one": 1,
		"two": 2,
		"true": true,
		"false": false,
		"null": null,
		"list": [
			1,
			2,
			3,
			"foo",
			"bar",
			{
				"pet": "cat"
			}
		]
	},
	"arrays": {
		"empty": [],
		"auto": [
			1,
			2,
			3,
			"foo",
			"bar"
		],
		"numbers": [
			1,
			2,
			3,
			null, // <-- Non-digit.
			null // <-- Non-digit.
		]
	},
	"json": {
		"empty": {},
		"not empty": {
			"my": "stuff"
		}
	}
}

Types can also be specified with the attribute data-value-type, instead of having to add the ":type" suffix:

<form>
  <input type="text" name="anumb"   data-value-type="number"  value="1"/>
  <input type="text" name="abool"   data-value-type="boolean" value="true"/>
  <input type="text" name="astring" data-value-type="string"  value="0"/>
</form>

Options

By default .serializeForm() with default options has this behavior:

  • Values are always auto (unless appending :types to the input names)
  • Unchecked checkboxes are ignored (as defined in the W3C rules for successful controls).
  • Disabled elements are ignored (W3C rules)
  • String keys are always string except the numbers

Allowed options NSerializeJson.options to change the default behavior:

  • forceNullOnEmpty: false, if true, will record null instead of empty value. Otherwise, records empties ("", 0, false).
  • useDotSeparatorInPath: false, if true allows you to use the dot notation instead of brackets in the name attribute (i.e. <input name="food.fruits[]" value="banana">).
  • useNumKeysAsArrayIndex: true, when using integers as keys (i.e. <input name="foods[0]" value="banana">), serialize as an array ({"foods": ["banana"]}) instead of an object ({"foods": {"0": "banana"}).
  • onBeforeParseValue: null, if not null, allows you to prepare the value and return it by this method with signature (value: string, type: string) => string;.

Also you may parametrize the serialization method: .serializeForm(htmlFormElement, options, parsers).

More info about options usage in the sections below.

Custom Types

You can define your own types or override the defaults with the customTypes option. For example:

<form id="myForm">
  <input type="text" name="scary:alwaysBoo" value="not boo"/>
  <input type="text" name="str:string"      value="str"/>
  <input type="text" name="number:number"   value="5"/>
</form>
NSerializeJson.parsers.push([
	{
        name: "alwaysBoo",
        parse: (val: any, forceNull: boolean): any => {
			return "boo";
        }
    }
]);

var stringParser = NSerializeJson.parsers.filter(x => x.name === "string")[0];
stringParser.parse = (val: any, forceNull: boolean): any => {
	return val + " override";
}

NSerializeJson.serializeForm(document.getElementById("myForm") as HTMLFormElement);

// returns =>
{
  "scary": "boo",        // <-- parsed with type :alwaysBoo
  "str": "str override", // <-- parsed with new type :string (instead of the default)
  "number": 5,           // <-- the default :number still works
}

The default parsers are defined in NSerializeJson.parsers. If you want to define your own set of parsers, you could also re-define that object.

Use integer keys as array indexes

By default, all serialized integer numbers are indices, so if you want to serialize it as string keys you have to set the useNumKeysAsArrayIndex: false:

<form id="myForm">
  <input type="text" name="arr[0]" value="foo"/>
  <input type="text" name="arr[1]" value="var"/>
  <input type="text" name="arr[5]" value="inn"/>
</form>
NSerializeJson.options.useNumKeysAsArrayIndex = false;
NSerializeJson.serializeForm(document.getElementById("myForm") as HTMLFormElement);
// arr is an object =>
{'arr': {'0': 'foo', '1': 'var', '5': 'inn' }}

NSerializeJson.options.useNumKeysAsArrayIndex = true;
NSerializeJson.serializeForm(document.getElementById("myForm") as HTMLFormElement);
// arr is an array =>
{'arr': ['foo', 'var', null, null, null, 'inn']}