googleworkspace/cli · error

Encrypted data too short

Error message

Encrypted data too short

What it means

decrypt() expects input in nonce||ciphertext layout, so anything shorter than the 12-byte GCM nonce cannot possibly be valid and is rejected before crypto begins. This means the encrypted credentials file exists but is truncated or otherwise not the file format decrypt() produces — typically a 0-byte or near-empty file.

Source

Thrown at crates/google-workspace-cli/src/credential_store.rs:402

    let key = get_or_create_key()?;
    let cipher = Aes256Gcm::new_from_slice(&key)
        .map_err(|e| anyhow::anyhow!("Failed to create cipher: {e}"))?;

    let nonce = Aes256Gcm::generate_nonce(&mut OsRng);
    let ciphertext = cipher
        .encrypt(&nonce, plaintext)
        .map_err(|e| anyhow::anyhow!("Encryption failed: {e}"))?;

    // Prepend nonce to ciphertext
    let mut result = nonce.to_vec();
    result.extend_from_slice(&ciphertext);
    Ok(result)
}

/// Decrypts data produced by `encrypt()`.
pub fn decrypt(data: &[u8]) -> anyhow::Result<Vec<u8>> {
    if data.len() < 12 {
        anyhow::bail!("Encrypted data too short");
    }

    let key = get_or_create_key()?;
    let cipher = Aes256Gcm::new_from_slice(&key)
        .map_err(|e| anyhow::anyhow!("Failed to create cipher: {e}"))?;

    let nonce = Nonce::from_slice(&data[..12]);
    let plaintext = cipher.decrypt(nonce, &data[12..]).map_err(|_| {
        anyhow::anyhow!(
            "Decryption failed. Credentials may have been created on a different machine. \
                 Run `gws auth logout` and `gws auth login` to re-authenticate."
        )
    })?;

    Ok(plaintext)
}

/// Returns the name of the active keyring backend for status display.

View on GitHub (pinned to a3768d0e82)

Solutions

  1. Run `gws auth logout` to clear the corrupt file, then `gws auth login` to recreate it
  2. If logout also fails, delete the encrypted credentials file in ~/.config/gws and log in again
  3. Exclude the gws config dir from sync tools, and check disk space

Example fix

// before: feeding any file straight into decrypt
let plaintext = credential_store::decrypt(&std::fs::read(&path)?)?;

// after: sanity-check the minimum viable length (12-byte nonce + 16-byte GCM tag)
let data = std::fs::read(&path)?;
if data.len() < 28 {
    anyhow::bail!("credentials file {} is corrupt ({} bytes) — re-run auth login", path.display(), data.len());
}
Defensive patterns

Strategy: validation

Validate before calling

// Guard before decrypt: nonce(12) + tag(16) is the minimum valid ciphertext
fn looks_like_ciphertext(data: &[u8]) -> bool {
    data.len() >= 12 + 16
}

let data = std::fs::read(&cred_path)?;
anyhow::ensure!(looks_like_ciphertext(&data), "credentials file is corrupt ({} bytes)", data.len());

Prevention

When it happens

Trigger: Credentials file truncated to 0 bytes by a crash in a pre-atomic-write version, a full disk, or an overwriting sync tool; a plaintext JSON accidentally saved at the encrypted-credentials path; a placeholder file created by tooling.

Common situations: Dropbox/Syncthing sync conflicts zeroing the file; disk-full during an old-version write; manual experimentation with the config dir; restore from a partial backup.

Related errors


AI-assisted analysis of googleworkspace/cli@a3768d0e82 (2026-08-16). Data as JSON: /api/errors/55001f148d4e6ae8. Report an issue: GitHub.