Compare commits
390 Commits
115-tor-pe
...
725-result
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
71d8947265 | ||
|
|
6fc42f7296 | ||
|
|
55af22ca04 | ||
|
|
6ab8219394 | ||
|
|
7d1ddb6d65 | ||
|
|
f1371f1db8 | ||
|
|
491e0adc9c | ||
|
|
f10ac13350 | ||
|
|
38f46a9c60 | ||
|
|
20de6f1aa5 | ||
|
|
cbdeb0ad32 | ||
|
|
a60414517c | ||
|
|
988c3e4b58 | ||
|
|
b0098fb054 | ||
|
|
a7c28f04de | ||
|
|
4eec29a631 | ||
|
|
76504387ff | ||
|
|
ea0ad08f57 | ||
|
|
e4676517ef | ||
|
|
dbbeb37485 | ||
|
|
89a7f41a07 | ||
|
|
936ee5e95b | ||
|
|
1697c2af04 | ||
|
|
cb8e0beea9 | ||
|
|
98cb077dd9 | ||
|
|
e6a8ad5d49 | ||
|
|
5e4116efa0 | ||
|
|
a01eeafe4e | ||
|
|
c86d971166 | ||
|
|
d5f8808597 | ||
|
|
e98f4901f5 | ||
|
|
9b09b64ad3 | ||
|
|
20708bc156 | ||
|
|
0814458cb9 | ||
|
|
e32313c30b | ||
|
|
593152e7cd | ||
|
|
ab91520813 | ||
|
|
37e61c97ea | ||
|
|
303fcc9ece | ||
|
|
e2bbe7429b | ||
|
|
eaf17c054f | ||
|
|
f97f30ce42 | ||
|
|
f4c26d9cc7 | ||
|
|
68abf8ba1a | ||
|
|
58f6af513d | ||
|
|
c9170fa5a0 | ||
|
|
ec1f4dccdb | ||
|
|
8c3b598ab2 | ||
|
|
bd3bba6e8a | ||
|
|
11fcad89c6 | ||
|
|
007df4288b | ||
|
|
9798654c23 | ||
|
|
7b58d003a1 | ||
|
|
b60f6b0789 | ||
|
|
914b72505a | ||
|
|
24dd4fda69 | ||
|
|
52eb261a11 | ||
|
|
980a6d18bb | ||
|
|
c4a152b543 | ||
|
|
ed728e816e | ||
|
|
efbce95399 | ||
|
|
98c81f71b4 | ||
|
|
da543c1004 | ||
|
|
7ab4d12d83 | ||
|
|
59964c5087 | ||
|
|
b885e49ba2 | ||
|
|
63da860681 | ||
|
|
aa210fc555 | ||
|
|
68f0e91f32 | ||
|
|
3a2205123f | ||
|
|
ab16ee7465 | ||
|
|
eb66924e21 | ||
|
|
563d897651 | ||
|
|
98cf6b5bba | ||
|
|
ade7e50f65 | ||
|
|
ccc9d53ac7 | ||
|
|
d232529eb3 | ||
|
|
a532f03784 | ||
|
|
5e5bf7ec05 | ||
|
|
7414abd1ce | ||
|
|
dc76ce2be2 | ||
|
|
3eed0bfe81 | ||
|
|
ec8982438a | ||
|
|
501c2dab31 | ||
|
|
2fe69af6d8 | ||
|
|
b20c107010 | ||
|
|
f410e4eddd | ||
|
|
bb82bd70e2 | ||
|
|
138a6e11a7 | ||
|
|
178d72114b | ||
|
|
c1f1eb7dfa | ||
|
|
d2a3804cfe | ||
|
|
fb095c1f4d | ||
|
|
f89d8cbe38 | ||
|
|
d2434123a9 | ||
|
|
edbf5ff5b4 | ||
|
|
32f0b53d15 | ||
|
|
55ecdd9a13 | ||
|
|
e47e3242a6 | ||
|
|
4387bfc5bd | ||
|
|
d11ee5e43b | ||
|
|
ce53589c33 | ||
|
|
e96b3a8c68 | ||
|
|
62040d45b8 | ||
|
|
1809943f1d | ||
|
|
d204757395 | ||
|
|
c640ee8e51 | ||
|
|
04d4ecad05 | ||
|
|
c36bb3e60e | ||
|
|
7327029fca | ||
|
|
81d341374d | ||
|
|
7b884d2425 | ||
|
|
fbcf334941 | ||
|
|
238100bcac | ||
|
|
7c3805260d | ||
|
|
51bcf7b1b8 | ||
|
|
719a53dc94 | ||
|
|
3f9a254a0b | ||
|
|
e810a1265a | ||
|
|
c36f5c795b | ||
|
|
f52186ac8c | ||
|
|
e0f4be931d | ||
|
|
7536c00a34 | ||
|
|
847b6e4179 | ||
|
|
58793068c3 | ||
|
|
7125248677 | ||
|
|
4bad7076e7 | ||
|
|
2bb16bb75f | ||
|
|
b5a427f876 | ||
|
|
b34b4623ed | ||
|
|
f3b9214702 | ||
|
|
36f087c512 | ||
|
|
0c30f16d7e | ||
|
|
4d8a84a48d | ||
|
|
2650f3114e | ||
|
|
dfdde9799f | ||
|
|
114a2dc8f2 | ||
|
|
642fa7df18 | ||
|
|
c85767d2a0 | ||
|
|
55af1b954e | ||
|
|
88272c5d61 | ||
|
|
eaa393a7ed | ||
|
|
19080ad957 | ||
|
|
7eeeb5f1ed | ||
|
|
d55503ee92 | ||
|
|
8448d27d20 | ||
|
|
47d6fc526f | ||
|
|
3da879cfd9 | ||
|
|
8fdce5ba51 | ||
|
|
f759a7506f | ||
|
|
0b11aea7a2 | ||
|
|
aa954cee63 | ||
|
|
68024c264e | ||
|
|
78740a6942 | ||
|
|
9e553ef9c8 | ||
|
|
1147b8ffaf | ||
|
|
67866dbe66 | ||
|
|
8dac2d1ca6 | ||
|
|
b0a5a69b81 | ||
|
|
a18317e912 | ||
|
|
ad7d0d8e74 | ||
|
|
fe79131f4a | ||
|
|
cb61d91074 | ||
|
|
399a4890de | ||
|
|
656a947f5a | ||
|
|
7191967092 | ||
|
|
5ce8b1978d | ||
|
|
c0aa255bb6 | ||
|
|
c79ce61f6d | ||
|
|
0caabda303 | ||
|
|
679b54b2b4 | ||
|
|
349a34ffd8 | ||
|
|
2c8aaa215c | ||
|
|
4f4f1956eb | ||
|
|
e06726b2f9 | ||
|
|
a6e3827127 | ||
|
|
8dc529cc3f | ||
|
|
1e36f21cc8 | ||
|
|
2cc650d85f | ||
|
|
3407d0c0a8 | ||
|
|
ca8d3babaa | ||
|
|
7b627bb427 | ||
|
|
f027b832d4 | ||
|
|
42175dca7a | ||
|
|
5ffcdc4e46 | ||
|
|
e00219c15f | ||
|
|
96666273d3 | ||
|
|
a92f7e1c9f | ||
|
|
02a39f5694 | ||
|
|
a33d7d1663 | ||
|
|
8eeaf4e347 | ||
|
|
835bd86346 | ||
|
|
84b2a171ab | ||
|
|
1df00f5702 | ||
|
|
292e1c3e8e | ||
|
|
c8c0281efc | ||
|
|
e8c48ccf8d | ||
|
|
09baa2ebe1 | ||
|
|
1176741ea4 | ||
|
|
e6def70030 | ||
|
|
1a812f1327 | ||
|
|
8dc3bd2c4c | ||
|
|
c934ec30aa | ||
|
|
d5f6e71cba | ||
|
|
feed2581c9 | ||
|
|
bd1f3fc2bd | ||
|
|
d25f4d1fbe | ||
|
|
e84d1c5996 | ||
|
|
06831bafc3 | ||
|
|
9284167a2e | ||
|
|
df44015ccb | ||
|
|
c4716ca457 | ||
|
|
9bb16b424f | ||
|
|
e8ebdc2884 | ||
|
|
2140a290e4 | ||
|
|
50a70f7649 | ||
|
|
b3e5d1ff85 | ||
|
|
690142ce07 | ||
|
|
82eea6bb77 | ||
|
|
3ad3332649 | ||
|
|
5a0fa5dcc7 | ||
|
|
97223cce97 | ||
|
|
08b191d72e | ||
|
|
06335c2c30 | ||
|
|
8f882dc910 | ||
|
|
0523c4e718 | ||
|
|
7bf4aebdaf | ||
|
|
6db59ffce5 | ||
|
|
e0835ad460 | ||
|
|
c83d4bbb39 | ||
|
|
65b47bb5d2 | ||
|
|
9ce95d6de7 | ||
|
|
9d2c56e75f | ||
|
|
32c4f61e68 | ||
|
|
6e04664915 | ||
|
|
5674ee2d88 | ||
|
|
8637faf858 | ||
|
|
970cbbf557 | ||
|
|
57ac4a5374 | ||
|
|
2b91631ba5 | ||
|
|
b327122255 | ||
|
|
0b3ec9aa4c | ||
|
|
154e02723f | ||
|
|
b09e30a95f | ||
|
|
3ea36bbd40 | ||
|
|
cb983f02c2 | ||
|
|
f1730aa7d9 | ||
|
|
857665db79 | ||
|
|
7f2db71160 | ||
|
|
60dee5c4cb | ||
|
|
784561144a | ||
|
|
70d39d03bc | ||
|
|
48a3db46bc | ||
|
|
f52819f4ca | ||
|
|
457c30f3f2 | ||
|
|
1731369d7a | ||
|
|
064b920626 | ||
|
|
b2fa039474 | ||
|
|
9112d17a4b | ||
|
|
86fbb89637 | ||
|
|
b3bea1f945 | ||
|
|
543304973e | ||
|
|
fc38738428 | ||
|
|
d661fa0661 | ||
|
|
e2eda8fef0 | ||
|
|
604542c19b | ||
|
|
a727a0817e | ||
|
|
3fa84ec7a8 | ||
|
|
e5f5511112 | ||
|
|
16ecb2ce8d | ||
|
|
c49c888f9f | ||
|
|
6b3db67ef5 | ||
|
|
293c06fd61 | ||
|
|
1c55fae704 | ||
|
|
95670937c3 | ||
|
|
165deebb40 | ||
|
|
0b0cae06ae | ||
|
|
f8e0441de8 | ||
|
|
a422c626b3 | ||
|
|
6ece398a21 | ||
|
|
8b50cb1461 | ||
|
|
f28bc691a5 | ||
|
|
42056720fa | ||
|
|
0861ee1f10 | ||
|
|
a30de6309d | ||
|
|
d112b42d20 | ||
|
|
fd6719301a | ||
|
|
92f2e7b0fc | ||
|
|
ee98900613 | ||
|
|
747553f577 | ||
|
|
8a4c162bba | ||
|
|
7e806c8cf2 | ||
|
|
e466ed580c | ||
|
|
d058172429 | ||
|
|
1f0b305139 | ||
|
|
7a0db798d1 | ||
|
|
7e6a522eee | ||
|
|
33795e7046 | ||
|
|
2d59b9095c | ||
|
|
8fb820c967 | ||
|
|
53d0b8b21e | ||
|
|
d389f79a48 | ||
|
|
b278c7d9cb | ||
|
|
a85043efb5 | ||
|
|
133722dd2c | ||
|
|
9e3db12ea2 | ||
|
|
f461ec4ab0 | ||
|
|
e87c301e3a | ||
|
|
17bacc1116 | ||
|
|
401abf2c0c | ||
|
|
a4d08f4cf1 | ||
|
|
eb6189150f | ||
|
|
c917110e6a | ||
|
|
d5beca5351 | ||
|
|
1fdbe65dde | ||
|
|
1583163f88 | ||
|
|
ee35110167 | ||
|
|
72bf701345 | ||
|
|
fd4dbdc081 | ||
|
|
97937428bb | ||
|
|
4be1c1bb7d | ||
|
|
89ab4dd04e | ||
|
|
f3ea731565 | ||
|
|
bf023874f0 | ||
|
|
16ac73d002 | ||
|
|
cc439aa74f | ||
|
|
7a1003178d | ||
|
|
cab667ef6a | ||
|
|
7035d8063c | ||
|
|
2fbbb663a3 | ||
|
|
b4714b5360 | ||
|
|
8a3e5bfb50 | ||
|
|
fd4275733f | ||
|
|
af5b246d7b | ||
|
|
49e9ee2b6d | ||
|
|
1a611d55be | ||
|
|
7c5945de01 | ||
|
|
ccc49df08e | ||
|
|
ac325d4423 | ||
|
|
0a0e1b4280 | ||
|
|
cb64740916 | ||
|
|
73bc86df4a | ||
|
|
307e124ee8 | ||
|
|
60b4c5649a | ||
|
|
e0e46a726e | ||
|
|
668eaf45f6 | ||
|
|
fb9d743d11 | ||
|
|
fc2213c042 | ||
|
|
34f9311f43 | ||
|
|
28fd84b261 | ||
|
|
448bf86379 | ||
|
|
91e529a9e9 | ||
|
|
74f9a0dd73 | ||
|
|
54290bc374 | ||
|
|
3e39ad8a68 | ||
|
|
07445ada41 | ||
|
|
5281d8b468 | ||
|
|
0deac1d1b6 | ||
|
|
387e44d114 | ||
|
|
bb00412187 | ||
|
|
bb0a2a5b32 | ||
|
|
6d7e0aab07 | ||
|
|
da08072409 | ||
|
|
9664aea520 | ||
|
|
636b587b9c | ||
|
|
0afab09fdf | ||
|
|
fe4f71fe0f | ||
|
|
6f0ffa8439 | ||
|
|
69dd399bd2 | ||
|
|
8b7304f4cb | ||
|
|
e023e5d8fc | ||
|
|
042050453a | ||
|
|
1c15e690e1 | ||
|
|
61c05c1dd4 | ||
|
|
d8a9d83caf | ||
|
|
70a44e8a27 | ||
|
|
fc5a7290e3 | ||
|
|
7db0e4472a | ||
|
|
65bdd5558e | ||
|
|
3dd3a18694 | ||
|
|
743fc7dd1f | ||
|
|
eb3da2aac9 | ||
|
|
4518f59a54 | ||
|
|
11c0cb667f | ||
|
|
132a03d0a9 | ||
|
|
c666b0493c | ||
|
|
625276067a | ||
|
|
30f2c192c6 | ||
|
|
28be7d5de3 | ||
|
|
dbdf567d4e |
30
.idea/codeStyleSettings.xml
generated
@@ -31,12 +31,42 @@
|
||||
</value>
|
||||
</option>
|
||||
<option name="RIGHT_MARGIN" value="100" />
|
||||
<option name="JD_ALIGN_PARAM_COMMENTS" value="false" />
|
||||
<option name="JD_ALIGN_EXCEPTION_COMMENTS" value="false" />
|
||||
<AndroidXmlCodeStyleSettings>
|
||||
<option name="USE_CUSTOM_SETTINGS" value="true" />
|
||||
</AndroidXmlCodeStyleSettings>
|
||||
<JavaCodeStyleSettings>
|
||||
<option name="ANNOTATION_PARAMETER_WRAP" value="1" />
|
||||
</JavaCodeStyleSettings>
|
||||
<Objective-C-extensions>
|
||||
<option name="GENERATE_INSTANCE_VARIABLES_FOR_PROPERTIES" value="ASK" />
|
||||
<option name="RELEASE_STYLE" value="IVAR" />
|
||||
<option name="TYPE_QUALIFIERS_PLACEMENT" value="BEFORE" />
|
||||
<file>
|
||||
<option name="com.jetbrains.cidr.lang.util.OCDeclarationKind" value="Import" />
|
||||
<option name="com.jetbrains.cidr.lang.util.OCDeclarationKind" value="Macro" />
|
||||
<option name="com.jetbrains.cidr.lang.util.OCDeclarationKind" value="Typedef" />
|
||||
<option name="com.jetbrains.cidr.lang.util.OCDeclarationKind" value="Enum" />
|
||||
<option name="com.jetbrains.cidr.lang.util.OCDeclarationKind" value="Constant" />
|
||||
<option name="com.jetbrains.cidr.lang.util.OCDeclarationKind" value="Global" />
|
||||
<option name="com.jetbrains.cidr.lang.util.OCDeclarationKind" value="Struct" />
|
||||
<option name="com.jetbrains.cidr.lang.util.OCDeclarationKind" value="FunctionPredecl" />
|
||||
<option name="com.jetbrains.cidr.lang.util.OCDeclarationKind" value="Function" />
|
||||
</file>
|
||||
<class>
|
||||
<option name="com.jetbrains.cidr.lang.util.OCDeclarationKind" value="Property" />
|
||||
<option name="com.jetbrains.cidr.lang.util.OCDeclarationKind" value="Synthesize" />
|
||||
<option name="com.jetbrains.cidr.lang.util.OCDeclarationKind" value="InitMethod" />
|
||||
<option name="com.jetbrains.cidr.lang.util.OCDeclarationKind" value="StaticMethod" />
|
||||
<option name="com.jetbrains.cidr.lang.util.OCDeclarationKind" value="InstanceMethod" />
|
||||
<option name="com.jetbrains.cidr.lang.util.OCDeclarationKind" value="DeallocMethod" />
|
||||
</class>
|
||||
<extensions>
|
||||
<pair source="cpp" header="h" />
|
||||
<pair source="c" header="h" />
|
||||
</extensions>
|
||||
</Objective-C-extensions>
|
||||
<XML>
|
||||
<option name="XML_LEGACY_SETTINGS_IMPORTED" value="true" />
|
||||
</XML>
|
||||
|
||||
17
LICENSE.txt
@@ -13,23 +13,6 @@
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
-------------------------------------------------------------------------
|
||||
|
||||
All files under the directories briar-android/src, briar-api/src,
|
||||
briar-core/src, briar-desktop/src and briar-test/src are licensed
|
||||
under the Apache License, version 2.0 (the "License"); you may not
|
||||
use these files 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.
|
||||
|
||||
-------------------------------------------------------------------------
|
||||
|
||||
GNU GENERAL PUBLIC LICENSE
|
||||
|
||||
@@ -11,10 +11,6 @@ android {
|
||||
consumerProguardFiles getDefaultProguardFile('proguard-android.txt'), '../briar-android/proguard-rules.txt'
|
||||
}
|
||||
|
||||
dexOptions {
|
||||
incremental true
|
||||
}
|
||||
|
||||
compileOptions {
|
||||
sourceCompatibility JavaVersion.VERSION_1_7
|
||||
targetCompatibility JavaVersion.VERSION_1_7
|
||||
|
||||
@@ -3,6 +3,7 @@ package org.briarproject;
|
||||
import net.jodah.concurrentunit.Waiter;
|
||||
|
||||
import org.briarproject.api.blogs.Blog;
|
||||
import org.briarproject.api.blogs.BlogCommentHeader;
|
||||
import org.briarproject.api.blogs.BlogFactory;
|
||||
import org.briarproject.api.blogs.BlogManager;
|
||||
import org.briarproject.api.blogs.BlogPost;
|
||||
@@ -11,7 +12,6 @@ import org.briarproject.api.blogs.BlogPostHeader;
|
||||
import org.briarproject.api.contact.ContactId;
|
||||
import org.briarproject.api.contact.ContactManager;
|
||||
import org.briarproject.api.crypto.CryptoComponent;
|
||||
import org.briarproject.api.crypto.KeyPair;
|
||||
import org.briarproject.api.crypto.SecretKey;
|
||||
import org.briarproject.api.db.DbException;
|
||||
import org.briarproject.api.event.Event;
|
||||
@@ -50,15 +50,17 @@ import javax.inject.Inject;
|
||||
|
||||
import static junit.framework.Assert.assertFalse;
|
||||
import static org.briarproject.TestPluginsModule.MAX_LATENCY;
|
||||
import static org.briarproject.api.blogs.MessageType.COMMENT;
|
||||
import static org.briarproject.api.blogs.MessageType.POST;
|
||||
import static org.briarproject.api.blogs.MessageType.WRAPPED_COMMENT;
|
||||
import static org.briarproject.api.blogs.MessageType.WRAPPED_POST;
|
||||
import static org.briarproject.api.sync.ValidationManager.State.DELIVERED;
|
||||
import static org.briarproject.api.sync.ValidationManager.State.INVALID;
|
||||
import static org.briarproject.api.sync.ValidationManager.State.PENDING;
|
||||
import static org.briarproject.api.sync.ValidationManager.State.VALID;
|
||||
import static org.junit.Assert.assertArrayEquals;
|
||||
import static org.junit.Assert.assertEquals;
|
||||
import static org.junit.Assert.assertTrue;
|
||||
|
||||
public class BlogManagerTest {
|
||||
public class BlogManagerTest extends BriarIntegrationTest {
|
||||
|
||||
private LifecycleManager lifecycleManager0, lifecycleManager1;
|
||||
private SyncSessionFactory sync0, sync1;
|
||||
@@ -89,10 +91,9 @@ public class BlogManagerTest {
|
||||
private final int TIMEOUT = 15000;
|
||||
private final String AUTHOR1 = "Author 1";
|
||||
private final String AUTHOR2 = "Author 2";
|
||||
private final String CONTENT_TYPE = "text/plain";
|
||||
|
||||
private static final Logger LOG =
|
||||
Logger.getLogger(ForumSharingIntegrationTest.class.getName());
|
||||
Logger.getLogger(BlogManagerTest.class.getName());
|
||||
|
||||
private BlogManagerTestComponent t0, t1;
|
||||
|
||||
@@ -172,15 +173,15 @@ public class BlogManagerTest {
|
||||
defaultInit();
|
||||
|
||||
// check that blog0 has no posts
|
||||
final byte[] body = TestUtils.getRandomBytes(42);
|
||||
final String body = TestUtils.getRandomString(42);
|
||||
Collection<BlogPostHeader> headers0 =
|
||||
blogManager0.getPostHeaders(blog0.getId());
|
||||
assertEquals(0, headers0.size());
|
||||
|
||||
// add a post to blog0
|
||||
BlogPost p = blogPostFactory
|
||||
.createBlogPost(blog0.getId(), null, clock.currentTimeMillis(),
|
||||
null, author0, CONTENT_TYPE, body);
|
||||
.createBlogPost(blog0.getId(), clock.currentTimeMillis(), null,
|
||||
author0, body);
|
||||
blogManager0.addLocalPost(p);
|
||||
|
||||
// check that post is now in blog0
|
||||
@@ -188,8 +189,7 @@ public class BlogManagerTest {
|
||||
assertEquals(1, headers0.size());
|
||||
|
||||
// check that body is there
|
||||
assertArrayEquals(body,
|
||||
blogManager0.getPostBody(p.getMessage().getId()));
|
||||
assertEquals(body, blogManager0.getPostBody(p.getMessage().getId()));
|
||||
|
||||
// make sure that blog0 at author1 doesn't have the post yet
|
||||
Collection<BlogPostHeader> headers1 =
|
||||
@@ -203,10 +203,10 @@ public class BlogManagerTest {
|
||||
// make sure post arrived
|
||||
headers1 = blogManager1.getPostHeaders(blog0.getId());
|
||||
assertEquals(1, headers1.size());
|
||||
assertEquals(POST, headers1.iterator().next().getType());
|
||||
|
||||
// check that body is there
|
||||
assertArrayEquals(body,
|
||||
blogManager1.getPostBody(p.getMessage().getId()));
|
||||
assertEquals(body, blogManager1.getPostBody(p.getMessage().getId()));
|
||||
|
||||
stopLifecycles();
|
||||
}
|
||||
@@ -217,10 +217,10 @@ public class BlogManagerTest {
|
||||
defaultInit();
|
||||
|
||||
// add a post to blog1
|
||||
final byte[] body = TestUtils.getRandomBytes(42);
|
||||
final String body = TestUtils.getRandomString(42);
|
||||
BlogPost p = blogPostFactory
|
||||
.createBlogPost(blog1.getId(), null, clock.currentTimeMillis(),
|
||||
null, author0, CONTENT_TYPE, body);
|
||||
.createBlogPost(blog1.getId(), clock.currentTimeMillis(), null,
|
||||
author0, body);
|
||||
blogManager0.addLocalPost(p);
|
||||
|
||||
// check that post is now in blog1
|
||||
@@ -240,32 +240,6 @@ public class BlogManagerTest {
|
||||
stopLifecycles();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testAddAndRemoveBlog() throws Exception {
|
||||
startLifecycles();
|
||||
defaultInit();
|
||||
|
||||
String name = "Test Blog";
|
||||
String desc = "Description";
|
||||
|
||||
// add blog
|
||||
Blog blog = blogManager0.addBlog(author0, name, desc);
|
||||
Collection<Blog> blogs0 = blogManager0.getBlogs();
|
||||
assertEquals(3, blogs0.size());
|
||||
assertTrue(blogs0.contains(blog));
|
||||
assertEquals(2, blogManager0.getBlogs(author0).size());
|
||||
assertTrue(blogManager0.canBeRemoved(blog.getId()));
|
||||
|
||||
// remove blog
|
||||
blogManager0.removeBlog(blog);
|
||||
blogs0 = blogManager0.getBlogs();
|
||||
assertEquals(2, blogs0.size());
|
||||
assertFalse(blogs0.contains(blog));
|
||||
assertEquals(1, blogManager0.getBlogs(author0).size());
|
||||
|
||||
stopLifecycles();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testCanNotRemoveContactsPersonalBlog() throws Exception {
|
||||
startLifecycles();
|
||||
@@ -287,20 +261,262 @@ public class BlogManagerTest {
|
||||
stopLifecycles();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testBlogComment() throws Exception {
|
||||
startLifecycles();
|
||||
defaultInit();
|
||||
|
||||
// add a post to blog0
|
||||
final String body = TestUtils.getRandomString(42);
|
||||
BlogPost p = blogPostFactory
|
||||
.createBlogPost(blog0.getId(), clock.currentTimeMillis(), null,
|
||||
author0, body);
|
||||
blogManager0.addLocalPost(p);
|
||||
|
||||
// sync the post over
|
||||
sync0To1();
|
||||
deliveryWaiter.await(TIMEOUT, 1);
|
||||
|
||||
// make sure post arrived
|
||||
Collection<BlogPostHeader> headers1 =
|
||||
blogManager1.getPostHeaders(blog0.getId());
|
||||
assertEquals(1, headers1.size());
|
||||
assertEquals(POST, headers1.iterator().next().getType());
|
||||
|
||||
// 1 adds a comment to that blog post
|
||||
String comment = "This is a comment on a blog post!";
|
||||
blogManager1
|
||||
.addLocalComment(author1, blog1.getId(), comment,
|
||||
headers1.iterator().next());
|
||||
|
||||
// sync comment over
|
||||
sync1To0();
|
||||
deliveryWaiter.await(TIMEOUT, 2);
|
||||
|
||||
// make sure comment and wrapped post arrived
|
||||
Collection<BlogPostHeader> headers0 =
|
||||
blogManager0.getPostHeaders(blog1.getId());
|
||||
assertEquals(1, headers0.size());
|
||||
assertEquals(COMMENT, headers0.iterator().next().getType());
|
||||
BlogCommentHeader h = (BlogCommentHeader) headers0.iterator().next();
|
||||
assertEquals(author0, h.getParent().getAuthor());
|
||||
|
||||
// ensure that body can be retrieved from wrapped post
|
||||
assertEquals(body, blogManager0.getPostBody(h.getParentId()));
|
||||
|
||||
// 1 has only their own comment in their blog
|
||||
headers1 = blogManager1.getPostHeaders(blog1.getId());
|
||||
assertEquals(1, headers1.size());
|
||||
|
||||
stopLifecycles();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testBlogCommentOnOwnPost() throws Exception {
|
||||
startLifecycles();
|
||||
defaultInit();
|
||||
|
||||
// add a post to blog0
|
||||
final String body = TestUtils.getRandomString(42);
|
||||
BlogPost p = blogPostFactory
|
||||
.createBlogPost(blog0.getId(), clock.currentTimeMillis(), null,
|
||||
author0, body);
|
||||
blogManager0.addLocalPost(p);
|
||||
|
||||
// get header of own post
|
||||
Collection<BlogPostHeader> headers0 =
|
||||
blogManager0.getPostHeaders(blog0.getId());
|
||||
assertEquals(1, headers0.size());
|
||||
BlogPostHeader header = headers0.iterator().next();
|
||||
|
||||
// add a comment on own post
|
||||
String comment = "This is a comment on my own blog post!";
|
||||
blogManager0
|
||||
.addLocalComment(author0, blog0.getId(), comment, header);
|
||||
|
||||
// sync the post and comment over
|
||||
sync0To1();
|
||||
deliveryWaiter.await(TIMEOUT, 2);
|
||||
|
||||
// make sure post arrived
|
||||
Collection<BlogPostHeader> headers1 =
|
||||
blogManager1.getPostHeaders(blog0.getId());
|
||||
assertEquals(2, headers1.size());
|
||||
for (BlogPostHeader h : headers1) {
|
||||
if (h.getType() == POST) {
|
||||
assertEquals(body, blogManager1.getPostBody(h.getId()));
|
||||
} else {
|
||||
assertEquals(comment, ((BlogCommentHeader)h).getComment());
|
||||
}
|
||||
}
|
||||
|
||||
stopLifecycles();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testCommentOnComment() throws Exception {
|
||||
startLifecycles();
|
||||
defaultInit();
|
||||
|
||||
// add a post to blog0
|
||||
final String body = TestUtils.getRandomString(42);
|
||||
BlogPost p = blogPostFactory
|
||||
.createBlogPost(blog0.getId(), clock.currentTimeMillis(), null,
|
||||
author0, body);
|
||||
blogManager0.addLocalPost(p);
|
||||
|
||||
// sync the post over
|
||||
sync0To1();
|
||||
deliveryWaiter.await(TIMEOUT, 1);
|
||||
|
||||
// make sure post arrived
|
||||
Collection<BlogPostHeader> headers1 =
|
||||
blogManager1.getPostHeaders(blog0.getId());
|
||||
assertEquals(1, headers1.size());
|
||||
assertEquals(POST, headers1.iterator().next().getType());
|
||||
|
||||
// 1 reblogs that blog post
|
||||
blogManager1
|
||||
.addLocalComment(author1, blog1.getId(), null,
|
||||
headers1.iterator().next());
|
||||
|
||||
// sync comment over
|
||||
sync1To0();
|
||||
deliveryWaiter.await(TIMEOUT, 2);
|
||||
|
||||
// make sure comment and wrapped post arrived
|
||||
Collection<BlogPostHeader> headers0 =
|
||||
blogManager0.getPostHeaders(blog1.getId());
|
||||
assertEquals(1, headers0.size());
|
||||
|
||||
// get header of comment
|
||||
BlogPostHeader cHeader = headers0.iterator().next();
|
||||
assertEquals(COMMENT, cHeader.getType());
|
||||
|
||||
// comment on the comment
|
||||
String comment = "This is a comment on a reblogged post.";
|
||||
blogManager0
|
||||
.addLocalComment(author0, blog0.getId(), comment, cHeader);
|
||||
|
||||
// sync comment over
|
||||
sync0To1();
|
||||
deliveryWaiter.await(TIMEOUT, 3);
|
||||
|
||||
// check that comment arrived
|
||||
headers1 =
|
||||
blogManager1.getPostHeaders(blog0.getId());
|
||||
assertEquals(2, headers1.size());
|
||||
|
||||
// get header of comment
|
||||
cHeader = null;
|
||||
for (BlogPostHeader h : headers1) {
|
||||
if (h.getType() == COMMENT) {
|
||||
cHeader = h;
|
||||
}
|
||||
}
|
||||
assertTrue(cHeader != null);
|
||||
|
||||
// another comment on the comment
|
||||
String comment2 = "This is a comment on a comment.";
|
||||
blogManager1.addLocalComment(author1, blog1.getId(), comment2, cHeader);
|
||||
|
||||
// sync comment over
|
||||
sync1To0();
|
||||
deliveryWaiter.await(TIMEOUT, 4);
|
||||
|
||||
// make sure new comment arrived
|
||||
headers0 =
|
||||
blogManager0.getPostHeaders(blog1.getId());
|
||||
assertEquals(2, headers0.size());
|
||||
boolean satisfied = false;
|
||||
for (BlogPostHeader h : headers0) {
|
||||
assertEquals(COMMENT, h.getType());
|
||||
BlogCommentHeader c = (BlogCommentHeader) h;
|
||||
if (c.getComment() != null && c.getComment().equals(comment2)) {
|
||||
assertEquals(author0, c.getParent().getAuthor());
|
||||
assertEquals(WRAPPED_COMMENT, c.getParent().getType());
|
||||
assertEquals(comment,
|
||||
((BlogCommentHeader) c.getParent()).getComment());
|
||||
assertEquals(WRAPPED_COMMENT,
|
||||
((BlogCommentHeader) c.getParent()).getParent()
|
||||
.getType());
|
||||
assertEquals(WRAPPED_POST,
|
||||
((BlogCommentHeader) ((BlogCommentHeader) c
|
||||
.getParent()).getParent()).getParent()
|
||||
.getType());
|
||||
satisfied = true;
|
||||
}
|
||||
}
|
||||
assertTrue(satisfied);
|
||||
|
||||
stopLifecycles();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testCommentOnOwnComment() throws Exception {
|
||||
|
||||
startLifecycles();
|
||||
defaultInit();
|
||||
|
||||
// add a post to blog0
|
||||
final String body = TestUtils.getRandomString(42);
|
||||
BlogPost p = blogPostFactory
|
||||
.createBlogPost(blog0.getId(), clock.currentTimeMillis(), null,
|
||||
author0, body);
|
||||
blogManager0.addLocalPost(p);
|
||||
|
||||
// sync the post over
|
||||
sync0To1();
|
||||
deliveryWaiter.await(TIMEOUT, 1);
|
||||
|
||||
// make sure post arrived
|
||||
Collection<BlogPostHeader> headers1 =
|
||||
blogManager1.getPostHeaders(blog0.getId());
|
||||
assertEquals(1, headers1.size());
|
||||
assertEquals(POST, headers1.iterator().next().getType());
|
||||
|
||||
// 1 reblogs that blog post with a comment
|
||||
String comment = "This is a comment on a post.";
|
||||
blogManager1
|
||||
.addLocalComment(author1, blog1.getId(), comment,
|
||||
headers1.iterator().next());
|
||||
|
||||
// get comment from own blog
|
||||
headers1 = blogManager1.getPostHeaders(blog1.getId());
|
||||
assertEquals(1, headers1.size());
|
||||
assertEquals(COMMENT, headers1.iterator().next().getType());
|
||||
BlogCommentHeader ch = (BlogCommentHeader) headers1.iterator().next();
|
||||
assertEquals(comment, ch.getComment());
|
||||
|
||||
comment = "This is a comment on a post with a comment.";
|
||||
blogManager1.addLocalComment(author1, blog1.getId(), comment, ch);
|
||||
|
||||
// sync both comments over (2 comments + 1 wrapped post)
|
||||
sync1To0();
|
||||
deliveryWaiter.await(TIMEOUT, 3);
|
||||
|
||||
// make sure both comments arrived
|
||||
Collection<BlogPostHeader> headers0 =
|
||||
blogManager0.getPostHeaders(blog1.getId());
|
||||
assertEquals(2, headers0.size());
|
||||
|
||||
stopLifecycles();
|
||||
}
|
||||
|
||||
@After
|
||||
public void tearDown() throws Exception {
|
||||
TestUtils.deleteTestDirectory(testDir);
|
||||
}
|
||||
|
||||
private class Listener implements EventListener {
|
||||
@Override
|
||||
public void eventOccurred(Event e) {
|
||||
if (e instanceof MessageStateChangedEvent) {
|
||||
MessageStateChangedEvent event = (MessageStateChangedEvent) e;
|
||||
if (!event.isLocal()) {
|
||||
if (event.getState() == DELIVERED) {
|
||||
deliveryWaiter.resume();
|
||||
} else if (event.getState() == VALID ||
|
||||
event.getState() == INVALID ||
|
||||
} else if (event.getState() == INVALID ||
|
||||
event.getState() == PENDING) {
|
||||
validationWaiter.resume();
|
||||
}
|
||||
@@ -310,27 +526,16 @@ public class BlogManagerTest {
|
||||
}
|
||||
|
||||
private void defaultInit() throws DbException {
|
||||
addDefaultIdentities();
|
||||
getDefaultIdentities();
|
||||
addDefaultContacts();
|
||||
listenToEvents();
|
||||
}
|
||||
|
||||
private void addDefaultIdentities() throws DbException {
|
||||
KeyPair keyPair0 = crypto.generateSignatureKeyPair();
|
||||
byte[] publicKey0 = keyPair0.getPublic().getEncoded();
|
||||
byte[] privateKey0 = keyPair0.getPrivate().getEncoded();
|
||||
author0 = authorFactory
|
||||
.createLocalAuthor(AUTHOR1, publicKey0, privateKey0);
|
||||
identityManager0.addLocalAuthor(author0);
|
||||
blog0 = blogFactory.createPersonalBlog(author0);
|
||||
|
||||
KeyPair keyPair1 = crypto.generateSignatureKeyPair();
|
||||
byte[] publicKey1 = keyPair1.getPublic().getEncoded();
|
||||
byte[] privateKey1 = keyPair1.getPrivate().getEncoded();
|
||||
author1 = authorFactory
|
||||
.createLocalAuthor(AUTHOR2, publicKey1, privateKey1);
|
||||
identityManager1.addLocalAuthor(author1);
|
||||
blog1 = blogFactory.createPersonalBlog(author1);
|
||||
private void getDefaultIdentities() throws DbException {
|
||||
author0 = identityManager0.getLocalAuthor();
|
||||
author1 = identityManager1.getLocalAuthor();
|
||||
blog0 = blogFactory.createBlog(author0);
|
||||
blog1 = blogFactory.createBlog(author1);
|
||||
}
|
||||
|
||||
private void addDefaultContacts() throws DbException {
|
||||
@@ -387,8 +592,8 @@ public class BlogManagerTest {
|
||||
// Start the lifecycle manager and wait for it to finish
|
||||
lifecycleManager0 = t0.getLifecycleManager();
|
||||
lifecycleManager1 = t1.getLifecycleManager();
|
||||
lifecycleManager0.startServices();
|
||||
lifecycleManager1.startServices();
|
||||
lifecycleManager0.startServices(AUTHOR1);
|
||||
lifecycleManager1.startServices(AUTHOR2);
|
||||
lifecycleManager0.waitForStartup();
|
||||
lifecycleManager1.waitForStartup();
|
||||
}
|
||||
|
||||
@@ -8,11 +8,12 @@ import org.briarproject.api.blogs.BlogInvitationResponse;
|
||||
import org.briarproject.api.blogs.BlogManager;
|
||||
import org.briarproject.api.blogs.BlogPostFactory;
|
||||
import org.briarproject.api.blogs.BlogSharingManager;
|
||||
import org.briarproject.api.clients.ContactGroupFactory;
|
||||
import org.briarproject.api.clients.MessageTracker;
|
||||
import org.briarproject.api.contact.Contact;
|
||||
import org.briarproject.api.contact.ContactId;
|
||||
import org.briarproject.api.contact.ContactManager;
|
||||
import org.briarproject.api.crypto.CryptoComponent;
|
||||
import org.briarproject.api.crypto.KeyPair;
|
||||
import org.briarproject.api.crypto.SecretKey;
|
||||
import org.briarproject.api.db.DbException;
|
||||
import org.briarproject.api.event.BlogInvitationReceivedEvent;
|
||||
@@ -25,7 +26,7 @@ import org.briarproject.api.identity.IdentityManager;
|
||||
import org.briarproject.api.identity.LocalAuthor;
|
||||
import org.briarproject.api.lifecycle.LifecycleManager;
|
||||
import org.briarproject.api.sharing.InvitationMessage;
|
||||
import org.briarproject.api.sync.ClientId;
|
||||
import org.briarproject.api.sync.GroupId;
|
||||
import org.briarproject.api.sync.SyncSession;
|
||||
import org.briarproject.api.sync.SyncSessionFactory;
|
||||
import org.briarproject.api.sync.ValidationManager.State;
|
||||
@@ -57,26 +58,28 @@ import java.util.logging.Logger;
|
||||
import javax.inject.Inject;
|
||||
|
||||
import static org.briarproject.TestPluginsModule.MAX_LATENCY;
|
||||
import static org.briarproject.api.blogs.BlogSharingManager.CLIENT_ID;
|
||||
import static org.briarproject.api.sync.ValidationManager.State.DELIVERED;
|
||||
import static org.briarproject.api.sync.ValidationManager.State.INVALID;
|
||||
import static org.junit.Assert.assertEquals;
|
||||
import static org.junit.Assert.assertFalse;
|
||||
import static org.junit.Assert.assertTrue;
|
||||
|
||||
public class BlogSharingIntegrationTest extends BriarTestCase {
|
||||
public class BlogSharingIntegrationTest extends BriarIntegrationTest {
|
||||
|
||||
private LifecycleManager lifecycleManager0, lifecycleManager1,
|
||||
lifecycleManager2;
|
||||
private SyncSessionFactory sync0, sync1, sync2;
|
||||
private BlogManager blogManager0, blogManager1, blogManager2;
|
||||
private SyncSessionFactory sync0, sync1;
|
||||
private BlogManager blogManager0, blogManager1;
|
||||
private MessageTracker messageTracker0, messageTracker1;
|
||||
private ContactManager contactManager0, contactManager1, contactManager2;
|
||||
private Contact contact1, contact2, contact01, contact02;
|
||||
private ContactId contactId1, contactId2, contactId01, contactId02;
|
||||
private ContactId contactId1, contactId01;
|
||||
private IdentityManager identityManager0, identityManager1,
|
||||
identityManager2;
|
||||
private LocalAuthor author0, author1, author2;
|
||||
private Blog blog0, blog1, blog2;
|
||||
private SharerListener listener0, listener2;
|
||||
private SharerListener listener0;
|
||||
private InviteeListener listener1;
|
||||
|
||||
@Inject
|
||||
@@ -84,6 +87,8 @@ public class BlogSharingIntegrationTest extends BriarTestCase {
|
||||
@Inject
|
||||
AuthorFactory authorFactory;
|
||||
@Inject
|
||||
ContactGroupFactory contactGroupFactory;
|
||||
@Inject
|
||||
BlogPostFactory blogPostFactory;
|
||||
@Inject
|
||||
CryptoComponent cryptoComponent;
|
||||
@@ -139,13 +144,13 @@ public class BlogSharingIntegrationTest extends BriarTestCase {
|
||||
contactManager2 = t2.getContactManager();
|
||||
blogManager0 = t0.getBlogManager();
|
||||
blogManager1 = t1.getBlogManager();
|
||||
blogManager2 = t2.getBlogManager();
|
||||
messageTracker0 = t0.getMessageTracker();
|
||||
messageTracker1 = t1.getMessageTracker();
|
||||
blogSharingManager0 = t0.getBlogSharingManager();
|
||||
blogSharingManager1 = t1.getBlogSharingManager();
|
||||
blogSharingManager2 = t2.getBlogSharingManager();
|
||||
sync0 = t0.getSyncSessionFactory();
|
||||
sync1 = t1.getSyncSessionFactory();
|
||||
sync2 = t2.getSyncSessionFactory();
|
||||
|
||||
// initialize waiters fresh for each test
|
||||
eventWaiter = new Waiter();
|
||||
@@ -188,15 +193,22 @@ public class BlogSharingIntegrationTest extends BriarTestCase {
|
||||
// invitee has own blog and that of the sharer
|
||||
assertEquals(2, blogManager1.getBlogs().size());
|
||||
|
||||
// get sharing group and assert group message count
|
||||
GroupId g = contactGroupFactory.createContactGroup(CLIENT_ID, contact1)
|
||||
.getId();
|
||||
assertGroupCount(messageTracker0, g, 1, 0);
|
||||
|
||||
// sync first request message
|
||||
sync0To1();
|
||||
eventWaiter.await(TIMEOUT, 1);
|
||||
assertTrue(listener1.requestReceived);
|
||||
assertGroupCount(messageTracker1, g, 2, 1);
|
||||
|
||||
// sync response back
|
||||
sync1To0();
|
||||
eventWaiter.await(TIMEOUT, 1);
|
||||
assertTrue(listener0.responseReceived);
|
||||
assertGroupCount(messageTracker0, g, 2, 1);
|
||||
|
||||
// blog was added successfully
|
||||
assertEquals(0, blogSharingManager0.getInvitations().size());
|
||||
@@ -233,6 +245,10 @@ public class BlogSharingIntegrationTest extends BriarTestCase {
|
||||
assertFalse(blogSharingManager0.canBeShared(blog2.getId(), contact1));
|
||||
assertFalse(blogSharingManager1.canBeShared(blog2.getId(), contact01));
|
||||
|
||||
// group message count is still correct
|
||||
assertGroupCount(messageTracker0, g, 2, 1);
|
||||
assertGroupCount(messageTracker1, g, 2, 1);
|
||||
|
||||
stopLifecycles();
|
||||
}
|
||||
|
||||
@@ -424,7 +440,7 @@ public class BlogSharingIntegrationTest extends BriarTestCase {
|
||||
eventWaiter.await(TIMEOUT, 1);
|
||||
assertTrue(listener0.responseReceived);
|
||||
|
||||
// blog was added successfully and is shard both ways
|
||||
// blog was added successfully and is shared both ways
|
||||
assertEquals(3, blogManager1.getBlogs().size());
|
||||
Collection<Contact> sharedWith =
|
||||
blogSharingManager0.getSharedWith(blog2.getId());
|
||||
@@ -511,23 +527,15 @@ public class BlogSharingIntegrationTest extends BriarTestCase {
|
||||
|
||||
private class SharerListener implements EventListener {
|
||||
|
||||
volatile boolean requestReceived = false;
|
||||
volatile boolean responseReceived = false;
|
||||
private volatile boolean responseReceived = false;
|
||||
|
||||
@Override
|
||||
public void eventOccurred(Event e) {
|
||||
if (e instanceof MessageStateChangedEvent) {
|
||||
MessageStateChangedEvent event = (MessageStateChangedEvent) e;
|
||||
State s = event.getState();
|
||||
ClientId c = event.getClientId();
|
||||
if ((s == DELIVERED || s == INVALID) &&
|
||||
c.equals(blogSharingManager0.getClientId()) &&
|
||||
!event.isLocal()) {
|
||||
LOG.info("TEST: Sharer received message in group " +
|
||||
event.getMessage().getGroupId().hashCode());
|
||||
msgWaiter.resume();
|
||||
} else if (s == DELIVERED && !event.isLocal() &&
|
||||
c.equals(blogManager0.getClientId())) {
|
||||
LOG.info("TEST: Sharer received blog post");
|
||||
if ((s == DELIVERED || s == INVALID) && !event.isLocal()) {
|
||||
LOG.info("TEST: Sharer received message");
|
||||
msgWaiter.resume();
|
||||
}
|
||||
} else if (e instanceof BlogInvitationResponseReceivedEvent) {
|
||||
@@ -542,8 +550,7 @@ public class BlogSharingIntegrationTest extends BriarTestCase {
|
||||
BlogInvitationReceivedEvent event =
|
||||
(BlogInvitationReceivedEvent) e;
|
||||
eventWaiter.assertEquals(contactId1, event.getContactId());
|
||||
requestReceived = true;
|
||||
Blog b = event.getBlog();
|
||||
Blog b = event.getShareable();
|
||||
try {
|
||||
Contact c = contactManager0.getContact(contactId1);
|
||||
blogSharingManager0.respondToInvitation(b, c, true);
|
||||
@@ -558,34 +565,26 @@ public class BlogSharingIntegrationTest extends BriarTestCase {
|
||||
|
||||
private class InviteeListener implements EventListener {
|
||||
|
||||
volatile boolean requestReceived = false;
|
||||
volatile boolean responseReceived = false;
|
||||
private volatile boolean requestReceived = false;
|
||||
|
||||
private final boolean accept, answer;
|
||||
|
||||
InviteeListener(boolean accept, boolean answer) {
|
||||
private InviteeListener(boolean accept, boolean answer) {
|
||||
this.accept = accept;
|
||||
this.answer = answer;
|
||||
}
|
||||
|
||||
InviteeListener(boolean accept) {
|
||||
private InviteeListener(boolean accept) {
|
||||
this(accept, true);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void eventOccurred(Event e) {
|
||||
if (e instanceof MessageStateChangedEvent) {
|
||||
MessageStateChangedEvent event = (MessageStateChangedEvent) e;
|
||||
State s = event.getState();
|
||||
ClientId c = event.getClientId();
|
||||
if ((s == DELIVERED || s == INVALID) &&
|
||||
c.equals(blogSharingManager0.getClientId()) &&
|
||||
!event.isLocal()) {
|
||||
LOG.info("TEST: Invitee received message in group " +
|
||||
event.getMessage().getGroupId().hashCode());
|
||||
msgWaiter.resume();
|
||||
} else if (s == DELIVERED && !event.isLocal() &&
|
||||
c.equals(blogManager0.getClientId())) {
|
||||
LOG.info("TEST: Invitee received blog post");
|
||||
if ((s == DELIVERED || s == INVALID) && !event.isLocal()) {
|
||||
LOG.info("TEST: Invitee received message");
|
||||
msgWaiter.resume();
|
||||
}
|
||||
} else if (e instanceof BlogInvitationReceivedEvent) {
|
||||
@@ -593,7 +592,7 @@ public class BlogSharingIntegrationTest extends BriarTestCase {
|
||||
(BlogInvitationReceivedEvent) e;
|
||||
requestReceived = true;
|
||||
if (!answer) return;
|
||||
Blog b = event.getBlog();
|
||||
Blog b = event.getShareable();
|
||||
try {
|
||||
eventWaiter.assertEquals(1,
|
||||
blogSharingManager1.getInvitations().size());
|
||||
@@ -611,7 +610,6 @@ public class BlogSharingIntegrationTest extends BriarTestCase {
|
||||
BlogInvitationResponseReceivedEvent event =
|
||||
(BlogInvitationResponseReceivedEvent) e;
|
||||
eventWaiter.assertEquals(contactId01, event.getContactId());
|
||||
responseReceived = true;
|
||||
eventWaiter.resume();
|
||||
}
|
||||
}
|
||||
@@ -622,9 +620,9 @@ public class BlogSharingIntegrationTest extends BriarTestCase {
|
||||
lifecycleManager0 = t0.getLifecycleManager();
|
||||
lifecycleManager1 = t1.getLifecycleManager();
|
||||
lifecycleManager2 = t2.getLifecycleManager();
|
||||
lifecycleManager0.startServices();
|
||||
lifecycleManager1.startServices();
|
||||
lifecycleManager2.startServices();
|
||||
lifecycleManager0.startServices(SHARER);
|
||||
lifecycleManager1.startServices(INVITEE);
|
||||
lifecycleManager2.startServices(CONTACT2);
|
||||
lifecycleManager0.waitForStartup();
|
||||
lifecycleManager1.waitForStartup();
|
||||
lifecycleManager2.waitForStartup();
|
||||
@@ -641,30 +639,16 @@ public class BlogSharingIntegrationTest extends BriarTestCase {
|
||||
}
|
||||
|
||||
private void defaultInit(boolean accept) throws DbException {
|
||||
addDefaultIdentities();
|
||||
getDefaultIdentities();
|
||||
addDefaultContacts();
|
||||
getPersonalBlogOfSharer();
|
||||
listenToEvents(accept);
|
||||
}
|
||||
|
||||
private void addDefaultIdentities() throws DbException {
|
||||
KeyPair keyPair = cryptoComponent.generateSignatureKeyPair();
|
||||
author0 = authorFactory.createLocalAuthor(SHARER,
|
||||
keyPair.getPublic().getEncoded(),
|
||||
keyPair.getPrivate().getEncoded());
|
||||
identityManager0.addLocalAuthor(author0);
|
||||
|
||||
keyPair = cryptoComponent.generateSignatureKeyPair();
|
||||
author1 = authorFactory.createLocalAuthor(INVITEE,
|
||||
keyPair.getPublic().getEncoded(),
|
||||
keyPair.getPrivate().getEncoded());
|
||||
identityManager1.addLocalAuthor(author1);
|
||||
|
||||
keyPair = cryptoComponent.generateSignatureKeyPair();
|
||||
author2 = authorFactory.createLocalAuthor(CONTACT2,
|
||||
keyPair.getPublic().getEncoded(),
|
||||
keyPair.getPrivate().getEncoded());
|
||||
identityManager2.addLocalAuthor(author2);
|
||||
private void getDefaultIdentities() throws DbException {
|
||||
author0 = identityManager0.getLocalAuthor();
|
||||
author1 = identityManager1.getLocalAuthor();
|
||||
author2 = identityManager2.getLocalAuthor();
|
||||
}
|
||||
|
||||
private void addDefaultContacts() throws DbException {
|
||||
@@ -675,7 +659,7 @@ public class BlogSharingIntegrationTest extends BriarTestCase {
|
||||
);
|
||||
contact1 = contactManager0.getContact(contactId1);
|
||||
// sharer adds second contact
|
||||
contactId2 = contactManager0.addContact(author2,
|
||||
ContactId contactId2 = contactManager0.addContact(author2,
|
||||
author0.getId(), master, clock.currentTimeMillis(), true,
|
||||
true, true
|
||||
);
|
||||
@@ -686,7 +670,7 @@ public class BlogSharingIntegrationTest extends BriarTestCase {
|
||||
true, true
|
||||
);
|
||||
contact01 = contactManager1.getContact(contactId01);
|
||||
contactId02 = contactManager2.addContact(author0,
|
||||
ContactId contactId02 = contactManager2.addContact(author0,
|
||||
author2.getId(), master, clock.currentTimeMillis(), true,
|
||||
true, true
|
||||
);
|
||||
@@ -704,7 +688,7 @@ public class BlogSharingIntegrationTest extends BriarTestCase {
|
||||
t0.getEventBus().addListener(listener0);
|
||||
listener1 = new InviteeListener(accept);
|
||||
t1.getEventBus().addListener(listener1);
|
||||
listener2 = new SharerListener();
|
||||
SharerListener listener2 = new SharerListener();
|
||||
t2.getEventBus().addListener(listener2);
|
||||
}
|
||||
|
||||
|
||||
@@ -2,13 +2,9 @@ package org.briarproject;
|
||||
|
||||
import org.briarproject.api.blogs.BlogManager;
|
||||
import org.briarproject.api.blogs.BlogSharingManager;
|
||||
import org.briarproject.api.clients.ClientHelper;
|
||||
import org.briarproject.api.clients.MessageQueueManager;
|
||||
import org.briarproject.api.clients.PrivateGroupFactory;
|
||||
import org.briarproject.api.clients.MessageTracker;
|
||||
import org.briarproject.api.contact.ContactManager;
|
||||
import org.briarproject.api.db.DatabaseComponent;
|
||||
import org.briarproject.api.event.EventBus;
|
||||
import org.briarproject.api.forum.ForumManager;
|
||||
import org.briarproject.api.identity.IdentityManager;
|
||||
import org.briarproject.api.lifecycle.LifecycleManager;
|
||||
import org.briarproject.api.sync.SyncSessionFactory;
|
||||
@@ -22,6 +18,7 @@ import org.briarproject.event.EventModule;
|
||||
import org.briarproject.forum.ForumModule;
|
||||
import org.briarproject.identity.IdentityModule;
|
||||
import org.briarproject.lifecycle.LifecycleModule;
|
||||
import org.briarproject.messaging.MessagingModule;
|
||||
import org.briarproject.properties.PropertiesModule;
|
||||
import org.briarproject.sharing.SharingModule;
|
||||
import org.briarproject.sync.SyncModule;
|
||||
@@ -51,7 +48,8 @@ import dagger.Component;
|
||||
SharingModule.class,
|
||||
SyncModule.class,
|
||||
SystemModule.class,
|
||||
TransportModule.class
|
||||
TransportModule.class,
|
||||
MessagingModule.class
|
||||
})
|
||||
interface BlogSharingIntegrationTestComponent {
|
||||
|
||||
@@ -85,16 +83,8 @@ interface BlogSharingIntegrationTestComponent {
|
||||
|
||||
BlogManager getBlogManager();
|
||||
|
||||
MessageTracker getMessageTracker();
|
||||
|
||||
SyncSessionFactory getSyncSessionFactory();
|
||||
|
||||
/* the following methods are only needed to manually construct messages */
|
||||
|
||||
DatabaseComponent getDatabaseComponent();
|
||||
|
||||
PrivateGroupFactory getPrivateGroupFactory();
|
||||
|
||||
ClientHelper getClientHelper();
|
||||
|
||||
MessageQueueManager getMessageQueueManager();
|
||||
|
||||
}
|
||||
|
||||
@@ -0,0 +1,30 @@
|
||||
package org.briarproject;
|
||||
|
||||
import org.briarproject.api.clients.MessageTracker;
|
||||
import org.briarproject.api.clients.MessageTracker.GroupCount;
|
||||
import org.briarproject.api.db.DbException;
|
||||
import org.briarproject.api.sync.GroupId;
|
||||
|
||||
import static org.junit.Assert.assertEquals;
|
||||
|
||||
public abstract class BriarIntegrationTest extends BriarTestCase {
|
||||
|
||||
protected static void assertGroupCount(MessageTracker tracker, GroupId g,
|
||||
long msgCount, long unreadCount, long latestMsg)
|
||||
throws DbException {
|
||||
|
||||
GroupCount groupCount = tracker.getGroupCount(g);
|
||||
assertEquals(msgCount, groupCount.getMsgCount());
|
||||
assertEquals(unreadCount, groupCount.getUnreadCount());
|
||||
assertEquals(latestMsg, groupCount.getLatestMsgTime());
|
||||
}
|
||||
|
||||
protected static void assertGroupCount(MessageTracker tracker, GroupId g,
|
||||
long msgCount, long unreadCount) throws DbException {
|
||||
|
||||
GroupCount c1 = tracker.getGroupCount(g);
|
||||
assertEquals(msgCount, c1.getMsgCount());
|
||||
assertEquals(unreadCount, c1.getUnreadCount());
|
||||
}
|
||||
|
||||
}
|
||||
@@ -4,9 +4,11 @@ import junit.framework.Assert;
|
||||
|
||||
import net.jodah.concurrentunit.Waiter;
|
||||
|
||||
import org.briarproject.api.clients.MessageTracker;
|
||||
import org.briarproject.api.contact.Contact;
|
||||
import org.briarproject.api.contact.ContactId;
|
||||
import org.briarproject.api.contact.ContactManager;
|
||||
import org.briarproject.api.crypto.CryptoComponent;
|
||||
import org.briarproject.api.crypto.SecretKey;
|
||||
import org.briarproject.api.db.DbException;
|
||||
import org.briarproject.api.event.Event;
|
||||
@@ -34,7 +36,7 @@ import org.briarproject.properties.PropertiesModule;
|
||||
import org.briarproject.sharing.SharingModule;
|
||||
import org.briarproject.sync.SyncModule;
|
||||
import org.briarproject.transport.TransportModule;
|
||||
import org.briarproject.util.StringUtils;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
import org.junit.After;
|
||||
import org.junit.Before;
|
||||
import org.junit.Test;
|
||||
@@ -53,19 +55,18 @@ import static junit.framework.Assert.assertEquals;
|
||||
import static junit.framework.Assert.assertNull;
|
||||
import static junit.framework.TestCase.assertFalse;
|
||||
import static org.briarproject.TestPluginsModule.MAX_LATENCY;
|
||||
import static org.briarproject.api.identity.AuthorConstants.MAX_PUBLIC_KEY_LENGTH;
|
||||
import static org.briarproject.api.sync.ValidationManager.State.DELIVERED;
|
||||
import static org.briarproject.api.sync.ValidationManager.State.INVALID;
|
||||
import static org.briarproject.api.sync.ValidationManager.State.PENDING;
|
||||
import static org.briarproject.api.sync.ValidationManager.State.VALID;
|
||||
import static org.junit.Assert.assertTrue;
|
||||
|
||||
public class ForumManagerTest {
|
||||
public class ForumManagerTest extends BriarIntegrationTest {
|
||||
|
||||
private LifecycleManager lifecycleManager0, lifecycleManager1;
|
||||
private SyncSessionFactory sync0, sync1;
|
||||
private ForumManager forumManager0, forumManager1;
|
||||
private ContactManager contactManager0, contactManager1;
|
||||
private MessageTracker messageTracker0, messageTracker1;
|
||||
private ContactId contactId0,contactId1;
|
||||
private IdentityManager identityManager0, identityManager1;
|
||||
private LocalAuthor author0, author1;
|
||||
@@ -76,6 +77,8 @@ public class ForumManagerTest {
|
||||
@Inject
|
||||
AuthorFactory authorFactory;
|
||||
@Inject
|
||||
CryptoComponent crypto;
|
||||
@Inject
|
||||
ForumPostFactory forumPostFactory;
|
||||
|
||||
// objects accessed from background threads need to be volatile
|
||||
@@ -116,6 +119,8 @@ public class ForumManagerTest {
|
||||
identityManager1 = t1.getIdentityManager();
|
||||
contactManager0 = t0.getContactManager();
|
||||
contactManager1 = t1.getContactManager();
|
||||
messageTracker0 = t0.getMessageTracker();
|
||||
messageTracker1 = t1.getMessageTracker();
|
||||
forumManager0 = t0.getForumManager();
|
||||
forumManager1 = t1.getForumManager();
|
||||
forumSharingManager0 = t0.getForumSharingManager();
|
||||
@@ -128,16 +133,17 @@ public class ForumManagerTest {
|
||||
deliveryWaiter = new Waiter();
|
||||
}
|
||||
|
||||
private ForumPost createForumPost(GroupId groupId, ForumPost parent,
|
||||
String body, long ms) throws Exception {
|
||||
return forumPostFactory.createAnonymousPost(groupId, ms,
|
||||
private ForumPost createForumPost(GroupId groupId,
|
||||
@Nullable ForumPost parent, String body, long ms) throws Exception {
|
||||
return forumPostFactory.createPost(groupId, ms,
|
||||
parent == null ? null : parent.getMessage().getId(),
|
||||
"text/plain", StringUtils.toUtf8(body));
|
||||
author0, body);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testForumPost() throws Exception {
|
||||
startLifecycles();
|
||||
getDefaultIdentities();
|
||||
Forum forum = forumManager0.addForum("TestForum");
|
||||
assertEquals(1, forumManager0.getForums().size());
|
||||
final long ms1 = clock.currentTimeMillis() - 1000L;
|
||||
@@ -151,15 +157,24 @@ public class ForumManagerTest {
|
||||
createForumPost(forum.getGroup().getId(), post1, body2, ms2);
|
||||
assertEquals(ms2, post2.getMessage().getTimestamp());
|
||||
forumManager0.addLocalPost(post1);
|
||||
forumManager0.setReadFlag(post1.getMessage().getId(), true);
|
||||
forumManager0.setReadFlag(forum.getGroup().getId(),
|
||||
post1.getMessage().getId(), true);
|
||||
assertGroupCount(messageTracker0, forum.getGroup().getId(), 1, 0,
|
||||
post1.getMessage().getTimestamp());
|
||||
forumManager0.addLocalPost(post2);
|
||||
forumManager0.setReadFlag(post2.getMessage().getId(), false);
|
||||
forumManager0.setReadFlag(forum.getGroup().getId(),
|
||||
post2.getMessage().getId(), false);
|
||||
assertGroupCount(messageTracker0, forum.getGroup().getId(), 2, 1,
|
||||
post2.getMessage().getTimestamp());
|
||||
forumManager0.setReadFlag(forum.getGroup().getId(),
|
||||
post2.getMessage().getId(), false);
|
||||
assertGroupCount(messageTracker0, forum.getGroup().getId(), 2, 1,
|
||||
post2.getMessage().getTimestamp());
|
||||
Collection<ForumPostHeader> headers =
|
||||
forumManager0.getPostHeaders(forum.getGroup().getId());
|
||||
assertEquals(2, headers.size());
|
||||
for (ForumPostHeader h : headers) {
|
||||
final String hBody =
|
||||
StringUtils.fromUtf8(forumManager0.getPostBody(h.getId()));
|
||||
final String hBody = forumManager0.getPostBody(h.getId());
|
||||
|
||||
boolean isPost1 = h.getId().equals(post1.getMessage().getId());
|
||||
boolean isPost2 = h.getId().equals(post2.getMessage().getId());
|
||||
@@ -203,23 +218,29 @@ public class ForumManagerTest {
|
||||
forumManager0.addLocalPost(post1);
|
||||
assertEquals(1, forumManager0.getPostHeaders(g).size());
|
||||
assertEquals(0, forumManager1.getPostHeaders(g).size());
|
||||
assertGroupCount(messageTracker0, g, 1, 0, time);
|
||||
assertGroupCount(messageTracker1, g, 0, 0, 0);
|
||||
|
||||
// send post to 1
|
||||
sync0To1();
|
||||
deliveryWaiter.await(TIMEOUT, 1);
|
||||
assertEquals(1, forumManager1.getPostHeaders(g).size());
|
||||
assertGroupCount(messageTracker1, g, 1, 1, time);
|
||||
|
||||
// add another forum post
|
||||
time = clock.currentTimeMillis();
|
||||
ForumPost post2 = createForumPost(g, null, "b", time);
|
||||
long time2 = clock.currentTimeMillis();
|
||||
ForumPost post2 = createForumPost(g, null, "b", time2);
|
||||
forumManager1.addLocalPost(post2);
|
||||
assertEquals(1, forumManager0.getPostHeaders(g).size());
|
||||
assertEquals(2, forumManager1.getPostHeaders(g).size());
|
||||
assertGroupCount(messageTracker0, g, 1, 0, time);
|
||||
assertGroupCount(messageTracker1, g, 2, 1, time2);
|
||||
|
||||
// send post to 0
|
||||
sync1To0();
|
||||
deliveryWaiter.await(TIMEOUT, 1);
|
||||
assertEquals(2, forumManager1.getPostHeaders(g).size());
|
||||
assertGroupCount(messageTracker0, g, 2, 1, time2);
|
||||
|
||||
stopLifecycles();
|
||||
}
|
||||
@@ -298,7 +319,7 @@ public class ForumManagerTest {
|
||||
assertEquals(1, forumManager0.getPostHeaders(g).size());
|
||||
assertEquals(0, forumManager1.getPostHeaders(g).size());
|
||||
|
||||
// send posts to 1
|
||||
// send the child post to 1
|
||||
sync0To1();
|
||||
validationWaiter.await(TIMEOUT, 1);
|
||||
assertEquals(1, forumManager0.getPostHeaders(g).size());
|
||||
@@ -327,14 +348,14 @@ public class ForumManagerTest {
|
||||
}
|
||||
|
||||
private class Listener implements EventListener {
|
||||
@Override
|
||||
public void eventOccurred(Event e) {
|
||||
if (e instanceof MessageStateChangedEvent) {
|
||||
MessageStateChangedEvent event = (MessageStateChangedEvent) e;
|
||||
if (!event.isLocal()) {
|
||||
if (event.getState() == DELIVERED) {
|
||||
deliveryWaiter.resume();
|
||||
} else if (event.getState() == VALID ||
|
||||
event.getState() == INVALID ||
|
||||
} else if (event.getState() == INVALID ||
|
||||
event.getState() == PENDING) {
|
||||
validationWaiter.resume();
|
||||
}
|
||||
@@ -344,21 +365,15 @@ public class ForumManagerTest {
|
||||
}
|
||||
|
||||
private void defaultInit() throws DbException {
|
||||
addDefaultIdentities();
|
||||
getDefaultIdentities();
|
||||
addDefaultContacts();
|
||||
addForum();
|
||||
listenToEvents();
|
||||
}
|
||||
|
||||
private void addDefaultIdentities() throws DbException {
|
||||
author0 = authorFactory.createLocalAuthor(SHARER,
|
||||
TestUtils.getRandomBytes(MAX_PUBLIC_KEY_LENGTH),
|
||||
TestUtils.getRandomBytes(123));
|
||||
identityManager0.addLocalAuthor(author0);
|
||||
author1 = authorFactory.createLocalAuthor(INVITEE,
|
||||
TestUtils.getRandomBytes(MAX_PUBLIC_KEY_LENGTH),
|
||||
TestUtils.getRandomBytes(123));
|
||||
identityManager1.addLocalAuthor(author1);
|
||||
private void getDefaultIdentities() throws DbException {
|
||||
author0 = identityManager0.getLocalAuthor();
|
||||
author1 = identityManager1.getLocalAuthor();
|
||||
}
|
||||
|
||||
private void addDefaultContacts() throws DbException {
|
||||
@@ -419,8 +434,8 @@ public class ForumManagerTest {
|
||||
// Start the lifecycle manager and wait for it to finish
|
||||
lifecycleManager0 = t0.getLifecycleManager();
|
||||
lifecycleManager1 = t1.getLifecycleManager();
|
||||
lifecycleManager0.startServices();
|
||||
lifecycleManager1.startServices();
|
||||
lifecycleManager0.startServices(SHARER);
|
||||
lifecycleManager1.startServices(INVITEE);
|
||||
lifecycleManager0.waitForStartup();
|
||||
lifecycleManager1.waitForStartup();
|
||||
}
|
||||
|
||||
@@ -1,5 +1,6 @@
|
||||
package org.briarproject;
|
||||
|
||||
import org.briarproject.api.clients.MessageTracker;
|
||||
import org.briarproject.api.contact.ContactManager;
|
||||
import org.briarproject.api.event.EventBus;
|
||||
import org.briarproject.api.forum.ForumManager;
|
||||
@@ -17,6 +18,7 @@ import org.briarproject.event.EventModule;
|
||||
import org.briarproject.forum.ForumModule;
|
||||
import org.briarproject.identity.IdentityModule;
|
||||
import org.briarproject.lifecycle.LifecycleModule;
|
||||
import org.briarproject.messaging.MessagingModule;
|
||||
import org.briarproject.properties.PropertiesModule;
|
||||
import org.briarproject.sharing.SharingModule;
|
||||
import org.briarproject.sync.SyncModule;
|
||||
@@ -46,7 +48,8 @@ import dagger.Component;
|
||||
SharingModule.class,
|
||||
SyncModule.class,
|
||||
SystemModule.class,
|
||||
TransportModule.class
|
||||
TransportModule.class,
|
||||
MessagingModule.class
|
||||
})
|
||||
interface ForumManagerTestComponent {
|
||||
|
||||
@@ -76,6 +79,8 @@ interface ForumManagerTestComponent {
|
||||
|
||||
ContactManager getContactManager();
|
||||
|
||||
MessageTracker getMessageTracker();
|
||||
|
||||
ForumSharingManager getForumSharingManager();
|
||||
|
||||
ForumManager getForumManager();
|
||||
|
||||
@@ -3,16 +3,13 @@ package org.briarproject;
|
||||
import net.jodah.concurrentunit.Waiter;
|
||||
|
||||
import org.briarproject.api.Bytes;
|
||||
import org.briarproject.api.clients.ContactGroupFactory;
|
||||
import org.briarproject.api.clients.MessageQueueManager;
|
||||
import org.briarproject.api.clients.PrivateGroupFactory;
|
||||
import org.briarproject.api.clients.SessionId;
|
||||
import org.briarproject.api.contact.Contact;
|
||||
import org.briarproject.api.contact.ContactId;
|
||||
import org.briarproject.api.contact.ContactManager;
|
||||
import org.briarproject.api.crypto.CryptoComponent;
|
||||
import org.briarproject.api.crypto.KeyPair;
|
||||
import org.briarproject.api.crypto.KeyParser;
|
||||
import org.briarproject.api.crypto.PrivateKey;
|
||||
import org.briarproject.api.crypto.SecretKey;
|
||||
import org.briarproject.api.data.BdfList;
|
||||
import org.briarproject.api.db.DatabaseComponent;
|
||||
@@ -36,9 +33,8 @@ import org.briarproject.api.identity.AuthorFactory;
|
||||
import org.briarproject.api.identity.IdentityManager;
|
||||
import org.briarproject.api.identity.LocalAuthor;
|
||||
import org.briarproject.api.lifecycle.LifecycleManager;
|
||||
import org.briarproject.api.sharing.InvitationItem;
|
||||
import org.briarproject.api.sharing.SharingInvitationItem;
|
||||
import org.briarproject.api.sharing.InvitationMessage;
|
||||
import org.briarproject.api.sync.ClientId;
|
||||
import org.briarproject.api.sync.Group;
|
||||
import org.briarproject.api.sync.SyncSession;
|
||||
import org.briarproject.api.sync.SyncSessionFactory;
|
||||
@@ -72,6 +68,7 @@ import javax.inject.Inject;
|
||||
|
||||
import static org.briarproject.TestPluginsModule.MAX_LATENCY;
|
||||
import static org.briarproject.api.forum.ForumConstants.FORUM_SALT_LENGTH;
|
||||
import static org.briarproject.api.forum.ForumSharingManager.CLIENT_ID;
|
||||
import static org.briarproject.api.sharing.SharingConstants.SHARE_MSG_TYPE_INVITATION;
|
||||
import static org.briarproject.api.sync.ValidationManager.State.DELIVERED;
|
||||
import static org.briarproject.api.sync.ValidationManager.State.INVALID;
|
||||
@@ -424,13 +421,11 @@ public class ForumSharingIntegrationTest extends BriarTestCase {
|
||||
respond = false;
|
||||
|
||||
// sync first request message and leave message
|
||||
syncToInvitee();
|
||||
deliverMessage(sync0, contactId0, sync1, contactId1, 2,
|
||||
"Sharer to Invitee");
|
||||
eventWaiter.await(TIMEOUT, 1);
|
||||
assertTrue(listener1.requestReceived);
|
||||
|
||||
// wait also for second message to arrive
|
||||
msgWaiter.await(TIMEOUT, 1);
|
||||
|
||||
// ensure that invitee has no forum invitations available
|
||||
assertEquals(0, forumSharingManager1.getInvitations().size());
|
||||
assertEquals(0, forumManager1.getForums().size());
|
||||
@@ -447,13 +442,11 @@ public class ForumSharingIntegrationTest extends BriarTestCase {
|
||||
forumManager0.removeForum(forum0);
|
||||
|
||||
// sync first request message and leave message
|
||||
syncToInvitee();
|
||||
deliverMessage(sync0, contactId0, sync1, contactId1, 2,
|
||||
"Sharer to Invitee");
|
||||
eventWaiter.await(TIMEOUT, 1);
|
||||
assertTrue(listener1.requestReceived);
|
||||
|
||||
// wait also for second message to arrive
|
||||
msgWaiter.await(TIMEOUT, 1);
|
||||
|
||||
// ensure that invitee has no forum invitations available
|
||||
assertEquals(0, forumSharingManager1.getInvitations().size());
|
||||
assertEquals(1, forumManager1.getForums().size());
|
||||
@@ -502,9 +495,8 @@ public class ForumSharingIntegrationTest extends BriarTestCase {
|
||||
DatabaseComponent db = t0.getDatabaseComponent();
|
||||
MessageQueueManager queue = t0.getMessageQueueManager();
|
||||
Contact c1 = contactManager0.getContact(contactId1);
|
||||
PrivateGroupFactory groupFactory = t0.getPrivateGroupFactory();
|
||||
Group group = groupFactory
|
||||
.createPrivateGroup(forumSharingManager0.getClientId(), c1);
|
||||
ContactGroupFactory groupFactory = t0.getContactGroupFactory();
|
||||
Group group = groupFactory.createContactGroup(CLIENT_ID, c1);
|
||||
long time = clock.currentTimeMillis();
|
||||
BdfList bodyList = BdfList.of(SHARE_MSG_TYPE_INVITATION,
|
||||
sessionId.getBytes(),
|
||||
@@ -517,7 +509,7 @@ public class ForumSharingIntegrationTest extends BriarTestCase {
|
||||
Transaction txn = db.startTransaction(false);
|
||||
try {
|
||||
queue.sendMessage(txn, group, time, body, new Metadata());
|
||||
txn.setComplete();
|
||||
db.commitTransaction(txn);
|
||||
} finally {
|
||||
db.endTransaction(txn);
|
||||
}
|
||||
@@ -588,7 +580,7 @@ public class ForumSharingIntegrationTest extends BriarTestCase {
|
||||
DatabaseComponent db1 = t1.getDatabaseComponent();
|
||||
Transaction txn = db1.startTransaction(false);
|
||||
db1.addGroup(txn, forum0.getGroup());
|
||||
txn.setComplete();
|
||||
db1.commitTransaction(txn);
|
||||
db1.endTransaction(txn);
|
||||
|
||||
// send invitation
|
||||
@@ -698,9 +690,8 @@ public class ForumSharingIntegrationTest extends BriarTestCase {
|
||||
DatabaseComponent db = t0.getDatabaseComponent();
|
||||
MessageQueueManager queue = t0.getMessageQueueManager();
|
||||
Contact c1 = contactManager0.getContact(contactId1);
|
||||
PrivateGroupFactory groupFactory = t0.getPrivateGroupFactory();
|
||||
Group group = groupFactory
|
||||
.createPrivateGroup(forumSharingManager0.getClientId(), c1);
|
||||
ContactGroupFactory groupFactory = t0.getContactGroupFactory();
|
||||
Group group = groupFactory.createContactGroup(CLIENT_ID, c1);
|
||||
long time = clock.currentTimeMillis();
|
||||
|
||||
// construct a new message re-using the old SessionId
|
||||
@@ -715,7 +706,7 @@ public class ForumSharingIntegrationTest extends BriarTestCase {
|
||||
Transaction txn = db.startTransaction(false);
|
||||
try {
|
||||
queue.sendMessage(txn, group, time, body, new Metadata());
|
||||
txn.setComplete();
|
||||
db.commitTransaction(txn);
|
||||
} finally {
|
||||
db.endTransaction(txn);
|
||||
}
|
||||
@@ -736,7 +727,7 @@ public class ForumSharingIntegrationTest extends BriarTestCase {
|
||||
startLifecycles();
|
||||
try {
|
||||
// initialize
|
||||
addDefaultIdentities();
|
||||
getDefaultIdentities();
|
||||
addDefaultContacts();
|
||||
addForumForSharer();
|
||||
|
||||
@@ -744,7 +735,7 @@ public class ForumSharingIntegrationTest extends BriarTestCase {
|
||||
DatabaseComponent db2 = t2.getDatabaseComponent();
|
||||
Transaction txn = db2.startTransaction(false);
|
||||
db2.addGroup(txn, forum0.getGroup());
|
||||
txn.setComplete();
|
||||
db2.commitTransaction(txn);
|
||||
db2.endTransaction(txn);
|
||||
|
||||
// add listeners
|
||||
@@ -765,11 +756,11 @@ public class ForumSharingIntegrationTest extends BriarTestCase {
|
||||
forumSharingManager2
|
||||
.sendInvitation(forum0.getId(), contactId1, null);
|
||||
// sync second request message
|
||||
deliverMessage(sync2, contactId2, sync1, contactId1,
|
||||
deliverMessage(sync2, contactId2, sync1, contactId1, 1,
|
||||
"Sharer2 to Invitee");
|
||||
|
||||
// make sure we now have two invitations to the same forum available
|
||||
Collection<InvitationItem> forums =
|
||||
Collection<SharingInvitationItem> forums =
|
||||
forumSharingManager1.getInvitations();
|
||||
assertEquals(1, forums.size());
|
||||
assertEquals(2, forums.iterator().next().getNewSharers().size());
|
||||
@@ -786,7 +777,7 @@ public class ForumSharingIntegrationTest extends BriarTestCase {
|
||||
Contact c2 = contactManager1.getContact(contactId2);
|
||||
forumSharingManager1.respondToInvitation(forum0, c2, true);
|
||||
// sync response
|
||||
deliverMessage(sync1, contactId21, sync2, contactId2,
|
||||
deliverMessage(sync1, contactId21, sync2, contactId2, 1,
|
||||
"Invitee to Sharer2");
|
||||
eventWaiter.await(TIMEOUT, 1);
|
||||
assertTrue(listener2.responseReceived);
|
||||
@@ -825,12 +816,10 @@ public class ForumSharingIntegrationTest extends BriarTestCase {
|
||||
|
||||
// sharer posts into the forum
|
||||
long time = clock.currentTimeMillis();
|
||||
byte[] body = TestUtils.getRandomBytes(42);
|
||||
KeyParser keyParser = cryptoComponent.getSignatureKeyParser();
|
||||
PrivateKey key = keyParser.parsePrivateKey(author0.getPrivateKey());
|
||||
String body = TestUtils.getRandomString(42);
|
||||
ForumPost p = forumPostFactory
|
||||
.createPseudonymousPost(forum0.getId(), time, null, author0,
|
||||
"text/plain", body, key);
|
||||
.createPost(forum0.getId(), time, null, author0,
|
||||
body);
|
||||
forumManager0.addLocalPost(p);
|
||||
|
||||
// sync forum post
|
||||
@@ -846,11 +835,10 @@ public class ForumSharingIntegrationTest extends BriarTestCase {
|
||||
|
||||
// now invitee creates a post
|
||||
time = clock.currentTimeMillis();
|
||||
body = TestUtils.getRandomBytes(42);
|
||||
key = keyParser.parsePrivateKey(author1.getPrivateKey());
|
||||
body = TestUtils.getRandomString(42);
|
||||
p = forumPostFactory
|
||||
.createPseudonymousPost(forum0.getId(), time, null, author1,
|
||||
"text/plain", body, key);
|
||||
.createPost(forum0.getId(), time, null, author1,
|
||||
body);
|
||||
forumManager1.addLocalPost(p);
|
||||
|
||||
// sync forum post
|
||||
@@ -891,11 +879,10 @@ public class ForumSharingIntegrationTest extends BriarTestCase {
|
||||
|
||||
// now invitee creates a post
|
||||
time = clock.currentTimeMillis();
|
||||
body = TestUtils.getRandomBytes(42);
|
||||
key = keyParser.parsePrivateKey(author1.getPrivateKey());
|
||||
body = TestUtils.getRandomString(42);
|
||||
p = forumPostFactory
|
||||
.createPseudonymousPost(forum0.getId(), time, null, author1,
|
||||
"text/plain", body, key);
|
||||
.createPost(forum0.getId(), time, null, author1,
|
||||
body);
|
||||
forumManager1.addLocalPost(p);
|
||||
|
||||
// sync forum post
|
||||
@@ -925,23 +912,16 @@ public class ForumSharingIntegrationTest extends BriarTestCase {
|
||||
|
||||
private class SharerListener implements EventListener {
|
||||
|
||||
volatile boolean requestReceived = false;
|
||||
volatile boolean responseReceived = false;
|
||||
private volatile boolean requestReceived = false;
|
||||
private volatile boolean responseReceived = false;
|
||||
|
||||
@Override
|
||||
public void eventOccurred(Event e) {
|
||||
if (e instanceof MessageStateChangedEvent) {
|
||||
MessageStateChangedEvent event = (MessageStateChangedEvent) e;
|
||||
State s = event.getState();
|
||||
ClientId c = event.getClientId();
|
||||
if ((s == DELIVERED || s == INVALID) &&
|
||||
c.equals(forumSharingManager0.getClientId()) &&
|
||||
!event.isLocal()) {
|
||||
LOG.info("TEST: Sharer received message in group " +
|
||||
event.getMessage().getGroupId().hashCode());
|
||||
msgWaiter.resume();
|
||||
} else if (s == DELIVERED && !event.isLocal() &&
|
||||
c.equals(forumManager0.getClientId())) {
|
||||
LOG.info("TEST: Sharer received forum post");
|
||||
if ((s == DELIVERED || s == INVALID) && !event.isLocal()) {
|
||||
LOG.info("TEST: Sharer received message");
|
||||
msgWaiter.resume();
|
||||
}
|
||||
} else if (e instanceof ForumInvitationResponseReceivedEvent) {
|
||||
@@ -957,7 +937,7 @@ public class ForumSharingIntegrationTest extends BriarTestCase {
|
||||
(ForumInvitationReceivedEvent) e;
|
||||
eventWaiter.assertEquals(contactId1, event.getContactId());
|
||||
requestReceived = true;
|
||||
Forum f = event.getForum();
|
||||
Forum f = event.getShareable();
|
||||
try {
|
||||
Contact c = contactManager0.getContact(contactId1);
|
||||
forumSharingManager0.respondToInvitation(f, c, true);
|
||||
@@ -972,34 +952,27 @@ public class ForumSharingIntegrationTest extends BriarTestCase {
|
||||
|
||||
private class InviteeListener implements EventListener {
|
||||
|
||||
volatile boolean requestReceived = false;
|
||||
volatile boolean responseReceived = false;
|
||||
private volatile boolean requestReceived = false;
|
||||
private volatile boolean responseReceived = false;
|
||||
|
||||
private final boolean accept, answer;
|
||||
|
||||
InviteeListener(boolean accept, boolean answer) {
|
||||
private InviteeListener(boolean accept, boolean answer) {
|
||||
this.accept = accept;
|
||||
this.answer = answer;
|
||||
}
|
||||
|
||||
InviteeListener(boolean accept) {
|
||||
private InviteeListener(boolean accept) {
|
||||
this(accept, true);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void eventOccurred(Event e) {
|
||||
if (e instanceof MessageStateChangedEvent) {
|
||||
MessageStateChangedEvent event = (MessageStateChangedEvent) e;
|
||||
State s = event.getState();
|
||||
ClientId c = event.getClientId();
|
||||
if ((s == DELIVERED || s == INVALID) &&
|
||||
c.equals(forumSharingManager0.getClientId()) &&
|
||||
!event.isLocal()) {
|
||||
LOG.info("TEST: Invitee received message in group " +
|
||||
event.getMessage().getGroupId().hashCode());
|
||||
msgWaiter.resume();
|
||||
} else if (s == DELIVERED && !event.isLocal() &&
|
||||
c.equals(forumManager0.getClientId())) {
|
||||
LOG.info("TEST: Invitee received forum post");
|
||||
if ((s == DELIVERED || s == INVALID) && !event.isLocal()) {
|
||||
LOG.info("TEST: Invitee received message");
|
||||
msgWaiter.resume();
|
||||
}
|
||||
} else if (e instanceof ForumInvitationReceivedEvent) {
|
||||
@@ -1007,11 +980,11 @@ public class ForumSharingIntegrationTest extends BriarTestCase {
|
||||
(ForumInvitationReceivedEvent) e;
|
||||
requestReceived = true;
|
||||
if (!answer) return;
|
||||
Forum f = event.getForum();
|
||||
Forum f = event.getShareable();
|
||||
try {
|
||||
eventWaiter.assertEquals(1,
|
||||
forumSharingManager1.getInvitations().size());
|
||||
InvitationItem invitation =
|
||||
SharingInvitationItem invitation =
|
||||
forumSharingManager1.getInvitations().iterator()
|
||||
.next();
|
||||
eventWaiter.assertEquals(f, invitation.getShareable());
|
||||
@@ -1042,9 +1015,9 @@ public class ForumSharingIntegrationTest extends BriarTestCase {
|
||||
lifecycleManager0 = t0.getLifecycleManager();
|
||||
lifecycleManager1 = t1.getLifecycleManager();
|
||||
lifecycleManager2 = t2.getLifecycleManager();
|
||||
lifecycleManager0.startServices();
|
||||
lifecycleManager1.startServices();
|
||||
lifecycleManager2.startServices();
|
||||
lifecycleManager0.startServices(SHARER);
|
||||
lifecycleManager1.startServices(INVITEE);
|
||||
lifecycleManager2.startServices(SHARER2);
|
||||
lifecycleManager0.waitForStartup();
|
||||
lifecycleManager1.waitForStartup();
|
||||
lifecycleManager2.waitForStartup();
|
||||
@@ -1061,30 +1034,16 @@ public class ForumSharingIntegrationTest extends BriarTestCase {
|
||||
}
|
||||
|
||||
private void defaultInit(boolean accept) throws DbException {
|
||||
addDefaultIdentities();
|
||||
getDefaultIdentities();
|
||||
addDefaultContacts();
|
||||
addForumForSharer();
|
||||
listenToEvents(accept);
|
||||
}
|
||||
|
||||
private void addDefaultIdentities() throws DbException {
|
||||
KeyPair keyPair = cryptoComponent.generateSignatureKeyPair();
|
||||
author0 = authorFactory.createLocalAuthor(SHARER,
|
||||
keyPair.getPublic().getEncoded(),
|
||||
keyPair.getPrivate().getEncoded());
|
||||
identityManager0.addLocalAuthor(author0);
|
||||
|
||||
keyPair = cryptoComponent.generateSignatureKeyPair();
|
||||
author1 = authorFactory.createLocalAuthor(INVITEE,
|
||||
keyPair.getPublic().getEncoded(),
|
||||
keyPair.getPrivate().getEncoded());
|
||||
identityManager1.addLocalAuthor(author1);
|
||||
|
||||
keyPair = cryptoComponent.generateSignatureKeyPair();
|
||||
author2 = authorFactory.createLocalAuthor(SHARER2,
|
||||
keyPair.getPublic().getEncoded(),
|
||||
keyPair.getPrivate().getEncoded());
|
||||
identityManager2.addLocalAuthor(author2);
|
||||
private void getDefaultIdentities() throws DbException {
|
||||
author0 = identityManager0.getLocalAuthor();
|
||||
author1 = identityManager1.getLocalAuthor();
|
||||
author2 = identityManager2.getLocalAuthor();
|
||||
}
|
||||
|
||||
private void addDefaultContacts() throws DbException {
|
||||
@@ -1124,17 +1083,17 @@ public class ForumSharingIntegrationTest extends BriarTestCase {
|
||||
}
|
||||
|
||||
private void syncToInvitee() throws IOException, TimeoutException {
|
||||
deliverMessage(sync0, contactId0, sync1, contactId1,
|
||||
deliverMessage(sync0, contactId0, sync1, contactId1, 1,
|
||||
"Sharer to Invitee");
|
||||
}
|
||||
|
||||
private void syncToSharer() throws IOException, TimeoutException {
|
||||
deliverMessage(sync1, contactId1, sync0, contactId0,
|
||||
deliverMessage(sync1, contactId1, sync0, contactId0, 1,
|
||||
"Invitee to Sharer");
|
||||
}
|
||||
|
||||
private void deliverMessage(SyncSessionFactory fromSync, ContactId fromId,
|
||||
SyncSessionFactory toSync, ContactId toId, String debug)
|
||||
SyncSessionFactory toSync, ContactId toId, int num, String debug)
|
||||
throws IOException, TimeoutException {
|
||||
|
||||
if (debug != null) LOG.info("TEST: Sending message from " + debug);
|
||||
@@ -1155,7 +1114,7 @@ public class ForumSharingIntegrationTest extends BriarTestCase {
|
||||
in.close();
|
||||
|
||||
// wait for message to actually arrive
|
||||
msgWaiter.await(TIMEOUT, 1);
|
||||
msgWaiter.await(TIMEOUT, num);
|
||||
}
|
||||
|
||||
private void injectEagerSingletons(
|
||||
|
||||
@@ -2,7 +2,7 @@ package org.briarproject;
|
||||
|
||||
import org.briarproject.api.clients.ClientHelper;
|
||||
import org.briarproject.api.clients.MessageQueueManager;
|
||||
import org.briarproject.api.clients.PrivateGroupFactory;
|
||||
import org.briarproject.api.clients.ContactGroupFactory;
|
||||
import org.briarproject.api.contact.ContactManager;
|
||||
import org.briarproject.api.db.DatabaseComponent;
|
||||
import org.briarproject.api.event.EventBus;
|
||||
@@ -21,6 +21,7 @@ import org.briarproject.event.EventModule;
|
||||
import org.briarproject.forum.ForumModule;
|
||||
import org.briarproject.identity.IdentityModule;
|
||||
import org.briarproject.lifecycle.LifecycleModule;
|
||||
import org.briarproject.messaging.MessagingModule;
|
||||
import org.briarproject.properties.PropertiesModule;
|
||||
import org.briarproject.sharing.SharingModule;
|
||||
import org.briarproject.sync.SyncModule;
|
||||
@@ -50,7 +51,8 @@ import dagger.Component;
|
||||
SharingModule.class,
|
||||
SyncModule.class,
|
||||
SystemModule.class,
|
||||
TransportModule.class
|
||||
TransportModule.class,
|
||||
MessagingModule.class
|
||||
})
|
||||
interface ForumSharingIntegrationTestComponent {
|
||||
|
||||
@@ -90,7 +92,7 @@ interface ForumSharingIntegrationTestComponent {
|
||||
|
||||
DatabaseComponent getDatabaseComponent();
|
||||
|
||||
PrivateGroupFactory getPrivateGroupFactory();
|
||||
ContactGroupFactory getContactGroupFactory();
|
||||
|
||||
ClientHelper getClientHelper();
|
||||
|
||||
|
||||
@@ -6,14 +6,14 @@ import org.briarproject.api.crypto.PrivateKey;
|
||||
import org.briarproject.api.forum.ForumConstants;
|
||||
import org.briarproject.api.forum.ForumPost;
|
||||
import org.briarproject.api.forum.ForumPostFactory;
|
||||
import org.briarproject.api.identity.Author;
|
||||
import org.briarproject.api.identity.AuthorFactory;
|
||||
import org.briarproject.api.messaging.MessagingConstants;
|
||||
import org.briarproject.api.identity.LocalAuthor;
|
||||
import org.briarproject.api.messaging.PrivateMessage;
|
||||
import org.briarproject.api.messaging.PrivateMessageFactory;
|
||||
import org.briarproject.api.sync.GroupId;
|
||||
import org.briarproject.api.sync.MessageId;
|
||||
import org.briarproject.system.SystemModule;
|
||||
import org.briarproject.util.StringUtils;
|
||||
import org.junit.Test;
|
||||
|
||||
import javax.inject.Inject;
|
||||
@@ -48,17 +48,14 @@ public class MessageSizeIntegrationTest extends BriarTestCase {
|
||||
// Create a maximum-length private message
|
||||
GroupId groupId = new GroupId(TestUtils.getRandomId());
|
||||
long timestamp = Long.MAX_VALUE;
|
||||
MessageId parent = new MessageId(TestUtils.getRandomId());
|
||||
String contentType = TestUtils.getRandomString(
|
||||
MessagingConstants.MAX_CONTENT_TYPE_LENGTH);
|
||||
byte[] body = new byte[MAX_PRIVATE_MESSAGE_BODY_LENGTH];
|
||||
String body =
|
||||
StringUtils.fromUtf8(new byte[MAX_PRIVATE_MESSAGE_BODY_LENGTH]);
|
||||
PrivateMessage message = privateMessageFactory.createPrivateMessage(
|
||||
groupId, timestamp, parent, contentType, body);
|
||||
groupId, timestamp, body);
|
||||
// Check the size of the serialised message
|
||||
int length = message.getMessage().getRaw().length;
|
||||
assertTrue(length > UniqueId.LENGTH + 8 + UniqueId.LENGTH
|
||||
+ MessagingConstants.MAX_CONTENT_TYPE_LENGTH
|
||||
+ MAX_PRIVATE_MESSAGE_BODY_LENGTH);
|
||||
assertTrue(
|
||||
length > UniqueId.LENGTH + 8 + MAX_PRIVATE_MESSAGE_BODY_LENGTH);
|
||||
assertTrue(length <= MAX_PACKET_PAYLOAD_LENGTH);
|
||||
}
|
||||
|
||||
@@ -68,17 +65,17 @@ public class MessageSizeIntegrationTest extends BriarTestCase {
|
||||
String authorName = TestUtils.getRandomString(
|
||||
MAX_AUTHOR_NAME_LENGTH);
|
||||
byte[] authorPublic = new byte[MAX_PUBLIC_KEY_LENGTH];
|
||||
Author author = authorFactory.createAuthor(authorName, authorPublic);
|
||||
PrivateKey privateKey = crypto.generateSignatureKeyPair().getPrivate();
|
||||
LocalAuthor author = authorFactory
|
||||
.createLocalAuthor(authorName, authorPublic,
|
||||
privateKey.getEncoded());
|
||||
// Create a maximum-length forum post
|
||||
GroupId groupId = new GroupId(TestUtils.getRandomId());
|
||||
long timestamp = Long.MAX_VALUE;
|
||||
MessageId parent = new MessageId(TestUtils.getRandomId());
|
||||
String contentType = TestUtils.getRandomString(
|
||||
ForumConstants.MAX_CONTENT_TYPE_LENGTH);
|
||||
byte[] body = new byte[MAX_FORUM_POST_BODY_LENGTH];
|
||||
PrivateKey privateKey = crypto.generateSignatureKeyPair().getPrivate();
|
||||
ForumPost post = forumPostFactory.createPseudonymousPost(groupId,
|
||||
timestamp, parent, author, contentType, body, privateKey);
|
||||
String body = TestUtils.getRandomString(MAX_FORUM_POST_BODY_LENGTH);
|
||||
ForumPost post = forumPostFactory.createPost(groupId,
|
||||
timestamp, parent, author, body);
|
||||
// Check the size of the serialised message
|
||||
int length = post.getMessage().getRaw().length;
|
||||
assertTrue(length > UniqueId.LENGTH + 8 + UniqueId.LENGTH
|
||||
|
||||
@@ -0,0 +1,838 @@
|
||||
package org.briarproject;
|
||||
|
||||
import net.jodah.concurrentunit.Waiter;
|
||||
|
||||
import org.briarproject.api.clients.ClientHelper;
|
||||
import org.briarproject.api.clients.ContactGroupFactory;
|
||||
import org.briarproject.api.clients.MessageTracker.GroupCount;
|
||||
import org.briarproject.api.contact.Contact;
|
||||
import org.briarproject.api.contact.ContactId;
|
||||
import org.briarproject.api.contact.ContactManager;
|
||||
import org.briarproject.api.crypto.CryptoComponent;
|
||||
import org.briarproject.api.crypto.KeyPair;
|
||||
import org.briarproject.api.crypto.SecretKey;
|
||||
import org.briarproject.api.data.BdfList;
|
||||
import org.briarproject.api.db.DatabaseComponent;
|
||||
import org.briarproject.api.db.DbException;
|
||||
import org.briarproject.api.db.Transaction;
|
||||
import org.briarproject.api.event.Event;
|
||||
import org.briarproject.api.event.EventListener;
|
||||
import org.briarproject.api.event.MessageStateChangedEvent;
|
||||
import org.briarproject.api.identity.AuthorFactory;
|
||||
import org.briarproject.api.identity.IdentityManager;
|
||||
import org.briarproject.api.identity.LocalAuthor;
|
||||
import org.briarproject.api.lifecycle.LifecycleManager;
|
||||
import org.briarproject.api.privategroup.GroupMember;
|
||||
import org.briarproject.api.privategroup.GroupMessage;
|
||||
import org.briarproject.api.privategroup.GroupMessageFactory;
|
||||
import org.briarproject.api.privategroup.GroupMessageHeader;
|
||||
import org.briarproject.api.privategroup.JoinMessageHeader;
|
||||
import org.briarproject.api.privategroup.PrivateGroup;
|
||||
import org.briarproject.api.privategroup.PrivateGroupFactory;
|
||||
import org.briarproject.api.privategroup.PrivateGroupManager;
|
||||
import org.briarproject.api.privategroup.invitation.GroupInvitationFactory;
|
||||
import org.briarproject.api.sync.GroupId;
|
||||
import org.briarproject.api.sync.MessageId;
|
||||
import org.briarproject.api.sync.SyncSession;
|
||||
import org.briarproject.api.sync.SyncSessionFactory;
|
||||
import org.briarproject.api.system.Clock;
|
||||
import org.briarproject.contact.ContactModule;
|
||||
import org.briarproject.crypto.CryptoModule;
|
||||
import org.briarproject.lifecycle.LifecycleModule;
|
||||
import org.briarproject.privategroup.PrivateGroupModule;
|
||||
import org.briarproject.properties.PropertiesModule;
|
||||
import org.briarproject.sync.SyncModule;
|
||||
import org.briarproject.transport.TransportModule;
|
||||
import org.junit.After;
|
||||
import org.junit.Before;
|
||||
import org.junit.Rule;
|
||||
import org.junit.Test;
|
||||
import org.junit.rules.ExpectedException;
|
||||
|
||||
import java.io.ByteArrayInputStream;
|
||||
import java.io.ByteArrayOutputStream;
|
||||
import java.io.File;
|
||||
import java.io.IOException;
|
||||
import java.util.Collection;
|
||||
import java.util.concurrent.TimeoutException;
|
||||
import java.util.logging.Logger;
|
||||
|
||||
import javax.inject.Inject;
|
||||
|
||||
import static org.briarproject.TestPluginsModule.MAX_LATENCY;
|
||||
import static org.briarproject.TestUtils.getRandomBytes;
|
||||
import static org.briarproject.api.identity.Author.Status.VERIFIED;
|
||||
import static org.briarproject.api.privategroup.Visibility.INVISIBLE;
|
||||
import static org.briarproject.api.privategroup.Visibility.REVEALED_BY_CONTACT;
|
||||
import static org.briarproject.api.privategroup.Visibility.REVEALED_BY_US;
|
||||
import static org.briarproject.api.privategroup.Visibility.VISIBLE;
|
||||
import static org.briarproject.api.privategroup.invitation.GroupInvitationFactory.SIGNING_LABEL_INVITE;
|
||||
import static org.briarproject.api.sync.Group.Visibility.SHARED;
|
||||
import static org.briarproject.api.sync.ValidationManager.State.DELIVERED;
|
||||
import static org.briarproject.api.sync.ValidationManager.State.INVALID;
|
||||
import static org.briarproject.api.sync.ValidationManager.State.PENDING;
|
||||
import static org.junit.Assert.assertEquals;
|
||||
import static org.junit.Assert.assertFalse;
|
||||
import static org.junit.Assert.assertTrue;
|
||||
|
||||
public class PrivateGroupManagerTest extends BriarIntegrationTest {
|
||||
|
||||
private LifecycleManager lifecycleManager0, lifecycleManager1,
|
||||
lifecycleManager2;
|
||||
private SyncSessionFactory sync0, sync1, sync2;
|
||||
private PrivateGroupManager groupManager0, groupManager1, groupManager2;
|
||||
private ContactManager contactManager0, contactManager1, contactManager2;
|
||||
private ContactId contactId01, contactId02, contactId1, contactId2;
|
||||
private IdentityManager identityManager0, identityManager1,
|
||||
identityManager2;
|
||||
private LocalAuthor author0, author1, author2;
|
||||
private DatabaseComponent db0, db1, db2;
|
||||
private PrivateGroup privateGroup0;
|
||||
private GroupId groupId0;
|
||||
|
||||
@Inject
|
||||
Clock clock;
|
||||
@Inject
|
||||
AuthorFactory authorFactory;
|
||||
@Inject
|
||||
ClientHelper clientHelper;
|
||||
@Inject
|
||||
CryptoComponent crypto;
|
||||
@Inject
|
||||
ContactGroupFactory contactGroupFactory;
|
||||
@Inject
|
||||
PrivateGroupFactory privateGroupFactory;
|
||||
@Inject
|
||||
GroupMessageFactory groupMessageFactory;
|
||||
@Inject
|
||||
GroupInvitationFactory groupInvitationFactory;
|
||||
|
||||
// objects accessed from background threads need to be volatile
|
||||
private volatile Waiter validationWaiter;
|
||||
private volatile Waiter deliveryWaiter;
|
||||
|
||||
private final File testDir = TestUtils.getTestDirectory();
|
||||
private final SecretKey master = TestUtils.getSecretKey();
|
||||
private final int TIMEOUT = 15000;
|
||||
private final String AUTHOR0 = "Author 0";
|
||||
private final String AUTHOR1 = "Author 1";
|
||||
private final String AUTHOR2 = "Author 2";
|
||||
|
||||
private static final Logger LOG =
|
||||
Logger.getLogger(PrivateGroupManagerTest.class.getName());
|
||||
|
||||
private PrivateGroupManagerTestComponent t0, t1, t2;
|
||||
|
||||
@Rule
|
||||
public ExpectedException thrown = ExpectedException.none();
|
||||
|
||||
@Before
|
||||
public void setUp() throws Exception {
|
||||
PrivateGroupManagerTestComponent component =
|
||||
DaggerPrivateGroupManagerTestComponent.builder().build();
|
||||
component.inject(this);
|
||||
|
||||
assertTrue(testDir.mkdirs());
|
||||
File t0Dir = new File(testDir, AUTHOR0);
|
||||
t0 = DaggerPrivateGroupManagerTestComponent.builder()
|
||||
.testDatabaseModule(new TestDatabaseModule(t0Dir)).build();
|
||||
injectEagerSingletons(t0);
|
||||
File t1Dir = new File(testDir, AUTHOR1);
|
||||
t1 = DaggerPrivateGroupManagerTestComponent.builder()
|
||||
.testDatabaseModule(new TestDatabaseModule(t1Dir)).build();
|
||||
injectEagerSingletons(t1);
|
||||
File t2Dir = new File(testDir, AUTHOR2);
|
||||
t2 = DaggerPrivateGroupManagerTestComponent.builder()
|
||||
.testDatabaseModule(new TestDatabaseModule(t2Dir)).build();
|
||||
injectEagerSingletons(t2);
|
||||
|
||||
identityManager0 = t0.getIdentityManager();
|
||||
identityManager1 = t1.getIdentityManager();
|
||||
identityManager2 = t2.getIdentityManager();
|
||||
contactManager0 = t0.getContactManager();
|
||||
contactManager1 = t1.getContactManager();
|
||||
contactManager2 = t2.getContactManager();
|
||||
db0 = t0.getDatabaseComponent();
|
||||
db1 = t1.getDatabaseComponent();
|
||||
db2 = t2.getDatabaseComponent();
|
||||
groupManager0 = t0.getPrivateGroupManager();
|
||||
groupManager1 = t1.getPrivateGroupManager();
|
||||
groupManager2 = t2.getPrivateGroupManager();
|
||||
sync0 = t0.getSyncSessionFactory();
|
||||
sync1 = t1.getSyncSessionFactory();
|
||||
sync2 = t2.getSyncSessionFactory();
|
||||
|
||||
// initialize waiters fresh for each test
|
||||
validationWaiter = new Waiter();
|
||||
deliveryWaiter = new Waiter();
|
||||
|
||||
startLifecycles();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testSendingMessage() throws Exception {
|
||||
defaultInit();
|
||||
|
||||
// create and add test message
|
||||
long time = clock.currentTimeMillis();
|
||||
String body = "This is a test message!";
|
||||
MessageId previousMsgId =
|
||||
groupManager0.getPreviousMsgId(groupId0);
|
||||
GroupMessage msg = groupMessageFactory
|
||||
.createGroupMessage(groupId0, time, null, author0, body,
|
||||
previousMsgId);
|
||||
groupManager0.addLocalMessage(msg);
|
||||
assertEquals(msg.getMessage().getId(),
|
||||
groupManager0.getPreviousMsgId(groupId0));
|
||||
|
||||
// sync test message
|
||||
sync0To1();
|
||||
deliveryWaiter.await(TIMEOUT, 1);
|
||||
|
||||
// assert that message arrived as expected
|
||||
Collection<GroupMessageHeader> headers =
|
||||
groupManager1.getHeaders(groupId0);
|
||||
assertEquals(3, headers.size());
|
||||
GroupMessageHeader header = null;
|
||||
for (GroupMessageHeader h : headers) {
|
||||
if (!(h instanceof JoinMessageHeader)) {
|
||||
header = h;
|
||||
}
|
||||
}
|
||||
assertTrue(header != null);
|
||||
assertFalse(header.isRead());
|
||||
assertEquals(author0, header.getAuthor());
|
||||
assertEquals(time, header.getTimestamp());
|
||||
assertEquals(VERIFIED, header.getAuthorStatus());
|
||||
assertEquals(body, groupManager1.getMessageBody(header.getId()));
|
||||
GroupCount count = groupManager1.getGroupCount(groupId0);
|
||||
assertEquals(2, count.getUnreadCount());
|
||||
assertEquals(time, count.getLatestMsgTime());
|
||||
assertEquals(3, count.getMsgCount());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testMessageWithWrongPreviousMsgId() throws Exception {
|
||||
defaultInit();
|
||||
|
||||
// create and add test message with no previousMsgId
|
||||
@SuppressWarnings("ConstantConditions")
|
||||
GroupMessage msg = groupMessageFactory
|
||||
.createGroupMessage(groupId0, clock.currentTimeMillis(), null,
|
||||
author0, "test", null);
|
||||
groupManager0.addLocalMessage(msg);
|
||||
|
||||
// sync test message
|
||||
sync0To1();
|
||||
validationWaiter.await(TIMEOUT, 1);
|
||||
|
||||
// assert that message did not arrive
|
||||
assertEquals(2, groupManager1.getHeaders(groupId0).size());
|
||||
|
||||
// create and add test message with random previousMsgId
|
||||
MessageId previousMsgId = new MessageId(TestUtils.getRandomId());
|
||||
msg = groupMessageFactory
|
||||
.createGroupMessage(groupId0, clock.currentTimeMillis(), null,
|
||||
author0, "test", previousMsgId);
|
||||
groupManager0.addLocalMessage(msg);
|
||||
|
||||
// sync test message
|
||||
sync0To1();
|
||||
validationWaiter.await(TIMEOUT, 1);
|
||||
|
||||
// assert that message did not arrive
|
||||
assertEquals(2, groupManager1.getHeaders(groupId0).size());
|
||||
|
||||
// create and add test message with wrong previousMsgId
|
||||
previousMsgId = groupManager1.getPreviousMsgId(groupId0);
|
||||
msg = groupMessageFactory
|
||||
.createGroupMessage(groupId0, clock.currentTimeMillis(), null,
|
||||
author0, "test", previousMsgId);
|
||||
groupManager0.addLocalMessage(msg);
|
||||
|
||||
// sync test message
|
||||
sync0To1();
|
||||
validationWaiter.await(TIMEOUT, 1);
|
||||
|
||||
// assert that message did not arrive
|
||||
assertEquals(2, groupManager1.getHeaders(groupId0).size());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testMessageWithWrongParentMsgId() throws Exception {
|
||||
defaultInit();
|
||||
|
||||
// create and add test message with random parentMsgId
|
||||
MessageId parentMsgId = new MessageId(TestUtils.getRandomId());
|
||||
MessageId previousMsgId = groupManager0.getPreviousMsgId(groupId0);
|
||||
GroupMessage msg = groupMessageFactory
|
||||
.createGroupMessage(groupId0, clock.currentTimeMillis(),
|
||||
parentMsgId, author0, "test", previousMsgId);
|
||||
groupManager0.addLocalMessage(msg);
|
||||
|
||||
// sync test message
|
||||
sync0To1();
|
||||
validationWaiter.await(TIMEOUT, 1);
|
||||
|
||||
// assert that message did not arrive
|
||||
assertEquals(2, groupManager1.getHeaders(groupId0).size());
|
||||
|
||||
// create and add test message with wrong parentMsgId
|
||||
parentMsgId = previousMsgId;
|
||||
msg = groupMessageFactory
|
||||
.createGroupMessage(groupId0, clock.currentTimeMillis(),
|
||||
parentMsgId, author0, "test", previousMsgId);
|
||||
groupManager0.addLocalMessage(msg);
|
||||
|
||||
// sync test message
|
||||
sync0To1();
|
||||
validationWaiter.await(TIMEOUT, 1);
|
||||
|
||||
// assert that message did not arrive
|
||||
assertEquals(2, groupManager1.getHeaders(groupId0).size());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testMessageWithWrongTimestamp() throws Exception {
|
||||
defaultInit();
|
||||
|
||||
// create and add test message with wrong timestamp
|
||||
MessageId previousMsgId = groupManager0.getPreviousMsgId(groupId0);
|
||||
GroupMessage msg = groupMessageFactory
|
||||
.createGroupMessage(groupId0, 42, null, author0, "test",
|
||||
previousMsgId);
|
||||
groupManager0.addLocalMessage(msg);
|
||||
|
||||
// sync test message
|
||||
sync0To1();
|
||||
validationWaiter.await(TIMEOUT, 1);
|
||||
|
||||
// assert that message did not arrive
|
||||
assertEquals(2, groupManager1.getHeaders(groupId0).size());
|
||||
|
||||
// create and add test message with good timestamp
|
||||
long time = clock.currentTimeMillis();
|
||||
msg = groupMessageFactory
|
||||
.createGroupMessage(groupId0, time, null, author0, "test",
|
||||
previousMsgId);
|
||||
groupManager0.addLocalMessage(msg);
|
||||
|
||||
// sync test message
|
||||
sync0To1();
|
||||
deliveryWaiter.await(TIMEOUT, 1);
|
||||
assertEquals(3, groupManager1.getHeaders(groupId0).size());
|
||||
|
||||
// create and add test message with same timestamp as previous message
|
||||
previousMsgId = msg.getMessage().getId();
|
||||
msg = groupMessageFactory
|
||||
.createGroupMessage(groupId0, time, previousMsgId, author0,
|
||||
"test2", previousMsgId);
|
||||
groupManager0.addLocalMessage(msg);
|
||||
|
||||
// sync test message
|
||||
sync0To1();
|
||||
validationWaiter.await(TIMEOUT, 1);
|
||||
|
||||
// assert that message did not arrive
|
||||
assertEquals(3, groupManager1.getHeaders(groupId0).size());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testWrongJoinMessages1() throws Exception {
|
||||
addDefaultIdentities();
|
||||
addDefaultContacts();
|
||||
listenToEvents();
|
||||
|
||||
// author0 joins privateGroup0 with wrong join message
|
||||
long joinTime = clock.currentTimeMillis();
|
||||
GroupMessage joinMsg0 = groupMessageFactory
|
||||
.createJoinMessage(privateGroup0.getId(), joinTime, author0,
|
||||
joinTime, getRandomBytes(12));
|
||||
groupManager0.addPrivateGroup(privateGroup0, joinMsg0, true);
|
||||
assertEquals(joinMsg0.getMessage().getId(),
|
||||
groupManager0.getPreviousMsgId(groupId0));
|
||||
|
||||
// share the group with 1
|
||||
Transaction txn0 = db0.startTransaction(false);
|
||||
db0.setGroupVisibility(txn0, contactId1, privateGroup0.getId(), SHARED);
|
||||
db0.commitTransaction(txn0);
|
||||
db0.endTransaction(txn0);
|
||||
|
||||
// author1 joins privateGroup0 with wrong timestamp
|
||||
joinTime = clock.currentTimeMillis();
|
||||
long inviteTime = joinTime;
|
||||
Contact c1 = contactManager0.getContact(contactId1);
|
||||
byte[] creatorSignature = groupInvitationFactory
|
||||
.signInvitation(c1, privateGroup0.getId(), inviteTime,
|
||||
author0.getPrivateKey());
|
||||
GroupMessage joinMsg1 = groupMessageFactory
|
||||
.createJoinMessage(privateGroup0.getId(), joinTime, author1,
|
||||
inviteTime, creatorSignature);
|
||||
groupManager1.addPrivateGroup(privateGroup0, joinMsg1, false);
|
||||
assertEquals(joinMsg1.getMessage().getId(),
|
||||
groupManager1.getPreviousMsgId(groupId0));
|
||||
|
||||
// share the group with 0
|
||||
Transaction txn1 = db1.startTransaction(false);
|
||||
db1.setGroupVisibility(txn1, contactId01, privateGroup0.getId(),
|
||||
SHARED);
|
||||
db1.commitTransaction(txn1);
|
||||
db1.endTransaction(txn1);
|
||||
|
||||
// sync join messages
|
||||
sync0To1();
|
||||
validationWaiter.await(TIMEOUT, 1);
|
||||
|
||||
// assert that 0 never joined the group from 1's perspective
|
||||
assertEquals(1, groupManager1.getHeaders(groupId0).size());
|
||||
|
||||
sync1To0();
|
||||
validationWaiter.await(TIMEOUT, 1);
|
||||
|
||||
// assert that 1 never joined the group from 0's perspective
|
||||
assertEquals(1, groupManager0.getHeaders(groupId0).size());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testWrongJoinMessages2() throws Exception {
|
||||
addDefaultIdentities();
|
||||
addDefaultContacts();
|
||||
listenToEvents();
|
||||
|
||||
// author0 joins privateGroup0 with wrong member's join message
|
||||
long joinTime = clock.currentTimeMillis();
|
||||
long inviteTime = joinTime - 1;
|
||||
BdfList toSign = groupInvitationFactory
|
||||
.createInviteToken(author0.getId(), author0.getId(),
|
||||
privateGroup0.getId(), inviteTime);
|
||||
byte[] creatorSignature = clientHelper
|
||||
.sign(SIGNING_LABEL_INVITE, toSign, author0.getPrivateKey());
|
||||
// join message should not include invite time and creator's signature
|
||||
GroupMessage joinMsg0 = groupMessageFactory
|
||||
.createJoinMessage(privateGroup0.getId(), joinTime, author0,
|
||||
inviteTime, creatorSignature);
|
||||
groupManager0.addPrivateGroup(privateGroup0, joinMsg0, true);
|
||||
assertEquals(joinMsg0.getMessage().getId(),
|
||||
groupManager0.getPreviousMsgId(groupId0));
|
||||
|
||||
// share the group with 1
|
||||
Transaction txn0 = db0.startTransaction(false);
|
||||
db0.setGroupVisibility(txn0, contactId1, privateGroup0.getId(), SHARED);
|
||||
db0.commitTransaction(txn0);
|
||||
db0.endTransaction(txn0);
|
||||
|
||||
// author1 joins privateGroup0 with wrong signature in join message
|
||||
joinTime = clock.currentTimeMillis();
|
||||
inviteTime = joinTime - 1;
|
||||
// signature uses joiner's key, not creator's key
|
||||
Contact c1 = contactManager0.getContact(contactId1);
|
||||
creatorSignature = groupInvitationFactory
|
||||
.signInvitation(c1, privateGroup0.getId(), inviteTime,
|
||||
author1.getPrivateKey());
|
||||
GroupMessage joinMsg1 = groupMessageFactory
|
||||
.createJoinMessage(privateGroup0.getId(), joinTime, author1,
|
||||
inviteTime, creatorSignature);
|
||||
groupManager1.addPrivateGroup(privateGroup0, joinMsg1, false);
|
||||
assertEquals(joinMsg1.getMessage().getId(),
|
||||
groupManager1.getPreviousMsgId(groupId0));
|
||||
|
||||
// share the group with 0
|
||||
Transaction txn1 = db1.startTransaction(false);
|
||||
db1.setGroupVisibility(txn1, contactId01, privateGroup0.getId(), SHARED);
|
||||
db1.commitTransaction(txn1);
|
||||
db1.endTransaction(txn1);
|
||||
|
||||
// sync join messages
|
||||
sync0To1();
|
||||
validationWaiter.await(TIMEOUT, 1);
|
||||
|
||||
// assert that 0 never joined the group from 1's perspective
|
||||
assertEquals(1, groupManager1.getHeaders(groupId0).size());
|
||||
|
||||
sync1To0();
|
||||
validationWaiter.await(TIMEOUT, 1);
|
||||
|
||||
// assert that 1 never joined the group from 0's perspective
|
||||
assertEquals(1, groupManager0.getHeaders(groupId0).size());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testGetMembers() throws Exception {
|
||||
defaultInit();
|
||||
|
||||
Collection<GroupMember> members0 = groupManager0.getMembers(groupId0);
|
||||
assertEquals(2, members0.size());
|
||||
for (GroupMember m : members0) {
|
||||
if (m.getAuthor().equals(author0)) {
|
||||
assertEquals(VISIBLE, m.getVisibility());
|
||||
} else {
|
||||
assertEquals(author1, m.getAuthor());
|
||||
assertEquals(VISIBLE, m.getVisibility());
|
||||
}
|
||||
}
|
||||
|
||||
Collection<GroupMember> members1 = groupManager1.getMembers(groupId0);
|
||||
assertEquals(2, members1.size());
|
||||
for (GroupMember m : members1) {
|
||||
if (m.getAuthor().equals(author1)) {
|
||||
assertEquals(VISIBLE, m.getVisibility());
|
||||
} else {
|
||||
assertEquals(author0, m.getAuthor());
|
||||
assertEquals(VISIBLE, m.getVisibility());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testJoinMessages() throws Exception {
|
||||
defaultInit();
|
||||
|
||||
Collection<GroupMessageHeader> headers0 =
|
||||
groupManager0.getHeaders(groupId0);
|
||||
for (GroupMessageHeader h : headers0) {
|
||||
if (h instanceof JoinMessageHeader) {
|
||||
JoinMessageHeader j = (JoinMessageHeader) h;
|
||||
// all relationships of the creator are visible
|
||||
assertEquals(VISIBLE, j.getVisibility());
|
||||
}
|
||||
}
|
||||
|
||||
Collection<GroupMessageHeader> headers1 =
|
||||
groupManager1.getHeaders(groupId0);
|
||||
for (GroupMessageHeader h : headers1) {
|
||||
if (h instanceof JoinMessageHeader) {
|
||||
JoinMessageHeader j = (JoinMessageHeader) h;
|
||||
if (h.getAuthor().equals(author1))
|
||||
// we are visible to ourselves
|
||||
assertEquals(VISIBLE, j.getVisibility());
|
||||
else
|
||||
// our relationship to the creator is visible
|
||||
assertEquals(VISIBLE, j.getVisibility());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testRevealingRelationships() throws Exception {
|
||||
defaultInit();
|
||||
|
||||
// share the group with 2
|
||||
Transaction txn0 = db0.startTransaction(false);
|
||||
db0.setGroupVisibility(txn0, contactId2, privateGroup0.getId(), SHARED);
|
||||
db0.commitTransaction(txn0);
|
||||
db0.endTransaction(txn0);
|
||||
|
||||
// author2 joins privateGroup0
|
||||
long joinTime = clock.currentTimeMillis();
|
||||
long inviteTime = joinTime - 1;
|
||||
Contact c2 = contactManager0.getContact(contactId2);
|
||||
byte[] creatorSignature = groupInvitationFactory
|
||||
.signInvitation(c2, privateGroup0.getId(), inviteTime,
|
||||
author0.getPrivateKey());
|
||||
GroupMessage joinMsg2 = groupMessageFactory
|
||||
.createJoinMessage(privateGroup0.getId(), joinTime, author2,
|
||||
inviteTime, creatorSignature);
|
||||
Transaction txn2 = db2.startTransaction(false);
|
||||
groupManager2.addPrivateGroup(txn2, privateGroup0, joinMsg2, false);
|
||||
|
||||
// share the group with 0
|
||||
db2.setGroupVisibility(txn2, contactId01, privateGroup0.getId(),
|
||||
SHARED);
|
||||
db2.commitTransaction(txn2);
|
||||
db2.endTransaction(txn2);
|
||||
|
||||
// sync join messages
|
||||
deliverMessage(sync2, contactId2, sync0, contactId02, "2 to 0");
|
||||
deliveryWaiter.await(TIMEOUT, 1);
|
||||
deliverMessage(sync0, contactId02, sync2, contactId2, "0 to 2");
|
||||
deliveryWaiter.await(TIMEOUT, 2);
|
||||
sync0To1();
|
||||
deliveryWaiter.await(TIMEOUT, 1);
|
||||
|
||||
// check that everybody sees everybody else as joined
|
||||
Collection<GroupMember> members0 = groupManager0.getMembers(groupId0);
|
||||
assertEquals(3, members0.size());
|
||||
Collection<GroupMember> members1 = groupManager1.getMembers(groupId0);
|
||||
assertEquals(3, members1.size());
|
||||
Collection<GroupMember> members2 = groupManager2.getMembers(groupId0);
|
||||
assertEquals(3, members2.size());
|
||||
|
||||
// assert that contact relationship is not revealed initially
|
||||
for (GroupMember m : members1) {
|
||||
if (m.getAuthor().equals(author2)) {
|
||||
assertEquals(INVISIBLE, m.getVisibility());
|
||||
}
|
||||
}
|
||||
for (GroupMember m : members2) {
|
||||
if (m.getAuthor().equals(author1)) {
|
||||
assertEquals(INVISIBLE, m.getVisibility());
|
||||
}
|
||||
}
|
||||
|
||||
// reveal contact relationship
|
||||
Transaction txn1 = db1.startTransaction(false);
|
||||
groupManager1
|
||||
.relationshipRevealed(txn1, groupId0, author2.getId(), false);
|
||||
db1.commitTransaction(txn1);
|
||||
db1.endTransaction(txn1);
|
||||
txn2 = db2.startTransaction(false);
|
||||
groupManager2
|
||||
.relationshipRevealed(txn2, groupId0, author1.getId(), true);
|
||||
db2.commitTransaction(txn2);
|
||||
db2.endTransaction(txn2);
|
||||
|
||||
// assert that contact relationship is now revealed properly
|
||||
members1 = groupManager1.getMembers(groupId0);
|
||||
for (GroupMember m : members1) {
|
||||
if (m.getAuthor().equals(author2)) {
|
||||
assertEquals(REVEALED_BY_US, m.getVisibility());
|
||||
}
|
||||
}
|
||||
members2 = groupManager2.getMembers(groupId0);
|
||||
for (GroupMember m : members2) {
|
||||
if (m.getAuthor().equals(author1)) {
|
||||
assertEquals(REVEALED_BY_CONTACT, m.getVisibility());
|
||||
}
|
||||
}
|
||||
|
||||
// assert that join messages reflect revealed relationship
|
||||
Collection<GroupMessageHeader> headers1 =
|
||||
groupManager1.getHeaders(groupId0);
|
||||
for (GroupMessageHeader h : headers1) {
|
||||
if (h instanceof JoinMessageHeader) {
|
||||
JoinMessageHeader j = (JoinMessageHeader) h;
|
||||
if (h.getAuthor().equals(author2))
|
||||
// 1 revealed the relationship to 2
|
||||
assertEquals(REVEALED_BY_US, j.getVisibility());
|
||||
else
|
||||
// 1's other relationship (to 1 and creator) are visible
|
||||
assertEquals(VISIBLE, j.getVisibility());
|
||||
}
|
||||
}
|
||||
Collection<GroupMessageHeader> headers2 =
|
||||
groupManager2.getHeaders(groupId0);
|
||||
for (GroupMessageHeader h : headers2) {
|
||||
if (h instanceof JoinMessageHeader) {
|
||||
JoinMessageHeader j = (JoinMessageHeader) h;
|
||||
if (h.getAuthor().equals(author1))
|
||||
// 2's relationship was revealed by 1
|
||||
assertEquals(REVEALED_BY_CONTACT, j.getVisibility());
|
||||
else
|
||||
// 2's other relationship (to 2 and creator) are visible
|
||||
assertEquals(VISIBLE, j.getVisibility());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testDissolveGroup() throws Exception {
|
||||
defaultInit();
|
||||
|
||||
// group is not dissolved initially
|
||||
assertFalse(groupManager1.isDissolved(groupId0));
|
||||
|
||||
// creator dissolves group
|
||||
Transaction txn1 = db1.startTransaction(false);
|
||||
groupManager1.markGroupDissolved(txn1, groupId0);
|
||||
db1.commitTransaction(txn1);
|
||||
db1.endTransaction(txn1);
|
||||
|
||||
// group is dissolved now
|
||||
assertTrue(groupManager1.isDissolved(groupId0));
|
||||
}
|
||||
|
||||
@After
|
||||
public void tearDown() throws Exception {
|
||||
stopLifecycles();
|
||||
TestUtils.deleteTestDirectory(testDir);
|
||||
}
|
||||
|
||||
private class Listener implements EventListener {
|
||||
@Override
|
||||
public void eventOccurred(Event e) {
|
||||
if (e instanceof MessageStateChangedEvent) {
|
||||
MessageStateChangedEvent event = (MessageStateChangedEvent) e;
|
||||
if (!event.isLocal()) {
|
||||
if (event.getState() == DELIVERED) {
|
||||
LOG.info("Delivered new message");
|
||||
deliveryWaiter.resume();
|
||||
} else if (event.getState() == INVALID ||
|
||||
event.getState() == PENDING) {
|
||||
LOG.info("Validated new " + event.getState().name() +
|
||||
" message");
|
||||
validationWaiter.resume();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void defaultInit() throws Exception {
|
||||
addDefaultIdentities();
|
||||
addDefaultContacts();
|
||||
listenToEvents();
|
||||
addGroup();
|
||||
}
|
||||
|
||||
private void addDefaultIdentities() throws DbException {
|
||||
KeyPair keyPair0 = crypto.generateSignatureKeyPair();
|
||||
byte[] publicKey0 = keyPair0.getPublic().getEncoded();
|
||||
byte[] privateKey0 = keyPair0.getPrivate().getEncoded();
|
||||
author0 = authorFactory
|
||||
.createLocalAuthor(AUTHOR0, publicKey0, privateKey0);
|
||||
identityManager0.registerLocalAuthor(author0);
|
||||
privateGroup0 =
|
||||
privateGroupFactory.createPrivateGroup("Testgroup", author0);
|
||||
groupId0 = privateGroup0.getId();
|
||||
|
||||
KeyPair keyPair1 = crypto.generateSignatureKeyPair();
|
||||
byte[] publicKey1 = keyPair1.getPublic().getEncoded();
|
||||
byte[] privateKey1 = keyPair1.getPrivate().getEncoded();
|
||||
author1 = authorFactory
|
||||
.createLocalAuthor(AUTHOR1, publicKey1, privateKey1);
|
||||
identityManager1.registerLocalAuthor(author1);
|
||||
|
||||
KeyPair keyPair2 = crypto.generateSignatureKeyPair();
|
||||
byte[] publicKey2 = keyPair2.getPublic().getEncoded();
|
||||
byte[] privateKey2 = keyPair2.getPrivate().getEncoded();
|
||||
author2 = authorFactory
|
||||
.createLocalAuthor(AUTHOR2, publicKey2, privateKey2);
|
||||
identityManager2.registerLocalAuthor(author2);
|
||||
}
|
||||
|
||||
private void addDefaultContacts() throws DbException {
|
||||
// creator adds invitee as contact
|
||||
contactId1 = contactManager0
|
||||
.addContact(author1, author0.getId(), master,
|
||||
clock.currentTimeMillis(), true, true, true);
|
||||
// invitee adds creator back
|
||||
contactId01 = contactManager1
|
||||
.addContact(author0, author1.getId(), master,
|
||||
clock.currentTimeMillis(), true, true, true);
|
||||
// creator adds invitee as contact
|
||||
contactId2 = contactManager0
|
||||
.addContact(author2, author0.getId(), master,
|
||||
clock.currentTimeMillis(), true, true, true);
|
||||
// invitee adds creator back
|
||||
contactId02 = contactManager2
|
||||
.addContact(author0, author2.getId(), master,
|
||||
clock.currentTimeMillis(), true, true, true);
|
||||
}
|
||||
|
||||
private void listenToEvents() {
|
||||
Listener listener0 = new Listener();
|
||||
t0.getEventBus().addListener(listener0);
|
||||
Listener listener1 = new Listener();
|
||||
t1.getEventBus().addListener(listener1);
|
||||
Listener listener2 = new Listener();
|
||||
t2.getEventBus().addListener(listener2);
|
||||
}
|
||||
|
||||
private void addGroup() throws Exception {
|
||||
// author0 joins privateGroup0
|
||||
long joinTime = clock.currentTimeMillis();
|
||||
GroupMessage joinMsg0 = groupMessageFactory
|
||||
.createJoinMessage(privateGroup0.getId(), joinTime, author0);
|
||||
groupManager0.addPrivateGroup(privateGroup0, joinMsg0, true);
|
||||
assertEquals(joinMsg0.getMessage().getId(),
|
||||
groupManager0.getPreviousMsgId(groupId0));
|
||||
|
||||
// share the group with 1
|
||||
Transaction txn0 = db0.startTransaction(false);
|
||||
db0.setGroupVisibility(txn0, contactId1, privateGroup0.getId(), SHARED);
|
||||
db0.commitTransaction(txn0);
|
||||
db0.endTransaction(txn0);
|
||||
|
||||
// author1 joins privateGroup0
|
||||
joinTime = clock.currentTimeMillis();
|
||||
long inviteTime = joinTime - 1;
|
||||
Contact c1 = contactManager0.getContact(contactId1);
|
||||
byte[] creatorSignature = groupInvitationFactory
|
||||
.signInvitation(c1, privateGroup0.getId(), inviteTime,
|
||||
author0.getPrivateKey());
|
||||
GroupMessage joinMsg1 = groupMessageFactory
|
||||
.createJoinMessage(privateGroup0.getId(), joinTime, author1,
|
||||
inviteTime, creatorSignature);
|
||||
groupManager1.addPrivateGroup(privateGroup0, joinMsg1, false);
|
||||
|
||||
// share the group with 0
|
||||
Transaction txn1 = db1.startTransaction(false);
|
||||
db1.setGroupVisibility(txn1, contactId01, privateGroup0.getId(),
|
||||
SHARED);
|
||||
db1.commitTransaction(txn1);
|
||||
db1.endTransaction(txn1);
|
||||
assertEquals(joinMsg1.getMessage().getId(),
|
||||
groupManager1.getPreviousMsgId(groupId0));
|
||||
|
||||
// sync join messages
|
||||
sync0To1();
|
||||
deliveryWaiter.await(TIMEOUT, 1);
|
||||
sync1To0();
|
||||
deliveryWaiter.await(TIMEOUT, 1);
|
||||
}
|
||||
|
||||
private void sync0To1() throws IOException, TimeoutException {
|
||||
deliverMessage(sync0, contactId01, sync1, contactId1, "0 to 1");
|
||||
}
|
||||
|
||||
private void sync1To0() throws IOException, TimeoutException {
|
||||
deliverMessage(sync1, contactId1, sync0, contactId01, "1 to 0");
|
||||
}
|
||||
|
||||
private void deliverMessage(SyncSessionFactory fromSync, ContactId fromId,
|
||||
SyncSessionFactory toSync, ContactId toId, String debug)
|
||||
throws IOException, TimeoutException {
|
||||
|
||||
if (debug != null) LOG.info("TEST: Sending message from " + debug);
|
||||
|
||||
ByteArrayOutputStream out = new ByteArrayOutputStream();
|
||||
// Create an outgoing sync session
|
||||
SyncSession sessionFrom =
|
||||
fromSync.createSimplexOutgoingSession(toId, MAX_LATENCY, out);
|
||||
// Write whatever needs to be written
|
||||
sessionFrom.run();
|
||||
out.close();
|
||||
|
||||
ByteArrayInputStream in = new ByteArrayInputStream(out.toByteArray());
|
||||
// Create an incoming sync session
|
||||
SyncSession sessionTo = toSync.createIncomingSession(fromId, in);
|
||||
// Read whatever needs to be read
|
||||
sessionTo.run();
|
||||
in.close();
|
||||
}
|
||||
|
||||
private void startLifecycles() throws InterruptedException {
|
||||
// Start the lifecycle manager and wait for it to finish
|
||||
lifecycleManager0 = t0.getLifecycleManager();
|
||||
lifecycleManager1 = t1.getLifecycleManager();
|
||||
lifecycleManager2 = t2.getLifecycleManager();
|
||||
lifecycleManager0.startServices(AUTHOR0);
|
||||
lifecycleManager1.startServices(AUTHOR1);
|
||||
lifecycleManager2.startServices(AUTHOR2);
|
||||
lifecycleManager0.waitForStartup();
|
||||
lifecycleManager1.waitForStartup();
|
||||
lifecycleManager2.waitForStartup();
|
||||
}
|
||||
|
||||
private void stopLifecycles() throws InterruptedException {
|
||||
// Clean up
|
||||
lifecycleManager0.stopServices();
|
||||
lifecycleManager1.stopServices();
|
||||
lifecycleManager2.stopServices();
|
||||
lifecycleManager0.waitForShutdown();
|
||||
lifecycleManager1.waitForShutdown();
|
||||
lifecycleManager2.waitForShutdown();
|
||||
}
|
||||
|
||||
private void injectEagerSingletons(
|
||||
PrivateGroupManagerTestComponent component) {
|
||||
component.inject(new LifecycleModule.EagerSingletons());
|
||||
component.inject(new PrivateGroupModule.EagerSingletons());
|
||||
component.inject(new CryptoModule.EagerSingletons());
|
||||
component.inject(new ContactModule.EagerSingletons());
|
||||
component.inject(new TransportModule.EagerSingletons());
|
||||
component.inject(new SyncModule.EagerSingletons());
|
||||
component.inject(new PropertiesModule.EagerSingletons());
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,85 @@
|
||||
package org.briarproject;
|
||||
|
||||
import org.briarproject.api.contact.ContactManager;
|
||||
import org.briarproject.api.db.DatabaseComponent;
|
||||
import org.briarproject.api.event.EventBus;
|
||||
import org.briarproject.api.identity.IdentityManager;
|
||||
import org.briarproject.api.lifecycle.LifecycleManager;
|
||||
import org.briarproject.api.privategroup.PrivateGroupManager;
|
||||
import org.briarproject.api.sync.SyncSessionFactory;
|
||||
import org.briarproject.clients.ClientsModule;
|
||||
import org.briarproject.contact.ContactModule;
|
||||
import org.briarproject.crypto.CryptoModule;
|
||||
import org.briarproject.data.DataModule;
|
||||
import org.briarproject.db.DatabaseModule;
|
||||
import org.briarproject.event.EventModule;
|
||||
import org.briarproject.identity.IdentityModule;
|
||||
import org.briarproject.lifecycle.LifecycleModule;
|
||||
import org.briarproject.messaging.MessagingModule;
|
||||
import org.briarproject.privategroup.PrivateGroupModule;
|
||||
import org.briarproject.privategroup.invitation.GroupInvitationModule;
|
||||
import org.briarproject.properties.PropertiesModule;
|
||||
import org.briarproject.sharing.SharingModule;
|
||||
import org.briarproject.sync.SyncModule;
|
||||
import org.briarproject.system.SystemModule;
|
||||
import org.briarproject.transport.TransportModule;
|
||||
|
||||
import javax.inject.Singleton;
|
||||
|
||||
import dagger.Component;
|
||||
|
||||
@Singleton
|
||||
@Component(modules = {
|
||||
TestDatabaseModule.class,
|
||||
TestPluginsModule.class,
|
||||
TestSeedProviderModule.class,
|
||||
ClientsModule.class,
|
||||
ContactModule.class,
|
||||
CryptoModule.class,
|
||||
DataModule.class,
|
||||
DatabaseModule.class,
|
||||
EventModule.class,
|
||||
MessagingModule.class,
|
||||
PrivateGroupModule.class,
|
||||
GroupInvitationModule.class,
|
||||
IdentityModule.class,
|
||||
LifecycleModule.class,
|
||||
PropertiesModule.class,
|
||||
SharingModule.class,
|
||||
SyncModule.class,
|
||||
SystemModule.class,
|
||||
TransportModule.class
|
||||
})
|
||||
interface PrivateGroupManagerTestComponent {
|
||||
|
||||
void inject(PrivateGroupManagerTest testCase);
|
||||
|
||||
void inject(ContactModule.EagerSingletons init);
|
||||
|
||||
void inject(CryptoModule.EagerSingletons init);
|
||||
|
||||
void inject(PrivateGroupModule.EagerSingletons init);
|
||||
|
||||
void inject(LifecycleModule.EagerSingletons init);
|
||||
|
||||
void inject(PropertiesModule.EagerSingletons init);
|
||||
|
||||
void inject(SyncModule.EagerSingletons init);
|
||||
|
||||
void inject(TransportModule.EagerSingletons init);
|
||||
|
||||
LifecycleManager getLifecycleManager();
|
||||
|
||||
EventBus getEventBus();
|
||||
|
||||
IdentityManager getIdentityManager();
|
||||
|
||||
ContactManager getContactManager();
|
||||
|
||||
PrivateGroupManager getPrivateGroupManager();
|
||||
|
||||
SyncSessionFactory getSyncSessionFactory();
|
||||
|
||||
DatabaseComponent getDatabaseComponent();
|
||||
|
||||
}
|
||||
@@ -43,6 +43,9 @@ import static org.junit.Assert.assertTrue;
|
||||
|
||||
public class SimplexMessagingIntegrationTest extends BriarTestCase {
|
||||
|
||||
private final static String ALICE = "Alice";
|
||||
private final static String BOB = "Bob";
|
||||
|
||||
private final File testDir = TestUtils.getTestDirectory();
|
||||
private final File aliceDir = new File(testDir, "alice");
|
||||
private final File bobDir = new File(testDir, "bob");
|
||||
@@ -69,6 +72,7 @@ public class SimplexMessagingIntegrationTest extends BriarTestCase {
|
||||
read(write());
|
||||
}
|
||||
|
||||
|
||||
private byte[] write() throws Exception {
|
||||
// Instantiate Alice's services
|
||||
LifecycleManager lifecycleManager = alice.getLifecycleManager();
|
||||
@@ -83,23 +87,23 @@ public class SimplexMessagingIntegrationTest extends BriarTestCase {
|
||||
SyncSessionFactory syncSessionFactory = alice.getSyncSessionFactory();
|
||||
|
||||
// Start the lifecycle manager
|
||||
lifecycleManager.startServices();
|
||||
lifecycleManager.startServices(null);
|
||||
lifecycleManager.waitForStartup();
|
||||
// Add an identity for Alice
|
||||
LocalAuthor aliceAuthor = new LocalAuthor(aliceId, "Alice",
|
||||
new byte[MAX_PUBLIC_KEY_LENGTH], new byte[123], timestamp);
|
||||
identityManager.addLocalAuthor(aliceAuthor);
|
||||
identityManager.registerLocalAuthor(aliceAuthor);
|
||||
// Add Bob as a contact
|
||||
Author bobAuthor = new Author(bobId, "Bob",
|
||||
Author bobAuthor = new Author(bobId, BOB,
|
||||
new byte[MAX_PUBLIC_KEY_LENGTH]);
|
||||
ContactId contactId = contactManager.addContact(bobAuthor, aliceId,
|
||||
master, timestamp, true, true, true);
|
||||
ContactId contactId = contactManager.addContact(bobAuthor,
|
||||
aliceAuthor.getId(), master, timestamp, true, true, true);
|
||||
|
||||
// Send Bob a message
|
||||
GroupId groupId = messagingManager.getConversationId(contactId);
|
||||
byte[] body = "Hi Bob!".getBytes("UTF-8");
|
||||
String body = "Hi Bob!";
|
||||
PrivateMessage message = privateMessageFactory.createPrivateMessage(
|
||||
groupId, timestamp, null, "text/plain", body);
|
||||
groupId, timestamp, body);
|
||||
messagingManager.addLocalMessage(message);
|
||||
// Get a stream context
|
||||
StreamContext ctx = keyManager.getStreamContext(contactId,
|
||||
@@ -136,18 +140,17 @@ public class SimplexMessagingIntegrationTest extends BriarTestCase {
|
||||
bob.getMessagingManager();
|
||||
|
||||
// Start the lifecyle manager
|
||||
lifecycleManager.startServices();
|
||||
lifecycleManager.startServices(null);
|
||||
lifecycleManager.waitForStartup();
|
||||
// Add an identity for Bob
|
||||
LocalAuthor bobAuthor = new LocalAuthor(bobId, "Bob",
|
||||
LocalAuthor bobAuthor = new LocalAuthor(bobId, BOB,
|
||||
new byte[MAX_PUBLIC_KEY_LENGTH], new byte[123], timestamp);
|
||||
identityManager.addLocalAuthor(bobAuthor);
|
||||
identityManager.registerLocalAuthor(bobAuthor);
|
||||
// Add Alice as a contact
|
||||
Author aliceAuthor = new Author(aliceId, "Alice",
|
||||
Author aliceAuthor = new Author(aliceId, ALICE,
|
||||
new byte[MAX_PUBLIC_KEY_LENGTH]);
|
||||
ContactId contactId = contactManager.addContact(aliceAuthor, bobId,
|
||||
master, timestamp, false, true, true);
|
||||
|
||||
ContactId contactId = contactManager.addContact(aliceAuthor,
|
||||
bobAuthor.getId(), master, timestamp, false, true, true);
|
||||
// Set up an event listener
|
||||
MessageListener listener = new MessageListener();
|
||||
bob.getEventBus().addListener(listener);
|
||||
|
||||
@@ -74,7 +74,7 @@ public class SyncIntegrationTest extends BriarTestCase {
|
||||
headerKey = TestUtils.getSecretKey();
|
||||
streamNumber = 123;
|
||||
// Create a group
|
||||
ClientId clientId = new ClientId(TestUtils.getRandomId());
|
||||
ClientId clientId = new ClientId(TestUtils.getRandomString(5));
|
||||
byte[] descriptor = new byte[0];
|
||||
Group group = groupFactory.createGroup(clientId, descriptor);
|
||||
// Add two messages to the group
|
||||
@@ -122,7 +122,7 @@ public class SyncIntegrationTest extends BriarTestCase {
|
||||
|
||||
// Create the readers
|
||||
StreamContext ctx = new StreamContext(contactId, transportId, tagKey,
|
||||
headerKey, 0);
|
||||
headerKey, streamNumber);
|
||||
InputStream streamReader = streamReaderFactory.createStreamReader(in,
|
||||
ctx);
|
||||
PacketReader packetReader = packetReaderFactory.createPacketReader(
|
||||
|
||||
@@ -1,5 +1,10 @@
|
||||
package org.briarproject;
|
||||
package org.briarproject.introduction;
|
||||
|
||||
import org.briarproject.TestDatabaseModule;
|
||||
import org.briarproject.TestPluginsModule;
|
||||
import org.briarproject.TestSeedProviderModule;
|
||||
import org.briarproject.api.clients.ClientHelper;
|
||||
import org.briarproject.api.clients.MessageTracker;
|
||||
import org.briarproject.api.contact.ContactManager;
|
||||
import org.briarproject.api.db.DatabaseComponent;
|
||||
import org.briarproject.api.event.EventBus;
|
||||
@@ -15,10 +20,8 @@ import org.briarproject.data.DataModule;
|
||||
import org.briarproject.db.DatabaseModule;
|
||||
import org.briarproject.event.EventModule;
|
||||
import org.briarproject.identity.IdentityModule;
|
||||
import org.briarproject.introduction.IntroductionGroupFactory;
|
||||
import org.briarproject.introduction.IntroductionModule;
|
||||
import org.briarproject.introduction.MessageSender;
|
||||
import org.briarproject.lifecycle.LifecycleModule;
|
||||
import org.briarproject.messaging.MessagingModule;
|
||||
import org.briarproject.properties.PropertiesModule;
|
||||
import org.briarproject.sync.SyncModule;
|
||||
import org.briarproject.system.SystemModule;
|
||||
@@ -45,9 +48,10 @@ import dagger.Component;
|
||||
SyncModule.class,
|
||||
SystemModule.class,
|
||||
DataModule.class,
|
||||
PropertiesModule.class
|
||||
PropertiesModule.class,
|
||||
MessagingModule.class
|
||||
})
|
||||
public interface IntroductionIntegrationTestComponent {
|
||||
interface IntroductionIntegrationTestComponent {
|
||||
|
||||
void inject(IntroductionIntegrationTest testCase);
|
||||
|
||||
@@ -79,12 +83,16 @@ public interface IntroductionIntegrationTestComponent {
|
||||
|
||||
TransportPropertyManager getTransportPropertyManager();
|
||||
|
||||
MessageTracker getMessageTracker();
|
||||
|
||||
SyncSessionFactory getSyncSessionFactory();
|
||||
|
||||
/* the following methods are only needed to manually construct messages */
|
||||
|
||||
DatabaseComponent getDatabaseComponent();
|
||||
|
||||
ClientHelper getClientHelper();
|
||||
|
||||
MessageSender getMessageSender();
|
||||
|
||||
IntroductionGroupFactory getIntroductionGroupFactory();
|
||||
@@ -1,6 +1,6 @@
|
||||
[main]
|
||||
host = https://www.transifex.com
|
||||
lang_map = pt_BR: pt-rBR
|
||||
lang_map = pt_BR: pt-rBR, fr_FR: fr
|
||||
|
||||
[briar.stringsxml-5]
|
||||
file_filter = res/values-<lang>/strings.xml
|
||||
|
||||
@@ -93,7 +93,7 @@
|
||||
android:label="@string/app_name"
|
||||
android:theme="@style/BriarThemeNoActionBar.Default"
|
||||
android:parentActivityName=".android.NavDrawerActivity"
|
||||
android:windowSoftInputMode="stateHidden">
|
||||
android:windowSoftInputMode="stateHidden|adjustResize">
|
||||
<meta-data
|
||||
android:name="android.support.PARENT_ACTIVITY"
|
||||
android:value=".android.NavDrawerActivity"
|
||||
@@ -101,7 +101,70 @@
|
||||
</activity>
|
||||
|
||||
<activity
|
||||
android:name=".android.sharing.InvitationsForumActivity"
|
||||
android:name=".android.privategroup.creation.CreateGroupActivity"
|
||||
android:label="@string/groups_create_group_title"
|
||||
android:parentActivityName=".android.NavDrawerActivity"
|
||||
android:windowSoftInputMode="adjustResize">
|
||||
<meta-data
|
||||
android:name="android.support.PARENT_ACTIVITY"
|
||||
android:value=".android.NavDrawerActivity"
|
||||
/>
|
||||
</activity>
|
||||
|
||||
<activity
|
||||
android:name=".android.privategroup.conversation.GroupActivity"
|
||||
android:label="@string/app_name"
|
||||
android:parentActivityName=".android.NavDrawerActivity"
|
||||
android:windowSoftInputMode="adjustResize|stateHidden">
|
||||
<meta-data
|
||||
android:name="android.support.PARENT_ACTIVITY"
|
||||
android:value=".android.NavDrawerActivity"
|
||||
/>
|
||||
</activity>
|
||||
|
||||
<activity
|
||||
android:name=".android.privategroup.invitation.GroupInvitationActivity"
|
||||
android:label="@string/groups_invitations_title"
|
||||
android:parentActivityName=".android.NavDrawerActivity">
|
||||
<meta-data
|
||||
android:name="android.support.PARENT_ACTIVITY"
|
||||
android:value=".android.NavDrawerActivity"/>
|
||||
</activity>
|
||||
|
||||
<activity
|
||||
android:name=".android.privategroup.memberlist.GroupMemberListActivity"
|
||||
android:label="@string/groups_member_list"
|
||||
android:parentActivityName=".android.privategroup.conversation.GroupActivity"
|
||||
android:windowSoftInputMode="adjustResize|stateHidden">
|
||||
<meta-data
|
||||
android:name="android.support.PARENT_ACTIVITY"
|
||||
android:value=".android.privategroup.conversation.GroupActivity"
|
||||
/>
|
||||
</activity>
|
||||
|
||||
<activity
|
||||
android:name=".android.privategroup.reveal.RevealContactsActivity"
|
||||
android:label="@string/groups_reveal_contacts"
|
||||
android:parentActivityName=".android.privategroup.conversation.GroupActivity"
|
||||
android:windowSoftInputMode="adjustResize|stateAlwaysHidden">
|
||||
<meta-data
|
||||
android:name="android.support.PARENT_ACTIVITY"
|
||||
android:value=".android.privategroup.conversation.GroupActivity"
|
||||
/>
|
||||
</activity>
|
||||
|
||||
<activity
|
||||
android:name=".android.privategroup.creation.GroupInviteActivity"
|
||||
android:label="@string/groups_invite_members"
|
||||
android:parentActivityName=".android.privategroup.conversation.GroupActivity"
|
||||
android:windowSoftInputMode="adjustResize|stateHidden">
|
||||
<meta-data
|
||||
android:name="android.support.PARENT_ACTIVITY"
|
||||
android:value=".android.privategroup.conversation.GroupActivity"/>
|
||||
</activity>
|
||||
|
||||
<activity
|
||||
android:name=".android.sharing.ForumInvitationActivity"
|
||||
android:label="@string/forum_invitations_title"
|
||||
android:parentActivityName=".android.NavDrawerActivity">
|
||||
<meta-data
|
||||
@@ -111,7 +174,7 @@
|
||||
</activity>
|
||||
|
||||
<activity
|
||||
android:name=".android.sharing.InvitationsBlogActivity"
|
||||
android:name=".android.sharing.BlogInvitationActivity"
|
||||
android:label="@string/blogs_sharing_invitations_title"
|
||||
android:parentActivityName=".android.contact.ConversationActivity">
|
||||
<meta-data
|
||||
@@ -134,7 +197,8 @@
|
||||
<activity
|
||||
android:name=".android.forum.ForumActivity"
|
||||
android:label="@string/app_name"
|
||||
android:parentActivityName=".android.NavDrawerActivity">
|
||||
android:parentActivityName=".android.NavDrawerActivity"
|
||||
android:windowSoftInputMode="adjustResize|stateHidden">
|
||||
<meta-data
|
||||
android:name="android.support.PARENT_ACTIVITY"
|
||||
android:value=".android.NavDrawerActivity"
|
||||
@@ -144,7 +208,8 @@
|
||||
<activity
|
||||
android:name=".android.sharing.ShareForumActivity"
|
||||
android:label="@string/activity_share_toolbar_header"
|
||||
android:parentActivityName=".android.forum.ForumActivity">
|
||||
android:parentActivityName=".android.forum.ForumActivity"
|
||||
android:windowSoftInputMode="adjustResize|stateHidden">
|
||||
<meta-data
|
||||
android:name="android.support.PARENT_ACTIVITY"
|
||||
android:value=".android.forum.ForumActivity"
|
||||
@@ -154,7 +219,8 @@
|
||||
<activity
|
||||
android:name=".android.sharing.ShareBlogActivity"
|
||||
android:label="@string/activity_share_toolbar_header"
|
||||
android:parentActivityName=".android.blogs.BlogActivity">
|
||||
android:parentActivityName=".android.blogs.BlogActivity"
|
||||
android:windowSoftInputMode="adjustResize|stateHidden">
|
||||
<meta-data
|
||||
android:name="android.support.PARENT_ACTIVITY"
|
||||
android:value=".android.blogs.BlogActivity"
|
||||
@@ -162,7 +228,7 @@
|
||||
</activity>
|
||||
|
||||
<activity
|
||||
android:name=".android.sharing.SharingStatusForumActivity"
|
||||
android:name=".android.sharing.ForumSharingStatusActivity"
|
||||
android:label="@string/sharing_status"
|
||||
android:parentActivityName=".android.forum.ForumActivity">
|
||||
<meta-data
|
||||
@@ -172,7 +238,7 @@
|
||||
</activity>
|
||||
|
||||
<activity
|
||||
android:name=".android.sharing.SharingStatusBlogActivity"
|
||||
android:name=".android.sharing.BlogSharingStatusActivity"
|
||||
android:label="@string/sharing_status"
|
||||
android:parentActivityName=".android.blogs.BlogActivity">
|
||||
<meta-data
|
||||
@@ -181,16 +247,6 @@
|
||||
/>
|
||||
</activity>
|
||||
|
||||
<activity
|
||||
android:name=".android.blogs.CreateBlogActivity"
|
||||
android:label="@string/blogs_my_blogs_label"
|
||||
android:parentActivityName=".android.NavDrawerActivity">
|
||||
<meta-data
|
||||
android:name="android.support.PARENT_ACTIVITY"
|
||||
android:value=".android.NavDrawerActivity"
|
||||
/>
|
||||
</activity>
|
||||
|
||||
<activity
|
||||
android:name=".android.blogs.BlogActivity"
|
||||
android:parentActivityName=".android.NavDrawerActivity">
|
||||
@@ -211,6 +267,17 @@
|
||||
/>
|
||||
</activity>
|
||||
|
||||
<activity
|
||||
android:name=".android.blogs.ReblogActivity"
|
||||
android:label="@string/blogs_reblog_button"
|
||||
android:parentActivityName=".android.blogs.BlogActivity"
|
||||
android:windowSoftInputMode="stateHidden">
|
||||
<meta-data
|
||||
android:name="android.support.PARENT_ACTIVITY"
|
||||
android:value=".android.blogs.BlogActivity"
|
||||
/>
|
||||
</activity>
|
||||
|
||||
<activity
|
||||
android:name=".android.blogs.RssFeedImportActivity"
|
||||
android:label="@string/blogs_rss_feeds_import"
|
||||
@@ -232,12 +299,6 @@
|
||||
/>
|
||||
</activity>
|
||||
|
||||
<activity
|
||||
android:name=".android.identity.CreateIdentityActivity"
|
||||
android:label="@string/new_identity_title"
|
||||
android:windowSoftInputMode="stateVisible">
|
||||
</activity>
|
||||
|
||||
<activity
|
||||
android:name=".android.invitation.AddContactActivity"
|
||||
android:label="@string/add_contact_title"
|
||||
|
||||
58
briar-android/artwork/ic_emoji_emoticons.svg
Normal file
@@ -0,0 +1,58 @@
|
||||
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
|
||||
<!-- Created with Inkscape (http://www.inkscape.org/) -->
|
||||
|
||||
<svg
|
||||
xmlns:dc="http://purl.org/dc/elements/1.1/"
|
||||
xmlns:cc="http://creativecommons.org/ns#"
|
||||
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
|
||||
xmlns:svg="http://www.w3.org/2000/svg"
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
|
||||
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
|
||||
id="svg2"
|
||||
version="1.1"
|
||||
inkscape:version="0.91 r13725"
|
||||
width="24"
|
||||
height="24"
|
||||
viewBox="0 0 24 24"
|
||||
sodipodi:docname="ic_emoji_emoticons.svg">
|
||||
<metadata
|
||||
id="metadata8">
|
||||
<rdf:RDF>
|
||||
<cc:Work
|
||||
rdf:about="">
|
||||
<dc:format>image/svg+xml</dc:format>
|
||||
<dc:type
|
||||
rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
|
||||
<dc:title></dc:title>
|
||||
</cc:Work>
|
||||
</rdf:RDF>
|
||||
</metadata>
|
||||
<defs
|
||||
id="defs6" />
|
||||
<sodipodi:namedview
|
||||
pagecolor="#ffffff"
|
||||
bordercolor="#666666"
|
||||
borderopacity="1"
|
||||
objecttolerance="10"
|
||||
gridtolerance="10"
|
||||
guidetolerance="10"
|
||||
inkscape:pageopacity="0"
|
||||
inkscape:pageshadow="2"
|
||||
inkscape:window-width="1920"
|
||||
inkscape:window-height="1021"
|
||||
id="namedview4"
|
||||
showgrid="false"
|
||||
inkscape:zoom="4.6354778"
|
||||
inkscape:cx="47.926788"
|
||||
inkscape:cy="24.127496"
|
||||
inkscape:window-x="1440"
|
||||
inkscape:window-y="23"
|
||||
inkscape:window-maximized="0"
|
||||
inkscape:current-layer="svg2" />
|
||||
<path
|
||||
style="fill:#000000;fill-opacity:1"
|
||||
d="m 15.483903,3.8556996 c -0.661546,0.040406 -0.536253,1.2125273 -0.08054,1.6240791 1.361771,1.4519837 1.747379,3.5080793 1.895646,5.4253553 0.109142,2.216286 -0.0846,4.555699 -1.171466,6.533591 -0.361828,0.731167 -1.339597,1.273078 -1.15283,2.195835 0.287109,1.037426 1.187031,0.242862 1.620751,-0.183708 1.991711,-1.742024 2.867744,-4.428018 2.93133,-7.013492 0.02009,-1.918049 -0.231841,-3.9213035 -1.212735,-5.6044037 -0.664187,-1.0906817 -1.39072,-2.2339438 -2.497355,-2.9193489 -0.127976,-0.045915 -0.238296,-0.06368 -0.332802,-0.057908 z M 5.9118212,7.6583077 A 1.3631614,1.3631614 0 0 0 4.54866,9.0214691 1.3631614,1.3631614 0 0 0 5.9118212,10.38463 1.3631614,1.3631614 0 0 0 7.2749824,9.0214691 1.3631614,1.3631614 0 0 0 5.9118212,7.6583077 Z m 3.0731032,3.0012183 0,2.044742 4.7710646,0 0,-2.044742 -4.7710646,0 z m -3.1496485,3.471136 a 1.3631614,1.3631614 0 0 0 -1.3631612,1.363161 1.3631614,1.3631614 0 0 0 1.3631612,1.363161 1.3631614,1.3631614 0 0 0 1.3631612,-1.363161 1.3631614,1.3631614 0 0 0 -1.3631612,-1.363161 z"
|
||||
id="path4142"
|
||||
inkscape:connector-curvature="0" />
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 2.6 KiB |
BIN
briar-android/assets/emoji_activity.png
Normal file
|
After Width: | Height: | Size: 244 KiB |
BIN
briar-android/assets/emoji_animals_nature.png
Normal file
|
After Width: | Height: | Size: 348 KiB |
BIN
briar-android/assets/emoji_flags.png
Normal file
|
After Width: | Height: | Size: 901 KiB |
BIN
briar-android/assets/emoji_food_drink.png
Normal file
|
After Width: | Height: | Size: 258 KiB |
BIN
briar-android/assets/emoji_objects.png
Normal file
|
After Width: | Height: | Size: 478 KiB |
BIN
briar-android/assets/emoji_smiley_people.png
Normal file
|
After Width: | Height: | Size: 650 KiB |
BIN
briar-android/assets/emoji_symbols.png
Normal file
|
After Width: | Height: | Size: 412 KiB |
BIN
briar-android/assets/emoji_travel_places.png
Normal file
|
After Width: | Height: | Size: 547 KiB |
@@ -11,9 +11,6 @@ dependencies {
|
||||
compile project(':briar-api')
|
||||
compile project(':briar-core')
|
||||
compile fileTree(dir: 'libs', include: '*.jar')
|
||||
// This shouldn't be necessary; per section 23.4.4 of the Gradle docs:
|
||||
// "file dependencies are included in transitive project dependencies within the same build".
|
||||
compile files('../briar-core/libs/jsocks.jar')
|
||||
|
||||
compile "com.android.support:support-v4:$supportVersion"
|
||||
compile("com.android.support:appcompat-v7:$supportVersion") {
|
||||
@@ -27,16 +24,21 @@ dependencies {
|
||||
exclude module: 'support-v4'
|
||||
exclude module: 'recyclerview-v7'
|
||||
}
|
||||
compile "com.android.support:cardview-v7:$supportVersion"
|
||||
compile 'com.android.support:support-annotations:23.4.0'
|
||||
compile('ch.acra:acra:4.8.5') {
|
||||
exclude module: 'support-v4'
|
||||
exclude module: 'support-annotations'
|
||||
}
|
||||
compile 'info.guardianproject.panic:panic:0.5'
|
||||
compile 'info.guardianproject.trustedintents:trustedintents:0.2'
|
||||
compile 'de.hdodenhof:circleimageview:2.0.0'
|
||||
compile 'de.hdodenhof:circleimageview:2.1.0'
|
||||
compile 'com.google.zxing:core:3.2.1'
|
||||
apt 'com.google.dagger:dagger-compiler:2.0.2'
|
||||
provided 'javax.annotation:jsr250-api:1.0'
|
||||
compile 'com.jpardogo.materialtabstrip:library:1.1.0'
|
||||
compile 'com.github.bumptech.glide:glide:3.7.0'
|
||||
compile 'uk.co.samuelwall:material-tap-target-prompt:1.3.0'
|
||||
|
||||
testCompile 'junit:junit:4.12'
|
||||
testCompile 'net.jodah:concurrentunit:0.4.2'
|
||||
@@ -51,16 +53,20 @@ dependencyVerification {
|
||||
'ch.acra:acra:afd5b28934d5166b55f261c85685ad59e8a4ebe9ca1960906afaa8c76d8dc9eb',
|
||||
'info.guardianproject.panic:panic:a7ed9439826db2e9901649892cf9afbe76f00991b768d8f4c26332d7c9406cb2',
|
||||
'info.guardianproject.trustedintents:trustedintents:6221456d8821a8d974c2acf86306900237cf6afaaa94a4c9c44e161350f80f3e',
|
||||
'de.hdodenhof:circleimageview:c76d936395b50705a3f98c9220c22d2599aeb9e609f559f6048975cfc1f686b8',
|
||||
'de.hdodenhof:circleimageview:bcbc588e19e6dcf8c120b1957776bfe229efba5d2fbe5da7156372eeacf65503',
|
||||
'com.google.zxing:core:b4d82452e7a6bf6ec2698904b332431717ed8f9a850224f295aec89de80f2259',
|
||||
'com.android.support:support-v4:81ce890f26d35c75ad17d0f998a7e3230330c3b41e0b629566bc744bee89e448',
|
||||
'com.android.support:appcompat-v7:00f9d93acacd6731f309724054bf51492814b4b2869f16d7d5c0038dcb8c9a0d',
|
||||
'com.android.support:preference-v14:44881bb46094e86d0bc2426f205419674a5b4eb514b44b5a4659b5de29f71eb7',
|
||||
'com.android.support:design:003e0c0bea0a6891f8b2bc43f20ae7af2a49a17363e5bb10df5ee0bae12fa686',
|
||||
'com.android.support:support-annotations:786ab0d060774fb95cfdaf4878771e14b85733b1af9d72a4aae762dc7c1dff9f',
|
||||
'com.android.support:support-annotations:e91a88dd0c5e99069b7f09d4a46b5e06f1e9c4c72fc0a8e987e25d86af480f01',
|
||||
'com.android.support:animated-vector-drawable:06d1963b85aa917099d7757e6a7b3e4dc06889413dc747f625ae8683606db3a1',
|
||||
'com.android.support:support-vector-drawable:799bafe4c3de812386f0b291f744d5d6876452722dd40189b9ab87dbbf594ea1',
|
||||
'com.android.support:recyclerview-v7:44040a888e23e0c93162a3377cfe06751080e3c22d369ab0d4301ef60d63b0fe',
|
||||
'com.android.support:cardview-v7:4595f1c4a28cfa083b6c0920ad4d49e1c2ca4b8302a955e548f68eb63b74931b',
|
||||
'com.jpardogo.materialtabstrip:library:24d19232b319f8c73e25793432357919a7ed972186f57a3b2c9093ea74ad8311',
|
||||
'com.github.bumptech.glide:glide:76ef123957b5fbaebb05fcbe6606dd58c3bc3fcdadb257f99811d0ac9ea9b88b',
|
||||
'uk.co.samuelwall:material-tap-target-prompt:f67e1caead12a914525b32cbf6da52a96b93ff89573f93cb41102ef3130fb64a',
|
||||
]
|
||||
}
|
||||
|
||||
@@ -119,10 +125,6 @@ android {
|
||||
warning 'MissingTranslation'
|
||||
warning 'ImpliedQuantity'
|
||||
}
|
||||
|
||||
dexOptions {
|
||||
incremental true
|
||||
}
|
||||
}
|
||||
|
||||
task downloadTorGeoIp(type: Download) {
|
||||
@@ -189,8 +191,8 @@ project.afterEvaluate {
|
||||
preBuild.dependsOn {
|
||||
[
|
||||
'verifyTorGeoIp',
|
||||
// 'verifyTorBinaryArm',
|
||||
// 'verifyTorBinaryArmPie',
|
||||
'verifyTorBinaryArm',
|
||||
'verifyTorBinaryArmPie',
|
||||
'verifyTorBinaryX86',
|
||||
'verifyTorBinaryX86Pie'
|
||||
]
|
||||
|
||||
@@ -54,9 +54,18 @@
|
||||
# RSS libraries
|
||||
-keep class com.rometools.rome.feed.synd.impl.** { *;}
|
||||
-keep class com.rometools.rome.io.impl.** { *;}
|
||||
-keep class org.jsoup.safety.Whitelist
|
||||
-dontnote com.rometools.rome.**
|
||||
-dontwarn javax.xml.stream.**
|
||||
-dontwarn org.jaxen.**
|
||||
-dontwarn java.nio.**
|
||||
-dontwarn org.codehaus.mojo.animal_sniffer.**
|
||||
-dontwarn org.slf4j.impl.**
|
||||
|
||||
# Emoji
|
||||
-keep class org.thoughtcrime.securesms.**
|
||||
-keep class com.astuetz.PagerSlidingTabStrip$OnTabReselectedListener
|
||||
-keep public enum com.bumptech.glide.load.resource.bitmap.ImageHeaderParser$** {
|
||||
**[] $VALUES;
|
||||
public *;
|
||||
}
|
||||
|
||||
|
Before Width: | Height: | Size: 1.4 KiB |
|
Before Width: | Height: | Size: 366 B |
|
Before Width: | Height: | Size: 28 KiB After Width: | Height: | Size: 2.1 KiB |
BIN
briar-android/res/drawable-hdpi/msg_in_top.9.png
Normal file
|
After Width: | Height: | Size: 16 KiB |
|
Before Width: | Height: | Size: 28 KiB After Width: | Height: | Size: 2.1 KiB |
BIN
briar-android/res/drawable-hdpi/msg_out_top.9.png
Normal file
|
After Width: | Height: | Size: 16 KiB |
|
Before Width: | Height: | Size: 1.3 KiB |
|
Before Width: | Height: | Size: 28 KiB After Width: | Height: | Size: 2.0 KiB |
BIN
briar-android/res/drawable-hdpi/notice_in_bottom.9.png
Normal file
|
After Width: | Height: | Size: 16 KiB |
|
Before Width: | Height: | Size: 28 KiB After Width: | Height: | Size: 2.0 KiB |
BIN
briar-android/res/drawable-hdpi/notice_out_bottom.9.png
Normal file
|
After Width: | Height: | Size: 16 KiB |
|
Before Width: | Height: | Size: 210 B |
|
Before Width: | Height: | Size: 1.3 KiB |
|
Before Width: | Height: | Size: 175 B |
|
Before Width: | Height: | Size: 27 KiB After Width: | Height: | Size: 1.9 KiB |
BIN
briar-android/res/drawable-mdpi/msg_in_top.9.png
Normal file
|
After Width: | Height: | Size: 16 KiB |
|
Before Width: | Height: | Size: 27 KiB After Width: | Height: | Size: 1.8 KiB |
BIN
briar-android/res/drawable-mdpi/msg_out_top.9.png
Normal file
|
After Width: | Height: | Size: 16 KiB |
|
Before Width: | Height: | Size: 1.2 KiB |
|
Before Width: | Height: | Size: 27 KiB After Width: | Height: | Size: 1.7 KiB |
BIN
briar-android/res/drawable-mdpi/notice_in_bottom.9.png
Normal file
|
After Width: | Height: | Size: 16 KiB |
|
Before Width: | Height: | Size: 27 KiB After Width: | Height: | Size: 1.7 KiB |
BIN
briar-android/res/drawable-mdpi/notice_out_bottom.9.png
Normal file
|
After Width: | Height: | Size: 15 KiB |
|
Before Width: | Height: | Size: 1.5 KiB |
|
Before Width: | Height: | Size: 515 B |
|
Before Width: | Height: | Size: 20 KiB After Width: | Height: | Size: 2.7 KiB |
BIN
briar-android/res/drawable-xhdpi/msg_in_top.9.png
Normal file
|
After Width: | Height: | Size: 16 KiB |
|
Before Width: | Height: | Size: 20 KiB After Width: | Height: | Size: 2.6 KiB |
BIN
briar-android/res/drawable-xhdpi/msg_out_top.9.png
Normal file
|
After Width: | Height: | Size: 18 KiB |
|
Before Width: | Height: | Size: 1.5 KiB |
|
Before Width: | Height: | Size: 19 KiB After Width: | Height: | Size: 2.4 KiB |
BIN
briar-android/res/drawable-xhdpi/notice_in_bottom.9.png
Normal file
|
After Width: | Height: | Size: 16 KiB |
|
Before Width: | Height: | Size: 20 KiB After Width: | Height: | Size: 2.3 KiB |
BIN
briar-android/res/drawable-xhdpi/notice_out_bottom.9.png
Normal file
|
After Width: | Height: | Size: 16 KiB |
|
Before Width: | Height: | Size: 31 KiB After Width: | Height: | Size: 3.1 KiB |
BIN
briar-android/res/drawable-xxhdpi/msg_in_top.9.png
Normal file
|
After Width: | Height: | Size: 17 KiB |
|
Before Width: | Height: | Size: 31 KiB After Width: | Height: | Size: 3.1 KiB |
BIN
briar-android/res/drawable-xxhdpi/msg_out_top.9.png
Normal file
|
After Width: | Height: | Size: 17 KiB |
|
Before Width: | Height: | Size: 20 KiB After Width: | Height: | Size: 3.0 KiB |
BIN
briar-android/res/drawable-xxhdpi/notice_in_bottom.9.png
Normal file
|
After Width: | Height: | Size: 16 KiB |
|
Before Width: | Height: | Size: 20 KiB After Width: | Height: | Size: 2.9 KiB |
BIN
briar-android/res/drawable-xxhdpi/notice_out_bottom.9.png
Normal file
|
After Width: | Height: | Size: 16 KiB |
5
briar-android/res/drawable/alerts_and_states_error.xml
Normal file
@@ -0,0 +1,5 @@
|
||||
<vector android:alpha="0.54" android:height="24dp"
|
||||
android:viewportHeight="24.0" android:viewportWidth="24.0"
|
||||
android:width="24dp" xmlns:android="http://schemas.android.com/apk/res/android">
|
||||
<path android:fillColor="#FF000000" android:pathData="M15.73,3L8.27,3L3,8.27v7.46L8.27,21h7.46L21,15.73L21,8.27L15.73,3zM12,17.3c-0.72,0 -1.3,-0.58 -1.3,-1.3 0,-0.72 0.58,-1.3 1.3,-1.3 0.72,0 1.3,0.58 1.3,1.3 0,0.72 -0.58,1.3 -1.3,1.3zM13,13h-2L11,7h2v6z"/>
|
||||
</vector>
|
||||
17
briar-android/res/drawable/bubble_white.xml
Normal file
@@ -0,0 +1,17 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<shape
|
||||
xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
android:shape="rectangle">
|
||||
|
||||
<corners
|
||||
android:radius="@dimen/unread_bubble_size"/>
|
||||
|
||||
<solid
|
||||
android:color="@color/briar_text_primary_inverse"/>
|
||||
|
||||
<stroke
|
||||
android:color="@color/briar_text_primary"
|
||||
android:width="1dp"/>
|
||||
|
||||
</shape>
|
||||
|
||||
10
briar-android/res/drawable/ic_backspace_black.xml
Normal file
@@ -0,0 +1,10 @@
|
||||
<vector xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
android:width="24dp"
|
||||
android:height="24dp"
|
||||
android:alpha="0.54"
|
||||
android:viewportHeight="24.0"
|
||||
android:viewportWidth="24.0">
|
||||
<path
|
||||
android:fillColor="#FF000000"
|
||||
android:pathData="M22,3L7,3c-0.69,0 -1.23,0.35 -1.59,0.88L0,12l5.41,8.11c0.36,0.53 0.9,0.89 1.59,0.89h15c1.1,0 2,-0.9 2,-2L24,5c0,-1.1 -0.9,-2 -2,-2zM19,15.59L17.59,17 14,13.41 10.41,17 9,15.59 12.59,12 9,8.41 10.41,7 14,10.59 17.59,7 19,8.41 15.41,12 19,15.59z"/>
|
||||
</vector>
|
||||
@@ -1,5 +1,10 @@
|
||||
<vector android:alpha="0.56" android:height="48dp"
|
||||
android:viewportHeight="24.0" android:viewportWidth="24.0"
|
||||
android:width="48dp" xmlns:android="http://schemas.android.com/apk/res/android">
|
||||
<path android:fillColor="#FF000000" android:pathData="M9.01,14L2,14v2h7.01v3L13,15l-3.99,-4v3zM14.99,13v-3L22,10L22,8h-7.01L14.99,5L11,9l3.99,4z"/>
|
||||
<vector xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
android:width="48dp"
|
||||
android:height="48dp"
|
||||
android:alpha="0.54"
|
||||
android:viewportHeight="24.0"
|
||||
android:viewportWidth="24.0">
|
||||
<path
|
||||
android:fillColor="#FF000000"
|
||||
android:pathData="M9.01,14L2,14v2h7.01v3L13,15l-3.99,-4v3zM14.99,13v-3L22,10L22,8h-7.01L14.99,5L11,9l3.99,4z"/>
|
||||
</vector>
|
||||
|
||||
10
briar-android/res/drawable/ic_contacts.xml
Normal file
@@ -0,0 +1,10 @@
|
||||
<vector xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
android:width="24dp"
|
||||
android:height="24dp"
|
||||
android:alpha="0.54"
|
||||
android:viewportHeight="24.0"
|
||||
android:viewportWidth="24.0">
|
||||
<path
|
||||
android:fillColor="#FF000000"
|
||||
android:pathData="M20,0L4,0v2h16L20,0zM4,24h16v-2L4,22v2zM20,4L4,4c-1.1,0 -2,0.9 -2,2v12c0,1.1 0.9,2 2,2h16c1.1,0 2,-0.9 2,-2L22,6c0,-1.1 -0.9,-2 -2,-2zM12,6.75c1.24,0 2.25,1.01 2.25,2.25s-1.01,2.25 -2.25,2.25S9.75,10.24 9.75,9 10.76,6.75 12,6.75zM17,17L7,17v-1.5c0,-1.67 3.33,-2.5 5,-2.5s5,0.83 5,2.5L17,17z"/>
|
||||
</vector>
|
||||
9
briar-android/res/drawable/ic_emoji_activity.xml
Normal file
@@ -0,0 +1,9 @@
|
||||
<vector xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
android:width="24dp"
|
||||
android:height="24dp"
|
||||
android:viewportHeight="24"
|
||||
android:viewportWidth="24">
|
||||
<path
|
||||
android:fillColor="#FF2D3E50"
|
||||
android:pathData="M7.5,7.5C9.17,5.87 11.29,4.69 13.37,4.18C15.46,3.67 17.5,3.83 18.6,4C19.71,4.15 19.87,4.31 20.03,5.41C20.18,6.5 20.33,8.55 19.82,10.63C19.31,12.71 18.13,14.83 16.5,16.5C14.83,18.13 12.71,19.31 10.63,19.82C8.55,20.33 6.5,20.18 5.41,20.03C4.31,19.87 4.15,19.71 4,18.6C3.83,17.5 3.67,15.46 4.18,13.37C4.69,11.29 5.87,9.17 7.5,7.5M7.3,15.79L8.21,16.7L9.42,15.5L10.63,16.7L11.54,15.79L10.34,14.58L12,12.91L13.21,14.12L14.12,13.21L12.91,12L14.58,10.34L15.79,11.54L16.7,10.63L15.5,9.42L16.7,8.21L15.79,7.3L14.58,8.5L13.37,7.3L12.46,8.21L13.66,9.42L12,11.09L10.79,9.88L9.88,10.79L11.09,12L9.42,13.66L8.21,12.46L7.3,13.37L8.5,14.58L7.3,15.79Z"/>
|
||||
</vector>
|
||||
9
briar-android/res/drawable/ic_emoji_animals_nature.xml
Normal file
@@ -0,0 +1,9 @@
|
||||
<vector xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
android:width="24dp"
|
||||
android:height="24dp"
|
||||
android:viewportHeight="24.0"
|
||||
android:viewportWidth="24.0">
|
||||
<path
|
||||
android:fillColor="#FF2D3E50"
|
||||
android:pathData="M18.7,12.4c-0.28,-0.16 -0.57,-0.29 -0.86,-0.4 0.29,-0.11 0.58,-0.24 0.86,-0.4 1.92,-1.11 2.99,-3.12 3,-5.19 -1.79,-1.03 -4.07,-1.11 -6,0 -0.28,0.16 -0.54,0.35 -0.78,0.54 0.05,-0.31 0.08,-0.63 0.08,-0.95 0,-2.22 -1.21,-4.15 -3,-5.19C10.21,1.85 9,3.78 9,6c0,0.32 0.03,0.64 0.08,0.95 -0.24,-0.2 -0.5,-0.39 -0.78,-0.55 -1.92,-1.11 -4.2,-1.03 -6,0 0,2.07 1.07,4.08 3,5.19 0.28,0.16 0.57,0.29 0.86,0.4 -0.29,0.11 -0.58,0.24 -0.86,0.4 -1.92,1.11 -2.99,3.12 -3,5.19 1.79,1.03 4.07,1.11 6,0 0.28,-0.16 0.54,-0.35 0.78,-0.54 -0.05,0.32 -0.08,0.64 -0.08,0.96 0,2.22 1.21,4.15 3,5.19 1.79,-1.04 3,-2.97 3,-5.19 0,-0.32 -0.03,-0.64 -0.08,-0.95 0.24,0.2 0.5,0.38 0.78,0.54 1.92,1.11 4.2,1.03 6,0 -0.01,-2.07 -1.08,-4.08 -3,-5.19zM12,16c-2.21,0 -4,-1.79 -4,-4s1.79,-4 4,-4 4,1.79 4,4 -1.79,4 -4,4z"/>
|
||||
</vector>
|
||||
28
briar-android/res/drawable/ic_emoji_emoticons.xml
Normal file
@@ -0,0 +1,28 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<vector xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
android:width="24dp"
|
||||
android:height="24dp"
|
||||
android:viewportHeight="24"
|
||||
android:viewportWidth="24">
|
||||
|
||||
<path
|
||||
android:fillColor="#FF2D3E50"
|
||||
android:pathData="M15.4839,3.8557 C14.8224,3.89611,14.9476,5.06823,15.4034,5.47978
|
||||
C16.7652,6.93176,17.1508,8.98786,17.299,10.9051
|
||||
C17.4081,13.1214,17.2144,15.4608,16.1275,17.4387
|
||||
C15.7657,18.1699,14.7879,18.7118,14.9747,19.6345
|
||||
C15.2618,20.6719,16.1617,19.8774,16.5955,19.4508
|
||||
C18.5872,17.7088,19.4632,15.0228,19.5268,12.4373
|
||||
C19.5469,10.5193,19.295,8.516,18.3141,6.8329
|
||||
C17.6499,5.74222,16.9234,4.59896,15.8167,3.91355
|
||||
C15.6887,3.86763,15.5784,3.84987,15.4839,3.85564 Z M5.91182,7.65831
|
||||
A1.3631614,1.3631614,0,0,0,4.54866,9.02147
|
||||
A1.3631614,1.3631614,0,0,0,5.91182,10.3846
|
||||
A1.3631614,1.3631614,0,0,0,7.27498,9.02147
|
||||
A1.3631614,1.3631614,0,0,0,5.91182,7.65831 Z M8.98492,10.6595 L8.98492,12.7042
|
||||
L13.756,12.7042 L13.756,10.6595 L8.98494,10.6595 Z M5.83527,14.1306
|
||||
A1.3631614,1.3631614,0,0,0,4.47211,15.4938
|
||||
A1.3631614,1.3631614,0,0,0,5.83527,16.857
|
||||
A1.3631614,1.3631614,0,0,0,7.19843,15.4938
|
||||
A1.3631614,1.3631614,0,0,0,5.83527,14.1306 Z"/>
|
||||
</vector>
|
||||
9
briar-android/res/drawable/ic_emoji_flags.xml
Normal file
@@ -0,0 +1,9 @@
|
||||
<vector xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
android:width="24dp"
|
||||
android:height="24dp"
|
||||
android:viewportHeight="24.0"
|
||||
android:viewportWidth="24.0">
|
||||
<path
|
||||
android:fillColor="#FF2D3E50"
|
||||
android:pathData="M14.4,6L14,4H5v17h2v-7h5.6l0.4,2h7V6z"/>
|
||||
</vector>
|
||||
9
briar-android/res/drawable/ic_emoji_food_drink.xml
Normal file
@@ -0,0 +1,9 @@
|
||||
<vector xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
android:width="24dp"
|
||||
android:height="24dp"
|
||||
android:viewportHeight="24.0"
|
||||
android:viewportWidth="24.0">
|
||||
<path
|
||||
android:fillColor="#FF2D3E50"
|
||||
android:pathData="M12,6c1.11,0 2,-0.9 2,-2 0,-0.38 -0.1,-0.73 -0.29,-1.03L12,0l-1.71,2.97c-0.19,0.3 -0.29,0.65 -0.29,1.03 0,1.1 0.9,2 2,2zM16.6,15.99l-1.07,-1.07 -1.08,1.07c-1.3,1.3 -3.58,1.31 -4.89,0l-1.07,-1.07 -1.09,1.07C6.75,16.64 5.88,17 4.96,17c-0.73,0 -1.4,-0.23 -1.96,-0.61L3,21c0,0.55 0.45,1 1,1h16c0.55,0 1,-0.45 1,-1v-4.61c-0.56,0.38 -1.23,0.61 -1.96,0.61 -0.92,0 -1.79,-0.36 -2.44,-1.01zM18,9h-5L13,7h-2v2L6,9c-1.66,0 -3,1.34 -3,3v1.54c0,1.08 0.88,1.96 1.96,1.96 0.52,0 1.02,-0.2 1.38,-0.57l2.14,-2.13 2.13,2.13c0.74,0.74 2.03,0.74 2.77,0l2.14,-2.13 2.13,2.13c0.37,0.37 0.86,0.57 1.38,0.57 1.08,0 1.96,-0.88 1.96,-1.96L20.99,12C21,10.34 19.66,9 18,9z"/>
|
||||
</vector>
|
||||
9
briar-android/res/drawable/ic_emoji_objects.xml
Normal file
@@ -0,0 +1,9 @@
|
||||
<vector xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
android:width="24dp"
|
||||
android:height="24dp"
|
||||
android:viewportHeight="24"
|
||||
android:viewportWidth="24">
|
||||
<path
|
||||
android:fillColor="#FF2D3E50"
|
||||
android:pathData="M5,16L3,5L8.5,12L12,5L15.5,12L21,5L19,16H5M19,19A1,1 0 0,1 18,20H6A1,1 0 0,1 5,19V18H19V19Z"/>
|
||||
</vector>
|
||||
9
briar-android/res/drawable/ic_emoji_recent.xml
Normal file
@@ -0,0 +1,9 @@
|
||||
<vector xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
android:width="24dp"
|
||||
android:height="24dp"
|
||||
android:viewportHeight="24.0"
|
||||
android:viewportWidth="24.0">
|
||||
<path
|
||||
android:fillColor="#FF2D3E50"
|
||||
android:pathData="M11.99,2C6.47,2 2,6.48 2,12s4.47,10 9.99,10C17.52,22 22,17.52 22,12S17.52,2 11.99,2zM12,20c-4.42,0 -8,-3.58 -8,-8s3.58,-8 8,-8 8,3.58 8,8 -3.58,8 -8,8zM12.5,7H11v6l5.25,3.15 0.75,-1.23 -4.5,-2.67z"/>
|
||||
</vector>
|
||||
9
briar-android/res/drawable/ic_emoji_smiley_people.xml
Normal file
@@ -0,0 +1,9 @@
|
||||
<vector xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
android:width="24dp"
|
||||
android:height="24dp"
|
||||
android:viewportHeight="24.0"
|
||||
android:viewportWidth="24.0">
|
||||
<path
|
||||
android:fillColor="#FF2D3E50"
|
||||
android:pathData="M11.99,2C6.47,2 2,6.48 2,12s4.47,10 9.99,10C17.52,22 22,17.52 22,12S17.52,2 11.99,2zM12,20c-4.42,0 -8,-3.58 -8,-8s3.58,-8 8,-8 8,3.58 8,8 -3.58,8 -8,8zM15.5,11c0.83,0 1.5,-0.67 1.5,-1.5S16.33,8 15.5,8 14,8.67 14,9.5s0.67,1.5 1.5,1.5zM8.5,11c0.83,0 1.5,-0.67 1.5,-1.5S9.33,8 8.5,8 7,8.67 7,9.5 7.67,11 8.5,11zM12,17.5c2.33,0 4.31,-1.46 5.11,-3.5L6.89,14c0.8,2.04 2.78,3.5 5.11,3.5z"/>
|
||||
</vector>
|
||||
9
briar-android/res/drawable/ic_emoji_symbols.xml
Normal file
@@ -0,0 +1,9 @@
|
||||
<vector xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
android:width="24dp"
|
||||
android:height="24dp"
|
||||
android:viewportHeight="24.0"
|
||||
android:viewportWidth="24.0">
|
||||
<path
|
||||
android:fillColor="#FF2D3E50"
|
||||
android:pathData="M12,7.77L18.39,18H5.61L12,7.77M12,4L2,20h20L12,4z"/>
|
||||
</vector>
|
||||
10
briar-android/res/drawable/ic_emoji_toggle.xml
Normal file
@@ -0,0 +1,10 @@
|
||||
<vector xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
android:width="24dp"
|
||||
android:height="24dp"
|
||||
android:alpha="0.54"
|
||||
android:viewportHeight="24.0"
|
||||
android:viewportWidth="24.0">
|
||||
<path
|
||||
android:fillColor="#FF000000"
|
||||
android:pathData="M11.99,2C6.47,2 2,6.48 2,12s4.47,10 9.99,10C17.52,22 22,17.52 22,12S17.52,2 11.99,2zM12,20c-4.42,0 -8,-3.58 -8,-8s3.58,-8 8,-8 8,3.58 8,8 -3.58,8 -8,8zM15.5,11c0.83,0 1.5,-0.67 1.5,-1.5S16.33,8 15.5,8 14,8.67 14,9.5s0.67,1.5 1.5,1.5zM8.5,11c0.83,0 1.5,-0.67 1.5,-1.5S9.33,8 8.5,8 7,8.67 7,9.5 7.67,11 8.5,11zM12,17.5c2.33,0 4.31,-1.46 5.11,-3.5L6.89,14c0.8,2.04 2.78,3.5 5.11,3.5z"/>
|
||||
</vector>
|
||||
9
briar-android/res/drawable/ic_emoji_travel_places.xml
Normal file
@@ -0,0 +1,9 @@
|
||||
<vector xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
android:width="24dp"
|
||||
android:height="24dp"
|
||||
android:viewportHeight="24.0"
|
||||
android:viewportWidth="24.0">
|
||||
<path
|
||||
android:fillColor="#FF2D3E50"
|
||||
android:pathData="M18.92,6.01C18.72,5.42 18.16,5 17.5,5h-11c-0.66,0 -1.21,0.42 -1.42,1.01L3,12v8c0,0.55 0.45,1 1,1h1c0.55,0 1,-0.45 1,-1v-1h12v1c0,0.55 0.45,1 1,1h1c0.55,0 1,-0.45 1,-1v-8l-2.08,-5.99zM6.5,16c-0.83,0 -1.5,-0.67 -1.5,-1.5S5.67,13 6.5,13s1.5,0.67 1.5,1.5S7.33,16 6.5,16zM17.5,16c-0.83,0 -1.5,-0.67 -1.5,-1.5s0.67,-1.5 1.5,-1.5 1.5,0.67 1.5,1.5 -0.67,1.5 -1.5,1.5zM5,11l1.5,-4.5h11L19,11L5,11z"/>
|
||||
</vector>
|
||||
9
briar-android/res/drawable/ic_group_white.xml
Normal file
@@ -0,0 +1,9 @@
|
||||
<vector xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
android:width="24dp"
|
||||
android:height="24dp"
|
||||
android:viewportHeight="24.0"
|
||||
android:viewportWidth="24.0">
|
||||
<path
|
||||
android:fillColor="#FFFFFFFF"
|
||||
android:pathData="M16,11c1.66,0 2.99,-1.34 2.99,-3S17.66,5 16,5c-1.66,0 -3,1.34 -3,3s1.34,3 3,3zM8,11c1.66,0 2.99,-1.34 2.99,-3S9.66,5 8,5C6.34,5 5,6.34 5,8s1.34,3 3,3zM8,13c-2.33,0 -7,1.17 -7,3.5L1,19h14v-2.5c0,-2.33 -4.67,-3.5 -7,-3.5zM16,13c-0.29,0 -0.62,0.02 -0.97,0.05 1.16,0.84 1.97,1.97 1.97,3.45L17,19h6v-2.5c0,-2.33 -4.67,-3.5 -7,-3.5z"/>
|
||||
</vector>
|
||||
9
briar-android/res/drawable/ic_info_white.xml
Normal file
@@ -0,0 +1,9 @@
|
||||
<vector xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
android:width="24dp"
|
||||
android:height="24dp"
|
||||
android:viewportHeight="24.0"
|
||||
android:viewportWidth="24.0">
|
||||
<path
|
||||
android:fillColor="#FFFFFFFF"
|
||||
android:pathData="M11,17h2v-6h-2v6zM12,2C6.48,2 2,6.48 2,12s4.48,10 10,10 10,-4.48 10,-10S17.52,2 12,2zM12,20c-4.41,0 -8,-3.59 -8,-8s3.59,-8 8,-8 8,3.59 8,8 -3.59,8 -8,8zM11,9h2L13,7h-2v2z"/>
|
||||
</vector>
|
||||
10
briar-android/res/drawable/ic_keyboard_black.xml
Normal file
@@ -0,0 +1,10 @@
|
||||
<vector xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
android:width="24dp"
|
||||
android:height="24dp"
|
||||
android:alpha="0.54"
|
||||
android:viewportHeight="24.0"
|
||||
android:viewportWidth="24.0">
|
||||
<path
|
||||
android:fillColor="#FF000000"
|
||||
android:pathData="M20,5L4,5c-1.1,0 -1.99,0.9 -1.99,2L2,17c0,1.1 0.9,2 2,2h16c1.1,0 2,-0.9 2,-2L22,7c0,-1.1 -0.9,-2 -2,-2zM11,8h2v2h-2L11,8zM11,11h2v2h-2v-2zM8,8h2v2L8,10L8,8zM8,11h2v2L8,13v-2zM7,13L5,13v-2h2v2zM7,10L5,10L5,8h2v2zM16,17L8,17v-2h8v2zM16,13h-2v-2h2v2zM16,10h-2L14,8h2v2zM19,13h-2v-2h2v2zM19,10h-2L17,8h2v2z"/>
|
||||
</vector>
|
||||
9
briar-android/res/drawable/ic_more_vert_accent.xml
Normal file
@@ -0,0 +1,9 @@
|
||||
<vector xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
android:width="24dp"
|
||||
android:height="24dp"
|
||||
android:viewportHeight="24.0"
|
||||
android:viewportWidth="24.0">
|
||||
<path
|
||||
android:fillColor="#FF2D3E50"
|
||||
android:pathData="M12,8c1.1,0 2,-0.9 2,-2s-0.9,-2 -2,-2 -2,0.9 -2,2 0.9,2 2,2zM12,10c-1.1,0 -2,0.9 -2,2s0.9,2 2,2 2,-0.9 2,-2 -0.9,-2 -2,-2zM12,16c-1.1,0 -2,0.9 -2,2s0.9,2 2,2 2,-0.9 2,-2 -0.9,-2 -2,-2z"/>
|
||||
</vector>
|
||||
10
briar-android/res/drawable/ic_our_identity_black.xml
Normal file
@@ -0,0 +1,10 @@
|
||||
<vector xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
android:width="16dp"
|
||||
android:height="16dp"
|
||||
android:alpha="0.54"
|
||||
android:viewportHeight="24.0"
|
||||
android:viewportWidth="24.0">
|
||||
<path
|
||||
android:fillColor="#FF000000"
|
||||
android:pathData="M12,5.9c1.16,0 2.1,0.94 2.1,2.1s-0.94,2.1 -2.1,2.1S9.9,9.16 9.9,8s0.94,-2.1 2.1,-2.1m0,9c2.97,0 6.1,1.46 6.1,2.1v1.1L5.9,18.1L5.9,17c0,-0.64 3.13,-2.1 6.1,-2.1M12,4C9.79,4 8,5.79 8,8s1.79,4 4,4 4,-1.79 4,-4 -1.79,-4 -4,-4zM12,13c-2.67,0 -8,1.34 -8,4v3h16v-3c0,-2.66 -5.33,-4 -8,-4z"/>
|
||||
</vector>
|
||||
10
briar-android/res/drawable/ic_visibility.xml
Normal file
@@ -0,0 +1,10 @@
|
||||
<vector xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
android:width="24dp"
|
||||
android:height="24dp"
|
||||
android:alpha="0.54"
|
||||
android:viewportHeight="24.0"
|
||||
android:viewportWidth="24.0">
|
||||
<path
|
||||
android:fillColor="#FF000000"
|
||||
android:pathData="M12,4.5C7,4.5 2.73,7.61 1,12c1.73,4.39 6,7.5 11,7.5s9.27,-3.11 11,-7.5c-1.73,-4.39 -6,-7.5 -11,-7.5zM12,17c-2.76,0 -5,-2.24 -5,-5s2.24,-5 5,-5 5,2.24 5,5 -2.24,5 -5,5zM12,9c-1.66,0 -3,1.34 -3,3s1.34,3 3,3 3,-1.34 3,-3 -1.34,-3 -3,-3z"/>
|
||||
</vector>
|
||||
10
briar-android/res/drawable/ic_visibility_off.xml
Normal file
@@ -0,0 +1,10 @@
|
||||
<vector xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
android:width="24dp"
|
||||
android:height="24dp"
|
||||
android:alpha="0.53"
|
||||
android:viewportHeight="24.0"
|
||||
android:viewportWidth="24.0">
|
||||
<path
|
||||
android:fillColor="#FF000000"
|
||||
android:pathData="M12,7c2.76,0 5,2.24 5,5 0,0.65 -0.13,1.26 -0.36,1.83l2.92,2.92c1.51,-1.26 2.7,-2.89 3.43,-4.75 -1.73,-4.39 -6,-7.5 -11,-7.5 -1.4,0 -2.74,0.25 -3.98,0.7l2.16,2.16C10.74,7.13 11.35,7 12,7zM2,4.27l2.28,2.28 0.46,0.46C3.08,8.3 1.78,10.02 1,12c1.73,4.39 6,7.5 11,7.5 1.55,0 3.03,-0.3 4.38,-0.84l0.42,0.42L19.73,22 21,20.73 3.27,3 2,4.27zM7.53,9.8l1.55,1.55c-0.05,0.21 -0.08,0.43 -0.08,0.65 0,1.66 1.34,3 3,3 0.22,0 0.44,-0.03 0.65,-0.08l1.55,1.55c-0.67,0.33 -1.41,0.53 -2.2,0.53 -2.76,0 -5,-2.24 -5,-5 0,-0.79 0.2,-1.53 0.53,-2.2zM11.84,9.02l3.15,3.15 0.02,-0.16c0,-1.66 -1.34,-3 -3,-3l-0.17,0.01z"/>
|
||||
</vector>
|
||||
9
briar-android/res/drawable/ic_visibility_white.xml
Normal file
@@ -0,0 +1,9 @@
|
||||
<vector xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
android:width="24dp"
|
||||
android:height="24dp"
|
||||
android:viewportHeight="24.0"
|
||||
android:viewportWidth="24.0">
|
||||
<path
|
||||
android:fillColor="#FFFFFFFF"
|
||||
android:pathData="M12,4.5C7,4.5 2.73,7.61 1,12c1.73,4.39 6,7.5 11,7.5s9.27,-3.11 11,-7.5c-1.73,-4.39 -6,-7.5 -11,-7.5zM12,17c-2.76,0 -5,-2.24 -5,-5s2.24,-5 5,-5 5,2.24 5,5 -2.24,5 -5,5zM12,9c-1.66,0 -3,1.34 -3,3s1.34,3 3,3 3,-1.34 3,-3 -1.34,-3 -3,-3z"/>
|
||||
</vector>
|
||||
@@ -4,6 +4,6 @@
|
||||
android:viewportWidth="24.0"
|
||||
android:viewportHeight="24.0">
|
||||
<path
|
||||
android:fillColor="#FF000000"
|
||||
android:pathData="M16.59,8.59L12,13.17 7.41,8.59 6,10l6,6 6,-6z"/>
|
||||
android:fillColor="#FFFFFFFF"
|
||||
android:pathData="M20,4L4,4c-1.1,0 -1.99,0.9 -1.99,2L2,18c0,1.1 0.9,2 2,2h16c1.1,0 2,-0.9 2,-2L22,6c0,-1.1 -0.9,-2 -2,-2zM20,8l-8,5 -8,-5L4,6l8,5 8,-5v2z"/>
|
||||
</vector>
|
||||
@@ -6,5 +6,5 @@
|
||||
android:viewportWidth="24.0">
|
||||
<path
|
||||
android:fillColor="#FF000000"
|
||||
android:pathData="M20,2L4,2c-1.1,0 -1.99,0.9 -1.99,2L2,22l4,-4h14c1.1,0 2,-0.9 2,-2L22,4c0,-1.1 -0.9,-2 -2,-2zM6,9h12v2L6,11L6,9zM14,14L6,14v-2h8v2zM18,8L6,8L6,6h12v2z"/>
|
||||
android:pathData="M9,16.17L4.83,12l-1.42,1.41L9,19 21,7l-1.41,-1.41z"/>
|
||||
</vector>
|
||||