New Case Study:See how Anthropic automated 95% of dependency reviews with Socket.Learn More
Socket
Sign inDemoInstall
Socket

@adobe/rum-distiller

Package Overview
Dependencies
Maintainers
0
Versions
24
Alerts
File Explorer

Advanced tools

Socket logo

Install Socket

Detect and block malicious and high-risk dependencies

Install

@adobe/rum-distiller - npm Package Compare versions

Comparing version 1.0.0 to 1.1.0

distiller.js

7

CHANGELOG.md

@@ -0,1 +1,8 @@

# [1.1.0](https://github.com/adobe/rum-distiller/compare/v1.0.0...v1.1.0) (2024-10-08)
### Features
* **index:** allow single entry point in main.js ([3d2df08](https://github.com/adobe/rum-distiller/commit/3d2df08d0c04e17742aa7eafafcb55ac2b6c440a))
# 1.0.0 (2024-10-08)

@@ -2,0 +9,0 @@

3

package.json
{
"name": "@adobe/rum-distiller",
"version": "1.0.0",
"version": "1.1.0",
"scripts": {

@@ -13,2 +13,3 @@ "test": "node --test --experimental-test-coverage --test-reporter=lcov --test-reporter-destination=../../lcov.info --test-reporter=spec --test-reporter-destination=stdout --test-reporter=junit --test-reporter-destination=../../junit.xml",

"type": "module",
"main": "index.js",
"license": "Apache-2.0",

@@ -15,0 +16,0 @@ "devDependencies": {

import { describe, it } from 'node:test';
import assert from 'node:assert/strict';
import { roundToConfidenceInterval, samplingError } from '../utils.js';
import { roundToConfidenceInterval, samplingError } from '../stats.js';
describe('samplingError', () => {

@@ -6,0 +7,0 @@ it('computes the sampling error', () => {

import { describe, it } from 'node:test';
import assert from 'node:assert/strict';
import {
escapeHTML, computeConversionRate, isKnownFacet,
computeConversionRate, isKnownFacet,
} from '../utils.js';
describe('escapeHTML', () => {
it('escapes HTML entities', () => {
assert.strictEqual(escapeHTML('<script>alert("xss")</script>'), '&#60;script&#62;alert(&#34;xss&#34;)&#60;/script&#62;');
assert.strictEqual(escapeHTML("<script>alert('xss')</script>"), '&#60;script&#62;alert(&#39;xss&#39;)&#60;/script&#62;');
assert.strictEqual(escapeHTML('<div>hello</div>'), '&#60;div&#62;hello&#60;/div&#62;');
});
});
describe('computeConversionRate', () => {

@@ -16,0 +8,0 @@ it('its 10% for 1 conversion and 10 visits', () => {

@@ -196,73 +196,3 @@ import classifyConsent from './consent.js';

export function escapeHTML(unsafe) {
return unsafe.replace(/[&<>"']/g, (c) => `&#${c.charCodeAt(0)};`);
}
export function cssVariable(name) {
return getComputedStyle(document.documentElement).getPropertyValue(name);
}
let gradient;
let width;
let height;
export function getGradient(ctx, chartArea, from, to) {
const chartWidth = chartArea.right - chartArea.left;
const chartHeight = chartArea.bottom - chartArea.top;
if (!gradient || width !== chartWidth || height !== chartHeight) {
// Create the gradient because this is either the first render
// or the size of the chart has changed
width = chartWidth;
height = chartHeight;
gradient = ctx.createLinearGradient(0, chartArea.bottom, 0, chartArea.top);
gradient.addColorStop(0, from);
gradient.addColorStop(1, to);
}
return gradient;
}
/**
* Function used for filtering wanted parameters. Its implementation depends on the context,
* for instance when parsing for conversion parameters we care about those that start with
* `conversion.`.
* @function filterFn
* @param {string} paramName - The parameter name.
* @returns {boolean} - Returns true if the parameter will be further parsed, false otherwise.
*/
/**
* In some cases, it may just be that the parameters need to be transformed in some way.
* For instance, when parsing conversion parameters we want to remove the `conversion.` prefix
* from the parameter name.
* @function transformFn
* @param {[string, string]} paramPair - The pair of parameter name and its value.
* @returns {[string, string]} - The result of the transformation.
*/
/**
* Parse search parameters and return a dictionary.
* @param {URLSearchParams} params - The search parameters.
* @param {filterFn} filterFn - The filtering function.
* @param {transformFn} transformFn - The transformation function.
* @returns {Object<string, string[]>} - The dictionary of parameters.
*/
export function parseSearchParams(params, filterFn, transformFn) {
return Array.from(params
.entries())
.filter(filterFn)
.map(transformFn)
.reduce((acc, [key, value]) => {
if (acc[key]) acc[key].push(value);
else acc[key] = [value];
return acc;
}, {});
}
const cached = {};
export function parseConversionSpec() {
if (cached.conversionSpec) return cached.conversionSpec;
const params = new URL(window.location).searchParams;
const transform = ([key, value]) => [key.replace('conversion.', ''), value];
const filter = ([key]) => (key.startsWith('conversion.'));
cached.conversionSpec = parseSearchParams(params, filter, transform);
return cached.conversionSpec;
}
/**
* Conversion rates are computed as the ratio of conversions to visits. The conversion rate is

@@ -282,75 +212,2 @@ * capped at 100%.

/**
* Determines the sampling error based on a binomial distribution.
* Each sample is a Bernoulli trial, where the probability of success is the
* proportion of the total population that has the attribute of interest.
* The sampling error is calculated as the standard error of the proportion.
* @param {number} total the expectation value of the total population
* @param {number} samples the number of successful trials (i.e. samples)
*/
export function samplingError(total, samples) {
if (samples === 0) {
return 0;
}
const weight = total / samples;
const variance = weight * weight * samples;
const standardError = Math.sqrt(variance);
const marginOfError = 1.96 * standardError;
// round up to the nearest integer
return Math.round(marginOfError);
}
const vulgarFractions = {
0: '0',
0.125: '⅛',
0.2: '⅕',
0.25: '¼',
0.333: '⅓',
0.375: '⅜',
0.5: '½',
0.625: '⅝',
0.666: '⅔',
0.75: '¾',
0.8: '⅘',
0.875: '⅞',
1: '1',
};
export function findNearestVulgarFraction(fraction) {
const closest = Object.keys(vulgarFractions).reduce((acc, key) => {
if (Math.abs(fraction - key) < Math.abs(fraction - acc)) {
return key;
}
return acc;
}, 0);
return vulgarFractions[closest];
}
export function roundToConfidenceInterval(
total,
samples = total,
maxPrecision = Infinity,
) {
const max = total + samplingError(total, samples);
const min = total - samplingError(total, samples);
// determine the number of significant digits that max and min have in common
// e.g. 3.14 and 3.16 have 2 significant digits in common
const maxStr = max.toPrecision(`${max}`.length);
const minStr = min.toPrecision(`${min}`.length);
const common = Math.min(maxStr.split('').reduce((acc, digit, i) => {
if (digit === minStr[i]) {
return acc + 1;
}
return acc;
}, 0), Number.isNaN(maxPrecision) ? Infinity : maxPrecision);
const precision = Math.max(
Math.min(2, Number.isNaN(maxPrecision) ? Infinity : maxPrecision),
common,
);
const rounded = toHumanReadable(total, precision);
return rounded;
}
export function reclassifyConsent({ source, target, checkpoint }) {

@@ -411,1 +268,28 @@ if (checkpoint === 'click' && source) {

}
/**
* Calculates properties on the bundle, so that bundle-level filtering can be performed
* @param {RawBundle} bundle the raw input bundle, without calculated properties
* @returns {Bundle} a bundle with additional properties
*/
export function addCalculatedProps(bundle) {
bundle.events.forEach((e) => {
if (e.checkpoint === 'enter') {
bundle.visit = true;
if (e.source === '') e.source = '(direct)';
}
if (e.checkpoint === 'cwv-inp') {
bundle.cwvINP = e.value;
}
if (e.checkpoint === 'cwv-lcp') {
bundle.cwvLCP = Math.max(e.value || 0, bundle.cwvLCP || 0);
}
if (e.checkpoint === 'cwv-cls') {
bundle.cwvCLS = Math.max(e.value || 0, bundle.cwvCLS || 0);
}
if (e.checkpoint === 'cwv-ttfb') {
bundle.cwvTTFB = e.value;
}
});
return bundle;
}
SocketSocket SOC 2 Logo

Product

  • Package Alerts
  • Integrations
  • Docs
  • Pricing
  • FAQ
  • Roadmap
  • Changelog

Packages

npm

Stay in touch

Get open source security insights delivered straight into your inbox.


  • Terms
  • Privacy
  • Security

Made with ⚡️ by Socket Inc