| 12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273 |
- using Invercargill;
- using Invercargill.Mapping;
- using Invercargill.DataStructures;
- using InvercargillJson;
- namespace Spry {
- public class CryptographyProvider : Object {
- private uint8[] signing_secret_key;
- private uint8[] signing_public_key;
- private uint8[] sealing_secret_key;
- private uint8[] sealing_public_key;
- construct {
- signing_secret_key = new uint8[Sodium.Asymmetric.Signing.SECRET_KEY_BYTES];
- signing_public_key = new uint8[Sodium.Asymmetric.Signing.PUBLIC_KEY_BYTES];
- Sodium.Asymmetric.Signing.generate_keypair(signing_public_key, signing_secret_key);
- sealing_secret_key = new uint8[Sodium.Asymmetric.Sealing.SECRET_KEY_BYTES];
- sealing_public_key = new uint8[Sodium.Asymmetric.Sealing.PUBLIC_KEY_BYTES];
- Sodium.Asymmetric.Sealing.generate_keypair(sealing_public_key, sealing_secret_key);
- }
- public string author_component_context_blob(ComponentContext context) throws Error {
- var mapper = ComponentContext.get_mapper();
- var properties = mapper.map_from(context);
- var json = new JsonElement.from_properties(properties);
- var blob = json.stringify(false);
- var signed = Sodium.Asymmetric.Signing.sign(blob.data, signing_secret_key);
- var @sealed = Sodium.Asymmetric.Sealing.seal(signed, sealing_public_key);
- return Base64.encode(@sealed).replace("+", "-").replace("/", "_");
- }
- public ComponentContext read_component_context_blob(string blob) throws Error {
- var mapper = ComponentContext.get_mapper();
- var signed = Sodium.Asymmetric.Sealing.unseal(Base64.decode(blob.replace("-", "+").replace("_", "/")), sealing_public_key, sealing_secret_key);
- if(signed == null) {
- throw new ComponentError.INVALID_CONTEXT("Could not unseal context");
- }
- var cleartext = Sodium.Asymmetric.Signing.verify(signed, signing_public_key);
- if(signed == null) {
- throw new ComponentError.INVALID_CONTEXT("Invalid context signature");
- }
- var json = new JsonElement.from_string(Wrap.byte_array(cleartext).to_raw_string());
- var context = mapper.materialise(json.as<JsonObject>());
- return context;
- }
- }
- public class ComponentContext {
- public string type_name { get; set; }
- public string context_key { get; set; }
- public DateTime timestamp { get; set; }
- public Properties data { get; set; }
- public static PropertyMapper<ComponentContext> get_mapper() {
- return PropertyMapper.build_for<ComponentContext>(cfg => {
- cfg.map<string>("c", o => o.type_name, (o, v) => o.type_name = v);
- cfg.map<string>("k", o => o.context_key, (o, v) => o.context_key = v);
- cfg.map<string>("t", o => o.timestamp.format_iso8601(), (o, v) => o.timestamp = new DateTime.from_iso8601(v, new TimeZone.utc()));
- cfg.map<Properties>("d", o => o.data, (o, v) => o.data = v);
- cfg.set_constructor(() => new ComponentContext());
- });
- }
- }
- }
|