-->
# nano-pow
+
_Proof-of-work generation and validation with WebGPU/WebGL for Nano cryptocurrency._
NanoPow uses WebGPU to generate proof-of-work nonces meeting the requirements
All calculations take place client-side, so nonces can be generated offline and
cached for the next transaction block. For more information about the
proof-of-work equation defined by Nano, see
-https://docs.nano.org/integration-guides/work-generation/#work-calculation-details
+<https://docs.nano.org/integration-guides/work-generation/#work-calculation-details>
## Installation
+
```console
-$ npm i nano-pow
+npm i nano-pow
```
+
NanoPow can also be installed globally to add the `nano-pow` command to the
system environment. To learn more, see [#Executables](#executables).
## Usage
+
### Import
+
The easiest way to use NanoPow is to import it directly. Based on the features
available in the environment, NanoPow will try to use its most performant API.
```html
<script type="module">
- (async () => {
- const { NanoPow } = await import('https://cdn.jsdelivr.net/npm/nano-pow@latest')
- const { work } = await NanoPow.work_generate(some_hash)
- console.log(work)
- })()
+ (async () => {
+ const { NanoPow } = await import('https://cdn.jsdelivr.net/npm/nano-pow@latest')
+ const { work } = await NanoPow.work_generate(some_hash)
+ console.log(work)
+ })()
</script>
```
### Generate
+
```javascript
// `hash` is a 64-char hex string
const hash = '0123456789abcdef0123456789abcdef0123456789abcdef0123456789abcdef'
```
### Validate
+
```javascript
// `work` is a 16-char hex string
const work = 'fedcba0987654321'
```
### Options
+
```javascript
const options = {
- // default best available in order: webgpu => webgl => wasm => cpu
- api: 'webgpu',
- // default FFFFFFF800000000 for send/change blocks
- difficulty: 'FFFFFFC000000000',
- // default 4, valid range 1-32
- effort: 2,
- // default false
- debug: true
+ // default best available in order: webgpu => webgl => wasm => cpu
+ api: 'webgpu',
+ // default FFFFFFF800000000 for send/change blocks
+ difficulty: 'FFFFFFC000000000',
+ // default 4, valid range 1-32
+ effort: 2,
+ // default false
+ debug: true
}
const { work } = await NanoPow.work_generate(hash, options)
```
#### What is "effort"?
+
NanoPow's "effort" metric is an abstraction of various GPU and CPU capabilities.
Different systems will have different optimal settings, but as a general rule of
thumb:
in the CPU.
## Executables
+
NanoPow can be installed globally and executed from the command line. This is
useful for systems without a graphical interface.
+
```console
-$ npm -g i nano-pow
-$ nano-pow --help # view abbreviated CLI help
-$ man nano-pow # view full manual
+npm -g i nano-pow
+nano-pow --help # view abbreviated CLI help
+man nano-pow # view full manual
```
+
Ensure proper permissions exist on the
[npm `prefix`](https://docs.npmjs.com/cli/v11/commands/npm-prefix) directory and
that `PATH` is also configured accordingly. [nvm](https://github.com/nvm-sh/nvm)
is a great tool that handles this automatically.
### Command Line
+
NanoPow provides a shell command—`nano-pow`—to accomodate systems
without a graphical user interface. It launches a headless Chrome browser using
`puppeteer` to access the required WebGPU or WebGL APIs. Use the `--global` flag
when installing to add the executable script to the system.
+
```console
-$ npm i -g nano-pow
+npm i -g nano-pow
```
+
Some examples are provided below, and for full documentation, read the manual
with `man nano-pow`.
```console
-$ # Generate a work value using default settings and debugging output enabled.
-$ nano-pow --debug 0123456789abcdef0123456789abcdef0123456789abcdef0123456789abcdef
+# Generate a work value using default settings and debugging output enabled.
+nano-pow --debug 0123456789abcdef0123456789abcdef0123456789abcdef0123456789abcdef
```
+
```console
-$ # Generate work using customized behavior with options.
-$ nano-pow --effort 32 --difficulty FFFFFFC000000000 0123456789abcdef0123456789abcdef0123456789abcdef0123456789abcdef
+# Generate work using customized behavior with options.
+nano-pow --effort 32 --difficulty FFFFFFC000000000 0123456789abcdef0123456789abcdef0123456789abcdef0123456789abcdef
```
+
```console
-$ # Validate an existing work nonce against a blockhash.
+# Validate an existing work nonce against a blockhash.
nano-pow --validate fedcba9876543210 0123456789abcdef0123456789abcdef0123456789abcdef0123456789abcdef
```
+
```console
-$ # Process blockhashes in batches to reduce the initial startup overhead.
-$ nano-pow 0123456789abcdef0123456789abcdef0123456789abcdef0123456789abcdef 0123456789abcdef0123456789abcdef0123456789abcdef0123456789abcdef [...]
-$ # OR
+# Process blockhashes in batches to reduce the initial startup overhead.
+nano-pow 0123456789abcdef0123456789abcdef0123456789abcdef0123456789abcdef 0123456789abcdef0123456789abcdef0123456789abcdef0123456789abcdef [...]
+# OR
nano-pow $(cat /path/to/hashes/file)
-$ # OR
-$ cat /path/to/hashes/file | nano-pow
+# OR
+cat /path/to/hashes/file | nano-pow
```
### Server
+
NanoPow also provides a basic work server similar to the one included in the
official Nano node software. The installed command will launch the server in a
detached process, and it can also be started manually to customize behavior by
executing the server script directly.
#### Environment Variables
+
`NANO_POW_DEBUG`: enable additional logging saved to the HOME directory
`NANO_POW_EFFORT`: increase or decrease demand on the GPU
`NANO_POW_PORT`: override the default port 5040
```console
-$ # Launch the server and detach from the current session
-$ NANO_POW_PORT=8080 nano-pow --server
-$ # View process ID for "NanoPow Server"
-$ cat ~/.nano-pow/server.pid
-$ # Display list of server logs
-$ ls ~/.nano-pow/logs/
-$ # Find process ID manually
-$ pgrep NanoPow
+# Launch the server and detach from the current session
+NANO_POW_PORT=8080 nano-pow --server
+# View process ID for "NanoPow Server"
+cat ~/.nano-pow/server.pid
+# Display list of server logs
+ls ~/.nano-pow/logs/
+# Find process ID manually
+pgrep NanoPow
```
+
Work is generated or validated by sending an HTTP `POST` request to the
configured hostname or IP address of the machine. Some basic help is available
via `GET` request.
+
```console
$ # Generate a work value
$ curl -d '{
- "action": "work_generate",
- "hash": "0123456789abcdef0123456789abcdef0123456789abcdef0123456789abcdef"
+ "action": "work_generate",
+ "hash": "0123456789abcdef0123456789abcdef0123456789abcdef0123456789abcdef"
}' localhost:5040
```
+
```console
$ # Validate a work value
$ curl -d '{
- "action": "work_validate",
- "work": "e45835c3b291c3d1",
- "hash": "0123456789abcdef0123456789abcdef0123456789abcdef0123456789abcdef"
+ "action": "work_validate",
+ "work": "e45835c3b291c3d1",
+ "hash": "0123456789abcdef0123456789abcdef0123456789abcdef0123456789abcdef"
}' localhost:5040
```
## Notes
+
The `work` field in a Nano transaction block contains an 8-byte nonce that
satisfies the following equation:
every last bit of speed and performance out of it.
## Tests
-A few basic tests are availabe in the source repository.
+
+A few basic tests are available in the source repository.
+
* `test/index.html` in the source repository contains a web interface to change
execution options and compare results.
* `test/script.sh` runs some basic benchmarks to check the CLI, and then it
starts the `nano-pow` server and sends some validate and generate requests.
## Building
+
1. Clone source
1. Enter the directory
1. Install dev dependencies
1. Compile, minify, and bundle
```console
-$ git clone https://zoso.dev/nano-pow.git
-$ cd nano-pow
-$ npm i
+git clone https://zoso.dev/nano-pow.git
+cd nano-pow
+npm i
```
## Reporting Bugs
+
Email: <bug-nano-pow@zoso.dev>
## Acknowledgements
+
[numtel/nano-webgl-pow](https://github.com/numtel/nano-webgl-pow) for his WebGL
implementation
## Licenses
+
GNU GPL version 3 or later <https://gnu.org/licenses/gpl.html>
Portions of this code are also provided under the MIT License: <https://spdx.org/licenses/MIT.html>
## Donations
+
Tips are always appreciated and can be sent to the following developer address:
-```
+
nano_1zosoqs47yt47bnfg7sdf46kj7asn58b7uzm9ek95jw7ccatq37898u1zoso
-```