In the signup process of Spring Lemon, I'm trying to send the verification email.
I've put messages_en.properties and messages_fr.properties in my resourcesfolder.
Here is the relevant content of messages_en.properties
com.naturalprogrammer.spring.verifyEmail: Hi,<br/><br/>Your email id at XYZ is unverified. Please click the link below to get verified:<br/><br/>{0}<br/><br/>
But when I look at the logs, it sends the mail without replacing the {0} by the verifyLink.
I looked at the code and figured out that this portion of LemonService is the isse :
// send the mail
mailSender.send(user.getEmail(),
LemonUtil.getMessage("com.naturalprogrammer.spring.verifySubject"),
LemonUtil.getMessage(
"com.naturalprogrammer.spring.verifyEmail", verifyLink));
But the actual work is being done by this code in LemonUtil.java :
/**
* Gets a message from messages.properties
*
* #param messageKey the key of the message
* #param args any arguments
*/
public static String getMessage(String messageKey, Object... args) {
// http://stackoverflow.com/questions/10792551/how-to-obtain-a-current-user-locale-from-spring-without-passing-it-as-a-paramete
return messageSource.getMessage(messageKey, args,
LocaleContextHolder.getLocale());
}
I managed to solve it somehow by deleting the {0} in the .properties, and by adding the link myself like this :
// send the mail
mailSender.send(user.getEmail(),
LemonUtil.getMessage("com.naturalprogrammer.spring.verifySubject"),
LemonUtil.getMessage(
"com.naturalprogrammer.spring.verifyEmail", verifyLink) + verifyLink);
I think the getMessage method of org.springframework.context.MessageSource is not working properly.
My question is : what could prevent messageSource from working ?
Related
I have a java spring integration project that is receving emails through the below code:
ClassPathXmlApplicationContext ac =
new ClassPathXmlApplicationContext(
"/integration/gmail-imap-idle-config.xml");
DirectChannel inputChannel = ac.getBean("receiveChannel", DirectChannel.class);
inputChannel.subscribe(message -> {
org.springframework.messaging.Message<MimeMailMessage> received =
(org.springframework.messaging.Message<MimeMailMessage>) message;
log.info("content" + message);
List<String> sentences = null;
try {
} catch (Exception e) {
}
I get the email, and I can get the subject, but I can never actually extract the message body. How do I do this?
Thank you!
You have to use this option on the channel adapter:
simple-content="true"
See its description:
When 'true', messages produced by the source will be rendered by 'MimeMessage.getContent()'
which is usually just the body for a simple text email. When false (default) the content
is rendered by the 'getContent()' method on the actual message returned by the underlying
javamail implementation.
For example, an IMAP message is rendered with some message headers.
This attribute is provided so that users can enable the previous behavior, which just
rendered the body.
But still it is doubtful, since I see in case of GMail message it is never simple. The content is a MimeMultipart and we need to read its parts to get access to the real body.
So, this is how you should change your code as well:
log.info("content" + ((MimeMultipart) ((MimeMessage) message.getPayload()).getContent()).getBodyPart(0).getContent());
I am trying to rename google drive file resource. I guess that I just am missing something since all other actions like getting list of files, inserting files, moving files between directories are working.
Precondition: trying to rename file resource using this doc https://developers.google.com/drive/v2/reference/files/update with java (with only JDK stuff). Also, I do not use gdrive java sdk, apache http client or other libraries... Just clean JDK tools.
So what I do:
Here is the file metadata I am trying to send.
Modify title property in this metadata
Here is the code:
URLConnection urlConnection = new URL("https://www.googleapis.com/drive/v2/files/" + fileId).openConnection();
if (urlConnection instanceof HttpURLConnection) {
HttpURLConnection httpURLConnection = (HttpURLConnection) urlConnection;
httpURLConnection.setRequestMethod("PUT");
httpURLConnection.setDoOutput(true);
httpURLConnection.setRequestProperty("Authorization", "Bearer " + accessToken);
DataOutputStream outputStream = new DataOutputStream(httpURLConnection.getOutputStream());
outputStream.writeBytes(FILE_RESOURCE_METADATA_WITH_CHANGED_TITLE_IN_JSON);
outputStream.flush();
outputStream.close();
}
After making an actual call to API I receive 200 status code and File resource in response body (as expected) but title remains the same. So I got no error no changed title.
Moreover, the google drive api ignores any change in the file resource. It just returns same file resource without any changes applied (tried with title, description, originalFileName, parents properties).
What I tried also so far:
Sending only the properties that should be changed, like
{"title":"some_new_name"}
Result is same.
Changing PUT to PATCH. Unfortunately, PATCH is not supported by HttpURLConnection but workarounds gave same results. Changes are ignored.
Used google api exlorer (which can be found on the right side of API reference page) - and... it works. Filled only fileId and title property in request body and it worked. File is renamed.
What I am missing ?
Found the solution...
Adding this request property fixed the problem.
httpURLConnection.setRequestProperty("Content-Type", "application/json")
Try the sample java code given in the documentation.
Since the code deals to update existing file's metadata and content.
From the code, you will find file.setTitle(newTitle) which I think the one what you want to implement.
import com.google.api.client.http.FileContent;
import com.google.api.services.drive.Drive;
import com.google.api.services.drive.model.File;
import java.io.IOException;
// ...
public class MyClass {
// ...
/**
* Update an existing file's metadata and content.
*
* #param service Drive API service instance.
* #param fileId ID of the file to update.
* #param newTitle New title for the file.
* #param newDescription New description for the file.
* #param newMimeType New MIME type for the file.
* #param newFilename Filename of the new content to upload.
* #param newRevision Whether or not to create a new revision for this
* file.
* #return Updated file metadata if successful, {#code null} otherwise.
*/
private static File updateFile(Drive service, String fileId, String newTitle,
String newDescription, String newMimeType, String newFilename, boolean newRevision) {
try {
// First retrieve the file from the API.
File file = service.files().get(fileId).execute();
// File's new metadata.
file.setTitle(newTitle);
file.setDescription(newDescription);
file.setMimeType(newMimeType);
// File's new content.
java.io.File fileContent = new java.io.File(newFilename);
FileContent mediaContent = new FileContent(newMimeType, fileContent);
// Send the request to the API.
File updatedFile = service.files().update(fileId, file, mediaContent).execute();
return updatedFile;
} catch (IOException e) {
System.out.println("An error occurred: " + e);
return null;
}
}
// ...
}
Hope this give you some points.
I am working on a project that requires loading incoming emails, process the email that only passed the filtering criteria, in the end mark the email has been SEEN and modify the subject.
There are couple of issues I couldn't figure out:
mail-filter-expression is not working for me. I want to find out the mails that has subject start with "AAA" and the sender's email is "BBB#gmail.com".
Here is my expression:
"(subject matches '(?i)AAA.*')|(sender matches '(?i).BBB#gmail.com.')"
The way how to set user defined flag is very slow. I have to load all email from the open folder and find the email that match with the message Id of current reading message. Is there any better and faster way to do this?
spring-context.xml
<int-mail:imap-idle-channel-adapter id="customAdapter"
store-uri="imaps://XXXX:XXXX#imap.gmail.com:993/inbox"
channel="receiveChannel"
auto-startup="true"
should-delete-messages="false"
should-mark-messages-as-read="true"
java-mail-properties="mailProperties"
mail-filter-expression="(subject matches '(?i)AAA.*')|(sender matches '(?i).*BBB#gmail.com.*')"/>/>
<bean id="mailReceiver" class="com.mfr.email.EmailReceiver"/>
<int:service-activator input-channel="receiveChannel" ref="mailReceiver" method="process"/>
EmailReceiver.java
public void process(Message message) {
System.out.println("Got mail match with filter criteria!");
try {
String subject = message.getSubject();
.........
Folder folder = message.getFolder();
folder.open(Folder.READ_WRITE);
String messageId = ((MimeMessage)message).getMessageID();
Message[] messages = folder.getMessages();
FetchProfile contentsProfile = new FetchProfile();
contentsProfile.add(FetchProfile.Item.ENVELOPE);
contentsProfile.add(FetchProfile.Item.CONTENT_INFO);
contentsProfile.add(FetchProfile.Item.FLAGS);
folder.fetch(messages, contentsProfile);
for (int i = 0; i < messages.length; i++) {
Message loopMsg = messages[i];
String loopMsgId = ((MimeMessage)loopMsg ).getMessageID();
if (loopMsgId.equals(messageId)) {
Flags processedFlag = new Flags();
processedFlag.add(Flags.Flag.ANSWERED);
processedFlag.add(Flags.Flag.SEEN);
loopMsg.setFlags(processedFlag, true);
break;
}
}
folder.expunge();
folder.close(true);
} catch (Exception e) {
e.printStackTrace();
}
}
The common folder protocols (IMAP, POP3) do not allow you to modify messages. You can set the SEEN flag with IMAP, although accessing the message will typically set that for you automatically. Depending on why you're trying to change the Subject, you might be better off setting a user-defined Flag on the message. If you really need to change the Subject, you'll need to copy the message using the MimeMessage copy constructor, modify the copy, append the copy to the folder, and delete the original.
Also, your code above appears to be using a Message object unrelated to the Folder you're opening. You shouldn't do that. Once you close a Folder, all the Message objects from that Folder are invalid. If you reopen the Folder, you need to get a new Message object corresponding to the message you're dealing with (e.g., by looking it up using the UID of the message).
I have created a contact page and contact model that has From Subject and Message as string values. Now when I try to send email from my development environment with code below, it won't work. I browsed around a bit looking for a solution but several things are unclear to me since I haven't dealt with this too often.
This is the method I use for sending e-mail. Commented part is also one of the attempts.
The error I get is: System.Net.Sockets.SocketException: A connection attempt failed because the connected party did not properly respond after a period of time, or established connection failed because connected host has failed to respond
I realize that this probably has something to do with me being on dev.env., does it? What am I doing wrong?
public class Email
{
public void Send(Contact contact)
{
MailMessage mail = new MailMessage(
contact.From,
ConfigurationManager.AppSettings["ContactEmail"],
contact.Subject,
contact.Message);
//new SmtpClient().Send(mail);
WebMail.Send(ConfigurationManager.AppSettings["ContactEmail"], contact.Subject, contact.Message, null, null, null, false, null);
}
}
Can you send mail like this, instead?
internal static void SendEmail(MailAddress fromAddress, MailAddress toAddress, string subject, string body)
{
var message = new MailMessage(fromAddress, toAddress)
{
Subject = subject,
Body = body
};
var client = new SmtpClient("smtpServerName");
client.Send(message);
}
Ref. asp.net mvc framework, automatically send e-mail
I think you need to check port number in you config file.
I have a project using Struts2 on the server side and I am trying to make it work with jqGrid (using JSON format). I have several tables made with jqGrid and I am using the add/edit/delete buttons from navGrid.
The main problem I have is with server validation error messages. I have created custom validators and they work with jsp pages, using s:fielderror, but I don't know how to make them work for add/edit popups from jqGrid. I am aware that jqGrid provides the users with custom validation on client, but this has its limitations(think about testing whether the email of a user is unique, you definitely must use the database for that, or if some fields depend on each other and must be tested together, like if isManager is true, then the managerCode must be not empty and vice versa...).
When I use the client validation, there is a message in the add/edit window whenever an error occurs. Can I somehow display my server validation error messages in the window in the same way?
I managed to solve the issue. I will explain how using a simple custom validator for age field, which must be > 18 for an Employee. It is supposed next that the validator was already declared in validators.xml and mapped on the action and that the message in case of ValidationException is "An employee should be older than 18.".
Using Firebug, I figured out that the id of the error area in the form is FormError. It is possible to configure a callback function errorTextFormat in jqgrid, in order to get a response from the server and process it. In the jqgrid configuration, one could write
errorTextFormat : errorFormat,
with
var errorFormat = function(response) {
var text = response.responseText;
$('#FormError').text(text); //sets the text in the error area to the validation //message from the server
return text;
};
The problem is now that the server will send implicitly a response containing the whole exception stack trace. To deal with it, I decided to create a new result type.
public class MyResult implements Result {
/**
*
*/
private static final long serialVersionUID = -6814596446076941639L;
private int errorCode = 500;
public void execute(ActionInvocation invocation) throws Exception {
ActionContext actionContext = invocation.getInvocationContext();
HttpServletResponse response = (HttpServletResponse) actionContext
.get("com.opensymphony.xwork2.dispatcher.HttpServletResponse");
Exception exception = (Exception) actionContext
.getValueStack().findValue("exception");
response.setStatus(getErrorCode());
try {
PrintWriter out = response.getWriter();
out.print(exception.getMessage());
} catch (IOException e) {
throw e;
}
}
/**
* #return the errorCode
*/
public int getErrorCode() {
return errorCode;
}
/**
* #param errorCode the errorCode to set
*/
public void setErrorCode(int errorCode) {
this.errorCode = errorCode;
}
}
It must also be configured in struts.xml as follows:
<package name="default" abstract="true" extends="struts-default">
...
<result-types>
<result-type name="validationError"
class="exercises.ex5.result.MyResult">
</result-type>
</result-types>
...
<action name="myaction">
...
<result name="validationException" type="validationError"></result>
<exception-mapping result="validationException"
exception="java.lang.Exception"></exception-mapping>
</action>
...
</package>
These are the steps I followed to get a validation error message in the add/edit window and now it works.