# # Issuer

An `issuer`

is the authority on what holds digital assets of its kind.
While it cannot create new value by creating digital assets like a `mint`

,
it recognizes and identifies `purses`

and `payments`

that carry actual value.
It can create empty `purses`

and transform `payments`

(by splitting,
combining, burning, or exclusively claiming).

An `issuer`

has an unchangeable one-to-one relationship with the `mint`

and
`brand`

that were created with it. For any `brand`

for which you will accept
`payments`

in, you should obtain its `issuer`

from a trusted source.
You can then rely on that `issuer`

as the authority to
validate an untrusted `payment`

of that `brand`

.

## # makeIssuerKit(allegedName, amountMathKind)

`allegedName`

`{String}`

`amountMathKind`

`{MathKind}`

- optional- Returns
`{IssuerKit}`

Makes a new `issuer`

as well as its one-to-one associated ERTP objects; a `mint`

and a `brand`

.
All are in unchangeable one-to-one relationships with each other. It also returns an `amountMath`

that can be used on `amounts`

of the created `brand`

.

The `allegedName`

is available from the `brand`

or the `issuer`

. The `allegedName`

is
useful for debugging and double-checking assumptions, but should not be trusted.

The optional `amountMathKind`

specifies the kind of math to use with the digital assets.
Each implements all of the same set of API methods (i.e. `amountMath`

methods are
polymorphic). We recommend you import and use the `MathKind`

values from `@agoric/ERTP`

instead of using strings.

`MathKind.NAT`

(`nat`

): Used with fungible assets.`amount`

values are natural numbers (non-negative integers). Default value.`MathKind.STRING_SET`

(`strSet`

): Used with non-fungible assets.`amount`

values are strings.`MathKind.SET`

(`set`

): Used with non-fungible assets.`amount`

values are objects or records with multiple properties.

```
import { MathKind, makeIssuerKit } from '@agoric/ertp';
makeIssuerKit('quatloos'); // Defaults to MathKind.NAT
makeIssuerKit('foobars', MathKind.STRING_SET);
makeIssuerKit('kitties', MathKind.SET);
```

```
const { issuer: quatloosIssuer, mint: quatloosMint, brand: quatloosBrand, amountMath: quatloosAmountMath } =
makeIssuerKit('quatloos');
// This is merely an amount, describing assets.
const quatloos2 = quatloosAmountMath.make(2);
const { mint: titleMint, issuer: titleIssuer amountMath: titleAmountMath } = makeIssuerKit('alamedaCountyPropertyTitle', MathKind.STRING_SET);
// These are merely amounts describing digital assets, not minting assets.
const cornerProperty = titleLocalAmountMath.make(harden['1292826']);
const adjacentProperty = titleLocalAmountMath.make(harden['1028393']);
const combinedProperty = titleLocalAmountMath.make(harden['1292826', '1028393']);
```

## # issuer.getAllegedName()

- Returns:
`{allegedName}`

Returns the `allegedName`

for this `issuer`

.

An alleged name is a human-readable string name
of a kind of digital asset. An alleged name
should not be trusted as accurate since there is
no public registry or expectation of uniqueness. This
means there can be multiple issuers/mints/brands with the
same alleged name, and thus the name by itself does not
uniquely identify an issuer. Rather, the `brand`

object does that.

To put it another way, nothing stops different people from creating
multiple `issuers`

with the alleged name `Quatloos`

...but that doesn't
make any of them **the** Quatloos `issuer`

. The alleged name is just a
human readable version which is helpful for debugging.

```
const { issuer: quatloosIssuer } = makeIssuerKit('quatloos');
const quatloosIssuerAllegedName = quatloosIssuer.getAllegedName();
// quatloosIssuerAllegedName === 'quatloos'
```

## # issuer.getAmountMathKind()

- Returns:
`{MathKind}`

Get the kind of this `issuer`

's `amountMath`

. It returns one of
`MathKind.NAT`

(`nat`

), `MathKind.STR`

(`str`

), or `MathKind.STRING_SET`

(`strSet`

).

The `amountMathKind`

value specifies which of three kinds an `amountMath`

is,
and what kind of values it is used on. Each kind implements all of the same set
of API methods (i.e. `amountMath`

methods are polymorphic).

`MathKind.NAT`

(`nat`

): Used with fungible assets.`amount`

