microstellar

package module
v0.1.9 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Mar 10, 2018 License: MIT Imports: 13 Imported by: 3

README


MicroStellar is an easy-to-use Go client for the Stellar blockchain network. The API is simple and clean, without sacrificing flexibility.

MicroStellar is intended to be robust, well tested, and well documented -- we designed it for our Microbanking platform at @qubit-sh. It's also fun to use!

To get started, follow the instructions below, or read the API docs for more.

QuickStart

Installation

go get github.com/0xfe/microstellar

Usage

Create and fund addresses
// Create a new MicroStellar client connected to the testnet. Use "public" to
// connect to public horizon servers, or "custom" to connect to your own instance.
ms := microstellar.New("test")

// Generate a new random keypair. In stellar lingo, a "seed" is a private key, and
// an "address" is a public key. (Not techincally accurate, but you get the picture.)
//
// Seed strings begin with "S" -- "S6H4HQPE6BRZKLK3QNV6LTD5BGS7S6SZPU3PUGMJDJ26V7YRG3FRNPGA"
// Address strings begin with "G" -- "GAUYTZ24ATLEBIV63MXMPOPQO2T6NHI6TQYEXRTFYXWYZ3JOCVO6UYUM"
pair, _ := ms.CreateKeyPair()
log.Print(pair.Seed, pair.Address)

// In stellar, you can create all kinds of asset types -- dollars, houses, kittens. These
// customized assets are called credit assets.
//
// However, the native asset is always lumens (XLM). Lumens are used to pay for transactions
// on the stellar network, and are used to fund the operations of Stellar.
//
// When you first create a key pair, you need to fund it with atleast 0.5 lumens. This
// is called the "base reserve", and makes the account valid. You can only transact to
// and from accounts that maintain the base reserve.
ms.FundAccount(
  "S6H4HQPE6BRZKLK3QNV6LTD5BGS7S6SZPU3PUGMJDJ26V7YRG3FRNPGA", // func source
  pair.Address,                                               // fund destination
  "1")                                                        // amount in lumens (XLM)

// On the test network, you can ask FriendBot to fund your account. You don't need to buy
// lumens. (If you do want to buy lumens for the test network, call me!)
microstellar.FundWithFriendBot(pair.Address)
Check balances
// Now load the account details from the ledger.
account, _ := ms.LoadAccount(pair.Address)

log.Printf("Native Balance: %v XLM", account.GetNativeBalance())
Make payments
// Pay someone 3 lumens.
ms.PayNative(
  "S6H4HQPE6BRZKLK3QNV6LTD5BGS7S6SZPU3PUGMJDJ26V7YRG3FRNPGA", // from
  "GAUYTZ24ATLEBIV63MXMPOPQO2T6NHI6TQYEXRTFYXWYZ3JOCVO6UYUM", // to
  "3")

// Set the memo field on a payment
ms.Pay(
  "S6H4HQPE6BRZKLK3QNV6LTD5BGS7S6SZPU3PUGMJDJ26V7YRG3FRNPGA", // from
  "GAUYTZ24ATLEBIV63MXMPOPQO2T6NHI6TQYEXRTFYXWYZ3JOCVO6UYUM", // to
  "3", microstellar.Opts().WithMemoText("thanks for the fish"))
Work with credit assets
// Create a custom asset with the code "USD" issued by some trusted issuer
USD := microstellar.NewAsset(
  "USD", // asset code
  "G6H4HQPE6BRZKLK3QNV6LTD5BGS7S6SZPU3PUGMJDJ26V7YRG3FRNPGA", // issuer address
  Credit4Type) // asset type (Credit4Type, Credit12Type, NativeType)

// Create a trust line from an account to the asset, with a limit of 10000
ms.CreateTrustLine(
  "S4H4HQPE6BRZKLK3QNV6LTD5BGS7S6SZPU3PUGMJDJ26V7YRG3FRNPGA", // source account
  USD,     // asset to trust
  "10000") // max holdings of this asset

// Make a payment in the asset
ms.Pay(
  "S6H4HQPE6BRZKLK3QNV6LTD5BGS7S6SZPU3PUGMJDJ26V7YRG3FRNPGA", // from
  "GAUYTZ24ATLEBIV63MXMPOPQO2T6NHI6TQYEXRTFYXWYZ3JOCVO6UYUM", // to
  USD, 10, microstellar.Opts().WithMemo("funny money"))
Multisignature payments
// Add two signers with weight 1 to account
ms.AddSigner(
  "S8H4HQPE6BRZKLK3QNV6LTD5BGS7S6SZPU3PUGMJDJ26V7YRG3FRNPGA", // source account
  "G6H4HQPE6BRZKLK3QNV6LTD5BGS7S6SZPU3PUGMJDJ26V7YRG3FRNPGA", // signer address
  1) // weight

ms.AddSigner(
  "S8H4HQPE6BRZKLK3QNV6LTD5BGS7S6SZPU3PUGMJDJ26V7YRG3FRNPGA", // source account
  "G9H4HQPE6BRZKLK3QNV6LTD5BGS7S6SZPU3PUGMJDJ26V7YRG3FRNPGB", // signer address
  1) // weight

// Set the low, medium, and high thresholds of the account. (Here we require a minimum
// total signing weight of 2 for all operations.)
ms.SetThresholds("S8H4HQPE6BRZKLK3QNV6LTD5BGS7S6SZPU3PUGMJDJ26V7YRG3FRNPGA", 2, 2, 2)

// Kill the master weight of account, so only the new signers can sign transactions
ms.SetMasterWeight("S8H4HQPE6BRZKLK3QNV6LTD5BGS7S6SZPU3PUGMJDJ26V7YRG3FRNPGA", 0,
   microstellar.Opts().WithSigner("S2H4HQPE6BRZKLK3QNV6LTD5BGS7S6SZPU3PUGMJDJ26V7YRG3FRNPGA"))

