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

@ibyra/angico

v1.0.6

Published

A small JSX async-rendering library.

Downloads

21

Readme

Angico

A small JSX async-rendering library.

View on NPM License

Installation

Use the npm package manager or bun runtime to install Angico

npm i @ibyra/angico
bun i @ibyra/angico

Usage

Setting up the configuration

Firstly, you'll need to configure your JSX transformer to use Angico.

If you are using Typescript, you'll need to set the JSX properties your tsconfig.json as follow:

{
  "jsx": "react-jsx",
  "jsxImportSource": "@ibyra/angico"
}

If you are using other transpiler, like Babel, you can use these pragma comments on the top of the your source file.

/** @jsxImportSource @ibyra/angico */

var descriptions = items.map((item) => (
  <>
    <dt>{item.name}</dt>
    <dd>{item.value}</dd>
  </>
));

Authoring JSX

After setting up the configuration, using Angico is very similar to any other JSX library. You can create and compose your components/fragments, even if they are asynchronous.

function Input(props: { type: 'text' | 'number' }): JSX.Element {
  return <input type={props.type} />;
}

type BoxProps = {
  width: JSX.StringNumber;
  height: JSX.StringNumber;
  children?: JSX.Children;
};

async function AsyncBox(props: BoxProps): JSX.AsyncElement {
  const { height, width, children } = props;
  const style = `height: ${height}px; width: ${width}px`;
  await timeout(10);
  return (
    <div style={style} class="box">
      {timeout(10).then(() => children)}
    </div>
  );
}

// Just to here to simulate an asynchronous operation
function timeout(ms: number): Promise<number> {
  return new Promise((resolve) => setTimeout(resolve, ms, ms));
}

const box = (
  <AsyncBox height="100" width="100">
    <Input type="number" />
    Type a number.
    <button type="submit">Submit</button>
  </AsyncBox>
);

console.log(box); // FunctionElement { ... }

As you can see, the JSX does not return an rendered version, but a instance of FunctionElement instead. This is because Angico does not renders anything immediately, only when it is required to do so.

Rendering JSX into a string

You can request an JSX element to render into a string using the render function, also available on Angico package.

import { render } from '@ibyra/angico';

// ...

const box = (
  <AsyncBox height="100" width="100">
    <Input type="number" />
    Type a number.
    <button type="submit">Submit</button>
  </AsyncBox>
);

const rendered = await render(box);

const expected = `<div style="height: 100px; width: 100px" class="box"><input type="number"/>Type a number.<button type="submit">Submit</button></div>`;

assert(rendered === expected);

HTML, SVG, MathML, XML…

You can use Angico to render any XML markup you desire. You can use SVG out of the box!

import Angico from '@ibyra/angico';

export type IconProps = JSX.SVGSVGTag & {
  fill?: string;
};

// The "envelope-simple" icon provided by @phosphor-icons/core
// https://github.com/phosphor-icons/core
export function EnvelopeSimple(props: IconProps): JSX.Element {
  const {
    fill = 'currentColor',
    height = '1.5em',
    width = '1.5em',
    ...rest
  } = props;
  return (
    <svg
      width={width}
      height={height}
      aria-hidden="true"
      inert
      {...rest}
      viewBox="0 0 256 256"
    >
      <path
        fill={fill}
        d="M224 48H32a8 8 0 0 0-8 8v136a16 16 0 0 0 16 16h176a16 16 0 0 0 16-16V56a8 8 0 0 0-8-8Zm-20.57 16L128 133.15L52.57 64ZM216 192H40V74.19l82.59 75.71a8 8 0 0 0 10.82 0L216 74.19V192Z"
      />
    </svg>
  );
}

[!WARNING] The current support for SVG and MathML is limited, only a few elements and attributes are defined. We aim to improve the support in the future.

Extending type definitions

Sometimes you want to extend the definitions of the JSX available intrinsic elements; e.g, when you are using an attribute-based JS library like HTMX or Alpine.js, or when you have some custom elements in your markup. You can extend the JSX.IntrinsicElements or HTMLAttributes interfaces with your custom definitions.

declare global {
  namespace JSX {
    interface HTMLAttributes {
      // HTMX attributes
      [hx: `hx-${string}`]: string | boolean;
    }

    interface OpenableAttributes extends HTMLAttributes {
      open?: boolean;
    }

    interface IntrinsicElements {
      ['my-custom-component']: OpenableAttributes;
    }
  }
}

Roadmap

  • Improve HTML elements and attributes typings;
  • Improve support for WAI-ARIA attributes typings;
  • Support all SVG elements and attributes typings;
  • Support all MathML elements and attributes typings;
  • Support streamed rendering;

Contributing

Pull requests are welcome. For major changes, please open an issue first to discuss what you would like to change.

Please make sure to update tests as appropriate.

License

MIT © Ibyra