values are natural numbers (non-negative integers). Default value.`MathKind.STRING_SET`

(`strSet`

): Used with non-fungible assets.`amount`

values are strings.`MathKind.SET`

(`set`

): Used with non-fungible assets.`amount`

values are objects or records with multiple properties.

```
const { issuer: quatloosIssuer } = makeIssuerKit('quatloos');
quatloosIssuer.getAmountMathKind(); // Returns 'nat', also known as MathKind.NAT, the default value.
const { issuer: moolaIssuer } = makeIssuerKit('moola', MathKind.STRING_SET);
moolaIssuer.getAmountMathKind(); // Returns 'str', also known as 'MathKind.STRING_SET`
```

## # issuer.getAmountOf(payment)

`payment`

`{Payment}`

- Returns:
`{Amount}`

Get the `payment`

's balance. Because the `payment`

is not trusted, we cannot
trust it to provide its true value, and must rely on the `issuer`

to validate
the `payment`

's `brand`

and tell us how much it contains.

```
const { issuer: quatloosIssuer, mint: quatloosMint } = makeIssuerKit('quatloos');
const quatloosPayment = quatloosMint.mintPayment(quatloosAmountMath.make(100));
quatloosIssuer.getAmountOf(quatloosPayment); // returns an amount of 100 Quatloos
```

## # issuer.getBrand()

- Returns:
`{Brand}`

Returns the `brand`

for this `issuer`

. The `brand`

indicates the kind of digital asset
and is the same for the `issuer`

's associated `mint`

, and any `purses`

and `payments`

of this particular
kind. The `brand`

is not closely held, so this function should not be trusted to identify
an `issuer`

alone. Fake digital assets and amounts can use another `issuer's`

`brand`

.

```
const { issuer: quatloosIssuer, brand: quatloosBrand } = makeIssuerKit('quatloos');
const quatloosBrand = quatloosIssuer.getBrand();
// brand === quatloosBrand
```

## # issuer.makeEmptyPurse()

- Returns:
`{Purse}`

Make and return an empty `purse`

that holds assets of the `brand`

associated with the `issuer`

.

```
const { issuer: quatloosIssuer } = makeIssuerKit('quatloos');
const quatloosPurse = quatloosIssuer.makeEmptyPurse();
```

## # issuer.burn(payment, optAmount)

`payment`

`{Payment}`

`optAmount`

`{Amount}`

- Optional- Returns:
`{Amount}`

Burn (destroy) all of the digital assets in the `payment`

and return an `amount`

of what was burned.

`optAmount`

is optional. If `optAmount`

is present,
the code insists the `payment`

balance is equal to `optAmount`

, to prevent sending the wrong `payment`

and other confusion.

If `payment`

is a `promise`

for a `payment`

, the operation proceeds after the
`promise`

resolves.

```
const { issuer: quatloosIssuer, mint: quatloosMint } =
makeIssuerKit('quatloos');
const amountToBurn = quatloosAmountMath.make(10);
const paymentToBurn = quatloosMint.mintPayment(amountToBurn);
// burntAmount should equal 10 Quatloos
const burntAmount = quatloosIssuer.burn(paymentToBurn, amountToBurn);
```

## # issuer.claim(payment, optAmount)

`payment`

`{Payment}`

`optAmount`

`{Amount}`

- Returns:
`{Payment}`

Transfer all digital assets from `payment`

to a new `payment`

and burn the
original. This allows the owner to be sure no other references to this
payment survive, so they are the exclusive owner.

`optAmount`

is optional.
If `optAmount`

is present, `payment`

's balance must be
equal to `optAmount`

, to prevent sending the wrong `payment`

and other confusion.
If `optAmount`

does not equal the balance in the original `payment`

then it throws an error.

If a `payment`

is a `promise`

for a `payment`

, the operation will
proceed after the `promise`

resolves. Since you might also have a `promise`

returned,
it might take a bit of time for the whole operation to resolve.

```
const { mint: quatloosMint, issuer: quatloosIssuer } = makeIssuerKit('quatloos');
const amountExpectedToTransfer = quatloosAmountMath.make(2);
const originalPayment = quatloosMint.mintPayment(amountExpectedToTransfer);
const newPayment = quatloosIssuer.claim(originalPayment, amountToTransfer);
```

## # issuer.combine(paymentsArray, optTotalAmount)

`paymentsArray`