// Make a payment (and sign with new signers). Note that the first parameter (source) here
// can be an address instead of a seed (since the seed can't sign anymore.)
ms.PayNative(
  "G6H4HQPE6BRZKLK3QNV6LTD5BGS7S6SZPU3PUGMJDJ26V7YRG3FRNPGA", // from
  "GAUYTZ24ATLEBIV63MXMPOPQO2T6NHI6TQYEXRTFYXWYZ3JOCVO6UYUM", // to
  "3", // amount
  microstellar.Opts().
    WithSigner("S1H4HQPE6BRZKLK3QNV6LTD5BGS7S6SZPU3PUGMJDJ26V7YRG3FRNPGA").
    WithSigner("S2H4HQPE6BRZKLK3QNV6LTD5BGS7S6SZPU3PUGMJDJ26V7YRG3FRNPGA"))

Streaming
// Watch for payments to address. (The fake network sends payments every 200ms.)
watcher, err := ms.WatchPayments("GCCRUJJGPYWKQWM5NLAXUCSBCJKO37VVJ74LIZ5AQUKT6KPVCPNAGC4A")

go func() {
  for p := range watcher.Ch {
    log.Printf("WatchPayments: %v -- %v %v from %v to %v\n",
      p.Type, p.Amount, p.AssetCode, p.From, p.To)
  }
  log.Printf("WatchPayments Done -- Error: %v\n", *watcher.StreamError)
}()

// Stream the ledger for about a second then stop the watcher.
time.Sleep(1 * time.Second)
watcher.Done()
Other stuff
// What's their USD balance?
account, _ = ms.LoadAccount("GAUYTZ24ATLEBIV63MXMPOPQO2T6NHI6TQYEXRTFYXWYZ3JOCVO6UYUM")
log.Printf("USD Balance: %v USD", account.GetBalance(USD))

// What's their home domain?
log.Printf("Home domain: %s", account.HomeDomain)

// Who are the signers on the account?
for i, s := range account.Signers {
    log.Printf("Signer %d (weight: %v): %v", i, s.PublicKey, s.Weight)
}

Documentation

Supported Features

  • Account creation and funding
  • Lookup balances, home domain, and account signers
  • Payment of native and custom assets
  • Add and remove trust lines
  • Multisig accounts -- add/remove signers and make multisig payments.
  • Watch the ledger for streaming payments

Coming Soon

  • Offer management
  • Path payments

Hacking on MicroStellar

Contribution Guidelines

  • We're managing dependencies with dep.
    • Add a new dependency with dep ensure -add ...
  • If you're adding a new feature:
    • Add unit tests
    • Add godoc comments
    • If necessary, update the integration test in macrotest/
    • If necessary, add examples and verify that they show up in godoc

Environment Setup

This package uses dep to manage dependencies. Before hacking on this package, install all dependencies:

dep ensure

Run tests

Run all unit tests:

go test -v ./...

Run end-to-end integration test:

go run -v macrotest/macrotest.go

Test documentation with:

godoc -v -http=:6060

Then: http://localhost:6060/pkg/github.com/0xfe/microstellar/

Updating dependencies

# Updates dependencies in vendor/ to latest tags/releases
dep ensure -update

# rinse and repeat
go test -v ./...

Versioning

This package uses semver versioning:

git tag v0.1.0
git push --tags

MIT License

Copyright Mohit Muthanna Cheppudira 2018 mohit@muthanna.com

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:

The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.

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.

Documentation

Overview

Package microstellar is an easy-to-use Go client for the Stellar network.

go get github.com/0xfe/microstellar

Author: Mohit Muthanna Cheppudira <mohit@muthanna.com>

Usage notes

In Stellar lingo, a private key is called a seed, and a public key is called an address. Seed strings start with "S", and address strings start with "G". (Not techincally accurate, but you get the picture.)

Seed:    S6H4HQPE6BRZKLK3QNV6LTD5BGS7S6SZPU3PUGMJDJ26V7YRG3FRNPGA
Address: GAUYTZ24ATLEBIV63MXMPOPQO2T6NHI6TQYEXRTFYXWYZ3JOCVO6UYUM

In most the methods below, the first parameter is usually "sourceSeed", which should be the seed of the account that signs the transaction.

You can add a *TxOptions struct to the end of many methods, which set extra parameters on the submitted transaction. If you add new signers via TxOptions, then sourceSeed will not be used to sign the transaction -- and it's okay to use a public address instead of a seed for sourceSeed. See examples for how to use TxOptions.

You can use ErrorString(...) to extract the Horizon error from a returned error.

Example
// Create a new MicroStellar client connected to a mock network.
ms := New("fake")

// Generate a new random keypair.
pair, _ := ms.CreateKeyPair()

// In stellar, you can create all kinds of asset types -- dollars, houses, kittens. These
// customized assets are called credit assets.
//
// However, the native asset is always lumens (XLM). Lumens are used to pay for transactions
// on the stellar network, and are used to fund the operations of Stellar.
//
// When you first create a key pair, you need to fund it with atleast 0.5 lumens. This
// is called the "base reserve", and makes the account valid. You can only transact to
// and from accounts that maintain the base reserve.
ms.FundAccount("S6H4HQPE6BRZKLK3QNV6LTD5BGS7S6SZPU3PUGMJDJ26V7YRG3FRNPGA", pair.Address, "1")

// On the test network, you can ask FriendBot to fund your account. You don't need to buy
// lumens. (If you do want to buy lumens for the test network, call me!)
FundWithFriendBot(pair.Address)

// Now load the account from the ledger and check its balance.
account, _ := ms.LoadAccount(pair.Address)
log.Printf("Native Balance: %v XLM", account.GetNativeBalance())

