nem-voting
TypeScript icon, indicating that this package has built-in type declarations

2.2.9 • Public • Published

NEM Voting

npm version Build Status Coverage Status License: MIT

nem-voting is a typescript / node.js module for using the NEM voting functionalities easily on any project. Created using NEM-library.

  1. Installation
  2. Examples
  3. Definitions
  4. Technical specification

Installation

to install the npm module on your typescript or node project run:

npm install nem-voting --save

the module is made to work together with nem-library, so you should install that too:

npm install nem-library@1.0.5 --save

it is important that 1.0.5 is installed since it needs to be the same version than the one in nem-voting

Examples

The module exports two main classes: UnbroadcastedPoll and BroadcastedPoll. They represent polls that exist only locally and polls that exist in the blockchain, respectively.

It also exports a PollConstants object with various usefull constants for voting and a PollIndex object for handling indexes other than the public one (public and private), along with some useful functions specified below.

Creating and Broadcasting a Poll to the blockchain

import { PollConstants, UnbroadcastedPoll, BroadcastedPoll } from "nem-voting";
import { NEMLibrary, NetworkTypes, Account, TransactionHttp } from "nem-library";
import { Observable } from "rxjs";

// This function will bootstrap both the internal nem-library for nem-voting and the local one
// if the local version of nem-library and the one in nem-voting don't match then this will give problems
NEMLibrary.bootstrap(NetworkTypes.TEST_NET); // Change to NetworkTypes.MAIN_NET for main net
const testPrivateKey = "c195d7699662b0e2dfae6a4aef87a082d11f74d2bd583f7dec5663a107823691"; // introduce the poll creator private key

const formData = {
    title: "test poll 2.0",
    doe: Date.now() + (60 * 1000 * 60), // Date of ending as timestamp in milliseconds
    type: PollConstants.POI_POLL, // type of vote counting
    multiple: false, // true if multiple votes are allowed
};
const description = "This is the description for the poll";
const options = ["option 1", "option 2"];

// Create poll object
const poll = new UnbroadcastedPoll(formData, description, options);
const account = Account.createWithPrivateKey(testPrivateKey);

// We get the broadcasted poll data, including the poll address and the option addresses
const broadcastData = poll.broadcast(account.publicKey);
// Now we sign and broadcast the transactions
const transactionHttp = new TransactionHttp();
Observable.merge(...(broadcastData.transactions.map((t) => {
    const signed = account.signTransaction(t);
    return transactionHttp.announceTransaction(signed);
})))
    .last()
    .subscribe(() => {
        // The poll is now broadcasted, but we need to wait for all the transactions to be confirmed
        console.log(broadcastData.broadcastedPoll);
    });

Fetching a Poll from the blockchain

import { BroadcastedPoll, NEMVoting } from "nem-voting";
import { NEMLibrary, Address, NetworkTypes } from "nem-library";

// This function will bootstrap both the internal nem-library for nem-voting and the local one
// if the local version of nem-library and the one in nem-voting don't match then this will give problems
NEMLibrary.bootstrap(NetworkTypes.TEST_NET); // Change to NetworkTypes.MAIN_NET for main net
const pollAddress = new Address("TCX6LT3Y43IQL3DKU6FAGDMWJFROQGFPWSJMUY7R");

BroadcastedPoll.fromAddress(pollAddress)
    .map((poll) => {
        return poll;
    })
    .subscribe((data) => {
        console.log(data);
    });

Getting the results for a broadcasted poll

import { BroadcastedPoll, NEMVoting } from "nem-voting";
import { NEMLibrary, Address, NetworkTypes } from "nem-library";

// This function will bootstrap both the internal nem-library for nem-voting and the local one
// if the local version of nem-library and the one in nem-voting don't match then this will give problems
NEMLibrary.bootstrap(NetworkTypes.TEST_NET); // Change to NetworkTypes.MAIN_NET for main net
const pollAddress = new Address("TCX6LT3Y43IQL3DKU6FAGDMWJFROQGFPWSJMUY7R");

BroadcastedPoll.fromAddress(pollAddress)
    .switchMap((poll) => {
        return poll.getResults();
    })
    .subscribe((results) => {
        console.log(results);
    });

Voting on a poll

import { BroadcastedPoll } from "nem-voting";
import { NEMLibrary, Address, NetworkTypes, Account, TransactionHttp } from 'nem-library';

