|
1 /* Any copyright is dedicated to the Public Domain. |
|
2 http://creativecommons.org/publicdomain/zero/1.0/ */ |
|
3 |
|
4 package org.mozilla.gecko.background.db; |
|
5 |
|
6 import org.json.simple.JSONArray; |
|
7 import org.mozilla.gecko.background.helpers.AndroidSyncTestCase; |
|
8 import org.mozilla.gecko.background.sync.helpers.ExpectFetchDelegate; |
|
9 import org.mozilla.gecko.background.sync.helpers.SessionTestHelper; |
|
10 import org.mozilla.gecko.db.BrowserContract; |
|
11 import org.mozilla.gecko.sync.repositories.NoContentProviderException; |
|
12 import org.mozilla.gecko.sync.repositories.RepositorySession; |
|
13 import org.mozilla.gecko.sync.repositories.android.BrowserContractHelpers; |
|
14 import org.mozilla.gecko.sync.repositories.android.FennecTabsRepository; |
|
15 import org.mozilla.gecko.sync.repositories.android.FennecTabsRepository.FennecTabsRepositorySession; |
|
16 import org.mozilla.gecko.sync.repositories.delegates.RepositorySessionCreationDelegate; |
|
17 import org.mozilla.gecko.sync.repositories.domain.Record; |
|
18 import org.mozilla.gecko.sync.repositories.domain.TabsRecord; |
|
19 |
|
20 import android.content.ContentProviderClient; |
|
21 import android.content.ContentResolver; |
|
22 import android.content.Context; |
|
23 import android.database.Cursor; |
|
24 import android.os.RemoteException; |
|
25 |
|
26 public class TestFennecTabsRepositorySession extends AndroidSyncTestCase { |
|
27 public static final String TEST_CLIENT_GUID = "test guid"; // Real GUIDs never contain spaces. |
|
28 public static final String TEST_CLIENT_NAME = "test client name"; |
|
29 |
|
30 // Override these to test against data that is not live. |
|
31 public static final String TEST_TABS_CLIENT_GUID_IS_LOCAL_SELECTION = BrowserContract.Tabs.CLIENT_GUID + " IS ?"; |
|
32 public static final String[] TEST_TABS_CLIENT_GUID_IS_LOCAL_SELECTION_ARGS = new String[] { TEST_CLIENT_GUID }; |
|
33 |
|
34 protected ContentProviderClient tabsClient = null; |
|
35 |
|
36 protected ContentProviderClient getTabsClient() { |
|
37 final ContentResolver cr = getApplicationContext().getContentResolver(); |
|
38 return cr.acquireContentProviderClient(BrowserContractHelpers.TABS_CONTENT_URI); |
|
39 } |
|
40 |
|
41 public TestFennecTabsRepositorySession() throws NoContentProviderException { |
|
42 super(); |
|
43 } |
|
44 |
|
45 @Override |
|
46 public void setUp() { |
|
47 if (tabsClient == null) { |
|
48 tabsClient = getTabsClient(); |
|
49 } |
|
50 } |
|
51 |
|
52 protected int deleteAllTestTabs(final ContentProviderClient tabsClient) throws RemoteException { |
|
53 if (tabsClient == null) { |
|
54 return -1; |
|
55 } |
|
56 return tabsClient.delete(BrowserContractHelpers.TABS_CONTENT_URI, |
|
57 TEST_TABS_CLIENT_GUID_IS_LOCAL_SELECTION, TEST_TABS_CLIENT_GUID_IS_LOCAL_SELECTION_ARGS); |
|
58 } |
|
59 |
|
60 @Override |
|
61 protected void tearDown() throws Exception { |
|
62 if (tabsClient != null) { |
|
63 deleteAllTestTabs(tabsClient); |
|
64 |
|
65 tabsClient.release(); |
|
66 tabsClient = null; |
|
67 } |
|
68 } |
|
69 |
|
70 protected FennecTabsRepository getRepository() { |
|
71 /** |
|
72 * Override this chain in order to avoid our test code having to create two |
|
73 * sessions all the time. |
|
74 */ |
|
75 return new FennecTabsRepository(TEST_CLIENT_NAME, TEST_CLIENT_GUID) { |
|
76 @Override |
|
77 public void createSession(RepositorySessionCreationDelegate delegate, |
|
78 Context context) { |
|
79 try { |
|
80 final FennecTabsRepositorySession session = new FennecTabsRepositorySession(this, context) { |
|
81 @Override |
|
82 protected synchronized void trackGUID(String guid) { |
|
83 } |
|
84 |
|
85 @Override |
|
86 protected String localClientSelection() { |
|
87 return TEST_TABS_CLIENT_GUID_IS_LOCAL_SELECTION; |
|
88 } |
|
89 |
|
90 @Override |
|
91 protected String[] localClientSelectionArgs() { |
|
92 return TEST_TABS_CLIENT_GUID_IS_LOCAL_SELECTION_ARGS; |
|
93 } |
|
94 }; |
|
95 delegate.onSessionCreated(session); |
|
96 } catch (Exception e) { |
|
97 delegate.onSessionCreateFailed(e); |
|
98 } |
|
99 } |
|
100 }; |
|
101 } |
|
102 |
|
103 protected FennecTabsRepositorySession createSession() { |
|
104 return (FennecTabsRepositorySession) SessionTestHelper.createSession( |
|
105 getApplicationContext(), |
|
106 getRepository()); |
|
107 } |
|
108 |
|
109 protected FennecTabsRepositorySession createAndBeginSession() { |
|
110 return (FennecTabsRepositorySession) SessionTestHelper.createAndBeginSession( |
|
111 getApplicationContext(), |
|
112 getRepository()); |
|
113 } |
|
114 |
|
115 protected Runnable fetchSinceRunnable(final RepositorySession session, final long timestamp, final Record[] expectedRecords) { |
|
116 return new Runnable() { |
|
117 @Override |
|
118 public void run() { |
|
119 session.fetchSince(timestamp, new ExpectFetchDelegate(expectedRecords)); |
|
120 } |
|
121 }; |
|
122 } |
|
123 |
|
124 protected Runnable fetchAllRunnable(final RepositorySession session, final Record[] expectedRecords) { |
|
125 return new Runnable() { |
|
126 @Override |
|
127 public void run() { |
|
128 session.fetchAll(new ExpectFetchDelegate(expectedRecords)); |
|
129 } |
|
130 }; |
|
131 } |
|
132 |
|
133 protected Tab testTab1; |
|
134 protected Tab testTab2; |
|
135 protected Tab testTab3; |
|
136 |
|
137 @SuppressWarnings("unchecked") |
|
138 private void insertSomeTestTabs(ContentProviderClient tabsClient) throws RemoteException { |
|
139 final JSONArray history1 = new JSONArray(); |
|
140 history1.add("http://test.com/test1.html"); |
|
141 testTab1 = new Tab("test title 1", "http://test.com/test1.png", history1, 1000); |
|
142 |
|
143 final JSONArray history2 = new JSONArray(); |
|
144 history2.add("http://test.com/test2.html#1"); |
|
145 history2.add("http://test.com/test2.html#2"); |
|
146 history2.add("http://test.com/test2.html#3"); |
|
147 testTab2 = new Tab("test title 2", "http://test.com/test2.png", history2, 2000); |
|
148 |
|
149 final JSONArray history3 = new JSONArray(); |
|
150 history3.add("http://test.com/test3.html#1"); |
|
151 history3.add("http://test.com/test3.html#2"); |
|
152 testTab3 = new Tab("test title 3", "http://test.com/test3.png", history3, 3000); |
|
153 |
|
154 tabsClient.insert(BrowserContractHelpers.TABS_CONTENT_URI, testTab1.toContentValues(TEST_CLIENT_GUID, 0)); |
|
155 tabsClient.insert(BrowserContractHelpers.TABS_CONTENT_URI, testTab2.toContentValues(TEST_CLIENT_GUID, 1)); |
|
156 tabsClient.insert(BrowserContractHelpers.TABS_CONTENT_URI, testTab3.toContentValues(TEST_CLIENT_GUID, 2)); |
|
157 } |
|
158 |
|
159 protected TabsRecord insertTestTabsAndExtractTabsRecord() throws RemoteException { |
|
160 insertSomeTestTabs(tabsClient); |
|
161 |
|
162 final String positionAscending = BrowserContract.Tabs.POSITION + " ASC"; |
|
163 Cursor cursor = null; |
|
164 try { |
|
165 cursor = tabsClient.query(BrowserContractHelpers.TABS_CONTENT_URI, null, |
|
166 TEST_TABS_CLIENT_GUID_IS_LOCAL_SELECTION, TEST_TABS_CLIENT_GUID_IS_LOCAL_SELECTION_ARGS, positionAscending); |
|
167 CursorDumper.dumpCursor(cursor); |
|
168 |
|
169 final TabsRecord tabsRecord = FennecTabsRepository.tabsRecordFromCursor(cursor, TEST_CLIENT_GUID, TEST_CLIENT_NAME); |
|
170 |
|
171 assertEquals(TEST_CLIENT_GUID, tabsRecord.guid); |
|
172 assertEquals(TEST_CLIENT_NAME, tabsRecord.clientName); |
|
173 |
|
174 assertNotNull(tabsRecord.tabs); |
|
175 assertEquals(cursor.getCount(), tabsRecord.tabs.size()); |
|
176 |
|
177 return tabsRecord; |
|
178 } finally { |
|
179 cursor.close(); |
|
180 } |
|
181 } |
|
182 |
|
183 public void testFetchAll() throws NoContentProviderException, RemoteException { |
|
184 final TabsRecord tabsRecord = insertTestTabsAndExtractTabsRecord(); |
|
185 |
|
186 final FennecTabsRepositorySession session = createAndBeginSession(); |
|
187 performWait(fetchAllRunnable(session, new Record[] { tabsRecord })); |
|
188 |
|
189 session.abort(); |
|
190 } |
|
191 |
|
192 public void testFetchSince() throws NoContentProviderException, RemoteException { |
|
193 final TabsRecord tabsRecord = insertTestTabsAndExtractTabsRecord(); |
|
194 |
|
195 final FennecTabsRepositorySession session = createAndBeginSession(); |
|
196 |
|
197 // Not all tabs are modified after this, but the record should contain them all. |
|
198 performWait(fetchSinceRunnable(session, 1000, new Record[] { tabsRecord })); |
|
199 |
|
200 // No tabs are modified after this, so we shouldn't get a record at all. |
|
201 performWait(fetchSinceRunnable(session, 4000, new Record[] { })); |
|
202 |
|
203 session.abort(); |
|
204 } |
|
205 } |