// Note that we used GetNativeBalance() above, which implies lumens as the asset. You
// could also do the following.
log.Printf("Native Balance: %v XLM", account.GetBalance(NativeAsset))

// Pay your buddy 3 lumens.
ms.PayNative("S6H4HQPE6BRZKLK3QNV6LTD5BGS7S6SZPU3PUGMJDJ26V7YRG3FRNPGA",
	"GAUYTZ24ATLEBIV63MXMPOPQO2T6NHI6TQYEXRTFYXWYZ3JOCVO6UYUM", "3")

// Alternatively, be explicit about lumens.
ms.Pay("S6H4HQPE6BRZKLK3QNV6LTD5BGS7S6SZPU3PUGMJDJ26V7YRG3FRNPGA",
	"GAUYTZ24ATLEBIV63MXMPOPQO2T6NHI6TQYEXRTFYXWYZ3JOCVO6UYUM", "3", NativeAsset)

// Create a credit asset called USD issued by anchor GAT5GKDILNY2G6NOBEIX7XMGSPPZD5MCHZ47MGTW4UL6CX55TKIUNN53
USD := NewAsset("USD", "GAT5GKDILNY2G6NOBEIX7XMGSPPZD5MCHZ47MGTW4UL6CX55TKIUNN53", Credit4Type)

// Pay your buddy 3 USD and add a memo
ms.Pay("S6H4HQPE6BRZKLK3QNV6LTD5BGS7S6SZPU3PUGMJDJ26V7YRG3FRNPGA",
	"GAUYTZ24ATLEBIV63MXMPOPQO2T6NHI6TQYEXRTFYXWYZ3JOCVO6UYUM",
	"3", USD,
	Opts().WithMemoText("for beer"))

// Create a trust line to the USD credit asset with a limit of 1000.
ms.CreateTrustLine("S4H4HQPE6BRZKLK3QNV6LTD5BGS7S6SZPU3PUGMJDJ26V7YRG3FRNPGA", USD, "10000")

// Check your balances.
account, _ = ms.LoadAccount("GAUYTZ24ATLEBIV63MXMPOPQO2T6NHI6TQYEXRTFYXWYZ3JOCVO6UYUM")
log.Printf("USD Balance: %v USD", account.GetBalance(USD))
log.Printf("Native Balance: %v XLM", account.GetNativeBalance())

// Find your home domain.
log.Printf("Home domain: %s", account.HomeDomain)

// Who are the signers on the account?
for i, s := range account.Signers {
	log.Printf("Signer %d (weight: %v): %v", i, s.PublicKey, s.Weight)
}

log.Printf("ok")
Example (Multisig)
// Create a new MicroStellar client connected to a mock network.
ms := New("fake")

// Add two signers to the source account with weight 1 each
ms.AddSigner(
	"S8H4HQPE6BRZKLK3QNV6LTD5BGS7S6SZPU3PUGMJDJ26V7YRG3FRNPGA", // source account
	"G6H4HQPE6BRZKLK3QNV6LTD5BGS7S6SZPU3PUGMJDJ26V7YRG3FRNPGA", // signer address
	1) // weight

ms.AddSigner(
	"S8H4HQPE6BRZKLK3QNV6LTD5BGS7S6SZPU3PUGMJDJ26V7YRG3FRNPGA", // source account
	"G9H4HQPE6BRZKLK3QNV6LTD5BGS7S6SZPU3PUGMJDJ26V7YRG3FRNPGB", // signer address
	1) // weight

// Set the low, medium, and high thresholds of the account. (Here we require a minimum
// total signing weight of 2 for all operations.)
ms.SetThresholds("S8H4HQPE6BRZKLK3QNV6LTD5BGS7S6SZPU3PUGMJDJ26V7YRG3FRNPGA", 2, 2, 2)

// Kill the master weight of account, so only the new signers can sign transactions
ms.SetMasterWeight("S8H4HQPE6BRZKLK3QNV6LTD5BGS7S6SZPU3PUGMJDJ26V7YRG3FRNPGA", 0,
	Opts().WithSigner("S2H4HQPE6BRZKLK3QNV6LTD5BGS7S6SZPU3PUGMJDJ26V7YRG3FRNPGA"))

// Make a payment (and sign with new signers). Note that the first parameter (source) here
// can be an address instead of a seed (since the seed can't sign anymore.)
ms.PayNative(
	"G6H4HQPE6BRZKLK3QNV6LTD5BGS7S6SZPU3PUGMJDJ26V7YRG3FRNPGA", // from
	"GAUYTZ24ATLEBIV63MXMPOPQO2T6NHI6TQYEXRTFYXWYZ3JOCVO6UYUM", // to
	"3", // amount
	Opts().
		WithSigner("S1H4HQPE6BRZKLK3QNV6LTD5BGS7S6SZPU3PUGMJDJ26V7YRG3FRNPGA").
		WithSigner("S2H4HQPE6BRZKLK3QNV6LTD5BGS7S6SZPU3PUGMJDJ26V7YRG3FRNPGA"))

log.Printf("ok")

Index

Examples

Constants

View Source
const (
	// FlagAuthRequired requires the issuing account to give the receiving
	// account permission to hold the asset.
	FlagAuthRequired = AccountFlags(1)

	// FlagAuthRevocable allows the issuer to revoke the credit held by another
	// account.
	FlagAuthRevocable = AccountFlags(2)

	// FlagAuthImmutable means that the other auth parameters can never be set
	// and the issuer's account can never be deleted.
	FlagAuthImmutable = AccountFlags(4)
)
View Source
const (
	MemoNone   = MemoType(0) // No memo
	MemoID     = MemoType(1) // ID memo
	MemoText   = MemoType(2) // Text memo (max 28 chars)
	MemoHash   = MemoType(3) // Hash memo
	MemoReturn = MemoType(4) // Return hash memo
)

