use std::time::{Duration, SystemTime};
use crate::packet::{
Key,
key,
};
use crate::Result;
use crate::Packet;
use crate::packet::signature::{
SignatureBuilder,
SIG_BACKDATE_BY,
subpacket::SubpacketTag,
};
use crate::cert::prelude::*;
use crate::Error;
use crate::crypto::{Password, Signer};
use crate::types::{
HashAlgorithm,
KeyFlags,
SignatureType,
};
/// A Key builder.
///
/// A `KeyBuilder` is used to create a key, which can then be attached
/// to an existing certificate as a subkey using
/// [`KeyBuilder::subkey`].
///
/// # Examples
///
/// Generate a signing key and attach it to a certificate:
///
/// ```
/// use sequoia_openpgp as openpgp;
/// use openpgp::cert::prelude::*;
/// use openpgp::policy::StandardPolicy;
/// use openpgp::types::KeyFlags;
///
/// # fn main() -> openpgp::Result<()> {
/// let p = &StandardPolicy::new();
///
/// # let (cert, _) =
/// # CertBuilder::general_purpose(None, Some("alice@example.org"))
/// # .generate()?;
/// #
/// let vc = cert.with_policy(p, None)?;
/// # let vc1 = vc.clone();
/// let cert_new = KeyBuilder::new(KeyFlags::empty().set_signing())
/// .subkey(vc)?
/// .attach_cert()?;
/// # let vc2 = cert_new.with_policy(p, None)?;
/// # assert_eq!(vc1.keys().count() + 1, vc2.keys().count());
/// # Ok(())
/// # }
/// ```
pub struct KeyBuilder {
flags: KeyFlags,
cipher_suite: CipherSuite,
password: Option<Password>,
creation_time: Option<SystemTime>,
}
assert_send_and_sync!(KeyBuilder);
impl KeyBuilder {
/// Returns a new `KeyBuilder`.
///
/// Use [`KeyBuilder::subkey`] to generate a subkey and get a
/// [`SubkeyBuilder`], which can be used to add the subkey to a
/// certificate.
pub fn new(flags: KeyFlags) -> Self {
KeyBuilder {
flags,
cipher_suite: Default::default(),
creation_time: None,
password: None,
}
}
/// Returns the selected cipher suite.
pub fn cipher_suite(&self) -> CipherSuite {
self.cipher_suite
}
/// Sets the cipher suite.
pub fn set_cipher_suite(mut self, cipher_suite: CipherSuite) -> Self {
self.cipher_suite = cipher_suite;
self
}
/// Returns the creation time.
///
/// Returns `None` if the creation time hasn't been specified. In
/// that case, the creation time will be set to the current time
/// when the key material is generated by [`KeyBuilder::subkey`].
pub fn creation_time(&self) -> Option<SystemTime> {
self.creation_time
}
/// Sets the creation time.
///
/// If `None`, then the creation time will be set to the current
/// time when the key material is generated by
/// [`KeyBuilder::subkey`].
pub fn set_creation_time<T>(mut sel