|
|
@@ -52,6 +52,7 @@ import org.springframework.beans.factory.annotation.Autowired; |
|
|
|
import org.springframework.stereotype.Service; |
|
|
|
import org.springframework.transaction.annotation.Transactional; |
|
|
|
|
|
|
|
import javax.annotation.Nullable; |
|
|
|
import javax.validation.Valid; |
|
|
|
import javax.ws.rs.*; |
|
|
|
import javax.ws.rs.core.Context; |
|
|
@@ -181,29 +182,34 @@ public class AuthResource { |
|
|
|
@Autowired private SageHelloService sageHelloService; |
|
|
|
@Autowired private RestoreService restoreService; |
|
|
|
|
|
|
|
@POST @Path(EP_RESTORE+"/{restoreKey}") |
|
|
|
public Response restore(@Context Request req, |
|
|
|
@Context ContainerRequest ctx, |
|
|
|
@PathParam("restoreKey") String restoreKey, |
|
|
|
@Valid NetworkKeys.EncryptedNetworkKeys encryptedKeys) { |
|
|
|
@NonNull private BubbleNode checkRestoreRequest(@Nullable final String restoreKey) { |
|
|
|
if (restoreKey == null) throw invalidEx("err.restoreKey.required"); |
|
|
|
|
|
|
|
// ensure we have been initialized |
|
|
|
long start = now(); |
|
|
|
while (!sageHelloService.sageHelloSuccessful() && (now() - start < NODE_INIT_TIMEOUT)) { |
|
|
|
sleep(SECONDS.toMillis(1), "restore: waiting for node initialization"); |
|
|
|
} |
|
|
|
if (!sageHelloService.sageHelloSuccessful()) { |
|
|
|
return invalid("err.node.notInitialized"); |
|
|
|
} |
|
|
|
if (!sageHelloService.sageHelloSuccessful()) throw invalidEx("err.node.notInitialized"); |
|
|
|
|
|
|
|
if (restoreKey == null) return invalid("err.restoreKey.required"); |
|
|
|
if (!restoreKey.equalsIgnoreCase(getRestoreKey())) return invalid("err.restoreKey.invalid"); |
|
|
|
if (!restoreKey.equalsIgnoreCase(getRestoreKey())) throw invalidEx("err.restoreKey.invalid"); |
|
|
|
|
|
|
|
final BubbleNode thisNode = configuration.getThisNode(); |
|
|
|
if (!thisNode.hasSageNode()) return invalid("err.sageNode.required"); |
|
|
|
if (!thisNode.hasSageNode()) throw invalidEx("err.sageNode.required"); |
|
|
|
|
|
|
|
final BubbleNode sageNode = nodeDAO.findByUuid(thisNode.getSageNode()); |
|
|
|
if (sageNode == null) return invalid("err.sageNode.notFound"); |
|
|
|
if (sageNode == null) throw invalidEx("err.sageNode.notFound"); |
|
|
|
|
|
|
|
return sageNode; |
|
|
|
} |
|
|
|
|
|
|
|
@POST @Path(EP_RESTORE+"/{restoreKey}") |
|
|
|
public Response restore(@NonNull @Context final Request req, |
|
|
|
@NonNull @Context final ContainerRequest ctx, |
|
|
|
@Nullable @PathParam("restoreKey") final String restoreKey, |
|
|
|
@NonNull @Valid final NetworkKeys.EncryptedNetworkKeys encryptedKeys) { |
|
|
|
|
|
|
|
final var sageNode = checkRestoreRequest(restoreKey); |
|
|
|
|
|
|
|
final NetworkKeys keys; |
|
|
|
try { |
|
|
@@ -214,7 +220,8 @@ public class AuthResource { |
|
|
|
} |
|
|
|
|
|
|
|
restoreService.registerRestore(restoreKey, keys); |
|
|
|
final NotificationReceipt receipt = notificationService.notify(sageNode, retrieve_backup, thisNode.setRestoreKey(getRestoreKey())); |
|
|
|
final var receipt = notificationService.notify(sageNode, retrieve_backup, |
|
|
|
configuration.getThisNode().setRestoreKey(getRestoreKey())); |
|
|
|
|
|
|
|
return ok(receipt); |
|
|
|
} |
|
|
@@ -226,9 +233,12 @@ public class AuthResource { |
|
|
|
@NonNull @PathParam("restoreKey") final String restoreKey, |
|
|
|
@NonNull @FormDataParam("file") final InputStream in, |
|
|
|
@NonNull @FormDataParam("password") final String password) { |
|
|
|
authenticatorService.ensureAuthenticated(ctx); |
|
|
|
if (empty(password)) return invalid("err.password.required"); |
|
|
|
|
|
|
|
checkRestoreRequest(restoreKey); |
|
|
|
|
|
|
|
restoreService.registerRestore(restoreKey, new NetworkKeys()); |
|
|
|
|
|
|
|
try { |
|
|
|
if (restoreService.restoreFromPackage(restoreKey, in, password)) return ok(); |
|
|
|
} catch (IOException e) { |
|
|
|