Embedded database for accounts transactions.

Overview

transaction

Build Status Mentioned in Awesome Go API documentation Go Report Card

Embedded transactional database of accounts, running in multithreaded mode. Coverage 92.8%

The library operates only with integers. If you want to work with hundredths (for example, cents in dollars), multiply everything by 100. For example, a dollar and a half, it will be 150. Limit on the maximum account size: 2 to 63 degrees (9,223,372,036,854,775,807). For example: on the account cannot be more than $92,233,720,368,547,758.07

The library works in parallel mode and can process millions of requests per second. Parallel requests to the same account should not lead to an erroneous change in the balance of this account. Debit and credit with the account can be done ONLY as part of the transaction.

The library has two main entities: a unit and an account.

Unit

  • A unit can be a customer, a company, etc.
  • A unit can have many accounts (accounts are called a string variable)
  • A unit cannot be deleted if at least one of its accounts is not zero
  • If a unit receives a certain amount for a nonexistent account, such an account will be created

Account

  • The account serves to account for money, shares, etc.
  • The account necessarily belongs to any unit.
  • The account belongs to only one unit.
  • There is only one balance on one account.
  • Balance is calculated only in whole numbers.

Usage

Important: in the description of methods all error return codes are written. Descriptions in the documentation: https://godoc.org/github.com/claygod/transaction The transaction has no limits on the number of credits and debits.

Create / delete

tr := transaction.New()
tr.Start()
tr.AddUnit(123)
tr.DelUnit(123)

Credit/debit of an account

Credit and debit operations with the account:

t.Begin().Credit(id, "USD", 1).End()
t.Begin().Debit(id, "USD", 1).End()

Transfer

Example of transfer of one dollar from one account to another.

t.Begin().
	Credit(idFrom, "USD", 1).
	Debit(idTo, "USD", 1).
	End()

Purchase / Sale

A purchase is essentially two simultaneous funds transfers

// Example of buying two shares of "Apple" for $10
tr.Begin().
	Credit(buyerId, "USD", 10).Debit(sellerId, "USD", 10).
	Debit(buyerId, "APPLE", 2).Credit(sellerId, "APPLE", 2).
	End()

Save / Load

// Save
	tr := New()
	tr.Start()
	tr.AddUnit(123)
	tr.Begin().Debit(123, "USD", 7).End()
	tr.Save(path)
	...
// Load
	tr := New()
	tr.Start()
	tr.Load(path)
	tr.Begin().Credit(123, "USD", 7).End()
	...

Example

package main

import (
	"fmt"

	tn "github.com/claygod/transaction"
)

func main() {
	tr := tn.New()
	tr.Start()

	// add unit
	switch res := tr.AddUnit(123); res {
	case tn.Ok:
		fmt.Println("Done! Unit created")
	case tn.ErrCodeCoreCatch:
		fmt.Println("Not obtained permission")
	case tn.ErrCodeUnitExist:
		fmt.Println("Such a unit already exists")
	default:
		fmt.Println("Unknown error")
	}

	// transaction
	switch res := tr.Begin().Debit(123, "USD", 5).End(); res {
	case tn.Ok:
		fmt.Println("Done! Money added")
	case tn.ErrCodeUnitNotExist:
		fmt.Println("Unit  not exist")
	case tn.ErrCodeTransactionCatch:
		fmt.Println("Account not catch")
	case tn.ErrCodeTransactionDebit:
		fmt.Println("Such a unit already exists")
	default:
		fmt.Println("Unknown error")
	}

	// save
	switch res := tr.Save("./test.tdb"); res {
	case tn.Ok:
		fmt.Println("Done! Data saved to file")
	case tn.ErrCodeCoreStop:
		fmt.Println("Unable to stop app")
	case tn.ErrCodeSaveCreateFile:
		fmt.Println("Could not create file")
	default:
		fmt.Println("Unknown error")
	}

	// del unit (There will be an error!)
	switch _, res := tr.DelUnit(123); res {
	case tn.Ok:
		fmt.Println("Done!")
	case tn.ErrCodeCoreCatch:
		fmt.Println("Not obtained permission")
	case tn.ErrCodeUnitExist:
		fmt.Println("There is no such unit")
	case tn.ErrCodeAccountNotStop:
		fmt.Println("Accounts failed to stop")
	case tn.ErrCodeUnitNotEmpty:
		fmt.Println("Accounts are not zero! You must withdraw money from the account")
	default:
		fmt.Println("Unknown error")
	}

	// transaction
	switch res := tr.Begin().Credit(123, "USD", 5).End(); res {
	case tn.Ok:
		fmt.Println("Done! Account cleared")
	case tn.ErrCodeUnitNotExist:
		fmt.Println("Unit not exist")
	case tn.ErrCodeTransactionCatch:
		fmt.Println("Account not catch")
	case tn.ErrCodeTransactionCredit:
		fmt.Println("Such a unit already exists")
	default:
		fmt.Println("Unknown error")
	}

	// del unit (Now it will work out!)
	switch _, res := tr.DelUnit(123); res {
	case tn.Ok:
		fmt.Println("Done! Now the account has been deleted")
	case tn.ErrCodeCoreCatch:
		fmt.Println("Not obtained permission")
	case tn.ErrCodeUnitNotExist:
		fmt.Println("There is no such unit")
	case tn.ErrCodeAccountNotStop:
		fmt.Println("Accounts failed to stop")
	case tn.ErrCodeUnitNotEmpty:
		fmt.Println("Accounts are not zero")
	default:
		fmt.Println(res)
	}
}