Variables

View Source
var NativeAsset = &Asset{"XLM", "", NativeType}

NativeAsset is a convenience const representing a native asset.

Functions

func ErrorString

func ErrorString(err error, showStackTrace ...bool) string

ErrorString parses the horizon error out of err.

func FundWithFriendBot

func FundWithFriendBot(address string) (string, error)

FundWithFriendBot funds address on the test network with some initial funds.

func ValidAddress

func ValidAddress(address string) error

ValidAddress returns error if address is an invalid stellar address

func ValidAddressOrSeed

func ValidAddressOrSeed(addressOrSeed string) bool

ValidAddressOrSeed returns true if the string is a valid address or seed

func ValidSeed

func ValidSeed(seed string) error

ValidSeed returns error if the seed is invalid

Types

type Account

type Account struct {
	Balances      []Balance
	Signers       []Signer
	NativeBalance Balance
	HomeDomain    string
	Sequence      string
}

Account represents an account on the stellar network.

func (*Account) GetBalance

func (account *Account) GetBalance(asset *Asset) string

GetBalance returns the balance for asset in account. If no balance is found for the asset, returns "".

func (*Account) GetMasterWeight

func (account *Account) GetMasterWeight() int32

GetMasterWeight returns the weight of the primary key in the account.

func (*Account) GetNativeBalance

func (account *Account) GetNativeBalance() string

GetNativeBalance returns the balance of the native currency (typically lumens) in the account.

type AccountFlags

type AccountFlags int32

AccountFlags are used by issuers of assets.

type Address

type Address string

Address represents a stellar address or public key

type Asset

type Asset struct {
	Code   string
	Issuer string
	Type   AssetType // Credit4Type, Credit12Type, NativeType
}

Asset represents a specific asset class on the stellar network. For native assets "Code" and "Issuer" are ignored.

func NewAsset

func NewAsset(code string, issuer string, assetType AssetType) *Asset

NewAsset creates a new asset with the given code, issuer, and assetType. assetType can be one of: NativeType, Credit4Type, or Credit12Type.

USD := microstellar.NewAsset("USD", "issuer_address", microstellar.Credit4Type)

func (Asset) Equals

func (this Asset) Equals(that Asset) bool

Equals returns true if "this" and "that" represent the same asset class.

func (Asset) IsNative

func (asset Asset) IsNative() bool

IsNative returns true if the asset is a native asset (e.g., lumens.)

func (Asset) Validate

func (asset Asset) Validate() error

Validate returns error if the asset is not valid.

type AssetType

type AssetType string

AssetType represents an asset type on the stellar network.

const Credit12Type AssetType = "credit_alphanum12"

Credit12Type represents credit assets with 12-digit codes.

const Credit4Type AssetType = "credit_alphanum4"

Credit4Type represents credit assets with 4-digit codes.

const NativeType AssetType = "native"

NativeType represents native assets (like lumens.)

type Balance

type Balance struct {
	Asset  *Asset
	Amount string
	Limit  string
}

Balance is the balance amount of the asset in the account.

type Error

type Error struct {
	HorizonError horizon.Error
}

Error wraps underlying errors (e.g., horizon)

type KeyPair

type KeyPair struct {
	Seed    string // private key
	Address string // public key
}

KeyPair represents a key pair for a signer on a stellar account. An account can have multiple signers.

type MemoType

type MemoType int

MemoType sets the memotype field on the payment request.

type MicroStellar

type MicroStellar struct {
	// contains filtered or unexported fields
}

MicroStellar is the user handle to the Stellar network. Use the New function to create a new instance.

func New

func New(networkName string, params ...Params) *MicroStellar

New returns a new MicroStellar client connected that operates on the network specified by networkName. The supported networks are:

public: the public horizon network
test: the public horizon testnet
fake: a fake network used for tests
custom: a custom network specified by the parameters

If you're using "custom", provide the URL and Passphrase to your horizon network server in the parameters.

NewTx("custom", Params{
    "url": "https://my-horizon-server.com",
    "passphrase": "foobar"})

func (*MicroStellar) AddSigner

func (ms *MicroStellar) AddSigner(sourceSeed string, signerAddress string, signerWeight uint32, options ...*TxOptions) error

AddSigner adds signerAddress as a signer to sourceSeed's account with weight signerWeight.

Example

This example adds a signer to an account.

// Create a new MicroStellar client connected to a fake network. To
// use a real network replace "fake" below with "test" or "public".
ms := New("fake")

// Add signer to account
err := ms.AddSigner("SCSMBQYTXKZYY7CLVT6NPPYWVDQYDOQ6BB3QND4OIXC7762JYJYZ3RMK", "GCCRUJJGPYWKQWM5NLAXUCSBCJKO37VVJ74LIZ5AQUKT6KPVCPNAGC4A", 10)

if err != nil {
	log.Fatalf("AddSigner: %v", err)
}

fmt.Printf("ok")
Output:

ok

func (*MicroStellar) CreateKeyPair

func (ms *MicroStellar) CreateKeyPair() (*KeyPair, error)

CreateKeyPair generates a new random key pair.

Example

This example creates a key pair and displays the private and public keys. In stellar-terminology, the private key is typically called a "seed", and the publick key. an "address."

ms := New("test")

// Generate a new random keypair.
pair, err := ms.CreateKeyPair()

if err != nil {
	log.Fatalf("CreateKeyPair: %v", err)
}

// Display address and key
log.Printf("Private seed: %s, Public address: %s", pair.Seed, pair.Address)

fmt.Printf("ok")
Output:

ok

func (*MicroStellar) CreateTrustLine

