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

@accordproject/concerto-tools

Package Overview
Dependencies
Maintainers
6
Versions
697
Alerts
File Explorer

Advanced tools

Socket logo

Install Socket

Detect and block malicious and high-risk dependencies

Install

@accordproject/concerto-tools - npm Package Compare versions

Comparing version 3.1.0 to 3.1.1-20221215162924

lib/codegen/fromcto/avro/avrovisitor.js

10

lib/codegen/codegen.js

@@ -31,2 +31,6 @@ /*

const ProtobufVisitor = require('./fromcto/protobuf/protobufvisitor');
const OpenApiVisitor = require('./fromcto/openapi/openapivisitor');
const AvroVisitor = require('./fromcto/avro/avrovisitor');
const InferFromJsonSchema = require('./fromJsonSchema/cto/inferModel');

@@ -48,2 +52,4 @@

ProtobufVisitor,
OpenApiVisitor,
AvroVisitor,
InferFromJsonSchema,

@@ -62,4 +68,6 @@ formats: {

markdown: MarkdownVisitor,
protobuf: ProtobufVisitor
protobuf: ProtobufVisitor,
openapi: OpenApiVisitor,
avro: AvroVisitor
}
};

@@ -61,2 +61,4 @@ /*

return this.visitClassDeclaration(thing, parameters);
} else if (thing.isTypeScalar?.()) {
return this.visitField(thing.getScalarField(), parameters);
} else if (thing.isField?.()) {

@@ -68,2 +70,4 @@ return this.visitField(thing, parameters);

return this.visitEnumValueDeclaration(thing, parameters);
} else if (thing.isScalarDeclaration?.()) {
return;
} else {

@@ -70,0 +74,0 @@ throw new Error('Unrecognised type: ' + typeof thing + ', value: ' + util.inspect(thing, {

@@ -52,2 +52,4 @@ /*

return this.visitClassDeclaration(thing, parameters);
} else if (thing.isTypeScalar?.()) {
return this.visitField(thing.getScalarField(), parameters);
} else if (thing.isField?.()) {

@@ -59,2 +61,4 @@ return this.visitField(thing, parameters);

return this.visitEnumValueDeclaration(thing, parameters);
} else if (thing.isScalarDeclaration?.()) {
return;
} else {

@@ -233,3 +237,4 @@ throw new Error('Unrecognised type: ' + typeof thing + ', value: ' + util.inspect(thing, { showHidden: true, depth: null }));

containsDateTimeField(modelFile) {
let classDeclarations = modelFile.getAllDeclarations();
let classDeclarations = modelFile.getAllDeclarations()
.filter(declaration => !declaration.isScalarDeclaration?.());
for(let n=0; n < classDeclarations.length; n++) {

@@ -236,0 +241,0 @@ let classDecl = classDeclarations[n];

@@ -50,2 +50,4 @@ /*

return this.visitModelFile(thing, parameters);
} else if (thing.isTypeScalar?.()) {
return this.visitField(thing.getScalarField(), parameters);
} else if (thing.isField?.()) {

@@ -59,2 +61,4 @@ return this.visitField(thing, parameters);

return this.visitClassDeclaration(thing, parameters);
} else if (thing.isScalarDeclaration?.()) {
return;
}

@@ -61,0 +65,0 @@ else {

@@ -54,2 +54,4 @@ /*

return this.visitClassDeclaration(thing, parameters);
} else if (thing.isTypeScalar?.()) {
return this.visitField(thing.getScalarField(), parameters);
} else if (thing.isField?.()) {

@@ -61,2 +63,4 @@ return this.visitField(thing, parameters);

return this.visitEnumValueDeclaration(thing, parameters);
} else if (thing.isScalarDeclaration?.()) {
return;
} else {

@@ -63,0 +67,0 @@ throw new Error('Unrecognised type: ' + typeof thing + ', value: ' + util.inspect(thing, { showHidden: true, depth: 2 }));

125

lib/codegen/fromcto/jsonschema/jsonschemavisitor.js

@@ -33,2 +33,5 @@ /*

*
* The default value for refRoot is '#/definitions'. Set the refRoot parameter
* to override.
*
* The meta schema used is http://json-schema.org/draft-07/schema#

@@ -59,2 +62,55 @@ *

/**
* Get the validators for a field or a scalar definition in JSON schema form.
* @param {Object} field - the scalar declaration being visited
* @return {Object} the result of visiting or null
* @private
*/
getFieldOrScalarDeclarationValidatorsForSchema(field) {
const validator = field.getValidator();
let jsonSchema = {};
switch (field.getType()) {
case 'String':
jsonSchema.type = 'string';
if(validator) {
// Note that regex flags are lost in this transformation
jsonSchema.pattern = validator.getRegex().source;
}
break;
case 'Double':
jsonSchema.type = 'number';
if(validator) {
if(validator.getLowerBound() !== null) {
jsonSchema.minimum = validator.getLowerBound();
}
if(validator.getUpperBound() !== null) {
jsonSchema.maximum = validator.getUpperBound();
}
}
break;
case 'Integer':
case 'Long':
jsonSchema.type = 'integer';
if(validator) {
if(validator.getLowerBound() !== null) {
jsonSchema.minimum = Math.trunc(validator.getLowerBound());
}
if(validator.getUpperBound() !== null) {
jsonSchema.maximum = Math.trunc(validator.getUpperBound());
}
}
break;
case 'DateTime':
jsonSchema.format = 'date-time';
jsonSchema.type = 'string';
break;
case 'Boolean':
jsonSchema.type = 'boolean';
break;
}
return jsonSchema;
}
/**
* Returns true if the class declaration contains recursive references.

@@ -97,2 +153,4 @@ *

return this.visitClassDeclaration(thing, parameters);
} else if (thing.isTypeScalar?.()) {
return this.visitField(thing.getScalarField(), parameters);
} else if (thing.isField?.()) {

@@ -102,2 +160,4 @@ return this.visitField(thing, parameters);

return this.visitRelationshipDeclaration(thing, parameters);
} else if (thing.isScalarDeclaration?.()) {
return this.visitScalarDeclaration(thing, parameters);
} else if (thing.isEnumValue?.()) {

@@ -277,2 +337,17 @@ return this.visitEnumValueDeclaration(thing, parameters);

* Visitor design pattern
* @param {ScalarDeclaration} scalarDeclaration - the object being visited
* @param {Object} parameters - the parameter
* @return {Object} the result of visiting or null
* @private
*/
visitScalarDeclaration(scalarDeclaration, parameters) {
debug('entering visitScalarDeclaration', scalarDeclaration.getName());
return {
$id: scalarDeclaration.getFullyQualifiedName(),
schema: this.getFieldOrScalarDeclarationValidatorsForSchema(scalarDeclaration)
};
}
/**
* Visitor design pattern
* @param {Field} field - the object being visited

@@ -289,5 +364,2 @@ * @param {Object} parameters - the parameter

if (field.isPrimitive()) {
const validator = field.getValidator();
// Render the type as JSON Schema.

@@ -300,41 +372,6 @@ jsonSchema = {};

switch (field.getType()) {
case 'String':
jsonSchema.type = 'string';
if(validator) {
// Note that regex flags are lost in this transformation
jsonSchema.pattern = validator.getRegex().source;
}
break;
case 'Double':
jsonSchema.type = 'number';
if(validator) {
if(validator.getLowerBound() !== null) {
jsonSchema.minimum = validator.getLowerBound();
}
if(validator.getUpperBound() !== null) {
jsonSchema.maximum = validator.getUpperBound();
}
}
break;
case 'Integer':
case 'Long':
jsonSchema.type = 'integer';
if(validator) {
if(validator.getLowerBound() !== null) {
jsonSchema.minimum = Math.trunc(validator.getLowerBound());
}
if(validator.getUpperBound() !== null) {
jsonSchema.maximum = Math.trunc(validator.getUpperBound());
}
}
break;
case 'DateTime':
jsonSchema.format = 'date-time';
jsonSchema.type = 'string';
break;
case 'Boolean':
jsonSchema.type = 'boolean';
break;
}
jsonSchema = {
...jsonSchema,
...this.getFieldOrScalarDeclarationValidatorsForSchema(field)
};

@@ -356,3 +393,4 @@ // If this field has a default value, add it.

if(!parameters.inlineTypes) {
jsonSchema = { $ref: `#/definitions/${type.getFullyQualifiedName()}` };
const refRoot = parameters.refRoot ? parameters.refRoot : '#/definitions';
jsonSchema = { $ref: `${refRoot}/${type.getFullyQualifiedName()}` };
} else {

@@ -463,5 +501,4 @@ // inline the schema

}
}
module.exports = JSONSchemaVisitor;

@@ -48,2 +48,6 @@ /*

return this.visitClassDeclaration(thing, parameters);
} else if (thing.isScalarDeclaration?.()) {
return false;
} else if (thing.isTypeScalar?.()) {
return this.visitField(thing.getScalarField(), parameters);
} else if (thing.isField?.()) {

@@ -50,0 +54,0 @@ return this.visitField(thing, parameters);

@@ -74,2 +74,4 @@ /*

return this.visitEnumDeclaration(thing, parameters);
} else if (thing.isTypeScalar?.()) {
return this.visitField(thing.getScalarField(), parameters);
} else if (thing.isField?.()) {

@@ -76,0 +78,0 @@ return this.visitField(thing, parameters);

@@ -51,2 +51,4 @@ /*

return this.visitClassDeclaration(thing, parameters);
} else if (thing.isTypeScalar?.()) {
return this.visitField(thing.getScalarField(), parameters);
} else if (thing.isField?.()) {

@@ -58,2 +60,4 @@ return this.visitField(thing, parameters);

return this.visitEnumValueDeclaration(thing, parameters);
} else if (thing.isScalarDeclaration?.()) {
return;
} else {

@@ -242,2 +246,2 @@ throw new Error('Unrecognised ' + JSON.stringify(thing) );

module.exports = MermaidVisitor;
module.exports = MermaidVisitor;

@@ -65,2 +65,4 @@ /*

return this.visitClassDeclaration(thing, parameters);
} else if (thing.isTypeScalar?.()) {
return this.visitField(thing.getScalarField(), parameters);
} else if (thing.isField?.()) {

@@ -74,2 +76,4 @@ return this.visitField(thing, parameters);

return this.visitDecorator(thing, parameters);
} else if (thing.isScalarDeclaration?.()) {
return;
} else {

@@ -76,0 +80,0 @@ throw new Error('Unrecognised ' + JSON.stringify(thing));

@@ -52,2 +52,4 @@ /*

return this.visitClassDeclaration(thing, parameters);
} else if (thing.isTypeScalar?.()) {
return this.visitField(thing.getScalarField(), parameters);
} else if (thing.isField?.()) {

@@ -59,2 +61,4 @@ return this.visitField(thing, parameters);

return this.visitEnumValueDeclaration(thing, parameters);
} else if (thing.isScalarDeclaration?.()) {
return;
} else {

@@ -61,0 +65,0 @@ throw new Error('Unrecognised ' + JSON.stringify(thing) );

@@ -19,2 +19,3 @@ /*

const util = require('util');
const ModelUtil = require('@accordproject/concerto-core').ModelUtil;

@@ -37,3 +38,4 @@ /**

// Proto3 needs the namespace to have a standard Java-like format, so the "@" and the dots in the version need to be replaces with underscores.
return `${concertoNamespace.split('@')[0]}.v${concertoNamespace.split('@')[1].replace(/\./ig, '_')}`;
const {name,version} = ModelUtil.parseNamespace(concertoNamespace);
return `${name}.v${version ? version.replace(/\./g,'_') : ''}`;
}

@@ -106,3 +108,3 @@

return imports
.filter(importObject => importObject.namespace.split('@')[0] !== 'concerto')
.filter(importObject => ModelUtil.parseNamespace(importObject.namespace).name !== 'concerto')
.map(importObject => `${this.concertoNamespaceToProto3SafePackageName(importObject.namespace)}.proto`);

@@ -179,2 +181,4 @@ }

return this.visitClassDeclaration(thing, parameters);
} else if (thing.isTypeScalar?.()) {
return this.visitField(thing.getScalarField(), parameters);
} else if (thing.isField?.()) {

@@ -186,2 +190,4 @@ return this.visitField(thing, parameters);

return this.visitEnumValueDeclaration(thing, parameters);
} else if (thing.isScalarDeclaration?.()) {
return;
} else {

@@ -188,0 +194,0 @@ throw new Error('Unrecognised type: ' + typeof thing + ', value: ' + util.inspect(thing, { showHidden: true, depth: null }));

@@ -47,2 +47,4 @@ /*

return this.visitClassDeclaration(thing, parameters);
} else if (thing.isTypeScalar?.()) {
return this.visitField(thing.getScalarField(), parameters);
} else if (thing.isField?.()) {

@@ -94,2 +96,3 @@ return this.visitField(thing, parameters);

modelFile.getAllDeclarations()
.filter(declaration => !declaration.isScalarDeclaration?.())
.filter(v => !v.isEnum())

@@ -151,5 +154,6 @@ .forEach(classDeclaration => {

parameters.fileWriter.writeLine(0, '\n// interfaces');
modelFile.getAllDeclarations().forEach((decl) => {
decl.accept(this, parameters);
});
modelFile.getAllDeclarations()
.filter(declaration => !declaration.isScalarDeclaration?.()).forEach((decl) => {
decl.accept(this, parameters);
});

@@ -156,0 +160,0 @@ parameters.fileWriter.closeFile();

@@ -46,2 +46,4 @@ /*

return this.visitClassDeclaration(thing, parameters);
} else if (thing.isTypeScalar?.()) {
return this.visitField(thing.getScalarField(), parameters);
} else if (thing.isField?.()) {

@@ -53,2 +55,4 @@ return this.visitField(thing, parameters);

return this.visitEnumValueDeclaration(thing, parameters);
} else if (thing.isScalarDeclaration?.()) {
return;
} else {

@@ -55,0 +59,0 @@ throw new Error('Unrecognised ' + JSON.stringify(thing) );

@@ -18,3 +18,2 @@ /*

const Writer = require('@accordproject/concerto-util').Writer;
const TypedStack = require('@accordproject/concerto-util').TypedStack;
const Ajv2019 = require('ajv/dist/2019');

@@ -36,16 +35,23 @@ const Ajv2020 = require('ajv/dist/2020');

const REGEX_ESCAPED_CHARS = /[\s\\.-]/g;
/**
* Remove whitespace and periods from a Type identifier
* @param {string} type the input string
* @param {object} options processing options for inference
* @returns {string} the normalized type name
* @private
*/
function normalizeType(type) {
return capitalizeFirstLetter(
type
// In CTO we only have one place to store definitions, so we flatten the storage structure from JSON Schema
.replace(/^#\/(definitions|\$defs|components\/schemas)\//, '')
// Replace delimiters with underscore
.replace(/[\s\\.-]/g, '_')
);
function normalizeType(type, options) {
const typeName = type
// TODO This could cause naming collisions
// In CTO we only have one place to store definitions, so we flatten the storage structure from JSON Schema
.replace(/^#\/(definitions|\$defs|components\/schemas)\//, '')
// Replace delimiters with underscore
.replace(REGEX_ESCAPED_CHARS, '_');
if (options?.capitalizeFirstLetterOfTypeName){
return capitalizeFirstLetter(typeName);
}
return typeName;
}

@@ -56,6 +62,7 @@

* @param {string} id - the $id value from a JSON schema
* @param {object} options processing options for inference
* @returns {object} A namespace and type pair
* @private
*/
function parseIdUri(id) {
function parseIdUri(id, options) {
if (!id) { return; }

@@ -70,3 +77,3 @@

.replace(/\.json$/, '') // Convention is to add .schema.json to $id
.replace(/\.schema$/, ''));
.replace(/\.schema$/, ''), options);

@@ -88,12 +95,23 @@ namespace += path.length > 0 ? path.join('.') : '';

if (definition.$ref) {
return normalizeType(definition.$ref);
return normalizeType(definition.$ref, context.options);
}
const name = context.parents.peek();
const { type } = parseIdUri(definition.$id) ||
{ type: definition.title || name };
const name = context.parents.slice(-1).pop();
const { type } = parseIdUri(definition.$id, context.options) || { type: name };
if (skipDictionary || context.dictionary.has(normalizeType(type))){
return normalizeType(type);
if (skipDictionary || context.dictionary.has(normalizeType(type, context.options))){
return normalizeType(type, context.options);
}
// We've found an inline sub-schema
if (definition.properties || definition.enum){
const subSchemaName = context.parents
.map(p => normalizeType(p, context.options))
.join('_');
// Come back to this later
context.jobs.push({ name: subSchemaName, definition });
return subSchemaName;
}
// We fallback to a stringified object representation. This is "untyped".

@@ -111,3 +129,3 @@ return 'String';

function inferType(definition, context) {
const name = context.parents.peek();
const name = context.parents.slice(-1).pop();
if (definition.$ref) {

@@ -117,3 +135,3 @@ // Recursive defintion

const top = context.parents.pop();
const parent = context.parents.peek();
const parent = context.parents.slice(-1).pop();
context.parents.push(top);

@@ -126,3 +144,2 @@ return parent;

// TODO Also add local sub-schema definition
if (definition.enum) {

@@ -186,5 +203,12 @@ return inferTypeName(definition, context);

definition.enum.forEach((value) => {
let normalizedValue = value;
// Concerto does not allow enum values to start with numbers or values such as `true`
// If we can relax the parser rules, this branch could be removed
if (typeof normalizedValue !== 'string' || normalizedValue.match(/^\d/)){
normalizedValue = `_${normalizedValue}`;
}
normalizedValue = normalizedValue.replace(REGEX_ESCAPED_CHARS, '_');
writer.writeLine(
1,
`o ${value}`
`o ${normalizedValue}`
);

@@ -239,3 +263,3 @@ });

} else if (type === 'String' && propertyDefinition.pattern) {
validator = ` regex=/${propertyDefinition.pattern}/`;
validator = ` regex=/${propertyDefinition.pattern.replace(/\//g, '\\/')}/`;
}

@@ -268,3 +292,3 @@

function inferDeclaration(definition, context) {
const name = context.parents.peek();
const name = context.parents.slice(-1).pop();

@@ -302,5 +326,6 @@ if (definition.enum) {

* @param {object} schema the input json object
* @param {object} options processing options for inference
* @returns {string} the Concerto model
*/
function inferModelFile(defaultNamespace, defaultType, schema) {
function inferModelFile(defaultNamespace, defaultType, schema, options = {}) {
const schemaVersion = schema.$schema;

@@ -327,8 +352,10 @@

// Will throw an error for bad schemas
ajv.validate(type);
ajv.compile(schema);
const context = {
parents: new TypedStack(),
parents: new Array(), // Track ancestors in the tree
writer: new Writer(),
dictionary: new Set(),
dictionary: new Set(), // Track types that we've seen before
jobs: new Array(), // Queue of inline definitions to come-back to
options,
};

@@ -345,3 +372,3 @@

if (schema.$id) {
context.dictionary.add(normalizeType(parseIdUri(schema.$id).type));
context.dictionary.add(normalizeType(parseIdUri(schema.$id).type, options));
}

@@ -372,2 +399,11 @@ Object.keys(defs).forEach((key) => {

// Generate declarations for all inline sub-schemas
while(context.jobs.length > 0){
const job = context.jobs.pop();
context.parents.push(job.name);
context.dictionary.add(job.name);
inferDeclaration(job.definition, context);
context.parents.pop();
}
return context.writer.getBuffer();

@@ -374,0 +410,0 @@ }

{
"name": "@accordproject/concerto-tools",
"version": "3.1.0",
"version": "3.1.1-20221215162924",
"description": "Tools for the Concerto Modeling Language",

@@ -14,3 +14,3 @@ "homepage": "https://github.com/accordproject/concerto",

"scripts": {
"prepublishOnly": "webpack --config webpack.config.js --mode production",
"prepublishOnly": "npm run webpack",
"pretest": "npm run lint",

@@ -22,3 +22,2 @@ "lint": "eslint .",

"doc": "jsdoc --pedantic --recurse -c jsdoc.json",
"postdoc": "npm run build:types",
"test": "nyc mocha --recursive -t 10000",

@@ -29,2 +28,5 @@ "test:updateSnapshots": "nyc mocha --updateSnapshot --recursive -t 10000",

"nyc": "nyc mocha --recursive -t 10000",
"build": "npm run build:types",
"postbuild": "npm run webpack",
"webpack": "webpack --config webpack.config.js --mode production",
"build:types": "tsc index.js --declaration --allowJs --emitDeclarationOnly --outDir types"

@@ -71,8 +73,9 @@ },

"dependencies": {
"@accordproject/concerto-core": "3.1.0",
"@accordproject/concerto-util": "3.1.0",
"@accordproject/concerto-core": "3.1.1-20221215162924",
"@accordproject/concerto-util": "3.1.1-20221215162924",
"ajv": "8.10.0",
"ajv-formats": "2.1.1",
"camelcase": "6.3.0",
"debug": "4.3.1"
"debug": "4.3.1",
"pluralize": "8.0.0"
},

@@ -140,3 +143,3 @@ "license-check-and-add-config": {

"statements": 99,
"branches": 98,
"branches": 97,
"functions": 100,

@@ -143,0 +146,0 @@ "lines": 99

@@ -15,2 +15,4 @@ export var CodeGen: {

ProtobufVisitor: typeof import("./lib/codegen/fromcto/protobuf/protobufvisitor");
OpenApiVisitor: typeof import("./lib/codegen/fromcto/openapi/openapivisitor");
AvroVisitor: typeof import("./lib/codegen/fromcto/avro/avrovisitor");
InferFromJsonSchema: typeof import("./lib/codegen/fromJsonSchema/cto/inferModel");

@@ -30,4 +32,6 @@ formats: {

protobuf: typeof import("./lib/codegen/fromcto/protobuf/protobufvisitor");
openapi: typeof import("./lib/codegen/fromcto/openapi/openapivisitor");
avro: typeof import("./lib/codegen/fromcto/avro/avrovisitor");
};
};
export var version: any;

@@ -14,2 +14,4 @@ import AbstractPlugin = require("./abstractplugin");

import ProtobufVisitor = require("./fromcto/protobuf/protobufvisitor");
import OpenApiVisitor = require("./fromcto/openapi/openapivisitor");
import AvroVisitor = require("./fromcto/avro/avrovisitor");
import InferFromJsonSchema = require("./fromJsonSchema/cto/inferModel");

@@ -29,3 +31,5 @@ export declare namespace formats {

export { ProtobufVisitor as protobuf };
export { OpenApiVisitor as openapi };
export { AvroVisitor as avro };
}
export { AbstractPlugin, GoLangVisitor, JSONSchemaVisitor, XmlSchemaVisitor, PlantUMLVisitor, TypescriptVisitor, JavaVisitor, GraphQLVisitor, CSharpVisitor, ODataVisitor, MermaidVisitor, MarkdownVisitor, ProtobufVisitor, InferFromJsonSchema };
export { AbstractPlugin, GoLangVisitor, JSONSchemaVisitor, XmlSchemaVisitor, PlantUMLVisitor, TypescriptVisitor, JavaVisitor, GraphQLVisitor, CSharpVisitor, ODataVisitor, MermaidVisitor, MarkdownVisitor, ProtobufVisitor, OpenApiVisitor, AvroVisitor, InferFromJsonSchema };

@@ -14,2 +14,5 @@ export = JSONSchemaVisitor;

*
* The default value for refRoot is '#/definitions'. Set the refRoot parameter
* to override.
*
* The meta schema used is http://json-schema.org/draft-07/schema#

@@ -30,2 +33,9 @@ *

/**
* Get the validators for a field or a scalar definition in JSON schema form.
* @param {Object} field - the scalar declaration being visited
* @return {Object} the result of visiting or null
* @private
*/
private getFieldOrScalarDeclarationValidatorsForSchema;
/**
* Returns true if the class declaration contains recursive references.

@@ -109,2 +119,10 @@ *

* Visitor design pattern
* @param {ScalarDeclaration} scalarDeclaration - the object being visited
* @param {Object} parameters - the parameter
* @return {Object} the result of visiting or null
* @private
*/
private visitScalarDeclaration;
/**
* Visitor design pattern
* @param {Field} field - the object being visited

@@ -111,0 +129,0 @@ * @param {Object} parameters - the parameter

@@ -7,4 +7,5 @@ export = inferModelFile;

* @param {object} schema the input json object
* @param {object} options processing options for inference
* @returns {string} the Concerto model
*/
declare function inferModelFile(defaultNamespace: string, defaultType: string, schema: object): string;
declare function inferModelFile(defaultNamespace: string, defaultType: string, schema: object, options?: object): string;
/*!
* Concerto Tools v3.1.0
* Concerto Tools v3.1.1-20221215162924
* Licensed under the Apache License, Version 2.0 (the "License");

@@ -4,0 +4,0 @@ * you may not use this file except in compliance with the License.

Sorry, the diff of this file is too big to display

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