Output:

Done! Unit created
Done! Money added
Done! Data saved to file
Accounts are not zero! You must withdraw money from the account
Done! Account cleared
Done! Now the account has been deleted

Sequence diagram

Sequence diagram

API

  • New
  • Load ("path")
  • Start ()
  • AddUnit(ID)
  • Begin().Debit(ID, key, amount).End()
  • Begin().Credit(ID, key, amount).End()
  • TotalUnit(ID)
  • TotalAccount(ID, key)
  • DelUnit(ID)
  • Stop ()
  • Save ("path")

F.A.Q.

Why can not I add or withdraw funds from the account without a transaction, because it's faster?

  • The user should not be able to make a transaction on his own. This reduces the risk. In addition, in the world of finance, single operations are rare.

Does the performance of your library depend on the number of processor cores?

  • Depends on the processor (cache size, number of cores, frequency, generation), and also depends on the RAM (size and speed), the number of accounts, the type of disk (HDD / SSD) when saving and loading.

I have a single-core processor, should I use your library in this case?

  • The performance of the library is very high, so it will not be a break in your application. However, the system block is better to upgrade ;-)

ToDo

  • Draw a sequence diagram
  • Example of using a library as a server
  • Write-Ahead Logging (WAL)

Bench

i7-6700T:

  • BenchmarkTotalUnitSequence-8 3000000 419 ns/op
  • BenchmarkTotalUnitParallel-8 10000000 185 ns/op
  • BenchmarkCreditSequence-8 5000000 311 ns/op
  • BenchmarkCreditParallel-8 10000000 175 ns/op
  • BenchmarkDebitSequence-8 5000000 314 ns/op
  • BenchmarkDebitParallel-8 10000000 178 ns/op
  • BenchmarkTransferSequence-8 3000000 417 ns/op
  • BenchmarkTransferParallel-8 5000000 277 ns/op
  • BenchmarkBuySequence-8 2000000 644 ns/op
  • BenchmarkBuyParallel-8 5000000 354 ns/op

Copyright © 2017-2018 Eduard Sesigin. All rights reserved. Contacts: [email protected]

You might also like...
An embedded key/value database for Go.

bbolt bbolt is a fork of Ben Johnson's Bolt key/value store. The purpose of this fork is to provide the Go community with an active maintenance and de

An embedded key/value database for Go.

Bolt Bolt is a pure Go key/value store inspired by Howard Chu's LMDB project. The goal of the project is to provide a simple, fast, and reliable datab

An embedded key/value database for Go.

bbolt bbolt is a fork of Ben Johnson's Bolt key/value store. The purpose of this fork is to provide the Go community with an active maintenance and de

Document-oriented, embedded SQL database

Genji Document-oriented, embedded, SQL database Table of contents Table of contents Introduction Features Installation Usage Using Genji's API Using d

rosedb is an embedded and fast k-v database based on LSM + WAL
rosedb is an embedded and fast k-v database based on LSM + WAL

A simple k-v database in pure Golang, supports string, list, hash, set, sorted set.

An embedded, hardened key/value database for Go.

Bolt Bolt is a pure Go key/value store inspired by Howard Chu's LMDB project. The goal of the project is to provide a simple, fast, and reliable datab

A HTTP RESTful type kv database which embedded some frequently-used mid-ware.

A HTTP RESTful type kv database which embedded some frequently-used mid-ware.

`kawipiko` -- blazingly fast static HTTP server -- focused on low latency and high concurrency, by leveraging Go, `fasthttp` and the CDB embedded database
`kawipiko` -- blazingly fast static HTTP server -- focused on low latency and high concurrency, by leveraging Go, `fasthttp` and the CDB embedded database

kawipiko -- blazingly fast static HTTP server kawipiko is a lightweight static HTTP server written in Go; focused on serving static content as fast an

A simple, fast, embeddable, persistent key/value store written in pure Go. It supports fully serializable transactions and many data structures such as list, set, sorted set.

NutsDB English | 简体中文 NutsDB is a simple, fast, embeddable and persistent key/value store written in pure Go. It supports fully serializable transacti

