use of com.google.spanner.admin.database.v1.Backup in project java-spanner by googleapis.
the class ITBackupTest method testRestore.
private void testRestore(Backup backup, Timestamp versionTime, String expectedKey) throws InterruptedException, ExecutionException {
// Restore the backup to a new database.
String restoredDb = testHelper.getUniqueDatabaseId();
String restoreOperationName;
OperationFuture<Database, RestoreDatabaseMetadata> restoreOperation;
int attempts = 0;
while (true) {
try {
logger.info(String.format("Restoring backup %s to database %s", backup.getId().getBackup(), restoredDb));
final Restore restore = dbAdminClient.newRestoreBuilder(backup.getId(), DatabaseId.of(projectId, instanceId, restoredDb)).setEncryptionConfig(EncryptionConfigs.customerManagedEncryption(expectedKey)).build();
restoreOperation = dbAdminClient.restoreDatabase(restore);
restoreOperationName = restoreOperation.getName();
break;
} catch (ExecutionException e) {
if (e.getCause() instanceof FailedPreconditionException && e.getCause().getMessage().contains("Please retry the operation once the pending restores complete")) {
attempts++;
if (attempts == 10) {
logger.info("Restore operation failed 10 times because of other pending restores. Skipping restore test.");
return;
}
// wait and then retry.
logger.info(String.format("Restoring backup %s to database %s must wait because of other pending restore operation", backup.getId().getBackup(), restoredDb));
// noinspection BusyWait
Thread.sleep(60_000L);
} else {
throw e;
}
}
}
databases.add(restoredDb);
logger.info(String.format("Restore operation %s running", restoreOperationName));
RestoreDatabaseMetadata metadata = restoreOperation.getMetadata().get();
assertEquals(backup.getId().getName(), metadata.getBackupInfo().getBackup());
assertEquals(RestoreSourceType.BACKUP, metadata.getSourceType());
assertEquals(DatabaseId.of(testHelper.getInstanceId(), restoredDb).getName(), metadata.getName());
assertEquals(versionTime, Timestamp.fromProto(metadata.getBackupInfo().getVersionTime()));
// Ensure the operations show up in the right collections.
// TODO: Re-enable when it is clear why this fails on the CI environment.
// verifyRestoreOperations(backupOp.getName(), restoreOperationName);
// Wait until the restore operation has finished successfully.
Database database = restoreOperation.get();
assertEquals(restoredDb, database.getId().getDatabase());
// Reloads the database
final Database reloadedDatabase = database.reload();
assertNotNull(reloadedDatabase.getProto());
assertEquals(versionTime, Timestamp.fromProto(reloadedDatabase.getProto().getRestoreInfo().getBackupInfo().getVersionTime()));
testDatabaseEncryption(reloadedDatabase, expectedKey);
testDatabaseDialect(reloadedDatabase, Dialect.GOOGLE_STANDARD_SQL);
// Restoring the backup to an existing database should fail.
logger.info(String.format("Restoring backup %s to existing database %s", backup.getId().getBackup(), restoredDb));
ExecutionException executionException = assertThrows(ExecutionException.class, () -> backup.restore(DatabaseId.of(testHelper.getInstanceId(), restoredDb)).get());
assertEquals(SpannerException.class, executionException.getCause().getClass());
SpannerException spannerException = (SpannerException) executionException.getCause();
assertEquals(ErrorCode.ALREADY_EXISTS, spannerException.getErrorCode());
}
use of com.google.spanner.admin.database.v1.Backup in project java-spanner by googleapis.
the class CreateBackupWithEncryptionKey method createBackupWithEncryptionKey.
static Void createBackupWithEncryptionKey(DatabaseAdminClient adminClient, String projectId, String instanceId, String databaseId, String backupId, String kmsKeyName) throws InterruptedException {
// Set expire time to 14 days from now.
final Timestamp expireTime = Timestamp.ofTimeMicroseconds(TimeUnit.MICROSECONDS.convert(System.currentTimeMillis() + TimeUnit.DAYS.toMillis(14), TimeUnit.MILLISECONDS));
final Backup backupToCreate = adminClient.newBackupBuilder(BackupId.of(projectId, instanceId, backupId)).setDatabase(DatabaseId.of(projectId, instanceId, databaseId)).setExpireTime(expireTime).setEncryptionConfig(EncryptionConfigs.customerManagedEncryption(kmsKeyName)).build();
final OperationFuture<Backup, CreateBackupMetadata> operation = adminClient.createBackup(backupToCreate);
Backup backup;
try {
System.out.println("Waiting for operation to complete...");
backup = operation.get(1200, TimeUnit.SECONDS);
} catch (ExecutionException e) {
// If the operation failed during execution, expose the cause.
throw SpannerExceptionFactory.asSpannerException(e.getCause());
} catch (InterruptedException e) {
// and the thread is interrupted, either before or during the activity.
throw SpannerExceptionFactory.propagateInterrupt(e);
} catch (TimeoutException e) {
// If the operation timed out propagates the timeout
throw SpannerExceptionFactory.propagateTimeout(e);
}
System.out.printf("Backup %s of size %d bytes was created at %s using encryption key %s%n", backup.getId().getName(), backup.getSize(), LocalDateTime.ofEpochSecond(backup.getProto().getCreateTime().getSeconds(), backup.getProto().getCreateTime().getNanos(), OffsetDateTime.now().getOffset()), kmsKeyName);
return null;
}
use of com.google.spanner.admin.database.v1.Backup in project java-spanner by googleapis.
the class SpannerSample method listBackupOperations.
// [END spanner_cancel_backup_create]
// [START spanner_list_backup_operations]
static void listBackupOperations(InstanceAdminClient instanceAdminClient, DatabaseId databaseId) {
Instance instance = instanceAdminClient.getInstance(databaseId.getInstanceId().getInstance());
// Get create backup operations for the sample database.
Timestamp last24Hours = Timestamp.ofTimeSecondsAndNanos(TimeUnit.SECONDS.convert(TimeUnit.HOURS.convert(Timestamp.now().getSeconds(), TimeUnit.SECONDS) - 24, TimeUnit.HOURS), 0);
String filter = String.format("(metadata.database:%s) AND " + "(metadata.@type:type.googleapis.com/" + "google.spanner.admin.database.v1.CreateBackupMetadata) AND " + "(metadata.progress.start_time > \"%s\")", databaseId.getName(), last24Hours);
Page<Operation> operations = instance.listBackupOperations(Options.filter(filter));
for (Operation op : operations.iterateAll()) {
try {
CreateBackupMetadata metadata = op.getMetadata().unpack(CreateBackupMetadata.class);
System.out.println(String.format("Backup %s on database %s pending: %d%% complete", metadata.getName(), metadata.getDatabase(), metadata.getProgress().getProgressPercent()));
} catch (InvalidProtocolBufferException e) {
// The returned operation does not contain CreateBackupMetadata.
System.err.println(e.getMessage());
}
}
}
Aggregations