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

@quantum-metric/plugin-analytics-module-qm

v1.0.2

Published

Welcome to the Quantum Metric Analytics Plugin for Backstage! This plugin aims to provide a quick and robust means to integrate Quantum Metric analytics with your Backstage instance.

Downloads

6

Readme

Analytics Module: Quantum Metric

Welcome to the Quantum Metric Analytics Plugin for Backstage! This plugin aims to provide a quick and robust means to integrate Quantum Metric analytics with your Backstage instance.

QM Platform

This plugin requires an account with Quantum Metric

Installation

Install the plugin

yarn --cwd packages/app add @quantum-metric/plugin-analytics-module-qm

Open the packages/app/src/apis.ts file and import the required dependencies

import {
  analyticsApiRef,
  configApiRef,
  identityApiRef,
} from '@backstage/core-plugin-api';
import { QuantumMetric } from '@quantum-metric/plugin-analytics-module-qm';

Next, add the following code to packages/app/src/apis.ts to create the Quantum Metric Analytics API

  createApiFactory({
    api: analyticsApiRef,
    deps: { configApi: configApiRef, identityApi: identityApiRef },
    factory: ({ configApi, identityApi }) =>
      QuantumMetric.fromConfig(configApi, {
        identityApi,
      }),
  }),

Configuration

After installing the plugin, the Quantum Metric Analytics plugin will need to be configured. The options and reference example are detailed below.

Configuration Options

The table below lists the available configuration options for the Quantum Metric Analytics plugin:

| Field Name | Type | Required | Default | Description | | ----------------- | ------------------------------------- | -------- | ------- | ---------------------------------------------------------------------------------------------------------------- | | enabled | boolean | Yes | | Disables plugin. | | src | string | Yes | | CDN location of Quantum Metric API. The value is qtm.src on your subscriptions Install page. | | debug | boolean | No | false | Turns on console.debug messages. | | test | boolean | No | false | When enabled, events are logged to console instead of sent to Quantum Metric. | | async | boolean | No | false | Sets the async attribute of the resulting HTML <script> element. | | events.mappings | list of {name: string, id: integer} | Yes | {} | Maps Backstage AnalyticsEvent actions to Quantum Metric Event ID's as a list of objects with name and id. | | events.attributes | list of {name: string, value: string} | Yes | {} | Included on every event sent to Quantum Metric under Event Details as a list of objects with name and value. |

Example Configuration

Below is a reference configuration file:

app:
analytics:
  qm:
    enabled: true
    src: https://cdn.quantummetric.com/qscripts/quantum-$SUB_NAME.js
    debug: false
    test: false
    async: false
    events:
      mappings:
        - name: navigate
          id: $QUANTUM_NAVIGATE_EVENT_ID
        - name: click
          id: $QUANTUM_CLICK_EVENT_ID
        - name: search
          id: $QUANTUM_SEARCH_EVENT_ID
        - name: discover
          id: $QUANTUM_DISCOVER_EVENT_ID
      attributes:
        - name: environment
          value: development
        - name: version
          value: 0.0.1

Where the event mappings IDs are the Quantum Metric event IDs you wish to send.

Event Transformers

The plugin comes with default Event Transformers for each predefined Backstage key event as described in Default Transformers. However, you can customize or extend these transformers. To override a default transformer or add transformers for new actions, modify the Analytics API configuration as follows:

  createApiFactory({
    api: analyticsApiRef,
    deps: { configApi: configApiRef },
    factory: ({ configApi }) =>
      QuantumMetric.fromConfig(configApi, {
        eventTransforms: {
          discover: (event, mapping) => {
            return { eventId: mapping[event.action], eventValue: event.attributes.to, attributes: { ...event.attributes, event.subject } };
          },
        },
      }),
  })

In the above example, the default transformer for the discover key event is overridden. The value sent to Quantum Metric is changed to event.attributes.to instead of the provided event.subject, and the event.subject is added as an attribute.

Default Transformers

There is a transformer for every Backstage key event, and a default transformer when an action is not found in the eventTransforms record. The definitions can be found in src/api/util/transforms.ts.

| Backstage Analytics Action | Quantum Metric Event ID | Quantum Metric Event Value | Quantum Metric Event Attributes | Quantum Metric Event Conversion | | -------------------------- | ------------------------------------------ | ------------------------------------------------------------ | ------------------------------------------------------------------------------------------ | ------------------------------- | | sendEvent | Set to Backstage event subject | Set to Backstage event value | Event attributes | Set to false | | navigate | Mapped from configuration event.mappings | Set to Backstage event subject | Combined attributes from context and event attributes | Set to false | | search | Mapped from configuration event.mappings | Set to Backstage event subject | Combined attributes from context, event attributes, and results-found from event value | Set to false | | discover | Mapped from configuration event.mappings | Set to Backstage event subject | Combined attributes from context, event attributes, and search-position from event value | Set to false | | click | Mapped from configuration event.mappings | Set to Backstage event subject | Combined attributes from context and event attributes | Set to false | | defaultEventTransform | Mapped from configuration event.mappings | Set to Backstage event value and if not present then subject | Combined attributes from context and event attributes | Set to false |

Identity

To configure identity from Backstage to Quantum Metric provide the IdentityAPI to the plugin like so:

  createApiFactory({
    api: analyticsApiRef,
    deps: { configApi: configApiRef },
    factory: ({ configApi, identityApi }) =>
      QuantumMetric.fromConfig(configApi, {
        identityApi
      }),
  }),

This will identify users in Quantum Metric by their Backstage profile email.

Global Attributes

Global attributes allow you to add attributes to all events sent through the Quantum Metric analytics plugin. When configured, these attributes will be included in the event details in Quantum Metric.

To configure global attributes, use the following format in your configuration file:

