Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
8 changes: 8 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,3 +1,11 @@
#### 2.0.0 (2025-01-01)

##### Features

* Add support for arm64 ([03707dd](https://github.com/primno/dpapi/commit/03707dd007a60f4f4abfc423f781e503edbcc92e))
* Add platform support flag ([755cb93](https://github.com/primno/dpapi/commit/755cb9326c8254861859aa0219d49fa06aa421d5))


#### 1.1.1 (2023-03-25)

##### Chores
Expand Down
61 changes: 44 additions & 17 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,9 @@

Native module to encrypt/decrypt data on Windows with DPAPI.

This native module is **prebuilt** for Node.JS running on Windows. It provides the win32-x64 N-API module.
This native module is **prebuilt** for Node.JS running on Windows. It provides the **x64** and the **arm64** N-API modules for Windows.

This package indicates if the prebuilt module is supported on the current platform.

Based on the port to N-API made by [Microsoft](https://github.com/AzureAD/microsoft-authentication-library-for-js/tree/dev/extensions/msal-node-extensions/src/dpapi-addon) in @msal-node-extension from the work of [Brad Hughes](https://github.com/bradhugh/node-dpapi).

Expand All @@ -21,7 +23,7 @@ This package is prebuilt, so you don't need to have build tools installed on the

## Install

The win32-x64 prebuilt module will be installed with the following command.
The prebuilt module will be installed with the following command.

```bash
npm install @primno/dpapi
Expand All @@ -30,28 +32,53 @@ npm install @primno/dpapi
## Definition

```ts
function protectData(
userData: Uint8Array,
optionalEntropy: Uint8Array | null,
scope: "CurrentUser" | "LocalMachine"
): Uint8Array;

function unprotectData(
encryptedData: Uint8Array,
optionalEntropy: Uint8Array | null,
scope: "CurrentUser" | "LocalMachine"
): Uint8Array;
class Dpapi {
public protectData(
userData: Uint8Array,
optionalEntropy: Uint8Array | null,
scope: "CurrentUser" | "LocalMachine"
): Uint8Array;

public unprotectData(
encryptedData: Uint8Array,
optionalEntropy: Uint8Array | null,
scope: "CurrentUser" | "LocalMachine"
): Uint8Array;
}

const isPlatformSupported: boolean;
```

## Usage

### ECMAScript Module
```ts
import { Dpapi } from "@primno/dpapi";
import { Dpapi, isPlatformSupported } from "@primno/dpapi";

if (isPlatformSupported) {
const buffer = Buffer.from("Hello world", "utf-8");

const encrypted = Dpapi.protectData(buffer, null, "CurrentUser");
const decrypted = Dpapi.unprotectData(encrypted, null, "CurrentUser");
}
else {
console.error("Platform not supported. Only Windows is supported (x64, ARM64)");
}
```

### CommonJS
```js
const { Dpapi, isPlatformSupported } = require("@primno/dpapi");

const buffer = Buffer.from("Hello world", "utf-8");
if (isPlatformSupported) {
const buffer = Buffer.from("Hello world", "utf-8");

const encrypted = Dpapi.protectData(buffer, null, "CurrentUser");
const decrypted = Dpapi.unprotectData(encrypted, null, "CurrentUser");
const encrypted = Dpapi.protectData(buffer, null, "CurrentUser");
const decrypted = Dpapi.unprotectData(encrypted, null, "CurrentUser");
}
else {
console.error("Platform not supported. Only Windows is supported (x64, ARM64)");
}
```

## Credits
Expand Down
36 changes: 35 additions & 1 deletion lib/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -7,5 +7,39 @@ export interface DpapiBindings {

export type DataProtectionScope = "CurrentUser" | "LocalMachine";

export var Dpapi: DpapiBindings = require("node-gyp-build")(path.join(__dirname, ".."));
class ErrorWithInnerError extends Error {
public innerError: Error;

constructor(message: string, innerError: Error) {
super(message);
this.innerError = innerError;
}
}

class UnsupportedPlatformDpapiBindings implements DpapiBindings {
private error: Error;

constructor(error: Error) {
this.error = error;
}

protectData(dataToEncrypt: Uint8Array, optionalEntropy: Uint8Array | null, scope: DataProtectionScope): Uint8Array {
throw new ErrorWithInnerError("DPAPI is not supported on this platform.", this.error);
}
unprotectData(encryptData: Uint8Array, optionalEntropy: Uint8Array | null, scope: DataProtectionScope): Uint8Array {
throw new ErrorWithInnerError("DPAPI is not supported on this platform.", this.error);
}
}

let dpapi: DpapiBindings;

try {
dpapi = require("node-gyp-build")(path.join(__dirname, ".."));
}
catch (e: any) {
dpapi = new UnsupportedPlatformDpapiBindings(e);
}

export var isPlatformSupported : boolean = !(dpapi instanceof UnsupportedPlatformDpapiBindings);
export var Dpapi: DpapiBindings = dpapi;
export default Dpapi;
Loading