# Welcome to the Kryptokrona Wiki

![Kryptokrona Logo](https://2858262040-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fx7WCorBnqCP2oVt16bNf%2Fuploads%2Fgit-blob-7d7b8790156f367e81c0f878689eef024dc173f5%2Fxkr-logo.svg?alt=media)

This wiki is the main source of documentation for newcomers to the Kryptokrona project. If this is your first time hearing about Kryptokrona, check out the [Kryptokrona website](https://kryptokrona.org/).

### What is Kryptokrona?

Kryptokrona is a fast, easy and private cryptocurrency which allows you to send money to friends and businesses.

One of Kryptokrona's main goals is to make things as simple and as accessible as possible for everyday people, creating a cryptocurrency which is inviting, fun and friendly.

### Quick Navigation

|                                                                                                  **About Kryptokrona**                                                                                                  |                                                                                                  **Wallets**                                                                                                 |                                                                                                  **Mining**                                                                                                 |                                                                                            **Contributing**                                                                                           |
| :---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------: | :----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------: | :---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------: | :---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------: |
| ![Logo](https://2858262040-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fx7WCorBnqCP2oVt16bNf%2Fuploads%2Fgit-blob-a017a11a890351b1ec82fa804613417f46bad4ae%2Fxkr-logo-color-small.png?alt=media) | ![Wallets](https://2858262040-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fx7WCorBnqCP2oVt16bNf%2Fuploads%2Fgit-blob-680aa02cc629ba846e226dab2c0227f483cfc927%2Fwallet.png?alt=media) | ![Mining](https://2858262040-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fx7WCorBnqCP2oVt16bNf%2Fuploads%2Fgit-blob-7952132d2c121a46c2b61ec9f616b0ff27b4a5ee%2Fmining.png?alt=media) | ![Dev](https://2858262040-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fx7WCorBnqCP2oVt16bNf%2Fuploads%2Fgit-blob-c8b2fc5f952c339d23de972ac92c22961ace9e0a%2Fdev.png?alt=media) |
|                                                             [About Kryptokrona](https://github.com/kryptokrona/kryptokrona-docs/blob/master/about/README.md)                                                            |                                                                          [Setting up a New Wallet](/guides/wallets/making-a-wallet)                                                                          |                                                                                     [Mining Kryptokrona](/mining/mining)                                                                                    |                                                                           [Contributing to Kryptokrona](/about/contributing)                                                                          |
|                                                                                      Learn more about Kryptokrona and the community                                                                                     |                                                                  A guide on setting up a Kryptokrona wallet to start receiving some turtles!                                                                 |                                                                               A step-by-step guide to start mining Kryptokrona                                                                              |                                                                               Information on contributing to Kryptokrona                                                                              |

### Have Questions or Need Help?

Check out our [Discord](http://chat.kryptokrona.se) to get in touch.


# About


# About Kryptokrona

Kryptokrona is a fast, easy and private cryptocurrency which allows you to send money to friends and businesses.

One of Kryptokrona's main goals is to make things as simple and as accessible as possible for everyday people, creating a cryptocurrency which is inviting, fun and friendly.

Kryptokrona's code is forked from the Bytecoin code, and it has majorly the same privacy features you'll find in Monero and Aeon. Every transaction is private, by default.

Some of the main features of Kryptokrona include:

* On-chain privacy
* Only two decimal places
* Fast transactions
* User-centric developers
* Easy to mine
* Easy to use
* Amazing community
* Send to anyone, around the world

To learn more about us, check out our other various articles, describing:

* [Our Background and History](https://github.com/kryptokrona/kryptokrona-docs/blob/master/Background-and-History.md)
* [Our Community](https://github.com/kryptokrona/kryptokrona-docs/blob/master/Community.md)
* [How to Contribute](https://github.com/kryptokrona/kryptokrona-docs/blob/master/Contributing.md)
* [its Technical Data](https://github.com/kryptokrona/kryptokrona-docs/blob/master/Technical-Data.md)
* [Our Timeline](https://github.com/kryptokrona/kryptokrona-docs/blob/master/Timeline.md)

We recommend you check em out, to get acquainted with Kryptokrona!


# Background and History

### Why was Kryptokrona Created?

**Kryptokrona** was created as an answer to the Swedish Riksbank commission of the centralized digital currency **E-krona** to further impose their control over Swedens native currency.

The digital asset, **Kryptokrona**, was created without a pre-mine and without an initial coin offering to provide private trustless transactions.

### Our Background

We are a team of devoted developers that aim to bring decentralized economic freedom to the Nordic regions, with our core values of privacy and freedom close at heart we will work to further the individuals rights to digital financial privacy.


# Kryptokrona Community

Come and socialize with us! We would love if you would stop by our discord for a chat or check out our twitter!

| Twitter                                                                                            | Discord                                                                                           |
| -------------------------------------------------------------------------------------------------- | ------------------------------------------------------------------------------------------------- |
| ![twitter](https://github.com/kryptokrona/kryptokrona-docs/blob/master/About/assets/twit-logo.png) | ![discord](https://github.com/kryptokrona/kryptokrona-docs/blob/master/About/assets/dis-logo.png) |
| [Twitter Page](https://twitter.com/kryptokrona)                                                    | [Discord](https://discord.gg/v8duNZ6)                                                             |


# Contributing

To help contribute and improve the Kryptokrona project, you can:

* submit pull requests, or create issues over at our [GitHub Repo](https://github.com/kryptokrona/kryptokrona).
* help improve this wiki by submitting a pull request/making an issue over at its [GitHub Repo](https://github.com/kryptokrona/kryptokrona-docs).
* You can run a [Public Node](/node/run-a-public-node) or [Mining Pool](/mining/run-a-mining-pool)
* help make various tools which need to be refined/be worked on (wallets, daemons etc.).\
  Check the [GitHub Repo](https://github.com/kryptokrona/kryptokrona) for more information.

  The #bounties channel in the Discord has a list of bounties (pinned) offered to users who can help improve functionality in existing tools/make a tool which can be used.


# Contributors

Huge thank you to everyone here, they've made major commits to the project and helped make it what it is today!

* @zpalmtree
* @ar-x
* @Sajo8
* @holytastyguacamole
* @SoreGums
* the TurtleCoin Community
* The Kryptokrona Community
* @f-r00t
* @nilsjr
* @ulviux
* @vildet
* @Swepool
* @TechyGuy
* @coffeboi
* @c1phx


# Frequently Asked Questions

### Kryptokrona node / xkrwallet Issues

**Q: I'm seeing an error in Kryptokrona `Proof of work too weak for block...` and the syncing stopped.**

This occurs because of the blockchain forking, generally when one mining pool has a very large hashrate.

This can be fixed by re-syncing the correct blockchain from scratch. See here.

**Q: I'm getting a "corrupted blockchain" error like this?**

```
2018-May-07 15:52:19.877323 INFO    initializing core
2018-May-07 15:52:19.908530 INFO    Importing blocks from blockchain storage
2018-May-07 15:52:19.908530 ERROR   Corrupted blockchain. Block with index 428973 and hash aafa7fd33d476535188bdd9e86ba51bb5e058be8e52367b78e9c0c03e74299c5 has previous block hash 2c0cf6c07612b9e1ea19c6922a56746b83cb42c7b11edfc4b185572225bb0f20, but parent has hash 26189359b64d4bb357a04b102a42a01d2771a3f3d80db3ca1b7395a2aeaede4a. Resynchronize your daemon please.
2018-May-07 15:52:19.924135 INFO    Closing DB.
```

Re-sync your daemon from scratch(see below question)

**Q: How can I re-sync the blockchain?**

Close any Kryptokrona-related software, then go to `%APPDATA%`, and delete the `Kryptokrona` folder.\
Reopen Kryptokronad/the GUI wallet and let it re-sync.

Alternatively, check [this guide](https://github.com/kryptokrona/kryptokrona-docs/blob/master/guides/wallets/Using-Checkpoints/README.md) for instructions on how to use checkpoints for a quicker sync, or try a [remote node](https://github.com/kryptokrona/kryptokrona-docs/blob/master/guides/wallets/Using-Remote-Nodes/README.md)

**Q: When I open Kryptokrona on a Mac, I get an error `Illegal instruction: 4`. How can I fix it?**

This is a known issue with older macs or un-updated macs.

Try entering this into a terminal -

```
curl -sL "https://raw.githubusercontent.com/Kryptokrona/Kryptokrona/master/multi_installer.sh" | bash
```

This automated script should compile the software itself, and place the binaries in ./src once done.

**Q: I've opened the wallet, and I'm getting lots of red messages like "It looks like Kryptokrona isn't open!"...**

```
It looks like Kryptokrona isn't open!

Ensure Kryptokronad is open and has finished initializing.
If it's still not working, try restarting Kryptokrona. The daemon sometimes gets
stuck.
Alternatively, perhaps Kryptokrona can't communicate with any peers.

The wallet can't function until it can communicate with the network.
```

You need to also open up `Kryptokrona.exe` and let it sync. Kryptokrona is your connection to the network, and needs to be open and synced whenever you want to use your wallet.

**Q: I've opened the wallet, and I'm getting lots of messages like "Your Kryptokrona isn't fully synced yet!"..**

```
Until you are fully synced, you won't be able to send transactions, and your balance may be missing or incorrect!
```

Your daemon hasn't finished syncing yet. Keep xkrwallet open, and wait until you are 0 days behind the current block, and for the daemon to print out a green message saying `Successfully synchronized with the Kryptokrona Network.`\
You can also type `status` in the daemon and press enter to see the current height it's at.

**Q: I think I should have more money in my balance than it is showing, what should I do?**

Re-sync your daemon from scratch(see [here](#q-how-can-i-re-sync-the-blockchain)) or use a [remote node](broken://pages/xNbusqzPgZZnR1j6zHDf)) if you're using the GUI wallet. If it still doesn't work, then [update](https://github.com/kryptokrona/kryptokrona/releases)

* Then, close and reopen xkrwallet and Kryptokronad.
* Type `reset` in xkrwallet after reopening your wallet file.
* It should start resetting your wallet, but the progress might not be immediately obvious - wait a while, and it should start counting up the blocks and printing out your transactions as it gets to them.

**Q: How do I backup my wallet?**

Open xkrwallet and type `export_keys`.\
Save the view and spend key somewhere safe, and you can use them to reimport your wallet if you lose it.

Q: My transactions are very slow

Try attemping a fusion transaction:

* Open up xkrwallet, and type `optimize`, then press enter.
* It will confirm if you want to optimize your wallet; it will take a bit. If you're fine with that, type `Y` and press enter again.

Your wallet is now being optimized. When it finishes, your transaction should be able to send

**Q: How do I send XKR?**

You can check [this out](https://github.com/kryptokrona/kryptokrona-docs/blob/master/guides/wallets/Using-xkrwallet.md##sending-Kryptokrona-transactions) for steps on how to send XKR to someone.

**Q: How do I send money to exchanges / use payment ID?**

You can check [this out](https://github.com/kryptokrona/kryptokrona-docs/blob/master/guides/wallets/Using-xkrwallet.md#payment-id) for steps on how to send XKR with the payment ID.

**Q: What is mixin?**

Mixin is how many times your transaction is "mixed" with others for obfuscation and privacy.\
Mixin is locked by the network to `7` as of block `620,000` and is not adjustable by the user; this is done to ensure that no one can send a non-private transaction(`0` mixin) or be a victim of the "Tall Poppy Syndrome" by using a high mixin compared to everyone else on the network.

**Q: How can I view my balance?**

If `Kryptokrona.exe` is fully synced, in xkrwallet, simply type `balance`.

**Q: How long does it take to sync Kryptokrona.exe?**

Currently it takes a couple of hours. This number will increase as more people use XKR and the blockchain gets larger. If you'd like to speed up the process, check out the question below.

**Q: Can I speed up the syncing of the blockchain?**

You can sync [with checkpoints](https://github.com/kryptokrona/kryptokrona-docs/blob/master/guides/wallets/Using-Checkpoints.md) (only with xkrwallet) or use a [remote node](broken://pages/xNbusqzPgZZnR1j6zHDf)

**Q: Can I skip the syncing?**

Yes, you can currently use a remote node with xkrwallet and the desktopwallet. The keys stay on your PC, so it's secure. Check [this guide](broken://pages/xNbusqzPgZZnR1j6zHDf) for more information.

**Q: What does it mean if my balance is locked?**

This is a transfer which hasn't been confirmed by the network yet. It will move into your main balance shortly, generally after 3 minutes.

**Q: In xkrwallet.exe, I get an error `Error: failed to save new wallet: boost::filesystem::unique__path: Keyset as registered is invalid`. How can I fix it?**

This is caused by some broken Windows crypto keys. In the address bar in Windows Explorer, type `%AppData%/Microsoft/Crypto/RSA/`.

There should be a folder in there, with a long name, like `S-1-5-21-1416222650-108526586-4052533318-1000`.

Go into this folder and delete the files in there. Then reboot, and try again.

### Mining

#### General mining questions

**Q: How do I get started mining?**

You can check [this guide](/mining/mining)

**Q: I'm using a Mac, can I still mine?**

Yes, of course! We're working on a guide. You can install xmrig with [Brew](https://brew.sh/) and then use xmrig directly in your terminal. You can generate a config-file for xmrig [here](https://kryptokrona.org/mining) and then use: xmrig -c ../path/to/config.json to start mining.

**Q: I've started mining, how can I view my stats?**

Visit your pool's homepage. There should be a spot for you to put in your XKR address, and you can then view your hashrate, pending balance, payouts, and more.

**Q: Why is the hashrate on the pool website different to what is shown in my miner?**

The values will always be slightly different as it is an estimate, but if there is a large difference, it is likely you have just started mining.

Your hashrate is calculated over time, and so it will slowly go up to the correct level.

**Q: I've been mining for a while, but my pending balance hasn't gone up?**

On your pool website, check the time that the last block was found on your pool, and the average time to find a block.

Your stats will only update when your pool finds a block and it matures, so if your pool doesn't find blocks very often, you will have slower updating stats.

**Q: I've been mining, but the balance in my wallet hasn't gone up?**

To save money on fees, the pools send payouts in chunks. [Check your pool website for your pending balance](#q-i-ve-been-mining-for-a-while-but-my-pending-balance-hasn-t-gone-up).

**Q: Why are my results being rejected from the pool?**

You're using a incorrect algorithm. You should be using `cn-pico/trtl`.

**Q: I got banned from my mining pool. Why?**

If you submit lots of invalid shares, a pool might ban you. Possible reasons for invalid shares can be

* your hardware getting overworked,
* high ping to the pool,
* or your difficulty being set too low.

Try lowering any overclocks, choosing a pool closer to you or setting a higher difficulty port.

You should get unbanned after approximately 20 minutes. This is a good time to setup some backup pools!

**Q: Should I set up multiple pools?**

Yes, in case you get banned, or a pool goes down for some time, you can keep mining. A good amount to have would be at least three.

**Q: Where can I find a list of pools?**

[Here](/mining/pools) is a list. It also has other nifty stats like the pool's fee, minimum payout and server location.

**Q: What pool should I choose?**

There are a few factors to consider when choosing a pool.

* One is your ping, you can find this out by pinging the server in a command prompt by typing `ping example.org`, where `example.org` is the pool address.
* Another is the hashrate of the pool. If you go on the pool's website, you can see how often they find blocks.

  If the pool takes a long time to find a block, your stats will take a long time to update.
* Finally, the minimum payouts can be significant if you're a small miner.

  This is the amount you need to mine before you get paid. Most pools will list this under the "Payments" tab.

  You can check [this list](/mining/pools) of pools. It specifies each pool's minimum payout as well as server location.

**Q: How many hashes per second is good for my hardware?**

<http://monerobenchmarks.info/> is a good source for this. You can look up your [CPU](http://monerobenchmarks.info/searchCPU.php) and [GPU](http://monerobenchmarks.info/searchGPU.php). We also have our own benchmarks [here](https://kryptokrona.org/benchmarks).

**Q: I can't get the miner working, is there an easier way to mine?**

You can get some free XKR [here](https://kryptokrona.org/faucet).

Alternatively, you can hop onto the \[Discord]\[<https://discord.gg/nRK5k7wYy8>] if you're having issues and we'll help you out.

**Q: What is the miner executable / why isn't it working?**

This is a solo miner, which is CPU only. This means to gain any XKR, you have to find a block by yourself, which unless you have many powerful CPUs, is very unlikely.

We strongly recommend using a pool, and a miner such as NinjaRig.

Nevertheless, if you want to try it out, open a command prompt in the same directory, and run

```
./miner --address SEKR...
```

replacing `SEKR...` with your full XKR address.

You need to have `Kryptokrona` open and synced to use this miner, unlike conventional miners, where the pool hosts the daemon. You can also use a public node with the -r flag.

**Q: Is there a calculator to see how much XKR I'll mine per day?**

Your pool's homepage should have one - enter your hashrate and it'll give an estimate of how much XKR you'll mine per day.\
If there isn't, you can check one [here](https://explorer.kryptokrona.se).

### Paper Wallet / Cold Storage?

**Q: Wait, what's Cold Storage?**

The term "cold storage" refers to a wallet that has been created via an offline means.

The preferred way to do this is via a computer than has never ever been connected to the internet, commonly referred to as an air gapped device.

Why is this a thing? If done properly it means it is near impossible for the keys to be secretly intercepted since the data is never viewable by other compute devices.

You see above/elsewhere wallet files are being created via the wallet software, these files might be stored unencrypted, if unencrypted then the keys can be read by malicious software and balances of those wallets, transferred.

Thus to protect against that scenario you could transfer any XKR balance to one of these cold storage addresses. Please remember to keep secure/secret backups of your keys. If you lose the keys you lose any balance that was transferred to that wallet.

**Q: Can I make a paper wallet?**

Yes, you can view the guide [here](/guides/wallets/making-a-paper-wallet)

**Q: I made a paper wallet, how do I use it?**

You can check out [this guide](/guides/wallets/recovering-your-wallet) for steps on how to import your paper wallet into a wallet of your choice(choose a wallet and import the keys).

**Q: Can I view the balance of my wallet online?**

A: Due to Kryptokrona being a cryptonote-based coin(private), this is not possible.

It should be possible in the future to allow users to give away just their Private View Key to view transactions, but this hasn't been implemented by anyone so far, and would allow that website to see every transaction that you make.

### Other

**Q: How can I get some XKR?**

There are multiple ways to acquire XKR, for example:

* Mining - see [here](/mining/mining)
* Bounties - Bounties for developing XKR software, spreading the word of XKR, and many other things are often posted in the #bounties channel on \[Discord]\[<https://discord.gg/nRK5k7wYy8>]. Check the pinned messages for current bounties.
* Tips - In the Kryptokrona discord we often tip each other, especially if you make spicy memes in the `#memes` channel.
* Buy at an exchange - Check out [this guide](broken://pages/jqxT9vu7KmdNq8hCkhL0).

**Q: Are there any mobile wallets?**

There is currently an Android wallet available in the (Play Store)\[<https://play.google.com/store/apps/details?id=com.xkr>].

**Q: Where is the blockchain stored?**

On Windows, it is in `%APPDATA%/Kryptokrona`. On Mac and Linux, it is in `~/.kryptokrona`.

**Q: Is there a block explorer?**

Yes, the official one is

* <https://explorer.Kryptokrona.se>

**Q: How do I make sure a pool isn't forked?**

Check what network block height it is reporting, compared to other sources.

**Q: I have a question which wasn't answered here, what should I do?**

\[Join the Discord server]\[<https://discord.gg/nRK5k7wYy8>], and come to the `#help` channel, we'll try and fix any issues.


# Getting Started

### What is Kryptokrona?

Kryptokrona is a fast, easy and private cryptocurrency which allows you to send money to friends and businesses.

One of Kryptokrona's main goals is to make things as simple and as accessible as possible for everyday people, creating a cryptocurrency which is inviting, fun and friendly.

Below is essentially a checklist of tasks you have to do to get started with Kryptokrona.

### 1. Setting Up a New Wallet

There are multiple types of wallets you can use with Kryptokrona.

To view a list of them, their interface and a brief description, as a well as guides on how to use them, you can check [this guide](/guides/wallets/making-a-wallet).

### 2. Start Mining Kryptokrona

Mining is essentially the process of using your computer to help verify and secure a cryptocurrency network, in our case, it is the Kryptokrona network. By doing this, you will be rewarded with Kryptokrona.

If you want to learn about cryptocurrencies, mining is a great place to start!

To view an in-depth guide on how to mine Kryptokrona, you can view [this guide](/mining/mining)

### 3. Socialize!

We have an awesome community and would love for you to join in!

You can join our [Discord](https://discord.gg/nRK5k7wYy8) We can't wait to see you :)


# Supporting


# Technical Data

Name: Kryptokrona

Mining Algorithm - CryptoNight-Pico, which offers:

* ASIC resistance
* Enhanced Privacy
* Elastic Blocks
* Fair Mining

Block time: `90` second target block time.

Decimal places: 5, like such `1.00000`

Supply Cap: `1,000,000,000.00000` (1 billion)

Address Prefix: `SEKR`

Currency Code: `XKR`

Pre-mine: Absolutely none, and no presale of any kind.


# Timeline

This is a timeline dedicated to important dates in the history of Kryptokrona

2 April 2019 - Kryptokrona was forked from TurtleCoin

16 April 2019 - The first Kryptokrona Pool, Göta Poolen, was born.

10 Juli 2019 - Hugin was born.

2 April 2020 - Kryptokrona network online for 1 year


# Kryptokrona


# Compiling from Source

The instructions here cover common platforms for compiling from source.

We offer binaries of the latest releases here: <https://github.com/kryptokrona/kryptokrona/releases>

If you would like to compile yourself, read on.

## Prerequisites

You will need the following packages: boost, cmake (3.8 or higher), make, and git.

You will also need either GCC/G++, or Clang.

If you are using GCC, you will need GCC-11.0 or higher.

If you are using Clang, you will need Clang 6.0 or higher. You will also need libstdc++-6.0 or higher.

## Ubuntu

### Build using GCC

If you are using Ubuntu 22.04 LTS GCC11 and C++11 now comes as default and no need to install this.

* `sudo add-apt-repository ppa:ubuntu-toolchain-r/test -y`
* `sudo apt-get update`
* `sudo apt-get install aptitude python3-pip -y`
* `sudo aptitude install -y build-essential g++-11 gcc-11 git libboost-all-dev`
* `sudo pip3 install cmake`
* `export CC=gcc-11`
* `export CXX=g++-11`
* `git clone -b master --single-branch https://github.com/kryptokrona/kryptokrona`
* `cd kryptokrona`
* `mkdir build`
* `cd build`
* `cmake ..`
* `make`

The binaries will be in the `src` folder when you are complete.

* `cd src`
* `./kryptokrona --version`

### Build using Clang

* `sudo add-apt-repository ppa:ubuntu-toolchain-r/test -y`
* `wget -O - https://apt.llvm.org/llvm-snapshot.gpg.key | sudo apt-key add -`

You need to modify the below command for your version of ubuntu - see <https://apt.llvm.org/>

* Ubuntu 14.04 (Trusty)
* `sudo add-apt-repository "deb https://apt.llvm.org/trusty/ llvm-toolchain-trusty 6.0 main"`
* Ubuntu 16.04 (Xenial)
* `sudo add-apt-repository "deb https://apt.llvm.org/xenial/ llvm-toolchain-xenial 6.0 main"`
* Ubuntu 18.04 (Bionic)
* `sudo add-apt-repository "deb https://apt.llvm.org/bionic/ llvm-toolchain-bionic 6.0 main"`
* `sudo apt-get update`
* `sudo apt-get install aptitude -y`
* `sudo aptitude install -y -o Aptitude::ProblemResolver::SolutionCost='100*canceled-actions,200*removals' build-essential clang-6.0 libstdc++-7-dev git libboost-all-dev python-pip`
* `sudo pip install cmake`
* `export CC=clang-6.0`
* `export CXX=clang++-6.0`
* `git clone -b master --single-branch https://github.com/kryptokrona/kryptokrona`
* `cd kryptokrona`
* `mkdir build`
* `cd build`
* `cmake ..`
* `make`

The binaries will be in the `src` folder when you are complete.

* `cd src`
* `./kryptokrona --version`

## Generic Linux

### Build

* `git clone -b master --single-branch https://github.com/kryptokrona/kryptokrona`
* `cd turtlecoin`
* `mkdir build`
* `cd build`
* `cmake ..`
* `make`

The binaries will be in the `src` folder when you are complete.

* `cd src`
* `./kryptokrona --version`

## OSX/Apple

### Prerequisites

* Install XCode and Developer Tools.

### Build using GCC

If using M1 chip, switch gcc\@8 to gcc\@11 when installing through brew.

* `which brew || /usr/bin/ruby -e "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/master/install)"`
* `brew install --force cmake boost llvm gcc@8`
* `export CC=gcc-8`
* `export CXX=g++-8`
* `git clone -b master --single-branch https://github.com/kryptokrona/kryptokrona`
* `cd kryptokrona`
* `mkdir build`
* `cd build`
* `cmake ..`
* `make`

The binaries will be in the `src` folder when you are complete.

* `cd src`
* `./kryptokrona --version`

### Build using Clang

* `which brew || /usr/bin/ruby -e "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/master/install)"`
* `brew install --force cmake boost llvm`
* `export CC=/usr/local/opt/llvm/bin/clang`
* `export CXX=/usr/local/opt/llvm/bin/clang++`
* `git clone -b master --single-branch https://github.com/kryptokrona/kryptokrona`
* `cd kryptokrona`
* `mkdir build`
* `cd build`
* `cmake ..`
* `make`

The binaries will be in the `src` folder when you are complete.

* `cd src`
* `./kryptokrona --version`

## Windows

### Prerequisites

* Install [Visual Studio 2017 Community Edition](https://www.visualstudio.com/thank-you-downloading-visual-studio/?sku=Community\&rel=15\&page=inlineinstall)
* When installing Visual Studio, it is **required** that you install **Desktop development with C++**
* Install the latest version of [Boost](https://bintray.com/boostorg/release/download_file?file_path=1.68.0%2Fbinaries%2Fboost_1_68_0-msvc-14.1-64.exe) - Currently Boost 1.68.

### Build using Visual C++

* From the start menu, open 'x64 Native Tools Command Prompt for vs2017'.
* `cd <your_kryptokrona_directory>`
* `mkdir build`
* `cd build`
* `set PATH="C:\Program Files (x86)\Microsoft Visual Studio\2017\Community\Common7\IDE\CommonExtensions\Microsoft\CMake\CMake\bin";%PATH%`
* `cmake -G "Visual Studio 15 2017 Win64" .. -DBOOST_ROOT=C:/local/boost_1_68_0`

If you have errors on this step about not being able to find the following static libraries, you may need to update your cmake. Open 'Visual Studio Installer' and click 'Update'.

* `MSBuild kryptokrona.sln /p:Configuration=Release /m`

The binaries will be in the `src/Release` folder when you are complete.

* `cd src`
* `cd Release`
* `kryptokrona.exe --version`

## Raspberry Pi 3 B+ (AARCH64/ARM64)

The following images are known to work. Your operation system image **MUST** be 64 bit.

### Known working images

* <https://github.com/Crazyhead90/pi64/releases>
* <https://fedoraproject.org/wiki/Architectures/ARM/Raspberry\\_Pi#aarch64\\_supported\\_images\\_for\\_Raspberry\\_Pi\\_3>
* <https://archlinuxarm.org/platforms/armv8/broadcom/raspberry-pi-3>

Once you have a 64 bit image installed, setup proceeds the same as any Linux distribution. Ensure you have at least 2GB of ram, or the build is likely to fail. You may need to setup swap space.

## CentOS 7

kryptokrona build on CENTOS 7 or RHEL 7 with DEVTOOLS 7

```
$ sudo yum groupinstall 'Development Tools'
```

OR

```
$ sudo yum groups mark install 'Development Tools'
$ sudo yum update 
```

### Install devtools 7

```
# 1. Install a package with repository for your system:
# On CentOS, install package centos-release-scl available in CentOS repository:
$ sudo yum install centos-release-scl # On RHEL, enable RHSCL repository for you system:
$ sudo yum-config-manager --enable rhel-server-rhscl-7-rpms # 2. Install the collection:
$ sudo yum install devtoolset-7# 3. Start using software collections:
$ scl enable devtoolset-7 bash
```

### Requirements

```
$ sudo yum install git wget automake make cmake cmake3  -y

$ sudo yum install gflags-devel snappy-devel zlib-devel bzip2-devel gcc gcc-c++ libstdc++-devel libstdc++-static -y
$ sudo yum install python-devel -y
```

### Install boost 1.62 or above version

Version 1.62 successfully build with gcc 7

```
$ wget https://sourceforge.net/projects/boost/files/boost/1.62.0/boost_1_62_0.tar.gz
$ tar xvf boost_1_62_0.tar.gz
$ cd boost_1_62_0
$ scl enable devtoolset-7 bash
$ ./bootstrap.sh
$ ./b2
```

### Get kryptokrona source and Compile

```
$ cd ..

$ git clone https://github.com/kryptokrona/kryptokrona.git
$ cd kryptokrona
$ mkdir build && cd build
$ scl enable devtoolset-7 bash
$ export CXXFLAGS="-std=gnu++11"
$ cmake3 .. -DBOOST_ROOT=~/boost_1_62_0
$ make
```

polar-it: Is faster than the equivalent version on Ubuntu 16.04


# Forking Kryptokrona

#### **NB:** This guide is deprecated and will not be updated anymore. See the latest version [here](https://kryptokrona.github.io/fork/)

So you want to fork Kryptokrona, huh?

This guide will help you change the necessary sections of the code to set up your coin how you like it.

Firstly, lets quickly talk about *licenses*.

### Licences

When you're poking around the codebase, you might see something like this:

```
// Copyright (c) 2012-2017, The CryptoNote developers, The Bytecoin developers
// Copyright (c) 2014-2018, The Monero Project
// Copyright (c) 2018, The TurtleCoin Developers
// Copyright (c) 2019-2020, Kryptokrona Developers
//
// Please see the included LICENSE file for more information.
```

At the top of each file. We ask when you fork us to make sure you leave these license headers intact.\
When we're programming on codebases like this, we're standing upon the shoulders of giants, and it's both polite, and a legal requirement of the licenses used, to credit the other contributors to the code.

As you may be aware, the CryptoNote white paper set out the initial specification for CryptoNote coins.\
The ByteCoin developers created the first implementation of this specification working closely with the CryptoNote developers, and this is what has become ByteCoin today.\
This was forked early on to become Bitmonero, and then Monero.\
The Monero developers have contributed back significant chunks of code to the original ByteCoin codebase, and of course, they maintain their own repositories and code.

The ForkNote Project was created as a fork of ByteCoin, to create a way to fork ByteCoin, easily by separating the needed constants and strings out into a separate file.

Kryptokrona then forked the Forknote Project and made our own changes, some of which were then contributed back to ForkNote.

So, make sure if you're doing a find and replace that all of these lines remain intact.\
You can of course start adding your own copyright line, for example,

```
// Copyright (c) 2012-2017, The CryptoNote developers, The Bytecoin developers
// Copyright (c) 2014-2018, The Monero Project
// Copyright (c) 2018, The TurtleCoin Developers
// Copyright (c) 2019-2020, Kryptokrona Developers
// Copyright (c) 2020, my super cool coin 
//
// Please see the included LICENSE file for more information.
```

Ok, now we understand about licenses, let's get the code!

### The actual forking process

* The easiest way to fork Kryptokrona, is to start by making a GitHub account. You can do this [here](https://github.com/join) if you don't have an account already.
* Make sure you're signed in. Next, head over to the Kryptokrona repo, and hit `Fork` in the top right corner.
* It should look something like this:

  <img src="https://i.imgur.com/ZNUS8ED.png" alt="Fork it!" data-size="original">
* Next, you want to get the source code on your computer. Head over to the repository you just forked, and click the `Clone or Download` button. We want to clone the source code, so we can make changes, then push it back up to GitHub.
* It should look something like this:

  <img src="https://i.imgur.com/UlqtvF6.png" alt="Clone it!" data-size="original">
* Now, take this URL shown, and copy it.
* Next, you will need to download a git client. If you are a windows user, I would suggest [Git for Windows](https://gitforwindows.org/), whilst if you are a Linux or Mac user, you should have this either already installed, or can install it from your repos or with brew.
* Once you have opened up git bash or a terminal, you should be able to type `git clone URL`, where `URL` is the link you copied earlier, from GitHub.
* It should look something like this:

![Bop it!](https://i.imgur.com/Fv435iR.png)

* Great, now the code is on our computer. We're almost ready to start changing it!

### Compiling

First, it might be a good idea to try compiling our code, so we can mess around with it later.

Just incase this guide gets outdated, you can always find the latest instructions on how to compile Kryptokrona on our [GitHub](https://github.com/Kryptokrona/Kryptokrona#how-to-compile).

#### Linux

**Prerequisites**

* You will need a few dependencies for the build, most notably, cmake, make, gcc, g++, and boost.
* On ubuntu: `sudo apt-get install -y build-essential python-dev gcc g++ git cmake libboost-all-dev`

**Building**

* `cd Kryptokrona`
* `mkdir build`
* `cd build`
* `cmake ..`
* `make`
* The binaries will be placed in the `Kryptokrona/build/src` folder.

#### Apple

**Prerequisites**

* Ensure you have brew installed. If you don't, you can install it like so: `/usr/bin/ruby -e "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/master/install)"`
* Now we've got brew installed, we can install the dependencies.
* `brew install cmake boost`

**Building**

* `cd Kryptokrona`
* `mkdir build`
* `cd build`
* `cmake ..`
* `make`
* The binaries will be placed in the `Kryptokrona/build/src` folder.

#### Windows

**Prerequisites**

* Install [Visual Studio 2017 Community Edition](https://www.visualstudio.com/thank-you-downloading-visual-studio/?sku=Community\&rel=15\&page=inlineinstall)
* When installing Visual Studio, ensure you install `Desktop development with C++` and the `VC++ v140 toolchain` when selecting features.
* The option to install the v140 toolchain can be found by expanding the `Desktop development with C++` node on the right. You will need this for the project to build correctly.
* Install [Boost 1.59.0](https://sourceforge.net/projects/boost/files/boost-binaries/1.59.0/), ensuring you download the installer for MSVC 14

**Building**

* From the start menu, open `x64 Native Tools Command Prompt for vs2017`
* `cd <your_Kryptokrona_directory>`
* `mkdir build`
* `cd build`
* Set the PATH variable for cmake: e.g. `set PATH="C:\Program Files (x86)\Microsoft Visual Studio\2017\Community\Common7\IDE\CommonExtensions\Microsoft\CMake\CMake\bin";%PATH%`
* `cmake -G "Visual Studio 14 Win64" .. -DBOOST_ROOT=C:/local/boost_1_59_0` (Or your boost installed dir.)
* `MSBuild Kryptokrona.sln /p:Configuration=Release /m`
* The binaries will be placed in the `Kryptokrona/build/src/Release` folder.

### Recompiling

Once you've compiled your code, you don't have to perform the full process above again.

There are two rules. If you've added a new file, or removed a file, you will have to remove the build folder, recreate it, then re-run cmake, and then re-run make (Or MSBuild).

If you've just changed code in a file, you just need to re-run make from the build folder. It will save bits which don't need to be recompiled, so this is a lot quicker most of the time.

### Atomic Units

Next, I'd like to talk quickly about *atomic units*. You can skip this section if you're a pro already.

All of the constants in CryptoNoteConfig.h and most of the code, that refers to the actual amount of coins, is in *Atomic Units*.

**What does this mean?**

Well, if we're talking about Kryptokrona, we have 2 decimal places. That means, to get the atomic units of an amount of XKR, we need to multiply the amount by 100, or 10^2.

If we have 10.23 XKR, this is 1023 in atomic units. Atomic units have no decimal point, and so can be represented as an integer, in the code. Some different currencies have a special name for their atomic units, to make it easier to talk about. In Bitcoin, this is called a *satoshi*, and in Kryptokrona, it is called a *shell*.

**Why is this helpful?**

Computers are unable to accurately store floating point numbers (or, numbers with a decimal point), and so performing math on them is often problematic.

For example, let's say we want to split 10.00 XKR between 3 people. If you perform `10.00 / 3` in a programming language, you will probably see a result similar to `3.3333333333333335`. Where did that 5 come from?! The computer is incapable of storing this number to its full amount of decimal places.

**How do we fix this?**

Now, let's demonstrate how we can solve this issue, with *atomic units*. Again, we have 10.00 XKR, and we want to split it between 3 people. Recall that to get the number of atomic units, we need to multiply by 100. So, we have a value of 1000 in atomic units. Now we can perform *integer division* instead. Let's perform `1000 / 3` - make sure you are using *integral division* in your programming language - and you should get a result of `333`.

That's correct, each person can only get 333 units, or, if we want to convert back to XKR, 3.33 XKR. You might have noticed we're missing one atomic unit, or 0.01 XKR. We have to use remainders when dealing with atomic values, as one atomic unit cannot be split down anymore.

So, the code might look something like this, when using atomic units.

```cpp
/* 10.00 XKR in atomic units */
float XKR = 10.00;
int shells = static_cast<int>(XKR) * 100;

int numPeople = 3;

int shellsPerPerson = shells / numPeople;
int remainder = shells % numPeople;

std::cout << "Splitting " << XKR << " XKR" between << numPeople << " gives "
          << (shellsPerPerson / 100) << " XKR each, with " << (remainder / 100)
          << " XKR spare." << std::endl;
```

Usually, we will *always* use atomic units in our code, and only convert back to the expected representation with a decimal point when we print things to the user.

Ok, we know what atomic units are, lets go change some stuff!

### Changing the name of your binaries, i.e. CMakeLists.txt

We're gonna start with some boring stuff - changing the name of your binaries.

Open up CMakeLists.txt in the `src/` folder.

Note that there is also a CMakeLists.txt in the root directory, this is not the file you want!

The lines we want to be changing are at the very bottom of the file.

```
set_property(TARGET Kryptokrona PROPERTY OUTPUT_NAME "Kryptokrona")
set_property(TARGET zedwallet PROPERTY OUTPUT_NAME "zedwallet")
set_property(TARGET PaymentGateService PROPERTY OUTPUT_NAME "walletd")
set_property(TARGET PoolWallet PROPERTY OUTPUT_NAME "poolwallet")
set_property(TARGET Miner PROPERTY OUTPUT_NAME "miner")
```

To change the name of a binary, change the final string in one of these lines. For example:

`set_property(TARGET Kryptokrona PROPERTY OUTPUT_NAME "AppleCoind")`

Save the file, and recompile.

### Changing version numbers

Another boring one - changing the version numbers. This is the thing that appears when you start up Kryptokrona, e.g. `Welcome to Kryptokrona v0.6.4.1264`

Open up `src/version.h.in`.

The values are pretty self-explanatory. Set `PROJECT_NAME` to the name of your coin, `PROJECT_SITE` to your coins website, and `PROJECT_COPYRIGHT` to your copyright string.

Next, the version numbers.

`APP_VER_MAJOR` determines the first part of the version. You usually increment this value if you make a substantial change to your code, which potentially breaks APIs, wallet formats, blockchain formats, and so on.

`APP_VER_MINOR` determines the second number of the version. This is usually incremented for significant upgrades, such as hard forks.

`APP_VER_BUILD` determines the final number of the version. This is usually incremented for small changes, such as bug fixes, speedups, small wallet changes, and so on.

These numbers are then combined to form the full version number, in the format:

`APP_VER_MAJOR`.`APP_VER_MINOR`.`APP_VER_BUILD`.

For example, if we set the 3 values to 0, 6, and 4, we would end up with a version number of 0.6.4.

A good start for your project is 0.0.1, so

```
#define APP_VER_MAJOR 0
#define APP_VER_MINOR 0
#define APP_VER_REV 1
```

### CryptoNoteConfig.h

Ok, now onto the fun stuff!

Open up the file `CryptoNoteConfig.h`, located in the `src` folder.

Let's start at the top. We'll only focus on the constants which need changing, as some of them are fine to keep as they are.

**`const uint64_t DIFFICULTY_TARGET = 30; // seconds`**<br>

This is how fast you want blocks to be. In Kryptokrona, we have blocks on average every 30 seconds. If you wanted blocks to be every 2 minutes, you would set this to be:

* `const uint64_t DIFFICULTY_TARGET = 120; // seconds`<br>

**`const uint64_t CRYPTONOTE_PUBLIC_ADDRESS_BASE58_PREFIX = 3914525;`**<br>

This defines what the addresses will start with. In Kryptokrona, this decodes to `XKR`.

So how do we get this prefix? We can use this [handy tool](https://cryptonotestarter.org/tools.html).

![Prefix Generator](https://i.imgur.com/F2ZARZ9.png)

Scroll down to the prefix generator, and enter your desired address prefix. Note that some characters are disabled, so you may not be able to get the perfect prefix. For example, `aPPLE` is allowed, but `APPLE` isn't.

You may note that XKR's prefix is a number, while the output of this generator is not. These values are in hex format, and will automatically be decoded into a number when compiled, though you can use any standard hexadecimal to decimal converter to change the prefix into a number if you prefer.

So, if we wanted our prefix to be 'aPPLE', we would set this to be:

* `const uint64_t CRYPTONOTE_PUBLIC_ADDRESS_BASE58_PREFIX = 0x1e1f8cc7;`<br>

**`const uint32_t CRYPTONOTE_MINED_MONEY_UNLOCK_WINDOW = 40;`**<br>

This value defines how many blocks need to be followed in the current chain before releasing the reward for mining a block for spending.

We would suggest you set this value to be roughly equal to 20 minutes - in Kryptokrona's case that's exactly what we have - 40 blocks \* 30 seconds = 20 minutes.

If you have a block time of 2 minutes for example, we would set this value to 10.

* `const uint32_t CRYPTONOTE_MINED_MONEY_UNLOCK_WINDOW = 10;`<br>

**`const uint64_t MONEY_SUPPLY = UINT64_C(100000000000000);`**<br>

This line is a pretty significant one. It determines the max supply of coins your cryptocurrency will have. In Kryptokrona, this is 1 trillion XKR, but as previously mentioned, all these values are in *atomic units*, so this value also includes the amount after the decimal point. Thus, this value is 1 trillion \* 100, as Kryptokrona has 2 places after the decimal point.

Therefore, we suggest you decide how many decimal places your coin has, before filling in this value.

If you want your coin to have 6 decimal places, and the total supply to be ten thousand (10,000), the MONEY\_SUPPLY value would be: `10^6 (or 1,000,000) * ten thousand (10,000) = 10000000000`.

So, we would then pop this value in to give us:

* `const uint64_t MONEY_SUPPLY = UINT64_C(10000000000);`<br>

**`const uint32_t ZAWY_DIFFICULTY_BLOCK_INDEX = 187000;`**<br>

This section will cover all of these, since they are all related:

```
const uint32_t ZAWY_DIFFICULTY_BLOCK_INDEX 	                 = 187000;
const uint64_t LWMA_2_DIFFICULTY_BLOCK_INDEX                 = 620000;
const uint64_t LWMA_2_DIFFICULTY_BLOCK_INDEX_V2              = 700000;
const uint64_t LWMA_2_DIFFICULTY_BLOCK_INDEX_V3              = 800000;
```

These values set the heights where the different difficulty algorithms go live. A difficulty algorithm determines how hard it is to mine a block at a given height. If there are more people mining, it gets harder, and visa versa. This ensures blocks are found on average every 30 seconds (In XKR's case).

Difficulty algorithms are pretty hard to write, so we have quite a lot of revisions! We strongly suggest you use the latest version, to make you more resistant to pulse mining and timewarp attacks. The below section will activate each one at the first available block height, so you will be running the latest LWMA-2 by block 3.

* `const uint32_t ZAWY_DIFFICULTY_BLOCK_INDEX = 0;`\ <br>
* `const uint32_t LWMA_2_DIFFICULTY_BLOCK_INDEX = 1;`\ <br>
* `const uint32_t LWMA_2_DIFFICULTY_BLOCK_INDEX = 2;`\ <br>
* `const uint32_t LWMA_2_DIFFICULTY_BLOCK_INDEX = 3;`\ <br>

**`const unsigned EMISSION_SPEED_FACTOR = 25;`**<br>

This value defines how fast the maximum supply will be emitted. A smaller value means the supply will be emitted faster, and a higher values means it will take longer for the supply to be released. You can again use the website [linked earlier](https://cryptonotestarter.org/tools.html) to experiment with different values for the emission and how they will affect how long it takes for the supply to be distributed.

If we wanted a fast emission, we could set this to a value like 21.

* `const unsigned EMISSION_SPEED_FACTOR = 21;`<br>

**`const size_t CRYPTONOTE_DISPLAY_DECIMAL_POINT = 2;`**<br>

This value defines how many numbers there are after the decimal point in your currency. In Kryptokrona, this value is 2, so we have amounts like 10.23 XKR. If we set this to 6, we would have an amount like 10.234567 XKR instead. Remember, as previously mentioned, this affects your money supply and other parameters which depend upon atomic units.

* `const size_t CRYPTONOTE_DISPLAY_DECIMAL_POINT = 6;`<br>

**`const uint64_t MINIMUM_FEE = UINT64_C(10);`**<br>

This value defines what the minimum fee a user must spend to send a transaction is. Note this doesn't apply to fusion transactions.

A lower value allows cheaper transactions, but can mean your network can be spammed by lots of small transactions.

A happy medium is generally desired, though you could optionally raise this at a later date.

This value is defined again in *atomic units*, so multiply your desired minimum fee by 10 \* the number of numbers after the decimal point in your coin.

* `const uint64_t MINIMUM_FEE = UINT64_C(1000);`<br>

**`const uint64_t MINIMUM_MIXIN_V1 = 0;`**<br>

This section will cover all of these, because they are all related:

```
const uint64_t MINIMUM_MIXIN_V1                              = 0;
const uint64_t MAXIMUM_MIXIN_V1                              = 100;
const uint64_t MINIMUM_MIXIN_V2                              = 7;
const uint64_t MAXIMUM_MIXIN_V2                              = 7;

const uint32_t MIXIN_LIMITS_V1_HEIGHT                        = 440000;
const uint32_t MIXIN_LIMITS_V2_HEIGHT                        = 620000;

const uint64_t DEFAULT_MIXIN = MINIMUM_MIXIN_V2;
```

These set the mixin values that are allowed on the network, and at what height they are applied. If you want a private coin from the get-go, I would suggest setting MIXIN\_LIMITS\_V1\_HEIGHT to 0, and MIXIN\_LIMITS\_V2\_HEIGHT to 1. Then, set the MINIMUM\_MIXIN\_V1/V2 and MAXIMUM\_MIXIN\_V1/V2 values as appropriate.

Don't set a value that is *too* high, otherwise your network will have difficulty processing transactions. You shouldn't set the minimum anymore than 100, and sane values would be somewhere in the 0 - 30 range.

`DEFAULT_MIXIN` is used to set the mixin value used in zedwallet, so set it to a sane value.

Make sure your minimum is less than or equal to your maximum!

```
const uint64_t MINIMUM_MIXIN_V1                              = 0;
const uint64_t MAXIMUM_MIXIN_V1                              = 100;
const uint64_t MINIMUM_MIXIN_V2                              = 7;
const uint64_t MAXIMUM_MIXIN_V2                              = 7;

const uint32_t MIXIN_LIMITS_V1_HEIGHT                        = 0;
const uint32_t MIXIN_LIMITS_V2_HEIGHT                        = 1;

const uint64_t DEFAULT_MIXIN = MINIMUM_MIXIN_V2;
```

<br>

**`const uint64_t DEFAULT_DUST_THRESHOLD = UINT64_C(10);`**<br>

This section will cover all of these, because they are all related:

```
const uint64_t DEFAULT_DUST_THRESHOLD = UINT64_C(10);
const uint64_t DEFAULT_DUST_THRESHOLD_V2 = UINT64_C(0);

const uint32_t DUST_THRESHOLD_V2_HEIGHT = MIXIN_LIMITS_V2_HEIGHT;
```

The dust threshold determines the smallest amount that can be sent in a transaction, and can lead to lots of tiny amounts accumulating in your wallet which cannot be sent.

Setting the dust threshold to zero prevents this, but has a side effect of making transactions slightly bigger.

I suggest setting DUST\_THRESHOLD\_V2\_HEIGHT to 0, to make small amounts always spendable.

* `const uint32_t DUST_THRESHOLD_V2_HEIGHT = 0;`<br>

**`const uint32_t UPGRADE_HEIGHT_V4 = 350000;`**<br>

This value determines when the mining algorithm will transition to Original CryptoNight, also known as CN v0, to CryptoNight Lite v1, also known as CryptoNight Lite v7.

Original CN currently allows ASICs on the network, so we suggest you set this upgrade height to 3, to near instantly switch to the ASIC resistant CryptoNight Lite v1.

However, if you would prefer to stay on original CryptoNight, you can either find where this variable is used and patch it out, or, you can set the upgrade height to `std::numeric_limits<uint32_t>::max()`

(You will probably need to add `#include <limits>` to the top of the file if you choose this option)

* `const uint32_t UPGRADE_HEIGHT_V4 = 3; // Upgrade height for CN-Lite Variant 1 switch.`<br>

**`const uint64_t FORK_HEIGHTS[] =`**<br>

This variable is used by the `status` command in zedwallet and Kryptokrona to notify users when a fork is upcoming, or their software is outdated. We suggest you set up some regular forks ahead of time, if you then need to update the software this will let users know when to expect this.

If you wish to not pre-prepare any forks, you can empty the list.

This will set the status command to notify of a fork at 100k and 300k blocks.

* ```
  const uint64_t FORK_HEIGHTS[] =
  {
    100000,
    300000
  };
  ```

  <br>

**`const uint8_t CURRENT_FORK_INDEX = FORK_HEIGHTS_SIZE == 0 ? 0 : 3;`**<br>

This value relates to the previous FORK\_HEIGHTS array. It determines which fork heights the software supports. (This value is zero-indexed). For example, if our `FORK_HEIGHTS = {100, 200, 300}` and `CURRENT_FORK_INDEX = 1` then the software will support the fork at FORK\_HEIGHTS\[1] - which is the fork at 200 blocks.

We have a ternary to check FORK\_HEIGHTS\_SIZE so if you wish to empty the FORK\_HEIGHTS array, you don't need to set a CURRENT\_FORK\_INDEX.

* `const uint8_t CURRENT_FORK_INDEX = FORK_HEIGHTS_SIZE == 0 ? 0 : 1;`<br>

**`const char CRYPTONOTE_NAME[] = "Kryptokrona";`**<br>

This is an obvious one. It's the name of your coin!

* `const char CRYPTONOTE_NAME[] = "SuperCoolCoin";`<br>

**`const int P2P_DEFAULT_PORT` and `const int RPC_DEFAULT_PORT`**

These values define the ports that are used by the daemon to communicate. There is no real issue with using the same values as the Kryptokrona software, but if you are running both a Kryptokrona daemon and your own daemon, you would have to change the port one uses, as they will both need control over the port.

Ports can be in the range of 0 - 65535, however using ports in the 0 - 1023 range is not recommended, as on unix systems a program will require administrative permissions to use these ports.

* `const int P2P_DEFAULT_PORT = 10101;`
* `const int RPC_DEFAULT_PORT = 10102;`<br>

**`const static boost::uuids::uuid CRYPTONOTE_NETWORK =`**

This value sets the 'Network ID' of your coin. This ensures your network will not respond to network connections from other coins, such as Kryptokrona.

This value is using hex values, which should be in the form 0x?? where `?` is a valid hex value (0-9, a-f).

* ```
  const static boost::uuids::uuid CRYPTONOTE_NETWORK =
  {
      {  0x11, 0x22, 0x33, 0x44, 0x55, 0x66, 0x77, 0x88, 0x99, 0xaa, 0xbb, 0xcc, 0xdd, 0xee, 0xff, 0x00  }
  };
  ```

<br>

**`const char* const SEED_NODES[] = {`**<br>

This variable defines the seed nodes daemons will connect to on the very first launch, before they are aware of any peers. You will need to run these on different servers, to bootstrap other nodes. Once your coin is established, it might be a good idea to ask other trusted community members to host some seed nodes, to help decentralize your coin.

* ```
  const char* const SEED_NODES[] =
  {
      "111.111.111.111:11897",
      "222.222.222.222:11897",
  };
  ```

  <br>

### CryptoNoteCheckpoints.h

A nice quick job, we need to remove all the checkpoints in `src/CryptoNoteCheckpoints.h`

Checkpoints are used to verify that whilst syncing, you are on the right path, and not wasting your time syncing blocks from an incorrect daemon. It does this by matching a block hash to a block height.

This is all grand, however if you are creating a new chain, you will of course have new hashes for your blocks!

To fix it, just set `const std::initializer_list<CheckpointData> CHECKPOINTS = {};`

It would be a good idea to add some checkpoints here for your new chain when you're up and running.

### WalletConfig.h

Next up to modify is WalletConfig.h, located in `src/zedwallet/WalletConfig.h`

These fields are all pretty well documented already, but we'll go over them anyway.<br>

**`const std::string addressPrefix = "XKR";`**<br>

This value is used to check inputted addresses are correct. This value corresponds to the value you chose for your address prefix earlier, in `const uint64_t CRYPTONOTE_PUBLIC_ADDRESS_BASE58_PREFIX =`

* `const std::string addressPrefix = "aPPLE";`<br>

**`const std::string ticker = "XKR";`**<br>

This refers to the 'short name' your coin has, which is often used as a ticker on exchanges. For example, in Kryptokrona this is XKR, in Monero this is XMR, and in Bitcoin this is BTC.

* `const std::string ticker = "APPLE";`<br>

**`const std::string daemonName = "Kryptokrona";`**<br>

This variable determines what the name of your daemon is. We'll talk about changing the names of the executables generated in the `CmakeLists.txt` section. We'll skip mentioning `walletName`, and `walletdName` as these both follow the same format.

* `const std::string daemonName = "AppleCoind";`<br>

**`const std::string contactLink = "http://chat.kryptokrona.se";`**<br>

This value is used to let the user know where they can get support if their wallet gets stuck whilst syncing. In our case, this is the Kryptokrona discord. Maybe you have a forum or an IRC chat instead?

* `const std::string contactLink = "https://applecoin.com/livechat"`<br>

**`const long unsigned int standardAddressLength = 99;`**

This value is used to verify inputted addresses are correct. You can easily get this value by compiling, generating an address with zedwallet, and checking how long it is.

* `const long unsigned int addressLength = 100;`<br>

**`const long unsigned int integratedAddressLength = 236;`**<br>

This value is used to verify inputted addresses are correct. An integrated address is an address which also contains an embedded payment ID, to alleviate users from having to remember to supply one with the transaction.

You can easily get this value by compiling, generating an address with zedwallet, then using the `make_integrated_address` command, and checking how long it is.

You can use your own address with this command, and any payment ID. If you don't know how to generate a payment ID, here's a random one for you to use.

`8eba031ca60bf9b9f680309819bddf071e619c53ff71766e48e365812e229452`

* `const long unsigned int integratedAddressLength = 237;`<br>

**`const uint64_t defaultMixin = CryptoNote::parameters::DEFAULT_MIXIN;`**<br>

This sets the mixin value to be used with transactions. Make sure this is in the bounds you set earlier, with `MINIMUM_MIXIN_V1/V2` and `MAXIMUM_MIXIN_V1/V2`.

* `const uint64_t defaultMixin = 7;`<br>

**`const uint64_t defaultFee = CryptoNote::parameters::MINIMUM_FEE`**<br>

If you want to set a higher default fee, perhaps to make transactions go through quicker, you can do that here. As usual, this is in *atomic units*. You may also wish to change `const uint64_t minimumFee = CryptoNote::parameters::MINIMUM_FEE;` to prevent users from sending a lower fee than desired.

Remember this limit is only enforced by zedwallet, and the user can change the limit and recompile, or use a different wallet program. If you want to enforce higher fees across the network, change the value of `CryptoNote::parameters::MINIMUM_FEE` in `CryptoNoteConfig.h`.

* `const uint64_t defaultFee = 100;`<br>

**`const bool mixinZeroDisabled = true;`**<br>

Is a mixin of zero allowed on the network? If at some point a mixin of zero will be disabled, but that point is at a later fork, still set this to `true`.

If you set this to true, you can change the value of

```
const uint64_t mixinZeroDisabledHeight = CryptoNote::parameters::MIXIN_LIMITS_V2_HEIGHT;
```

To determine what block height a mixin of zero gets disabled. In Kryptokrona's case, this was disabled at block 620k, but being a new network, you have the advantage of being able to disable a mixin of zero much earlier, or even from the launch of your network.

Again, this is only a client-side limitation. Ensure you have set your mixin limits in `CryptoNoteConfig.h` so that the network will enforce the mixin limits. Any ideas you always want to happen, need to be done at the network level, else custom daemons/wallets etc. can be written to avoid those ideas/limits.

If you want to allow zero mixins, then `mixinZeroDisabledHeight` does nothing.

* ```
  const bool mixinZeroDisabled = true;
  const uint64_t mixinZeroDisabledHeight = 0;
  ```

  <br>

### Setup

Ok, so you've finished tweaking all the configs, and now you're ready to go! To start with, you will need to compile your code. See the compiling section below.

Make sure you've got the IPs of your seed nodes filled in in the config, 3 daemons need to be connected to the network for your coin to work.

Once you've compiled the code on all your machines, you can start up your daemon. If you are unable to connect to the seed nodes, you will see something like `Failed to connect to seed nodes` in your daemon output.

Ensure your firewalls are not preventing the daemon connection, you may need to open the p2p and RPC ports for the daemon, which by default are 11898 and 11897.

If your daemons are now talking to each other, you can start mining, and launch your blockchain!

You can use the solo mining `miner` executable for this. From a command prompt or terminal, launch the miner like so: `miner --threads 1 --log-level 3 --address <your address>`, replacing with an address you have generated and control.

You can, of course, increase the threads value, however as you are the only one currently mining on the network, there is not much point in that yet!

E.g.

```
./miner --threads 8 --log-level 3 --address SEKRuyTvsJZjAsbtgbYmZeV1pb43dXqcv1jNdYNwokv8GUa1ZbYzivzg2gEgXeAfUqJF12APf3Rq89UneaQKiZ1nGW1vYqkGb8Y
```

If you've done this correctly, you should see output like this: `Block successfully submitted, hash xxxx`, and in your daemon window, you should see the `New block detected` value increasing in height.

Congratulations!

### Compiling

You can always find the latest instructions on how to compile Kryptokrona on our [GitHub](https://github.com/Kryptokrona/Kryptokrona#how-to-compile).

### Support, Questions?

Something not clear? Head over to our [Discord](http://chat.kryptokrona.se) and ask in the #help channel, and hopefully, someone will be able to help you out.

Let us know if something is wrong with this guide, or missing, so we can update it and make it better!

Good luck with your new coin!


# Local Testnet

Setting up a testnet using just one PC is very easy, and lets you test things out with very minimal setup.

## Setup

### Setup with Docker

#### Change config

Before we start we just need to change slight a bit on the `cryptonote_config.h` header file with some constants so we don't use our main net to test on.

Open up `src/config/cryptonote_config.h`

Then we need to change the constants **P2P\_DEFAULT\_PORT** and **RPC\_DEFAULT\_PORT** to:

```cpp
const int      P2P_DEFAULT_PORT                              =  11898;
const int      RPC_DEFAULT_PORT                              =  11899;
```

And put some different letter or number in one of these **CRYPTONOTE\_NETWORK** uuids:

```cpp
const static   boost::uuids::uuid CRYPTONOTE_NETWORK         =
{
    {  0xf1, 0x4c, 0xb8, 0xc8, 0xb2, 0x56, 0x45, 0x2e, 0xee, 0xf0, 0xb4, 0x99, 0xab, 0x71, 0x6c, 0xcc  }
};
```

And also we need to comment out seed nodes:

```cpp
const char* const SEED_NODES[] = {
  // "68.183.214.93:11897",//pool1
  // "5.9.250.93:11898"//techy
};
```

Now we are good to go to start with Docker. So if we want to setup our own testnet locally on our computer we will need to install Docker on our computer.

#### Install Docker

On Windows or Mac it's enough to install Docker Desktop and we will have everything we need in order to setup. For GNU/Linux however there is a slight different process. We are going through the steps for doing it on a Ubuntu distribution, it should work on all Debian derived distributions. Read below.

Update our headers:

```bash
sudo apt-get update
```

Installing neccessary dependencies for Docker:

```bash
sudo apt-get -y install \
    ca-certificates \
    curl \
    gnupg \
    lsb-release
```

Setting up the keyring:

```bash
curl -fsSL https://download.docker.com/linux/ubuntu/gpg | sudo gpg --dearmor -o /usr/share/keyrings/docker-archive-keyring.gpg
```

Updating our sources.list for be able to download Docker:

```bash
echo \
"deb [arch=$(dpkg --print-architecture) signed-by=/usr/share/keyrings/docker-archive-keyring.gpg] https://download.docker.com/linux/ubuntu \
$(lsb_release -cs) stable" | sudo tee /etc/apt/sources.list.d/docker.list > /dev/null
```

Installing Docker and Docker Compose:

```bash
sudo apt-get update
sudo apt-get install -y docker-ce docker-ce-cli containerd.io docker-compose
```

#### Start the orchestration of Docker containers

So now we have everything in place in order for us to build and orchestrate up a local testnet. We do not need to install all dependencies mentioned before this section of Docker on your computer. When we start the process of setting up the testnet we will build a Docker Image that installs everything for us automatically.

So to start from scratch we will use the shell script `setup-testnet.sh` but before that we must make sure that all our shell scripts that we need are executable on our system. To make the shell scripts executable:

```bash
sudo chmod +x setup-testnet.sh \
              remove-testnet.sh \
              start-testnet.sh \
              teardown-testnet.sh
```

To start:

* `./setup-testnet.sh`

So now the first time when starting the script it will take a while to compile and link all the files (around 15-20 minutes dependening on how powerful computer you have). So when it's done you will see a lot of output of the Daemons starting on three nodes. The miner do not have any output on the terminal.

#### Stop all Docker containers

So all of these containers running will take up some memory and CPU usage on your system so it could be wise to stop these when not using them. To do that just run the shell script:

* `./teardown-testnet.sh`

This makes sure that we still have the image saved locally so we don't need to build it again when we will start it.

#### Start all Docker containers again

Instead of using `setup-testnet.sh` file we will use the file `start-testnet.sh`:

* `./start-testnet.sh`

The difference here is that we will not build the image again and thus has to wait a while. Now this will only take seconds. And now we have our testnet up again!

#### Removing all data

When we want to do a full cleanup on our system with Docker we can start the script `remove-testnet.sh`:

* `./remove-testnet.sh`

Now we will remove networks, volumes, images and containers existing on our system. If you after removing everything want to start again. Just use the file `setup-testnet.sh` again.

### Setup without Docker

#### Disabling outside peers

First, we need to disable incoming peers, so they don't interfere with our testnet. This step is not mandatory, but it's likely you'll get other daemons connected to you (or you will connect to the seed nodes), messing up your testnet.

You can block the p2p port of your daemon with `ufw`, or another firewall program.

We need to apply this to each daemon p2p port we launch.

```
sufo ufw enable
sudo ufw deny 10000;
sudo ufw deny 10001;
sudo ufw deny 10002;
```

Once you're done, and want to re-enable, either disable ufw, or run

```
sudo ufw disable
sudo ufw allow 10000;
sudo ufw allow 10001;
sudo ufw allow 10002;
```

#### Clearing checkpoints

If you're wanting to mine any blocks, you'll want to empty the checkpoints file. Open up `src/config/CryptoNoteCheckpoints`, and empty the checkpoints there. Recompile.

#### Data directories

First, we need three new folders to be the location for the blockchains for each daemon.

In this example, I'm simply going to use the folder `a`, `b`, and `c`.

On linux: `mkdir a b c`, to make the folders.

#### Running

#### Launching daemons

Next we need to launch three daemons. Each need to have a different p2p port, different rpc port, and different data directory, to not conflict.

In the below commands, replace `kryptokrona` with the name of your daemon executable, if you are a kryptokrona fork.

**Daemon 1**

```
./kryptokrona --data-dir a --add-exclusive-node 127.0.0.1:10001 --add-exclusive-node 127.0.0.1:10002 --p2p-bind-port 10000 --rpc-bind-port 20000
```

**Daemon 2**

```
./kryptokrona --data-dir b --add-exclusive-node 127.0.0.1:10000 --add-exclusive-node 127.0.0.1:10002 --p2p-bind-port 10001 --rpc-bind-port 20001
```

**Daemon 3**

```
./kryptokrona --data-dir c --add-exclusive-node 127.0.0.1:10000 --add-exclusive-node 127.0.0.1:10001 --p2p-bind-port 10002 --rpc-bind-port 20002
```

And you're done! The three daemons should connect to each other.

Start up a miner, and test stuff out. Remember to use the rpc port you started one of your daemons on with your wallet/miner.


# Developer Resources

Technical resources to start building on Kryptokrona.

### Kryptokrona Source Code

* [Kryptokrona-Soure-Code](https://github.com/kryptokrona/kryptokrona)

### Libraries

* [Kryptokrona-wallet-backend-js](https://github.com/kryptokrona/kryptokrona-wallet-backend-js): NodeJS Kryptokrona Wallet Backend
* [Kryptokrona-utils](https://github.com/kryptokrona/kryptokrona-utils): Kryptokrona-Utils

Since Kryptokronan is a fork of turtlecoin, these links will also prove useful.

### TurtleCoin Core RPC APIs

* [TurtleCoind](https://github.com/kryptokrona/kryptokrona-docs/blob/master/docs/api/Daemon-JSON-RPC-API/README.md) - Blockchain daemon
* [wallet-api](https://turtlecoin.github.io/wallet-api-docs/) - Recommended RPC API to use for new projects or to migrate to from existing projects. Swagger based REST interface.
* [turtle-service](https://github.com/kryptokrona/kryptokrona-docs/blob/master/docs/api/Legacy-Wallet-RPC-API/README.md) - Turtle Service Wallet API. Will eventually be deprecated, suggested to use wallet-api for new projects.

### RPC API Clients

* [NodeJS](https://www.npmjs.com/package/turtlecoin-rpc)
* [PHP](https://github.com/turtlecoin/turtlecoin-rpc-php)
* [Python](https://github.com/turtlecoin/turtlecoin-rpc-python)
* [Go](https://github.com/turtlecoin/turtlecoin-rpc-go)

### Libraries

* [turtlecoin-wallet-backend-js](https://github.com/turtlecoin/turtlecoin-wallet-backend-js): NodeJS TurtleCoin Wallet Backend
* [turtlecoin-wallet-backend-cpp](https://github.com/zpalmtree/turtlecoin-wallet-backend-cpp): C++ TurtleCoin Wallet Backend
* [TurtleCoin.Net API](https://github.com/turtlecoin/turtlecoin-walletd-csharp): An asynchronous wrapper API for loading and accessing the TurtleCoin daemon and wallet application through C#.
* [Woo Turtle](https://github.com/turtlecoin/woo-turtle): A TurtleCoin Payment Gateway Plugin for WooCommerce.
* [turtlecoind-ha](https://www.npmjs.com/package/turtlecoind-ha): NodeJS TurtleCoind High-Availability Daemon Wrapper
* [turtleservice-ha](https://www.npmjs.com/package/turtleservice-ha): NodeJS Turtle-Service High-Availability Wrapper\
  (*note: turtle-service is deprecated and it is recommended to use wallet-api for new projects*)

### Reads

* [CantiLib](https://github.com/turtlecoin/cs-turtlecoin): TurtleCoin daemon spec and PoC.
* [TurtleCoin Blog](https://blog.turtlecoin.lol)

### Misc

* [RPC API Error Conditions](https://github.com/kryptokrona/kryptokrona-docs/blob/master/docs/api/RPC-API-Error-Conditions/README.md) - un-exhaustive list of commons errors which TurtleCoind and turtle-service make, why they happen, and solutions.


# Running a Node on a Pi

This guide is going to walk you through the process of installing and setting up a 64 bit OS, downloading the kryptokrona ARM binaries and syncing your node on a Raspberry Pi. ARM builds just recently got fixed, so this is great news for anyone that has been wanting to run a node on one.

### Requirements

You'll need:

* a raspberry pi with a 64bit processor (Raspberry Pi 2, 3, 3B and 3B+)
  * Recommended: [Raspberry Pi 3 B](https://www.amazon.com/ELEMENT-Element14-Raspberry-Pi-Motherboard/dp/B07BDR5PDW/ref=sr_1_4?keywords=raspberry%20pi%203%20b\&qid=1548102902\&sr=8-4)
* a microSD card for the OS (keep in mind faster is better here)
* a SATA to USB adapter such at [this one](https://www.amazon.com/StarTech-com-SATA-Drive-Adapter-Cable/dp/B00HJZJI84/ref=sr_1_3?keywords=startech%20usb%20to%20sata\&qid=1548102862\&sr=8-3)
* A 2.5" SATA SSD of at least 120GB (I recommend 240gb to future proof it)
* A 64 bit OS image file (I'm using pi64 lite edition for this tutorial, which you can find [here](https://github.com/bamarni/pi64/releases))
* [Etcher](https://www.google.com/search?client=firefox-b-1-ab\&q=etcher) installed in order to flash the micro SD card easily

### Setting Up the OS

Make sure you've downloaded and installed [Etcher](https://www.google.com/search?client=firefox-b-1-ab\&q=etcher) and have the pi64.img file saved somewhere on your hard drive. Insert your microSD card into your computer, select the image file in Etcher, click flash and wait for completion. When it's finished flashing and validating, remove the microSD from your computer and insert it into the pi.

### OS Setup

Connect your ethernet cable and plug in the pi. Either install a keyboard, mouse and monitor in order to do preliminary setup or SSH into the pi from another computer (open-ssh server is installed and enabled by default on pi64.) The default user is `pi` and its password `raspberry`, it has passwordless root privileges escalation through `sudo`.

Once logged in, you might want to run `sudo pi64-config` in order to get assisted with your setup! Otherwise, set up the linux environment to your liking.

### Download kryptokrona

Once you're either ssh'd into your OS or using it directly with a mouse and keyboard, we're going to need to download the kryptokrona software. You can use these commands to do so:

`cd ~` `mkdir kryptokrona` `cd kryptokrona` `sudo apt install p7zip-full` `wget https://github.com/kryptokrona/kryptokrona/releases/download/0.0.1/kryptokrona-linux.zip` `7z xz kryptokrona-linux.zip`

and check that it's working ok with

`./kryptokrona --version`

> Note: you'll notice we're wgetting this link from discord's servers. With the ARM builds being fixed so recently, none of the official releases have been updated yet. Once a new official released is pushed this link will be updated.

### Mount your SSD

kryptokrona needs alot of space on a fast drive for the database. So plug in your SSD to one of the USB ports on the pi and we'll create a mount point for it.

First, run this command to view your available disks.

`lsblk`

Look at the options and take note of which one is your SSD. It should say something about "SCSI Device" and have the correct size as your drive. For me, it was located at /dev/sda1.

I recommend formatting the device to exFAT so that I can access it easily on both windows and linux systems. In order to mount this type of format, we'll need some additional packages...

`sudo apt install exfat-fuse exfat-utils`

Now, we can create a folder called .blockchain in the home directory and mount the SSD there.

`cd ~` `mkdir .blockchain` `sudo mount /dev/sda1 /home/pi/.blockchain`

> Note: replace /dev/sda1 with your drive location and pi with your username if you changed it.

That will temporarily mount the drive in \~/.blockchain, but we want it to be permanent. We'll need to edit the fstab file.

`sudo nano /etc/fstab`

Scroll to the bottom and add

`/dev/sda1 /home/pi/.blockchain exFAT defaults 0 2`

Save and close by pressing `Ctrl+X`, `y`

### Run kryptokrona and Keep it Running

`sudo apt install screen`

> install screen to keep the daemon running in the background

`cd ~/kryptokrona/` `./kryptokrona --data-dir '/home/pi/.blockchain' --save-config 'daemon.conf'`

> (point kryptokrona to use the mount point we made earlier as the database location, and save a config file to do so automatically in the future)

`screen -d -m ./kryptokrona -c daemon.conf`

> tell kryptokrona to run with the config file we just generated inside of a detached screen session

Now just wait to sync!

### Speeding Up Synchronization

There's a couple things you can do to speed up the blockchain sync. One is to use checkpoints: follow the directions [here](https://github.com/kryptokrona/kryptokrona-docs/blob/master/guides/wallets/Using-Checkpoints/README.md).

Alternatively, if you have another computer that already has a synced blockchain, you can copy the data in the .kryptokrona or Appdata/Roaming/kryptokrona folder onto your SSD and enjoy starting with a fully synced chain!

### Special Thanks

Thanks to LeoCuvee, thinkpol, ibmcd, zpalm, rocksteady, and anyone else who helped get these binaries functional on ARM architecture!


# Subwallets

Lets start with the obvious question.

## What are subwallets?

Subwallets are a way to use multiple distinct addresses in one wallet 'container'. Each subwallet has the same, shared private and public view keys as other wallets in the container; however, they have different private and public spend keys.

## Why would I want to use subwallets?

The first reason is simple: It allows each of your users to have their own unique address, without having to fire up a wallet-api or Kryptokrona-service instance for each.

The second reason is performance. Syncing 1000 subwallets is nearly as fast as syncing 1 wallet, and far, far faster than syncing 1000 unrelated wallets.

### Why is syncing subwallets faster?

Remember how each subwallet has the same, shared private and public view keys?

Well, when you sync a wallet, you start by downloading a range of blocks from the daemon, then, you perform a quite slow 'derivation' using your private view key, and the transaction public key. Finally, you check if the public spend key generated in this process matches one of your wallets public spend keys.

Since you are using the same private view key for each wallet, we only have to perform this expensive derivation once for each transaction, instead of 1000 times for each wallet.

We then just check if the public spend key generated matches one of the 1000 subwallets public spend key, which is very fast.

## What are the downsides of using subwallets?

Because each subwallet shares the same private view key, they also share the same *public* view key. Since the public address is the combination of the public spend key, public view key, and a checksum in base58, the first half of every address from the same subwallet container will be identical. This makes it easy to detect if a specific address belongs to your service.

Another downside is that you cannot give out mnemonic seeds to a subwallet address. A mnemonic seed is just a friendly representation of a private spend key. When you import a mnemonic, this private spend key is hashed to derive the private view key. Since subwallets must all have the same private view key, this process is not possible.

## Can I give out the private keys to subwallets?

Yes! You can safely give out the private spend key and shared private view key of each subwallet to your users.

However, there is one caveat - since every wallet has the same shared private view key, if anyone knows the address of another user of your service, they will be able to import this into a *view only wallet*. This allows them to view only *incoming* transactions of this wallet. They cannot spend the funds, or see any outgoing transactions the wallet has sent.

If you're wondering why a view wallet cannot see outgoing transactions, this is because without a private spend key you cannot generate key images. The generated key images are then included in outgoing transactions sent, and so we can detect an outgoing transaction made by us if the key images match ones we have previously generated.


# kryptokronad behind HAProxy

From polar-it on Discord

There is a lot to add to this to fill details, however this is enough for people familar to get going ;)

If you are not familar with HAProxy then check it out if you're a sysadmin/devops person it is pretty great. If you are a Containers/Kubernetes kind of person then this kind of thing is handle by the load balancers, sometimes they are HAProxy under the covers.

Combine the below with iburnmycd's [turtlecoind-ha](https://github.com/turtlecoin/turtlecoind-ha) and [turtlecoin-api-proxy](https://github.com/turtlecoin/turtlecoin-api-proxy) and you should have a farily reliable end point for daemon requests.

```
#---------------------------------------------------------------------
# main frontend which proxys to the backends
#---------------------------------------------------------------------
frontend  main *:11898

    default_backend            trtl-daemon 

#---------------------------------------------------------------------
# round robin balancing between the various backends
#---------------------------------------------------------------------
backend trtl-daemon 
    balance     roundrobin
    option httpchk GET /getinfo
    http-check expect rstring true

# Local node on port 11999
    server  app1 127.0.0.1:11999 check
    server  app2 < node host1 >:11898 check
    server  app3 < node host2 >.11898 check
    server  app4 < node host3 >:11898 check
```

***polar-it:** This actually work on* [*trtl-explorer.xhub.cloud*](https://trtl-explorer.xhub.cloud/)


# CI/CD

This project is automatically built and tested using GitHub Actions. We have two pipelines:

* **Kryptokrona Main Pipeline** - This is the pipeline that runs the code merged into our main branch.
* **Kryptokrona Pull Request Pipeline** - This is the pipeline that runs each time a pull request come in so the reviewer has some help evaluating the code status.

The Kryptokrona Main Pipeline do everything the Kryptokrona Pull Request Pipeline does in addition to generate Doxygen and building and publishing a Docker Image to the project tagged by the project name, owner, repository and short form of commit SHA value.

The purpose of publishing prepared Docker images is to make it faster and easier to deploy a Kryptokrona node/pool.


# Versioning

Kryptokrona uses [Semantic Versioning Standard 2.0.0](https://semver.org/).

Given a version number MAJOR.MINOR.PATCH, increment the:

* MAJOR version when you make incompatible API changes
* MINOR version when you add functionality in a backwards compatible manner
* PATCH version when you make backwards compatible bug fixes

Additional labels for pre-release and build metadata are available as extensions to the MAJOR.MINOR.PATCH format.


# Help and Support

For questions and support please use the channel #support in [Kryptokrona](https://discord.gg/mkRpVgDubC) Discord server. The issue tracker is for bug reports and feature discussions only.


# Kryptokrona API Docs


# Daemon JSON RPC API

The daemon JSON RPC is a HTTP server which provides JSON 2.0 RPC interface for interacting with a daemon and a block explorer.

### Installation

```
npm i kryptokrona-rpc
```

### Interacting with the API

#### API endpoint example

```
http://localhost:11898/json_rpc
```

#### Configuration and Instantiation

To start the Daemon JSON RPC API server at `http://localhost:11898/json_rpc`, run:

`kryptokrona --rpc-bind-port=11898`

To make the server accessible from another computer, use the `--rpc-bind-ip 0.0.0.0` switch.

`kryptokrona --rpc-bind-ip=0.0.0.0 --rpc-bind-port=11898`

To enable block explorer API access (like for `getblocks`, `gettransactionpool`, etc.), use the `--enable-blockexplorer` switch.

`kryptokrona --enable-blockexplorer`

The above given switches can be combined to achieve remote access with block explorer methods as shown below.

`kryptokrona --enable-blockexplorer --rpc-bind-ip=0.0.0.0 --rpc-bind-port=11898`

This would make the RPC server accessible at

`http://<your ip address>:11898/json_rpc`

and, locally at

`http://localhost:11898/json_rpc`

To make a JSON RPC request to your Daemon RPC you should use a GET request that looks like this:

`http://<service address>:<service port>/json_rpc`

| Parameter           | Description                                                                                              |
| ------------------- | -------------------------------------------------------------------------------------------------------- |
| `<service address>` | IP of Daemon RPC, if it is located on local machine it is either 127.0.0.1 or localhost                  |
| `<service port>`    | Daemon RPC port, by default it is bound to 11898 port, but it can be manually bound to any port you want |

```js
const kryptokrona = require('kryptokrona-rpc').kryptokrona

const daemon = new kryptokrona({
  host: '0.0.0.0', // ip address or hostname of the kryptokrona host
  port: 11898, // what port is the RPC server running on
  timeout: 2000, // request timeout
  ssl: false // whether we need to connect using SSL/TLS
})
```

### getblockcount

`getblockcount()` method returns the current chain height.

No Input.

**Output**

| Argument | Description          | Format |
| -------- | -------------------- | ------ |
| count    | Current chain height | int    |
| status   | Status of request    | string |

```
curl -d '{"jsonrpc":"2.0", "method":"getblockcount", "params":{}}' http://localhost:11898/json_rpc
```

```js
daemon.getBlockCount().then((blockCount) => {
  // do something
}).catch((error) => {
  // do something
})
```

**Expected Output**

```json
{
    "jsonrpc":"2.0",
    "result":{
        "count":560915,
        "status":"OK"
    }
}
```

### getblockhash

`getblockhash()` method returns block hash for a given height off by one.

**Input**

| Argument | Mandatory | Description                                                     | Format |
| -------- | --------- | --------------------------------------------------------------- | ------ |
| height   | Yes       | The height of the block whose previous hash is to be retrieved. | int    |

**Output**

| Argument | Description            | Format |
| -------- | ---------------------- | ------ |
| result   | Hash of previous block | int    |

```
curl -d '{"jsonrpc":"2.0","method":"on_getblockhash","params":[123456]}' http://localhost:11898/json_rpc
```

```js
daemon.getBlockHash({
  height: 500000
}).then((blockHash) => {
  // do something
}).catch((error) => {
  // do something
})
```

**Expected Output:**

```json
{
    "jsonrpc":"2.0",
    "result":"4bd7d..."
}
```

### getblocktemplate

`getblocktemplate(reserve_size, addr)` method returns blocktemplate with an empty "hole" for nonce.

**Input**

| Argument        | Mandatory | Description                         | Format |
| --------------- | --------- | ----------------------------------- | ------ |
| reserve\_size   | Yes       | Size of the reserve to be specified | int    |
| wallet\_address | Yes       | Valid kryptokrona wallet address    | String |

**Output**

| Argument           | Description                               | Format |
| ------------------ | ----------------------------------------- | ------ |
| blocktempate\_blob | Blocktemplate with empty "hole" for nonce | string |
| difficulty         | Difficulty of the network                 | int    |
| height             | Chain height of the network               | int    |
| reserved\_offset   | Offset reserved                           | int    |
| status             | Status of the network                     | string |

```
curl -d '{"jsonrpc":"2.0","method":"getblocktemplate","params":{"reserve_size":200,"wallet_address":"TRTLxxxx..."}}' http://localhost:11898/json_rpc
```

```js
daemon.getBlockTemplate({
  reserveSize: 200,
  walletAddress: 'TRTLv1pacKFJk9QgSmzk2LJWn14JGmTKzReFLz1RgY3K9Ryn7783RDT2TretzfYdck5GMCGzXTuwKfePWQYViNs4avKpnUbrwfQ'
}).then((blockTemplate) => {
  // do something
}).catch((error) => {
  // do something
})
```

**Expected Output:**

```json
{
	"jsonrpc": "2.0",
	"result": {
		"blocktemplate_blob": "0100de...",
		"difficulty": 65563,
		"height": 123456,
		"reserved_offset": 395,
		"status": "OK"
	}
}
```

### submitblock

`submitblock(block_blob)` method submits mined block.

**Input**

| Argument    | Mandatory | Description                   | Format |
| ----------- | --------- | ----------------------------- | ------ |
| block\_blob | Yes       | Block blob of the mined block | string |

**Output**

| Argument | Description       | Format |
| -------- | ----------------- | ------ |
| status   | Status of request | string |

```
curl -d '{"jsonrpc":"2.0","method":"submitblock","params":["0100b...."]}' https://localhost:11898/json_rpc
```

```js
daemon.submitBlock({
  blockBlob: '...'
}).then((result) => {
  // do something
}).catch((error) => {
  // do something
})
```

**Expected Output:**

```json
{
	"jsonrpc": "2.0",
	"result": {
		"status" : "OK"
	}
}
```

### getlastblockheader

`getlastblockheader` method returns the block header of the last block.

No Input

**Output**

| Argument       | Description                                                      | Format |
| -------------- | ---------------------------------------------------------------- | ------ |
| block\_size    | size of the block                                                | int    |
| depth          | height away from the known top block                             | int    |
| difficulty     | difficulty of the last block                                     | int    |
| hash           | hash of the last block                                           | string |
| height         | height of the last block                                         | int    |
| major\_version | -                                                                | int    |
| minor\_version | -                                                                | int    |
| nonce          | -                                                                | int    |
| num\_txs       | Number of transactions in the block                              | int    |
| orphan\_status | whether the last block was an orphan or not                      | bool   |
| prev\_hash     | hash of the previous block                                       | string |
| reward         | reward of the block                                              | str    |
| timestamp      | the time at which the block is occured on chain since Unix epoch | int    |
| status         | status of the request                                            | string |

```
curl -d '{"jsonrpc":"2.0","method":"getlastblockheader","params":{}}' http://localhost:11898/json_rpc
```

```js
daemon.getLastBlockHeader().then((result) => {
  // do something
}).catch((error) => {
  // do something
})
```

**Expected Output:**

```json
{
    "jsonrpc":"2.0",
    "result":{
        "block_header":{
            "block_size":86171,
            "depth":0,
            "difficulty":431119113,
            "hash":"b746b...",
            "height":561342,
            "major_version":4,
            "minor_version":0,
            "nonce":715846563,
            "num_txes":4,
            "orphan_status":false,
            "prev_hash":"b8e02...",
            "reward":2930801,
            "timestamp":1529750993
        },
        "status":"OK"
    }
}
```

### getblockheaderbyhash

`getblockheaderbyhash()` returns block header by given block hash

**Input**

| Argument | Mandatory | Description       | Format |
| -------- | --------- | ----------------- | ------ |
| hash     | Yes       | Hash of the block | string |

**Output**

| Argument       | Description                                                      | Format |
| -------------- | ---------------------------------------------------------------- | ------ |
| block\_size    | size of the block                                                | int    |
| depth          | height away from the known top block                             | int    |
| difficulty     | difficulty of the requested block                                | int    |
| hash           | hash of the requested block                                      | string |
| height         | height of the requested block                                    | int    |
| major\_version | -                                                                | int    |
| minor\_version | -                                                                | int    |
| nonce          | -                                                                | int    |
| num\_txs       | Number of transactions in the block                              | int    |
| orphan\_status | whether the requested block was an orphan or not                 | bool   |
| prev\_hash     | hash of the previous block                                       | string |
| reward         | reward of the block                                              | str    |
| timestamp      | the time at which the block is occured on chain since Unix epoch | int    |
| status         | status of the request                                            | string |

```
curl -d '{"jsonrpc":"2.0","method":"getblockheaderbyhash","params":{"hash":"30706..."}}' http://localhost:11898/json_rpc
```

```js
daemon.getBlockHeaderByHash({
  hash: '7d6db7b77232d41c19d898e81c85ecf08c4e8dfa3434f975a319f6261a695739'
}).then((result) => {
  // do something
}).catch((error) => {
  // do something
})
```

**Expected Output:**

```json
{
    "jsonrpc":"2.0",
    "result":{
        "block_header":{
            "block_size":11640,
            "depth":437898,
            "difficulty":70050782,
            "hash":"30706...",
            "height":123456,
            "major_version":3,
            "minor_version":0,
            "nonce":3177228614,
            "num_txes":3,
            "orphan_status":false,
            "prev_hash":"4bd7d...",
            "reward":2969487,
            "timestamp":1516631879
        },
    "status":"OK"
    }
}
```

### getblockheaderbyheight

`getblockheaderbyheight()` method returns block header by given block height

**Input**

| Argument | Mandatory | Description         | Format |
| -------- | --------- | ------------------- | ------ |
| height   | Yes       | Height of the block | int    |

**Output**

| Argument       | Description                                                      | Format |
| -------------- | ---------------------------------------------------------------- | ------ |
| block\_size    | size of the block                                                | int    |
| depth          | height away from the known top block                             | int    |
| difficulty     | difficulty of the requested block                                | int    |
| hash           | hash of the requested block                                      | string |
| height         | height of the requested block                                    | int    |
| major\_version | -                                                                | int    |
| minor\_version | -                                                                | int    |
| nonce          | -                                                                | int    |
| num\_txs       | Number of transactions in the block                              | int    |
| orphan\_status | whether the requested block was an orphan or not                 | bool   |
| prev\_hash     | hash of the previous block                                       | string |
| reward         | reward of the block                                              | str    |
| timestamp      | the time at which the block is occured on chain since Unix epoch | int    |
| status         | status of the request                                            | string |

```
curl -d '{"jsonrpc":"2.0","method":"getblockheaderbyheight","params":{"height":123456}}' http://localhost:11898/json_rpc
```

```js
daemon.getBlockHeaderByHeight({
  height: 502345
}).then((result) => {
  // do something
}).catch((error) => {
  // do something
})
```

**Expected Output:**

```json
{
    "jsonrpc":"2.0",
    "result":{
        "block_header":{
            "block_size":11640,
            "depth":437898,
            "difficulty":70050782,
            "hash":"30706...",
            "height":123456,
            "major_version":3,
            "minor_version":0,
            "nonce":3177228614,
            "num_txes":3,
            "orphan_status":false,
            "prev_hash":"4bd7d...",
            "reward":2969487,
            "timestamp":1516631879
        },
    "status":"OK"
    }
}
```

### getcurrencyid

`getcurrencyid()` method returns unique currency identifier.

No Input

**Output**

| Argument           | Description                | Format |
| ------------------ | -------------------------- | ------ |
| currency\_id\_blob | unique currency identifier | string |

```
curl -d '{"jsonrpc":"2.0","method":"getcurrencyid","params":{}}' http://localhost:11898/json_rpc
```

```js
daemon.getCurrencyId().then((result) => {
  // do something
}).catch((error) => {
  // do something
})
```

**Expected Output:**

```json
{
    "jsonrpc":"2.0",
    "result":{
        "currency_id_blob":"7fb97..."
    }
}
```

### getblocks

`getblocks()` method returns information on the last 30 blocks from height (inclusive)

**Input**

| Argument | Mandatory | Description                                            | Format |
| -------- | --------- | ------------------------------------------------------ | ------ |
| height   | Yes       | height of the last block to be included in the result. | int    |

**Output**

| Argument |              | Description           | Format |
| -------- | ------------ | --------------------- | ------ |
| status   |              | status of the request | string |
| blocks   | **Array of** |                       |        |

```
     | cumul_size   | size of the block                     | int
     | difficulty   | difficulty of the block               | int
     | hash         | hash of the block                     | string
     | height       | height of the block                   | int
     | timestamp    | the time at which the block is occured on the chain since Unix epoch | int
     | tx_count     | number of transactions in the block   | int
```

```
curl -d '{"jsonrpc":"2.0","method":"f_blocks_list_json","params":{"height":500000}}' http://localhost:11898/json_rpc
```

```js
daemon.getBlocks({
  height: 500000
}).then((blocks) => {
  // do something
}).catch((error) => {
  // do something
})
```

**Expected Output:**

```json
{
    "jsonrpc": "2.0",
    "result": {
        "blocks":[
            {
                "cumul_size": 22041,
                "difficulty": 285124963,
                "hash": "62f00...",
                "height": 500000,
                "timestamp": 1527834137,
                "tx_count": 4
            }
        ],
        "status": "OK"
    }
}
```

### getblock

`getblock()` method returns information on a single block

**Input**

| Argument | Mandatory | Description       | Format |
| -------- | --------- | ----------------- | ------ |
| hash     | Yes       | hash of the block | string |

**Output**

| Argument                     | Description                                                         | Format |
| ---------------------------- | ------------------------------------------------------------------- | ------ |
| alreadyGeneratedCoins        | total number of coins generated in the network upto that block      | string |
| alreadyGeneratedTransactions | total number of transactions present in the network upto that block | int    |
| baseReward                   | calculated reward                                                   | int    |
| block\_size                  | size of the block                                                   | int    |
| depth                        | height away from the known top block                                | int    |
| difficulty                   | difficulty of the requested block                                   | int    |
| effectiveSizeMedian          | fixed constant for max size of block                                | int    |
| hash                         | hash of the requested block                                         | string |
| height                       | height of the requested block                                       | int    |
| major\_version               | -                                                                   | int    |
| minor\_version               | -                                                                   | int    |
| nonce                        | -                                                                   | int    |
| orphan\_status               | whether the requested block was an orphan or not                    | bool   |
| penalty                      | penalty in block reward determined for deviation                    | float  |
| prev\_hash                   | hash of the previous block                                          | string |
| reward                       | total reward of the block after removing penalty                    | str    |
| sizeMedian                   | calculated median size from last 100 blocks                         | int    |
| timestamp                    | the time at which the block is occured on chain since Unix epoch    | int    |
| totalFeeAmount               | total fees for the transactions in the block                        | int    |
| transactions                 | Array of transactions in the block                                  | array  |
| transactionsCumulativeSize   | total sum of size of all transactions in the block                  | int    |
| status                       | status of the request                                               | string |

Transaction Attributes:

| Argument    | Description                      | Format |
| ----------- | -------------------------------- | ------ |
| amount\_out | output amount of the transaction | int    |
| fee         | fees for the transaction         | int    |
| hash        | hash of the transaction          | string |
| size        | size of the transaction          | int    |

```
curl -d '{"jsonrpc":"2.0","method":"f_block_json","params":{"hash":"980ff..."}}' http://localhost:11898/json_rpc
```

```js
daemon.getBlock({
  hash: 'f11580d74134ac34673c74f8da458080aacbe1eccea05b197e9d10bde05139f5'
}).then((block) => {
  // do something
}).catch((error) => {
  // do something
})
```

**Expected Output:**

```json
{
    "jsonrpc":"2.0",
    "result":{
        "block":{
            "alreadyGeneratedCoins":"1659188157030",
            "alreadyGeneratedTransactions":1097221,
            "baseReward":2930784,
            "blockSize":384,
            "depth":1,
            "difficulty":264289473,
            "effectiveSizeMedian":100000,
            "hash":"980ff...",
            "height":561537,
            "major_version":4,
            "minor_version":0,
            "nonce":60779,
            "orphan_status":false,
            "penalty":0.0,
            "prev_hash":"c37f8...",
            "reward":2930784,
            "sizeMedian":265,
            "timestamp":1529757254,
            "totalFeeAmount":0,
            "transactions":[
                {
                    "amount_out":2930784,
                    "fee":0,
                    "hash":"c0a2d...",
                    "size":265
                }
            ],
            "transactionsCumulativeSize":265
        },
        "status":"OK"
    }
}
```

### gettransaction

`gettransaction()` method returns information on single transaction.

**Input**

| Argument | Mandatory | Description             | Format |
| -------- | --------- | ----------------------- | ------ |
| hash     | Yes       | hash of the transaction | string |

**Output**

| Argument  | Description                                          | Format      |
| --------- | ---------------------------------------------------- | ----------- |
| block     | details of the block in which transaction is present | json object |
| status    | status of the request                                | string      |
| tx        | sub-transactions in the transaction                  | json object |
| txDetails | details of the transaction                           | json object |

Block attributes:

| Argument    | Description                                                      | Format |
| ----------- | ---------------------------------------------------------------- | ------ |
| cumul\_size | size of the block                                                | int    |
| difficulty  | difficulty of the block                                          | int    |
| hash        | hash of the block                                                | string |
| height      | height of the block                                              | int    |
| timestamp   | the time at which the block is occured on chain since Unix epoch | int    |
| tx\_count   | number of transactions in the block                              | int    |

Transaction Details attributes:

| Argument    | Description                             | Format |
| ----------- | --------------------------------------- | ------ |
| amount\_out | total amount present in the transaction | int    |
| fee         | total fees of the transaction           | int    |
| hash        | hash of the transaction                 | string |
| mixin       | mixin of the transaction                | int    |
| paymentId   | payment Id of the transaction           | string |
| size        | total size of the transaction           | int    |

Transaction attributes:

| Argument     | Description                                           | Format |
| ------------ | ----------------------------------------------------- | ------ |
| extra        | Transaction extra which can be any information in hex | string |
| unlock\_time | delay in unlocking the amount                         | int    |
| version      | -                                                     | int    |
| vin          | array of input transactions                           | array  |
| vout         | array of output transactions                          | array  |

```
curl -d '{"jsonrpc":"2.0","method":"f_transaction_json","params":{"hash":"702ad..."}}' http://localhost:11898/json_rpc
```

```js
daemon.getTransaction({
  hash: '702ad5bd04b9eff14b080d508f69a320da1909e989d6c163c18f80ae7a5ab832'
}).then((transaction) => {
  // do something
}).catch((error) => {
  // do something
})
```

**Expected Output:**

```json
{
    "jsonrpc":"2.0",
    "result":{
        "block":{
            "cumul_size":22041,
            "difficulty":106780143,
            "hash":"62f00...",
            "height":500000,
            "timestamp":1527834137,
            "tx_count":4
        },
        "status":"OK",
        "tx":{
            "extra":"019e4...",
            "unlock_time":500040,
            "version":1,
            "vin":[
                {
                    "type":"ff",
                    "value":{
                        "height":500000
                    }
                }
            ],
            "vout":[
                {
                    "amount":80,
                    "target":{
                        "data":{
                            "key":"5ce69..."
                        },
                        "type":"02"
                    }
                }
            ]
        },
        "txDetails":{
            "amount_out":2936280,
            "fee":0,
            "hash":"702ad...",
            "mixin":0,
            "paymentId":"",
            "size":266
        }
    }
}
```

### gettransactionpool

`gettransactionpool()` returns the list of transaction hashes present in mempool

No Input

**Output**

| Argument     | Description                      | Format |
| ------------ | -------------------------------- | ------ |
| status       | status of the request            | string |
| transactions | array of transactions in mempool | array  |

Transactions attributes:

| Argument    | Description                      | Format |
| ----------- | -------------------------------- | ------ |
| amount\_out | output amount of the transaction | int    |
| fee         | fees for the transaction         | int    |
| hash        | hash of the transaction          | string |
| size        | size of the transaction          | int    |

```
curl -d '{"jsonrpc":"2.0","method":"f_on_transactions_pool_json","params":{}}' http://localhost:11898/json_rpc
```

```js
daemon.getTransactionPool().then((transactions) => {
  // do something
}).catch((error) => {
  // do something
})
```

**Expected Output:**

```json
{
    "jsonrpc":"2.0",
    "result":{
        "status":"OK",
        "transactions":[
            {
                "amount_out":8990,
                "fee":10,
                "hash":"a5e88...",
                "size":541
            }
        ]
    }
}
```

### License

[![Creative Commons License](broken://files/EU6IlMk8og1YjvlfUR2k)](https://creativecommons.org/licenses/by-sa/3.0/)

The content in this document was originally written by the [Bytecoin (BCN) Developers](https://bytecoin.org/). It is licensed under the [CC BY SA 3.0 license](https://creativecommons.org/licenses/by-sa/3.0/). The source material can be found at the [Bytecoin Wiki](https://github.com/bcndev/bytecoin).

Also of note, kryptokrona developers have altered and adapted the content to suit our implementation of the API. This was done independently of the Bytecoin development team. They neither endorse or acknowledge our changes. Feel free to adopt or change our content as per the [CC BY SA 3.0 license](https://creativecommons.org/licenses/by-sa/3.0/) requirements.


# kryptokrona-wallet-backend-js

Documentation for the JavasScript (actually TypeScript) wallet backend used for Node apps.

Read the documentation for kryptokrona-wallet-backend-js [here](https://kryptokrona.github.io/kryptokrona-wallet-backend-js/docs/).


# kryptokrona-service

The kryptokrona RPC Wallet is a HTTP server which provides JSON 2.0 RPC interface for kryptokrona payment operations and address management.

Currently we support the following official client bindings:

* [PHP](https://github.com/kryptokrona/kryptokrona-rpc-php)
* [Python](https://github.com/kryptokrona/kryptokrona-rpc-python)
* [Go](https://github.com/kryptokrona/kryptokrona-rpc-go)

### Note: Eventually, kryptokrona-service will be deprecated. It is suggested to use [wallet-api](https://kryptokrona.github.io/wallet-api-docs) for new applications.

### Installation

```
composer require kryptokrona/kryptokrona-rpc-php
```

```
pip3 install kryptokrona
```

```
go get github.com/kryptokrona/kryptokrona-rpc-go
```

### Interacting with the API

#### API endpoint example

```
http://localhost:8070/json_rpc
```

#### Configuration and instantiation

To make a JSON RPC request to your kryptokrona RPC Wallet you should use a GET request that looks like this:

`http://<service address>:<service port>/json_rpc`

| Parameter           | Description                                                                                                         |
| ------------------- | ------------------------------------------------------------------------------------------------------------------- |
| `<service address>` | IP of kryptokrona RPC Wallet, if RPC Wallet is located on local machine it is either 127.0.0.1 or localhost         |
| `<service port>`    | kryptokrona RPC Wallet port, by default it is bound to 8070 port, but it can be manually bound to any port you want |

```
<?php
use kryptokrona\kryptokronaService;

$config = [
    'rpcHost'     => 'http://localhost',
    'rpcPort'     => 8070,
    'rpcPassword' => 'passw0rd',
];

$kryptokronaService = new kryptokronaService($config);
```

```
from kryptokrona import Walletd

rpc_host = 'localhost'
rpc_port = 8070
rpc_password = 'passw0rd'

walletd = Walletd(rpc_password, rpc_host, rpc_port)
```

```
import (
  "fmt"
  trpc "github.com/kryptokrona/kryptokrona-rpc-go"
)

rpcHost := "localhost"
rpcPort := 8070
rpcPassword := "passw0rd"

service := trpc.Walletd{
  URL: rpcHost,
  Port: rpcPort,
  RPCPassword: rpcPassword}
```

### reset

`reset()` method allows you to re-sync your wallet.

**Input**

| Argument   | Mandatory | Description                                                                                      | Format |
| ---------- | --------- | ------------------------------------------------------------------------------------------------ | ------ |
| scanHeight | No        | The height to begin scanning for transactions at. This can greatly speed up wallet syncing time. | int    |

```
curl -d '{"jsonrpc":"2.0","id":1,"password":"passw0rd","method":"reset","params":{"scanHeight":100000}}' http://localhost:8070/json_rpc
```

```
<?php
$scanHeight = 100000;
$response = $kryptokronaService->reset($scanHeight);
echo $response;
```

```
scan_height = 100000
response = walletd.reset(scan_height)
print(response)
```

```
scanHeight := 0 // starting height to scan
response, err := service.Reset(scanHeight)
if err != nil {
  fmt.Println(err)
} else {
  fmt.Println(response)
}
```

**Expected Output:**

```
{
  "id":1,
  "jsonrpc":"2.0",
  "result":{}
}
```

No output in case of success.

> Note: If the `viewSecretKey` argument is not provided, the `reset()` method resets the wallet and re-syncs it. If the `viewSecretKey` argument is provided, the `reset()` method substitutes the existing wallet with a new one with the specified key.

### save

`save()` method allows you to save your wallet by request.

No input. No output in case of success.

```
curl -d '{"jsonrpc":"2.0","id":1,"password":"passw0rd","method":"save","params":{}}' http://localhost:8070/json_rpc
```

```
<?php
$response = $kryptokronaService->save();
echo $response;
```

```
response = walletd.save()
print(response)
```

```
response, err := service.Save()
if err != nil {
  fmt.Println(err)
} else {
  fmt.Println(response)
}
```

**Expected Output:**

```
{
  "id":1,
  "jsonrpc":"2.0",
  "result":{}
}
```

### getViewKey

`getViewKey()` method returns your view key.

No input.

**Output**

| Argument      | Description      | Format |
| ------------- | ---------------- | ------ |
| viewSecretKey | Private view key | string |

```
curl -d '{"jsonrpc":"2.0","id":1,"password":"passw0rd","method":"getViewKey","params":{}}' http://localhost:8070/json_rpc
```

```
<?php
$response = $kryptokronaService->getViewKey();
echo $response;
```

```
response = walletd.get_view_key()
print(response)
```

```
response, err := service.GetViewKey()
if err != nil {
  fmt.Println(err)
} else {
  fmt.Println(response)
}
```

**Expected Output:**

```
{
  "id":1,
  "jsonrpc":"2.0",
  "result":{
    "viewSecretKey":"xxxxx..."
  }
}
```

### getSpendKeys

`getSpendKeys()` method returns your spend keys.

**Input**

| Argument | Mandatory | Description                                 | Format |
| -------- | --------- | ------------------------------------------- | ------ |
| address  | Yes       | Valid address that exists in this container | string |

**Output**

| Argument       | Description       | Format |
| -------------- | ----------------- | ------ |
| spendSecretKey | Private spend key | string |
| spendPublicKey | Public spend key  | string |

```
curl -d '{"jsonrpc":"2.0","id":1,"password":"passw0rd","method":"getSpendKeys","params":{"address":"SEKRxxxx..."}}' http://localhost:8070/json_rpc
```

```
<?php
$address = 'SEKRxxxx...';
$response = $kryptokronaService->getSpendKeys($address);
echo $response;
```

```
address = 'SEKRxxxx...'
response = walletd.get_spend_keys(address)
print(response)
```

```
address := "SEKRxxxx..."
response, err := service.GetSpendKeys(address)
if err != nil {
  fmt.Println(err)
} else {
  fmt.Println(response)
}
```

**Expected Output:**

```
{
  "id":1,
  "jsonrpc":"2.0",
  "result":{
    "spendSecretKey":"xxxxx...",
    "spendPublicKey":"xxxxx..."
  }
}
```

### getMnemonicSeed

`getMnemonicSeed()` method returns the mnemonic seed for the given *deterministic* address. A mnemonic seed is a list of words which can be used to recover a wallet.

**Input**

| Argument | Mandatory | Description                                               | Format |
| -------- | --------- | --------------------------------------------------------- | ------ |
| address  | Yes       | Valid deterministic address that exists in this container | string |

**Output**

| Argument     | Description   | Format |
| ------------ | ------------- | ------ |
| mnemonicSeed | Mnemonic seed | string |

> **Note:** The first wallet address that is generated when the container is created is the deterministic address. Only one wallet from a multi-wallet container can be deterministic. If a non-deterministic address is given, the RPC response will be an error with the message: "Keys not deterministic."

```
curl -d '{"jsonrpc":"2.0","id":1,"password":"passw0rd","method":"getMnemonicSeed","params":{"address":"SEKRxxxx..."}}' http://localhost:8070/json_rpc
```

```
<?php
$address = 'SEKRxxxx...';
$response = $kryptokronaService->getMnemonicSeed($address);
echo $response;
```

```
address = 'SEKRxxxx...'
response = walletd.get_mnemonic_seed(address)
print(response)
```

```
address := "SEKRxxxx..."
response, err := service.GetMnemonicSeed(address)
if err != nil {
  fmt.Println(err)
} else {
  fmt.Println(response)
}
```

**Expected Output:**

```
{
  "id":1,
  "jsonrpc":"2.0",
  "result":{
    "mnemonicSeed":"turtles are cool..."
  }
}
```

### getStatus

`getStatus()` method returns information about the current RPC Wallet state: block count, known block count, last block hash and peer count.

No input.

**Output**

| Argument        | Description                                                                | Format |
| --------------- | -------------------------------------------------------------------------- | ------ |
| blockCount      | Node's known number of blocks                                              | int    |
| knownBlockCount | Maximum known number of blocks of all seeds that are connected to the node | int    |
| lastBlockHash   | Hash of the last known block                                               | string |
| peerCount       | Connected peers number                                                     | int    |

```
curl -d '{"jsonrpc":"2.0","id":1,"password":"passw0rd","method":"getStatus","params":{}}' http://localhost:8070/json_rpc
```

```
<?php
$response = $kryptokronaService->getStatus();
echo $response;
```

```
response = walletd.get_status()
print(response)
```

```
response, err := service.GetStatus()
if err != nil {
  fmt.Println(err)
} else {
  fmt.Println(response)
}
```

**Expected Output:**

```
{
  "id":1,
  "jsonrpc":"2.0",
  "result":{
    "blockCount":455956,
    "knownBlockCount":455955,
    "lastBlockHash":"8d6f8...",
    "peerCount":8
  }
}
```

### getAddresses

`getAddresses()` method returns an array of your RPC Wallet's addresses.

No input.

**Output**

| Argument  | Description                                       | Format |
| --------- | ------------------------------------------------- | ------ |
| addresses | Array of strings, where each string is an address | array  |

```
curl -d '{"jsonrpc":"2.0","id":1,"password":"passw0rd","method":"getAddresses","params":{}}' http://localhost:8070/json_rpc
```

```
<?php
$response = $kryptokronaService->getAddresses();
echo $response;
```

```
response = walletd.get_addresses()
print(response)
```

```
response, err := service.GetAddresses()
if err != nil {
  fmt.Println(err)
} else {
  fmt.Println(response)
}
```

**Expected Output:**

```
{
  "id":1,
  "jsonrpc":"2.0",
  "result":{
    "addresses":[
      "SEKRxxxx...",
      "SEKRxxxx..."
    ]
  }
}
```

### createAddress

`createAddress()` method creates an additional address in your wallet.

**Input**

| Argument       | Mandatory | Description                                                                                                                                                                                | Format |
| -------------- | --------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ | ------ |
| spendSecretKey | No        | Private spend key. If `spendSecretKey` was specified, RPC Wallet creates spend address                                                                                                     | string |
| spendPublicKey | No        | Public spend key. If `spendPublicKey` was specified, RPC Wallet creates view address                                                                                                       | string |
| newAddress     | No        | Is this a new address being created? If so, blocks before the creation timestamp will not be scanned. Defaults to true if neither keys are given, as it is guaranteed to be a new address. | bool   |
| scanHeight     | No        | The height to begin scanning for transactions at. Only applies if a public/secret key is supplied. This can greatly speed up wallet syncing time.                                          | int    |

```
curl -d '{"jsonrpc":"2.0","id":1,"password":"passw0rd","method":"createAddress","params":{}}' http://localhost:8070/json_rpc
```

```
<?php
$spendSecretKey = null;
$spendPublicKey = null;
$response = $kryptokronaService->createAddress($spendSecretKey, $spendPublicKey);
echo $response;
```

```
spend_secret_key = ''
spend_public_key = ''
response = walletd.create_address(spend_secret_key, spend_public_key)
print(response)
```

```
spendSecretKey := ""
spendPublicKey := ""
scanHeight := 850000
newAddress := true
response, err := service.CreateAddress(spendSecretKey, spendPublicKey, scanHeight, newAddress)
if err != nil {
  fmt.Println(err)
} else {
  fmt.Println(response)
}
```

**Expected Output:**

```
{
  "id":1,
  "jsonrpc":"2.0",
  "result":{
    "address":"SEKRxxxx..."
  }
}
```

### deleteAddress

`deleteAddress()` method deletes a specified address.

**Input**

| Argument | Mandatory | Description              | Format |
| -------- | --------- | ------------------------ | ------ |
| address  | Yes       | An address to be deleted | string |

**Output**

In case of success returns an empty JSON object.

```
curl -d '{"jsonrpc":"2.0","id":1,"password":"passw0rd","method":"deleteAddress","params":{"address":"SEKRxxxx..."}}' http://localhost:8070/json_rpc
```

```
<?php
$address = 'SEKRxxxx...';
$response = $kryptokronaService->deleteAddress($address);
echo $response;
```

```
address = 'SEKRxxxx...'
response = walletd.delete_address(address)

# If the delete was successful, response will be True
print(response)
```

```
address := "SEKRxxxx..."
response, err := service.DeleteAddress(address)
if err != nil {
  fmt.Println(err)
} else {
  fmt.Println(response)
}
```

**Expected Output:**

```
{
  "id":1,
  "jsonrpc":"2.0",
  "result":{}
}
```

### getBalance

`getBalance()` method returns a balance for a specified address.

**Input**

| Argument | Mandatory | Description                                 | Format |
| -------- | --------- | ------------------------------------------- | ------ |
| address  | No        | Valid address that exists in this container | string |

**Output**

| Argument         | Description                                          | Format |
| ---------------- | ---------------------------------------------------- | ------ |
| availableBalance | Available balance of the specified address in shells | int    |
| lockedAmount     | Locked amount of the specified address in shells     | int    |

> **Note:** If an address is not specified, `getBalance()` returns a cumulative balance of all RPC Wallet's addresses.

> **Note:** Balances are expressed in shells, so a balance of 10000 is equal to 100.00 SEKR

```
curl -d '{"jsonrpc":"2.0","id":1,"password":"passw0rd","method":"getBalance","params":{"address":"SEKRxxxx..."}}' http://localhost:8070/json_rpc
```

```
<?php
$address = 'SEKRxxxx...';
$response = $kryptokronaService->getBalance($address);
echo $response;
```

```
address = 'SEKRxxxx...'
response = walletd.get_balance(address)
print(response)
```

```
address := "SEKRxxxx..."
response, err := service.GetBalance(address)
if err != nil {
  fmt.Println(err)
} else {
  fmt.Println(response)
}
```

**Expected Output:**

```
{
  "id":1,
  "jsonrpc":"2.0",
  "result":{
    "availableBalance":10000,
    "lockedAmount":0
  }
}
```

### getBlockHashes

`getBlockHashes()` method returns an array of block hashes for a specified block range.

**Input**

| Argument        | Mandatory | Description                 | Format |
| --------------- | --------- | --------------------------- | ------ |
| firstBlockIndex | Yes       | Starting height             | int    |
| blockCount      | Yes       | Number of blocks to process | int    |

**Output**

| Argument    | Description                                          | Format |
| ----------- | ---------------------------------------------------- | ------ |
| blockHashes | Array of strings, where each element is a block hash | array  |

```
curl -d '{"jsonrpc":"2.0","id":1,"password":"passw0rd","method":"getBlockHashes","params":{"firstBlockIndex":0,"blockCount":3}}' http://localhost:8070/json_rpc
```

```
<?php
$firstBlockIndex = 0;
$blockCount = 3;
$response = $kryptokronaService->getBlockHashes($firstBlockIndex, $blockCount);
echo $response;
```

```
first_block_index = 0
block_count = 3
response = walletd.get_block_hashes(first_block_index, block_count)
print(response)
```

```
firstBlockIndex := 0
blockCount := 3
response, err := service.GetBlockHashes(firstBlockIndex, blockCount)
if err != nil {
  fmt.Println(err)
} else {
  fmt.Println(response)
}
```

**Expected Output:**

```
{
  "id":1,
  "jsonrpc":"2.0",
  "result":{
    "blockHashes":[
      "7fb97...",
      "8c973...",
      "2ef06..."
    ]
  }
}
```

### getTransactionHashes

`getTransactionHashes()` method returns an array of block and transaction hashes. A transaction consists of transfers. A transfer is an amount-address pair. There could be several transfers in a single transaction.

**Input**

| Argument        | Mandatory                                                              | Description                                        | Format |
| --------------- | ---------------------------------------------------------------------- | -------------------------------------------------- | ------ |
| addresses       | No                                                                     | Array of strings, where each string is an address  | array  |
| blockHash       | Only one of these parameters (blockHash or firstBlockIndex) is allowed | Hash of the starting block                         | string |
| firstBlockIndex | Only one of these parameters (blockHash or firstBlockIndex) is allowed | Starting height                                    | int    |
| blockCount      | Yes                                                                    | Number of blocks to return transaction hashes from | int    |
| paymentId       | No                                                                     | Valid payment ID (64char hex string)               | string |

* If `paymentId` parameter is set, `getTransactionHashes()` method returns transaction hashes of transactions that contain specified payment ID in the given block range.
* If `addresses` parameter is set, `getTransactionHashes()` method returns transaction hashes of transactions that contain transfer from at least one of specified addresses.
* If both above mentioned parameters are set, `getTransactionHashes()` method returns transaction hashes of transactions that contain both specified payment ID and transfer from at least one of specified addresses.

**Output**

| Argument | Description  |   |   |
| -------- | ------------ | - | - |
| items    | **Array of** |   |   |

```
	   | **Attribute**            	                         | **Description**                                              | **Format** |                                        
       | blockHash                                           | Hash of the block which contains transaction hashes          | string     |
       | transactionHashes                                   | Array of strings, where each string is a transaction hash    | array      |
```

```
curl -d '{"jsonrpc":"2.0","id":1,"password":"passw0rd","method":"getTransactionHashes","params":{"firstBlockIndex":400000,"blockCount":100000}}' http://localhost:8070/json_rpc
```

```
<?php
$blockCount = 100000;
$firstBlockIndex = 400000;
$blockHash = null;
$addresses = null;
$paymentId = null;

$response = $kryptokronaService->getTransactionHashes(
    $blockCount, $firstBlockIndex, $blockHash, $addresses, $paymentId
);

echo $response;
```

```
block_count = 100000
block_hash = '6c285...'
addresses = []
payment_id = ''

response = walletd.get_transaction_hashes(addresses, block_hash, block_count, payment_id)
print(response)
```

```
addresses := []string{"SEKRxxxx..."}
blockHash := ""
firstBlockIndex := 0
blockCount := 3
paymentID := ""
response, err := service.GetTransactionHashes(addresses, blockHash, firstBlockIndex, blockCount, paymentID)
if err != nil {
  fmt.Println(err)
} else {
  fmt.Println(response)
}
```

**Expected Output:**

```
{
  "id":1,
  "jsonrpc":"2.0",
  "result":{
    "items":[
      {
        "blockHash":"f0d8c...",
        "transactionHashes":["529ea..."]
      },
      {
        "blockHash":"4a1ae...",
        "transactionHashes":["2e709..."]
      }
    ]
  }
}
```

### getTransactions

`getTransactions()` method returns an array of block and transaction hashes. A transaction consists of transfers. A transfer is an amount-address pair. There could be several transfers in a single transaction.

**Input**

| Argument        | Mandatory                                                                   | Description                                        | Format |
| --------------- | --------------------------------------------------------------------------- | -------------------------------------------------- | ------ |
| addresses       | No                                                                          | Array of strings, where each string is an address  | array  |
| blockHash       | Only one of these parameters (`blockHash` or `firstBlockIndex`) is allowed. | Hash of the starting block                         | string |
| firstBlockIndex | Only one of these parameters (`blockHash` or `firstBlockIndex`) is allowed. | Starting height >0 (1,2,3...)                      | int    |
| blockCount      | Yes                                                                         | Number of blocks to return transaction hashes from | int    |
| paymentId       | No                                                                          | Valid payment ID (64char hex string)               | string |

* If `paymentId` parameter is set, `getTransactions()` method returns transactions that contain specified payment ID in the given block range.
* If `addresses` parameter is set, `getTransactions()` method returns transactions that contain transfer from at least one of specified addresses.
* If both above mentioned parameters are set, `getTransactions()` method returns transactions that contain both specified payment ID and transfer from at least one of specified addresses.

**Output**

| Argument |              | Description | Format |
| -------- | ------------ | ----------- | ------ |
| items    | **Array of** |             |        |

```
	   | block_hash                   | hash of the block which contains a transaction    | string
	   | transactions                 | see below                                         | array
```

Transaction attributes:

| Argument        | Description                                                                | Format  |
| --------------- | -------------------------------------------------------------------------- | ------- |
| transactionHash | Hash of the transaction                                                    | string  |
| blockIndex      | Number of the block that contains a transaction                            | int     |
| timestamp       | Timestamp of the transaction                                               | int     |
| isBase          | Shows if the transaction is a CoinBase transaction or not                  | boolean |
| unlockTime      | Height of the block when transaction is going to be available for spending | int     |
| amount          | Amount of the transaction                                                  | int     |
| fee             | Transaction fee                                                            | int     |
| extra           | Hash of the transaction                                                    | string  |
| paymentId       | Payment ID of the transaction (optional) (64char hex string)               | string  |
| transfers       | Array of address (string), amount (int)                                    | array   |

```
curl -d '{"jsonrpc":"2.0","id":1,"password":"passw0rd","method":"getTransactions","params":{"firstBlockIndex":400000,"blockCount":100000}}' http://localhost:8070/json_rpc
```

```
<?php
$blockCount = 100000;
$firstBlockIndex = 400000;
$blockHash = null;
$addresses = null;
$paymentId = null;

$response = $kryptokronaService->getTransactions(
    $blockCount, $firstBlockIndex, $blockHash, $addresses, $paymentId
);

echo $response;
```

```
block_count = 100000
block_hash = '6c285...'
addresses = []
payment_id = ''

response = walletd.get_transactions(addresses, block_hash, block_count, payment_id)
print(response)
```

```
addresses := []string{"SEKRxxxx..."}
blockHash := ""
firstBlockIndex := 0
blockCount := 3
paymentID := ""
response, err := service.GetTransactions(addresses, blockHash, firstBlockIndex, blockCount, paymentID)
if err != nil {
  fmt.Println(err)
} else {
  fmt.Println(response)
}
```

**Expected Output:**

```
{
  "id":1,
  "jsonrpc":"2.0",
  "result":{
    "items":[
      {
        "blockHash":"f0d8c...",
        "transactions":[
          {
            "amount":10000,
            "blockIndex":456018,
            "extra":"01bd0...",
            "fee":10,
            "isBase":false,
            "paymentId":"b6fc6...",
            "state":0,
            "timestamp":1526458339,
            "transactionHash":"529ea...",
            "transfers":[
              {"address":"SEKRxxxx...","amount":10000,"type":0},
              {"address":"","amount":-100000,"type":0},
              {"address":"","amount":89990,"type":0}
            ],
            "unlockTime":0
          }
        ]
      },
      {
        "blockHash":"4a1ae...",
        "transactions":[
          {
            "amount":5000,
            "blockIndex":456076,
            "extra":"018c1...",
            "fee":10,
            "isBase":false,
            "paymentId":"55255...",
            "state":0,
            "timestamp":1526460243,
            "transactionHash":"2e709...",
            "transfers":[
              {"address":"SEKRxxxx...","amount":5000,"type":0},
              {"address":"","amount":-8000,"type":0},
              {"address":"","amount":2990,"type":0}
            ],
            "unlockTime":0
          }
        ]
      }
    ]
  }
}
```

### getUnconfirmedTransactionHashes

`getUnconfirmedTransactionHashes()` method returns information about the current unconfirmed transaction pool or for a specified addresses.

Transaction consists of transfers. Transfer is an amount-address pair. There could be several transfers in a single transaction.

**Input**

| Argument  | Mandatory | Description                                            | Format |
| --------- | --------- | ------------------------------------------------------ | ------ |
| addresses | No        | Array of strings, where each string is a valid address | array  |

> **Note:** If addresses parameter is set, transactions that contain transfer from at least one of specified addresses are returned.

**Output**

| Argument          | Description                                                                 | Format |
| ----------------- | --------------------------------------------------------------------------- | ------ |
| transactionHashes | Array of strings, where each string is a hash of an unconfirmed transaction | array  |

```
curl -d '{"jsonrpc":"2.0","id":1,"password":"passw0rd","method":"getUnconfirmedTransactionHashes","params":{}}' http://localhost:8070/json_rpc
```

```
<?php
$addresses = null;
$response = $kryptokronaService->getUnconfirmedTransactionHashes($addresses);
echo $response;
```

```
addresses = []
response = walletd.get_unconfirmed_transaction_hashes(addresses)
print(response)
```

```
addresses := []string{"SEKRxxxx..."}
response, err := service.GetUnconfirmedTransactionHashes(addresses)
if err != nil {
		fmt.Println(err)
} else {
  fmt.Println(response)
}
```

**Expected Output:**

```
{
  "id":1,
  "jsonrpc":"2.0",
  "result":{
    "transactionHashes":[
      "55a23..."
    ]
  }
}
```

### getTransaction

`getTransaction()` method returns information about a particular transaction.

Transaction consists of transfers. Transfer is an amount-address pair. There could be several transfers in a single transaction.

**Input**

| Argument        | Mandatory | Description                       | Format |
| --------------- | --------- | --------------------------------- | ------ |
| transactionHash | Yes       | Hash of the requested transaction | string |

**Output**

| Argument    | Description |
| ----------- | ----------- |
| transaction | see below   |

Transaction attributes:

| Argument        | Description                                                                | Format  |
| --------------- | -------------------------------------------------------------------------- | ------- |
| transactionHash | Hash of the transaction                                                    | string  |
| blockIndex      | Number of the block that contains a transaction                            | int     |
| timestamp       | Timestamp of the transaction                                               | int     |
| isBase          | Shows if the transaction is a CoinBase transaction or not                  | boolean |
| unlockTime      | Height of the block when transaction is going to be available for spending | int     |
| amount          | Amount of the transaction                                                  | int     |
| fee             | Transaction fee                                                            | int     |
| extra           | Hash of the transaction                                                    | string  |
| paymentId       | Payment ID of the transaction (optional) (64char hex string)               | string  |
| transfers       | Array of addresses (string), amount (int)                                  | array   |

```
curl -d '{"jsonrpc":"2.0","id":1,"password":"passw0rd","method":"getTransaction","params":{"transactionHash":"55a23..."}}' http://localhost:8070/json_rpc
```

```
<?php
$transactionHash = '55a23...';
$response = $kryptokronaService->getTransaction($transactionHash);
echo $response;
```

```
transaction_hash = '55a23...'
response = walletd.get_transaction(transaction_hash)
print(response)
```

```
transactionHash := "55a23..."
response, err := service.GetTransaction(transactionHash)
if err != nil {
	fmt.Println(err)
} else {
  fmt.Println(response)
}
```

**Expected Output:**

```
{
  "id":1,
  "jsonrpc":"2.0",
  "result":{
    "transaction":{
      "amount":5000,
      "blockIndex":456635,
      "extra":"0134b...",
      "fee":10,
      "isBase":false,
      "paymentId":"ac9c5...",
      "state":0,
      "timestamp":1526477499,
      "transactionHash":"55a23...",
      "transfers":[
        {"address":"SEKRxxxx...","amount":5000,"type":0},
        {"address":"","amount":-10000,"type":0},
        {"address":"","amount":4990,"type":0}
      ],
      "unlockTime":0
    }
  }
}
```

### sendTransaction

`sendTransaction()` method allows you to send transaction(s) to one or several addresses. Also, it allows you to use a payment ID for a transaction to a single address.

**Input**

| Argument      | Mandatory | Description                                                                                                                                           | Format |
| ------------- | --------- | ----------------------------------------------------------------------------------------------------------------------------------------------------- | ------ |
| addresses     | No        | Array of strings, where each string is an address to take the funds from                                                                              | array  |
| transfers     | Yes       | Array of objects, address: (string address), amount: (int amount)                                                                                     | array  |
| fee           | No        | Transaction fee. Should be given in atomic units. Leave blank to use the minimum fee possible.                                                        | int    |
| feePerByte    | No        | Fee to pay per byte of the transaction. Should be given in atomic units. If given, should be greater than 1.953125, the minimum network fee per byte. | float  |
| unlockTime    | No        | The block height at which the transaction will be unlocked for spending.                                                                              | int    |
| anonymity     | Yes       | Privacy (mixin) level from block 800,000 three (3)                                                                                                    | int    |
| extra         | No        | String of variable length. Can contain A-Z, 0-9 characters.                                                                                           | string |
| paymentId     | No        | Payment ID (64char hex string)                                                                                                                        | string |
| changeAddress | No        | Valid and existing address in this container.                                                                                                         | string |

* If container contains only 1 address, `changeAddress` field can be left empty and the change is going to be sent to this address.
* If addresses field contains only 1 address, `changeAddress` can be left empty and the change is going to be sent to this address.
* In the rest of the cases, `changeAddress` field is mandatory and must contain an address.

**Output**

| Argument        | Description                     | Format |
| --------------- | ------------------------------- | ------ |
| transactionHash | Hash of the sent transaction    | string |
| fee             | The fee of the send transaction | int    |

```
curl -X POST -i -H "Accept: application/json" -d '{"jsonrpc":"2.0","id":"0","password":"passw0rd","method":"sendTransaction","params":{"transfers":[{"amount":5000,"address":"SEKReTFHsz8G4...Y5owuFxLd"}],"fee":100,"anonymity":3,"unlockTime":0}}' http://localhost:8070/json_rpc
```

```
<?php
$anonymity = 3;
$fee = 243000;
$addresses = null;
$unlockTime = null;
$extra = null;
$paymentId = null;
$changeAddress = 'SEKRyyyy...';

$transfers = [
    ["address" => "SEKRxxxx...", "amount"  => 5000],
];

$response = $kryptokronaService->sendTransaction(
    $anonymity, $transfers, $fee, $addresses, $unlockTime, $extra, $paymentId, $changeAddress
);

echo $response;
```

```
anonymity = 3
fee = 243000
addresses = []
unlock_time = 0
extra = ''
payment_id = ''
change_address = 'SEKRyyyy...'

transfers = [
    {"address" : "SEKRxxxx...", "amount" : 5000},
]

response = walletd.send_transaction(
    transfers, anonymity, fee, addresses, change_address, extra, payment_id, unlock_time
)
print(response)
```

```
addresses := []string{"SEKRyyyy..."} // can be empty
unlockTime := 0
extra := ""
paymentID := ""
fee := 243000
changeAddress := "SEKRyyyy..."

transfers := []map[string]interface{}{
  {
    "address" : "SEKRxxxx...",
    "amount" : 5000,
  },
}

response, err := service.SendTransaction(addresses, transfers, fee, unlockTime, extra, paymentID, changeAddress)
if err != nil {
	fmt.Println(err)
} else {
  fmt.Println(response)
}
```

**Expected Output:**

```
{
  "id":1,
  "jsonrpc":"2.0",
  "result":{
    "transactionHash":"ae57e...",
    "fee": 4500
  }
}
```

### createDelayedTransaction

`createDelayedTransaction()` method creates a delayed transaction. Such transactions are not sent into the network automatically and should be pushed using `sendDelayedTransaction` method.

**Input**

| Argument      | Mandatory | Description                                                                                                                                           | Format |
| ------------- | --------- | ----------------------------------------------------------------------------------------------------------------------------------------------------- | ------ |
| addresses     | No        | Array of strings, where each string is an address                                                                                                     | array  |
| transfers     | Yes       | Array of address (string), amount (int)                                                                                                               | array  |
| fee           | No        | Transaction fee. Should be given in atomic units. Leave blank to use the minimum fee possible.                                                        | int    |
| feePerByte    | No        | Fee to pay per byte of the transaction. Should be given in atomic units. If given, should be greater than 1.953125, the minimum network fee per byte. | float  |
| unlockTime    | No        | Height of the block until which transaction is going to be locked for spending.                                                                       | int    |
| anonymity     | Yes       | Privacy (mixin) level from block 800,000 three (3)                                                                                                    | int    |
| extra         | No        | String of variable length. Can contain A-Z, 0-9 characters.                                                                                           | string |
| paymentId     | No        | Payment ID (64char hex string)                                                                                                                        | string |
| changeAddress | No        | Valid and existing in this container address.                                                                                                         | string |

* If container contains only 1 address, `changeAddress` field can be left empty and the change is going to be sent to this address
* If addresses field contains only 1 address, `changeAddress` can be left empty and the change is going to be sent to this address
* In the rest of the cases, `changeAddress` field is mandatory and must contain an address.
* Outputs that were used for this transactions will be locked until the transaction is sent or cancelled

**Output**

| Argument        | Description                     | Format |
| --------------- | ------------------------------- | ------ |
| transactionHash | Hash of the sent transaction    | string |
| fee             | The fee of the send transaction | int    |

```
curl -d '{"jsonrpc":"2.0","id":1,"password":"passw0rd","method":"createDelayedTransaction","params":{"transfers":[{"address":"SEKRxxxx...","amount":5000}],"anonymity":3,"changeAddress":"SEKRyyyy..."}}' http://localhost:8070/json_rpc
```

```
<?php
$anonymity = 3;
$fee = 243000;
$addresses = null;
$unlockTime = null;
$extra = null;
$paymentId = null;
$changeAddress = 'SEKRyyyy...';

$transfers = [
    ["address" => "SEKRxxxx...", "amount"  => 5000],
];

$response = $kryptokronaService->createDelayedTransaction(
    $anonymity, $transfers, $fee, $addresses, $unlockTime, $extra, $paymentId, $changeAddress
);

echo $response;
```

```
anonymity = 3
fee = 243000
addresses = []
unlock_time = 0
extra = ''
payment_id = ''
change_address = 'SEKRyyyy...'

transfers = [
    {"address" : "SEKRxxxx...", "amount" : 5000},
]

response = walletd.create_delayed_transaction(
    transfers, anonymity, fee, addresses, change_address, extra, payment_id, unlock_time
)
print(response)
```

```
addresses := []string{"SEKRyyyy..."} // can be empty
unlockTime := 0
extra := ""
paymentID := ""
fee := 243000
changeAddress := "SEKRyyyy..."

transfers := []map[string]interface{}{
  {
    "address" : "SEKRxxxx...",
    "amount" : 5000,
  },
}

response, err := service.CreateDelayedTransaction(addresses, transfers, fee, unlockTime, extra, paymentID, changeAddress)
if err != nil {
	fmt.Println(err)
} else {
  fmt.Println(response)
}
```

**Expected Output:**

```
{
  "id":1,
  "jsonrpc":"2.0",
  "result":{
    "transactionHash":"ae57e...",
    "fee": 4500
  }
}
```

### getDelayedTransactionHashes

`getDelayedTransactionHashes()` method returns hashes of delayed transactions.

No input.

**Output**

| Argument          | Description                                               | Format |
| ----------------- | --------------------------------------------------------- | ------ |
| transactionHashes | Array of strings, where each string is a transaction hash | array  |

```
curl -d '{"jsonrpc":"2.0","id":1,"password":"passw0rd","method":"getDelayedTransactionHashes","params":{}}' http://localhost:8070/json_rpc
```

```
<?php
$response = $kryptokronaService->getDelayedTransactionHashes();
echo $response;
```

```
response = walletd.get_delayed_transaction_hashes()
print(response)
```

```
response, err := service.GetDelayedTransactionHashes()
if err != nil {
	fmt.Println(err)
} else {
  fmt.Println(response)
}
```

**Expected Output:**

```
{
  "id":1,
  "jsonrpc":"2.0",
  "result":{
    "transactionHashes":["b3e374..."]
  }
}
```

### deleteDelayedTransaction

`deleteDelayedTransaction()` method deletes a specified delayed transaction.

**Input**

| Argument        | Mandatory | Description                         | Format |
| --------------- | --------- | ----------------------------------- | ------ |
| transactionHash | Yes       | Valid, existing delayed transaction | string |

**Output**

In case of success returns an empty JSON object.

```
curl -d '{"jsonrpc":"2.0","id":1,"password":"passw0rd","method":"deleteDelayedTransaction","params":{"transactionHash":"b3e37..."}}' http://localhost:8070/json_rpc
```

```
<?php
$transactionHash = 'b3e37...';
$response = $kryptokronaService->deleteDelayedTransaction($transactionHash);
echo $response;
```

```
transaction_hash = '50d83...'
response = walletd.delete_delayed_transaction(transaction_hash)

# If delete is successful, the response will be True
print(response)
```

```
transactionHash := "50d83..."
response, err := service.DeleteDelayedTransaction(transactionHash)
if err != nil {
	fmt.Println(err)
} else {
  fmt.Println(response)
}
```

**Expected Output:**

```
{
  "id":1,
  "jsonrpc":"2.0",
  "result":{}
}
```

### sendDelayedTransaction

`sendDelayedTransaction()` method sends a specified delayed transaction.

**Input**

| Argument        | Mandatory | Description                         | Format |
| --------------- | --------- | ----------------------------------- | ------ |
| transactionHash | Yes       | Valid, existing delayed transaction | string |

**Output**

In case of success returns an empty JSON object.

```
curl -d '{"jsonrpc":"2.0","id":1,"password":"passw0rd","method":"sendDelayedTransaction","params":{"transactionHash":"c37cd..."}}' http://localhost:8070/json_rpc
```

```
<?php
$transactionHash = 'c37cd...';
$response = $kryptokronaService->sendDelayedTransaction($transactionHash);

echo $response;
```

```
transaction_hash = '50d83...'
response = walletd.send_delayed_transaction(transaction_hash)

# If transaction is sent successful, the response will be True
print(response)
```

```
transactionHash := "50d83..."
response, err := service.SendDelayedTransaction(transactionHash)
if err != nil {
	fmt.Println(err)
} else {
  fmt.Println(response)
}
```

**Expected Output:**

```
{
  "id":1,
  "jsonrpc":"2.0",
  "result":{}
}
```

### sendFusionTransaction

`sendFusionTransaction()` method allows you to send a fusion transaction, by taking funds from selected addresses and transferring them to the destination address. If there aren't any outputs that can be optimized, `sendFusionTransaction()` will return an error. You can use `estimateFusion` to check the outputs, available for the optimization.

**Input**

| Argument           | Mandatory | Description                                                                                                                                           | Format |
| ------------------ | --------- | ----------------------------------------------------------------------------------------------------------------------------------------------------- | ------ |
| threshold          | Yes       | Value that determines which outputs will be optimized. Only the outputs, lesser than the threshold value, will be included into a fusion transaction. | int    |
| anonymity          | Yes       | Privacy (mixin) level from block 800,000 three (3)                                                                                                    | int    |
| addresses          | No        | Array of strings, where each string is an address to take the funds from.                                                                             | array  |
| destinationAddress | No        | An address that the optimized funds will be sent to. Valid and existing in this container address.                                                    | string |

* If container contains only 1 address, `destinationAddress` field can be left empty and the funds are going to be sent to this address.
* If addresses field contains only 1 address, `destinationAddress` can be left empty and the funds are going to be sent to this address.
* In the rest of the cases, `destinationAddress` field is mandatory and must contain an address.

**Output**

| Argument        | Description                  | Format |
| --------------- | ---------------------------- | ------ |
| transactionHash | Hash of the sent transaction | string |

```
curl -d '{"jsonrpc":"2.0","id":1,"password":"passw0rd","method":"sendFusionTransaction","params":{"threshold":1000000,"anonymity":3,"addresses":["SEKRxxxx...","SEKRyyyy..."],"destinationAddress":"SEKRzzzz..."}}' http://localhost:8070/json_rpc
```

```
<?php
$threshold = 1000000;
$anonymity = 3;
$addresses = ['SEKRxxxx...', 'SEKRyyyy...'];
$destinationAddress = 'SEKRzzzz...';
$response = $kryptokronaService->sendFusionTransaction($threshold, $anonymity, $addresses, $destinationAddress);

echo $response;
```

```
threshold = 1000000
anonymity = 3
addresses = ['SEKRxxxx...', 'SEKRyyyy...']
destination_address = 'SEKRzzzz...'
response = walletd.send_fusion_transaction(threshold, anonymity, addresses, destination_address)

print(response)
```

```
threshold := 1000000
addresses := []string{"SEKRxxxx...", "SEKRyyyy..."}
destinationAddress := "SEKRzzzz..."
response, err := service.SendfusionTransaction(threshold, addresses, destinationAddress)
if err != nil {
	fmt.Println(err)
} else {
  fmt.Println(response)
}
```

**Expected Output:**

```
{
  "id":1,
  "jsonrpc":"2.0",
  "result":{
    "transactionHash":"93faed..."
  }
}
```

### estimateFusion

`estimateFusion()` method counts the number of unspent outputs of the specified addresses and returns how many of those outputs can be optimized. This method is used to understand if a fusion transaction can be created. If `fusionReadyCount` returns a value = 0, then a fusion transaction cannot be created.

**Input**

| Argument  | Mandatory | Description                                                                                                                                           | Format |
| --------- | --------- | ----------------------------------------------------------------------------------------------------------------------------------------------------- | ------ |
| threshold | Yes       | Value that determines which outputs will be optimized. Only the outputs, lesser than the threshold value, will be included into a fusion transaction. | int    |
| addresses | No        | Array of strings, where each string is an address to take the funds from.                                                                             | string |

**Output**

| Argument         | Description                                                 | Format |
| ---------------- | ----------------------------------------------------------- | ------ |
| totalOutputCount | Total number of unspent outputs of the specified addresses. | int    |
| fusionReadyCount | Number of outputs that can be optimized.                    | int    |

```
curl -d '{"jsonrpc":"2.0","id":1,"password":"passw0rd","method":"estimateFusion","params":{"threshold":1000000,"addresses":["SEKRxxxx...","SEKRyyyy..."]}}' http://localhost:8070/json_rpc
```

```
<?php
$threshold = 1000000;
$addresses = ['SEKRxxxx...', 'SEKRyyyy...'];
$response = $kryptokronaService->estimateFusion($threshold, $addresses);

echo $response;
```

```
threshold = 1000000
addresses = ['SEKRxxxx...', 'SEKRyyyy...']
response = walletd.estimate_fusion(threshold, addresses)
print(response)
```

```
threshold := 1000000
addresses := []string{"SEKRxxxx...","SEKRyyyy..."}
response, err := service.EstimateFusion(threshold, addresses)
if err != nil {
	fmt.Println(err)
} else {
  fmt.Println(response)
}
```

**Expected Output:**

```
{
  "id":1,
  "jsonrpc":"2.0",
  "result":{
    "fusionReadyCount":0,
    "totalOutputCount":8
  }
}
```

### createIntegratedAddress

`createIntegratedAddress()` method allows you to create a combined address, containing a standard address and a paymentId, to be used in sendTransaction() or for supplying to a user, instead of using an address and paymentId as separate parameters. This is helpful to ensure users cannot forget to supply a payment Id.

**Input**

| Argument  | Mandatory | Description                           | Format |
| --------- | --------- | ------------------------------------- | ------ |
| address   | Yes       | A valid address                       | string |
| paymentId | Yes       | A valid paymentId (64char hex string) | string |

**Output**

| Argument          | Description                    | Format |
| ----------------- | ------------------------------ | ------ |
| integratedAddress | The created integrated address | string |

```
curl -d '{"jsonrpc":"2.0","id":1,"password":"passw0rd","method":"createIntegratedAddress","params":{"paymentId":"7FE73BD90EF05DEA0B5C15FC78696619C50DD5F2BA628F2FD16A2E3445B1922F", "address":"SEKRxxxx..."}}' http://localhost:8070/json_rpc
```

```
<?php
$address = 'SEKRxxxx...';
$paymentId = '7FE73BD90EF05DEA0B5C15FC78696619C50DD5F2BA628F2FD16A2E3445B1922F';
$response = $kryptokronaService->createIntegratedAddress($address, $paymentId);

echo $response;
```

```
address = 'SEKRxxxx...'
payment_id = '7FE73BD90EF05DEA0B5C15FC78696619C50DD5F2BA628F2FD16A2E3445B1922F'
response = walletd.create_integrated_address(address, payment_id)
print(response)
```

```
address := "SEKRxxxx..."
paymentID := "7FE73BD90EF05DEA0B5C15FC78696619C50DD5F2BA628F2FD16A2E3445B1922F"
response, err := service.CreateIntegratedAddress(address, paymentID)
if err != nil {
	fmt.Println(err)
} else {
  fmt.Println(response)
}
```

**Expected Output:**

```
{
  "id": 1,
  "jsonrpc": "2.0",
  "result": {
    "integratedAddress": "SEKRxxx..."
  }
}
```

### getFeeInfo

`getFeeInfo()` method retrieves the fee and address (if any) that that kryptokronad walletd is connecting to is using. This fee will automatically be added to any transactions sent by sendTransaction() or sendDelayedTransaction(). Note it does not apply to sendFusionTransaction().

No input.

**Output**

| Argument | Description                                                                | Format |
| -------- | -------------------------------------------------------------------------- | ------ |
| address  | The address of the node owner                                              | string |
| amount   | The fee that will be sent to the node owners address with each transaction | int    |

```
curl -d '{"jsonrpc":"2.0","id":1,"password":"passw0rd","method":"getFeeInfo","params":{}}' http://localhost:8070/json_rpc
```

```
<?php
$response = $kryptokronaService->getFeeInfo();

echo $response;
```

```
response = walletd.get_fee_info()
print(response)
```

```
response, err := service.GetFeeInfo()
if err != nil {
	fmt.Println(err)
} else {
  fmt.Println(response)
}
```

**Expected Output:**

```
{
  "id": 1,
  "jsonrpc": "2.0",
  "result": {
    "address": "SEKRxxx...",
    "amount": 5000
  }
}
```

### validateAddress

`validateAddress()` method takes an address as it's only argument and returns isValid: true/false, depending on the validity of the address provided.

**Input**

| Argument | Description             | Format |
| -------- | ----------------------- | ------ |
| address  | The address to validate | string |

**Output**

| Argument | Description                                                  | Format  |
| -------- | ------------------------------------------------------------ | ------- |
| isValid  | The result, i.e. wheter the provided address is valid or not | boolean |

```
curl -X POST -i -H "Content-Type: application/json" -d '{"jsonrpc":"2.0","id":"0","password":"passw0rd","method":"validateAddress","params":{"address":"SEKReYisjz5FqzU4bxS48aA5BTcercMddeqsYnoCU2WLNJeeRf1gVwqUHJx3paXBzuVGUJimRsMtKaNABCZLnSUBE2YpVKeyxuj"}}' http://localhost:8070/json_rpc
```

**Expected Output:**

```
{
  "id":"0",
  "jsonrpc":"2.0",
  "result": {
    "isValid":true
  }
}
```

### License

[![Creative Commons License](https://github.com/kryptokrona/kryptokrona-docs/raw/master/docs/assets/cc-by-sa.png)](https://creativecommons.org/licenses/by-sa/3.0/)

The content in this document was originally written by the [Bytecoin (BCN) Developers](https://bytecoin.org/). It is licensed under the [CC BY SA 3.0 license](https://creativecommons.org/licenses/by-sa/3.0/). The source material can be found at the [Bytecoin Wiki](https://github.com/bcndev/bytecoin).

Also of note, kryptokrona developers have altered and adapted the content to suit our implementation of the API. This was done independently of the Bytecoin development team. They neither endorse or acknowledge our changes. Feel free to adopt or change our content as per the [CC BY SA 3.0 license](https://creativecommons.org/licenses/by-sa/3.0/) requirements.


# RPC Errors

Here are some common error messages that Kryptokrona and Kryptokrona-service spit out, why they occured and how to fix them.\
Listed are also some possible alternative errors which they could spit out.

#### BAD\_ADDRESS / Bad address

> **Possible Alternative Error:** The supplied address parameter is invalid or in an incorrect format

**Description:** This error can happen when an address you supply is invalid, or the address field in your request is improperly formatted.

**Solution:** First make sure that the address you are attempting to send to is a valid 99 character long TRTL address, or 236 character integrated address. Next, make sure that your request is properly formatted - for instance, in a SendTransaction request where you are sending from multiple addresses, the address field must be an array of strings, and the address field within the transfers array must be a single string.

#### WRONG\_AMOUNT / Wrong amount

> **Possible Alternative Error:** The requested send amount is in an incorrect format, or your wallet does not have enough balance or available inputs to send the requested amount

**Description:** This error can happen when the amount you are trying to send within a transaction is above the sum of your available inputs, or is in an incorrect format. This can also occur when you have *dust* inputs that are unsendable. These generally comprise a very small amount of your balance, but may prevent you from sending all your balance at once.

**Solution:** This error can be solved by ensuring that the amount you are attempting to send is valid and within the bounds of your available balance, and that your wallet has been properly optimized/fused.

#### MIXIN\_COUNT\_TOO\_BIG / MixIn count is too big

> **Possible Alternative Error:** I'm not sure if internal node error suggests something else as well, I have seen it only when encountering the mixin too big error.

**Description:** The network can't find enough outputs to mix your transaction with.

**Solution:** This can be rectified by using zero mixin or lowering the amount you are sending. This is very unlikely to be encountered on mainnet, and is mainly found on testnet.

#### NOT\_INITIALIZED / Object was not initialized

**Description:** -

**Solution:** -

#### WRONG\_PASSWORD / The password is wrong

> **Possible Alternative Error:** The wallet password is incorrect

**Description:** This is a pretty simple one. The wallet password is wrong. If you're 100% sure it's correct, check that you're opening a wallet file, and it's not got corrupted.

**Solution:** Enter the correct password! Import via keys if you cannot remember it.

#### ALREADY\_INITIALIZED / The object is already initialized

**Description:** -

**Solution:** -

#### INTERNAL\_WALLET\_ERROR / Internal error occurred

**Description:** -

**Solution:** -

#### TRANSACTION\_SIZE\_TOO\_BIG / Transaction size is too big

> **Possible Alternative Error:** Transaction is too large to fit in a block, try reducing the amount you are sending

**Description:** This is caused when the transaction size (in bytes, not amount), is too large to fit into a block. Currently this limit is around 125k bytes, and the size of transactions is based upon how many key images you need to supply for the transaction - each key image comes from a previous transaction, and so if you have lots of small payments, your transactions will need a lot of key images to sum to the desired amount.

**Solution:** You can either:

* Perform fusion transactions, to fuse your small key images into larger ones, letting you send more at once, or
* Split your one transaction into multiple transactions, until each smaller one can fit into a block. This will slightly raise the fee you have to pay of course.

\###SUM\_OVERFLOW / Sum overflow

> **Possible Alternative Error:** Amount + fee would cause integer overflow. Please lower the amount you are sending.

**Description:** When sending a transaction, the amount+fee would cause integer overflow. This is very unlikely to occur in practice, as the data type used is a uint64\_t.

**Solution:** Send a smaller amount in one transaction.

\###ZERO\_DESTINATION / The destination is empty

> **Possible Alternative Error:** No destination address specified, or amount specified is zero

**Description:** This is caused by either:

* A transaction amount of zero, or
* No address was specified to transfer to.

**Solution:** Ensure you supply an address parameter in the transfers array, and that the amount is larger than zero.

#### TX\_CANCEL\_IMPOSSIBLE / Impossible to cancel transaction

**Description:** -

**Solution:** -

#### WRONG\_STATE / The wallet is in wrong state (maybe loading or saving),try again later

**Description:** -

**Solution:** -

#### OPERATION\_CANCELLED / The operation you've requested has been cancelled

**Description:** -

**Solution:** -

#### TX\_TRANSFER\_IMPOSSIBLE / Transaction transfer impossible

**Description:** -

**Solution:** -

#### WRONG\_VERSION / Wrong version

**Description:** This is encountered when loading the wallet file with walletd. There are a few possible causes for it:

* Your wallet file is the wrong version
* The wallet file has got corrupted.

**Solution:** Delete the blockchain db, delete the .wallet file, import your keys, and resync from scratch

#### FEE\_TOO\_SMALL / Transaction fee is too small

> **Possible Alternative Error:** Transaction fee lower than minimum of 0.1 TRTL.

**Description:** This occurs if the transaction fee is below the minimum allowed.

**Solution:** Make sure the fee used is at least 0.1 TRTL, or 10 in atomic units.

#### KEY\_GENERATION\_ERROR / Cannot generate new key

**Description:** -

**Solution:** -

#### INDEX\_OUT\_OF\_RANGE / Index is out of range

**Description:** -

**Solution:** -

#### ADDRESS\_ALREADY\_EXISTS / Address already exists

> **Possible Alternative Error:** The address you are trying to create already exists in this wallet.

**Description:** The address you are trying to add with createAddress() already exists.

**Solution:** Um, address already exists, so don't do that? If you just want a new random address, don't supply the view/spend key parameter, and it will generate a random one.

#### TRACKING\_MODE / The wallet is in tracking mode

> **Possible Alternative Error:** This method is not usable in a view only wallet.

**Description:** This error occurs when you are using a view only wallet (A tracking wallet), and call a method that can only be used with wallets that can spend, such as sendTransaction().

**Solution:** Don't use methods which require spending with a view only wallet.

#### WRONG\_PARAMETERS / Wrong parameters passed

> **Possible Alternative Error:** Individual errors for each specific issue.

**Description:** This error can occur in a number of scenarios.

* A supplied private/public key is invalid/cannot be parsed.
* A spend key was specified to createAddress in a view only wallet, or a null spend key was specified in a non view only wallet
* The blocks count given is less than 1
* The blockindex given is less than 1

For more info on the exact error, check your walletd.log or console window.

**Solution:** Check the API Docs for examples on how to use the method you are toying with, to help determine what parameter is invalid.

#### OBJECT\_NOT\_FOUND / Object not found

**Description:** -

**Solution:** -

#### WALLET\_NOT\_FOUND / Requested wallet not found

> **Possible Alternative Error:** Wallet address could not be found in the wallet container.

**Description:** The wallet address you are trying to retrieve the balance of does not exist in your wallet container.

**Solution:** Ensure you are checking the balance of a wallet that exists in your container.

#### CHANGE\_ADDRESS\_REQUIRED / Change address required

> **Possible Alternative Error:** No change address given with a multi address wallet.

**Description:** This occurs when you omit the change address parameter in a transaction. This is not required in a single address wallet, but if multiple addresses have been added to a wallet container, then the change address is required. Generally, you will want this value to be the same as the address you are sending from.

**Solution:** Include a change address with your requests to allow your code to work with single and multi address wallets.

#### CHANGE\_ADDRESS\_NOT\_FOUND / Change address not found

> **Possible Alternative Error:** Change address is not present in your wallet container.

**Description:** This occurs when the address you specified in the change address parameter is not a wallet that exists in your wallet container file.

**Solution:** Make sure you set the change address value to a wallet address that exists in your container.

#### DESTINATION\_ADDRESS\_REQUIRED / Destination address required

> **Possible Alternative Error:** No destination address given with a multi address wallet.

**Description:** This occurs when you omit the destination address parameter in a fusion transaction. This is not required in a single address wallet, but if multiple addresses have been added to a wallet container, then the destination address is required. Generally, you will want this value to be the same as the address you are sending from.

**Solution:** Include a destination address with your fusion transactions to allow your code to work with single and multi address wallets.

#### DESTINATION\_ADDRESS\_NOT\_FOUND / Destination address not found

> **Possible Alternative Error:** Destination address is not present in your wallet container.

**Description:** This occurs when the address you specified in the destination address parameter is not a wallet that exists in your wallet container file.

**Solution:** Make sure you set the destination address value to a wallet address that exists in your container.

#### BAD\_PAYMENT\_ID / Wrong payment id format

> **Possible Alternative Error:** Payment ID is not 64 characters or is not a valid hex string.

**Description:** Your payment ID is not a valid, 64 char hex string.

**Solution:** Ensure you are correctly generating payment ID's. They should contain only a-z 0-9 characters, and be 64 characters long.

#### BAD\_TRANSACTION\_EXTRA / Wrong transaction extra format

> **Possible Alternative Error:** Transaction extra is not a valid hex string.

**Description:** This occurs when your transaction extra is not hex encoded data.

**Solution:** Your transaction extra should only contain a-z 0-9 characters.

#### MIXIN\_ABOVE\_THRESHOLD / Mixin above maximum allowed threshold

> **Possible Alternative Error:** Mixin is above maximum allowed threshold of \<x>

**Description:** This occurs when your anonymity value is above the maximum allowed. You can check the current mixin limits by viewing their values in CryptoNoteConfig.h. Currently, the maximum allowed mixin is 100. This will change to 7 at block 620k.

**Solution:** Make sure your anonymity value is within the allowed limits.

#### MIXIN\_BELOW\_THRESHOLD / Mixin below minimum allowed threshold

> **Possible Alternative Error:** Mixin is below minimum allowed threshold of \<x>

**Description:** This occurs when your anonymity value is above the minimum allowed. You can check the current mixin limits by viewing their values in CryptoNoteConfig.h. Currently, the minimum allowed mixin is 0. This will change to 7 at block 620k.

**Solution:** Make sure your anonymity value is withing the allowed limits.

#### CONFLICTING\_PAYMENT\_IDS / Multiple conflicting payment ID's werespecified via the use of integrated addresses

**Description:** When using integrated addresses, if a payment ID is specified, it must match the payment ID included in the integrated address. Furthermore, if multiple integrated addresses are used, they must all have the same payment ID.

**Solution:** Only send to one integrated address at once, and don't include a payment ID, to avoid confusion.

### KryptokronaCoind Errors

* <https://github.com/Kryptokronacoin/Kryptokronacoin/blob/master/src/NodeRpcProxy/NodeErrors.h>

#### NOT\_INITIALIZED / Object was not initialized

**Description:** -

**Solution:** -

#### ALREADY\_INITIALIZED / Object has been already initialized

**Description:** -

**Solution:** -

#### NETWORK\_ERROR / Network error

**Description:** KryptokronaCoind is not open / not responding.

**Solution:** I'm not sure if you can experience this with walletd, I have seen it with walletgreen.

#### NODE\_BUSY / Node is busy

**Description:** -

**Solution:** -

#### INTERNAL\_NODE\_ERROR / Internal node error

**Description:** -

**Solution:** -

#### REQUEST\_ERROR / Error in request parameters

**Description:** -

**Solution:** -

#### CONNECT\_ERROR / Can't connect to daemon

**Description:** -

**Solution:** -


# Wallet RPC API

API Documentation is available [here](https://kryptokrona.se/wallet-api) for wallet-api


# Daemon HTTP RPC API

The daemon HTTP RPC is a HTTP server which provides additional information regarding network and daemon connections.

### Installation

```
npm i kryptokrona-rpc
```

### Interacting with the API

#### API endpoint example

```
http://localhost:11898
```

#### Configuration and Instantiation

To start the Daemon JSON RPC API server at `http://localhost:11898`, run:

`kryptokrona --rpc-bind-port=11898`

To make the server accessible from another computer, use the `--rpc-bind-ip 0.0.0.0` switch.

`kryptokrona --rpc-bind-ip=0.0.0.0 --rpc-bind-port=11898`

To enable block explorer API access (like for `getblocks`, `gettransactionpool`, etc.), use the `--enable-blockexplorer` switch.

`kryptokrona --enable-blockexplorer`

The above given switches can be combined to achieve remote access with block explorer methods as shown below.

`kryptokrona --enable-blockexplorer --rpc-bind-ip=0.0.0.0 --rpc-bind-port=11898`

This would make the RPC server accessible at

`http://<your ip address>:11898`

and, locally at

`http://localhost:11898`

To make a HTTP RPC request to your Daemon RPC you should use a GET request that looks like this:

`http://<service address>:<service port>`

| Parameter           | Description                                                                                              |
| ------------------- | -------------------------------------------------------------------------------------------------------- |
| `<service address>` | IP of Daemon RPC, if it is located on local machine it is either 127.0.0.1 or localhost                  |
| `<service port>`    | Daemon RPC port, by default it is bound to 11898 port, but it can be manually bound to any port you want |

```js
const kryptokrona = require('kryptokrona-rpc').kryptokrona

const daemon = new kryptokrona({
  host: '0.0.0.0', // ip address or hostname of the kryptokrona host
  port: 11898, // what port is the RPC server running on
  timeout: 2000, // request timeout
  ssl: false // whether we need to connect using SSL/TLS
})
```

### getheight

`getheight()` returns the height of the daemon and the network

No Input.

**Output**

| Argument        | Description            | Format |
| --------------- | ---------------------- | ------ |
| height          | Current daemon height  | int    |
| network\_height | Current Network height | int    |
| status          | Status of request      | string |

```shell
curl http://localhost:11898/getheight
```

```js
daemon.getHeight().then((result) => {
  // do something
}).catch((error) => {
  // do something
})
```

**Expected Output**

```json
{
    "height":614214,
    "network_height":614218,
    "status":"OK"
}
```

### getinfo

`getinfo()` returns information related to the network and daemon connection

No Input.

**Output**

| Argument                     | Description                                                                                                                                 | Format |
| ---------------------------- | ------------------------------------------------------------------------------------------------------------------------------------------- | ------ |
| alt\_blocks\_count           | the number of blocks on alternative (split) chains since the start of the daemon                                                            | int    |
| difficulty                   | difficulty of the top block                                                                                                                 | int    |
| grey\_peerlist\_size         | list of peers that were alive but not any more (offline)                                                                                    | int    |
| hashrate                     | estimated network hashrate for given block (top block if general chain info) = difficulty / 30s (block time target)                         | int    |
| height                       | daemon height. index of the last locally stored block. different from network\_height when syncing the network, or when just found a block. | int    |
| incoming\_connections\_count | Number of peers connected to and pulling from this daemon node.                                                                             | int    |
| last\_known\_block\_index    | ?                                                                                                                                           | int    |
| major\_version               | blockchain major version. such as hash algorithm change                                                                                     | int    |
| minor\_version               | blockchain minor version. for example, difficulty algo adjustment. rarely used.                                                             | int    |
| network\_height              | blockchain length reported by peers. the longest value given by any connected peer.                                                         | int    |
| outgoing\_connections\_count | number of outgoing connections from the daemon                                                                                              | int    |
| start\_time                  | the time when this daemon was started. epoch time in seconds                                                                                | int    |
| status                       | Status of request                                                                                                                           | string |
| supported\_height            | the height of the blockchain for supported fork. if forked after this block height, this version does not support it                        | int    |
| synced                       | sync status. does the height of this node match the height of the network?                                                                  | bool   |
| testnet                      | whether the daemon is on testnet or not                                                                                                     | bool   |
| tx\_count                    | Total number of non-coinbase transaction in the chain.                                                                                      | int    |
| tx\_pool\_size               | Number of transactions that have been broadcast but not included in a block.                                                                | int    |
| upgrade\_heights             | pre-determined fork heights. blockchain heights where it forked.                                                                            | array  |
| version                      | version of the daemon software                                                                                                              | string |
| white\_peerlist\_size        | list of online peers                                                                                                                        | int    |

```shell
curl http://localhost:11898/getinfo
```

```js
daemon.getInfo().then((result) => {
  // do something
}).catch((error) => {
  // do something
})
```

**Expected Output**

```json
{
    "alt_blocks_count":1,
    "difficulty":250340644,
    "grey_peerlist_size":493,
    "hashrate":8344688,
    "height":614321,
    "incoming_connections_count":28,
    "last_known_block_index":614319,
    "major_version":4,
    "minor_version":0,
    "network_height":614321,
    "outgoing_connections_count":8,
    "start_time":1531403048,
    "status":"OK",
    "supported_height":620000,
    "synced":true,
    "testnet":false,
    "tx_count":720189,
    "tx_pool_size":0,
    "upgrade_heights":[
        187000,
        350000,
        440000,
        620000,
        .....
    ],
    "version":"0.6.3",
    "white_peerlist_size":43
}
```

### gettransactions

`gettransactions()` method returns list of missed transactions. "Missed transactions" are invalid transactions in the sense that they do not exist in the blockchain. Input should include the transaction hashes to check. Try figuring that out. This method is likely to go away in near future.

No Input

**Output**

| Argument     | Description                                | Format |
| ------------ | ------------------------------------------ | ------ |
| missed\_tx   | array of missed transactions               | array  |
| status       | Status of request                          | string |
| txs\_as\_hex | array of hex values of missed transactions | array  |

```shell
curl http://localhost:11898/gettransactions
```

```js
daemon.getTransactions({
  hashes: [
    '549828e75151982b0e51b27e8f53b26ebc174f0ef78063984c8952b13e2a3564',
    '549828e75151982b0e51b27e8f53b26ebc174f0ef78063984c8952b13e2a3563'
  ]
}).then((result) => {
  // do something
}).catch((error) => {
  // do something
})
```

**Expected Output**

```json
{
    "missed_tx":[],
    "status":"OK",
    "txs_as_hex":[]
}
```

### getpeers

`getpeers()` method returns the list of peers connected to the daemon

No Input.

**Output**

| Argument | Description                          | Format |
| -------- | ------------------------------------ | ------ |
| peers    | array of peers (peer\_ip:peer\_port) | array  |
| status   | Status of request                    | string |

```shell
curl http://localhost:11898/getpeers
```

```js
daemon.getPeers().then((result) => {
  // do something
}).catch((error) => {
  // do something
})
```

**Expected Output**

```json
{
    "peers":[
        "192.222.157.172:11897",
        "94.23.49.75:11897",
        "112.78.10.43:11897",
        .....
    ],
    "status":"OK"
}
```

### feeinfo

`feeinfo()` method returns information about the fee set for the remote node.

No Input.

**Output**

| Argument | Description                      | Format |
| -------- | -------------------------------- | ------ |
| address  | address to which the fee is paid | string |
| amount   | fee amount                       | int    |
| status   | Status of fees for the node      | string |

```shell
curl http://localhost:11898/feeinfo
```

```js
daemon.feeInfo().then((result) => {
  // do something
}).catch((error) => {
  // do something
})
```

**Expected Output**

```json
{
    "address":"",
    "amount":0,
    "status":"Node's fee address is not set"
}
```

### License

[![Creative Commons License](https://github.com/kryptokrona/kryptokrona-docs/blob/master/assets/cc-by-sa.png)](https://creativecommons.org/licenses/by-sa/3.0/)

The content in this document was originally written by the [Bytecoin (BCN) Developers](https://bytecoin.org/). It is licensed under the [CC BY SA 3.0 license](https://creativecommons.org/licenses/by-sa/3.0/). The source material can be found at the [Bytecoin Wiki](https://github.com/bcndev/bytecoin).

Also of note, kryptokrona developers have altered and adapted the content to suit our implementation of the API. This was done independently of the Bytecoin development team. They neither endorse or acknowledge our changes. Feel free to adopt or change our content as per the [CC BY SA 3.0 license](https://creativecommons.org/licenses/by-sa/3.0/) requirements.


# Guides


# Wallets


# Making a Paper Wallet

The main purpose of a paper wallet is to quickly create a wallet to start receiving funds.

**You will not be able to spend or send your funds to other people until you set up a CLI, GUI or Web Wallet.**

You can view a guide on how to make a wallet [here](https://github.com/kryptokrona/kryptokrona-docs/blob/master/docs/guides/Making-a-Wallet/README.md)

There are two options for a paper wallet.

### Making A Paper Wallet on an Internet-Connected Machine

Go to [this link](https://kryptokrona.se/paperwallet/) and follow [these steps](#generating-the-wallet).

### Making a Paper Wallet on an Air-Gapped Machine

Go to [this GitHub repository](https://github.com/kryptokrona/kryptokrona-paperwallet-generator)(on a machine connected to the internet).

To use it, follow these steps:

**Windows**

* Click on `Clone or Download`
* Click on `Download ZIP`
* Extract the `.zip` file to a directory of your choice (say, `C:/paper`)
* Copy/paste the files through a flash drive to your air-gapped machine.
* Open the folder where you pasted the files, (say `C:/paper`) and double click on `index.html`
* Follow [these steps.](#generating-the-wallet)

**Linux**

* Open the terminal
* Install git if it's not already installed (`apt-install git`)
* Type, `git clone https://github.com/kryptokrona/kryptokrona-paperwallet-generator.git`and press enter
* Then enter `cd kryptokrona-paperwallet-generator`
* After doing so, enter `index.html`
* A page should open up in your browser
* Follow [these steps.](#generating-the-wallet)

#### Generating the Wallet

* Click on `Generate a Wallet`
* Mash your keyboard and start entering a bunch of random letters, numbers and signs in the field. Make sure you toggle on Caps Lock repeatedly! (Don't go too crazy - otherwise you might end up shutting down your PC!)
* After you're done mashing your keyboard, press `Generate Wallet`
* The letters and numbers in the green box, starting with `SEKR`, is your public address. You can share it freely.
* Save the `Seed Phrase`, the 25 words in the red box, safely.\
  **DO NOT SHARE IT WITH ANYONE**.\
  **Anyone who has access to this can&#x20;*****access your funds*****&#x20;and has&#x20;*****complete control*****&#x20;over your wallet.**
* Save the `Spend Key` and the `View Key`, the two very long strings of (seemingly) random letters and numbers, safely.\
  **DO NOT SHARE IT WITH ANYONE**.\
  **Anyone who has access to this can&#x20;*****access your funds*****&#x20;and has&#x20;*****complete control*****&#x20;over your wallet.**


# Making a Kryptokrona Wallet

There are multiple different types of wallets you can choose to use for Kryptokrona, paper wallet, CLI wallet and GUI wallet.

We recommend making a paper wallet so that you can start receiving funds, and later import them into a GUI or CLI wallet.

## Paper Wallet

The main purpose of a paper wallet is to quickly create a wallet to start receiving funds.

**You will not be able to spend or send your funds to other people until you set up a CLI, GUI or Web Wallet.**

To view a guide on how to make a paper wallet, you can go [here](https://github.com/kryptokrona/kryptokrona-docs/blob/master/docs/guides/Making-a-paper-wallet/README.md).

## xkr-wallet (CLI Wallet)

The CLI Wallet, called xkr-wallet, is a multi-platform program (Win/Linux/Mac) that requires you to enter commands for it to work and you cannot use your mouse. However, it is currently the most stable and gets the newest updates first.

You can find a guide on how to use xkr-wallet [here](#xkr-wallet-cli-wallet).

## Kryptokrona Wallet (GUI Wallet)

Kryptokrona also has a GUI wallet, It's open sourced and available on every major OS. You can download it [here](https://kryptokrona.se/en/kryptokrona-wallet-2/), or view the source code [here](https://github.com/kryptokrona/kryptokrona-wallet)

If you would like to use it, you can check out [this guide](https://github.com/kryptokrona/kryptokrona-docs/blob/master/docs/guides/Using-Remote-Nodes/README.md#proton-wallet).

## Android wallet

You can also use your Android phone to store your XKR funds in. You can find it on [Google Play Store](https://play.google.com/store/apps/details?id=com.xkr).


# Recovering your Wallet

In case you have lost your wallet, but still have either your private spend and view keys *or* your 25 word mnemonic seed, you can still recover it. Below are the guides for various types of wallets.

### xkrwallet

View [this guide](/guides/wallets/command-line/using-kkrwallet#restoring-your-wallet) for steps on recovering your wallet with your private spend and view keys, or your 25 word mnemonic seed with xkrwallet.

### Kryptokrona Desktop Wallet

View [this guide](/guides/wallets/using-kryptokrona-wallet#restoring-a-wallet-from-seed-or-keys) for steps on recovering your wallet with your private spend and view keys, or your 25 word mnemonic seed with Proton Wallet.


# Using Kryptokrona Desktop Wallet

<figure><img src="https://2858262040-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fx7WCorBnqCP2oVt16bNf%2Fuploads%2FjglQOVVGms4PFqn91Pa5%2FScreenshot%202024-11-04%20at%2023.45.45.png?alt=media&amp;token=b9935996-bc14-4709-9f83-a5e4f6dce332" alt=""><figcaption></figcaption></figure>

Our new desktop wallet - codename Aesir - has just been released. Stay tuned for more info. The app can be downloaded from [here](https://github.com/kryptokrona/aesir-wallet/releases).


# Command Line

You will find information about command line wallets & api's on this page (for expert users/developers)

{% tabs %}
{% tab title="Terminal/CLI" %}
[**xkr-wallet**](/guides/wallets/command-line/using-kkrwallet)

An easy to use terminal (CLI) interface for Mac/Windows/Linux.

[**wallet-api**](/kryptokrona/api/wallet-rpc-api)

A high performance api that can handle multiple wallets.

[**kryptokrona-service**](/kryptokrona/api/legacy-wallet-rpc-api)

A somewhat outdated api that should be deferred.
{% endtab %}

{% tab title="JavaScript" %}
[**wallet-backend-js**](/kryptokrona/api/kryptokrona-wallet-backend-js)

wallet-backend-js is a JavaScript implementation of a fully capable XKR-wallet that may be used for developing JavaScript (node.js) apps.
{% endtab %}
{% endtabs %}

There are more options available for developers, check them out [here](/kryptokrona/api).


# Using xkrwallet

### Downloading

Binary distributions can be found [here](https://github.com/kryptokrona/kryptokrona/releases).

Select the appropriate file for the target platform (Windows, Mac, Linux).

Binaries are provided in `.zip` format, while source code is provided in `.zip` and `.tar.gz` format.

### Installing

#### Installing on Windows

Extract the *.zip* file (`kryptokrona-...-windows.zip`).

#### Installing on Mac

Extract the *.zip* file:

```bash
unzip kryptokrona-...-mac.zip
```

#### Installing on Linux

Extract the *.zip* file:

```bash
unzip kryptokrona-...-linux.zip
```

### Synchronizing the Blockchain

Running `kryptokrona` will start the *kryptokrona* network daemon, which will connect to the network and begin downloading and verifying the kryptokrona blockchain.

Because the blockchain is constantly growing, the file size always increases (the blockchain is currently over 35 GB), and *kryptokrona must verify every block*, which is both CPU and disk intensive. An SSD with at least this much free disk space is recommended, unless you plan to use [remote nodes](broken://pages/xNbusqzPgZZnR1j6zHDf#kkrwallet).

#### Using Checkpoints

In **versions 0.4.3+** you can sync a fresh chain from block 0 much quicker by using checkpoints. Follow [this guide](https://github.com/kryptokrona/kryptokrona-docs/blob/master/docs/guides/Using-Checkpoints/README.md) to learn more.

#### Windows

Run the `kryptokrona.exe` executable extracted from the Windows binary zip:

#### Mac / Linux

Run the `kryptokrona` binary extracted from the `.zip` download:

```bash
./kryptokronad
```

### Using xkrwallet

With `kryptokrona` still running in the background or another terminal/shell/command prompt, open xkrwallet:

**Windows**

Run the `xkrwallet.exe` executable from the extracted folder.

**Mac / Linux**

```bash
./xkrwallet
```

#### Using xkrwallet commands

xkrwallet has a twin command system; a numerical shortcut for navigating the menu, and typed commands you can access directly. The more you use xkrwallet the more typed commands you'll pick up. This guide is written using the written commnand system. Feel free to use the numbers associated with the command.

#### Creating a Wallet

To create a wallet, type `create` and press `enter`:

```
Welcome, please choose an option below:

 1	open                     Open a wallet already on your system
 2	create                   Create a new wallet
 3	seed_restore             Restore a wallet using a seed phrase of words
 4	key_restore              Restore a wallet using a view and spend key
 5	view_wallet              Import a view only wallet
 6	exit                     Exit the program

What would you like to do?: create
What would you like to call your new wallet?: newWallet
Give your new wallet a password: **************
Confirm your new password: **************
Welcome to your new wallet, here is your payment address:
SEKRuxqfDys1pfQ1omkHMVViY4sFh6My5Ff3HBY8XPp3cJBkEfD7romVyzKug3mb9NNR4A8kEjZxZ9CHUgWckBSpPfbxnWAQUGL

Please copy your secret keys and mnemonic seed and store them in a secure location: 
Private spend key:
41c834f7c26e12373e5c39a9c9b1f8beb665324ad0d098cabda1234567b5d30f

Private view key:
df51e85dfa4fe48d0123475ec966124b1234c98abda6789060fe6d69b503490b

Mnemonic seed:
truth neon vials ignore butterfly cactus soggy vibrate meant wizard awesome fountain axis skater itself egotistic pumpkins ultimate foaming fatal request sifting merger egotistic fierce

If you lose these your wallet cannot be recreated!


Your wallet is syncing with the network in the background.
Until this is completed new transactions might not show up.
Use the status command to check the progress.

 1	advanced                 List available advanced commands
 2	address                  Display your payment address
 3	balance                  Display how much KKR you have
 4	backup                   Backup your private keys and/or seed
 5	exit                     Exit and save your wallet
 6	help                     List this help message
 7	transfer                 Send KKR to someone

[KKR newWallet]: 
```

#### Opening a Wallet

To open an existing wallet; type `open` and press `enter`:

```
 1	open                     Open a wallet already on your system
 2	create                   Create a new wallet
 3	seed_restore             Restore a wallet using a seed phrase of words
 4	key_restore              Restore a wallet using a view and spend key
 5	view_wallet              Import a view only wallet
 6	exit                     Exit the program

What would you like to do?: 1
What is the name of the wallet you want to open?: newWallet
Enter password: ***********

Making initial contact with kryptokrona.
Please wait, this sometimes can take a long time...


Your wallet SEKRuxqfDys1pfQ1omkHMVViY4sFh6My5Ff3HBY8XPp3cJBkEfD7romVyzKug3mb9NNR4A8kEjZxZ9CHUgWckBSpPfbxnWAQUGL has been successfully opened!

Your kryptokrona isn't fully synced yet!
Until you are fully synced, you won't be able to send transactions,
and your balance may be missing or incorrect!

Scanning through the blockchain to find any new transactions you received
whilst your wallet wasn't open.
Please wait, this may take some time.


Finished scanning blockchain!

 1	advanced                 List available advanced commands
 2	address                  Display your payment address
 3	balance                  Display how much XKR you have
 4	backup                   Backup your private keys and/or seed
 5	exit                     Exit and save your wallet
 6	help                     List this help message
 7	transfer                 Send XKR to someone

[XKR newWallet]: 
```

#### Viewing Wallet Address

To view a wallet's public address; at the menu, type `address` and press `enter`.

```
[XKR newWallet]: address
SEKRuxqfDys1pfQ1omkHMVViY4sFh6My5Ff3HBY8XPp3cJBkEfD7romVyzKug3mb9NNR4A8kEjZxZ9CHUgWckBSpPfbxnWAQUGL
[XKR newWallet]:
```

#### Exporting Keys

Each kryptokrona wallet is essentially, just a pair of keys (*View Key* and *Spend Key*) from which the public address is derived. It is **very** important to export these keys and back them up somewhere that is safe and secure (meaning somewhere reliable/permanent that no one else can access).

In the event of a lost or corrupted wallet file, computer crash, etc., the *View Key* and *Spend Key* are the only way to restore a wallet and recover the funds it holds.

**DO NOT SHARE IT WITH ANYONE**. **Anyone who has these can&#x20;*****access your funds*****&#x20;and has&#x20;*****complete control*****&#x20;over your wallet.**

To print your keys; at the menu type `backup` and press `enter`. The *View Key* and *Spend Key* will appear. Copy them and store them **safely and securely**.

```
[XKR newWallet]: backup
Enter password: **********
Private spend key: 41c834f7c26e12373e5c39a9c9b1f8beb665324ad0d098cabda1234567b5d30f
Private view key: df51e85dfa4fe48d0123475ec966124b1234c98abda6789060fe6d69b503490b
Mnemonic seed: truth neon vials ignore butterfly cactus soggy vibrate meant wizard awesome fountain axis skater itself egotistic pumpkins ultimate foaming fatal request sifting merger egotistic fierce
[XKR newWallet]:
```

#### Viewing Wallet Balance

To view your wallet's balance; at the menu, type `balance` and press `enter`:

```
[XKR newWallet]: balance
Available balance: 1000.00 XKR
Locked (unconfirmed) balance: 100.00 XKR
Total balance: 1100.00 XKR
[XKR newWallet]:
```

#### Sending kryptokrona Transactions

To send kryptokrona; at the xkrwallet menu:

* Type: `transfer` and press `enter`
* Type/paste the address you want to send the XKR to and press `enter`
* Type the amount of XKR you want to send (like `100`) and press `enter`
* Press `enter` to use the default fee of 0.1 XKR (or set it higher if you're sending a large amount of XKR)
* Enter the payment ID if the recipient has provided one. Check the [payment ID section](#payment-id) if you're not sure when/how to use it
* If you make a mistake or need to stop the transaction, type `cancel` at any time
* Confirm that the details are correct and enter `y`. If something is amiss, enter `n` and follow the steps again
* Enter your password

Depending on the amount you transfer, you may need to wait a while for confirmation. If you have had too many small incoming transactions, or the amount you wish to send is too large; either break up your transfer into several smaller amounts, or optimise your wallet.

**Optimizing your Wallet**

Fusion transactions take all your (small) incoming payments and combine them into bigger ones, allowing you to send huge sums at once!

To optimize your wallet, type `optimize` and press `enter`:

```
[XKR newWallet]: optimize
Attempting to optimize your wallet to allow you to send large amounts at once. 
This may take a very long time!
Do you want to proceed? (Y/n): y
Running optimization round 1...
Full optimization completed!
[XKR newWallet]: 
```

**Payment ID**

Because transactions on the kryptokrona blockchain are privatikkr, in some situations a payment ID is necessary for the recipient to be able to determine where the payment came from, for instance when depositing to an exchange or other service.

Note that typically, the service/recipient will generate and provide the required payment ID.

#### Exiting the Wallet

Wallets loaded into the x*krwallet* client must be synced with the blockchain in order to properly calculate balance, view transaction history, etc.

It is important to properly save the wallet data before exiting xk*rwallet* so that the synchronikkr data is not lost.

To save a wallet's data and exit; at the menu, type `exit` and press `enter`:

```
[XKR newWallet]: exit
Shutting down...
Saving wallet file...
Shutting down wallet interface...
Shutting down node connection...
Bye.
```

#### Restoring your Wallet

**Private Spend and View Keys**

To restore a wallet using spend and view keys; at the menu type `key_restore` and press `enter`, then follow the prompts:

```
 1	open                     Open a wallet already on your system
 2	create                   Create a new wallet
 3	seed_restore             Restore a wallet using a seed phrase of words
 4	key_restore              Restore a wallet using a view and spend key
 5	view_wallet              Import a view only wallet
 6	exit                     Exit the program

What would you like to do?: key_restore
Enter your private spend key: 41c834f7c26e12373e5c39a9c9b1f8beb665324ad0d098cabda1234567b5d30f
Enter your private view key: df51e85dfa4fe48d0123475ec966124b1234c98abda6789060fe6d69b503490b
What would you like to call your new wallet?: newWallet2
Give your new wallet a password: ***********
Confirm your new password: ***********
What height would you like to begin scanning your wallet from?

This can greatly speed up the initial wallet scanning process.

If you do not know the exact height, err on the side of caution so transactions do not get missed.

Hit enter for the sub-optimal default of zero: 748000

Making initial contact with kryptokrona.
Please wait, this sometimes can take a long time...


Your wallet SEKRuxqfDys1pfQ1omkHMVViY4sFh6My5Ff3HBY8XPp3cJBkEfD7romVyzKug3mb9NNR4A8kEjZxZ9CHUgWckBSpPfbxnWAQUGL has been successfully imported!

Your kryptokrona isn't fully synced yet!
Until you are fully synced, you won't be able to send transactions,
and your balance may be missing or incorrect!

Scanning through the blockchain to find transactions that belong to you.
Please wait, this will take some time.


Finished scanning blockchain!

 1	advanced                 List available advanced commands
 2	address                  Display your payment address
 3	balance                  Display how much XKR you have
 4	backup                   Backup your private keys and/or seed
 5	exit                     Exit and save your wallet
 6	help                     List this help message
 7	transfer                 Send XKR to someone

[XKR newWallet2]: 
```

**25 Word Mnemonic Seed**

To restore a wallet using spend and view keys; at the menu type `seed_restore` and press `enter`, then follow the prompts:

```
 1	open                     Open a wallet already on your system
 2	create                   Create a new wallet
 3	seed_restore             Restore a wallet using a seed phrase of words
 4	key_restore              Restore a wallet using a view and spend key
 5	view_wallet              Import a view only wallet
 6	exit                     Exit the program

What would you like to do?: seed_restore
Enter your mnemonic phrase (25 words): karate pause dozen exquisite lipstick among situated bobsled family giant dabbing diplomat governing hefty devoid scoop factual natural diet saucepan gauze jazz yeti always gauze
What would you like to call your new wallet?: test
Give your new wallet a password: ****
Confirm your new password: ****

What height would you like to begin scanning your wallet from?

This can greatly speed up the initial wallet scanning process.

If you do not know the exact height, err on the side of caution so transactions do not get missed.

Hit enter for the sub-optimal default of zero: 1713000

Your wallet SEKRuxm1BmQBTyz6tgpdpTdoq3dx3xaCE1VbuftusEEs7u1cRL6H8NnEpM3k8aM5EzaHBLJaDPZsgGBkGFqBU1KycZAAZSruffH has been successfully imported!

It looks like kryptokrona isn't open!

Ensure kryptokrona is open and has finished syncing. (It will often not respond when syncing)
If it's still not working, try restarting kryptokrona (or try a different remote node).
The daemon sometimes gets stuck.
Alternatively, perhaps kryptokrona can't communicate with any peers.

The wallet can't function fully until it can communicate with the network.

 1	try_again                Try to connect to the node again
 2	continue                 Continue to the wallet interface regardless
 3	swap_node                Specify a new daemon address/port to connect to
 4	exit                     Exit the program

What would you like to do?: 2

 1	advanced                 List available advanced commands
 2	address                  Display your payment address
 3	balance                  Display how much XKR you have
 4	backup                   Backup your private keys and/or seed
 5	exit                     Exit and save your wallet
 6	help                     List this help message
 7	transfer                 Send XKR to someone

[XKR test]: 
```

#### Other Commands

To see a list of additional commands not already covered; at the menu type `advanced` and press `enter`:

```
 1	advanced                 List available advanced commands
 2	address                  Display your payment address
 3	balance                  Display how much XKR you have
 4	backup                   Backup your private keys and/or seed
 5	exit                     Exit and save your wallet
 6	help                     List this help message
 7	transfer                 Send XKR to someone

[XKR newWallet]: advanced

 8	ab_add                   Add a person to your address book
 9	ab_delete                Delete a person in your address book
 10	ab_list                  List everyone in your address book
 11	ab_send                  Send XKR to someone in your address book
 12	change_password          Change your wallet password
 13	make_integrated_address  Make a combined address + payment ID
 14	incoming_transfers       Show incoming transfers
 15	list_transfers           Show all transfers
 16	optimize                 Optimize your wallet to send large amounts
 17	outgoing_transfers       Show outgoing transfers
 18	reset                    Recheck the chain from zero for transactions
 19	save                     Save your wallet state
 20	save_csv                 Save all wallet transactions to a CSV file
 21	send_all                 Send all your balance to someone
 22	status                   Display sync status and network hashrate
```

#### Help

To see the main menu of commands; type `help` and press `enter`:

```
[XKR newWallet]: help

 1	advanced                 List available advanced commands
 2	address                  Display your payment address
 3	balance                  Display how much XKR you have
 4	backup                   Backup your private keys and/or seed
 5	exit                     Exit and save your wallet
 6	help                     List this help message
 7	transfer                 Send XKR to someone
```


# Hugin Messenger

Hugin Messenger is an encrypted messaging service relayed by the XKR network nodes.

Here are some of it's features:

| 🔒 Private Messages                                                                                                                              | 📹 Voice & Video                                                                                                                         | 🗂 Unlimited Sharing                                                                                                                               |
| ------------------------------------------------------------------------------------------------------------------------------------------------ | ---------------------------------------------------------------------------------------------------------------------------------------- | -------------------------------------------------------------------------------------------------------------------------------------------------- |
| Every message is encrypted with leading asymmetric encryption, specifically NaCl. Read more about the encryption [here](https://nacl.cr.yp.to/). | Communicate with voice & video without the use of any intermediate server that process your data. Data is passed directly between peers. | Share without looking at the file size. This feature is powered by Bittorrent technology, which is the leading peer-to-peer file sharing protocol. |

| 🌐 Social Network                                                                                                                                 | 📡 Ungovernable                                                                                      | 🥰 Open-source                                                                                                |
| ------------------------------------------------------------------------------------------------------------------------------------------------- | ---------------------------------------------------------------------------------------------------- | ------------------------------------------------------------------------------------------------------------- |
| Hugin Boards, the next step in the evolution of social media. Instead of likes, you have tips, instead of censorship, you have freedom of speech! | Hugin cannot be taken down or be censored, and most importantly Hugin does not function without you! | Our source code is open for everyone to view and our community is open for anyone interested in contributing. |

### Downloads

#### Mobile (Android)

{% embed url="<https://play.google.com/store/apps/details?id=com.hugin>" %}

#### Desktop (macOS, Windows, Linux)

{% embed url="<https://github.com/kryptokrona/hugin-desktop/releases/latest>" %}
Download the .exe for Windows, .dmg for macOS & .AppImage for Linux.
{% endembed %}


# How to use Hugin Mobile

## Download the app

First, install the latest version of Hugin Messenger to your Android phone by going to the Play Store:

{% embed url="<https://play.google.com/store/apps/details?id=com.hugin>" %}

If you do not have access to the Google Play Store, then you can download the .apk file directly from our GitHub:

{% embed url="<https://github.com/kryptokrona/hugin-mobile/releases/latest>" %}
After downloading the .apk-file, open it from your File-browser to start the installation.
{% endembed %}

## Create an account

After installing the app, open it up and you will be greeted by this welcome screen:

<img src="https://2858262040-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fx7WCorBnqCP2oVt16bNf%2Fuploads%2Fgit-blob-480d5ba73cddca1f2a60c3e21211a59ec306ef3c%2FScreenshot_20220810-215508.png?alt=media" alt="" data-size="original">

As a first time user, tap "Create new account" and follow the instructions. If you have had an account before, you may choose the "Restore account" option instead.

If you created a new account, make sure to save the mnemonic seed at the step shown in the picture below:

![](https://2858262040-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fx7WCorBnqCP2oVt16bNf%2Fuploads%2FBhhGg9XwJCK2rWb59TS3%2FScreenshot_20220810-215524.png?alt=media\&token=b79c1ac0-c2c4-4e94-ac22-2245cc998ec0)

Your Hugin account is both your messaging account and a wallet for XKR. If you lose your device, the only way to restore your XKR balance is by restoring your account on another device with the mnemonic seed. **Store it somewhere safe!**

## **Funding your account**

After following the instructions for creating/restoring your account, you should be greeted by your profile page:

![](https://2858262040-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fx7WCorBnqCP2oVt16bNf%2Fuploads%2FXnVkFqxJZhJd7gCI6inz%2FScreenshot_20220810-215550.png?alt=media\&token=ac179acf-e979-4f52-9e07-19a1f6f2e9f7)

Your profile page contains your contact details and your wallet balance. If you want to give your contact details to someone, you can click the "Copy" button (see picture above) and send your address to someone. You may also click the background to reveal your QR-code (see picture below) that can be scanned by someone else in order to quickly add you.

![](https://2858262040-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fx7WCorBnqCP2oVt16bNf%2Fuploads%2FoKMg6PVEHmAeoiGsvJr3%2FScreenshot_20220810-220207.png?alt=media\&token=7f86d1a6-4259-415c-9cb3-87fa7d417248)

The XKR wallet in Hugin is used both as a small stake while sending messages, and as a way to transfer funds privately.

If you don't have any XKR, you can only receive messages, so make sure your account is always funded. You can get funds either by [mining](https://kryptokrona.org/en/mining), [buying](broken://pages/jqxT9vu7KmdNq8hCkhL0), or using the [faucet](https://kryptokrona.org/en/faucet). If you have 0 balance, you should be able to see the "Top up" button on your profile. Click it to go directly to the faucet, which will give you 5 XKR to start out with.

![](https://2858262040-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fx7WCorBnqCP2oVt16bNf%2Fuploads%2FAmyPZDxD2w1TnrXoDfDt%2FScreenshot_20220810-215648.png?alt=media\&token=f4efccc6-bf46-4a22-8bc1-359340ea1938)

Make sure your payment address is added to the address-field, solve the captcha and then hit 'Claim'. That should give you 5 free XKR. After \~90 seconds your funds is available in your account (go to your profile page to see your current balance).

![](https://2858262040-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fx7WCorBnqCP2oVt16bNf%2Fuploads%2FUpAliJNwRjoFg7O72B7G%2FScreenshot_20220810-225414.png?alt=media\&token=2518c3d5-c920-482c-8a4e-ba31218f528a)

As you can see in the picture above, the account has now been funded with 5 XKR and is now ready to be used!

## Adding contacts

To add a new chat contact, go to the private message page (the 💬 icon) and click the Add contact button in the top right corner (pictured below).

![](https://2858262040-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fx7WCorBnqCP2oVt16bNf%2Fuploads%2Fp9U0G5f5cHpQTo3d1qbo%2FScreenshot_20220810-215719.png?alt=media\&token=ee80f7c9-6501-4d04-b250-6df0a6d9d195)

Then you may either paste your contacts Address and message key into the form, or scan your friends QR code - and then enter a nickname for your contact.

![](https://2858262040-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fx7WCorBnqCP2oVt16bNf%2Fuploads%2FhV4qGTrJJg7lqtj3VRfH%2FScreenshot_20220810-215924.png?alt=media\&token=7133737a-b4bb-441f-960d-71b23eb18641)

Tap 'Continue' and the you will find yourself in an open chat with your new contact! Simply type a message and hit 'Send' to send them a message!

![](https://2858262040-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fx7WCorBnqCP2oVt16bNf%2Fuploads%2FFOx5Z0VKyqJhRPVjAhA8%2FScreenshot_20220810-215956.png?alt=media\&token=4d7b5687-4ab4-4240-9786-9eb644be522a)

## Sending payments

In addition to sending messages, you can also send payments to your contacts! Do this by going to the payment screen (the wallet icon). Then pick the contact you want to send funds to at the screen in the picture below:

![](https://2858262040-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fx7WCorBnqCP2oVt16bNf%2Fuploads%2FZAj9s44xuCw0RmBnLX63%2FScreenshot_20220810-221157.png?alt=media\&token=f2f4986d-efd1-4c5e-8346-79040a9d86cf)

Now just enter the amount you want to send, or pick "Send all" if you want to send your entire balance. Then confirm the transfer and it should be on it's way! 💸

## Using boards

Boards are public message boards where you can communicate with strangers and friends alike. Unlike with private messages in Hugin, boards messages are *not* encrypted!

To use boards in Hugin Mobile, click the double 💬 icon in the menu and you will se a screen that looks a little bit like this:

![](https://2858262040-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fx7WCorBnqCP2oVt16bNf%2Fuploads%2FG47uvZ8WMqFfNeV97fdR%2FScreenshot_20220810-220240.png?alt=media\&token=2e02f0da-ebed-4635-bfd2-6025a6ee788a)

This is the Home board and it collects message from all other boards. You may click a post to browse the board that it was posted in. You can also switch board, and add or remove subscriptions to boards by clicking the active board title (the blue "Home" in the top right corner in the picture above).

### Add/remove board subscriptions

![](https://2858262040-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fx7WCorBnqCP2oVt16bNf%2Fuploads%2FfCduzTzE6TlXYABLxOw7%2FScreenshot_20220810-220248.png?alt=media\&token=ca0dcc7d-6fe2-49f8-ae58-5ff74e1407c5)

The picture above is the My Boards screen, you can tap 'Edit' to remove subscriptions to boards, or add a new board subscription by typing it's name in the 'Add board'-field directly under the title and then hitting enter on the keyboard.

To create a brand new board, you do the exact same thing as above.

![](https://2858262040-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fx7WCorBnqCP2oVt16bNf%2Fuploads%2FGHiqfGt7MX6wU88btrPA%2FScreenshot_20220810-221122.png?alt=media\&token=a9fcd76b-4dbc-4380-b678-e0312e9aa34f)

In the picture above you can see how I have created a new board called 'My Cool Community' which I can then use to talk to my cool friends!

## That's all folks!

If you're having trouble or want to know more, you can come ask us anything in our [Discord server](https://chat.kryptokrona.se). Welcome!


# How to run a Hugin Node

This page will help you get started with starting a Hugin Node.

### What are Hugin Nodes?

Hugin Nodes are the cornerstone of the Hugin Messenger message distribution system. When two users who are online try to send a message to one another, the message will be sent through a P2P tunnel, powered by [HyperSwarm](https://github.com/holepunchto/hyperswarm).

However, when the recipient of a message is not online, the message is instead sent to the decentralized Hugin Node network. If the user has a registered a mobile device with the Hugin Master Nodes, the message will first be sent as a push notification to it's device. Additionally, the Hugin Nodes will store encrypted messages for 25h so they can be read once the user is back online. Messages sent to the nodes are always end-to-end encrypted.

To reward Hugin Node operators, each message sent from a client to the node network will also have a small proof-of-work segment appended to the message, that the receiving Hugin Node can send to the XKR mining network in order to garner a small XKR reward for each message relayed. This also provides the network with spam protection.

### How to install the Hugin Node software

1. Install nodejs <https://nodejs.org/en/download> (version 20+).
2. Install the Hugin Node software by running the following command in your terminal:

```
npm i hugin-node -g
```

### How to start the Hugin Node

Simply run this command in your terminal to start the node:

```
hugin-node
```

On the first start, you will be prompted to input your XKR address where rewards should be sent. After you've done so, the node should be up and running!

You can also use the following command:

```
hugin-node --debug
```

This will print some useful debug logs so you can make sure the node is getting connection to other nodes as well as clients.\
\
Thanks for helping the Hugin Messenger network!


# Kryptokrona node


# Deploy a Public Node (manually)

How to deploy a public node on Ubuntu Linux

**Have you ever considered what you can do for Kryptokrona?**

\
Well, as you may know public nodes are vital to the network as they allow for people to sync their wallets and new nodes to sync the blockchain.\
This guide will provide you with the tools and knowledge to run a public node 24/7 for 365 days for free, in fact you will be earning some XKR in the process.\
Intrigued? Well, read along as i detail the process below!

I made this work on MacOS but you could make this work on Ubuntu or Windows Aswell by installing a SSH client and connect to your AWS instance using that and start compiling..\
If that is the case then skip step 3-6 and connect to your free aws instance through your preferred SSH client using the .pem file that your instance generates.\
For windows perhaps use putty or the native tools, for ubuntu openSSH or putty.

This method requires registering a credit/debit card with AWS, they will charge 1 dollar to make sure your card isnt canceled but you will get that dollar back.

### **Creating AWS ubuntu Instance and Connecting to it via SSH**

***Skip step 1-4 if you already have access to a VPS or a machine to run the node on.***

1. Start by creating a AWS free tier account: <https://aws.amazon.com/?nc2=h_lg>
2. Deploy an instance in US east Virginia, choose ubuntu server 18.04 LTS and then t2 micro instance.
3. Make sure to save the .pem file in your home folder.
4. Once it is ready, choose connect and copy the example line
5. Open a terminal and type sudo before pasting the line, then hit enter.
6. If your ssh connection is successful then your are ready to install the node software but before you do that..
7. Install a handy tool called screen which will allow you to navigate between terminal windows in your vm by typing sudo apt install screen and follow the prompts.\
   (Quick guide on screen: <https://bit.ly/38NPG6v>)
8. Then install a handy tool for unzipping folders by typing sudo apt install unzip and hitting enter
9. Follow the steps below to start the node:

```
screen
```

```
wget https://github.com/kryptokrona/kryptokrona/releases/latest/kryptokrona-ubuntu-18.zip
```

```
unzip kryptokrona-ubuntu-18.zip
```

```
rm kryptokrona-ubuntu-18.zip
```

```
cd kryptokrona
```

```
./kryptokronad
```

Once fully synced open you can go ahead and close your node by hitting ctrl + c, now it is time to open port **11898**.\
Head on over to your AWS management console and click on security groups under network & security.\
Mark the first one of the security groups, click actions and then edit inbound rules.\
Add a custom TCP rule specifying port **11898** and allow it anywhere and then save.\
Repeat the process for outbound rules by clicking actions and edit outbound rules.\
Now unmark the first security group and mark the second one and repeat the same process as above.\
Then head back to your ssh terminal typ screen and hit enter and then start your node with:

```
./kryptokronad --enable-cors=* --enable-blockexplorer --rpc-bind-ip=0.0.0.0 --rpc-bind-port=11898
```

Please consider submitting your public node ip to our [GitHub-page](https://github.com/kryptokrona/kryptokrona-nodes-list) so others might find it.

Thats it, you are now running a public node within the XKR network and also chugging some hashes at about 100-700 h/s.

\
You can monitor your instance through AWS management console if you like but once you have set this up it will handle it self for the rest of the year.\
Once your year is up AWS will actually allow you to create a new account using the same credit card as the previous year to repeat the process so thats pretty sweet.

Copy and paste your XKR adress into the terminal and hit enter.\
you are now mining on your cloud server, hit ctrl + a and ctrl + d again to minimise the mining terminal window and type clear and hit enter after that.\
Then verify your running processes by typing ps -a and hit enter, you should then be seeing kryptokrona and miner running as separate processes.\
You can now go ahead and close the ssh terminal window.

```
./miner
```

```
screen
```

If it answers with the current block count then your all good to start mining!\
Head on back to the SSH terminal window and copy and paste these commands:

```
curl -d '{"jsonrpc":"2.0", "method":"getblockcount", "params":{}}' http://0.0.0.0:11898/json_rpc
```

Open a terminal on your local machine and check if your node is responding (replace 0.0.0.0 with your instance ip)

Let your node sync.. then press ctrl + a and ctrl + d in rapid succession to mimize the node terminal window.


# Deploy node with Docker

With this guide you will learn how to deploy a public node quickly and easily with Docker.

## Get the script

First we need to get the shell script from the Kryptokrona repository. Go to <https://github.com/kryptokrona/kryptokrona/tree/master> and to the directory called deploy. Inside this directory you will find a `setup-node.sh` file. Download this file to your computer. Now we just have to modify this script with our own constant values. Open the file up in your favorite text editor.

```
DOMAIN="node.c1phx.com"
EMAIL="c1phx@proton.me"
```

Change these values to your own values and save the file.

## Upload script to VPS

Now we need to upload this to the VPS. We are going to go through how to set it up on a Ubuntu VPS server. You can either copy all the contents of this file and login to your VPS and create this file with nano/vim and save it as `setup-node.sh` or send it through scp.

```
scp ~/Downloads/setup-node.sh ubuntu@ip-address:/home/ubuntu/setup-node.sh
```

This will copy the file to the home directory of the user ubuntu. Now we just have to login to the VPS and set the executable permissions.

```
ssh ubuntu@ip-address
chmod +x setup.node.sh
```

## Run script

Now we can run the file and it will take care of everything for us.

```
./setup-node.sh
```

This process will take a while since it will build the Kryptokrona core to a Docker Image.


# Deploy a Hugin Full Node with Docker

This tutorial will guide you through the process of deploying a "Hugin Full Node", that is, a publically available Kryptokrona node bundled with Hugin API for extra functionality

## Setup

Let’s head over to the repository <https://github.com/kryptokrona/kryptokrona> and download a latest release: <https://github.com/kryptokrona/kryptokrona/releases>

Unzip the directory to a directory such as `~/Projects` then use the terminal to navigate to the directory of kryptokrona-`<version>`.

## Installation

First install Ansible locally.

### Mac using brew package manager:

* `brew install ansible`
* `brew install esolitos/ipa/sshpass`

### Ubuntu/Debian

```
sudo apt update
sudo apt install software-properties-common python3-jmespath
sudo add-apt-repository --yes --update ppa:ansible/ansible
sudo apt install ansible
sudo apt install sshpass
```

### Windows using WSL

Since Ansible can not run natively on Windows we need to use the subsystem for Linux in Windows. Please check out this tutorial on how to get it started: <https://docs.ansible.com/ansible/latest/user\\_guide/windows\\_faq.html#windows-faq-ansible>

## Verify

Then we need to run the following to verify that our installation was successful:

`ansible --version`

## Configuration

So now that we have Ansible up and running on our OS we will start looking into what kind of configuration we need to do in order for us to provision our VPS with Kryptokrona.

If you have never heard what provisioning are it simply means “providing” or making something available. What Ansible does is to setup Infrastructure as Code (IaC) that we define what we need to install and what needs to be configured in code and thus we do not need to manually set this up and do this everytime we make a change or add something new. It does everything for us in one command when running it. This can be a huge time and energy saver. If something would have happen of a server or infrastructure we could just spin up a new environment very easily.

So let’s start by going into the ansible directory and open up the `prod.inventory` file (you can of course use your favorite text editor instead of Vim):

```
[vps]
<ip address/hostname here>
```

Now we see a block of \[vps] and under it are the domain name followed by the `letsencrypt_email`, `domain_name` on the same row. This is all the hosts we are going to use. In this case we are just going to provision to one VPS. You could put the IP address there instead of `n1.vxo.nu` and remove additional lines if you don't use multiple VPS instances.

If we would like to provision to two or multiple VPS we could just copy the first one and change the ip/hostname and Ansible would pick them all up and setup everything on those VPS as well.

So change `n1.xkr.nu` to your ip/hostname and the `letencrypt_email` and the `domain_name` and remove the second line `n2.xkr.nu`.

Please bare in mind that fix the DNS settings *first* for this domain name and point to the VPS IP address a couple of hours before running this otherwise the certificate would not go through if it can not find that the DNS points to that domain name.

Also update `exporter_version` to the latest release over at <https://github.com/prometheus/node\\_exporter/releases/>

So now save the file and we will start looking at `provision_vps.yml` file.

### Ansible Vault

Before we start with the provisioning we need to edit the file in `ansible/group_vars/vps.yml` with your config. This information will be encrypted later. Leave out the alert configs according to the comments if you don't want to have the alert system in place.

Then we need to encrypt the file:

* `ansible-vault encrypt ./group_vars/vps.yml`

Then save and put a password that you NEED to remember.

Then we need to use that password we set for the file itself and save that in a file on our host system. Do that by:

* `vim ~/kryptokrona.pwd`

Then add that same password inside this file that we set for the `vps.yml` file and we will use this file to run the playbook.

Then save and exit:

* `:wq`

Then open up the file `ansible.sh` and edit it and edit the line ssh-copy-id with your <root@domain.com> and add an additional line with the second or more VPS instances. Just remember that we need to be ROOT to be able to run this. So don't use another user.

So now we can start provisioning by running our shell script:

* `sudo chmod +x ansible.sh`
* `./ansible.sh`

## Common issues

#### NGINX configuration breaks

**Problem:** If you made some change in NGINX configuration and it breaks during setup, the next time it will not always be able to update it so it works again.\
**Solution:** SSH into the machine and change the configuration manually and restart the NGINX server. Check the logs with `journalctl -xe` if you don't find the issue right away.


# Run a Node on a Raspberry Pi

This guide goes into detail on how to run a XKR node on a Raspberry Pi

![](https://2858262040-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fx7WCorBnqCP2oVt16bNf%2Fuploads%2FT2EOLOOsirOoSdlm1caW%2Fpi-plug-in.gif?alt=media\&token=2cf351a0-c764-4fd1-92f3-6cba5bdbb374)

***For Raspberry Pi 3B+:***<br>

`wget https://kryptokrona.se/downloads/xkr-rpi3.zip`\
\
`unzip kryptokrona-rpi-3b.zip`<br>

\
***For Raspberry Pi 4B:***

`wget https://kryptokrona.se/downloads/xkr-rpi-4b.zip`\
\
`unzip kryptokrona-rpi-4b.zip`

When you have unzipped the files, enter the directory where the kryptokrona binary was unzipped to and run the following to start your node:

`./kryptokrona --enable-cors=* --enable-blockexplorer --rpc-bind-ip=0.0.0.0 --rpc-bind-port=11898`


# How to configure the node?

Run kryptokronad with arg `--help` will print all options.

Kryptokrona can start with these options by command line args, or use `-c` followed a json file for configuration.

The option in config file will unwrap the front `--`, for example:

```json
// the config file
{
    "db-max-open-files": 125,
    "db-read-buffer-size": 128,
    "db-threads": 4,
    "db-write-buffer-size": 256
}
```

If you want to check the default options, use `--dump-config`.


# Node bootstrap

If you've just set up your node, it's a good idea to use our bootstrap to make the initial sync a lot faster!

Starting in your home folder (cd \~), the first order of business is to download our bootstrap with this command:

```
wget https://xkrbootstrap.vm-app.cloud.cbh.kth.se/latest.7z
```

After it has downloaded, use this command to extract the file:

```
// apt install 7z (if you don't have it installed)
7z x latest.7z
```

Then just start the node, which you can read up on how to do in the other guides! Thanks for hosting a node, and don't forget to add it to <https://github.com/kryptokrona/kryptokrona-public-nodes/> if you want to make it public in our apps!


# Mining


# p2pool

Mine Kryptokrona on the decentralized p2pool — no pool operator, paid straight to your wallet.

<figure><img src="https://2858262040-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fx7WCorBnqCP2oVt16bNf%2Fuploads%2FZQnpDTgU2uxbIzwz7KIV%2Fp2pool.png?alt=media&amp;token=d44e7982-5abd-47de-962c-7a6edf61982c" alt="" width="375"><figcaption></figcaption></figure>

> ⚠️ **Alpha software.** Kryptokrona p2pool is brand new and still being tested. Great for trying out and helping the network — just don't rely on it for anything critical yet.

## What is p2pool?

**p2pool is a mining pool with no operator.** Instead of connecting to someone else's pool server, you run a tiny pool of your own on your computer, next to your miner. All the p2pool users around the world are linked together into one shared network (a "sidechain"), so you get the **steady, regular payouts of a big pool** — but with none of the downsides:

* 🪙 **You get paid directly to your own wallet**, automatically, every time the pool finds a block. There are no withdrawals, no minimum payout, and nobody ever holds your coins.
* 🔒 **No trust required.** There's no operator who could disappear, get hacked, or run off with the rewards.
* 🧾 **No registration, no accounts, no website login.**
* 💸 **Basically zero fees.**

The trade-off is that you run one small extra program (p2pool) yourself. This guide walks you through it step by step.

### p2pool vs. a normal pool

|                       | Normal pool                           | p2pool                                  |
| --------------------- | ------------------------------------- | --------------------------------------- |
| Who holds your coins? | The pool operator, until you withdraw | **Nobody — paid straight to you**       |
| Payout                | Manual/minimum withdrawal             | **Automatic, on every block**           |
| Fee                   | Usually 0.1%–2%                       | **\~0%**                                |
| Trust                 | You trust the operator                | **Trustless**                           |
| Setup                 | Point miner at a URL                  | Run a small program + point miner at it |

## What you'll need

1. A **Kryptokrona wallet address** (starts with `SEKR…`).
2. A **Kryptokrona node** to connect to (your own, or a public one — see below).
3. The **p2pool** program.
4. A **miner** — we recommend [XMRig](/mining/xmrig-guide).

Don't have a wallet yet? Follow [Making a Kryptokrona Wallet](/guides/wallets/making-a-wallet) and **save your mnemonic seed** — that's the only way to recover your coins.

## Step-by-step guide

### 1. Get a Kryptokrona node

p2pool needs to talk to a Kryptokrona node (the `kryptokronad` daemon). You have two options:

* **Run your own node** (recommended — most reliable, and the whole point of decentralization). See [Deploy a Public Node](/node/run-a-public-node) or [Deploy a node with Docker](/node/deploy-your-own-node). Once it's synced, it listens on port `11898`.
* **Use a public node** (easiest — nothing to sync). Pick one from [Using Remote Nodes](https://github.com/kryptokrona/kryptokrona-docs/tree/master/guides/wallets/Using-Remote-Nodes.md) and note its address and RPC port. Just replace `127.0.0.1 --rpc-port 11898` in the commands below with the public node's address and port.

### 2. Download p2pool

Grab the file for your operating system from the latest release:

👉 [**github.com/kryptokrona/p2pool/releases**](https://github.com/kryptokrona/p2pool/releases)

| Your system                  | File to download             |
| ---------------------------- | ---------------------------- |
| Windows                      | `p2pool-msys2-gcc.exe`       |
| macOS (Apple Silicon, M1–M4) | `p2pool-macos-aarch64`       |
| macOS (Intel)                | `p2pool-macos`               |
| Linux                        | `p2pool-ubuntu-24.04-gcc-14` |

Put it in its own folder. On macOS/Linux, make it runnable first:

```bash
chmod +x p2pool-*
```

### 3. Start p2pool

Open a terminal (or Command Prompt on Windows) in that folder and run the command below, replacing `YOUR_WALLET_ADDRESS` with your `SEKR…` address:

**Windows:**

```
p2pool-msys2-gcc.exe --host 127.0.0.1 --rpc-port 11898 --wallet YOUR_WALLET_ADDRESS --stratum 0.0.0.0:3333 --p2p 0.0.0.0:37889
```

**macOS / Linux:**

```bash
./p2pool-* --host 127.0.0.1 --rpc-port 11898 --wallet YOUR_WALLET_ADDRESS --stratum 0.0.0.0:3333 --p2p 0.0.0.0:37889
```

When you see **`SideChain SYNCHRONIZED`** and it starts logging `ping is … ms`, p2pool is connected and ready. Leave this window open — it needs to keep running while you mine.

> 💡 **Small miner (a laptop or single PC)?** Add `--mini` (or `--nano` for very low hashrate) to the command. These are lighter sidechains that find shares more often, so your payouts are smoother.

### 4. Point your miner at p2pool

Mining to p2pool is just like [mining with XMRig](/mining/xmrig-guide) — the **only difference is the pool address**. Instead of a pool URL, point XMRig at your own p2pool:

* **URL / pool:** `127.0.0.1:3333`
* **Wallet / user:** anything you like (e.g. `x`) — it's only a label. **p2pool pays out to the address you set in step 3, not the one in your miner.**
* **TLS/SSL:** off

If you're reusing an existing Kryptokrona XMRig `config.json`, just change the `"url"` to `"127.0.0.1:3333"` and start the miner as usual.

### 5. That's it — you're mining! 🎉

Keep **both** the p2pool window and your miner running. As the network finds blocks, your share of the reward lands **directly in your wallet** — no action needed. You can watch p2pool's window to see shares being found.

## Tips

* **Keep it running.** You only earn while both p2pool and your miner are up.
* **Open port `37889`** on your router (forward it to your PC) for better connectivity with other p2pool nodes. It works without this, but connects to more peers with it.
* **One p2pool per computer.** Point all of a machine's miners at that one p2pool.

## Need help?

Something not working? Come ask in our [Discord](https://chat.kryptokrona.se/) — the community is happy to help.

Happy (decentralized) mining! 🌀


# Get started with mining

Step by step guide to get started with mining

<figure><img src="https://2858262040-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fx7WCorBnqCP2oVt16bNf%2Fuploads%2FQQVvGZ2OkwUpDsyZxzaT%2Fxmrig-600x467.png?alt=media&amp;token=1900698f-998e-49bf-a9b0-cea87bbd69e5" alt=""><figcaption><p>XMRig mining kryptokrona on Windows</p></figcaption></figure>

So you want to start mining XKR? Great! This is the place to start.

## Download

First order of business is to download the mining software, although there are many alternatives to choose between, we recommend XMRig.

Download XMRig here:

[Windows](https://github.com/xmrig/xmrig/releases/download/v5.11.1/xmrig-5.11.1-msvc-cuda10_1-win64.zip)

[Linux](https://github.com/xmrig/xmrig/releases/download/v5.11.1/xmrig-5.11.1-xenial-x64.tar.gz)

***Note to Windows users***\
*Your antivirus software may react to the mining software, this is because viruses often download mining software to unknowing peoples PC's, hijacking their computer for unwanted mining. Just add a rule in your anti virus software to prevent this.* [*Here's a guide*](https://www.nicehash.com/blog/post/exclude-nicehash-miner-from-windows-defender-immediately)*.*

## Configure

You need a config-file for the miner in order to mine. Generate one [here](https://www.kryptokrona.org/en/mining).

Don’t have a XKR address? Get one [here](https://explorer.kryptokrona.se/tools.html) (don't forget to save your mnemoic seed so you can access your funds with a wallet).

After you've generated your config.json file, place it into your XMRig folder.

<figure><img src="https://2858262040-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fx7WCorBnqCP2oVt16bNf%2Fuploads%2FMUpSEFO2LzEThembCWwp%2Fcfgmap-600x433.png?alt=media&amp;token=5da8fdc0-291e-4b3a-9742-260aac0414f1" alt=""><figcaption><p>Config file properly placed inside the XMRig-folder.</p></figcaption></figure>

## Start the miner

Simply open **start** to start mining.

<figure><img src="https://2858262040-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fx7WCorBnqCP2oVt16bNf%2Fuploads%2FDUb8Nz8yddh6auzAmG7v%2Fstartmap-600x447.png?alt=media&amp;token=044632a6-c33d-4ee6-b58d-53deaebc2217" alt=""><figcaption></figcaption></figure>

Congratulations!\
You’re mining!
--------------

Sit back and enjoy! Your computer is now generating XKR for you.

Got any issues? Visit our support-channel on [Discord](https://chat.kryptokrona.se/).

You can keep track on your mining progress from the pool's website.

Go to [MiningPoolStats.com ](https://miningpoolstats.stream/kryptokrona)to check out the statistics of the different mining pools and get access to their websites.

Happy mining!


# Solo-mining Kryptokrona

Solo-mining Kryptokrona means that you, alone, try to find the next block.\
**It is extremely hard, and not recommended** - try our [other guides](https://github.com/kryptokrona/kryptokrona-docs/blob/master/docs/guides/Mining/README.md) if you want a more steady flow of XKR.\
Solo-mining is limited to *only your CPU*.

If you're sure you want to solo mine, let's continue.

### Setup and Running

Make sure you have `Kryptokrona` and `miner`, both can be found in [the latest release](https://github.com/kryptokrona/kryptokrona/releases).

*Note*: If they aren't there, you'll have to compile it yourself:

* [Windows](https://kryptokrona.se/Kryptokrona-win.zip)
* [Linux](https://kryptokrona.se/Kryptokrona-linux.zip)
* [OSX](https://kryptokrona.se/Kryptokrona-mac.zip)

Ensure **`Kryptokrona` is running and fully synced, or find a public node to use here**.

Go to your folder that has `miner.exe` in it and start a cmd prompt.

* This can easily be done by moving to the `Kryptokrona` directory in Windows Explorer, then typing `cmd` in the search bar and hitting enter.

In Linux, you may be able to right click on your directory and "Open in" Terminal.

When it opens, type:\
`miner --address SEKR.. --threads 4 --scan-time 1 --log-level 3`

If you're using a remote node, you can add the following flag:

```
--daemon-address url.to.node:11898
```

Repace `SEKR..` with your Kryptokrona public address.\
We recommend setting the `--threads` option to half of how many you have. So if you have 12 threads in your CPU, set it to `6`.

Example:

```bash
miner --address  SEKReX2avthCKT4YUUKV3jgZ1Hderk9XbRciqp8vHVPoDSb9nA1dCV86Jia3TkD4jWgfxeh1AEYV3DKEAesSb7mSAvNqf6cB6kR --threads 4 --scan-time 1 --log-level 3
```

Congratulations, you are now solo mining Kryptokrona from your CPU.

**Notes**

* `Kryptokrona` *must* stay running for the miner to mine Kryptokrona, unless you use a remote node.
* Be patient. Finding a block may happen within the first few hours of mining. It also may take a week. Or it may never happen.
* If you accidently close out `Kryptokrona` you can restart the miner by hitting Ctrl+C on your keyboard, then re-entering the miner command given above.
* You may have to adjust the amount of threads based on your PC's capabilities(half of how many your CPU has is recommended).


# Mining with a SBC

The following guide will show you how to compile a CPU miner (XMRig) for SBCs like the Raspberry Pi.

If you're using a RPi3 or RPi3B+, check out [this guide](https://github.com/kryptokrona/kryptokrona-docs/blob/master/docs/guides/Optimizing-RPi-TurtleCoin-Mining/README.md) for a more optimized setup.

What are the benefits of compiling XMRig from scratch?

* You'll have the most up-to-date version of XMRig
* You can optimize XMRig for specific SBCs (improves hash rate)
* You can compile XMRig with different releases of GCC (may improve hash rate)
* It's possible to disable certain features of XMRig ([more info](https://github.com/xmrig/xmrig/wiki/Ubuntu-Build#additional-cmake-options))

### Setup

First we want to make sure your SBC's software is up to date:

```
sudo apt-get update && sudo apt-get upgrade
```

After that's done, we're going to install some tools that are important for the process:

```
sudo apt-get install git build-essential cmake make libuv1-dev libmicrohttpd-dev gcc g++ automake autoconf pkg-config libcurl4-openssl-dev libjansson-dev libssl-dev libgmp-dev
```

### Compiling XMRig

At this step we'll obtain the latest binaries of XMRig and create a directory called `build`:

```bash
cd ~
git clone https://github.com/xmrig/xmrig.git
cd xmrig && mkdir build && cd build
```

Now we specify the build flags to optimize XMRig for your SBC in particular. You'll have to **only choose one of these**:

* for any SBC:

```
cmake ..
```

* for the Raspberry Pi 2:

```bash
cmake .. -DCMAKE_C_FLAGS="-mcpu=cortex-a7 -mtune=cortex-a7" -DCMAKE_CXX_FLAGS="-mcpu=cortex-a7 -mtune=cortex-a7"
```

* for the Raspberry Pi 2 if the command above doesn't work:

```bash
cmake .. -DARM_TARGET=7
```

* for the Raspberry Pi 3:

```bash
cmake .. -DCMAKE_C_FLAGS="-mcpu=cortex-a53 -mtune=cortex-a53" -DCMAKE_CXX_FLAGS="-mcpu=cortex-a53 -mtune=cortex-a53"
```

* for the Raspberry Pi 4:

```bash
cmake .. -DCMAKE_C_FLAGS="-mcpu=cortex-a72 -mtune=cortex-a72" -DCMAKE_CXX_FLAGS="-mcpu=cortex-a72 -mtune=cortex-a72"
```

* for the Asus Tinker Board:

```bash
cmake .. -DCMAKE_C_FLAGS="-march=armv7-a" -DCMAKE_CXX_FLAGS="-march=armv7-a"
```

You may find the right flags for your board [here](https://gist.github.com/fm4dd/c663217935dc17f0fc73c9c81b0aa845). I was only able to test these on a Raspberry Pi 2 and the Asus Tinker Board. Also, this guide is not perfect, so **feel free to add/edit flags or devices**!

To finish the compilation type:

```
make
```

To speed up the compilation you can add `-j [amount_of_CPU_cores]`. On a Raspberry Pi 2/3 this would be `make -j 4` for example.

### Configuring and Running XMRig

First we need to copy `config.json` to the same directory the XMRig executable is located:

```
cp ~/xmrig/src/config.json config.json
```

Now we have to edit the configuration file properly. In this guide we'll be using `nano`, but any other text editor should also work fine:

```
nano config.json
```

Your terminal should display the contents of `config.json`.

* In order to mine Kryptokrona, we tell XMRig what algorithm you want to mine. Look out for the `"algo":` setting and change it to `"algo": "cryptonight-pico/trtl",`
* In place of `"url": "donate.v2.xmrig.com:3333",` you'll need to choose a pool to mine towards. Make sure to choose the right port. You can learn more about choosing a pool [here](https://github.com/kryptokrona/kryptokrona-docs/blob/master/docs/guides/Pools/README.md).
* Instead of `"user": "YOUR_WALLET_ADDRESS",` simply paste your Kryptokrona wallet address.

  If you don't have one yet, you can find out how to create a wallet [here](https://github.com/kryptokrona/kryptokrona-docs/blob/master/docs/wallets/Making-a-Wallet/README.md).

When you're done with that, press:

`CTRL + O` to save, confirm with `Enter`. And after that, hit `CTRL + X` to close the file.

Then start the miner:

```
./xmrig
```

After entering this command, the miner will start scanning your hardware and begin to mine.

Congratulations! You did it! :)


# Mining Intro

Mining is essentially the process of using your computer to help verify and secure a cryptocurrency network, in our case, it is the Kryptokrona network. By doing this, you will be rewarded with some Kryptokrona.

If you want to learn about cryptocurrencies, mining is a great place to start!

***

**Please note:** Unfortunately because of some bad people using mining software in malware, most antivirus software will detect the programs below as unsafe.

It is **likely** you will need to add exceptions and exclusions to your antivirus software in order to make things work properly.

Unless you know what you are doing, please ***only*** download from the links below.

***

There are currently a few different ways in which you can start mining Kryptokrona:

### Desktop Mining

#### [XMRig](https://github.com/xmrig/xmrig)

XMRig comes as a CPU and GPU miner separately and run two separate instances in your computer. One will use your CPU and the other one will use your GPU.

Please follow [this guide](https://github.com/kryptokrona/kryptokrona-docs/blob/master/docs/guides/XMRIG-Guide/README.md) to start mining Kryptokrona with XMRig.

#### Solo Mining

Solo Mining is where you, alone, try to solve a block. It is extremely difficult and not recommended. If you'd like to give it a hand regardless see [this guide](https://github.com/kryptokrona/kryptokrona-docs/blob/master/docs/guides/CPU-Solo-Mining/README.md)

### SBC/Raspberry Pi Mining

Please follow [this guide](https://github.com/kryptokrona/kryptokrona-docs/blob/master/docs/guides/Mining-with-SBC/README.md) to mine with a SBC/Rasperry Pi.

### Pools

You may view more info on mining pools [here](https://github.com/kryptokrona/kryptokrona-docs/blob/master/docs/guides/Pools/README.md).

### Have Questions or Need Help?

Check out our [Discord](http://chat.kryptokrona.se) to get in touch.


# Notes

Looking for a more general SBC setup guide? Check out [this guide](https://github.com/kryptokrona/kryptokrona-docs/blob/master/docs/guides/Mining-with-SBC/README.md).

**Overview**

To maximize your hashrate, it is very important that you select a 64-bit OS image, a quality miner and the most current compiler that you can.

**OS Image**

The 64-bit Ubuntu Server for Raspberry Pi3 is a good choice:

<http://cdimage.ubuntu.com/releases/18.04/release/ubuntu-18.04.3-preinstalled-server-arm64+raspi3.img.xz>

You will need to write this image to an SD card with a utility such as [Etcher](https://www.balena.io/etcher). Once your OS is written, insert your SD Card and boot your Pi.

Once you've got it booted, you'll be asked for a username and password. These are both `ubuntu`.

Once you've logged in, you'll be asked to change the password. For the current password, enter `ubuntu` again. Then, enter a new password, and confirm it.

**Get the Latest Compiler**

You will need to edit your sources.list file and add the debian testing repository in order to install gcc-8 and g++-8 on your system:

```
sudo nano /etc/apt/sources.list
```

Add this line to the end of the file:

```
deb http://ftp.us.debian.org/debian testing main contrib non-free
```

Then save it with `Ctrl-x` and then the following:

```
sudo apt-get update
sudo apt-get install gcc-8 g++-8
```

**Download Compile, and Configure Your Miner**

Now you need to install the required dependencies and the latest release of the xmrig miner and compile it with gcc-8.

```bash
sudo apt-get install git build-essential cmake libuv1-dev libmicrohttpd-dev libssl-dev
git clone https://github.com/xmrig/xmrig.git
cd xmrig
sudo mkdir build
cd build
sudo cmake .. -DCMAKE_C_COMPILER=gcc-8 -DCMAKE_CXX_COMPILER=g++-8
sudo make -j4
```

Compiling the miner could take several minutes to complete. When your miner is ready you need to create a configuration file with your Kryptokrona settings. Navigate to your home directory and create a file named config.json.xkr.

```bash
cd ~
sudo nano config.json.xkr
```

Populate your configuration file with something similar to the code below. Make sure that `url`, `user`, and `pass` are populated with the your own unique and proper values.

```json
{
    "algo": "cryptonight-pico/trtl",
    "background": false,
    "colors": true,
    "retries": 5,
    "retry-pause": 5,
    "donate-level": 1,
    "syslog": false,
    "log-file": null,
    "print-time": 60,
    "av": 0,
    "safe": false,
    "max-cpu-usage": 100,
    "cpu-priority": null,
    "threads": null,
    "pools": [
        {
            "url": "YOUR_POOL_URL_PLUS_PORT_GOES_HERE",
            "user": "YOUR_TURTLE_ADDRESS_GOES_HERE",
            "pass": "YOUR_MINER_NAME_GOES_HERE",
            "keepalive": true,
            "nicehash": false,
            "variant": -1
        }
    ]
}
```

Create a separate miner start script so that you can easily start the miner and invoke the proper cofiguration file with a single command. I like to name it "minexkr".

```
sudo nano minexkr
```

Place the following code into the minexkr file:

```bash
#!/bin/bash
sudo sysctl -w vm.nr_hugepages=8
~/xmrig/build/xmrig --config=config.json.trtl
```

Make the file executable as a script:

```
sudo chmod +x minexkr
```

Now you can start the miner using the start script:

```
./minexkr
```

**Conclusion**

Happy mining and make sure to support small pools and keep Kryptokrona mining decentralized.


# Mining Pools

Unless you want to [solo mine](https://github.com/kryptokrona/kryptokrona-docs/blob/master/docs/guides/CPU-Solo-Mining/README.md), which is unfeasible for many people, you will need a pool to mine towards. Make sure to choose the one closest to you!

To view a list of pools, check out [the explorer](https://explorer.kryptokrona.se/pools.html)

### Pinging a Pool

The best pool is the one that is closest to you; this can easily be determined by *pinging* the pool through your terminal

Open up your terminal; look for "Command Prompt" or "Terminal" in your Start/Applications menu

When open, enter this command: `ping <pool url>`, replacing `<pool url>` with the address of your pool.

For example, if I was mining at gota.kryptokrona.se, then the pool url (what you put into your miner) is `geo.kryptokrona.se`. Thus, I would enter:

```
ping geo.kryptokrona.se
```

The port number is not necessary

Analyze the number before the `ms`; this is how long it takes for you to send a receive a packet from the pool. The *lower it is, the better*.

You may need to press Ctrl + C on your keyboard to exit the command.

### Definition of Fees

Rather simple; the pool operator will take a percentage of the reward of the block found for himself.

Example-

* the fee is 0.1%
* the block reward is 30000 XKR
* 30000 x 0.1% = 30

Therefore, the pool operator will take 30 XKR for himself.

### Definition of Different Types of Methods

These will be found on the pool website; if not specified, it is most likely proportional.

#### Proportional (share-based)

A proportional pool carries no risk to the pool operator as miners are simply paid out when a block is found. No blocks, no payout!

With a proportional pool the risk is all on the miners if it takes longer than expected to find a block then the miners earn less. On the flip side, if the pool is lucky (they will all average out the same eventually) the miners get more.

Example-

* A block is found after 100,000 shares
* You submitted 1,000 of those shares (you have 1% of the pool's total hash power)
* There’s 30000 XKR per block

Quite simply you will get 1% of the block = 300 XKR.

Now if the pool has a bad round (a round is the time taken to find a block) and it takes 200,000 shares to find a block (twice as long) and you have submitted 2,000 shares (as you’ve been mining twice as long), you still only get 1% of the block = 300 XKR

This can also work in the miners favor too, as if it takes half the time (50,000 shares) to find a block and you submitted only 500 shares - again 1% - 300 XKR.

Basically, you always get a percentage of the block and you win/lose depending on the “luck” of the pool.

The drawbacks to a proportional pool are that there is often a fee, although some pool operators rely on donations only, and you will have to bear the variance of the block times and luck unlike a PPLNS pool.

Also they are susceptible to “pool hoppers” where PPLNS pools are not.

#### PPLNS (Pay Per Last *n* Shares)

PPLNS does not pay out per block found, rather it pays based on the number of shares you last submitted, and helps to dissuade pool hoppers.

How it works is,

* you start mining with a PPLNS pool.
* Rather than paying you out based on the number of shares you submitted since you started mining/the last block was found, it will pay depending on how many shares you submitted in a period of time, called the window, which is an estimate of the time in which the pool in question finds a block.
* So, after you start mining, it will take a few hours for you to earn your normal earnings - and since the effect of pool hoppers is lessened, you may make comparatively more than other methods.

Basically, you get paid based on

* the number of shares you submitted (how good what you're mining with is)
* and how long you have been mining.


# Mining with XMRig

XMRig uses separate miners for CPU and GPU, you need to download a CPU and GPU miner separately and run two separate instances on your computer.

### Downloading and Installing for Windows

XMRig has separate miners for CPU and GPU. You can download them from here:

* [XMRig CPU Miner](https://github.com/xmrig/xmrig/releases)
* [XMRig GPU NVIDIA Miner](https://github.com/xmrig/xmrig-nvidia/releases)
* [XMRig GPU AMD Miner](https://github.com/xmrig/xmrig-amd/releases)

**Note:** You will need to download and run two separate instances if you want to mine with your GPU and CPU at the same time.

### Downloading and Installing for Linux

You can directly use the pre-built binaries for XMRig CPU. Download the `xmrig-*-xenial-amd64.tar.gz` file [here](https://github.com/xmrig/xmrig/releases).\
Run the file using `./xmrig`.

XMRig needs to be compiled for NVIDIA and AMD. Instructions for compiling are linked below(Ubuntu):

* [XMRig GPU NVIDIA Miner](https://github.com/xmrig/xmrig-nvidia/wiki/Ubuntu-Build)
* [XMRig GPU AMD Miner](https://github.com/xmrig/xmrig-amd/wiki/Ubuntu-Build)
* [XMRig CPU Miner](https://github.com/xmrig/xmrig/wiki/Build) (instructions for multiple platforms)

### Downloading and Installing for Mac

Needs to be compiled. Instructions [here](https://github.com/xmrig/xmrig/wiki/OS-X-Build).

### XMRig Setup and Configuration

#### CPU XMRig Configuration

1. Unzip the file and extract the files into a new folder (Make sure your anti-virus doesn't delete the files)
2. Open the `config.json` file with Notepad
3. Find and change the following lines:

* `"algo: "cryptonight-pico/trtl"`
* `"url: "[pool address]"`
* `"user: "[wallet address]"`
* Instead of `[wallet address]`, simply paste your Kryptokrona wallet's address. Make sure to keep the `"`!
  * If you don't have one yet, you can find out how to create a wallet [here](https://github.com/kryptokrona/kryptokrona-docs/blob/master/docs/wallets/Making-a-Wallet/README.md)
* In place of `[pool address]`, you'll need to choose a pool to mine towards. You can learn more about them [here](https://github.com/kryptokrona/kryptokrona-docs/blob/master/docs/guides/Pools/README.md). Make sure to keep the `"`s!

1. Save the file and:

* start `xmrig.exe` if you're mining with your CPU,
* `xmrig-amd.exe`. if you're mining with an AMD GPU,
* or `xmrig-nvidia.exe` if you're mining with a NVIDIA GPU.

**Remember:** if you want to mine with both your CPU and your GPU you must have both programs open at the same time!

That's it! You should be mining away now! :)


# Run a Mining Pool

This page will guide you through the process of setting up your very own mining pool for XKR! Mining pools are essential for keeping the kryptokrona network happy and decentralized.

Thanks to [@glen487](https://github.com/glen487) for this guide!

First make sure you are using **Ubuntu 18.04 LTS** (problems with the old node version 11 on 20.04)

```
sudo apt update
sudo apt upgrade
sudo apt-get install -y git curl wget screen build-essential libboost-all-dev cmake libssl-dev p7zip-full libsodium-dev
sudo reboot
```

### Node 12.x

Install Node version 12.x. currently required for cryptonote-nodejs-pool Add repository

```
curl -sL https://deb.nodesource.com/setup_12.x | sudo -E bash
```

Note: you will get warning "Node.js 11.x is no longer actively supported" but there is currently no other version working.

```
sudo apt-get install gcc g++ make  nodejs
```

### Install Redis server

```
sudo add-apt-repository ppa:chris-lea/redis-server
sudo apt-get update
sudo apt-get install redis-server
```

Dont forget to tune redis-server:

* Add this to your /etc/rc.local and make it executable with you favorite editor sample:

```
sudo vi /etc/rc.local
```

Content

```
#!/bin/bash
echo never > /sys/kernel/mm/transparent_hugepage/enabled
echo 1024 > /proc/sys/net/core/somaxconn
```

* Then make it executable

```
sudo chmod +x /etc/rc.local
```

* Create a start script for rc.local

```
sudo vi /etc/systemd/system/rc-local.service
```

* Add this:

```
[Unit]
 Description=/etc/rc.local Compatibility
 ConditionPathExists=/etc/rc.local

[Service]
 Type=forking
 ExecStart=/etc/rc.local start
 TimeoutSec=0
 StandardOutput=tty
 RemainAfterExit=yes
 

[Install]
 WantedBy=multi-user.target
```

* Enable rc-local

```
sudo systemctl enable rc-local
```

* Check status

```
sudo systemctl status rc-local
```

* Start redis-server.

```
sudo  systemctl start redis-server
```

### Create a kryptokrona user for daemon and wallet

Recommend to use a dedicated user in this example user "kryptokrona" is used to make it simple.

* Add user "kryptokrona" no need for this user to login remotely.

```
sudo adduser --disabled-password --disabled-login kryptokrona
```

* sudo to the new user "kryptokrona"

```
sudo su - kryptokrona
```

* Visit Github and download latest binaries.

<https://github.com/kryptokrona/kryptokrona/releases/>

Currently 1.0.2:

* Download and unpack

```
wget https://github.com/kryptokrona/kryptokrona/releases/download/v.0.1.0.2/kryptokrona-linux.zip
7z x kryptokrona-linux.zip
```

* Download and unpack bootstrap of the Kryptokrona blockchain quickly get going.

```
wget https://swenode.org/bootstrap.zip
7z x bootstrap.zip
```

### Start the kryptokrona node

* Now go in to the kryptokrona directory

```
cd kryptokrona
```

* Create XKR daemon start script and start in a "screen" sessions. "screen -S node"
* Create a start script for the node:

```
vi node.bash
```

* Add and save: Note: The pool daemon is running on local host only.

```
#!/bin/bash
./kryptokrona --rpc-bind-ip=127.0.0.1 --rpc-bind-port=11898
```

* Make the new script executable

```
chmod +x node.bash
```

* And start the node inside the sceeen session

```
./node.bash
```

* The node daemon will start " Imported block with index xxxx" and then sync the missing block with up to the current height of the blockchain. This will take some time. Wait to you see the "Successfully synchronized with the kryptokrona Network." Also the ascii loggo will show :D
* ctrl+a to exist the screen session

If you want to go back to the screen session use: "screen -rd" this will list the current sessions running.

Then add the one you want sample: screen -rd 1337.node

### Create pool wallet.

If you already have a wallet you could import the seed for that. Not covered in this guide.

```
./xkrwallet
```

* Chose option 2 to create

Sample:

```
What would you like to do?: 2
What would you like to call your new wallet?: Pool
Give your new wallet a password: **********
Confirm your new password: **********
Welcome to your new wallet, here is your payment address:
SEKReV8VHMiUg4kMFBfWE5tfb5d9xRQrB4xY8mxR36d2EaCPGBN6kGh9xyc3eGJtr98XpxAVHcqDzRSRXU7U3rTBd3cjdv2Nhbr

Please copy your secret keys and mnemonic seed and store them in a secure location:
Private spend key:
f1a58c31f88d5f8779cefdd70c6bd7f1bfb207ff28b09a1b7bf64b35dc49850e

Private view key:
5f12972e781f67dec0e96c08ee498d0b76323080796a520e0727b240cbd97801

Mnemonic seed:
building building building building cent peaches ostrich washing dexterity  highway tsunami tumbling request punch rest reorder cuddled  alchemy jittery  request uttered lamb opus portents punch

If you lose these your wallet cannot be recreated!
```

Note: This is fake , but remember to store you info in a secure place. Not on the VPS or pool server.

exit the wallet

* Create a XKR wallet script and start in a other "screen" session.

```
screen -S wallet
```

* Create the wallet script

```
vi wallet.bash
```

* Add below:

```
#!/bin/bash
./kryptokrona-service -w Pool.wallet -p <secret password> --rpc-legacy-security
```

* Make the wallet start script executable

```
chmod +x wallet.bash
```

* Start the wallet and make sure everything looks good ./wallet.bash

Again make sure to save the wallet seed!

ctrl+a to exist the screen session

```
exit
```

### Create a pool user.

```
sudo adduser --disabled-password --disabled-login pool
```

* sudo to the new pool user

```
sudo su - pool
```

* Download pool software, recommend this version for XKR pool. The newer "cryptonote-nodejs-pool" have problem with unlocker when used for XKR.

```
git clone https://github.com/kryptokrona/kryptokrona-nodejs-pool.git
cd kryptokrona-nodejs-pool
```

Install Node modules needed

```
npm i
```

* Copy config\_examples/kryptokrona.json to config.json and edit the following:

```
        "poolHost": "your hostname or IP address here",

        "coin": "Kryptokrona",
        "symbol": "XKR",
        "coinUnits": 100000,
        "coinDecimalPlaces": 5,
        "coinDifficultyTarget": 90,
        "blockchainExplorer": "https://explorer.kryptokrona.org/?hash={id}#blockchain_block'",
        "transactionExplorer": "https://explorer.kryptokrona.org/?hash={id}#blockchain_transaction",
        "daemonType": "bytecoin",
        "cnAlgorithm": "cryptonight_pico",
        "cnVariant": 2,
        "cnBlobType": 2,
```

* Change the pool address to you wallet address for the pool under "poolServer"

```
poolAddress": "SEKRe.....",
```

* Change password under "api"

```
"password" ""
```

⚠ 1 warning This is IMPORTANT because this is also used for /admin.html access to the pool.

Note: "wallet" password not used if you run the wallet rpc with "--rpc-legacy-security"

Make sure payment looks something like this.

```
"payments": {
                "enabled": true,
                "interval": 120,
                "maxAddresses": 5,
                "mixin": 3,
                "priority": 0,
                "transferFee": 100,
                "dynamicTransferFee": true,
                "minerPayFee": true,
                "minPayment": 100000,
                "maxPayment": null,
                "maxTransactionAmount": 500000000,
                "denomination": 100000
        },
```

## Start a screen for pool

```
screen -S pool
```

* Create script to start pool

```
vi start-pool.bash
```

Content:

```
#!/bin/bash
node init.js -config=config.json
```

* Make the script exceutable

```
chmod +x start-pool.bash
```

If you get the problem with the dateformat.js when starting pool. Edit the "package.json" and change changing the "dateformat": "\*" to "dateformat": "4.5.1" in package.json, and run "npm update" again to fixed the issue. also change the git url to include "git+https\://" like below.

Also add:

* "bufferutil": "^4.0.5",
* "utf-8-validate": "^5.0.7"
* "nodemailer": "4.0.1",

```
{
        "name": "cryptonote-nodejs-pool",
        "version": "1.4.0",
        "license": "GPL-2.0",
        "Original author": "Daniel Vandal",
        "Maintained by": "Musclesonvacation",
        "repository": {
                "type": "git",
                "url": "https://github.com/dvandal/cryptonote-nodejs-pool.git"
        },
        "dependencies": {
                "async": "1",
                "base58-native": "*",
                "bignum": "*",
                "bufferutil": "^4.0.5",
                "cli-color": "*",
                "cryptoforknote-util": "git+https://github.com/MoneroOcean/node-cryptoforknote-util.git",
                "cryptonight-hashing": "git+https://github.com/MoneroOcean/node-cryptonight-hashing.git",
                "dateformat": "4.5.1",
                "mailgun.js": "*",
                "node-telegram-bot-api": "*",
                "nodemailer": "4.0.1",
                "nodemailer-sendmail-transport": "*",
                "redis": "*",
                "socket.io": "^2.1.1",
                "time-ago": "*",
                "turtlecoin-multi-hashing": "git+https://github.com/turtlecoin/node8-multi-hashing.git",
                "utf-8-validate": "^5.0.7"
        },
        "engines": {
                "node": ">=8.11.3"
        }
}
```

Or simply download packages.json file for the pool from this repo. Make sure it's in the pool source directory.

```
wget https://raw.githubusercontent.com/glen487/XKR-Pool-Notes/main/packages.json
npm update
npm audit fix --force
```

Important run "npm update" after this change. Also "npm audit fix --force"

ctrl+a to exist the screen session

exit the pool user session

Use the sample website that comes with the pool under "website". In this guide webroot is pointing to "/var/www/html/pool"

Update the "config.js" in webroot to point to your API and add XKR explorer

Sample:

```
var api = "https://poolhostname.domain.tld/api/";
let parentCoin = ""

var email = "support@poolhost.com";
var telegram = "https://t.me/YourPool";
var discord = "https://discordapp.com/invite/YourPool";
var facebook = "https://www.facebook.com/<YourPoolFacebook>";

var marketCurrencies = ["{symbol}-BTC", "{symbol}-LTC", "{symbol}-DOGE", "{symbol}-USDT", "{symbol}-USD", "{symbol}-EUR", "{symbol}-CAD"];

var blockchainExplorer = "https://explorer.kryptokrona.se/?hash={id}#blockchain_block";
var transactionExplorer = "https://explorer.kryptokrona.se/?hash={id}#blockchain_transaction";

var blockchainExplorerMerged = "";
var transactionExplorerMerged = "";

var themeCss = "themes/default.css";
var defaultLang = 'en';
```

### Install you favorite webserver

If you want to support TLS on pool ports, copy your files to filename cert.pem, privkey.pem (no password) and chain.pem (or change in pool config.json) to the pool directory to replace the sample files. Remember to do this also after renewal. Follow the latest cert-bot if you need a certificate.

* Sample Nginx

```
sudo apt install nginx
```

* Create the nginx pool config.

```
sudo vi /etc/nginx/sites-available/pool 
```

Content in this sample with SSL certificate from Lets Replace "hostname.domain.tld" with your pool hostname and domain.

```
server {
        # Enable HTTP/2
        listen 443 ssl http2 default_server;
        server_name hostname.domain.tld;
        ssl_certificate /etc/letsencrypt/live/hostname.domain.tld/fullchain.pem; # managed by Certbot
        ssl_certificate_key /etc/letsencrypt/live/hostname.domain.tld/privkey.pem; # managed by Certbot
        include /etc/letsencrypt/options-ssl-nginx.conf; # managed by Certbot
        ssl_dhparam /etc/letsencrypt/ssl-dhparams.pem; # managed by Certbot

        root /var/www/html/pool;

        # Add index.php to the list if you are using PHP
        index index.html index.htm;

        location / {
                # First attempt to serve request as file, then
                # as directory, then fall back to displaying a 404.
                try_files $uri $uri/ =404;
                #add_header 'Access-Control-Allow-Origin' 'origin-list' always;
                if ($http_origin ~* (https?://[^/]*\.kryptokrona\.se(:[0-9]+)?)) {
                add_header 'Access-Control-Allow-Origin' "$http_origin";
                }
                #add_header 'Access-Control-Allow-Origin' '*';
                #add_header 'Access-Control-Allow-Credentials' 'true' always;
                add_header X-Content-Type-Options "nosniff" always;
                add_header X-Frame-Options "SAMEORIGIN";
                add_header X-XSS-Protection "1; mode=block";
                add_header Referrer-Policy origin-when-cross-origin;
                add_header X-Permitted-Cross-Domain-Policies none;

                 # Add Security cookie flags
                proxy_cookie_path ~(.*) "$1; SameSite=strict; secure; httponly";
        }
        if ($request_method !~ ^(GET|HEAD|POST)$ )
               {
                return 405;
               }

        location ~ ^/api/(.*) {
            proxy_pass http://127.0.0.1:8117/$1$is_args$args;
            proxy_set_header Host $host;
            proxy_set_header X-Real-IP $remote_addr;
            proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
            proxy_set_header X-Forwarded-Proto $scheme;

            # Add Security cookie flags
            proxy_cookie_path ~(.*) "$1; SameSite=strict; secure; httponly";
        }

        # Allow access to the ACME Challenge for Let's Encrypt <- <3
        location ~ /\.well-known\/acme-challenge {
                allow all;
        }


        # Deny all attempts to access hidden files
        # such as .htaccess, .htpasswd, .DS_Store (Mac), .git, .etc...

        location ~ /\. {
                deny all;
        }
}
```


# Mining on Android

Guide on how to mine XKR on Android smartphones

![](https://camo.githubusercontent.com/8321934519b782aa59679b76750d86b753fb7754d80c9a99302b2845a4902d58/68747470733a2f2f7062732e7477696d672e636f6d2f6d656469612f4535627533784e58774155764534443f666f726d61743d6a7067266e616d653d6d656469756d)

Mining on Android smartphones is surprisingly effective, with flagship models netting several KH/s. The power / hash/s ratio is also quite astonishing, and best of all, it's super easy to do!

Simply follow these two steps to start mining:

Download Termux

<https://play.google.com/store/apps/details?id=com.termux&hl=en&gl=US>

Then run

```
bash <(curl -s https://raw.githubusercontent.com/kryptokrona/xmrig-android/main/install.sh)
```


# Mining on macOS

Learn how to start mining on your mac computer, it's very fast and easy!

.. So you've got a Mac? Well, good news, the new Apple Silicon chips are very efficient to mine XKR on! You can expect at least 1kh/s on some of the newer Apple laptops, at a very low wattage.

Below you can follow a concise step-by-step guide on how to start mining!

### 1. Install brew

Homebrew is a terminal app that let's you install terminal applications with ease. They call it "The Missing Package Manager for macOS", which is an apt description. If you haven't installed it yet, do so by opening Terminal.app (command + space, and write terminal to open it) and write the following command:

```
/bin/bash -c "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/HEAD/install.sh)"
```

*Source:* [*https://brew.sh/*](https://brew.sh/)

### 2. Install xmrig

Then we will use your new brew installation to install the mining software, called xmrig. Simply type the following in the terminal to install it:

```
brew install xmrig
```

When it's finished (usually takes a few minutes), the software is installed and ready to go, but you will need a config so that you're mining the right coin to the right wallet.

### 3. Generate a config-file

You can generate a config on our website: <https://kryptokrona.org/mining>

To do so, you will need a wallet first. We recommend using [Aesir wallet](/guides/wallets/using-kryptokrona-wallet) to handle your XKR coins. If you want to get started without having to download any additional software, you can also generate a paper wallet at <https://explorer.kryptokrona.se/tools.html> and use that address, and then import it to the wallet in the app later. ***Dont forget to save the mnemonic seed, otherwise you won't be able to access the coins!***

When you've pasted your wallet address into the generator, it should start a download of a ***config.json*** file that will end up in your downloads folder.

### 4. Start the miner

Now you can simply start mining by typing the following into the terminal:

```
xmrig -c ~/Downloads/config.json
```

<figure><img src="https://2858262040-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fx7WCorBnqCP2oVt16bNf%2Fuploads%2FmeQEcE8UcEI3nFgF4HpX%2FScreenshot%202024-12-05%20at%2016.03.11.png?alt=media&amp;token=9464967a-03da-4a03-91af-f7595a2e7c3e" alt=""><figcaption><p>If everything went right, it should look something like this!</p></figcaption></figure>


# Mining on HiveOS

This guide takes you through the process of setting up XKR mining on HiveOS

Before we begin, you need to make sure you have the following:

* A HiveOS account and a connected mining rig ([Click here for a guide on how to set this up](https://hiveon.com/knowledge-base/getting_started/quick_install/))
* A kryptokrona wallet ([Click here to generate one](https://explorer.kryptokrona.se/tools.html))

If you have fulfilled the requirements above, go to your HiveOS dashboard.

At your dashboard, click on your rig and then go to the Flight sheets screen:

<figure><img src="https://2858262040-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fx7WCorBnqCP2oVt16bNf%2Fuploads%2FAtoZodI9VNzHfH5CWwzk%2FScreenshot%202022-09-18%20at%2003.20.59.png?alt=media&amp;token=038510a4-ffd9-46c5-8bfb-b1df3fd6150b" alt=""><figcaption><p>The Flight Sheets screen</p></figcaption></figure>

### Add wallet to HiveOS

Select XKR in the coins list, then click on **Add wallet** and enter you wallet details in the popup as shown below:

<figure><img src="https://2858262040-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fx7WCorBnqCP2oVt16bNf%2Fuploads%2FCpTTDnY1VuPfTzKx8rAr%2FScreenshot%202022-09-18%20at%2003.22.05.png?alt=media&amp;token=242d7fcf-fce6-4836-8179-4439d6bfb5ec" alt=""><figcaption><p>Wallet creation screen</p></figcaption></figure>

Back at the flight sheet screen, pick "Configure in miner" in the Pool dropdown menu.

### Choose mining software

Which miner to use depends on what kind of hardware you're running on your miner, in the following sections we will go through setting up mining from CPUs, NVIDIA GPUs and AMD GPUS, as well as a combination of two or more of these.

* [CPU setup](#cpu-mining-setup)
* [NVIDIA setup](#nvidia-setup)
* [AMD setup](#amd-setup)

### CPU mining setup

For CPU mining you want to use *XMRig (new)* that you may find in the Miner dropdown menu, then click **Setup Miner Config**.

<figure><img src="https://2858262040-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fx7WCorBnqCP2oVt16bNf%2Fuploads%2F8KaTZlj2R8qWehduYLqy%2FScreenshot%202022-09-18%20at%2003.22.58.png?alt=media&amp;token=3bb3338e-718d-4757-a106-78f1cb1df7bc" alt=""><figcaption></figcaption></figure>

Below is a picture of the miner config screen, here you will need to choose `CryptoNight-Pico` as hash algorithm, enter `%WAL%.%WORKER_NAME%` for Wallet template (or click **i** and then the text to copy it into the field automatically).

In this example I'm using `pool.kryptokrona.se:7777` as my pool of choice, but it is possible to use any kryptokrona pool. You can find more information about the available pools here: <https://miningpoolstats.stream/kryptokrona>

Set password to `x` and enable CPU with the toggle. Also make sure the TLS setting is on or off based on your chosen pool and finally click **Apply changes**.

<figure><img src="https://2858262040-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fx7WCorBnqCP2oVt16bNf%2Fuploads%2F8sQqImgiGcjmIaR6mQd7%2Fscreencapture-the-hiveos-farm-farms-410464-fs-2022-09-19-20_11_20.png?alt=media&amp;token=17150ba9-b375-4366-a464-9f34767e6953" alt=""><figcaption><p>CPU Mining config with XMRig (new)</p></figcaption></figure>

Now, for any additional GPU miners we have to click "Add miner" in the bottom right corner of the flight sheet config page and a new mining config field will pop up. Fill these in as you did [in this step.](#add-wallet-to-hiveos)

### NVIDIA Setup

For NVIDIA we want to hit the **Add miner** button and fill out the form as shown below, if you've already created a wallet you can pick it in the list, otherwise add a new one. We also want to choose **XmRig Nvidia** for our miner. Next click **Setup Miner Config**.

<figure><img src="https://2858262040-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fx7WCorBnqCP2oVt16bNf%2Fuploads%2Fiqrxzd5Gyviz8TgwLJUq%2FScreenshot%202022-09-19%20at%2021.01.34.png?alt=media&amp;token=7c0c75bb-f267-497c-906c-c3371636ea9e" alt=""><figcaption><p>A good looking NVIDIA setup</p></figcaption></figure>

On the setup miner screen you need to enter `%WAL%.%WORKER_NAME%` under Wallet template, then pick a pool, such as `pool.kryptokrona.se:11898`, choose `x` for password and enter `"algo": "cryptonight-pico"` under Config override. Finally click **Apply Changes.**

<figure><img src="https://2858262040-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fx7WCorBnqCP2oVt16bNf%2Fuploads%2Fro45lw0M5zoluQN23vsA%2FScreenshot%202022-09-19%20at%2021.03.43.png?alt=media&amp;token=e07d4bf0-fdd2-497f-89d1-cf560a2b5850" alt=""><figcaption><p>A fully configured XMRig NVIDIA</p></figcaption></figure>

### **AMD Setup**

For AMD we want to hit the **Add miner** button and fill out the form as below, if you've already created a wallet you can pick it in the list, otherwise add a new one. We also want to choose **XmRig AMD** for our miner. Next click **Setup Miner Config**.

<figure><img src="https://2858262040-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fx7WCorBnqCP2oVt16bNf%2Fuploads%2Fr4oEXzIuvPuNwyRk975s%2FScreenshot%202022-09-19%20at%2021.10.35.png?alt=media&amp;token=09b0774d-5c80-4550-b073-3393a1846f2e" alt=""><figcaption></figcaption></figure>

On the setup miner screen you need to enter `%WAL%.%WORKER_NAME%` under Wallet template, then pick a pool, such as `pool.kryptokrona.se:11898`, choose `x` for password and enter `"algo": "cryptonight-pico"` under Config override. Finally click **Apply Changes.**

<figure><img src="https://2858262040-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fx7WCorBnqCP2oVt16bNf%2Fuploads%2FfnXO23evsdN97sln5uhX%2FScreenshot%202022-09-19%20at%2021.12.46.png?alt=media&amp;token=ae940892-506c-4dcc-af7e-76f4df6aabbd" alt=""><figcaption><p>A fully configured AMD miner</p></figcaption></figure>

## Save and start mining

Now you have your flight sheet that (depending on what kind of miner your setting up) looks a little something like this:

<figure><img src="https://2858262040-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fx7WCorBnqCP2oVt16bNf%2Fuploads%2FayAXtmLTBRDuxPmx4q1M%2Fscreencapture-the-hiveos-farm-farms-410464-fs-2022-09-19-21_16_53.png?alt=media&amp;token=e114a581-815c-4eff-80a7-50ed501cba80" alt=""><figcaption><p>A miner running CPU + NVIDIA + AMD mining would look like this.</p></figcaption></figure>

Now you want to click **Create Flight Sheet** and then activate it! Activate it by going to to your Dashboard -> Your Farm -> Your Worker -> Flight sheets. Then click the :rocket: button next to your newly created flight sheet to start mining XKR!

<figure><img src="https://2858262040-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fx7WCorBnqCP2oVt16bNf%2Fuploads%2Funb50SJb5dZUJukafN27%2FScreenshot%202022-09-19%20at%2021.19.59.png?alt=media&amp;token=ac6b6beb-fc34-4daa-a264-b4bebd31db84" alt=""><figcaption><p>Start flight sheet from here</p></figcaption></figure>

If everything worked out, you should see the XKR badge with your hashrate on your HiveOS dashboard like in the image below:

<figure><img src="https://2858262040-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fx7WCorBnqCP2oVt16bNf%2Fuploads%2FvD55thKUrfRbWI6XvYFV%2FScreenshot%202022-09-19%20at%2021.29.36.png?alt=media&amp;token=43485c22-e3e4-4b8e-88db-a11b443a007d" alt=""><figcaption><p>Active hashrate on XKR</p></figcaption></figure>

### Conclusion

If you want to track your mining you may do so on the pool's website that you picked. In the examples above I used <https://pool.kryptokrona.se>. Simply paste your XKR address into the "Check stats" field on the pools website to track your mining progress.

#### Need help?

Come and say hello on our [Discord](https://chat.kryptokrona.org).

Happy mining :tada:


