mirror of
https://github.com/processone/ejabberd.git
synced 2024-11-20 16:15:59 +01:00
Save acquired certificates in persistent storage
This commit is contained in:
parent
9cf596c67b
commit
fa3108e6e2
@ -11,10 +11,6 @@
|
|||||||
key :: jose_jwk:key()
|
key :: jose_jwk:key()
|
||||||
}).
|
}).
|
||||||
|
|
||||||
-record(data_cert, {
|
|
||||||
domain :: list(),
|
|
||||||
pem :: binary()
|
|
||||||
}).
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
@ -39,6 +39,7 @@ is_valid_account_opt("old-account") -> true;
|
|||||||
is_valid_account_opt("new-account") -> true;
|
is_valid_account_opt("new-account") -> true;
|
||||||
is_valid_account_opt(_) -> false.
|
is_valid_account_opt(_) -> false.
|
||||||
|
|
||||||
|
|
||||||
%%
|
%%
|
||||||
%% Get Certificate
|
%% Get Certificate
|
||||||
%%
|
%%
|
||||||
@ -403,6 +404,10 @@ is_error(_) -> false.
|
|||||||
data_empty() ->
|
data_empty() ->
|
||||||
[].
|
[].
|
||||||
|
|
||||||
|
%%
|
||||||
|
%% Account
|
||||||
|
%%
|
||||||
|
|
||||||
data_get_account(Data) ->
|
data_get_account(Data) ->
|
||||||
case lists:keyfind(account, 1, Data) of
|
case lists:keyfind(account, 1, Data) of
|
||||||
{account, #data_acc{id = AccId, key = PrivateKey}} ->
|
{account, #data_acc{id = AccId, key = PrivateKey}} ->
|
||||||
@ -415,6 +420,27 @@ data_set_account(Data, {AccId, PrivateKey}) ->
|
|||||||
NewAcc = {account, #data_acc{id = AccId, key = PrivateKey}},
|
NewAcc = {account, #data_acc{id = AccId, key = PrivateKey}},
|
||||||
lists:keystore(account, 1, Data, NewAcc).
|
lists:keystore(account, 1, Data, NewAcc).
|
||||||
|
|
||||||
|
%%
|
||||||
|
%% Certificates
|
||||||
|
%%
|
||||||
|
|
||||||
|
data_get_certificates(Data) ->
|
||||||
|
case lists:keyfind(certs, 1, Data) of
|
||||||
|
{certs, Certs} ->
|
||||||
|
{ok, Certs};
|
||||||
|
false ->
|
||||||
|
{ok, []}
|
||||||
|
end.
|
||||||
|
|
||||||
|
data_set_certificates(Data, NewCerts) ->
|
||||||
|
lists:keystore(certs, 1, Data, {certs, NewCerts}).
|
||||||
|
|
||||||
|
%% ATM we preserve one certificate for each domain
|
||||||
|
data_add_certificate(Data, {Domain, PemCert}) ->
|
||||||
|
{ok, Certs} = data_get_certificates(Data),
|
||||||
|
NewCerts = lists:keystore(Domain, 1, Certs, {Domain, PemCert}),
|
||||||
|
data_set_certificates(Data, NewCerts).
|
||||||
|
|
||||||
|
|
||||||
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
|
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
|
||||||
%%
|
%%
|
||||||
@ -475,6 +501,15 @@ read_account_persistent() ->
|
|||||||
{ok, Data} = read_persistent(),
|
{ok, Data} = read_persistent(),
|
||||||
data_get_account(Data).
|
data_get_account(Data).
|
||||||
|
|
||||||
|
read_certificates_persistent() ->
|
||||||
|
{ok, Data} = read_persistent(),
|
||||||
|
data_get_certificates(Data).
|
||||||
|
|
||||||
|
add_certificate_persistent({Domain, PemCert}) ->
|
||||||
|
{ok, Data} = read_persistent(),
|
||||||
|
NewData = data_add_certificate(Data, {Domain, PemCert}),
|
||||||
|
ok = write_persistent(NewData).
|
||||||
|
|
||||||
save_certificate({error, _, _} = Error) ->
|
save_certificate({error, _, _} = Error) ->
|
||||||
Error;
|
Error;
|
||||||
save_certificate({ok, DomainName, Cert}) ->
|
save_certificate({ok, DomainName, Cert}) ->
|
||||||
@ -482,22 +517,30 @@ save_certificate({ok, DomainName, Cert}) ->
|
|||||||
{ok, CertDir} = get_config_cert_dir(),
|
{ok, CertDir} = get_config_cert_dir(),
|
||||||
DomainString = bitstring_to_list(DomainName),
|
DomainString = bitstring_to_list(DomainName),
|
||||||
CertificateFile = filename:join([CertDir, DomainString ++ "_cert.pem"]),
|
CertificateFile = filename:join([CertDir, DomainString ++ "_cert.pem"]),
|
||||||
case file:write_file(CertificateFile, Cert) of
|
%% TODO: At some point do the following using a Transaction so
|
||||||
ok ->
|
%% that there is no certificate saved if it cannot be added in
|
||||||
{ok, DomainName, saved};
|
%% certificate persistent storage
|
||||||
{error, Reason} ->
|
write_cert(CertificateFile, Cert, DomainName),
|
||||||
?ERROR_MSG("Error: ~p saving certificate at file: ~p",
|
add_certificate_persistent({DomainName, Cert}),
|
||||||
[Reason, CertificateFile]),
|
{ok, DomainName, saved}
|
||||||
throw({error, DomainName, saving})
|
|
||||||
end
|
|
||||||
catch
|
catch
|
||||||
throw:Throw ->
|
throw:Throw ->
|
||||||
Throw;
|
Throw;
|
||||||
E:R ->
|
E:R ->
|
||||||
?ERROR_MSG("unknown ~p:~p", [E,R]),
|
?ERROR_MSG("Unknown ~p:~p, ~p", [E, R, erlang:get_stacktrace()]),
|
||||||
{error, DomainName, saving}
|
{error, DomainName, saving}
|
||||||
end.
|
end.
|
||||||
|
|
||||||
|
write_cert(CertificateFile, Cert, DomainName) ->
|
||||||
|
case file:write_file(CertificateFile, Cert) of
|
||||||
|
ok ->
|
||||||
|
{ok, DomainName, saved};
|
||||||
|
{error, Reason} ->
|
||||||
|
?ERROR_MSG("Error: ~p saving certificate at file: ~p",
|
||||||
|
[Reason, CertificateFile]),
|
||||||
|
throw({error, DomainName, saving})
|
||||||
|
end.
|
||||||
|
|
||||||
get_config_acme() ->
|
get_config_acme() ->
|
||||||
case ejabberd_config:get_option(acme, undefined) of
|
case ejabberd_config:get_option(acme, undefined) of
|
||||||
undefined ->
|
undefined ->
|
||||||
@ -535,6 +578,25 @@ get_config_cert_dir() ->
|
|||||||
{ok, CertDir}
|
{ok, CertDir}
|
||||||
end.
|
end.
|
||||||
|
|
||||||
|
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
|
||||||
|
%%
|
||||||
|
%% Transaction Fun
|
||||||
|
%%
|
||||||
|
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
|
||||||
|
|
||||||
|
transaction([{Fun, Rollback} | Rest]) ->
|
||||||
|
try
|
||||||
|
{ok, Result} = Fun(),
|
||||||
|
[Result | transaction(Rest)]
|
||||||
|
catch Type:Reason ->
|
||||||
|
Rollback(),
|
||||||
|
erlang:raise(Type, Reason, erlang:get_stacktrace())
|
||||||
|
end;
|
||||||
|
transaction([Fun | Rest]) ->
|
||||||
|
% not every action require cleanup on error
|
||||||
|
transaction([{Fun, fun () -> ok end} | Rest]);
|
||||||
|
transaction([]) -> [].
|
||||||
|
|
||||||
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
|
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
|
||||||
%%
|
%%
|
||||||
%% Debugging Funcs -- They are only used for the development phase
|
%% Debugging Funcs -- They are only used for the development phase
|
||||||
|
Loading…
Reference in New Issue
Block a user