INFRA-3304 | Dhruv | Uploads aws policy file to a channel and uses the permaLink for jit
This commit is contained in:
@@ -130,6 +130,10 @@
|
||||
"name": "JIT_COMMON_CHANNEL",
|
||||
"value": "$JIT_COMMON_CHANNEL"
|
||||
},
|
||||
{
|
||||
"name": "JIT_POLICY_UPLOAD_CHANNEL",
|
||||
"value": "$JIT_POLICY_UPLOAD_CHANNEL"
|
||||
},
|
||||
{
|
||||
"name": "GITHUB_CLOUD_OAUTH_TOKEN",
|
||||
"value": "$GITHUB_CLOUD_OAUTH_TOKEN"
|
||||
|
||||
@@ -100,6 +100,10 @@
|
||||
{
|
||||
"name": "JIT_COMMON_CHANNEL",
|
||||
"value": "$JIT_COMMON_CHANNEL"
|
||||
},
|
||||
{
|
||||
"name": "JIT_POLICY_UPLOAD_CHANNEL",
|
||||
"value": "$JIT_POLICY_UPLOAD_CHANNEL"
|
||||
}
|
||||
],
|
||||
"namespace": "$NAMESPACE",
|
||||
|
||||
@@ -142,12 +142,15 @@ class JitServiceImpl implements JitService {
|
||||
|
||||
private void postReviewerDmOnSlack(
|
||||
User reviewer,
|
||||
String policyPermaLink,
|
||||
JitApproval jitApproval,
|
||||
SlackBotAttachment reviewMessage
|
||||
) throws IOException {
|
||||
var result = slackBotClient.postMessage(userService.getUsersSlackId(reviewer),
|
||||
reviewMessage);
|
||||
|
||||
var channelId = userService.getUsersSlackId(reviewer);
|
||||
var result = slackBotClient.postMessage(channelId, reviewMessage);
|
||||
if (policyPermaLink != null) {
|
||||
slackBotClient.postPermaLinkMessage(channelId, policyPermaLink);
|
||||
}
|
||||
jitApproval.setReviewerSlackMessageTimestamp(result.getTs());
|
||||
jitApproval.setBotChannelId(result.getChannel());
|
||||
jitApprovalsRepository.save(jitApproval);
|
||||
@@ -163,11 +166,14 @@ class JitServiceImpl implements JitService {
|
||||
|
||||
private void postRequestorDmOnSlack(
|
||||
JitRequest jitRequest,
|
||||
String policyPermaLink,
|
||||
SlackBotAttachment personalMessage
|
||||
) throws IOException {
|
||||
var result = slackBotClient.postMessage(
|
||||
userService.getUsersSlackId(jitRequest.getRequestedFor()), personalMessage);
|
||||
|
||||
var channelId = userService.getUsersSlackId(jitRequest.getRequestedFor());
|
||||
var result = slackBotClient.postMessage(channelId, personalMessage);
|
||||
if (policyPermaLink != null) {
|
||||
slackBotClient.postPermaLinkMessage(channelId, policyPermaLink);
|
||||
}
|
||||
jitRequest.setRequestorSlackMessageTimestamp(result.getTs());
|
||||
jitRequest.setBotChannelId(result.getChannel());
|
||||
}
|
||||
@@ -198,9 +204,13 @@ class JitServiceImpl implements JitService {
|
||||
|
||||
private void postChannelOnSlack(
|
||||
JitRequest jitRequest,
|
||||
String policyPermaLink,
|
||||
SlackBotAttachment commonChannelMessage
|
||||
) throws IOException {
|
||||
var result = slackBotClient.postMessage(commonChannelId, commonChannelMessage);
|
||||
if (policyPermaLink != null) {
|
||||
slackBotClient.postPermaLinkMessage(commonChannelId, policyPermaLink);
|
||||
}
|
||||
jitRequest.setChannelSlackMessageTimestamp(result.getTs());
|
||||
}
|
||||
|
||||
@@ -359,13 +369,13 @@ class JitServiceImpl implements JitService {
|
||||
actionEnabled = false;
|
||||
}
|
||||
if (reviewerEmail.equals(onCallApproverEmail)) {
|
||||
postRequestorDmOnSlack(jitRequest,
|
||||
postRequestorDmOnSlack(jitRequest, null,
|
||||
slackBotUtil.getRequestorDm(jitRequest, false, Collections.emptyList(),
|
||||
Collections.emptyList(), Collections.emptyList(),
|
||||
Collections.emptyList(),
|
||||
Collections.emptyList(),
|
||||
SlackColor.APPROVED));
|
||||
postChannelOnSlack(jitRequest,
|
||||
postChannelOnSlack(jitRequest, null,
|
||||
slackBotUtil.getChannelMessage(jitRequest, Collections.emptyList(),
|
||||
Collections.emptyList(), Collections.emptyList(),
|
||||
Collections.emptyList(),
|
||||
@@ -616,15 +626,19 @@ class JitServiceImpl implements JitService {
|
||||
});
|
||||
pendingTeams.sort(String::compareTo);
|
||||
|
||||
final String uploadedPolicyPermaLink = jitRequest.getAwsPolicy() != null
|
||||
? slackBotClient.sendAwsPolicyDocumentToCommonChannel(
|
||||
objectMapper.writeValueAsString(jitRequest.getAwsPolicy()))
|
||||
: null;
|
||||
// send personal message to user with details on pending and approved reviewers
|
||||
JitRequest jitRequestWithId = jitRequestRepository.save(jitRequest);
|
||||
postRequestorDmOnSlack(jitRequestWithId,
|
||||
postRequestorDmOnSlack(jitRequestWithId, uploadedPolicyPermaLink,
|
||||
slackBotUtil.getRequestorDm(jitRequestWithId, true, pendingTeams,
|
||||
new ArrayList<>(), new ArrayList<>(), new ArrayList<>(), new ArrayList<>(),
|
||||
SlackColor.INFO));
|
||||
|
||||
// send group message to common channel with details on pending and approved reviewers
|
||||
postChannelOnSlack(jitRequest,
|
||||
postChannelOnSlack(jitRequest, uploadedPolicyPermaLink,
|
||||
slackBotUtil.getChannelMessage(jitRequest, pendingTeams, new ArrayList<>(),
|
||||
new ArrayList<>(),
|
||||
new ArrayList<>(), new ArrayList<>(), SlackColor.INFO));
|
||||
@@ -633,8 +647,8 @@ class JitServiceImpl implements JitService {
|
||||
JitRequest finalJitRequest = jitRequest;
|
||||
jitApprovalsWithId.stream().forEach(jitApproval -> {
|
||||
try {
|
||||
postReviewerDmOnSlack(jitApproval.getReviewer(), jitApproval,
|
||||
slackBotUtil.getReviewerDm(finalJitRequest.getRequestedFor().getEmail(),
|
||||
postReviewerDmOnSlack(jitApproval.getReviewer(), uploadedPolicyPermaLink,
|
||||
jitApproval, slackBotUtil.getReviewerDm(finalJitRequest.getRequestedFor().getEmail(),
|
||||
finalJitRequest, jitApproval, true, SlackColor.INFO));
|
||||
} catch (IOException e) {
|
||||
throw new RuntimeException(e);
|
||||
|
||||
@@ -20,4 +20,5 @@ public class JitUtil {
|
||||
jitRequestDto.setTeam(jitTeamOverrideMap.get(team));
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -22,23 +22,6 @@ import org.springframework.stereotype.Component;
|
||||
@Component
|
||||
public class SlackBotUtil {
|
||||
|
||||
private final ObjectMapper objectMapper = new ObjectMapper();
|
||||
|
||||
private String prettyPrintJson(Map<String, Object> json) {
|
||||
try {
|
||||
ObjectWriter writer = objectMapper.writerWithDefaultPrettyPrinter();
|
||||
return writer.writeValueAsString(json);
|
||||
} catch (Exception e) {
|
||||
return json.toString();
|
||||
}
|
||||
}
|
||||
|
||||
private SlackMessageText createJsonTextBoxField(String title, Map<String, Object> json) {
|
||||
String formattedJson = prettyPrintJson(json);
|
||||
String formattedText = String.format("*%s*\n```%s```", title, formattedJson);
|
||||
return new SlackMessageText(SlackMessageTextType.MARKDOWN, formattedText);
|
||||
}
|
||||
|
||||
|
||||
private SlackMessageText createTextBoxField(String title, String text) {
|
||||
return new SlackMessageText(SlackMessageTextType.MARKDOWN,
|
||||
@@ -180,12 +163,6 @@ public class SlackBotUtil {
|
||||
style, value, actionId);
|
||||
}
|
||||
|
||||
SlackBotMessageBlock generateAwsPolicyBlocks(Map<String, Object> awsPolicy) {
|
||||
SlackMessageText awsPolicyText = createJsonTextBoxField("POLICY", awsPolicy);
|
||||
return new SlackBotMessageBlock(
|
||||
SlackMessageBlockType.SECTION, awsPolicyText, null, null);
|
||||
}
|
||||
|
||||
public SlackBotAttachment getReviewerDm(
|
||||
String userEmail, JitRequest jitRequest, JitApproval jitApproval,
|
||||
boolean actionEnabled, SlackColor color
|
||||
@@ -204,9 +181,6 @@ public class SlackBotUtil {
|
||||
|
||||
ArrayList<SlackBotMessageBlock> blocks = new ArrayList<>();
|
||||
blocks.add(reviewRequestSection);
|
||||
if (jitRequest.getAwsPolicy() != null) {
|
||||
blocks.add(generateAwsPolicyBlocks(jitRequest.getAwsPolicy()));
|
||||
}
|
||||
if (reviewRequestAction != null) {
|
||||
blocks.add(reviewRequestAction);
|
||||
}
|
||||
@@ -242,9 +216,6 @@ public class SlackBotUtil {
|
||||
blocks.add(reviewRequestSection);
|
||||
blocks.add(dividerSection);
|
||||
blocks.add(requestDetailSection);
|
||||
if (jitRequest.getAwsPolicy() != null) {
|
||||
blocks.add(generateAwsPolicyBlocks(jitRequest.getAwsPolicy()));
|
||||
}
|
||||
|
||||
if (actionEnabled) {
|
||||
ArrayList<SlackMessageElement> elements = new ArrayList<>();
|
||||
@@ -325,9 +296,6 @@ public class SlackBotUtil {
|
||||
blocks.add(infoSection);
|
||||
blocks.add(dividerSection);
|
||||
blocks.add(reviewRequestSection);
|
||||
if (jitRequest.getAwsPolicy() != null) {
|
||||
blocks.add(generateAwsPolicyBlocks(jitRequest.getAwsPolicy()));
|
||||
}
|
||||
return new SlackBotAttachment(color.color, blocks);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -5,14 +5,18 @@ import com.slack.api.methods.MethodsClient;
|
||||
import com.slack.api.methods.SlackApiException;
|
||||
import com.slack.api.methods.response.chat.ChatPostMessageResponse;
|
||||
import com.slack.api.methods.response.files.FilesUploadResponse;
|
||||
import com.slack.api.model.File;
|
||||
import com.slack.api.methods.response.files.FilesUploadV2Response;
|
||||
import com.slack.api.model.Attachment;
|
||||
import com.slack.api.model.User;
|
||||
import java.io.File;
|
||||
import java.io.IOException;
|
||||
import java.nio.charset.StandardCharsets;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import lombok.RequiredArgsConstructor;
|
||||
import lombok.extern.slf4j.Slf4j;
|
||||
import org.apache.commons.io.FileUtils;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.beans.factory.annotation.Value;
|
||||
import org.springframework.stereotype.Component;
|
||||
@@ -25,9 +29,10 @@ public class SlackBotClient {
|
||||
|
||||
private static final String SLACK_API_URL = "https://api.slack.com/methods/";
|
||||
private static final String postMessage = "chat.postMessage";
|
||||
@Value("${jit.slack.policy.upload.channel.id}") String policyUploadChannelId;
|
||||
|
||||
@Value("${slackbot.token}")
|
||||
private String slackBotToken;
|
||||
|
||||
@Autowired
|
||||
private MethodsClient client;
|
||||
|
||||
@@ -53,6 +58,38 @@ public class SlackBotClient {
|
||||
return userSlackIdMap;
|
||||
}
|
||||
|
||||
public String sendAwsPolicyDocumentToCommonChannel(
|
||||
String awsPolicyDocument
|
||||
) throws IOException {
|
||||
FilesUploadResponse uploadResponse = null;
|
||||
try {
|
||||
uploadResponse = client.filesUpload(req -> req
|
||||
.token(slackBotToken)
|
||||
.content(awsPolicyDocument)
|
||||
.channels(List.of(policyUploadChannelId))
|
||||
.filename("AwsPolicyDocument.json")
|
||||
.filetype("json")
|
||||
);
|
||||
var policyPermaLink = uploadResponse.getFile().getPermalink();
|
||||
var result = client.chatPostMessage(r -> r
|
||||
.token(slackBotToken)
|
||||
.channel(policyUploadChannelId)
|
||||
.attachments(List.of(
|
||||
Attachment.builder()
|
||||
.title("AWS Policy Document")
|
||||
.titleLink(policyPermaLink)
|
||||
.build()
|
||||
))
|
||||
);
|
||||
if (!result.isOk()) {
|
||||
throw new IOException("Unable to send policy document : " + result.getError());
|
||||
}
|
||||
return policyPermaLink;
|
||||
} catch (Exception e) {
|
||||
throw new IOException("Unable to upload policy document : " + e.getMessage());
|
||||
}
|
||||
}
|
||||
|
||||
public ChatPostMessageResponse postMessage(
|
||||
String channelId,
|
||||
SlackBotAttachment slackBotAttachment
|
||||
@@ -70,14 +107,37 @@ public class SlackBotClient {
|
||||
.attachmentsAsString(textJson)
|
||||
);
|
||||
if (!result.isOk()) {
|
||||
log.error("Unable to process Slack API request: {}", result.getError());
|
||||
throw new IOException("Unable to process Slack API request: " + result.getError());
|
||||
}
|
||||
} catch (IOException | SlackApiException e) {
|
||||
log.error("error: {}", e.getMessage(), e);
|
||||
} catch (Exception e) {
|
||||
throw new IOException("Unable to process Slack API request: " + e.getMessage());
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
public ChatPostMessageResponse postPermaLinkMessage(
|
||||
String channelId,
|
||||
String policyPermaLink
|
||||
) throws IOException {
|
||||
try {
|
||||
var result = client.chatPostMessage(r -> r
|
||||
.token(slackBotToken)
|
||||
.channel(channelId)
|
||||
.attachments(List.of(
|
||||
Attachment.builder().title("AWS Policy Document").titleLink(policyPermaLink)
|
||||
.build()
|
||||
))
|
||||
);
|
||||
if (!result.isOk()) {
|
||||
throw new IOException("Unable to process Slack API request: " + result.getError());
|
||||
}
|
||||
return result;
|
||||
} catch (Exception e) {
|
||||
throw new IOException("Unable to process Slack API request: " + e.getMessage());
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
public void updateMessage(String channelId, SlackBotAttachment slackBotAttachment, String ts)
|
||||
throws IOException {
|
||||
try {
|
||||
|
||||
@@ -36,6 +36,7 @@ slackbot.token=${SLACK_BOT_TOKEN:xoxb-format-12345}
|
||||
jit.dag.id=${JIT_DAG_ID:jit_dag}
|
||||
jit.oncall-approver.email=jit-slackbot@jit.com
|
||||
jit.slack.common.channel.id=${JIT_COMMON_CHANNEL:C06NDTBFA1G}
|
||||
jit.slack.policy.upload.channel.id=${JIT_POLICY_UPLOAD_CHANNEL:C0000000000}
|
||||
jit.request.config.path=classpath:jit
|
||||
jit.team-override.map={'Kubernetes Platform': 'Infra'}
|
||||
#pipeline creation
|
||||
|
||||
@@ -80,6 +80,7 @@ jit.dag.id=${JIT_DAG_ID:jit_dag}
|
||||
jit.gocd.dag.id=${JIT_GOCD_DAG_ID:jit_gocd_dag}
|
||||
jit.oncall-approver.email=jit-slackbot@jit.com
|
||||
jit.slack.common.channel.id=${JIT_COMMON_CHANNEL:C0000000000}
|
||||
jit.slack.policy.upload.channel.id=${JIT_POLICY_UPLOAD_CHANNEL:C0000000000}
|
||||
github.token=${GITHUB_CLOUD_OAUTH_TOKEN}
|
||||
gocd.pipelines.config=${GOCD_PIPELINES_CONFIG}
|
||||
vertical.owner.map={'lending':{'navi-data-science':'navi-data-science','default':'navi-medici'},'insurance':{'default':'navi-gi'},'sa':{'default':'navi-sa'},'amc':{'default':'navi-amc'},'navi-pay':{'default':'navi-pay'},'navi-ppl':{'default':'navi-ppl'}}
|
||||
|
||||
Reference in New Issue
Block a user