use super::Header;
use super::jwt::Claims;
use base64::Engine;
use base64::engine::general_purpose::URL_SAFE_NO_PAD;
use ecdsa::{
Signature, SignatureSize, SigningKey,
hazmat::{DigestPrimitive, SignPrimitive},
signature::Signer,
};
use elliptic_curve::{
CurveArithmetic, PrimeCurve, Scalar, generic_array::ArrayLength, ops::Invert, subtle::CtOption,
};
pub fn create_signed_jwt<C>(
key: SigningKey<C>,
header: Header,
claims: Claims,
) -> serde_json::Result<String>
where
C: PrimeCurve + CurveArithmetic + DigestPrimitive,
Scalar<C>: Invert<Output = CtOption<Scalar<C>>> + SignPrimitive<C>,
SignatureSize<C>: ArrayLength<u8>,
{
let header = URL_SAFE_NO_PAD.encode(serde_json::to_string(&header)?);
let payload = URL_SAFE_NO_PAD.encode(serde_json::to_string(&claims)?);
let signature: Signature<_> = key.sign(format!("{header}.{payload}").as_bytes());
Ok(format!("{header}.{payload}.{}", URL_SAFE_NO_PAD.encode(signature.to_bytes())))
}