`{Array <Payment>}`

`optTotalAmount`

`{Amount}`

- Optional.- Returns:
`{Payment}`

Combines multiple `payments`

into one `payment`

. If any `payment`

in `paymentsArray`

is
a `promise`

, the operation proceeds after all the `payments`

resolve. The `payments`

in `paymentsArray`

are burned.

If the optional `optTotalAmount`

is present, the total of all the `payment`

`amounts`

in the
array must equal `optTotalAmount`

or it throws an error.

If a `payment`

is a `promise`

for a `payment`

, the operation will
proceed after the `promise`

resolves. Since you might also have a `promise`

returned,
it might take a bit of time for the whole operation to resolve.

```
const { mint: quatloosMint, issuer: quatloosIssuer } = makeIssuerKit('quatloos');
const quatloosLocalAmountMath = makeLocalAmountMath(quatloosIssuer);
// create an array of 100 payments of 1 quatloo each
const payments = [];
for (let i = 0; i < 100; i += 1) {
payments.push(quatloosMint.mintPayment(quatloosAmountMath.make(1)));
}
// combinedPayment equals 100
const combinedPayment = quatloosIssuer.combine(payments);
```

**Note**: You **cannot** combine `payments`

from different `mints`

(as they are of different `brands`

):

```
const { mint: otherMint, issuer: otherIssuer } = makeIssuerKit('other');
const otherPayment = otherMint.mintPayment(otherAmountMath.make(10));
payments.push(otherPayment); // using the payments array from the above code
// throws error
const badPayment = quatloosIssuer.combine(payments);
```

## # issuer.split(payment, paymentAmountA)

`payment`

`{Payment}`

`paymentAmountA`

`{Amount}`

- Returns:
`{Array <Payment>}`

Split a single `payment`

into two new `payments`

, A and B, according to `paymentAmountA`

.
For example, if the `payment`

is for 10 Quatloos, and `paymentAmountA`

is 3 Quatloos,
it returns an array of two `payments`

with balances of 3 Quatloos and 7 Quatloos.

The original `payment`

is burned.

If the original `payment`

is a `promise`

for a `payment`

, the operation will
proceed after the `promise`

resolves. Since you might also have a `promise`

returned,
it might take a bit of time for the whole operation to resolve.

```
const { mint: quatloosMint, issuer: quatloosIssuer } = makeIssuerKit('quatloos');
const oldPayment = quatloosMint.mintPayment(quatloosAmountMath.make(20));
// After the split, paymentA has 5 quatloos and paymentB has 15.
const [paymentA, paymentB] = quatloosIssuer.split(oldPayment, quatloosAmountMath.make(5));
```

## # issuer.splitMany(payment, amountArray)

`payment`

`{Payment}`

`amountArray`

`{Array <Amount>}`

- Returns:
`{Array <Payment>}`

Split a single `payment`

into multiple `payments`

. The resulting array of `payments`

is
as long as `amountArray`

, and the `payments`

will have `amounts`

corresponding to
the `amountArray`

contents. The original `payment`

is burned. If the original `payment`

is a `promise`

, the operation proceeds after the `promise`

resolves. If the `amounts`

in `amountArray`

don't add up to the value of `payment`

, the operation fails. The `brands`

of the `amountArray`

`amounts`

must all be the same as the `payment`

`brand`

.

```
const { mint: quatloosMint, issuer: quatloosIssuer} = makeIssuerKit('quatloos');
const oldPayment = quatloosMint.mintPayment(quatloosAmountMath.make(100));
const goodAmounts = Array(10).fill(quatloosAmountMath.make(10));
const arrayOfNewPayments = quatloos.Issuer.splitMany(oldPayment, goodAmounts);
// The total amount in the amountArray must equal the original payment amount
// Set original amount to 1000
const payment = quatloosMint.mintPayment(quatloosAmountMath.make(1000));
// Total amounts in badAmounts equal 20, when it should equal 1000
const badAmounts = Array(2).fill(quatloosAmountMath.make(10));
// 20 does not equal 1000, so throws error
quatloosIssuer.splitMany(payment, badAmounts);
```

## # issuer.isLive(payment)

`payment`

`{Payment}`

- Returns:
`{Boolean}`

Returns `true`

if the `payment`

was created by the issuer and has not yet been destroyed.
If `payment`

is a promise, the operation proceeds upon resolution.