Skip to content

Commit

Permalink
Merge branch 'main' into add-jwk-check
Browse files Browse the repository at this point in the history
  • Loading branch information
heliuchuan committed Nov 1, 2024
2 parents a7cfb5e + 10d9c3f commit 7a3a5ea
Show file tree
Hide file tree
Showing 7 changed files with 117 additions and 15 deletions.
2 changes: 1 addition & 1 deletion examples/typescript/federated_keyless.ts
Original file line number Diff line number Diff line change
Expand Up @@ -90,7 +90,7 @@ const example = async () => {

const iss = "https://dev-qtdgjv22jh0v1k7g.us.auth0.com/";

console.log("\n=== Installing JWKs ===\n");
console.log("\n=== Installing JSON Web Key Set (JWKS) ===\n");
const jwkTxn = await aptos.updateFederatedKeylessJwkSetTransaction({ sender: bob, iss });
const committedJwkTxn = await aptos.signAndSubmitTransaction({ signer: bob, transaction: jwkTxn });
await aptos.waitForTransaction({ transactionHash: committedJwkTxn.hash });
Expand Down
2 changes: 1 addition & 1 deletion examples/typescript/jwk_update.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@
/* eslint-disable no-console */

/**
* This example shows how to use install JWKs on an account to support Federated Keyless Accounts
* This example shows how to use install JSON Web Key Set (JWKS) on an account to support Federated Keyless Accounts
*/

import { Aptos, AptosConfig, EphemeralKeyPair, Network } from "@aptos-labs/ts-sdk";
Expand Down
13 changes: 11 additions & 2 deletions scripts/generateDocs.sh
Original file line number Diff line number Diff line change
Expand Up @@ -15,8 +15,17 @@ if [ -d "docs/@aptos-labs/ts-sdk-$npm_package_version" ]; then
echo "WARNING! Docs folder already exists, overwriting docs for version $npm_package_version";
fi

# TODO: This uses the --skipErrorChecking flag as otherwise it incorrectly tries to compile the tests folder.
# Remove this once test compiler errors are not intefering with docs generation.
# `npx typedoc src/index.ts` generates the typedoc docs for this SDK using the proper formatting.
#
# Explanation of each flag:
# --options typedoc.json - Loads options from the typedoc.json configuration file
# --out "docs/@aptos-labs/ts-sdk-$npm_package_version" - Specifies the output directory for the generated documentation,
# dynamically including the current npm package version in the path using the $npm_package_version variable
# --plugin typedoc-plugin-missing-exports - Includes the plugin to include private code in the generated docs (needed to show the reference docs for the Aptos mixin implementation details)
# --cleanOutputDir - Clears the output directory before generating new documentation
# --excludeInternal - Excludes internal symbols from the generated documentation (symbols marked with @internal in comments)
# --includeVersion - Includes the version of the package in the generated documentation
# --skipErrorChecking - TODO: Remove this flag when no longer needed. This avoids the docs build failing due to compiler errors in the tests folder.
npx typedoc src/index.ts --options typedoc.json --out "docs/@aptos-labs/ts-sdk-$npm_package_version" --plugin typedoc-plugin-missing-exports --cleanOutputDir --excludeInternal --includeVersion --skipErrorChecking

# Update the main page
Expand Down
35 changes: 32 additions & 3 deletions src/account/AbstractKeylessAccount.ts
Original file line number Diff line number Diff line change
Expand Up @@ -108,7 +108,24 @@ export abstract class AbstractKeylessAccount extends Serializable implements Key
*/
private readonly emitter: EventEmitter<ProofFetchEvents>;

// Use the static constructor 'create' instead.
/**
* Use the static generator `create(...)` instead.
* Creates an instance of the KeylessAccount with an optional proof.
*
* @param args - The parameters for creating a KeylessAccount.
* @param args.address - Optional account address associated with the KeylessAccount.
* @param args.publicKey - A KeylessPublicKey or FederatedKeylessPublicKey.
* @param args.ephemeralKeyPair - The ephemeral key pair used in the account creation.
* @param args.iss - A JWT issuer.
* @param args.uidKey - The claim on the JWT to identify a user. This is typically 'sub' or 'email'.
* @param args.uidVal - The unique id for this user, intended to be a stable user identifier.
* @param args.aud - The value of the 'aud' claim on the JWT, also known as client ID. This is the identifier for the dApp's
* OIDC registration with the identity provider.
* @param args.pepper - A hexadecimal input used for additional security.
* @param args.proof - A Zero Knowledge Signature or a promise that resolves to one.
* @param args.proofFetchCallback - Optional callback function for fetching proof.
* @param args.jwt - A JSON Web Token used for authentication.
*/
protected constructor(args: {
address?: AccountAddress;
publicKey: KeylessPublicKey | FederatedKeylessPublicKey;
Expand Down Expand Up @@ -155,8 +172,8 @@ export abstract class AbstractKeylessAccount extends Serializable implements Key
}

/**
* This initializes the asynchronous proof fetch
* @return
* This initializes the asynchronous proof fetch.
* @return Emits whether the proof succeeds or fails, but has no return.
*/
async init(promise: Promise<ZeroKnowledgeSig>) {
try {
Expand All @@ -171,6 +188,12 @@ export abstract class AbstractKeylessAccount extends Serializable implements Key
}
}

/**
* Serializes the jwt data into a format suitable for transmission or storage.
* This function ensures that both the jwt data and the proof are properly serialized.
*
* @param serializer - The serializer instance used to convert the jwt data into bytes.
*/
serialize(serializer: Serializer): void {
serializer.serializeStr(this.jwt);
serializer.serializeStr(this.uidKey);
Expand Down Expand Up @@ -397,6 +420,12 @@ export class TransactionAndProof extends Serializable {
this.proof = proof;
}

/**
* Serializes the transaction data into a format suitable for transmission or storage.
* This function ensures that both the transaction bytes and the proof are properly serialized.
*
* @param serializer - The serializer instance used to convert the transaction data into bytes.
*/
serialize(serializer: Serializer): void {
serializer.serializeFixedBytes(this.transaction.bcsToBytes());
serializer.serializeOption(this.proof);
Expand Down
52 changes: 49 additions & 3 deletions src/account/FederatedKeylessAccount.ts
Original file line number Diff line number Diff line change
Expand Up @@ -16,8 +16,8 @@ import { AbstractKeylessAccount, ProofFetchCallback } from "./AbstractKeylessAcc
*
* Used to represent a FederatedKeyless based account and sign transactions with it.
*
* Use `FederatedKeylessAccount.create()` to instantiate a KeylessAccount with a JWT, proof, EphemeralKeyPair and the
* address the JWKs are installed that will be used to verify the JWT.
* Use `FederatedKeylessAccount.create()` to instantiate a KeylessAccount with a JSON Web Token (JWT), proof, EphemeralKeyPair and the
* address the JSON Web Key Set (JWKS) are installed that will be used to verify the JWT.
*
* When the proof expires or the JWT becomes invalid, the KeylessAccount must be instantiated again with a new JWT,
* EphemeralKeyPair, and corresponding proof.
Expand All @@ -28,7 +28,20 @@ export class FederatedKeylessAccount extends AbstractKeylessAccount {
*/
readonly publicKey: FederatedKeylessPublicKey;

// Use the static constructor 'create' instead.
/**
* Use the static generator `FederatedKeylessAccount.create(...)` instead.
* Creates a KeylessAccount instance using the provided parameters.
* This function allows you to set up a KeylessAccount with specific attributes such as address, proof, and JWT.
*
* @param args - The parameters for creating a KeylessAccount.
* @param args.address - Optional account address associated with the KeylessAccount.
* @param args.proof - A Zero Knowledge Signature or a promise that resolves to one.
* @param args.jwt - A JSON Web Token used for authentication.
* @param args.ephemeralKeyPair - The ephemeral key pair used in the account creation.
* @param args.jwkAddress - The address which stores the JSON Web Key Set (JWKS) used to verify the JWT.
* @param args.uidKey - Optional key for user identification, defaults to "sub".
* @param args.proofFetchCallback - Optional callback function for fetching proof.
*/
private constructor(args: {
address?: AccountAddress;
ephemeralKeyPair: EphemeralKeyPair;
Expand All @@ -47,6 +60,12 @@ export class FederatedKeylessAccount extends AbstractKeylessAccount {
this.publicKey = publicKey;
}

/**
* Serializes the transaction data into a format suitable for transmission or storage.
* This function ensures that both the transaction bytes and the proof are properly serialized.
*
* @param serializer - The serializer instance used to convert the transaction data into bytes.
*/
serialize(serializer: Serializer): void {
if (this.proof === undefined) {
throw new Error("Cannot serialize - proof undefined");
Expand All @@ -59,6 +78,13 @@ export class FederatedKeylessAccount extends AbstractKeylessAccount {
this.proof.serialize(serializer);
}

/**
* Deserializes the provided deserializer to create a KeylessAccount instance.
* This function extracts necessary components such as the JWT, UID key, pepper, ephemeral key pair, and proof from the deserializer.
*
* @param deserializer - The deserializer instance used to retrieve the serialized data.
* @returns A KeylessAccount instance created from the deserialized data.
*/
static deserialize(deserializer: Deserializer): FederatedKeylessAccount {
const jwt = deserializer.deserializeStr();
const uidKey = deserializer.deserializeStr();
Expand All @@ -76,10 +102,30 @@ export class FederatedKeylessAccount extends AbstractKeylessAccount {
});
}

/**
* Deserialize bytes using this account's information.
*
* @param bytes The bytes being interpreted.
* @returns
*/
static fromBytes(bytes: Uint8Array): FederatedKeylessAccount {
return FederatedKeylessAccount.deserialize(new Deserializer(bytes));
}

/**
* Creates a KeylessAccount instance using the provided parameters.
* This function allows you to set up a KeylessAccount with specific attributes such as address, proof, and JWT.
* This is used instead of the KeylessAccount constructor.
*
* @param args - The parameters for creating a KeylessAccount.
* @param args.address - Optional account address associated with the KeylessAccount.
* @param args.proof - A Zero Knowledge Signature or a promise that resolves to one.
* @param args.jwt - A JSON Web Token used for authentication.
* @param args.ephemeralKeyPair - The ephemeral key pair used in the account creation.
* @param args.jwkAddress - The address which stores the JSON Web Key Set (JWKS) used to verify the JWT.
* @param args.uidKey - Optional key for user identification, defaults to "sub".
* @param args.proofFetchCallback - Optional callback function for fetching proof.
*/
static create(args: {
address?: AccountAddress;
proof: ZeroKnowledgeSig | Promise<ZeroKnowledgeSig>;
Expand Down
24 changes: 21 additions & 3 deletions src/account/KeylessAccount.ts
Original file line number Diff line number Diff line change
Expand Up @@ -29,11 +29,22 @@ export class KeylessAccount extends AbstractKeylessAccount {
// Use the static constructor 'create' instead.

/**
* Creates an instance of the transaction with an optional proof.
* Use the static generator `create(...)` instead.
* Creates an instance of the KeylessAccount with an optional proof.
*
* @param args.proof - An optional ZkProof associated with the transaction.
* @param args - The parameters for creating a KeylessAccount.
* @param args.address - Optional account address associated with the KeylessAccount.
* @param args.ephemeralKeyPair - The ephemeral key pair used in the account creation.
* @param args.iss - A JWT issuer.
* @param args.uidKey - The claim on the JWT to identify a user. This is typically 'sub' or 'email'.
* @param args.uidVal - The unique id for this user, intended to be a stable user identifier.
* @param args.aud - The value of the 'aud' claim on the JWT, also known as client ID. This is the identifier for the dApp's
* OIDC registration with the identity provider.
* @param args.pepper - A hexadecimal input used for additional security.
* @param args.proof - A Zero Knowledge Signature or a promise that resolves to one.
* @param args.proofFetchCallback - Optional callback function for fetching proof.
* @param args.jwt - A JSON Web Token used for authentication.
*/
// TODO: Document rest of parameters
private constructor(args: {
address?: AccountAddress;
ephemeralKeyPair: EphemeralKeyPair;
Expand Down Expand Up @@ -90,13 +101,20 @@ export class KeylessAccount extends AbstractKeylessAccount {
});
}

/**
* Deserialize bytes using this account's information.
*
* @param bytes The bytes being interpreted.
* @returns
*/
static fromBytes(bytes: Uint8Array): KeylessAccount {
return KeylessAccount.deserialize(new Deserializer(bytes));
}

/**
* Creates a KeylessAccount instance using the provided parameters.
* This function allows you to set up a KeylessAccount with specific attributes such as address, proof, and JWT.
* This is used instead of the KeylessAccount constructor.
*
* @param args - The parameters for creating a KeylessAccount.
* @param args.address - Optional account address associated with the KeylessAccount.
Expand Down
4 changes: 2 additions & 2 deletions src/api/keyless.ts
Original file line number Diff line number Diff line change
Expand Up @@ -155,7 +155,7 @@ export class Keyless {
* @param args.jwt - The JWT token used for deriving the account.
* @param args.ephemeralKeyPair - The EphemeralKeyPair used to generate the nonce in the JWT token.
* @param args.jwkAddress - The address the where the JWKs used to verify signatures are found. Setting the value derives a
* FederatedKeylessAccount
* FederatedKeylessAccount.
* @param args.uidKey - An optional key in the JWT token to set the uidVal in the IdCommitment.
* @param args.pepper - An optional pepper value.
* @param args.proofFetchCallback - An optional callback function for fetching the proof in the background, allowing for a more
Expand Down Expand Up @@ -201,7 +201,7 @@ export class Keyless {
/**
* This installs a set of FederatedJWKs at an address for a given iss.
*
* It will fetch the JWK set from the well-known endpoint and update the FederatedJWKs at the sender's address
* It will fetch the JSON Web Keyset (JWK) set from the well-known endpoint and update the FederatedJWKs at the sender's address
* to reflect it.
*
* @param args.sender The account that will install the JWKs
Expand Down

0 comments on commit 7a3a5ea

Please sign in to comment.