use of com.walmartlabs.concord.server.sdk.metrics.WithTimer in project concord by walmartlabs.
the class AuditLogResource method list.
/**
* Returns a list of audit log events for the specified filters.
* <p>
* The endpoint performs additional permission checks if an entity filter
* (org, project, etc) is specified. If no filters specified the admin
* privileges are required.
* <p>
* The endpoint ignores all "unknown" filters. Only the {@link #ALLOWED_DETAILS_KEYS}
* are allowed.
*/
@GET
@ApiOperation(value = "List audit log entries for the specified organization", responseContainer = "list", response = AuditLogEntry.class)
@Produces(MediaType.APPLICATION_JSON)
@WithTimer
public List<AuditLogEntry> list(@ApiParam @QueryParam("object") AuditObject object, @ApiParam @QueryParam("action") AuditAction action, @ApiParam @QueryParam("userId") UUID userId, @ApiParam @QueryParam("username") String username, @ApiParam @QueryParam("after") OffsetDateTimeParam afterTimestamp, @ApiParam @QueryParam("before") OffsetDateTimeParam beforeTimestamp, @ApiParam @QueryParam("offset") @DefaultValue("0") int offset, @ApiParam @QueryParam("limit") @DefaultValue("30") int limit, @Context UriInfo uriInfo) {
Map<String, String> details = getDetails(uriInfo);
UUID effectiveUserId = userId;
if (effectiveUserId == null && username != null) {
effectiveUserId = userDao.getId(username, null, null);
if (effectiveUserId == null) {
// no such user in our DB, there shouldn't be any audit logs anyway
return Collections.emptyList();
}
}
UUID effectiveOrgId = getEffectiveOrgId(details);
UUID effectiveProjectId = getEffectiveProjectId(effectiveOrgId, details);
UUID effectiveSecretId = getEffectiveSecretId(effectiveOrgId, details);
UUID effectiveJsonStoreId = getEffectiveJsonStoreId(effectiveOrgId, details);
UUID effectiveTeamId = getEffectiveTeamId(effectiveOrgId, details);
String source = details.get("source");
Object eventId = details.get("eventId");
// only admins are allowed to proceed without any entity filters
if (effectiveOrgId == null && effectiveProjectId == null && effectiveSecretId == null && effectiveJsonStoreId == null && effectiveTeamId == null && source == null && eventId == null) {
if (!Roles.isAdmin()) {
throw new UnauthorizedException("Only admins can retrieve audit events without filtering by entity.");
}
}
ImmutableAuditLogFilter.Builder filterBuilder = AuditLogFilter.builder();
if (effectiveOrgId != null) {
filterBuilder.putDetails("orgId", effectiveOrgId);
}
if (effectiveProjectId != null) {
filterBuilder.putDetails("projectId", effectiveProjectId);
}
if (effectiveSecretId != null) {
filterBuilder.putDetails("secretId", effectiveSecretId);
}
if (effectiveJsonStoreId != null) {
filterBuilder.putDetails("jsonStoreId", effectiveJsonStoreId);
}
if (effectiveTeamId != null) {
filterBuilder.putDetails("teamId", effectiveTeamId);
}
if (source != null) {
filterBuilder.putDetails("source", source);
}
if (eventId != null) {
filterBuilder.putDetails("eventId", eventId);
}
if (details.get("githubEvent") != null) {
filterBuilder.putDetails("githubEvent", details.get("githubEvent"));
}
if (details.get("fullRepoName") != null) {
filterBuilder.putDetails("payload", Collections.singletonMap("repository", Collections.singletonMap("full_name", details.get("fullRepoName"))));
}
assertTimeInterval(unwrap(afterTimestamp), unwrap(beforeTimestamp));
return auditDao.list(filterBuilder.userId(effectiveUserId).object(object).action(action).after(unwrap(afterTimestamp)).before(unwrap(beforeTimestamp)).limit(limit).offset(offset).build());
}
use of com.walmartlabs.concord.server.sdk.metrics.WithTimer in project concord by walmartlabs.
the class Locks method lock.
@WithTimer
public void lock(DSLContext tx, long key) {
tx.connection(conn -> {
try (CallableStatement cs = conn.prepareCall(LOCK_SQL)) {
cs.setLong(1, key);
cs.execute();
}
});
}
use of com.walmartlabs.concord.server.sdk.metrics.WithTimer in project concord by walmartlabs.
the class SecretResource method getData.
@POST
@ApiOperation(value = "Get an existing secret's data", response = File.class)
@ApiResponses(value = { @ApiResponse(code = 200, message = "OK", response = File.class, responseHeaders = @ResponseHeader(name = "X-Concord-SecretType", description = "Secret type", response = String.class)) })
@Path("/{orgName}/secret/{secretName}/data")
@Consumes(MediaType.MULTIPART_FORM_DATA)
@Produces(MediaType.APPLICATION_OCTET_STREAM)
@WithTimer
public Response getData(@ApiParam @PathParam("orgName") @ConcordKey String orgName, @ApiParam @PathParam("secretName") @ConcordKey String secretName, @ApiParam MultipartInput input) {
OrganizationEntry org = orgManager.assertAccess(orgName, false);
String password = MultipartUtils.getString(input, Constants.Multipart.STORE_PASSWORD);
SecretDao.SecretDataEntry entry;
try {
entry = secretManager.getRaw(SecretManager.AccessScope.apiRequest(), org.getId(), secretName, password);
if (entry == null) {
throw new WebApplicationException("Secret not found: " + secretName, Status.NOT_FOUND);
}
} catch (SecurityException e) {
log.warn("fetchSecret -> error: {}", e.getMessage());
throw new SecretException("Error while fetching a secret '" + secretName + "': " + e.getMessage());
} catch (ValidationErrorsException e) {
log.warn("fetchSecret -> error: {}", e.getMessage());
return null;
}
try {
return Response.ok((StreamingOutput) output -> output.write(entry.getData()), MediaType.APPLICATION_OCTET_STREAM).header(Constants.Headers.SECRET_TYPE, entry.getType().name()).build();
} catch (Exception e) {
log.error("fetchSecret ['{}'] -> error while fetching a secret", secretName, e);
throw new ConcordApplicationException("Error while fetching a secret '" + secretName + "': " + e.getMessage());
}
}
use of com.walmartlabs.concord.server.sdk.metrics.WithTimer in project concord by walmartlabs.
the class ProjectAccessManager method hasAccess.
@WithTimer
public boolean hasAccess(ProjectEntry project, ResourceAccessLevel level, boolean orgMembersOnly) {
if (Roles.isAdmin()) {
// an admin can access any project
return true;
}
UserPrincipal principal = UserPrincipal.assertCurrent();
if (level == ResourceAccessLevel.READER && (Roles.isGlobalReader() || Roles.isGlobalWriter())) {
return true;
} else if (level == ResourceAccessLevel.WRITER && Roles.isGlobalWriter()) {
return true;
}
EntityOwner owner = project.getOwner();
if (ResourceAccessUtils.isSame(principal, owner)) {
// the owner can do anything with his projects
return true;
}
if (orgMembersOnly && project.getVisibility() == ProjectVisibility.PUBLIC && level == ResourceAccessLevel.READER && userDao.isInOrganization(principal.getId(), project.getOrgId())) {
// organization members can READ any public project in the same organization
return true;
}
OrganizationEntry org = orgManager.assertAccess(project.getOrgId(), false);
if (ResourceAccessUtils.isSame(principal, org.getOwner())) {
// the org owner can do anything with the org's projects
return true;
}
if (orgMembersOnly || project.getVisibility() != ProjectVisibility.PUBLIC) {
// the organization's members or the project is not public
if (!projectDao.hasAccessLevel(project.getId(), principal.getId(), ResourceAccessLevel.atLeast(level))) {
throw new UnauthorizedException("The current user (" + principal.getUsername() + ") doesn't have " + "the necessary access level (" + level + ") to the project: " + project.getName());
}
}
return true;
}
use of com.walmartlabs.concord.server.sdk.metrics.WithTimer in project concord by walmartlabs.
the class PayloadRestoreProcessor method process.
@Override
@WithTimer
public Payload process(Chain chain, Payload payload) {
ProcessKey processKey = payload.getProcessKey();
Map<String, Object> headers = stateManager.get(processKey, "_initial/payload.json", inputStream -> {
Map<String, Object> result = deserialize(inputStream);
return Optional.ofNullable(result);
}).orElseThrow(() -> new ConcordApplicationException("Initial state not found", Response.Status.INTERNAL_SERVER_ERROR));
payload = payload.putHeaders(headers);
Path baseDir = payload.getHeader(Payload.BASE_DIR);
ProcessStateManager.ItemConsumer cp = ProcessStateManager.copyTo(baseDir);
Map<String, Path> attachments = new HashMap<>();
stateManager.exportDirectory(processKey, "_initial/attachments/", (name, unixMode, src) -> {
cp.accept(name, unixMode, src);
attachments.put(name, baseDir.resolve(name));
});
payload = payload.putAttachments(attachments);
return chain.process(payload);
}
Aggregations