// This function will bootstrap both the internal nem-library for nem-voting and the local one
// if the local version of nem-library and the one in nem-voting don't match then this will give problems
NEMLibrary.bootstrap(NetworkTypes.TEST_NET); // Change to NetworkTypes.MAIN_NET for main net
const pollAddress = new Address("TBW2PIAVJPW7QRHWJ74PA4E36B6FNE7QWGOI3JAF"); // Poll Address
const testPrivateKey = "c195d7699662b0e2dfae6a4aef87a082d11f74d2bd583f7dec5663a107823691"; // Voter private key
const account = Account.createWithPrivateKey(testPrivateKey);

BroadcastedPoll.fromAddress(pollAddress)
    .switchMap((poll) => {
        // It is important to validate that a poll is valid before voting
        if (!poll.validate()) {
            throw new Error("Invalid Poll");
        }
        const voteTransaction = poll.vote(poll.data.options[0]); // get vote transaction
        const signed = account.signTransaction(voteTransaction); // sign transaction
        const transactionHttp = new TransactionHttp();
        return transactionHttp.announceTransaction(signed); // broadcast transaction
    })
    .subscribe((announceResult) => {
        console.log(announceResult);
    });

Definitions

UnbroadcastedPoll

interface IFormData {
    /**
     * Title of the poll
     */
    title: string;
    /**
     * date of ending, as milliseconds from UNIX epoch
     */
    doe: number;
    /**
     * True if multiple votes are accepted
     */
    multiple: boolean;
    /**
     * type of the poll
     */
    type: number;
}
interface IPollData {
    /**
     * General information abount the poll
     */
    formData: IFormData;
    /**
     * Detailed description for the poll
     */
    description: string;
    /**
     * Options of the poll
     */
    options: string[];
    /**
     * (optional) Array of Addresses to be whitelisted. Only for whitelist polls
     */
    whitelist?: Address[];
}
interface IBroadcastData {
    /**
     * Transactions that need to be sent and confirmed for the poll to be broadcasted
     */
    transactions: TransferTransaction[];
    /**
     * Broadcasted Poll object. Can not be used until the transactions have been broadcasted and confirmed
     */
    broadcastedPoll: BroadcastedPoll;
}
/**
 * Abstract class that represents a poll
 */
declare abstract class Poll {
    readonly data: IPollData;
}
/**
 * An unbroadcasted poll. Exists only locally and not on the blockchain yet
 */
declare class UnbroadcastedPoll extends Poll {
    constructor(formData: IFormData, description: string, options: string[], whitelist?: Address[]);
    /**
     * Broadcasts an unbroadcasted poll and returns the resulting broadcasted poll object (as a promise)
     * @param creatorPublicKey - public key of the poll creator
     * @param pollIndex - optionally provide the poll index to send the poll to.
     *                    If not specified the default public index is used
     * @return {pollAddress: Address, transactions: TransferTransaction[]} - returns the poll address
     * and the transactions that need to be sent for it to be broadcasted
     */
    broadcast: (creatorPublicKey: string, pollIndex?: PollIndex | undefined) => IBroadcastData;
}

BroadcastedPoll

/**
 * A broadcasted poll. Represents a Poll that exists in the blockchain.
 */
declare class BroadcastedPoll extends Poll {
    /**
     * The poll address
     */
    readonly address: Address;
    /**
     * Map from option to option address
     */
    private optionAddresses;
    /**
     * Fetches a Broadcasted Poll from the blockchain by its address
     * @param pollAddress - The poll's NEM Address
     * @return Promise<BroadcastedPoll>
     */
    private static fromAddressPromise;
    /**
     * Fetches a Broadcasted Poll from the blockchain by its address
     * @param pollAddress - The poll's NEM Address
     * @return Observable<BroadcastedPoll>
     */
    static fromAddress: (pollAddress: Address) => Observable<BroadcastedPoll>;
    /**
     * Gets the option address for a given option
     * @param option - The option
     * @return Address | null
     */
    getOptionAddress: (option: string) => Address | null;
    /**
     * Gets the results for the poll
     * @param pollAddress - The poll's NEM Address
     * @return Observable<IResults>
     */
    getResults: () => Observable<IResults>;
    /**
     * Gets the results for the poll as a csv string
     * @param pollAddress - The poll's NEM Address
     * @return Observable<string>
     */
    getCsvResults: () => Observable<string>;
    /**
     * Gets the results for the poll as an array of vote objects
     * @param pollAddress - The poll's NEM Address
     * @return Observable<IResults>
     */
    getVoters: () => Observable<IVote[]>;
    /**
     * validates a poll's structure and returns wether it is correct or not
     * @return boolean
     */
    validate: () => boolean;
    /**
     * Votes on the poll from a given account, returns the vote transaction result
     * @param option - The option to vote
     * @return TransferTransaction - the transaction that needs to be sent to vote
     */
    vote: (option: string) => TransferTransaction;
    /**
     * Votes on the poll from a multisig account, returns the vote transaction result
     * @param multisigAccount - The public account of the multisig account that votes
     * @param option - The option to vote
     * @return MultisigTransaction - the transaction that needs to be sent to vote
     */
    voteMultisig: (multisigAccount: PublicAccount, option: string) => MultisigTransaction;
    /**
     * Gets the votes that an address has sent to the poll, if it has not voted returns null
     * @param address - The address of the voter
     * @return Observable<Transaction[] | null>
     */
    getVotes: (address: Address) => Observable<Transaction[] | null>;
}