func (ms *MicroStellar) CreateTrustLine(sourceSeed string, asset *Asset, limit string, options ...*TxOptions) error

CreateTrustLine creates a trustline from sourceSeed to asset, with the specified trust limit. An empty limit string indicates no limit.

Example

This example creates a trust line to a credit asset.

// Create a new MicroStellar client connected to a fake network. To
// use a real network replace "fake" below with "test" or "public".
ms := New("fake")

// Custom USD asset issued by specified issuer
USD := NewAsset("USD", "GAIUIQNMSXTTR4TGZETSQCGBTIF32G2L5P4AML4LFTMTHKM44UHIN6XQ", Credit4Type)

// Create a trustline to the custom asset with no limit
err := ms.CreateTrustLine("SCSMBQYTXKZYY7CLVT6NPPYWVDQYDOQ6BB3QND4OIXC7762JYJYZ3RMK", USD, "")

if err != nil {
	log.Fatalf("CreateTrustLine: %v", err)
}

fmt.Printf("ok")
Output:

ok

func (*MicroStellar) FundAccount

func (ms *MicroStellar) FundAccount(sourceSeed string, addressOrSeed string, amount string, options ...*TxOptions) error

FundAccount creates a new account out of addressOrSeed by funding it with lumens from sourceSeed. The minimum funding amount today is 0.5 XLM.

Example

This example creates a key pair and funds the account with lumens. FundAccount is used for the initial funding of the account -- it is what turns a public address into an account.

// Create a new MicroStellar client connected to a fake network. To
// use a real network replace "fake" below with "test" or "public".
ms := New("fake")

// Generate a new random keypair.
pair, err := ms.CreateKeyPair()

if err != nil {
	log.Fatalf("CreateKeyPair: %v", err)
}

// Fund the account with 1 lumen from an existing account.
err = ms.FundAccount("SD3M3RG4G54JSFIG4RJYPPKTB4G77IPSXKZPTMN5CKAFWNRQP6V24ZDQ", pair.Address, "1")

if err != nil {
	log.Fatalf("FundAccount: %v", ErrorString(err))
}

fmt.Printf("ok")
Output:

ok

func (*MicroStellar) LoadAccount

func (ms *MicroStellar) LoadAccount(address string) (*Account, error)

LoadAccount loads the account information for the given address.

Example (Balance)

This example loads and displays the native and a non-native balance on an account.

// Create a new MicroStellar client connected to a fake network. To
// use a real network replace "fake" below with "test" or "public".
ms := New("fake")

// Custom USD asset issued by specified issuer
USD := NewAsset("USD", "GAIUIQNMSXTTR4TGZETSQCGBTIF32G2L5P4AML4LFTMTHKM44UHIN6XQ", Credit4Type)

// Load account from ledger.
account, err := ms.LoadAccount("GCCRUJJGPYWKQWM5NLAXUCSBCJKO37VVJ74LIZ5AQUKT6KPVCPNAGC4A")

if err != nil {
	log.Fatalf("LoadAccount: %v", err)
}

// See balances
log.Printf("Native Balance: %v", account.GetNativeBalance())
log.Printf("USD Balance: %v", account.GetBalance(USD))
fmt.Printf("ok")
Output:

ok

func (*MicroStellar) Pay

func (ms *MicroStellar) Pay(sourceSeed string, targetAddress string, amount string, asset *Asset, options ...*TxOptions) error

Pay lets you make payments with credit assets.

ms.Pay("source_seed", "target_address", "3", NativeAsset, microstellar.Opts().WithMemoText("for shelter"))
Example

This example makes a payment of a credit asset from one account to another.

// Create a new MicroStellar client connected to a fake network. To
// use a real network replace "fake" below with "test" or "public".
ms := New("fake")

// Custom USD asset issued by specified issuer
USD := NewAsset("USD", "GAIUIQNMSXTTR4TGZETSQCGBTIF32G2L5P4AML4LFTMTHKM44UHIN6XQ", Credit4Type)

// Pay 1 USD to targetAddress
err := ms.Pay("SAED4QHN3USETFHECASIM2LRI3H4QTVKZK44D2RC27IICZPZQEGXGXFC", "GAGTJGMT55IDNTFTF2F553VQBWRBLGTWLU4YOOIFYBR2F6H6S4AEC45E", "1", USD)

if err != nil {
	log.Fatalf("Pay: %v", ErrorString(err))
}

fmt.Printf("ok")
Output:

ok
Example (Memotext)

Payments with memotext and memoid

// Create a new MicroStellar client connected to a fake network. To
// use a real network replace "fake" below with "test" or "public".
ms := New("fake")

// Custom USD asset issued by specified issuer
USD := NewAsset("USD", "GALC5V4UUUICHENN3ZZLQY6UWAC67CMKVXYT4MT7YGQRD6RMXXCAMHP6", Credit4Type)

// Pay 1 USD to targetAddress and set the memotext field
err := ms.Pay("SAED4QHN3USETFHECASIM2LRI3H4QTVKZK44D2RC27IICZPZQEGXGXFC", "GAGTJGMT55IDNTFTF2F553VQBWRBLGTWLU4YOOIFYBR2F6H6S4AEC45E", "1", USD, Opts().WithMemoText("boo"))

if err != nil {
	log.Fatalf("Pay (memotext): %v", ErrorString(err))
}

// Pay 1 USD to targetAddress and set the memotext field
err = ms.Pay("SAED4QHN3USETFHECASIM2LRI3H4QTVKZK44D2RC27IICZPZQEGXGXFC", "GAGTJGMT55IDNTFTF2F553VQBWRBLGTWLU4YOOIFYBR2F6H6S4AEC45E", "1", USD, Opts().WithMemoID(42))

if err != nil {
	log.Fatalf("Pay (memoid): %v", ErrorString(err))
}

fmt.Printf("ok")
Output:

ok
Example (Multisig)

Makes a multisignature payment

// Create a new MicroStellar client connected to a fake network. To
// use a real network replace "fake" below with "test" or "public".
ms := New("fake")

// Custom USD asset issued by specified issuer
USD := NewAsset("USD", "GAIUIQNMSXTTR4TGZETSQCGBTIF32G2L5P4AML4LFTMTHKM44UHIN6XQ", Credit4Type)

// Pay 1 USD to targetAddress and set the memotext field
err := ms.Pay("SDKORMIXFL2QW2UC3HWJ4GKL4PYFUMDOPEJMGWVQBW4GWJ5W2ZBOGRSZ", "GAGTJGMT55IDNTFTF2F553VQBWRBLGTWLU4YOOIFYBR2F6H6S4AEC45E", "1", USD,
	Opts().WithMemoText("multisig").
		WithSigner("SAIUIQNMSXTTR4TGZETSQCGBTIF32G2L5P4AML4LFTMTHKM44UHIN6XQ").
		WithSigner("SBIUIQNMSXTGR4TGZETSQCGBTIF32G2L5D4AML4LFTMTHKM44UABFDMS"))

if err != nil {
	log.Fatalf("Pay (memotext): %v", ErrorString(err))
}

// Pay 1 USD to targetAddress and set the memotext field
err = ms.Pay("SAED4QHN3USETFHECASIM2LRI3H4QTVKZK44D2RC27IICZPZQEGXGXFC", "GAGTJGMT55IDNTFTF2F553VQBWRBLGTWLU4YOOIFYBR2F6H6S4AEC45E", "1", USD, Opts().WithMemoID(73223))

if err != nil {
	log.Fatalf("Pay (memoid): %v", ErrorString(err))
}

fmt.Printf("ok")
Output:

ok

func (*MicroStellar) PayNative

func (ms *MicroStellar) PayNative(sourceSeed string, targetAddress string, amount string, options ...*TxOptions) error

PayNative makes a native asset payment of amount from source to target.

Example

This example makes a native asset (lumens) payment from one account to another.

// Create a new MicroStellar client connected to a fake network. To
// use a real network replace "fake" below with "test" or "public".
ms := New("fake")

// Pay 1 XLM to targetAddress
err := ms.PayNative("SAED4QHN3USETFHECASIM2LRI3H4QTVKZK44D2RC27IICZPZQEGXGXFC", "GDS2DXCCTW5VO5A2KCEBHAP3W4XOCJSI2QVHNN63TXVGBUIIW4DI3BCW", "1")

if err != nil {
	log.Fatalf("PayNative: %v", ErrorString(err))
}

fmt.Printf("ok")
Output:

ok

func (*MicroStellar) RemoveSigner

func (ms *MicroStellar) RemoveSigner(sourceSeed string, signerAddress string, options ...*TxOptions) error

RemoveSigner removes signerAddress as a signer from sourceSeed's account.

Example

This example removes a signer from an account.

// Create a new MicroStellar client connected to a fake network. To
// use a real network replace "fake" below with "test" or "public".
ms := New("fake")

// Remove signer from account
err := ms.RemoveSigner("SCSMBQYTXKZYY7CLVT6NPPYWVDQYDOQ6BB3QND4OIXC7762JYJYZ3RMK", "GCCRUJJGPYWKQWM5NLAXUCSBCJKO37VVJ74LIZ5AQUKT6KPVCPNAGC4A")

if err != nil {
	log.Fatalf("RemoveSigner: %v", err)
}

fmt.Printf("ok")
Output:

ok

func (*MicroStellar) RemoveTrustLine

func (ms *MicroStellar) RemoveTrustLine(sourceSeed string, asset *Asset, options ...*TxOptions) error

RemoveTrustLine removes an trustline from sourceSeed to an asset.

Example

This example removes a trust line to a credit asset.

// Create a new MicroStellar client connected to a fake network. To
// use a real network replace "fake" below with "test" or "public".
ms := New("fake")

// Custom USD asset issued by specified issuer
USD := NewAsset("USD", "GAIUIQNMSXTTR4TGZETSQCGBTIF32G2L5P4AML4LFTMTHKM44UHIN6XQ", Credit4Type)

// Remove the trustline (if exists)
err := ms.RemoveTrustLine("SCSMBQYTXKZYY7CLVT6NPPYWVDQYDOQ6BB3QND4OIXC7762JYJYZ3RMK", USD)

if err != nil {
	log.Fatalf("RemoveTrustLine: %v", err)
}

fmt.Printf("ok")
Output:

ok

func (*MicroStellar) Resolve

func (ms *MicroStellar) Resolve(address string) (string, error)

Resolve looks up a federated address

func (*MicroStellar) SetFlags

func (ms *MicroStellar) SetFlags(sourceSeed string, flags AccountFlags, options ...*TxOptions) error

SetFlags changes the flags for the account.

Example

This example sets flags on an issuer's account

// Create a new MicroStellar client connected to a fake network. To
// use a real network replace "fake" below with "test" or "public".
ms := New("fake")

// Set the AUTH_REQUIRED and AUTH_REVOCABLE flags on the account.
err := ms.SetFlags("SCSMBQYTXKZYY7CLVT6NPPYWVDQYDOQ6BB3QND4OIXC7762JYJYZ3RMK", FlagAuthRequired|FlagAuthRevocable)

if err != nil {
	log.Fatalf("SetFlags: %v", err)
}

fmt.Printf("ok")
Output:

ok

func (*MicroStellar) SetHomeDomain

func (ms *MicroStellar) SetHomeDomain(sourceSeed string, domain string, options ...*TxOptions) error

SetHomeDomain changes the home domain of sourceSeed.

Example

