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

keeper-js

v1.3.2

Published

English | [简体中文](./README-zh_CN.md)

Downloads

9

Readme

Keeper JS

English | 简体中文

Keeper is a library for securely accessing properties of js objects.

It generates a Keeper instance by receiving a string describing the object type. Through the API provided by this instance, we can access data of the expected safe type, or create a new object that fully complies with the type description for use.

Keeper also has excellent TypeScript support. It can generate corresponding type declaration files based on the received type description string, eliminating the need to manually create these files.

Example:

const userKeeper = createKeeper(`
  name string
  age  int    renamefrom:user_age
`);

// this type is {name: string, age: number}
const data = userKeeper.from({
  name: "bruce",
  user_age: "18.0",
});

console.log(data); // { name: 'bruce', age: 18 }
const age = userKeeper.read({ user_age: "18.2" }, "age"); // 18

📦 Install

npm i keeper-js

🔨 Usage

Type Description

Keeper defines objects by receiving a string text that describes the object, which follows the format below:

<property> <type> <extentions>
  • <property>: Property name, supporting strings or numbers.
  • <type>: Property type, which can be a basic type (such as string, int, float, see details below) or an array type (such as int[]). In addition, it also supports using *<extends> format to implement nested types.
  • <extensions> (optional): Additional descriptions of the current property, currently supporting <copyas>:<alias> (copy the current type as a new property named <alias>) and <renamefrom>:<property> (the current property value returns from the <property> property of the source object).

Each description item is separated by one or more spaces, object descriptions support multiple lines, each line describes a property, and also supports comments with //. Example:

import { createKeeper } from "keeper-js";

const userInfo = createKeeper(`
   name    string
   age     int      renamefrom:user_age
`);

const human = createKeeper(
  `
  id      int
  scores  float[]
  info    *userInfo
`,
  { extends: { userInfo } },
); // Declare the inherited attributes of userInfo.

const data = human.from({
  id: "1",
  scores: ["80.1", "90"],
  info: { name: "bruce", user_age: "18.0" },
});

// data: {
//   id: 1,
//   scores: [80.1, 90], // Transform string into float number.
//   info: {
//     name: 'bruce',
//     age:  18,   // Retrieve the value from 'user_age' and convert the float string into an integer number.
//   }
// }

Object Access

The Keeper instance provides two methods for data retrieval, from(obj) and read(obj, path), which are used to generate a new object based on the type description and source object, and to get the value of the specified path in the source object according to the type description, respectively.

When we need to safely get a value from an object, we can use the read API to operate, for example:

const sourceData = {
  id: "1",
  scores: ["80.1", "90"],
  info: { name: "bruce", user_age: "18.0" },
};
const name = human.read(sourceData, "id"); // 1

This method supports multi-layer nested access, for example:

const userInfo = createKeeper(`
   name    string
   age     int      renamefrom:user_age
`);

const human = createKeeper(
  `
  id       int
  bros     *userInfo[]
  baseInfo *userInfo
`,
  { extends: { userInfo } },
); // Declare the inherited attributes of userInfo.

const sourceData = {
  id: "1",
  bros: [
    { name: "bro1", user_age: "16.0" },
    { name: "bro2", user_age: "17.2" },
  ],
  info: { name: "bruce", user_age: "18.1" },
};
const name = human.read(sourceData, "info.name"); // 'bruce'
const bro1Name = human.read(sourceData, "bros[0].name"); // 'bro1'

When we expect to correct from the source data and get an object that fully conforms to the type declaration definition, we can use the from API to operate, for example:

const sourceData = {
  id: "1",
  bros: [],
  info: { name: "bruce", user_age: "18.1" },
};
human.from(sourceData); // { id: 1, bros: [], { name: 'bruce', age: 18 } }

Note that when the original data is empty and the corresponding declared property is not an empty type (null|undefined), a default value will be given according to the declared type, for example:

const sourceData = {
  id: "1",
  bros: [],
  info: {},
};
human.from(sourceData); // { id: 1, bros: [], { name: '', age: 0 } }
human.read(sourceData, "bros[0].age"); // 0

Typescript Support

Keeper has good ts support. You can get ts types from the defined keeper instance through the exported DefineKeeperInterface type. Monosnap screencast 2024-02-24 01-12-58

In addition, the from() and read() methods also have good ts support: Monosnap screencast 2024-02-24 01-22-08 Monosnap screencast 2024-02-24 01-23-19

Lazy Parsing

The second parameter of createKeeper can be set to lazy as true. In this way, the Keeper will parse the type only at the first access, rather than parsing it at creation.

const userInfo = createKeeper(
  `
  name    string
  age     int      renamefrom:user_age
`,
  { lazy: true },
);

userInfo.properties.has("name"); // false
userInfo.get({ name: "bruce", user_age: "18.0" }, "name");
userInfo.properties.has("name"); // true

The supported types

| Data Type | JS Type | Default | Remarks | | --------- | --------- | --------- | ------------------- | | bool | boolean | false | - | | int | number | 0 | Integer type | | float | number | 0 | Floating point type | | string | string | '' | - | | null | null | null | - | | undefined | undefined | undefined | - | | func | Function | () => {} | - | | object | Object | {} | - |

Benchmark

Files: benchmark/index.js

result: benchmark.html lazy.api.html

License

MIT