Constants

export const PollConstants = {
    /**
     * Poll Types
     */
    POI_POLL: 0,
    WHITELIST_POLL: 1,

    /**
     * Poll Indexes
     */
    TESTNET_POLL_INDEX: "TAVGTNCVGALLUPZC4JTLKR2WX25RQM2QOK5BHBKC",
    MAINNET_POLL_INDEX: "NAZN26HYB7C5HVYVJ4SL3KBTDT773NZBAOMGRFZB",
};

Poll Indexes

/**
 * Represents the info from a poll header sent to an index
 */
interface IPollHeader {
    title: string;
    type: number;
    doe: number;
    address: Address;
    whitelist?: Address[];
}
/**
 * Contains the info for a poll index, public or private
 */
declare class PollIndex {
    /**
     * Poll Index Address
     */
    address: Address;
    /**
     * true if the index is private. On private indexes only the creator can send valid polls
     */
    isPrivate: boolean;
    /**
     * the creator of the poll, only needed for private indexes
     */
    creator?: Address;
    /**
     * array of broadcasted header polls for the index
     */
    headers: IPollHeader[];
    /**
     * Gets a poll index from its address with all of its broadcasted polls
     * @param address - the index account address
     * @return Observable<PollIndex>
     */
    static fromAddress: (address: Address) => Observable<PollIndex>;
    /**
     * Creates a new poll Index
     * @param isPrivate - will create a private index if true
     * @param creatorAddress - needed only if the index is private
     * @return Observable<PollIndex>
     */
    static create: (isPrivate: boolean, creatorAddress?: Address | undefined) => {
        address: Address;
        transaction: TransferTransaction;
    };
}
/**
 * Gets the addresses for all the poll indexes created by an address
 * @param creator - the address of the creator of the indexes we want
 * @return Observable<Address[]>
 */
declare const getCreatedIndexAddresses: (creator: Address) => Observable<Address[]>;

Technical specification

A Detailed Technical description of the NEM voting Standard is mantained at https://github.com/shierve/NEM-voting-specifications

Versions

Current Tags

VersionDownloads (Last 7 Days)Tag
2.2.94latest

Version History

VersionDownloads (Last 7 Days)Published
2.2.94
2.2.70
2.2.61
2.2.50
2.2.40
2.2.31
2.2.20
2.2.11
2.2.01
2.1.30
2.1.20
2.1.10
2.1.00
2.0.111
2.0.100
2.0.90
2.0.80
2.0.70
2.0.61
2.0.51
2.0.40
2.0.30
2.0.20
2.0.10
2.0.00
1.2.20
1.2.10
1.2.00
1.1.200
1.1.190
1.1.180
1.1.170
1.1.160
1.1.150
1.1.141
1.1.110
1.1.100
1.1.91
1.1.80
1.1.70
1.1.61
1.1.52
1.1.40
1.1.30
1.1.20
1.1.10
1.1.00
1.0.91
1.0.80
1.0.70
1.0.50
1.0.40
1.0.30
1.0.20
1.0.10
1.0.00

Package Sidebar

Install

npm i nem-voting

Weekly Downloads

17

Version

2.2.9

License

MIT

Unpacked Size

145 kB

Total Files

27

Last publish

Collaborators

  • shierve