@lit-protocol/auth-helpers
Version:
Advanced authentication utilities for managing blockchain resource permissions and capabilities within the Lit Protocol ecosystem. Built on top of SIWE (Sign-In with Ethereum) and SIWE-RECAP for robust authentication flows.
123 lines • 5.11 kB
JavaScript
;
Object.defineProperty(exports, "__esModule", { value: true });
exports.RecapSessionCapabilityObject = void 0;
const tslib_1 = require("tslib");
const constants_1 = require("@lit-protocol/constants");
const depd_1 = tslib_1.__importDefault(require("depd"));
const siwe_recap_1 = require("siwe-recap");
const utils_1 = require("./utils");
const siwe_helper_1 = require("../siwe/siwe-helper");
const deprecated = (0, depd_1.default)('lit-js-sdk:auth-recap:session-capability-object');
class RecapSessionCapabilityObject {
constructor(att = {}, prf = []) {
this._inner = new siwe_recap_1.Recap(att, prf);
}
static decode(encoded) {
const recap = siwe_recap_1.Recap.decode_urn(encoded);
return new this(recap.attenuations, recap.proofs.map((cid) => cid.toString()));
}
static extract(siwe) {
const recap = siwe_recap_1.Recap.extract_and_verify(siwe);
return new this(recap.attenuations, recap.proofs.map((cid) => cid.toString()));
}
get attenuations() {
return this._inner.attenuations;
}
get proofs() {
return this._inner.proofs.map((cid) => cid.toString());
}
get statement() {
return (0, siwe_helper_1.sanitizeSiweMessage)(this._inner.statement);
}
addProof(proof) {
return this._inner.addProof(proof);
}
addAttenuation(resource, namespace = '*', name = '*', restriction = {}) {
return this._inner.addAttenuation(resource, namespace, name, restriction);
}
addToSiweMessage(siwe) {
return this._inner.add_to_siwe_message(siwe);
}
encodeAsSiweResource() {
return this._inner.encode();
}
/** LIT specific methods */
addCapabilityForResource(litResource, ability, data = {}) {
// Validate Lit ability is compatible with the Lit resource.
if (!litResource.isValidLitAbility(ability)) {
throw new constants_1.InvalidArgumentException({
info: {
litResource,
ability,
},
}, `The specified Lit resource does not support the specified ability.`);
}
const { recapNamespace, recapAbility } = (0, utils_1.getRecapNamespaceAndAbility)(ability);
if (!data) {
return this.addAttenuation(litResource.getResourceKey(), recapNamespace, recapAbility);
}
return this.addAttenuation(litResource.getResourceKey(), recapNamespace, recapAbility, data);
}
verifyCapabilitiesForResource(litResource, ability) {
// Validate Lit ability is compatible with the Lit resource.
// The only exception is if there's a wildcard resource key in the session capability object.
if (!litResource.isValidLitAbility(ability)) {
return false;
}
// Get the attenuations object.
const attenuations = this.attenuations;
const { recapNamespace, recapAbility } = (0, utils_1.getRecapNamespaceAndAbility)(ability);
const recapAbilityToCheckFor = `${recapNamespace}/${recapAbility}`;
// Find an attenuated resource key to match against.
const attenuatedResourceKey = this._getResourceKeyToMatchAgainst(litResource);
if (!attenuations[attenuatedResourceKey]) {
// No attenuations specified for this resource.
return false;
}
// Check whether the exact Recap namespace/ability pair is present.
const attenuatedRecapAbilities = Object.keys(attenuations[attenuatedResourceKey]);
for (const attenuatedRecapAbility of attenuatedRecapAbilities) {
// Return early if the attenuated recap ability is a wildcard.
if (attenuatedRecapAbility === '*/*') {
return true;
}
if (attenuatedRecapAbility === recapAbilityToCheckFor) {
return true;
}
}
return false;
}
/**
* Returns the attenuated resource key to match against. This supports matching
* against a wildcard resource key too.
*
* @example If the attenuations object contains the following:
*
* ```
* {
* 'lit-acc://*': {
* '*\/*': {}
* }
* }
* ```
*
* Then, if the provided litResource is 'lit-acc://123', the method will return 'lit-acc://*'.
*/
_getResourceKeyToMatchAgainst(litResource) {
const attenuatedResourceKeysToMatchAgainst = [
`${litResource.resourcePrefix}://*`,
litResource.getResourceKey(),
];
for (const attenuatedResourceKeyToMatchAgainst of attenuatedResourceKeysToMatchAgainst) {
if (this.attenuations[attenuatedResourceKeyToMatchAgainst]) {
return attenuatedResourceKeyToMatchAgainst;
}
}
return '';
}
addAllCapabilitiesForResource(litResource) {
return this.addAttenuation(litResource.getResourceKey(), '*', '*');
}
}
exports.RecapSessionCapabilityObject = RecapSessionCapabilityObject;
//# sourceMappingURL=recap-session-capability-object.js.map