Sync your bank transactions with google sheets using Open Banking APIs

Sync your bank transactions with google sheets using Open Banking APIs

Sync your bank transactions with google sheets using Open Banking APIs

this is a markdown version of the copy on the site landing page: https://youneedaspreadsheet.com You need a spreadsheet 📊 Get on top of your finances

go-pix is a Go library for generating Pix transactions using Copy and Paste or QR codes. 💳 💰
go-pix is a Go library for generating Pix transactions using Copy and Paste or QR codes. 💳 💰

go-pix go-pix is a Go library for generating Pix transactions using Copy and Paste or QR codes.

🏛 A scriptable financial ledger, designed to make it easy to model complex financial transactions
🏛 A scriptable financial ledger, designed to make it easy to model complex financial transactions

Numary Ledger Numary is a programmable financial ledger that wants to make building financial apps safe, fun and cheap. Building financial software is

An easy tool to apply transactions to the current EVM state. Optimized for MEV.

sibyl A more embedded version of fxfactorial/run-evm-code. This tool makes it easy to apply transactions to the current EVM state. Call it a transacti

Signer manages Web3 transactions

Signer Website: https://signer-tech41.com Signer is a distributed, highly available, and data center aware solution to connect and configure applicati

Fabric-Batch-Chaincode (FBC) is a library that enables batch transactions in chaincode without additional trusted systems.

Fabric-Batch-Chaincode Fabric-Batch-Chaincode (FBC) is a library that enables batch transactions in chaincode without additional trusted systems. Over

A blockchains platform with high throughput, and blazing fast transactions
A blockchains platform with high throughput, and blazing fast transactions

Node implementation for the Avalanche network - a blockchains platform with high throughput, and blazing fast transactions. Installation Avalanche is

Go jackc/pgx helper to write proper transactions

Go jackc/pgx helper to write proper transactions.

Comments
  • Use cases and storage

    Use cases and storage

    I had two questions @claygod

    1. What kind of use cases is this library trying to help build?

    2. Is everything held in memory? Is data lost when the process ends?

    opened by asad-awadia 1
Owner
Eduard
Eduard
Converts grouped transactions in a ZKB transaction CSV (incl. details) to single transactions

ZKB Converter Converts grouped transactions in a ZKB transaction CSV (incl. deta

Tobias Nehrlich 0 Dec 26, 2021
A tool to manage accounts and codes of Google Authenticator.

A tool to manage accounts and codes of Google Authenticator.

Jormin 5 Sep 10, 2021
Cheiron is a Kubernetes Operator made with OperatorSDK for reconciling service account and attaching imagePullSecrets to service accounts automatically

anny-co/cheiron NOTE: Cheiron is currently in very early stages of development and and far from anything usable. Feel free to contribute if you want t

anny 2 Sep 13, 2021
CLI tool to update ~/.aws/config with all accounts and permission sets defined in AWS SSO

aws-sso-profiles Generate or update ~/.aws/config with a profile for each SSO account you have access to, by using an existing AWS SSO session. Bootst

SpareBank 1 Utvikling 3 Nov 3, 2022
Use SQL to instantly query Datadog resources across accounts. Open source CLI. No DB required.

steampipe-plugin-datadog Datadog Plugin for Steampipe Use SQL to query dashboards, users, roles and more from Datadog. Get started → Documentation: Ta

Turbot 8 Nov 10, 2022
Suricate-bank - API to transfer money between accounts at Suricate Bank,written in Go

⚠️ WORK IN PROGRESS ⚠️ Suricate Bank is an api that creates accounts and transfe

João Saraceni 12 Oct 8, 2022
Ghissue - This repo contains a github issue parser, that is useful for Enterprise Github accounts.

Ghissue - This repo contains a github issue parser, that is useful for Enterprise Github accounts. Sometimes is needed to parse the content of the issue for some data extraction or statistics purposes.

niloofargheibi 1 Feb 6, 2022
A tool for creating hidden accounts using the registry.

CreateHiddenAccount 创建隐藏账号 中文 | EN Tool Introduction There are two common ways to create a hidden account. One is to add the $ sign directly after the

Wolf Group Security Team 348 Nov 25, 2022
Wrapper for Lightning Network Daemon (lnd). It provides separate accounts with minimum trust for end users.

LndHub.go Wrapper for Lightning Network Daemon (lnd). It provides separate accounts with minimum trust for end users. LndHub compatible API implemente

Alby 38 Nov 22, 2022
Tnbassist - A CLI tool for thenewboston blockchain to perform various mundane tasks like taking daily accounts backup

TNB Assist is a CLI (Command Line Interface) tool for thenewboston blockchain to perform various mundane tasks like taking daily accounts backup, computing statistics, etc easier.

Open blockchain explorer 1 Feb 14, 2022