├── .gitignore ├── .travis.yml ├── package.json ├── LICENSE ├── readme.md ├── index.js └── test.js /.gitignore: -------------------------------------------------------------------------------- 1 | node_modules -------------------------------------------------------------------------------- /.travis.yml: -------------------------------------------------------------------------------- 1 | language: node_js 2 | 3 | node_js: 4 | - "4" 5 | - "6" 6 | - "8" 7 | 8 | sudo: false 9 | 10 | script: 11 | - npm test 12 | -------------------------------------------------------------------------------- /package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "hyperdrive-network-speed", 3 | "version": "2.1.1", 4 | "description": "track hyperdrive archive upload and download speeds", 5 | "main": "index.js", 6 | "scripts": { 7 | "test": "tape test.js | tap-spec" 8 | }, 9 | "repository": { 10 | "type": "git", 11 | "url": "git+https://github.com/joehand/hyperdrive-network-speed.git" 12 | }, 13 | "author": "Joe Hand (https://joeahand.com/)", 14 | "license": "MIT", 15 | "bugs": { 16 | "url": "https://github.com/joehand/hyperdrive-network-speed/issues" 17 | }, 18 | "homepage": "https://github.com/joehand/hyperdrive-network-speed#readme", 19 | "dependencies": { 20 | "debug": "^3.1.0", 21 | "speedometer": "^1.0.0" 22 | }, 23 | "devDependencies": { 24 | "hyperdiscovery": "^7.0.0", 25 | "hyperdrive": "^9.0.0", 26 | "pump": "^3.0.0", 27 | "random-access-memory": "^2.3.0", 28 | "standard": "^11.0.0", 29 | "tap-spec": "^4.1.1", 30 | "tape": "^4.6.3" 31 | } 32 | } 33 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | Copyright (c) 2016 Joe Hand 2 | 3 | Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions: 4 | 5 | The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software. 6 | 7 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. -------------------------------------------------------------------------------- /readme.md: -------------------------------------------------------------------------------- 1 | [![deprecated](http://badges.github.io/stability-badges/dist/deprecated.svg)](https://dat-ecosystem.org/) 2 | 3 | More info on active projects and modules at [dat-ecosystem.org](https://dat-ecosystem.org/) 4 | 5 | --- 6 | 7 | # hyperdrive-network-speed 8 | 9 | [![Travis](https://img.shields.io/travis/datproject/hyperdrive-network-speed.svg?style=flat-square)](https://travis-ci.org/datproject/hyperdrive-network-speed) [![npm](https://img.shields.io/npm/v/hyperdrive-network-speed.svg?style=flat-square)](https://npmjs.org/package/hyperdrive-network-speed) 10 | 11 | Get upload and download speeds for a hyperdrive archive. 12 | 13 | ## Usage 14 | 15 | ```js 16 | var archive = hyperdrive('.dat') 17 | var swarm = hyperdiscovery(archive) 18 | var speed = networkSpeed(archive, {timeout: 1000}) 19 | 20 | setInterval(function () { 21 | console.log('upload speed: ', speed.uploadSpeed) 22 | console.log('download speed: ', speed.downloadSpeed) 23 | }, 500) 24 | ``` 25 | 26 | ## API 27 | 28 | ### `var speed = networkSpeed(archive, [opts])` 29 | 30 | * `archive` is a hyperdrive archive. 31 | * `opts.timeout` is the only option. Speed will be reset to zero after the timeout. 32 | 33 | #### `speed.uploadSpeed` 34 | 35 | Archive upload speed across all peers. 36 | 37 | #### `speed.downloadSpeed` 38 | 39 | Archive download speed across all peers. 40 | 41 | #### `speed.downloadTotal` 42 | 43 | Archive total download. 44 | 45 | #### `speed.uploadTotal` 46 | 47 | Archive total upload. 48 | 49 | ## License 50 | 51 | MIT 52 | -------------------------------------------------------------------------------- /index.js: -------------------------------------------------------------------------------- 1 | var assert = require('assert') 2 | var speedometer = require('speedometer') 3 | var debug = require('debug')('dat-network') 4 | 5 | module.exports = function (archive, opts) { 6 | assert.ok(archive, 'archive required') 7 | opts = opts || {} 8 | 9 | var speed = {} 10 | var downloadSpeed = speedometer() 11 | var uploadSpeed = speedometer() 12 | var timeout = opts.timeout || 1000 13 | var upTimeout = null 14 | var downTimeout = null 15 | var totalTransfer = { 16 | up: 0, 17 | down: 0 18 | } 19 | 20 | if (debug.enabled) { 21 | setInterval(function () { 22 | if (totalTransfer.up) debug('Uploaded data:', totalTransfer.up) 23 | if (totalTransfer.down) debug('Downloaded data:', totalTransfer.down) 24 | }, 500) 25 | } 26 | 27 | archive.metadata.on('download', function (block, data) { 28 | totalTransfer.down += data.length 29 | ondownload(data.length) 30 | }) 31 | 32 | archive.metadata.on('upload', function (block, data) { 33 | totalTransfer.up += data.length 34 | onupload(data.length) 35 | }) 36 | 37 | if (archive.content) trackContent() 38 | else archive.on('content', trackContent) 39 | 40 | Object.defineProperty(speed, 'downloadSpeed', { 41 | enumerable: true, 42 | get: function () { return downloadSpeed() } 43 | }) 44 | 45 | Object.defineProperty(speed, 'uploadSpeed', { 46 | enumerable: true, 47 | get: function () { return uploadSpeed() } 48 | }) 49 | 50 | Object.defineProperty(speed, 'downloadTotal', { 51 | enumerable: true, 52 | get: function () { return totalTransfer.down } 53 | }) 54 | 55 | Object.defineProperty(speed, 'uploadTotal', { 56 | enumerable: true, 57 | get: function () { return totalTransfer.up } 58 | }) 59 | 60 | return speed 61 | 62 | function trackContent () { 63 | archive.content.on('download', function (block, data) { 64 | totalTransfer.down += data.length 65 | ondownload(data.length) 66 | }) 67 | 68 | archive.content.on('upload', function (block, data) { 69 | totalTransfer.up += data.length 70 | onupload(data.length) 71 | }) 72 | } 73 | 74 | // Zero out for uploads & disconnections 75 | function downZero () { 76 | downloadSpeed = speedometer() 77 | if (downTimeout) clearTimeout(downTimeout) 78 | } 79 | 80 | function upZero () { 81 | uploadSpeed = speedometer() 82 | if (upTimeout) clearTimeout(upTimeout) 83 | } 84 | 85 | function ondownload (bytes) { 86 | downloadSpeed(bytes) 87 | if (downTimeout) clearTimeout(downTimeout) 88 | downTimeout = setTimeout(downZero, timeout) 89 | } 90 | 91 | function onupload (bytes) { 92 | uploadSpeed(bytes) 93 | if (upTimeout) clearTimeout(upTimeout) 94 | upTimeout = setTimeout(upZero, timeout) 95 | } 96 | } 97 | -------------------------------------------------------------------------------- /test.js: -------------------------------------------------------------------------------- 1 | var fs = require('fs') 2 | var test = require('tape') 3 | var hyperdrive = require('hyperdrive') 4 | var ram = require('random-access-memory') 5 | var hyperdiscovery = require('hyperdiscovery') 6 | var pump = require('pump') 7 | 8 | var networkSpeed = require('.') 9 | 10 | var archive = hyperdrive(ram) 11 | var swarm 12 | 13 | archive.ready(function () { 14 | swarm = hyperdiscovery(archive) 15 | 16 | pump(fs.createReadStream('test.js'), archive.createWriteStream('test.js'), function (err) { 17 | if (err) throw err 18 | pump(fs.createReadStream('test.js'), archive.createWriteStream('test.js'), function (err) { 19 | if (err) throw err 20 | run() 21 | }) 22 | }) 23 | }) 24 | 25 | function run () { 26 | test('tracks upload speed', function (t) { 27 | var speed = networkSpeed(archive) 28 | 29 | var archiveClient = hyperdrive(ram, archive.key) 30 | 31 | archiveClient.ready(function () { 32 | var swarmClient = hyperdiscovery(archiveClient) 33 | 34 | archive.content.once('upload', function () { 35 | t.ok(speed.uploadTotal && speed.uploadTotal > 0, 'has upload total') 36 | t.ok(speed.uploadSpeed && speed.uploadSpeed > 0, 'has upload speed') 37 | t.ok(Object.keys(speed).indexOf('uploadSpeed') > -1, 'uploadSpeed enumerable') 38 | swarmClient.close(function () { 39 | t.end() 40 | }) 41 | }) 42 | }) 43 | }) 44 | 45 | test('tracks download speed', function (t) { 46 | var archiveClient = hyperdrive(ram, archive.key) 47 | var speed = networkSpeed(archiveClient) 48 | 49 | archiveClient.ready(function () { 50 | var swarmClient = hyperdiscovery(archiveClient) 51 | 52 | archiveClient.once('content', function () { 53 | archiveClient.content.once('download', function () { 54 | t.ok(speed.downloadTotal && speed.downloadTotal > 0, 'has download total') 55 | t.ok(speed.downloadSpeed && speed.downloadSpeed > 0, 'has download speed') 56 | t.ok(Object.keys(speed).indexOf('downloadSpeed') > -1, 'downloadSpeed enumerable') 57 | swarmClient.close(function () { 58 | t.end() 59 | }) 60 | }) 61 | }) 62 | }) 63 | }) 64 | 65 | test('zeros out speed after finishing', function (t) { 66 | var archiveClient = hyperdrive(ram, archive.key) 67 | var speedDown = networkSpeed(archiveClient) 68 | var stream = archiveClient.replicate({live: false}) 69 | 70 | archiveClient.ready(function () { 71 | var swarmClient = hyperdiscovery(archiveClient, {stream: function () { return stream}}) 72 | 73 | stream.once('close', function () { 74 | setTimeout(ondone, 300) 75 | }) 76 | 77 | function ondone () { 78 | t.same(speedDown.downloadSpeed, 0, 'download speed zero') 79 | swarmClient.close(function () { 80 | t.end() 81 | }) 82 | } 83 | }) 84 | }) 85 | 86 | test('zeros out speed after disconnection', function (t) { 87 | var archiveClient = hyperdrive(ram, archive.key) 88 | var speedDown = networkSpeed(archiveClient, {timeout: 250}) 89 | var speedUp = networkSpeed(archive, {timeout: 250}) 90 | 91 | archiveClient.ready(function () { 92 | var swarmClient = hyperdiscovery(archiveClient) 93 | archiveClient.metadata.once('download', function () { 94 | setTimeout(function () { 95 | t.same(speedUp.uploadSpeed, 0, 'upload speed zero') 96 | t.same(speedDown.downloadSpeed, 0, 'download speed zero') 97 | 98 | swarmClient.close(function () { 99 | swarm.close(function () { 100 | t.end() 101 | }) 102 | }) 103 | }, 500) 104 | swarmClient.leave(archive.key) 105 | }) 106 | }) 107 | }) 108 | } 109 | --------------------------------------------------------------------------------