app:
  analytics:
    qm:
      events:
        attributes:
          - name: environment
            value: development
          - name: version
            value: 0.0.1

With the above configuration, the event details in Quantum Metric will include the following attributes:

{
  "environment": "development",
  "version": "0.0.1"
}

If the event is generated from Backstage events and includes attributes via the event transformers, those attributes will also be included along with the global attributes.

For example, if a search event is triggered with the default event transformer it includes the attribute results-found and also has the global attributes configured, the event details will look like this:

{
  "results-found": 10,
  "environment": "development",
  "version": "0.0.1"
}

Note: In the case of attribute name collisions between global attributes and event-specific attributes, the global attributes will take precedence and be included in the event details.

Capturing Events

With the Quantum Metric plugin fully installed and configured, Backstage key events will be captured without extra effort.

Instrumenting events

To send events that are defined in the configuration's event mappings or event transformers, you can use the useAnalytics hook provided by @backstage/core-plugin-api.

Here's an example of capturing a basic event:

import { useAnalytics } from '@backstage/core-plugin-api';

const analytics = useAnalytics();

analytics.captureEvent('catalog-updated', catalogEntityName);

If you want to add more information sent to Quantum Metric, you can include additional attributes:

analytics.captureEvent('catalog-updated', catalogEntityName {
  value: numOfEntitiesUpdated,
  attributes: {
    entityOwner,
    entityType,
    userTeam,
  },
});

These additional attributes will show up under the events details in Quantum Metric.

The specific configuration for the catalog-updated event can be defined either in the event mappings or with an event transformer.

Example event mappings configuration:

app:
analytics:
  qm:
    events:
      mappings:
        - name: catalog-updated
          id: $QUANTUM_METRIC_CATALOG_UPDATED_EVENT_ID

Alternatively, the default event transformer can be extended to capture more attributes for catalog-updated:

  createApiFactory({
    api: analyticsApiRef,
    deps: { configApi: configApiRef },
    factory: ({ configApi }) =>
      QuantumMetric.fromConfig(configApi, {
        eventTransforms: {
          'catalog-updated': (event, mapping) => {
            return {
                eventId: mapping[event.action],
                eventValue: event.subject,
                attributes: { ...event.attributes, ...event.context, numberOfAffectedEntities: event.value }
            };
          },
        },
      }),
  })

Context

Additional information can also be added to Quantum Metric event details with the context React component.

import { AnalyticsContext, useAnalytics } from '@backstage/core-plugin-api';

const GreetingComponent = ({ name }) => {
  const analytics = useAnalytics();
  const handleClick = () => analytics.captureEvent('greeted', name);
  return <button onClick={handleClick}>Say Hello to {name}</button>;
};

const GreetingComponentWrapper = () => {
  return (
    <AnalyticsContext attributes={{ admin: true }}>
      <GreetingComponent name={'Alice'} />
    </AnalyticsContext>
  );
};

When the GreetingComponent button is clicked, it will send a greeted event to Quantum Metric with the value of Alice, and the event details will include information about Alice being an admin.

Contributing

Before submitting your pull request, ensure your title follows the semantic commit format. This not only helps our maintainers but also improves the overall transparency and readability of our project history.

For more detailed contributions guidelines, check our CONTRIBUTING.md file.

Local Development

Install dependencies

yarn install

Build dist folder

yarn build

From your Backstage directory run the following where $INSTALL_PATH is the path of this repo

yarn add @quantum-metric/plugin-analytics-module-qm@link:$INSTALL_PATH

Note: If making changes to config.d.ts against a Backstage instance started with backstage-cli package start, changes will not take effect till the next backstage-cli package start

Semantic Commit Messages

In this project, we enforce the use of semantic commit messages to streamline our release and changelog generation process. This ensures our commit history is readable and understandable.

What are Semantic Commit Messages?

Semantic commit messages follow a structured format to clearly describe the purpose and intent of each commit. The general format is:

  • <type>: This denotes the kind of change you're making. Common types include feat (new features), fix (bug fixes), docs (documentation changes), style (code styling, no functional changes), refactor (code changes that neither fix bugs nor add features), perf (performance improvements), test (adding missing tests), and chore (maintenance tasks).

  • <scope>: A scope provides additional contextual information, such as the part of the codebase affected (optional).

  • <description>: A brief, imperative mood description of the change.

Examples:

  • feat(auth): implement JWT authentication
  • fix(server): resolve memory leak issue
  • chore(readme): update installation instructions

Enforcing Semantic Commits

This project uses the amannn/action-semantic-pull-request GitHub Action to ensure all pull requests follow the semantic commit format. The action checks your pull request titles, not the individual commit messages. Make sure your PR titles follow the semantic format.

If your pull request title does not meet the semantic requirements, the check will fail, and you'll need to update the title accordingly. You can also add multiple types if your pull request covers more than one scope, separated by commas (e.g., feat, fix: implement new feature and fix a bug).

Semantic Versioning

Semantic versioning works by interpreting your semantic commit as described in the previous section and assigning it a classification based on the level of severity of the work. That classification then translates into a version number that follows the sequence: Major.Minor.Patch.

When a major, minor, or patch update is made, the corresponding number is increased.

  • Major version changes when incompatible API changes are made.
  • Minor version changes when new functionality is added backward-compatible manner.
  • Patch version changes when backward-compatible bug fixes are made.

The table below describes the relationship between the semantic commit message and the semantic version sequence:

| Commit Message | Inferred Type | Example Sequence Update | | ------------------------------------------------- | ------------- | ----------------------- | | feat(auth): implement JWT authentication | Major | 1.0.0 | | fix(server): resolve memory leak issue | Minor | 0.1.0 | | chore(readme): update installation instructions | Patch | 0.0.1 |