aboutsummaryrefslogtreecommitdiff
path: root/juick-server/src/main/java/com/juick/server/api/Service.java
diff options
context:
space:
mode:
Diffstat (limited to 'juick-server/src/main/java/com/juick/server/api/Service.java')
-rw-r--r--juick-server/src/main/java/com/juick/server/api/Service.java117
1 files changed, 117 insertions, 0 deletions
diff --git a/juick-server/src/main/java/com/juick/server/api/Service.java b/juick-server/src/main/java/com/juick/server/api/Service.java
new file mode 100644
index 00000000..f67f6986
--- /dev/null
+++ b/juick-server/src/main/java/com/juick/server/api/Service.java
@@ -0,0 +1,117 @@
+package com.juick.server.api;
+
+import com.juick.User;
+import com.juick.server.CommandsManager;
+import com.juick.server.EmailManager;
+import com.juick.server.util.HttpForbiddenException;
+import com.juick.server.util.UserUtils;
+import com.juick.service.UserService;
+import org.apache.commons.codec.digest.DigestUtils;
+import org.apache.commons.io.IOUtils;
+import org.apache.commons.lang3.StringUtils;
+import org.apache.commons.mail.util.MimeMessageParser;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+import org.springframework.beans.factory.annotation.Value;
+import org.springframework.http.HttpStatus;
+import org.springframework.stereotype.Controller;
+import org.springframework.web.bind.annotation.PostMapping;
+import org.springframework.web.bind.annotation.ResponseStatus;
+import springfox.documentation.annotations.ApiIgnore;
+
+import javax.inject.Inject;
+import javax.mail.Session;
+import javax.mail.internet.InternetAddress;
+import javax.mail.internet.MimeMessage;
+import java.io.FileOutputStream;
+import java.io.IOException;
+import java.io.InputStream;
+import java.net.URI;
+import java.nio.charset.StandardCharsets;
+import java.nio.file.Paths;
+import java.util.Properties;
+import java.util.Scanner;
+import java.util.UUID;
+
+@Controller
+public class Service {
+ private static Logger logger = LoggerFactory.getLogger(Post.class);
+ @Inject
+ private UserService userService;
+
+ @Inject
+ CommandsManager commandsManager;
+ @Value("${api_user:juick}")
+ private String serviceUser;
+ @Value("${upload_tmp_dir:#{systemEnvironment['TEMP'] ?: '/tmp'}}")
+ private String tmpDir;
+ Session session = Session.getDefaultInstance(new Properties());
+
+ @ApiIgnore
+ @PostMapping("/mail")
+ @ResponseStatus(value = HttpStatus.OK)
+ public void processMail(InputStream data) throws Exception {
+ if (UserUtils.getCurrentUser().getName().equals(serviceUser)) {
+ MimeMessage msg = new MimeMessage(session, data);
+ logger.info("got msg {}", msg.toString());
+ String from = msg.getFrom() == null || msg.getFrom().length > 1 ? ((InternetAddress) msg.getSender()).getAddress()
+ : ((InternetAddress) msg.getFrom()[0]).getAddress();
+
+ User visitor = userService.getUserByEmail(from);
+ if (!visitor.isAnonymous()) {
+ MimeMessageParser parser = new MimeMessageParser(msg);
+ parser.parse();
+ final String[] body = {parser.getPlainContent()};
+ if (body[0] == null) {
+ parser.getAttachmentList().stream()
+ .filter(a -> a.getContentType().equals("text/plain")).findFirst()
+ .ifPresent(a -> {
+ try {
+ body[0] = IOUtils.toString(a.getInputStream(), StandardCharsets.UTF_8);
+ logger.info("got text: {}", body[0]);
+ } catch (IOException e) {
+ logger.info("attachment error: {}", e);
+ }
+ });
+ }
+ final String[] attachmentFName = new String[1];
+ parser.getAttachmentList().stream().filter(a ->
+ a.getContentType().equals("image/jpeg") || a.getContentType().equals("image/png"))
+ .findFirst().ifPresent(a -> {
+ logger.info("got attachment: {}", a.getContentType());
+ String attachmentType;
+ if (a.getContentType().equals("image/jpeg")) {
+ attachmentType = "jpg";
+ } else {
+ attachmentType = "png";
+ }
+ attachmentFName[0] = DigestUtils.md5Hex(UUID.randomUUID().toString()) + "." + attachmentType;
+ try {
+ logger.info("got inputstream: {}", a.getInputStream());
+ FileOutputStream fos = new FileOutputStream(Paths.get(tmpDir, attachmentFName[0]).toString());
+ IOUtils.copy(a.getInputStream(), fos);
+ fos.close();
+ } catch (IOException e) {
+ logger.info("attachment error: {}", e);
+ }
+ });
+ String[] inReplyToHeaders = msg.getHeader("In-Reply-To");
+ if (inReplyToHeaders != null && inReplyToHeaders.length > 0) {
+ Scanner inReplyToScanner = new Scanner(inReplyToHeaders[0].trim()).useDelimiter(EmailManager.MSGID_PATTERN);
+ int mid = Integer.parseInt(inReplyToScanner.next());
+ int rid = Integer.parseInt(inReplyToScanner.next());
+ logger.info("Message is reply to #{}/{}", mid, rid);
+ body[0] = rid > 0 ? String.format("#%d/%d %s", mid, rid, body[0])
+ : String.format("#%d %s", mid, body[0]);
+ }
+ URI attachmentUri = StringUtils.isNotEmpty(attachmentFName[0]) ? URI.create(String.format("juick://%s", attachmentFName[0]))
+ : URI.create(StringUtils.EMPTY);
+ commandsManager.processCommand(visitor, body[0], attachmentUri);
+ } else {
+ logger.info("not registered: {}", from);
+ }
+ } else {
+ throw new HttpForbiddenException();
+ }
+ }
+}