This example sets the home domain for an account

// Create a new MicroStellar client connected to a fake network. To
// use a real network replace "fake" below with "test" or "public".
ms := New("fake")

// Set the home domain to qubit.sh
err := ms.SetHomeDomain("SCSMBQYTXKZYY7CLVT6NPPYWVDQYDOQ6BB3QND4OIXC7762JYJYZ3RMK", "qubit.sh")

if err != nil {
	log.Fatalf("SetHomeDomain: %v", err)
}

fmt.Printf("ok")
Output:

ok

func (*MicroStellar) SetMasterWeight

func (ms *MicroStellar) SetMasterWeight(sourceSeed string, weight uint32, options ...*TxOptions) error

SetMasterWeight changes the master weight of sourceSeed.

Example

This example sets the weight of the accounts primary signer (the master weight) to zero. This effectively kills the account.

// Create a new MicroStellar client connected to a fake network. To
// use a real network replace "fake" below with "test" or "public".
ms := New("fake")

// Set master weight to zero.
err := ms.SetMasterWeight("SCSMBQYTXKZYY7CLVT6NPPYWVDQYDOQ6BB3QND4OIXC7762JYJYZ3RMK", 0)

if err != nil {
	log.Fatalf("SetMasterWeight: %v", err)
}

// Load the account and check its master weight
account, err := ms.LoadAccount("GCCRUJJGPYWKQWM5NLAXUCSBCJKO37VVJ74LIZ5AQUKT6KPVCPNAGC4A")

if err != nil {
	log.Fatalf("LoadAccount: %v", err)
}

log.Printf("Master weight: %v", account.GetMasterWeight())
fmt.Printf("ok")
Output:

ok

func (*MicroStellar) SetThresholds

func (ms *MicroStellar) SetThresholds(sourceSeed string, low, medium, high uint32, options ...*TxOptions) error

SetThresholds sets the signing thresholds for the account.

Example

This example sets the signing thresholds for an account

// Create a new MicroStellar client connected to a fake network. To
// use a real network replace "fake" below with "test" or "public".
ms := New("fake")

// Set the low, medium, and high thresholds for an account
err := ms.SetThresholds("SCSMBQYTXKZYY7CLVT6NPPYWVDQYDOQ6BB3QND4OIXC7762JYJYZ3RMK", 2, 2, 2)

if err != nil {
	log.Fatalf("SetThresholds: %v", err)
}

fmt.Printf("ok")
Output:

ok

func (*MicroStellar) WatchPayments

func (ms *MicroStellar) WatchPayments(address string, options ...*TxOptions) (*PaymentWatcher, error)

WatchPayments watches the ledger for payments to and from address and streams them on a channel . Use TxOptions.WithContext to set a context.Context, and TxOptions.WithCursor to set a cursor.

Example
// Create a new MicroStellar client connected to a fake network. To
// use a real network replace "fake" below with "test" or "public".
ms := New("fake")

// Watch for payments to address. (The fake network sends payments every 200ms.)
watcher, err := ms.WatchPayments("GCCRUJJGPYWKQWM5NLAXUCSBCJKO37VVJ74LIZ5AQUKT6KPVCPNAGC4A",
	Opts().WithContext(context.Background()))

if err != nil {
	log.Fatalf("Can't watch ledger: %+v", err)
}

// Count the number of payments received.
paymentsReceived := 0

go func() {
	for p := range watcher.Ch {
		paymentsReceived++
		log.Printf("WatchPayments %d: %v -- %v %v from %v to %v\n", paymentsReceived, p.Type, p.Amount, p.AssetCode, p.From, p.To)
	}

	log.Printf("## WatchPayments ## Done -- Error: %v\n", *watcher.Err)
}()

// Stream the ledger for about a second then stop the watcher.
time.Sleep(1 * time.Second)
watcher.Done()

// Sleep a bit to wait for the done message from the goroutine.
time.Sleep(500 * time.Millisecond)
fmt.Printf("%d payments received", paymentsReceived)
Output:

5 payments received

type Params

type Params map[string]interface{}

Params lets you add optional parameters to New and NewTx.

type Payment

type Payment horizon.Payment

Payment represents a finalized payment in the ledger. You can subscribe to payments on the stellar network via the WatchPayments call.

func NewPaymentFromHorizon

func NewPaymentFromHorizon(p *horizon.Payment) *Payment

NewPaymentFromHorizon converts a horizon JSON payment struct to Payment

type PaymentWatcher

type PaymentWatcher struct {
	// Ch gets a *Payment everytime there's a new entry in the ledger.
	Ch chan *Payment

	// Call Done to stop watching the ledger. This closes Ch.
	Done func()

	// This is set if the stream terminates unexpectedly. Safe to check
	// after Ch is closed.
	Err *error
}

PaymentWatcher is returned by WatchPayments, which watches the ledger for payments to and from an address.

type Seed

type Seed string

Seed represents a stellar seed or private

type Signer

type Signer struct {
	PublicKey string
	Weight    int32
	Key       string
	Type      string
}

Signer represents a key that can sign for an account.

type Tx

type Tx struct {
	// contains filtered or unexported fields
}

Tx represents a unique stellar transaction. This is used by the MicroStellar library to abstract away the Horizon API and transport. To reuse Tx instances, you must call Tx.Reset() between operations.

This struct is not thread-safe by design -- you must use separate instances in different goroutines.

Unless you're hacking around in the guts, you should not need to use Tx.

func NewTx

func NewTx(networkName string, params ...Params) *Tx

NewTx returns a new Tx that operates on the network specified by networkName. The supported networks are:

public: the public horizon network
test: the public horizon testnet
fake: a fake network used for tests
custom: a custom network specified by the parameters

If you're using "custom", provide the URL and Passphrase to your horizon network server in the parameters.

