ellite/Wallos · error · InvalidArgumentException

The label is not set.

Error message

The label is not set.

What it means

OTP::generateURI (backing getProvisioningUri) requires a label; it throws InvalidArgumentException when getLabel() returns null. The otpauth URI scheme mandates otpauth://<type>/<label>, so a label must be set before a provisioning URI can be produced.

Solutions

  1. Call setLabel() before getProvisioningUri(): $totp->setLabel('alice@example.com').
  2. Include the label when creating: TOTP::create($secret, null, 'sha1', 6, 'alice@example.com').
  3. If loading from a URI, ensure the path segment (label) is present.
  4. Guard: if ($otp->getLabel() === null) { $otp->setLabel($defaultLabel); }

Example fix

// before
$totp = TOTP::create($secret);
$uri = $totp->getProvisioningUri(); // throws
// after
$totp = TOTP::create($secret);
$totp->setLabel('alice@example.com');
$uri = $totp->getProvisioningUri();
Defensive patterns

Strategy: validation

Validate before calling

if ($otp->getLabel() === null) {
    $otp->setLabel($user->email);
}
$uri = $otp->getProvisioningUri();

Type guard

function hasLabel(object $otp): bool {
    return is_string($otp->getLabel()) && $otp->getLabel() !== '';
}

Try / catch

try {
    $uri = $otp->getProvisioningUri();
} catch (InvalidArgumentException $e) {
    $otp->setLabel('unknown-account');
    $uri = $otp->getProvisioningUri();
}

Prevention

When it happens

Trigger: Calling getProvisioningUri() on a TOTP/HOTP object created from a secret alone without calling setLabel(), e.g. TOTP::create($secret) then getProvisioningUri().

Common situations: Generating QR codes for authenticator apps before assigning an account label; refactors that dropped setLabel(); labels lost when objects were rebuilt from secrets stored in DB.

Understand the failure class

Background: "missing required argument" and "the following required arguments were not provided": what required-argument errors mean and how to fix them — this error's family across 20 libraries.

Related errors


AI-assisted analysis of ellite/Wallos@52820e87ca (2026-09-13). Data as JSON: /api/errors/38828e5b9f896bda. Report an issue: GitHub.

Appendix: source

Thrown at libs/OTPHP/OTP.php:102

        ] as $key => $default) {
            if (isset($options[$key]) && $default === $options[$key]) {
                unset($options[$key]);
            }
        }

        ksort($options);
    }

    /**
     * @param non-empty-string $type
     * @param array<non-empty-string, mixed> $options
     *
     * @return non-empty-string
     */
    protected function generateURI(string $type, array $options): string
    {
        $label = $this->getLabel();
        is_string($label) || throw new InvalidArgumentException('The label is not set.');
        $this->hasColon($label) === false || throw new InvalidArgumentException('Label must not contain a colon.');
        $options = [...$options, ...$this->getParameters()];
        $this->filterOptions($options);
        $params = str_replace(['+', '%7E'], ['%20', '~'], http_build_query($options, '', '&'));

        return sprintf(
            'otpauth://%s/%s?%s',
            $type,
            rawurlencode(($this->getIssuer() !== null ? $this->getIssuer() . ':' : '') . $label),
            $params
        );
    }

    /**
     * @param non-empty-string $safe
     * @param non-empty-string $user
     */
    protected function compareOTP(string $safe, string $user): bool

View on GitHub (pinned to 52820e87ca)