Q: I already have a form on my website where I collect contact information. Can I use the Site Visitor API to send contact information from that form directly to my Constant Contact account?
A: Yes. This is the primary purpose of the Site Visitor API.
Q: I want two different signup forms on my website, one that will add contacts directly to list A and one that will add contacts directly to list B. Can I do this?
A: Yes. The Site Visitor API will enable you to have as many forms on your website as you would like and have each of them submit the contact to a specific list or lists. You will control which list(s) the contact gets added to through the server-side script that handles the form data and makes the call to the API.
Q: What skills are needed to implement the Site Visitor API?
A: Thorough understanding of web programming and server-side script development is necessary in order to successfully implement the Site Visitor API.
Q: I do not have access to web programming resources. Can Constant Contact help?
A: Constant Contact has identified business partners that have web programming expertise and who can complete the integration for an additional fee. We can provide you the contact information of these business partners if you are interested.
Q: Can I implement the Site Visitor API through an HTML web page?
A: While it is possible to implement the API within your client-side HTML page, we do not recommend you do this because the login name and password information you pass through the API will be visible. Furthermore, the “success” page is merely a blank screen with a zero in the upper left corner, so the customer experience will be poor.
Q: What programming languages can be used to integrate the Site Visitor API?
A: The API can be called using either a GET or POST method. Therefore, you can use the programming language that you are most familiar with.
Q: Within my server-side script I have constructed the URL call to the API correctly but my contact is not being properly subscribed, unsubscribed or updated. What’s going on?
A: There are a few common reasons why this could be happening:
--- One or more of the required parameters (login name, login password, email address, list name) are missing or incorrect.
--- The parameter names or values are not defined in the correct case. For example if the list you are adding the contact to is named “Customers” defining this name as “customers” in the API call will not work. You need to match uppercase and lowercase characters exactly.
--- You have made too many calls to the API with an incorrect password and now the account has been locked for too many failed logins. Contact Customer Support to have the account reset.
--- The list does not exist. The list that you are adding the contact to must already exist within the Constant Contact account.
Q: Can I use the Site Visitor APIs to find out what list(s) a contact is on?
A: No. At this time the Site Visitors APIs enable you to subscribe and unsubscribe a contact to / from your Constant Contact account. It is a one way communication channel from your web site to your Constant Contact account and the functionality does not support querying your account for information. HOWEVER...you can now use the REST APIs, documented on this web site, to determine what list a contact is on. You can also update the list association of that contact. Please see the Contacts Collection Resource for more information.
Q: Can I use the Site Visitor APIs for synchronizing my database with Constant Contact or adding / removing hundreds or thousands of email addresses at a time.
A: No. The Site Visitor APIs are meant to be used for subscribing or unsubscribing one contact at a time based on signup activity on your website. WHILE the SiteVisitor APIs are meant for managing individual contacts and *MAY NOT* be used for managing large sets of contacts - there is another solution. You can now use the REST APIs, documented on this web site, for bulk uploads and downloads of contacts. Please see the Activities Resource for more information.
Q: Will a welcome email be sent from Constant Contact when I add a contact with the SiteVisitor APIs?
A: Not with the SiteVisitor APIs. HOWEVER...you can now use the REST APIs, documented on this web site, to add individual contacts. With the REST APIs, the developer can indicate if the contact was 'added by the contact themself' (with, for example, a form on a public website) or 'added by the Constant Contact Customer' (with, for example, a desktop form used by the Constant Contact customer). Contacts who are 'added by the contact themself' receive a welcome email. Please see the Contacts Collection Resource for more information.
Q: Will a thank you page be shown when I add a contact?
A: No. If you would like the contact to see a thank you page after you have added them to your Constant Contact account, you will need to program this on your end and host that page on your own web servers. A developer has posted a simple sample script, in PHP, in this thread in the Constant Contact ConnectUp! community.
Q: I am receiving a 400 error when I make a call to the API, what does that mean?
A: The 400 code is not specific to the Constant Contact Subscriber API, rather it is an indication that the API call could not be understood by the server due most likely due to incorrect syntax. Make sure you are including the requirement parameters and that the values you are passing are the correct case. Refer to the API documentation here.
Q: Does the daily or weekly Site Visitor Signup Report include contacts that are added through the API?
A: Yes.
Q: If I use the Site Visitor API to handle unsubscribes from my website, can the Unsubscribe link in the footer of my emails be directed back to my website?
A: No. The unsubscribe link in the footer of your emails must point back directly to your Constant Contact account. This ensures that unsubscribe requests are being handled properly.
Q: I am having problems getting my Flash application to run and I think it is related to cross-site scripting limitations. Will Constant Contact add my cross domain file on their server to allow my application access?
A: While we can't manage individual cross domain files, we can suggest another approach that should work. Create a small proxy script on your server which acts as a proxy for the Flash file and invoke the Constant Contact APIs from that proxy. Here is PHP example (put this PHP file where the Flash file is served on your webserver):
Notes:
This proxy can be written in php, asp or jsp here. See more information here: http://kb.adobe.com/selfservice/viewContent.do?externalId=tn_16520&sliceId=2.
In this example, we named the PHP file proxy.php.
Now you can write the flex code to access the php or some other proxy that you have written and placed in your webserver.
Following is the flex code you can use to read the php file above (which inturn invokes the CTCT api url):
var httpService:HTTPService = new HTTPService();
var url:String = "proxy.php?ea="+emailText.text;
httpService.url = url;
httpService.showBusyCursor=true;
httpService.send();
You will find more on creating a signup form with Flash here.
Q: I am receiving a 400 error when I make a call to the API, what does that mean?
A: The 400 code is not specific to the Constant Contact Subscriber API, rather it is an indication that the API call could not be understood by the server due most likely due to incorrect syntax. One common reason for a 400 error (in the SiteVisitorAPI) is invalid login credentials. As a first step, make sure you can login to http://www.constantcontact.com with the login credentials which you are using in the API. If this does not solve the problem, make sure you are including the requirement parameters and that the values you are passing are the correct case. Refer to the API documentation here.
Q:
I am trying to use the API from a client side HTML form. The API works up to a point. I can add an email address to the list with no problem. But the page then displays a zero return code. This is not want I need. The user will see the 0 and wonder what
happened. I need the API to return to my site (or to another URL I specify) or it has not value to me.
A:
What you are seeing is the return code from the HTTP call you are making. This is of course not intended to be displayed to the user, but rather, to be captured by your program and treated appropriately (ie. If there is an error, you will receive a non-zero return code and you present a message to the user).
To do this, your program will need to trap the error and continue.
Once you have invoked the http: and managed the error, your program can redirect the user accordingly. There are simple examples of this (in PHP and ColdFusion) posted on our developer web site, here:
http://developer.constantcontact.com/doc/siteVisitorAPI
It addition, Constant Contact Community members have posted examples in the ConnectUp! community here:
http://community.constantcontact.com/forum/default.aspx?g=posts&t=2509
Comments
hi..this is harsha
hello
java source code for adding individual constantcontact from my application and is it possible??
please give me replyy
mohanharsha
i am trying to add this individual constantcontact from java cod
i am trying to add this individual constantcontact from java code using REST API ..i am attaching code written by me in tht preparing the way of content is correct or wrong i don't know ,if i run the attached servlet it displays 400 /401 error can anyone rectify this problem ..tht means plz chk my code and give changes if require ,
plz chk this attachemnt
its very very urgent,....
package com.constantcontact.webservices.sample;
import java.util.List;
import java.io.IOException;
import java.net.URLEncoder;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.Map;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import org.apache.commons.httpclient.HostConfiguration;
import org.apache.commons.httpclient.HttpClient;
import org.apache.commons.httpclient.HttpException;
import org.apache.commons.httpclient.UsernamePasswordCredentials;
import org.apache.commons.httpclient.auth.AuthPolicy;
import org.apache.commons.httpclient.auth.AuthScope;
import org.apache.commons.httpclient.auth.DigestScheme;
import org.apache.commons.httpclient.methods.PostMethod;
import org.apache.commons.httpclient.methods.RequestEntity;
import org.apache.commons.httpclient.methods.StringRequestEntity;
import org.apache.log4j.Logger;
import com.constantcontact.webservices.sample.model.AuthDetails;
import com.constantcontact.webservices.sample.model.ContactList;
import com.constantcontact.webservices.sample.util.Constants;
public class ContactAddServlet extends HttpServlet{
private static final Logger LOG = Logger.getLogger(ContactAddServlet.class);
/**
* Handles the get request.
*/
protected void doPost(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
System.out.println("inside servlet..........................");
// Extract username, apikey, and password from request and create
// as credentials for use with Abdera client
AuthDetails authDetails = this.extractAuthDetails(request);
ContactList contactDetails = this.extractContactDetails(request);
UsernamePasswordCredentials credentials = new UsernamePasswordCredentials(authDetails
.getApiKey()+ "%" + authDetails.getUserName(), authDetails.getPassword());
System.out.println("credentials------- >> "+credentials.getUserName());
// HTTPClient setup
HostConfiguration hostConfiguration = new HostConfiguration();
hostConfiguration.setHost(Constants.HOST);
AuthScope authScope = new AuthScope(Constants.HOST, Constants.PORT, Constants.AUTH_REALM);
System.out.println("authScope ------host------- >> "+authScope.getHost());
System.out.println("authScope ------port------- >> "+authScope.getPort());
System.out.println("authScope ------Realm------- >> "+authScope.getRealm());
AuthPolicy.registerAuthScheme("Digest", DigestScheme.class);
System.out.println("authScope ------schema------- >> "+AuthPolicy.getDefaultAuthPrefs());
HttpClient httpClient = new HttpClient();
// This is to make HttpClient pick the Digest authentication
// scheme
List list = new ArrayList();
list.add(AuthPolicy.DIGEST);
httpClient.getParams().setParameter(AuthPolicy.AUTH_SCHEME_PRIORITY, list);
httpClient.getState().setCredentials(authScope, credentials);
StringBuffer content = new StringBuffer("activityType=").append(URLEncoder.encode("ADD_CONTACTS","UTF-8"));
content.append("&sortBy=EMAIL_ADDRESS");
content.append("&OptInSource=ACTION_BY_CONTACT");
content.append("&type=application/vnd.ctct+xml");
content.append("&EmailAddress=mohanbhimineni@gmail.com");
content.append("&FirstName=mohan");
content.append("&LastName=krishna");
content.append("&id="+contactDetails.getId());
content.append("&name="+contactDetails.getName());
content.append("&link="+contactDetails.getLink());
content.append("&shortName="+contactDetails.getOptInDefault());
content.append("&sortOrder="+contactDetails.getOptInDefault());
content.append("&optInDefault="+contactDetails.getTitle());
RequestEntity requestEntity = new StringRequestEntity(content.toString(),"application/atom+xml", "UTF-8");
System.out.println("requestEntity >>>>>>>>>>>> "+requestEntity.toString().valueOf(content));
Map postResults = this.postToServer(httpClient,authDetails,requestEntity);
// postResult will hold the URL for the created Contact if successful
if (Boolean.parseBoolean(postResults.get("success"))) {
// Make sure the authentication fields are prefilled
// by passing them back to the request.
// Create URL to redirect user to view the created Activity.
request.setAttribute(Constants.PARAM_NAME_API_KEY, authDetails.getApiKey());
request.setAttribute(Constants.PARAM_NAME_USER_NAME, authDetails.getUserName());
request.setAttribute(Constants.PARAM_NAME_PASSWORD, authDetails.getPassword());
StringBuffer redirectUrl = new StringBuffer();
redirectUrl.append("showActivity?");
redirectUrl.append(Constants.PARAM_NAME_API_KEY);
redirectUrl.append("=");
redirectUrl.append(authDetails.getApiKey());
redirectUrl.append("&");
redirectUrl.append(Constants.PARAM_NAME_USER_NAME);
redirectUrl.append("=");
redirectUrl.append(authDetails.getUserName());
redirectUrl.append("&");
redirectUrl.append(Constants.PARAM_NAME_PASSWORD);
redirectUrl.append("=");
redirectUrl.append(authDetails.getPassword());
redirectUrl.append("&activityId=");
redirectUrl.append(postResults.get("location").substring(
postResults.get("location").lastIndexOf('/') + 1));
response.sendRedirect(redirectUrl.toString());
} else {
StringBuffer errorMsg = new StringBuffer();
errorMsg.append("There has been an error: ");
errorMsg.append(postResults.get("statusCode"));
errorMsg.append(" - ");
errorMsg.append(postResults.get("statusText"));
request.setAttribute("error", errorMsg.toString());
super.getServletContext().getRequestDispatcher("/error.jsp").forward(request, response);
return;
}
}
/**
* Method handles the actual HTTP post and returns a String that holds the
* location of the created Activity if the post was successful and has an
* error message if it was unsuccessful
*
* @param client
* @param authDetails
* @param requestEntity
* @return
* @throws HttpException
* @throws IOException
*/
private Map postToServer(HttpClient client, AuthDetails authDetails,RequestEntity requestEntity) throws HttpException, IOException {
// Post to activities resource for specific Site Owner (username)
//client.put(Constants.URI + "/ws/customers/"+ authDetails.getUserName() + "/contacts", requestEntity);
PostMethod httpPost = new PostMethod(Constants.URI + "/ws/customers/"+authDetails.getUserName()+"/contacts");
Map results = new HashMap();
httpPost.setRequestEntity(requestEntity);
try {
// execute POST and capture status.
int status = client.executeMethod(httpPost);
System.out.println("status >>>>>>>>>>> "+status);
if (status >= 200 && status < 300) {
results.put("success", "true");
results.put("location", httpPost.getResponseHeader("Location").getValue());
} else {
results.put("success", "false");
results.put("statusCode", String.valueOf(status));
results.put("statusText", httpPost.getStatusText());
}
} finally {
// release any connection resources used by the method
httpPost.releaseConnection();
}
return results;
}
/**
* Method extracts Contact fields from the request object and returns
* them in a Map
*
* @param request
* @return
*/
protected ContactList extractContactDetails(HttpServletRequest request) {
ContactList contactDetails = new ContactList();
/*contactDetails.setId(request.getParameter(Constants.PARAM_NAME_ID));
contactDetails.setName(request.getParameter(Constants.PARAM_NAME_NAME));
contactDetails.setLink( request.getParameter(Constants.PARAM_NAME_LINK));
contactDetails.setTitle(request.getParameter(Constants.PARAM_NAME_TITLE));
contactDetails.setShortName(request.getParameter(Constants.PARAM_NAME_SHORT_NAME));
contactDetails.setSortOrder(0);
contactDetails.setOptInDefault(request.getParameter(Constants.PARAM_NAME_OPT_DEF));*/
contactDetails.setId("http://api.constantcontact.com/ws/customers/epost2mohan/contacts/1");
contactDetails.setName("mohan");
contactDetails.setLink("/ws/customers/epost2mohan/contacts/1");
contactDetails.setTitle("Add contacts");
contactDetails.setShortName("mohan");
contactDetails.setSortOrder(1);
contactDetails.setOptInDefault("aaaa");
return contactDetails;
}
/**
* Method extracts authentication fields from the request object and returns
* them in a Map
*
* @param request
* @return
*/
protected AuthDetails extractAuthDetails(HttpServletRequest request) {
AuthDetails authDetails = new AuthDetails();
authDetails.setApiKey(request.getParameter(Constants.PARAM_NAME_API_KEY));
authDetails.setUserName( request
.getParameter(Constants.PARAM_NAME_USER_NAME));
authDetails.setPassword( request
.getParameter(Constants.PARAM_NAME_PASSWORD));
return authDetails;
}
}