NewTx("custom", Params{
    "url": "https://my-horizon-server.com",
    "passphrase": "foobar"})

func (*Tx) Build

func (tx *Tx) Build(sourceAccount build.TransactionMutator, muts ...build.TransactionMutator) error

Build creates a new operation out of the provided mutators.

func (*Tx) Err

func (tx *Tx) Err() error

Err returns the error from the most recent failed operation.

func (*Tx) GetClient

func (tx *Tx) GetClient() *horizon.Client

GetClient returns the underlying horizon client handle.

func (*Tx) IsSigned

func (tx *Tx) IsSigned() bool

IsSigned returns true of the transaction is signed.

func (*Tx) Reset

func (tx *Tx) Reset()

Reset clears all internal state, so you can run a new operation.

func (*Tx) Response

func (tx *Tx) Response() string

Response returns the horison response for the submitted operation.

func (*Tx) SetOptions

func (tx *Tx) SetOptions(options *TxOptions)

SetOptions sets the Tx options

func (*Tx) Sign

func (tx *Tx) Sign(keys ...string) error

Sign signs the transaction with every key in keys.

func (*Tx) Submit

func (tx *Tx) Submit() error

Submit sends the transaction to the stellar network.

func (*Tx) WithOptions

func (tx *Tx) WithOptions(options *TxOptions) *Tx

WithOptions sets the Tx options and returns the Tx

type TxOptions

type TxOptions struct {
	// contains filtered or unexported fields
}

TxOptions are additional parameters for a transaction. Use Opts() or NewTxOptions() to create a new instance.

Example (Memotext)

Payments with memotext and memoid

// Create a new MicroStellar client connected to a fake network. To
// use a real network replace "fake" below with "test" or "public".
ms := New("fake")

// Custom USD asset issued by specified issuer
USD := NewAsset("USD", "GALC5V4UUUICHENN3ZZLQY6UWAC67CMKVXYT4MT7YGQRD6RMXXCAMHP6", Credit4Type)

// Pay 1 USD to targetAddress and set the memotext field
err := ms.Pay("SAED4QHN3USETFHECASIM2LRI3H4QTVKZK44D2RC27IICZPZQEGXGXFC", "GAGTJGMT55IDNTFTF2F553VQBWRBLGTWLU4YOOIFYBR2F6H6S4AEC45E", "1", USD, Opts().WithMemoText("boo"))

if err != nil {
	log.Fatalf("Pay (memotext): %v", ErrorString(err))
}

// Pay 1 USD to targetAddress and set the memotext field
err = ms.Pay("SAED4QHN3USETFHECASIM2LRI3H4QTVKZK44D2RC27IICZPZQEGXGXFC", "GAGTJGMT55IDNTFTF2F553VQBWRBLGTWLU4YOOIFYBR2F6H6S4AEC45E", "1", USD, Opts().WithMemoID(42))

if err != nil {
	log.Fatalf("Pay (memoid): %v", ErrorString(err))
}

fmt.Printf("ok")
Output:

ok
Example (Multisig)

Makes a multisignature payment

// Create a new MicroStellar client connected to a fake network. To
// use a real network replace "fake" below with "test" or "public".
ms := New("fake")

// Custom USD asset issued by specified issuer
USD := NewAsset("USD", "GAIUIQNMSXTTR4TGZETSQCGBTIF32G2L5P4AML4LFTMTHKM44UHIN6XQ", Credit4Type)

// Pay 1 USD to targetAddress and set the memotext field
err := ms.Pay("SDKORMIXFL2QW2UC3HWJ4GKL4PYFUMDOPEJMGWVQBW4GWJ5W2ZBOGRSZ", "GAGTJGMT55IDNTFTF2F553VQBWRBLGTWLU4YOOIFYBR2F6H6S4AEC45E", "1", USD,
	Opts().WithMemoText("multisig").
		WithSigner("SAIUIQNMSXTTR4TGZETSQCGBTIF32G2L5P4AML4LFTMTHKM44UHIN6XQ").
		WithSigner("SBIUIQNMSXTGR4TGZETSQCGBTIF32G2L5D4AML4LFTMTHKM44UABFDMS"))

if err != nil {
	log.Fatalf("Pay (memotext): %v", ErrorString(err))
}

// Pay 1 USD to targetAddress and set the memotext field
err = ms.Pay("SAED4QHN3USETFHECASIM2LRI3H4QTVKZK44D2RC27IICZPZQEGXGXFC", "GAGTJGMT55IDNTFTF2F553VQBWRBLGTWLU4YOOIFYBR2F6H6S4AEC45E", "1", USD, Opts().WithMemoID(73223))

if err != nil {
	log.Fatalf("Pay (memoid): %v", ErrorString(err))
}

fmt.Printf("ok")
Output:

ok

func NewTxOptions

func NewTxOptions() *TxOptions

NewTxOptions creates a new options structure for Tx.

func Opts

func Opts() *TxOptions

Opts is just an alias for NewTxOptions

func (*TxOptions) WithContext

func (o *TxOptions) WithContext(context context.Context) *TxOptions

WithContext sets the context.Context for the connection

func (*TxOptions) WithCursor

func (o *TxOptions) WithCursor(cursor string) *TxOptions

WithCursor sets the cursor for watchers

func (*TxOptions) WithMemoID

func (o *TxOptions) WithMemoID(id uint64) *TxOptions

WithMemoID sets the memoType and memoID fields on Payment p

func (*TxOptions) WithMemoText

func (o *TxOptions) WithMemoText(text string) *TxOptions

WithMemoText sets the memoType and memoText fields on Payment p

func (*TxOptions) WithSigner

func (o *TxOptions) WithSigner(signerSeed string) *TxOptions

WithSigner adds a signer to Payment p

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL