diff options
| author | Jesse Morgan <jesse@jesterpm.net> | 2014-03-24 21:38:02 -0700 | 
|---|---|---|
| committer | Jesse Morgan <jesse@jesterpm.net> | 2014-03-31 19:39:30 -0700 | 
| commit | adba5974bae4da0def1f13d47cfcf28a37e3cf7a (patch) | |
| tree | e660c0090f942d4ac846666b0aabdfe83ea020e9 /src | |
| parent | be16eedfb3570da2dcd3975948419ecc3d996253 (diff) | |
Enabling the Feed and various bug fixes.
* Fixing thread ordering.
* Adding a limit of 5 threads per topic.
* Changing frontend /account references to UserRecord.
Diffstat (limited to 'src')
11 files changed, 106 insertions, 102 deletions
diff --git a/src/com/p4square/grow/backend/db/CassandraCollectionProvider.java b/src/com/p4square/grow/backend/db/CassandraCollectionProvider.java index cc11828..5e83247 100644 --- a/src/com/p4square/grow/backend/db/CassandraCollectionProvider.java +++ b/src/com/p4square/grow/backend/db/CassandraCollectionProvider.java @@ -7,7 +7,7 @@ package com.p4square.grow.backend.db;  import java.io.IOException;  import java.util.Collections; -import java.util.HashMap; +import java.util.LinkedHashMap;  import java.util.Map;  import com.netflix.astyanax.model.Column; @@ -45,21 +45,21 @@ public class CassandraCollectionProvider<V> implements CollectionProvider<String      @Override      public Map<String, V> query(String collection, int limit) throws IOException { -        Map<String, V> result = new HashMap<>(); +        Map<String, V> result = new LinkedHashMap<>();          ColumnList<String> row = mDb.getRow(mCF, collection);          if (!row.isEmpty()) {              int count = 0;              for (Column<String> c : row) { +                if (limit >= 0 && ++count > limit) { +                    break; // Limit reached. +                } +                  String key = c.getName();                  String blob = c.getStringValue();                  V obj = decode(blob);                  result.put(key, obj); - -                if (limit >= 0 && ++count > limit) { -                    break; // Limit reached. -                }              }          } diff --git a/src/com/p4square/grow/backend/feed/ThreadResource.java b/src/com/p4square/grow/backend/feed/ThreadResource.java index c0604a8..e8f46c2 100644 --- a/src/com/p4square/grow/backend/feed/ThreadResource.java +++ b/src/com/p4square/grow/backend/feed/ThreadResource.java @@ -8,7 +8,6 @@ import java.io.IOException;  import java.util.Date;  import java.util.Map; -import java.util.UUID;  import org.restlet.data.Status;  import org.restlet.resource.ServerResource; @@ -68,7 +67,7 @@ public class ThreadResource extends ServerResource {      }      /** -     * POST a new thread to the topic. +     * POST a new message to the thread.       */      @Override      protected Representation post(Representation entity) { @@ -86,7 +85,7 @@ public class ThreadResource extends ServerResource {              // Force the thread id and message to be what we expect.              message.setThreadId(mThreadId); -            message.setId(String.format("%x-%s", System.currentTimeMillis(), UUID.randomUUID().toString())); +            message.setId(Message.generateId());              if (message.getCreated() == null) {                  message.setCreated(new Date()); diff --git a/src/com/p4square/grow/backend/feed/TopicResource.java b/src/com/p4square/grow/backend/feed/TopicResource.java index 5826355..24b6a92 100644 --- a/src/com/p4square/grow/backend/feed/TopicResource.java +++ b/src/com/p4square/grow/backend/feed/TopicResource.java @@ -8,7 +8,6 @@ import java.io.IOException;  import java.util.Date;  import java.util.Map; -import java.util.UUID;  import org.restlet.data.Status;  import org.restlet.resource.ServerResource; @@ -50,10 +49,20 @@ public class TopicResource extends ServerResource {              return new JacksonRepresentation(FeedDataProvider.TOPICS);          } -        // TODO: Support limit query parameter. +        // Parse limit query parameter. +        int limit = -1; +        String limitString = getQueryValue("limit"); +        if (limitString != null) { +           try { +               limit = Integer.parseInt(limitString); +           } catch (NumberFormatException e) { +               setStatus(Status.CLIENT_ERROR_BAD_REQUEST); +               return null; +           } +        }          try { -            Map<String, MessageThread> threads = mBackend.getThreadProvider().query(mTopic); +            Map<String, MessageThread> threads = mBackend.getThreadProvider().query(mTopic, limit);              return new JacksonRepresentation(threads.values());          } catch (IOException e) { @@ -90,7 +99,7 @@ public class TopicResource extends ServerResource {              MessageThread newThread = MessageThread.createNew();              // Force the thread id and message to be what we expect. -            message.setId(String.format("%x-%s", System.currentTimeMillis(), UUID.randomUUID().toString())); +            message.setId(Message.generateId());              message.setThreadId(newThread.getId());              newThread.setMessage(message); diff --git a/src/com/p4square/grow/frontend/AccountRedirectResource.java b/src/com/p4square/grow/frontend/AccountRedirectResource.java index eb29e53..0bb40a2 100644 --- a/src/com/p4square/grow/frontend/AccountRedirectResource.java +++ b/src/com/p4square/grow/frontend/AccountRedirectResource.java @@ -14,13 +14,13 @@ import org.restlet.resource.ServerResource;  import org.apache.log4j.Logger; -import net.jesterpm.fmfacade.json.JsonRequestClient; -import net.jesterpm.fmfacade.json.JsonResponse; -import net.jesterpm.fmfacade.json.ClientException; -  import net.jesterpm.fmfacade.FreeMarkerPageResource;  import com.p4square.grow.config.Config; +import com.p4square.grow.model.UserRecord; +import com.p4square.grow.provider.Provider; +import com.p4square.grow.provider.DelegateProvider; +import com.p4square.grow.provider.JsonEncodedProvider;  /**   * This resource simply redirects the user to either the assessment @@ -32,7 +32,7 @@ public class AccountRedirectResource extends ServerResource {      private static final Logger LOG = Logger.getLogger(AccountRedirectResource.class);      private Config mConfig; -    private JsonRequestClient mJsonClient; +    private Provider<String, UserRecord> mUserRecordProvider;      // Fields pertaining to this request.      private String mUserId; @@ -44,7 +44,14 @@ public class AccountRedirectResource extends ServerResource {          GrowFrontend growFrontend = (GrowFrontend) getApplication();          mConfig = growFrontend.getConfig(); -        mJsonClient = new JsonRequestClient(getContext().getClientDispatcher()); +        mUserRecordProvider = new DelegateProvider<String, String, UserRecord>( +                new JsonRequestProvider<UserRecord>(getContext().getClientDispatcher(), +                    UserRecord.class)) { +            @Override +            public String makeKey(String userid) { +                return getBackendEndpoint() + "/accounts/" + userid; +            } +        };          mUserId = getRequest().getClientInfo().getUser().getIdentifier();      } @@ -56,25 +63,17 @@ public class AccountRedirectResource extends ServerResource {      protected Representation get() {          try {              // Fetch account Map. -            Map account = new HashMap(); -            try { -                JsonResponse response = backendGet("/accounts/" + mUserId); -                if (response.getStatus().isSuccess()) { -                    account = response.getMap(); -                } -            } catch (ClientException e) { - -            } +            UserRecord user = mUserRecordProvider.get(mUserId);              // Check for the new believers cookie              String cookie = getRequest().getCookies().getFirstValue(NewBelieverResource.COOKIE_NAME);              if (cookie != null && cookie.length() != 0) { -                account.put("landing", "training"); -                account.put("newbeliever", "true"); -                backendPut("/accounts/" + mUserId, account); +                user.setLanding("training"); +                user.setNewBeliever(true); +                mUserRecordProvider.put(mUserId, user);              } -            String landing = (String) account.get("landing"); +            String landing = user.getLanding();              if (landing == null) {                  landing = "assessment";              } @@ -97,31 +96,4 @@ public class AccountRedirectResource extends ServerResource {      private String getBackendEndpoint() {          return mConfig.getString("backendUri", "riap://component/backend");      } - -    /** -     * Helper method to send a GET to the backend. -     */ -    private JsonResponse backendGet(final String uri) { -        LOG.debug("Sending backend GET " + uri); - -        final JsonResponse response = mJsonClient.get(getBackendEndpoint() + uri); -        final Status status = response.getStatus(); -        if (!status.isSuccess() && !Status.CLIENT_ERROR_NOT_FOUND.equals(status)) { -            LOG.warn("Error making backend request for '" + uri + "'. status = " + response.getStatus().toString()); -        } - -        return response; -    } - -    protected JsonResponse backendPut(final String uri, final Map data) { -        LOG.debug("Sending backend PUT " + uri); - -        final JsonResponse response = mJsonClient.put(getBackendEndpoint() + uri, data); -        final Status status = response.getStatus(); -        if (!status.isSuccess() && !Status.CLIENT_ERROR_NOT_FOUND.equals(status)) { -            LOG.warn("Error making backend request for '" + uri + "'. status = " + response.getStatus().toString()); -        } - -        return response; -    }  } diff --git a/src/com/p4square/grow/frontend/FeedData.java b/src/com/p4square/grow/frontend/FeedData.java index 55e845c..feb03a1 100644 --- a/src/com/p4square/grow/frontend/FeedData.java +++ b/src/com/p4square/grow/frontend/FeedData.java @@ -62,8 +62,15 @@ public class FeedData {          mMessageProvider = new JsonRequestProvider<Message>(clientDispatcher, Message.class);      } -    public List<MessageThread> getThreads(final String topic) throws IOException { -        return mThreadsProvider.get(makeUrl(topic)); +    /** +     * Get the threads for a topic. +     * +     * @param topic The topic to request threads for. +     * @param limit The maximum number of threads. +     * @return A list of MessageThread objects. +     */ +    public List<MessageThread> getThreads(final String topic, final int limit) throws IOException { +        return mThreadsProvider.get(makeUrl(limit, topic));      }      public List<Message> getMessages(final String topic, final String threadId) throws IOException { @@ -91,4 +98,8 @@ public class FeedData {          return url;      } + +    private String makeUrl(int limit, String... parts) { +        return makeUrl(parts) + "?limit=" + limit; +    }  } diff --git a/src/com/p4square/grow/frontend/SurveyPageResource.java b/src/com/p4square/grow/frontend/SurveyPageResource.java index 803dfc4..07bc73c 100644 --- a/src/com/p4square/grow/frontend/SurveyPageResource.java +++ b/src/com/p4square/grow/frontend/SurveyPageResource.java @@ -29,8 +29,11 @@ import net.jesterpm.fmfacade.FreeMarkerPageResource;  import com.p4square.grow.config.Config;  import com.p4square.grow.model.Question; -import com.p4square.grow.provider.QuestionProvider; +import com.p4square.grow.model.UserRecord; +import com.p4square.grow.provider.DelegateProvider; +import com.p4square.grow.provider.JsonEncodedProvider;  import com.p4square.grow.provider.Provider; +import com.p4square.grow.provider.QuestionProvider;  /**   * SurveyPageResource handles rendering the survey and processing user's answers. @@ -49,6 +52,7 @@ public class SurveyPageResource extends FreeMarkerPageResource {      private Template mSurveyTemplate;      private JsonRequestClient mJsonClient;      private Provider<String, Question> mQuestionProvider; +    private Provider<String, UserRecord> mUserRecordProvider;      // Fields pertaining to this request.      private String mQuestionId; @@ -74,6 +78,15 @@ public class SurveyPageResource extends FreeMarkerPageResource {              }          }; +        mUserRecordProvider = new DelegateProvider<String, String, UserRecord>( +                new JsonRequestProvider<UserRecord>(getContext().getClientDispatcher(), +                    UserRecord.class)) { +            @Override +            public String makeKey(String userid) { +                return getBackendEndpoint() + "/accounts/" + userid; +            } +        }; +          mQuestionId = getAttribute("questionId");          mUserId = getRequest().getClientInfo().getUser().getIdentifier();      } @@ -205,24 +218,6 @@ public class SurveyPageResource extends FreeMarkerPageResource {          }      } -    private Map<?, ?> getAccount(String id) { -        try { -            Map<?, ?> account = null; - -            JsonResponse response = backendGet("/accounts/" + id); -            if (!response.getStatus().isSuccess()) { -                return null; -            } -            account = response.getMap(); - -            return account; - -        } catch (ClientException e) { -            LOG.warn("Error fetching account.", e); -            return null; -        } -    } -      private Question getQuestion(String id) {          try {              return mQuestionProvider.get(id); @@ -252,12 +247,16 @@ public class SurveyPageResource extends FreeMarkerPageResource {          if (nextQuestionId == null) {              // Just finished the last question. Update the user's account -            Map account = getAccount(mUserId); -            if (account == null) { -                account = new HashMap(); +            try { +                UserRecord account = mUserRecordProvider.get(mUserId); +                if (account == null) { +                    account = new UserRecord(); +                } +                account.setLanding("training"); +                mUserRecordProvider.put(mUserId, account); +            } catch (IOException e) { +                LOG.warn("IOException updating landing for " + mUserId, e);              } -            account.put("landing", "training"); -            backendPut("/accounts/" + mUserId, account);              String nextPage = mConfig.getString("dynamicRoot", "");              nextPage += "/account/assessment/results"; diff --git a/src/com/p4square/grow/frontend/TrainingPageResource.java b/src/com/p4square/grow/frontend/TrainingPageResource.java index 70a0d28..4096a3d 100644 --- a/src/com/p4square/grow/frontend/TrainingPageResource.java +++ b/src/com/p4square/grow/frontend/TrainingPageResource.java @@ -214,21 +214,8 @@ public class TrainingPageResource extends FreeMarkerPageResource {              root.put("videos", videos);              root.put("allowUserToSkip", allowUserToSkip); -            // Optionally show the feed. -            boolean showfeed = "true".equals(getRequest().getCookies().getFirstValue("showfeed")); -            if (getQueryValue("showfeed") != null) { -                CookieSetting cookie = new CookieSetting("showfeed", "true"); -                cookie.setPath("/"); -                if ("true".equals(getQueryValue("showfeed"))) { -                    showfeed = true; -                    getResponse().getCookieSettings().add(cookie); -                } else { -                    showfeed = false; -                    cookie.setValue("false"); -                    cookie.setMaxAge(0); -                    getResponse().getCookieSettings().add(cookie); -                } -            } +            // Determine if we should show the feed. +            boolean showfeed = true;              // Don't show the feed if the topic isn't allowed.              if (!FeedData.TOPICS.contains(mChapter)) { diff --git a/src/com/p4square/grow/model/Message.java b/src/com/p4square/grow/model/Message.java index ad02af9..9d33320 100644 --- a/src/com/p4square/grow/model/Message.java +++ b/src/com/p4square/grow/model/Message.java @@ -5,6 +5,7 @@  package com.p4square.grow.model;  import java.util.Date; +import java.util.UUID;  /**   * A feed message. @@ -19,6 +20,13 @@ public class Message {      private String mMessage;      /** +     * @return a new message id. +     */ +    public static String generateId() { +        return String.format("%x-%s", System.currentTimeMillis(), UUID.randomUUID().toString()); +    } + +    /**       * @return The id of the thread that the message belongs to.       */      public String getThreadId() { diff --git a/src/com/p4square/grow/model/MessageThread.java b/src/com/p4square/grow/model/MessageThread.java index 25a46b7..9542a18 100644 --- a/src/com/p4square/grow/model/MessageThread.java +++ b/src/com/p4square/grow/model/MessageThread.java @@ -21,7 +21,9 @@ public class MessageThread {       */      public static MessageThread createNew() {          MessageThread t = new MessageThread(); -        t.setId(String.format("%x-%s", System.currentTimeMillis(), UUID.randomUUID().toString())); +        // IDs are keyed to sort lexicographically from latest to oldest. +        t.setId(String.format("%016x-%s", Long.MAX_VALUE - System.currentTimeMillis(), +                    UUID.randomUUID().toString()));          return t;      } diff --git a/src/com/p4square/grow/model/UserRecord.java b/src/com/p4square/grow/model/UserRecord.java index b5aaa4e..4399282 100644 --- a/src/com/p4square/grow/model/UserRecord.java +++ b/src/com/p4square/grow/model/UserRecord.java @@ -21,6 +21,7 @@ public class UserRecord {      private String mLastName;      private String mEmail;      private String mLanding; +    private boolean mNewBeliever;      // Backend Access      private String mBackendPasswordHash; @@ -117,6 +118,21 @@ public class UserRecord {      }      /** +     * @return true if the user came from the New Believer's landing. +     */ +    public boolean getNewBeliever() { +        return mNewBeliever; +    } + +    /** +     * Set the user's new believer flag. +     * @param value The new flag. +     */ +    public void setNewBeliever(final boolean value) { +        mNewBeliever = value; +    } + +    /**       * @return The user's backend password hash, null if he doesn't have       * access.       */ diff --git a/src/templates/templates/communityfeed.ftl b/src/templates/templates/communityfeed.ftl index 7c68771..71b33bc 100644 --- a/src/templates/templates/communityfeed.ftl +++ b/src/templates/templates/communityfeed.ftl @@ -2,7 +2,8 @@  <div id="thefeed">      <h2>Discussion Forum</h2> -    <#assign threads = feeddata.getThreads(chapter)> +    <#assign max_threads = 5> +    <#assign threads = feeddata.getThreads(chapter, max_threads)>      <#list threads as thread>          <#assign messages = feeddata.getMessages(chapter, thread.id)>          <article>  | 
