On Mon, Jul 7, 2008 at 5:22 PM, <[EMAIL PROTECTED]> wrote: > Author: lryan > Date: Mon Jul 7 17:22:19 2008 > New Revision: 674686 > > URL: http://svn.apache.org/viewvc?rev=674686&view=rev > Log: > Dataservice implementation backed by the canonical JSON file. > > Added: > > > incubator/shindig/trunk/java/social-api/src/main/java/org/apache/shindig/social/canonical/JSONOpensocialService.java > > > incubator/shindig/trunk/java/social-api/src/test/java/org/apache/shindig/social/canonical/JSONOpensocialServiceTest.java
Can we change the casing here to be "JsonOpenSocialService"? > > Modified: > > > incubator/shindig/trunk/java/social-api/src/main/java/org/apache/shindig/social/opensocial/model/Person.java > incubator/shindig/trunk/javascript/sampledata/canonicaldb.json > > Added: > incubator/shindig/trunk/java/social-api/src/main/java/org/apache/shindig/social/canonical/JSONOpensocialService.java > URL: > http://svn.apache.org/viewvc/incubator/shindig/trunk/java/social-api/src/main/java/org/apache/shindig/social/canonical/JSONOpensocialService.java?rev=674686&view=auto > > ============================================================================== > --- > incubator/shindig/trunk/java/social-api/src/main/java/org/apache/shindig/social/canonical/JSONOpensocialService.java > (added) > +++ > incubator/shindig/trunk/java/social-api/src/main/java/org/apache/shindig/social/canonical/JSONOpensocialService.java > Mon Jul 7 17:22:19 2008 > @@ -0,0 +1,355 @@ > +/* > + * Licensed to the Apache Software Foundation (ASF) under one > + * or more contributor license agreements. See the NOTICE file > + * distributed with this work for additional information > + * regarding copyright ownership. The ASF licenses this file > + * to you under the Apache License, Version 2.0 (the > + * "License"); you may not use this file except in compliance > + * with the License. You may obtain a copy of the License at > + * > + * http://www.apache.org/licenses/LICENSE-2.0 > + * > + * Unless required by applicable law or agreed to in writing, > + * software distributed under the License is distributed on an > + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY > + * KIND, either express or implied. See the License for the > + * specific language governing permissions and limitations > + * under the License. > + */ > +package org.apache.shindig.social.canonical; > + > +import com.google.common.collect.Lists; > +import com.google.common.collect.Maps; > +import com.google.common.collect.Sets; > +import com.google.inject.Inject; > +import com.google.inject.name.Named; > + > +import org.apache.commons.io.IOUtils; > +import org.apache.shindig.common.SecurityToken; > +import org.apache.shindig.social.ResponseError; > +import org.apache.shindig.social.ResponseItem; > +import org.apache.shindig.social.dataservice.ActivityService; > +import org.apache.shindig.social.dataservice.AppDataService; > +import org.apache.shindig.social.dataservice.DataCollection; > +import org.apache.shindig.social.dataservice.GroupId; > +import org.apache.shindig.social.dataservice.PersonService; > +import org.apache.shindig.social.dataservice.RestfulCollection; > +import org.apache.shindig.social.dataservice.UserId; > +import org.apache.shindig.social.opensocial.model.Activity; > +import org.apache.shindig.social.opensocial.model.Person; > +import org.apache.shindig.social.opensocial.util.BeanConverter; > +import org.json.JSONArray; > +import org.json.JSONException; > +import org.json.JSONObject; > + > +import java.util.Iterator; > +import java.util.List; > +import java.util.Map; > +import java.util.Set; > + > +/** > + * Implementation of supported services backed by a JSON DB > + */ > +public class JSONOpensocialService implements ActivityService, > PersonService, AppDataService { > + > + /** > + * The DB > + */ > + private JSONObject db; > + > + /** > + * The JSON<->Bean converter > + */ > + private BeanConverter converter; > + > + /** > + * db["activities"] -> Array<Person> > + */ > + private static final String PEOPLE_TABLE = "people"; > + > + /** > + * db["people"] -> Map<Person.Id, Array<Activity>> > + */ > + private static final String ACTIVITIES_TABLE = "activities"; > + > + /** > + * db["data"] -> Map<Person.Id, Map<String, String>> > + */ > + private static final String DATA_TABLE = "data"; > + > + /** > + * db["friendLinks"] -> Map<Person.Id, Array<Person.Id>> > + */ > + private static final String FRIEND_LINK_TABLE = "friendLinks"; > + > + @Inject > + public JSONOpensocialService(@Named("canonical.json.db")String > jsonLocation, > + BeanConverter converter) throws Exception { > + String content = IOUtils.toString(new > java.net.URL(jsonLocation).openStream(), "UTF-8"); > + this.db = new JSONObject(content); > + this.converter = converter; > + } > + > + public ResponseItem<RestfulCollection<Activity>> getActivities(UserId > userId, GroupId groupId, > + String appId, Set<String> fields, SecurityToken token) { > + List<Activity> result = Lists.newArrayList(); > + try { > + // TODO Is it really valid to read activities across multiple users > in one rpc? > + Set<String> idSet = getIdSet(userId, groupId, token); > + for (String id : idSet) { > + if (db.getJSONObject(ACTIVITIES_TABLE).has(id)) { > + JSONArray activities = > db.getJSONObject(ACTIVITIES_TABLE).getJSONArray(id); > + for (int i = 0; i < activities.length(); i++) { > + JSONObject activity = activities.getJSONObject(i); > + if (appId != null && > activity.get(Activity.Field.APP_ID.toString()).equals(appId)) { > + result.add(convertToActivity(activity, fields)); > + } > + } > + } > + } > + return new ResponseItem<RestfulCollection<Activity>>(new > RestfulCollection<Activity>(result)); > + } catch (JSONException je) { > + return new > ResponseItem<RestfulCollection<Activity>>(ResponseError.INTERNAL_ERROR, > + je.getMessage(), null); > + } > + } > + > + public ResponseItem<Activity> getActivity(UserId userId, GroupId > groupId, String appId, > + Set<String> fields, String activityId, SecurityToken token) { > + try { > + if (db.getJSONObject(ACTIVITIES_TABLE).has(userId.getUserId(token))) > { > + JSONArray activities = > db.getJSONObject(ACTIVITIES_TABLE).getJSONArray(userId.getUserId(token)); > + for (int i = 0; i < activities.length(); i++) { > + JSONObject activity = activities.getJSONObject(i); > + if (userId != null && > activity.get(Activity.Field.USER_ID.toString()) > + .equals(userId.getUserId(token)) && > + > activity.get(Activity.Field.ID.toString()).equals(activityId)) { > + return new ResponseItem<Activity>(convertToActivity(activity, > fields)); > + } > + } > + } > + return null; > + } catch (JSONException je) { > + return new ResponseItem<Activity>(ResponseError.INTERNAL_ERROR, > je.getMessage(), null); > + } > + } > + > + public ResponseItem deleteActivity(UserId userId, GroupId groupId, > String appId, > + String activityId, SecurityToken token) { > + try { > + if (db.getJSONObject(ACTIVITIES_TABLE).has(userId.getUserId(token))) > { > + JSONArray activities = > db.getJSONObject(ACTIVITIES_TABLE).getJSONArray(userId.getUserId(token)); > + if (activities != null) { > + JSONArray newList = new JSONArray(); > + for (int i = 0; i < activities.length(); i++) { > + JSONObject activity = activities.getJSONObject(i); > + if > (!activity.get(Activity.Field.ID.toString()).equals(activityId)) { > + newList.put(activity); > + } > + } > + db.getJSONObject(ACTIVITIES_TABLE).put(userId.getUserId(token), > newList); > + // TODO. This seems very odd that we return no useful response > in this case > + // There is no way to represent not-found > + // if (found) { ?? > + //} > + } > + } > + // What is the appropriate response here?? > + return new ResponseItem<Object>(null); > + } catch (JSONException je) { > + return new ResponseItem<Object>(ResponseError.INTERNAL_ERROR, > je.getMessage(), null); > + } > + } > + > + public ResponseItem createActivity(UserId userId, GroupId groupId, > String appId, > + Set<String> fields, Activity activity, SecurityToken token) { > + // Are fields really needed here? > + try { > + JSONObject jsonObject = convertFromActivity(activity, fields); > + if (!jsonObject.has(Activity.Field.ID.toString())) { > + jsonObject.put(Activity.Field.ID.toString(), > System.currentTimeMillis()); > + } > + JSONArray jsonArray = > db.getJSONObject(ACTIVITIES_TABLE).getJSONArray(userId.getUserId(token)); > + if (jsonArray == null) { > + jsonArray = new JSONArray(); > + db.getJSONObject(ACTIVITIES_TABLE).put(userId.getUserId(token), > jsonArray); > + } > + jsonArray.put(jsonObject); > + // TODO ?? > + return null; > + } catch (JSONException je) { > + return new ResponseItem<Object>(ResponseError.INTERNAL_ERROR, > je.getMessage(), null); > + } > + } > + > + public ResponseItem<RestfulCollection<Person>> getPeople(UserId userId, > GroupId groupId, > + SortOrder sortOrder, FilterType filter, int first, int max, > + Set<String> fields, SecurityToken token) { > + List<Person> result = Lists.newArrayList(); > + try { > + JSONArray people = db.getJSONArray(PEOPLE_TABLE); > + > + Set<String> idSet = getIdSet(userId, groupId, token); > + > + for (int i = 0; i < people.length(); i++) { > + JSONObject person = people.getJSONObject(i); > + if (!idSet.contains(person.get(Person.Field.ID.toString()))) { > + continue; > + } > + // Add group support later > + result.add(convertToPerson(person, fields)); > + } > + return new ResponseItem<RestfulCollection<Person>>(new > RestfulCollection<Person>(result)); > + } catch (JSONException je) { > + return new > ResponseItem<RestfulCollection<Person>>(ResponseError.INTERNAL_ERROR, > + je.getMessage(), null); > + } > + } > + > + public ResponseItem<Person> getPerson(UserId id, Set<String> fields, > SecurityToken token) { > + try { > + JSONArray people = db.getJSONArray(PEOPLE_TABLE); > + > + for (int i = 0; i < people.length(); i++) { > + JSONObject person = people.getJSONObject(i); > + if (id != null && person.get(Person.Field.ID.toString()) > + .equals(id.getUserId(token))) { > + return new ResponseItem<Person>(convertToPerson(person, > fields)); > + } > + } > + // TODO What does this mean? > + return null; > + } catch (JSONException je) { > + return new ResponseItem<Person>(ResponseError.INTERNAL_ERROR, > je.getMessage(), null); > + } > + } > + > + public ResponseItem<DataCollection> getPersonData(UserId userId, GroupId > groupId, String appId, > + Set<String> fields, SecurityToken token) { > + // TODO. Does fields==null imply all? > + try { > + Map<String, Map<String, String>> idToData = Maps.newHashMap(); > + Set<String> idSet = getIdSet(userId, groupId, token); > + for (String id : idSet) { > + JSONObject personData; > + if (!db.getJSONObject(DATA_TABLE).has(id)) { > + personData = new JSONObject(); > + } else { > + if (fields != null) { > + personData = new JSONObject( > + db.getJSONObject(DATA_TABLE).getJSONObject(id), > + fields.toArray(new String[fields.size()])); > + } else { > + personData = db.getJSONObject(DATA_TABLE).getJSONObject(id); > + } > + } > + > + Iterator keys = personData.keys(); > + Map<String, String> data = Maps.newHashMap(); > + while (keys.hasNext()) { > + String key = (String) keys.next(); > + data.put(key, personData.getString(key)); > + } > + idToData.put(id, data); > + } > + return new ResponseItem<DataCollection>(new > DataCollection(idToData)); > + } catch (JSONException je) { > + return new > ResponseItem<DataCollection>(ResponseError.INTERNAL_ERROR, je.getMessage(), > null); > + } > + } > + > + public ResponseItem deletePersonData(UserId userId, GroupId groupId, > String appId, > + Set<String> fields, SecurityToken token) { > + try { > + if (!db.getJSONObject(DATA_TABLE).has(userId.getUserId(token))) { > + return null; > + } > + JSONObject newPersonData = new JSONObject(); > + JSONObject oldPersonData = > db.getJSONObject(DATA_TABLE).getJSONObject(userId.getUserId(token)); > + Iterator keys = oldPersonData.keys(); > + while (keys.hasNext()) { > + String key = (String) keys.next(); > + if (fields != null && !fields.contains(key)) { > + newPersonData.put(key, oldPersonData.getString(key)); > + } > + } > + db.getJSONObject(DATA_TABLE).put(userId.getUserId(token), > newPersonData); > + // TODO what is the appropriate return value > + return null; > + } catch (JSONException je) { > + return new ResponseItem<Object>(ResponseError.INTERNAL_ERROR, > je.getMessage(), null); > + } > + } > + > + public ResponseItem updatePersonData(UserId userId, GroupId groupId, > String appId, > + Set<String> fields, Map<String, String> values, SecurityToken token) > { > + // TODO this seems redundant. No need to pass both fields and a map of > field->value > + try { > + JSONObject personData = > db.getJSONObject(DATA_TABLE).getJSONObject(userId.getUserId(token)); > + if (personData == null) { > + personData = new JSONObject(); > + db.getJSONObject(DATA_TABLE).put(userId.getUserId(token), > personData); > + } > + > + for (Map.Entry<String, String> entry : values.entrySet()) { > + personData.put(entry.getKey(), entry.getValue()); > + } > + // TODO what is the appropriate return value > + return null; > + } catch (JSONException je) { > + return new ResponseItem<Object>(ResponseError.INTERNAL_ERROR, > je.getMessage(), null); > + } > + } > + > + /** > + * Get the set of user id's from a user and group > + */ > + private Set<String> getIdSet(UserId user, GroupId group, SecurityToken > token) > + throws JSONException { > + String userId = user.getUserId(token); > + > + if (group == null) { > + return Sets.newLinkedHashSet(userId); > + } > + > + Set<String> returnVal = Sets.newLinkedHashSet(); > + switch (group.getType()) { > + case all: > + case friends: > + case groupId: > + if (db.getJSONObject(FRIEND_LINK_TABLE).has(userId)) { > + JSONArray friends = > db.getJSONObject(FRIEND_LINK_TABLE).getJSONArray(userId); > + for (int i = 0; i < friends.length(); i++) { > + returnVal.add(friends.getString(i)); > + } > + } > + break; > + case self: > + returnVal.add(userId); > + break; > + } > + return returnVal; > + } > + > + private Activity convertToActivity(JSONObject object, Set<String> > fields) throws JSONException { > + if (fields != null && !fields.isEmpty()) { > + // Create a copy with just the specified fields > + object = new JSONObject(object, fields.toArray(new > String[fields.size()])); > + } > + return converter.convertToObject(object.toString(), Activity.class); > + } > + > + private JSONObject convertFromActivity(Activity activity, Set<String> > fields) > + throws JSONException { > + // TODO Not using fields yet > + return new JSONObject(converter.convertToString(activity)); > + } > + > + private Person convertToPerson(JSONObject object, Set<String> fields) > throws JSONException { > + if (fields != null && !fields.isEmpty()) { > + // Create a copy with just the specified fields > + object = new JSONObject(object, fields.toArray(new > String[fields.size()])); > + } > + return converter.convertToObject(object.toString(), Person.class); > + } > +} > > Modified: > incubator/shindig/trunk/java/social-api/src/main/java/org/apache/shindig/social/opensocial/model/Person.java > URL: > http://svn.apache.org/viewvc/incubator/shindig/trunk/java/social-api/src/main/java/org/apache/shindig/social/opensocial/model/Person.java?rev=674686&r1=674685&r2=674686&view=diff > > ============================================================================== > --- > incubator/shindig/trunk/java/social-api/src/main/java/org/apache/shindig/social/opensocial/model/Person.java > (original) > +++ > incubator/shindig/trunk/java/social-api/src/main/java/org/apache/shindig/social/opensocial/model/Person.java > Mon Jul 7 17:22:19 2008 > @@ -17,8 +17,11 @@ > */ > package org.apache.shindig.social.opensocial.model; > > -import java.util.List; > +import org.apache.shindig.social.opensocial.util.EnumUtil; > + > import java.util.Date; > +import java.util.List; > +import java.util.Set; > > /** > * see > @@ -87,6 +90,12 @@ > > private final String jsonString; > > + public static final Set<String> DEFAULT_FIELDS = > + EnumUtil.getEnumStrings(ID, NAME, THUMBNAIL_URL); > + > + public static final Set<String> ALL_FIELDS = > + EnumUtil.getEnumStrings(Field.values()); > + > private Field(String jsonString) { > this.jsonString = jsonString; > } > > Added: > incubator/shindig/trunk/java/social-api/src/test/java/org/apache/shindig/social/canonical/JSONOpensocialServiceTest.java > URL: > http://svn.apache.org/viewvc/incubator/shindig/trunk/java/social-api/src/test/java/org/apache/shindig/social/canonical/JSONOpensocialServiceTest.java?rev=674686&view=auto > > ============================================================================== > --- > incubator/shindig/trunk/java/social-api/src/test/java/org/apache/shindig/social/canonical/JSONOpensocialServiceTest.java > (added) > +++ > incubator/shindig/trunk/java/social-api/src/test/java/org/apache/shindig/social/canonical/JSONOpensocialServiceTest.java > Mon Jul 7 17:22:19 2008 > @@ -0,0 +1,164 @@ > +/* > + * Licensed to the Apache Software Foundation (ASF) under one > + * or more contributor license agreements. See the NOTICE file > + * distributed with this work for additional information > + * regarding copyright ownership. The ASF licenses this file > + * to you under the Apache License, Version 2.0 (the > + * "License"); you may not use this file except in compliance > + * with the License. You may obtain a copy of the License at > + * > + * http://www.apache.org/licenses/LICENSE-2.0 > + * > + * Unless required by applicable law or agreed to in writing, > + * software distributed under the License is distributed on an > + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY > + * KIND, either express or implied. See the License for the > + * specific language governing permissions and limitations > + * under the License. > + */ > +package org.apache.shindig.social.canonical; > + > +import com.google.common.collect.Maps; > +import com.google.common.collect.Sets; > +import com.google.inject.Guice; > + > +import junit.framework.TestCase; > + > +import org.apache.shindig.common.SecurityToken; > +import org.apache.shindig.common.testing.FakeGadgetToken; > +import org.apache.shindig.social.ResponseItem; > +import org.apache.shindig.social.SocialApiTestsGuiceModule; > +import org.apache.shindig.social.dataservice.DataCollection; > +import org.apache.shindig.social.dataservice.GroupId; > +import org.apache.shindig.social.dataservice.PersonService; > +import org.apache.shindig.social.dataservice.RestfulCollection; > +import org.apache.shindig.social.dataservice.UserId; > +import org.apache.shindig.social.opensocial.model.Activity; > +import org.apache.shindig.social.opensocial.model.Person; > +import org.apache.shindig.social.opensocial.util.BeanJsonConverter; > + > +/** > + * Test the JSONOpensocialService > + */ > +public class JSONOpensocialServiceTest extends TestCase { > + > + private JSONOpensocialService db; > + > + private static final UserId CANON_USER = new UserId(UserId.Type.userId, > "canonical"); > + private static final GroupId SELF_GROUP = new GroupId(GroupId.Type.self, > null); > + private static final String APP_ID = "1"; > + > + private static final String CANONICAL_USER_ID = "canonical"; > + private SecurityToken token = new FakeGadgetToken(); > + > + > + @Override > + protected void setUp() throws Exception { > + BeanJsonConverter beanJsonConverter = new BeanJsonConverter( > + Guice.createInjector(new SocialApiTestsGuiceModule())); > + db = new JSONOpensocialService( > + > "file:///home/lryan/shindig/trunk/javascript/sampledata/canonicaldb.json", > + beanJsonConverter); > + } > + > + public void testGetPersonDefaultFields() throws Exception { > + ResponseItem<Person> personResponseItem = db > + .getPerson(CANON_USER, Person.Field.DEFAULT_FIELDS, token); > + > + assertNotNull("Canonical user not found", > personResponseItem.getResponse()); > + assertNotNull("Canonical user has no id", > personResponseItem.getResponse().getId()); > + assertNotNull("Canonical user has no name", > personResponseItem.getResponse().getName()); > + assertNotNull("Canonical user has no thumbnail", > + personResponseItem.getResponse().getThumbnailUrl()); > + } > + > + public void testGetPersonAllFields() throws Exception { > + ResponseItem<Person> personResponseItem = db > + .getPerson(CANON_USER, Person.Field.ALL_FIELDS, token); > + assertNotNull("Canonical user not found", > personResponseItem.getResponse()); > + } > + > + public void testGetExpectedFriends() throws Exception { > + ResponseItem<RestfulCollection<Person>> responseItem = db.getPeople( > + CANON_USER, new GroupId(GroupId.Type.friends, null), > PersonService.SortOrder.topFriends, > + PersonService.FilterType.all, 0, Integer.MAX_VALUE, null, token); > + assertNotNull(responseItem.getResponse()); > + assertEquals(responseItem.getResponse().getTotalResults(), 4); > + // Test a couple of users > + assertEquals(responseItem.getResponse().getEntry().get(0).getId(), > "john.doe"); > + assertEquals(responseItem.getResponse().getEntry().get(1).getId(), > "jane.doe"); > + } > + > + public void testGetExpectedActivities() throws Exception { > + ResponseItem<RestfulCollection<Activity>> responseItem = > db.getActivities( > + CANON_USER, SELF_GROUP, APP_ID, null, new FakeGadgetToken()); > + assertTrue(responseItem.getResponse().getTotalResults() == 2); > + } > + > + public void testGetExpectedActivity() throws Exception { > + ResponseItem<Activity> responseItem = db.getActivity( > + CANON_USER, SELF_GROUP, APP_ID, > + Sets.newHashSet("appId", "body", "mediaItems"), APP_ID, new > FakeGadgetToken()); > + assertTrue(responseItem != null); > + assertTrue(responseItem.getResponse() != null); > + // Check that some fields are fetched and others are not > + assertTrue(responseItem.getResponse().getBody() != null); > + assertTrue(responseItem.getResponse().getBodyId() == null); > + } > + > + public void testDeleteExpectedActivity() throws Exception { > + db.deleteActivity(CANON_USER, SELF_GROUP, APP_ID, APP_ID, > + new FakeGadgetToken()); > + > + // Try to fetch the activity > + ResponseItem<Activity> responseItem = db.getActivity( > + CANON_USER, SELF_GROUP, APP_ID, > + Sets.newHashSet("appId", "body", "mediaItems"), APP_ID, new > FakeGadgetToken()); > + assertTrue(responseItem == null); > + } > + > + public void testGetExpectedAppData() throws Exception { > + ResponseItem<DataCollection> responseItem = db.getPersonData( > + CANON_USER, SELF_GROUP, APP_ID, null, new FakeGadgetToken()); > + assertTrue(!responseItem.getResponse().getEntry().isEmpty()); > + > > assertTrue(!responseItem.getResponse().getEntry().get(CANONICAL_USER_ID).isEmpty()); > + > > assertTrue(responseItem.getResponse().getEntry().get(CANONICAL_USER_ID).size() > == 2); > + > > assertTrue(responseItem.getResponse().getEntry().get(CANONICAL_USER_ID).containsKey("count")); > + > > assertTrue(responseItem.getResponse().getEntry().get(CANONICAL_USER_ID).containsKey("size")); > + } > + > + public void testDeleteExpectedAppData() throws Exception { > + // Delete the data > + db.deletePersonData(CANON_USER, SELF_GROUP, APP_ID, > + Sets.newHashSet("count"), new FakeGadgetToken()); > + > + //Fetch the remaining and test > + ResponseItem<DataCollection> responseItem = db.getPersonData( > + CANON_USER, SELF_GROUP, APP_ID, null, new FakeGadgetToken()); > + assertTrue(!responseItem.getResponse().getEntry().isEmpty()); > + > > assertTrue(!responseItem.getResponse().getEntry().get(CANONICAL_USER_ID).isEmpty()); > + > > assertTrue(responseItem.getResponse().getEntry().get(CANONICAL_USER_ID).size() > == 1); > + > > assertTrue(!responseItem.getResponse().getEntry().get(CANONICAL_USER_ID).containsKey("count")); > + > > assertTrue(responseItem.getResponse().getEntry().get(CANONICAL_USER_ID).containsKey("size")); > + } > + > + public void testUpdateExpectedAppData() throws Exception { > + // Delete the data > + db.updatePersonData(CANON_USER, SELF_GROUP, APP_ID, > + null, Maps.immutableMap("count", "10", "newvalue", "20"), new > FakeGadgetToken()); > + > + //Fetch the remaining and test > + ResponseItem<DataCollection> responseItem = db.getPersonData( > + CANON_USER, SELF_GROUP, APP_ID, null, new FakeGadgetToken()); > + assertTrue(!responseItem.getResponse().getEntry().isEmpty()); > + > > assertTrue(!responseItem.getResponse().getEntry().get(CANONICAL_USER_ID).isEmpty()); > + > > assertTrue(responseItem.getResponse().getEntry().get(CANONICAL_USER_ID).size() > == 3); > + > > assertTrue(responseItem.getResponse().getEntry().get(CANONICAL_USER_ID).containsKey("count")); > + assertTrue( > + > > responseItem.getResponse().getEntry().get(CANONICAL_USER_ID).get("count").equals("10")); > + assertTrue( > + > > responseItem.getResponse().getEntry().get(CANONICAL_USER_ID).containsKey("newvalue")); > + assertTrue( > + > > responseItem.getResponse().getEntry().get(CANONICAL_USER_ID).get("newvalue").equals("20")); > + } > +} > > Modified: incubator/shindig/trunk/javascript/sampledata/canonicaldb.json > URL: > http://svn.apache.org/viewvc/incubator/shindig/trunk/javascript/sampledata/canonicaldb.json?rev=674686&r1=674685&r2=674686&view=diff > > ============================================================================== > --- incubator/shindig/trunk/javascript/sampledata/canonicaldb.json > (original) > +++ incubator/shindig/trunk/javascript/sampledata/canonicaldb.json Mon Jul > 7 17:22:19 2008 > @@ -10,8 +10,8 @@ > // > // Notes: > // - The structure of Person, Activity MUST! match those in the RESTful > spec > -// - Data for "canonical" user should exercise every field in the spec. > And is relied on for unit-testing > -// so change at your peril > +// - Data for "canonical" user should exercise every field in the spec. > And is relied on > +// for unit-testing so change at your peril > // - Consider adding a structure for Map<Person.Id, Array<appId>> to > represent installed gadgets > // > // TODO: > @@ -175,7 +175,10 @@ > }, > { > "id" : "john.doe", > - "gender" : "M", > + "gender" : { > + "key" : "MALE", > + "displayvalue" : "Male" > + }, > "hasApp" : true, > "name" : { > "familyName" : "Doe", > @@ -185,7 +188,10 @@ > }, > { > "id" : "jane.doe", > - "gender" : "F", > + "gender" : { > + "key" : "FEMALE", > + "displayvalue" : "Female" > + }, > "hasApp" : true, > "name" : { > "familyName" : "Doe", > @@ -195,7 +201,10 @@ > }, > { > "id" : "george.doe", > - "gender" : "M", > + "gender" : { > + "key" : "MALE", > + "displayvalue" : "Female" > + }, > "hasApp" : true, > "name" : { > "familyName" : "Doe", > @@ -205,7 +214,10 @@ > }, > { > "id" : "mario.rossi", > - "gender" : "M", > + "gender" : { > + "key" : "MALE", > + "displayvalue" : "Male" > + }, > "hasApp" : true, > "name" : { > "familyName" : "Rossi", > @@ -215,7 +227,10 @@ > }, > { > "id" : "maija.m", > - "gender" : "F", > + "gender" : { > + "key" : "FEMALE", > + "displayvalue" : "Female" > + }, > "hasApp" : true, > "name" : { > "familyName" : "Meikäläinen", > @@ -324,6 +339,7 @@ > // ----------------------------- Data > --------------------------------------- > // > "friendLinks" : { > + "canonical" : ["john.doe", "jane.doe", "george.doe", "maija.m"], > "john.doe" : ["jane.doe", "george.doe", "maija.m"], > "jane.doe" : ["john.doe"], > "george.doe" : ["john.doe"], > > >

