Compare commits
81 Commits
master
...
Voter-Regi
Author | SHA1 | Date |
---|---|---|
Vladimir Eliezer Tokarev | 7fc0af2b1f | |
Vladimir Eliezer Tokarev | 47f68acae4 | |
Vladimir Eliezer Tokarev | 630588ca5b | |
Vladimir Eliezer Tokarev | 53fc701444 | |
Vladimir Eliezer Tokarev | 14d6759803 | |
Vladimir Eliezer Tokarev | 25781f40f7 | |
Vladimir Eliezer Tokarev | 1bf5861808 | |
Vladimir Eliezer Tokarev | 01874f7d1c | |
Vladimir Eliezer Tokarev | 7f39badaf7 | |
Vladimir Eliezer Tokarev | 259b4c2ae5 | |
Vladimir Eliezer Tokarev | f3ec49acc7 | |
Vladimir Eliezer Tokarev | 5398d5adc3 | |
Vladimir Eliezer Tokarev | b8cc12dfc1 | |
Vladimir Eliezer Tokarev | 8140dcd516 | |
Vladimir Eliezer Tokarev | c767d8af58 | |
Vladimir Eliezer Tokarev | 37002a7f1e | |
Vladimir Eliezer Tokarev | b4661d0fed | |
Vladimir Eliezer Tokarev | a9d96e59b2 | |
Vladimir Eliezer Tokarev | 4fac4bbb8c | |
Vladimir Eliezer Tokarev | 6d807cdd4d | |
Vladimir Eliezer Tokarev | 4d72d6083e | |
Vladimir Eliezer Tokarev | da614c13ab | |
Vladimir Eliezer Tokarev | 4b31e87d07 | |
Vladimir Eliezer Tokarev | 2d72822405 | |
Vladimir Eliezer Tokarev | 9828832553 | |
Vladimir Eliezer Tokarev | d9272c9f94 | |
Vladimir Eliezer Tokarev | 9c52eff109 | |
Vladimir Eliezer Tokarev | 6359f74a7b | |
Vladimir Eliezer Tokarev | fea0e8880f | |
Vladimir Eliezer Tokarev | 843d50c276 | |
Vladimir Eliezer Tokarev | 5c4b5a2150 | |
Vladimir Eliezer Tokarev | 687c2c6d7e | |
Vladimir Eliezer Tokarev | 311d1e8e8e | |
Vladimir Eliezer Tokarev | 87420a9d7d | |
Vladimir Eliezer Tokarev | 5169c935bf | |
Vladimir Eliezer Tokarev | 097aad4e7b | |
Vladimir Eliezer Tokarev | 64a9356dc2 | |
Vladimir Eliezer Tokarev | 230dfe6d3f | |
Vladimir Eliezer Tokarev | c8e747285c | |
Vladimir Eliezer Tokarev | 16a3102ca4 | |
Vladimir Eliezer Tokarev | 20d2b3e68c | |
Vladimir Eliezer Tokarev | 6ec0d4a668 | |
Vladimir Eliezer Tokarev | 3347a6c42d | |
Vladimir Eliezer Tokarev | 8c0e7f57bb | |
Vladimir Eliezer Tokarev | 64ccaff508 | |
Vladimir Eliezer Tokarev | 298dd5bf6e | |
Vladimir Eliezer Tokarev | bb4cc5b087 | |
Vladimir Eliezer Tokarev | 91e41af7a0 | |
Vladimir Eliezer Tokarev | 414452db84 | |
Vladimir Eliezer Tokarev | c4177cf487 | |
Vladimir Eliezer Tokarev | 003720839c | |
Vladimir Eliezer Tokarev | 6020ed3ab8 | |
Vladimir Eliezer Tokarev | 68caeee114 | |
Vladimir Eliezer Tokarev | c30ea072f2 | |
Vladimir Eliezer Tokarev | 7a167639db | |
Vladimir Eliezer Tokarev | 01604d1acb | |
Vladimir Eliezer Tokarev | 89bac8d346 | |
Vladimir Eliezer Tokarev | dfc5bf4b24 | |
Vladimir Eliezer Tokarev | 1815863746 | |
Vladimir Eliezer Tokarev | 0d8e522e93 | |
Vladimir Eliezer Tokarev | 4324bdeecd | |
Vladimir Eliezer Tokarev | d4d2d2f5b6 | |
Vladimir Eliezer Tokarev | e75317efa9 | |
Vladimir Eliezer Tokarev | 5971e8c16e | |
Vladimir Eliezer Tokarev | de835a8c13 | |
Vladimir Eliezer Tokarev | 109135ae1b | |
Vladimir Eliezer Tokarev | 7734ba8c91 | |
Vladimir Eliezer Tokarev | 8546a347ca | |
Vladimir Eliezer Tokarev | 65bc8bc160 | |
Vladimir Eliezer Tokarev | 36d94b41ab | |
Vladimir Eliezer Tokarev | 87e8ad9470 | |
Vladimir Eliezer Tokarev | 717c2e6e65 | |
Vladimir Eliezer Tokarev | 51b9f9decd | |
Vladimir Eliezer Tokarev | 05871a2ea7 | |
Vladimir Eliezer Tokarev | 070b851203 | |
Vladimir Eliezer Tokarev | 4aa6c25c0f | |
Vladimir Eliezer Tokarev | 84555f0639 | |
Vladimir Eliezer Tokarev | 42bc35cbe8 | |
Vladimir Eliezer Tokarev | f9d7b4b1ce | |
Vladimir Eliezer Tokarev | 25eefc4b16 | |
Arbel Deutsch Peled | a12685d757 |
|
@ -1,16 +1,20 @@
|
|||
.gradle
|
||||
.idea
|
||||
build
|
||||
bin
|
||||
.settings
|
||||
.classpath
|
||||
.project
|
||||
out
|
||||
*.iml
|
||||
*.ipr
|
||||
*.iws
|
||||
**/*.swp
|
||||
*.prefs
|
||||
*.project
|
||||
*.classpath
|
||||
bulletin-board-server/local-instances/meerkat.db
|
||||
/SQLiteDBTest.db
|
||||
/Wombat Code And Documentation Conventions
|
||||
/bulletin-board-server/trace.db/h2datasource.trace.db
|
||||
/bulletin-board-server/SQLiteDBTest.db
|
||||
.gradle
|
||||
.idea
|
||||
build
|
||||
bin
|
||||
.settings
|
||||
.classpath
|
||||
.project
|
||||
out
|
||||
*.iml
|
||||
*.ipr
|
||||
*.iws
|
||||
**/*.swp
|
||||
*.prefs
|
||||
*.project
|
||||
*.classpath
|
||||
bulletin-board-server/local-instances/meerkat.db
|
||||
|
|
Binary file not shown.
|
@ -1,15 +1,52 @@
|
|||
package meerkat.util;
|
||||
|
||||
import meerkat.protobuf.BulletinBoardAPI.*;
|
||||
import meerkat.crypto.DigitalSignature;
|
||||
import meerkat.protobuf.BulletinBoardAPI.BulletinBoardMessage;
|
||||
import meerkat.protobuf.BulletinBoardAPI.UnsignedBulletinBoardMessage;
|
||||
import meerkat.protobuf.Crypto;
|
||||
|
||||
import java.util.LinkedList;
|
||||
import java.util.List;
|
||||
import java.security.SignatureException;
|
||||
import java.util.*;
|
||||
|
||||
/**
|
||||
* Created by Arbel Deutsch Peled on 16-Feb-16.
|
||||
*/
|
||||
public class BulletinBoardUtils {
|
||||
|
||||
/**
|
||||
* Creates BulletinBoardMessage with UnsignedBulletinBoardMessage and its signature
|
||||
* signed by all given DigitalSignatures
|
||||
*
|
||||
* @param unsignedMessage BasicMessage
|
||||
* @param signer collection of DigitalSignature which will sign the
|
||||
* UnsignedBulletinBoardMessage message
|
||||
* @return BulletinBoardMessage
|
||||
*/
|
||||
public static BulletinBoardMessage signBulletinBoardMessage(UnsignedBulletinBoardMessage unsignedMessage,
|
||||
DigitalSignature signer) throws SignatureException {
|
||||
BulletinBoardMessage.Builder bulletinBoardMessage = BulletinBoardMessage.newBuilder();
|
||||
bulletinBoardMessage.setMsg(unsignedMessage);
|
||||
signer.updateContent(unsignedMessage);
|
||||
Crypto.Signature signature = signer.sign();
|
||||
bulletinBoardMessage.addSig(signature);
|
||||
return bulletinBoardMessage.build();
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the latest message from collection of messages (BulletinBoardMessage) based on timestamp
|
||||
* @param messages List of BulletinBoardMessage
|
||||
* @return BulletinBoardMessage
|
||||
*/
|
||||
public static BulletinBoardMessage getLatestMessage(Collection<BulletinBoardMessage> messages){
|
||||
return Collections.max(messages, new Comparator<BulletinBoardMessage>() {
|
||||
@Override
|
||||
public int compare(BulletinBoardMessage o1, BulletinBoardMessage o2) {
|
||||
TimestampComparator comparator = new TimestampComparator();
|
||||
return comparator.compare(o1.getMsg().getTimestamp(), o2.getMsg().getTimestamp());
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Searches the tags in the message for one that begins with given prefix
|
||||
* @param message is the message to search
|
||||
|
@ -17,7 +54,6 @@ public class BulletinBoardUtils {
|
|||
* @return the tag without the prefix, if found, or null if not found
|
||||
*/
|
||||
public static String findTagWithPrefix(BulletinBoardMessage message, String prefix) {
|
||||
|
||||
for (String tag : message.getMsg().getTagList()){
|
||||
if (tag.startsWith(prefix)) {
|
||||
return tag.substring(prefix.length());
|
||||
|
@ -28,6 +64,22 @@ public class BulletinBoardUtils {
|
|||
|
||||
}
|
||||
|
||||
|
||||
|
||||
/**
|
||||
* Gets list of tags values from given messages (tagName values)
|
||||
* @param messages list of messages from which we want to retrieve specific tag values
|
||||
* @return List<String>
|
||||
*/
|
||||
public static List<String> GetListOfTags(List<BulletinBoardMessage> messages, String tagName) {
|
||||
List<String> tagsValues = new ArrayList<>(messages.size());
|
||||
for ( int i = 0 ; i < messages.size() ; i++ ){
|
||||
BulletinBoardMessage message = messages.get(i);
|
||||
tagsValues.add(findTagWithPrefix(message, tagName));
|
||||
}
|
||||
return tagsValues;
|
||||
}
|
||||
|
||||
/**
|
||||
* Searches the tags in a message for tags that do not contain a given list of prefixes
|
||||
* @param message is the message to search
|
||||
|
|
|
@ -7,7 +7,7 @@ import java.util.Comparator;
|
|||
/**
|
||||
* Created by Arbel Deutsch Peled on 20-Feb-16.
|
||||
*/
|
||||
public class TimestampComparator implements Comparator<com.google.protobuf.Timestamp> {
|
||||
public class TimestampComparator implements Comparator<Timestamp> {
|
||||
|
||||
@Override
|
||||
public int compare(Timestamp o1, Timestamp o2) {
|
||||
|
|
|
@ -0,0 +1,23 @@
|
|||
syntax = "proto3";
|
||||
|
||||
package meerkat;
|
||||
|
||||
option java_package = "meerkat.protobuf";
|
||||
|
||||
message VoterID{
|
||||
string id = 1;
|
||||
}
|
||||
|
||||
message VoterInfo{
|
||||
VoterID id = 1;
|
||||
string info = 2;
|
||||
}
|
||||
|
||||
message GroupID{
|
||||
string id = 1;
|
||||
}
|
||||
|
||||
message VoterRegistryMessage{
|
||||
VoterID voterID = 1;
|
||||
repeated GroupID groupID = 2;
|
||||
}
|
|
@ -1,8 +1,9 @@
|
|||
include 'meerkat-common'
|
||||
include 'voting-booth'
|
||||
include 'bulletin-board-server'
|
||||
include 'polling-station'
|
||||
include 'restful-api-common'
|
||||
include 'bulletin-board-client'
|
||||
include 'distributed-key-generation'
|
||||
|
||||
include 'meerkat-common'
|
||||
include 'voting-booth'
|
||||
include 'voter-registry'
|
||||
include 'bulletin-board-server'
|
||||
include 'polling-station'
|
||||
include 'restful-api-common'
|
||||
include 'bulletin-board-client'
|
||||
include 'distributed-key-generation'
|
||||
|
||||
|
|
|
@ -0,0 +1,4 @@
|
|||
/bin/
|
||||
*.db
|
||||
/src/main/java/meerkat/manualTests.java
|
||||
/.gitignore
|
|
@ -0,0 +1,198 @@
|
|||
|
||||
plugins {
|
||||
id "us.kirchmeier.capsule" version "1.0.1"
|
||||
id 'com.google.protobuf' version '0.7.0'
|
||||
}
|
||||
|
||||
apply plugin: 'java'
|
||||
apply plugin: 'eclipse'
|
||||
apply plugin: 'idea'
|
||||
|
||||
apply plugin: 'maven-publish'
|
||||
|
||||
// Uncomment the lines below to define an application
|
||||
// (this will also allow you to build a "fatCapsule" which includes
|
||||
// the entire application, including all dependencies in a single jar)
|
||||
//apply plugin: 'application'
|
||||
//mainClassName='your.main.ApplicationClass'
|
||||
|
||||
|
||||
// Is this a snapshot version?
|
||||
ext { isSnapshot = false }
|
||||
|
||||
ext {
|
||||
groupId = 'org.factcenter.meerkat'
|
||||
nexusRepository = "https://cs.idc.ac.il/nexus/content/groups/${isSnapshot ? 'unstable' : 'public'}/"
|
||||
|
||||
// Credentials for IDC nexus repositories (needed only for using unstable repositories and publishing)
|
||||
// Should be set in ${HOME}/.gradle/gradle.properties
|
||||
nexusUser = project.hasProperty('nexusUser') ? project.property('nexusUser') : ""
|
||||
nexusPassword = project.hasProperty('nexusPassword') ? project.property('nexusPassword') : ""
|
||||
}
|
||||
|
||||
description = "Meerkat Voter registry application"
|
||||
|
||||
// Your project version
|
||||
version = "0.0"
|
||||
|
||||
version += "${isSnapshot ? '-SNAPSHOT' : ''}"
|
||||
|
||||
|
||||
dependencies {
|
||||
// Meerkat common
|
||||
compile project(':meerkat-common')
|
||||
compile project(':bulletin-board-client')
|
||||
|
||||
// Logging
|
||||
compile 'org.slf4j:slf4j-api:1.7.7'
|
||||
runtime 'ch.qos.logback:logback-classic:1.1.2'
|
||||
runtime 'ch.qos.logback:logback-core:1.1.2'
|
||||
|
||||
// Google protobufs
|
||||
compile 'com.google.protobuf:protobuf-java:3.+'
|
||||
|
||||
// Depend on test resources from meerkat-common
|
||||
testCompile project(path: ':meerkat-common', configuration: 'testOutput')
|
||||
|
||||
testCompile 'junit:junit:4.+'
|
||||
|
||||
runtime 'org.codehaus.groovy:groovy:2.4.+'
|
||||
}
|
||||
|
||||
|
||||
/*==== You probably don't have to edit below this line =======*/
|
||||
|
||||
protobuf {
|
||||
// Configure the protoc executable
|
||||
protoc {
|
||||
// Download from repositories
|
||||
artifact = 'com.google.protobuf:protoc:3.+'
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
idea {
|
||||
module {
|
||||
project.sourceSets.each { sourceSet ->
|
||||
|
||||
def srcDir = "${protobuf.generatedFilesBaseDir}/$sourceSet.name/java"
|
||||
|
||||
// add protobuf generated sources to generated source dir.
|
||||
if ("test".equals(sourceSet.name)) {
|
||||
testSourceDirs += file(srcDir)
|
||||
} else {
|
||||
sourceDirs += file(srcDir)
|
||||
}
|
||||
generatedSourceDirs += file(srcDir)
|
||||
|
||||
}
|
||||
|
||||
// Don't exclude build directory
|
||||
excludeDirs -= file(buildDir)
|
||||
}
|
||||
}
|
||||
|
||||
/*===================================
|
||||
* "Fat" Build targets
|
||||
*===================================*/
|
||||
|
||||
|
||||
if (project.hasProperty('mainClassName') && (mainClassName != null)) {
|
||||
|
||||
task mavenCapsule(type: MavenCapsule) {
|
||||
description = "Generate a capsule jar that automatically downloads and caches dependencies when run."
|
||||
applicationClass mainClassName
|
||||
destinationDir = buildDir
|
||||
}
|
||||
|
||||
task fatCapsule(type: FatCapsule) {
|
||||
description = "Generate a single capsule jar containing everything. Use -Pfatmain=... to override main class"
|
||||
|
||||
destinationDir = buildDir
|
||||
|
||||
def fatMain = hasProperty('fatmain') ? fatmain : mainClassName
|
||||
|
||||
applicationClass fatMain
|
||||
|
||||
def testJar = hasProperty('test')
|
||||
|
||||
if (hasProperty('fatmain')) {
|
||||
appendix = "fat-${fatMain}"
|
||||
} else {
|
||||
appendix = "fat"
|
||||
}
|
||||
|
||||
if (testJar) {
|
||||
from sourceSets.test.output
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/*===================================
|
||||
* Repositories
|
||||
*===================================*/
|
||||
|
||||
repositories {
|
||||
|
||||
// Prefer the local nexus repository (it may have 3rd party artifacts not found in mavenCentral)
|
||||
maven {
|
||||
url nexusRepository
|
||||
|
||||
if (isSnapshot) {
|
||||
credentials { username
|
||||
password
|
||||
|
||||
username nexusUser
|
||||
password nexusPassword
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Use local maven repository
|
||||
mavenLocal()
|
||||
|
||||
// Use 'maven central' for other dependencies.
|
||||
mavenCentral()
|
||||
}
|
||||
|
||||
task "info" << {
|
||||
println "Project: ${project.name}"
|
||||
println "Description: ${project.description}"
|
||||
println "--------------------------"
|
||||
println "GroupId: $groupId"
|
||||
println "Version: $version (${isSnapshot ? 'snapshot' : 'release'})"
|
||||
println ""
|
||||
}
|
||||
info.description 'Print some information about project parameters'
|
||||
|
||||
|
||||
/*===================================
|
||||
* Publishing
|
||||
*===================================*/
|
||||
|
||||
publishing {
|
||||
publications {
|
||||
mavenJava(MavenPublication) {
|
||||
groupId project.groupId
|
||||
pom.withXml {
|
||||
asNode().appendNode('description', project.description)
|
||||
}
|
||||
from project.components.java
|
||||
|
||||
}
|
||||
}
|
||||
repositories {
|
||||
maven {
|
||||
url "https://cs.idc.ac.il/nexus/content/repositories/${project.isSnapshot ? 'snapshots' : 'releases'}"
|
||||
credentials { username
|
||||
password
|
||||
|
||||
username nexusUser
|
||||
password nexusPassword
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
|
@ -0,0 +1 @@
|
|||
../gradlew
|
|
@ -0,0 +1,129 @@
|
|||
package meerkat;
|
||||
|
||||
import com.google.common.util.concurrent.FutureCallback;
|
||||
import meerkat.bulletinboard.SubscriptionAsyncBulletinBoardClient;
|
||||
import meerkat.crypto.DigitalSignature;
|
||||
import meerkat.protobuf.BulletinBoardAPI.UnsignedBulletinBoardMessage;
|
||||
import meerkat.protobuf.VoterRegistry.VoterID;
|
||||
import meerkat.protobuf.VoterRegistry.VoterInfo;
|
||||
import meerkat.protobuf.VoterRegistry.VoterRegistryMessage;
|
||||
import meerkat.registry.AsyncRegistryCallbacks.GetGroupsCallback;
|
||||
import meerkat.registry.AsyncRegistryCallbacks.GetVoterCallback;
|
||||
import meerkat.registry.AsyncRegistryCallbacks.HasVotedCallback;
|
||||
import meerkat.registry.MessageCollectionUtils;
|
||||
import meerkat.registry.RegistryTags;
|
||||
import meerkat.util.BulletinBoardUtils;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.security.SignatureException;
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
import static meerkat.util.BulletinBoardUtils.signBulletinBoardMessage;
|
||||
|
||||
|
||||
// TODO : add ability to use DB of certificates
|
||||
|
||||
/**
|
||||
* Created by Vladimir Eliezer Tokarev on 1/8/2016.
|
||||
* Gives the ability to synchronously manage voters information
|
||||
*/
|
||||
public class AsyncRegistry implements VoterRegistry{
|
||||
|
||||
final Logger logger = LoggerFactory.getLogger(getClass());
|
||||
|
||||
protected DigitalSignature signer;
|
||||
protected SubscriptionAsyncBulletinBoardClient cachedBulletinBoardClient;
|
||||
|
||||
@Override
|
||||
public void init(DigitalSignature signer, SubscriptionAsyncBulletinBoardClient communicator) {
|
||||
logger.debug("Initialized AsyncRegistry: ", new java.util.Date().getTime());
|
||||
this.signer = signer;
|
||||
this.cachedBulletinBoardClient = communicator;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void addVoter(VoterInfo voterInfo, FutureCallback<Boolean> callback) throws SignatureException {
|
||||
UnsignedBulletinBoardMessage basicMessage =
|
||||
UnsignedBulletinBoardMessage.newBuilder()
|
||||
.addTag(RegistryTags.ID_TAG + voterInfo.getId().getId())
|
||||
.addTag(RegistryTags.VOTER_ENTRY_TAG)
|
||||
.setData(voterInfo.toByteString())
|
||||
.setTimestamp(BulletinBoardUtils.getCurrentTimestampProto())
|
||||
.build();
|
||||
|
||||
cachedBulletinBoardClient.postMessage(signBulletinBoardMessage(basicMessage, signer), callback);
|
||||
logger.debug("Added voter : ", RegistryTags.ID_TAG, new java.util.Date().getTime());
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setVoterGroups(VoterRegistryMessage voterRegistryMessage, FutureCallback<Boolean> callback) throws SignatureException, IOException {
|
||||
UnsignedBulletinBoardMessage.Builder basicMessage =
|
||||
UnsignedBulletinBoardMessage.newBuilder()
|
||||
.addTag(RegistryTags.ID_TAG + voterRegistryMessage.getVoterID().getId())
|
||||
.addTag(RegistryTags.ADD_TO_GROUP_TAG)
|
||||
.setData(voterRegistryMessage.toByteString())
|
||||
.setTimestamp(BulletinBoardUtils.getCurrentTimestampProto());
|
||||
|
||||
cachedBulletinBoardClient.postMessage(signBulletinBoardMessage(basicMessage.build(), signer), callback);
|
||||
|
||||
logger.debug("Set voter groups to be : ", new java.util.Date().getTime());
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setVoted(VoterID voterId, FutureCallback<Boolean> callback) throws SignatureException {
|
||||
UnsignedBulletinBoardMessage basicMessage =
|
||||
UnsignedBulletinBoardMessage.newBuilder()
|
||||
.addTag(RegistryTags.ID_TAG + voterId.getId())
|
||||
.addTag(RegistryTags.VOTE_ACTION_TAG)
|
||||
.setTimestamp(BulletinBoardUtils.getCurrentTimestampProto())
|
||||
.build();
|
||||
|
||||
cachedBulletinBoardClient.postMessage(signBulletinBoardMessage(basicMessage, signer), callback);
|
||||
|
||||
logger.debug("Next voter has voted : ", voterId.getId(), new java.util.Date().getTime());
|
||||
}
|
||||
|
||||
@Override
|
||||
public void getGroups(VoterID voterID, FutureCallback<List<meerkat.protobuf.VoterRegistry.GroupID>> callback) {
|
||||
List<String> GroupsActionsTags = new ArrayList<String>(2) {{
|
||||
add(RegistryTags.ADD_TO_GROUP_TAG);
|
||||
add(RegistryTags.ID_TAG + voterID.getId());
|
||||
}};
|
||||
|
||||
cachedBulletinBoardClient.readMessages(MessageCollectionUtils.generateFiltersFromTags(GroupsActionsTags, logger),
|
||||
new GetGroupsCallback(callback));
|
||||
|
||||
logger.debug("Trying to retrieve next user groups : ",
|
||||
voterID.getId(),
|
||||
new java.util.Date().getTime());
|
||||
}
|
||||
|
||||
@Override
|
||||
public void getVoter(VoterID voterID, FutureCallback<VoterInfo> callback) {
|
||||
List<String> addVoterTags = new ArrayList<String>(2) {{
|
||||
add(RegistryTags.ID_TAG + voterID.getId());
|
||||
add(RegistryTags.VOTER_ENTRY_TAG);
|
||||
}};
|
||||
|
||||
cachedBulletinBoardClient.readMessages(MessageCollectionUtils.generateFiltersFromTags(addVoterTags, logger),
|
||||
new GetVoterCallback(callback));
|
||||
|
||||
logger.debug("Trying to retrieve next user information : ", voterID.getId(), new java.util.Date().getTime());
|
||||
}
|
||||
|
||||
@Override
|
||||
public void hasVoted(VoterID voterId, FutureCallback<Boolean> callBack) {
|
||||
List<String> setVotedTags = new ArrayList<String>(2) {{
|
||||
add(RegistryTags.ID_TAG + voterId.getId());
|
||||
add(RegistryTags.VOTE_ACTION_TAG);
|
||||
}};
|
||||
|
||||
cachedBulletinBoardClient.readMessages(MessageCollectionUtils.generateFiltersFromTags(setVotedTags, logger),
|
||||
new HasVotedCallback(callBack));
|
||||
|
||||
logger.debug("Trying to check if next has voted : ", voterId.getId(), new java.util.Date().getTime());
|
||||
}
|
||||
}
|
|
@ -0,0 +1,91 @@
|
|||
package meerkat;
|
||||
|
||||
import com.google.common.util.concurrent.FutureCallback;
|
||||
import meerkat.bulletinboard.SubscriptionAsyncBulletinBoardClient;
|
||||
import meerkat.crypto.DigitalSignature;
|
||||
import meerkat.protobuf.VoterRegistry.VoterID;
|
||||
import meerkat.protobuf.VoterRegistry.VoterInfo;
|
||||
import meerkat.protobuf.VoterRegistry.VoterRegistryMessage;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.security.SignatureException;
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* Created by Vladimir Eliezer Tokarev on 1/22/2016.
|
||||
* provides voters management options
|
||||
*/
|
||||
public interface VoterRegistry {
|
||||
|
||||
/**
|
||||
* Initialize the voter registry
|
||||
* @param signer object which sign the outputed message
|
||||
* @param communicator the object which communicates with the BulletinBoardServer
|
||||
*/
|
||||
void init(DigitalSignature signer, SubscriptionAsyncBulletinBoardClient communicator);
|
||||
|
||||
/**
|
||||
* Adds new voter to the bulletin-board
|
||||
* Passes true to callback.OnSuccess if the actions succeeded else
|
||||
* call the onFailure method of the callback with the arisen error
|
||||
*
|
||||
* @param voterInfo protobuff object that represents voter information
|
||||
* @param callBack when the adding voter done callback.OnSuccess will be called
|
||||
* @throws SignatureException
|
||||
*/
|
||||
void addVoter(VoterInfo voterInfo, FutureCallback<Boolean> callBack) throws SignatureException;
|
||||
|
||||
/**
|
||||
* Adding given voter to given group
|
||||
* Passes the group to callback.OnSuccess if the actions succeeded else
|
||||
* call the onFailure method of the callback with the arisen error
|
||||
*
|
||||
* @param voterRegistryMessage protobuff object that is coupling of voterId to groupId
|
||||
* @param callBack when the adding voter done callback.OnSuccess will be called
|
||||
* @throws SignatureException
|
||||
* @throws IOException
|
||||
*/
|
||||
void setVoterGroups(VoterRegistryMessage voterRegistryMessage, FutureCallback<Boolean> callBack) throws SignatureException, IOException;
|
||||
|
||||
/**
|
||||
* Sets that the voter have voted
|
||||
* Passes true to callback.OnSuccess if the actions succeeded else
|
||||
* call the onFailure method of the callback with the arisen error
|
||||
*
|
||||
* @param voterId protobuff object that represent the voter that have voted
|
||||
* @param callBack when the adding voter done callback.OnSuccess will be called
|
||||
* @throws SignatureException
|
||||
*/
|
||||
void setVoted(VoterID voterId, FutureCallback<Boolean> callBack) throws SignatureException;
|
||||
|
||||
/**
|
||||
* Requests all the groups that the given id voter is in
|
||||
* Passes wanted groups to callback.handleResult if the actions succeeded else
|
||||
* call the onFailure method of the callback with the arisen error
|
||||
*
|
||||
* @param voterID protobuff object that represent the voter
|
||||
* @param callBack when the adding voter done callback.OnSuccess will be called
|
||||
*/
|
||||
void getGroups(VoterID voterID, FutureCallback<List<meerkat.protobuf.VoterRegistry.GroupID>> callBack);
|
||||
|
||||
/**
|
||||
* Retrieves VoterInfo protobuff that represents voter
|
||||
* Passes wanted data to callback.handleResult if the actions succeeded else
|
||||
* call the onFailure method of the callback with the arisen error
|
||||
*
|
||||
* @param voterID protobuff object that represent the voter
|
||||
* @param callBack when the adding voter done callback.OnSuccess will be called
|
||||
*/
|
||||
void getVoter(VoterID voterID, FutureCallback<VoterInfo> callBack);
|
||||
|
||||
/**
|
||||
* Checks if the given voter (by his id) have already voted
|
||||
* passes true of the voter have been voted or not else
|
||||
* call the onFailure method of the callback with the arisen error
|
||||
*
|
||||
* @param voterID protobuff object that represent the voter
|
||||
* @param callBack method that will be called with the when the result will be found
|
||||
*/
|
||||
void hasVoted(VoterID voterID, FutureCallback<Boolean> callBack);
|
||||
}
|
||||
|
|
@ -0,0 +1,76 @@
|
|||
package meerkat.registry.AsyncRegistryCallbacks;
|
||||
|
||||
import com.google.common.util.concurrent.FutureCallback;
|
||||
import javassist.NotFoundException;
|
||||
import meerkat.protobuf.BulletinBoardAPI.BulletinBoardMessage;
|
||||
import meerkat.protobuf.VoterRegistry;
|
||||
import meerkat.registry.RegistryTags;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.util.List;
|
||||
|
||||
import static meerkat.util.BulletinBoardUtils.findTagWithPrefix;
|
||||
import static meerkat.util.BulletinBoardUtils.getLatestMessage;
|
||||
|
||||
|
||||
/**
|
||||
* Created by Vladimir Eliezer on 3/12/2016.
|
||||
* AsyncRegistry getGroups creates this callback to list of groups the voter in
|
||||
*/
|
||||
public class GetGroupsCallback implements FutureCallback<List<BulletinBoardMessage>> {
|
||||
protected FutureCallback<List<VoterRegistry.GroupID>> callback;
|
||||
final Logger logger = LoggerFactory.getLogger(getClass());
|
||||
|
||||
public GetGroupsCallback(FutureCallback<List<VoterRegistry.GroupID>> callback){
|
||||
this.callback = callback;
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets List of GroupId objects from given message
|
||||
* @param message BulletinBoardMessage which contains all groups ids of voter
|
||||
* @return list of GroupId
|
||||
* @throws IOException
|
||||
* @throws ClassNotFoundException
|
||||
*/
|
||||
private List<VoterRegistry.GroupID> getVoterGroups(BulletinBoardMessage message) throws IOException, ClassNotFoundException {
|
||||
logger.debug("Initialized GetGroupsCallback : ", new java.util.Date().getTime());
|
||||
VoterRegistry.VoterRegistryMessage voterRegistryMessage =
|
||||
VoterRegistry.VoterRegistryMessage.parseFrom(message.getMsg().getData());
|
||||
|
||||
return voterRegistryMessage.getGroupIDList();
|
||||
}
|
||||
|
||||
|
||||
@Override
|
||||
public void onSuccess(List<BulletinBoardMessage> messages) {
|
||||
if (messages.isEmpty()){
|
||||
callback.onFailure(new NotFoundException("Voter permissions not found in database"));
|
||||
return;
|
||||
}
|
||||
|
||||
BulletinBoardMessage message = getLatestMessage(messages);
|
||||
try {
|
||||
|
||||
logger.debug("Wanted voter groups been retrieved: ",
|
||||
findTagWithPrefix(message, RegistryTags.ID_TAG),
|
||||
new java.util.Date().getTime());
|
||||
|
||||
callback.onSuccess(getVoterGroups(message));
|
||||
} catch (IOException | ClassNotFoundException e) {
|
||||
logger.error("Error occurred while trying to get voter groups ",
|
||||
new java.util.Date().getTime(),
|
||||
e);
|
||||
callback.onFailure(e);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onFailure(Throwable t) {
|
||||
logger.error("Error occurred while trying to get voter groups ",
|
||||
new java.util.Date().getTime(),
|
||||
t);
|
||||
this.callback.onFailure(t);
|
||||
}
|
||||
}
|
|
@ -0,0 +1,47 @@
|
|||
package meerkat.registry.AsyncRegistryCallbacks;
|
||||
|
||||
import com.google.common.util.concurrent.FutureCallback;
|
||||
import meerkat.protobuf.BulletinBoardAPI.BulletinBoardMessage;
|
||||
import meerkat.registry.RegistryTags;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
import static meerkat.util.BulletinBoardUtils.findTagWithPrefix;
|
||||
|
||||
|
||||
/**
|
||||
* Created by Vladimir Eliezer Tokarev on 3/12/2016.
|
||||
* AsyncRegistry hasVoted creates this callback to check if wanted user has voted
|
||||
*/
|
||||
public class HasVotedCallback implements FutureCallback<List<BulletinBoardMessage>>{
|
||||
protected FutureCallback<Boolean> callback;
|
||||
final Logger logger = LoggerFactory.getLogger(getClass());
|
||||
|
||||
public HasVotedCallback(FutureCallback<Boolean> callback){
|
||||
logger.debug("Initialized HasVotedCallback : ", new java.util.Date().getTime());
|
||||
this.callback = callback;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onSuccess(List<BulletinBoardMessage> messages) {
|
||||
if (messages.isEmpty()){
|
||||
callback.onSuccess(false);
|
||||
return;
|
||||
}
|
||||
|
||||
logger.debug("The next voter has voted: ",
|
||||
findTagWithPrefix(messages.get(0), RegistryTags.ID_TAG),
|
||||
new java.util.Date().getTime());
|
||||
callback.onSuccess(true);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onFailure(Throwable t) {
|
||||
logger.error("Error occurred while trying to check if voter has voted: ",
|
||||
new java.util.Date().getTime(),
|
||||
t);
|
||||
this.callback.onFailure(t);
|
||||
}
|
||||
}
|
|
@ -0,0 +1,60 @@
|
|||
package meerkat.registry.AsyncRegistryCallbacks;
|
||||
|
||||
import com.google.common.util.concurrent.FutureCallback;
|
||||
import com.google.protobuf.InvalidProtocolBufferException;
|
||||
import javassist.NotFoundException;
|
||||
import meerkat.protobuf.BulletinBoardAPI.BulletinBoardMessage;
|
||||
import meerkat.protobuf.VoterRegistry;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
import static meerkat.util.BulletinBoardUtils.getLatestMessage;
|
||||
|
||||
|
||||
/**
|
||||
* Created by Vladimir Eliezer on 3/12/2016.
|
||||
* AsyncRegistry getVoter creates this callback to get voterInfo protobuff
|
||||
*/
|
||||
public class GetVoterCallback implements FutureCallback<List<BulletinBoardMessage>> {
|
||||
protected FutureCallback<VoterRegistry.VoterInfo> callback;
|
||||
final Logger logger = LoggerFactory.getLogger(getClass());
|
||||
|
||||
public GetVoterCallback(FutureCallback<VoterRegistry.VoterInfo> callback){
|
||||
logger.debug("Initialized GetVoterCallback : ", new java.util.Date().getTime());
|
||||
this.callback = callback;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onSuccess(List<BulletinBoardMessage> messages) {
|
||||
if(messages.isEmpty()){
|
||||
callback.onFailure(new NotFoundException("Voter info not found in database."));
|
||||
return;
|
||||
}
|
||||
BulletinBoardMessage latestMessage = getLatestMessage(messages);
|
||||
|
||||
try {
|
||||
VoterRegistry.VoterInfo info = VoterRegistry.VoterInfo.newBuilder()
|
||||
.mergeFrom(latestMessage.getMsg().getData()).build();
|
||||
|
||||
logger.debug("Wanted voter information: ", info.getId().getId(), info.getInfo(),
|
||||
new java.util.Date().getTime());
|
||||
|
||||
callback.onSuccess(info);
|
||||
} catch (InvalidProtocolBufferException e) {
|
||||
logger.error("Error occurred while trying to get voter information: ",
|
||||
new java.util.Date().getTime(),
|
||||
e);
|
||||
callback.onFailure(e);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onFailure(Throwable t) {
|
||||
logger.error("Error occurred while trying to get voter information:",
|
||||
new java.util.Date().getTime(),
|
||||
t);
|
||||
callback.onFailure(t);
|
||||
}
|
||||
}
|
|
@ -0,0 +1,40 @@
|
|||
package meerkat.registry;
|
||||
|
||||
import com.sun.deploy.util.StringUtils;
|
||||
import meerkat.protobuf.BulletinBoardAPI.FilterType;
|
||||
import meerkat.protobuf.BulletinBoardAPI.MessageFilter;
|
||||
import meerkat.protobuf.BulletinBoardAPI.MessageFilterList;
|
||||
import org.slf4j.Logger;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
|
||||
/**
|
||||
* Created by Vladimir Eliezer Tokarev on 1/15/2016.
|
||||
* adds extra functionality to Messages collections
|
||||
*/
|
||||
public abstract class MessageCollectionUtils {
|
||||
/**
|
||||
* Creates list of filters based on given list of strings (that are tags)
|
||||
*
|
||||
* @param logger logger object with debug method
|
||||
* @param tags the tags based on which the messages will be filtered
|
||||
* @return MessageFilterList.
|
||||
*/
|
||||
public static MessageFilterList generateFiltersFromTags(List<String> tags, Logger logger) {
|
||||
if (tags == null){
|
||||
return MessageFilterList.getDefaultInstance();
|
||||
}
|
||||
|
||||
MessageFilterList.Builder filters = MessageFilterList.newBuilder();
|
||||
|
||||
for (String tag : tags) {
|
||||
MessageFilter filter = MessageFilter.newBuilder().setTag(tag).setType(FilterType.TAG).build();
|
||||
filters.addFilter(filter);
|
||||
}
|
||||
|
||||
logger.debug("Converted next strings to filters", StringUtils.join(tags, " "));
|
||||
|
||||
return filters.build();
|
||||
}
|
||||
}
|
|
@ -0,0 +1,18 @@
|
|||
package meerkat.registry;
|
||||
|
||||
|
||||
/**
|
||||
* Created by Vladimir Eliezer Tokarev on 1/9/2016.
|
||||
* Have the tags for the registry messages
|
||||
*/
|
||||
public interface RegistryTags {
|
||||
public static final String ID_TAG = "ID: ";
|
||||
public static final String VOTER_ENTRY_TAG = "VoterEntry: ";
|
||||
public static final String GROUP_ID_TAG = "GroupID: ";
|
||||
public static final String ADD_TO_GROUP_TAG = "setVoterGroups: ";
|
||||
public static final String VOTE_ACTION_TAG = "VoteAction: ";
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
|
@ -0,0 +1,508 @@
|
|||
import com.google.common.util.concurrent.FutureCallback;
|
||||
import meerkat.AsyncRegistry;
|
||||
import meerkat.bulletinboard.BulletinBoardServer;
|
||||
import meerkat.bulletinboard.LocalBulletinBoardClient;
|
||||
import meerkat.bulletinboard.sqlserver.BulletinBoardSQLServer;
|
||||
import meerkat.bulletinboard.sqlserver.H2QueryProvider;
|
||||
import meerkat.comm.CommunicationException;
|
||||
import meerkat.crypto.DigitalSignature;
|
||||
import meerkat.crypto.concrete.ECDSASignature;
|
||||
import meerkat.protobuf.BulletinBoardAPI.BulletinBoardMessage;
|
||||
import meerkat.protobuf.BulletinBoardAPI.MessageFilterList;
|
||||
import meerkat.protobuf.VoterRegistry;
|
||||
import meerkat.protobuf.VoterRegistry.GroupID;
|
||||
import meerkat.protobuf.VoterRegistry.VoterID;
|
||||
import meerkat.protobuf.VoterRegistry.VoterInfo;
|
||||
import meerkat.registry.MessageCollectionUtils;
|
||||
import meerkat.registry.RegistryTags;
|
||||
import org.junit.Before;
|
||||
import org.junit.Test;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.io.InputStream;
|
||||
import java.math.BigInteger;
|
||||
import java.security.KeyStore;
|
||||
import java.security.SecureRandom;
|
||||
import java.security.SignatureException;
|
||||
import java.sql.Connection;
|
||||
import java.sql.SQLException;
|
||||
import java.sql.Statement;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Date;
|
||||
import java.util.List;
|
||||
import java.util.concurrent.Semaphore;
|
||||
|
||||
import static junit.framework.TestCase.assertEquals;
|
||||
import static junit.framework.TestCase.assertTrue;
|
||||
import static meerkat.util.BulletinBoardUtils.*;
|
||||
|
||||
/**
|
||||
* TODO: add logs prints for the tests to be clear what they are
|
||||
*/
|
||||
|
||||
/**
|
||||
* Created by Vladimir Eliezer Tokarev on 1/16/2016.
|
||||
* Tests the Simple registry contents
|
||||
* NOTE: for most of this tests to pass there should run BulletinBoardServer
|
||||
* that should be reachable on BULLETIN_BOARD_SERVER_ADDRESS
|
||||
*/
|
||||
public class SimpleRegistryTest {
|
||||
|
||||
private DigitalSignature signer;
|
||||
private LocalBulletinBoardClient localBulletinBoardClient;
|
||||
private SecureRandom random = new SecureRandom();
|
||||
Semaphore jobSemaphore;
|
||||
|
||||
public static String KEYFILE_EXAMPLE = "/certs/enduser-certs/user1-key-with-password-secret.p12";
|
||||
public static String CERT1_PEM_EXAMPLE = "/certs/enduser-certs/user1.crt";
|
||||
public static String KEYFILE_PASSWORD = "secret";
|
||||
private static final String DB_NAME = "TestDB";
|
||||
private static final int SUBSCRIPTION_DELAY = 3000;
|
||||
private static final int THREAD_NUM = 3;
|
||||
final Logger logger = LoggerFactory.getLogger(getClass());
|
||||
|
||||
class DummyRegistryCallBackHandler<T> implements FutureCallback<T>{
|
||||
public int counter;
|
||||
public T data;
|
||||
|
||||
public DummyRegistryCallBackHandler()
|
||||
{
|
||||
counter=0;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onSuccess(T result) {
|
||||
counter++;
|
||||
data = result;
|
||||
jobSemaphore.release();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onFailure(Throwable throwable) {
|
||||
System.out.print(throwable.toString());
|
||||
}
|
||||
}
|
||||
|
||||
public class DummyBulletinBoardCallBackHandler implements FutureCallback<List<BulletinBoardMessage>> {
|
||||
public List<BulletinBoardMessage> messages;
|
||||
|
||||
@Override
|
||||
public void onSuccess(List<BulletinBoardMessage> msg)
|
||||
{
|
||||
messages = msg;
|
||||
jobSemaphore.release();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onFailure(Throwable t){
|
||||
messages = null;
|
||||
jobSemaphore.release();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates LocalBulletinBoardClient which connects to TestDB
|
||||
* @return LocalBulletinBoardClient object
|
||||
* @throws CommunicationException
|
||||
*/
|
||||
private LocalBulletinBoardClient CreateLocalBulletinBoardClient() throws CommunicationException, SQLException {
|
||||
H2QueryProvider queryProvider = new H2QueryProvider(DB_NAME) ;
|
||||
|
||||
Connection conn = queryProvider.getDataSource().getConnection();
|
||||
Statement stmt = conn.createStatement();
|
||||
|
||||
List<String> deletionQueries = queryProvider.getSchemaDeletionCommands();
|
||||
|
||||
for (String deletionQuery : deletionQueries) {
|
||||
stmt.execute(deletionQuery);
|
||||
}
|
||||
|
||||
BulletinBoardServer server = new BulletinBoardSQLServer(queryProvider);
|
||||
server.init(DB_NAME);
|
||||
|
||||
logger.debug("Created new LocalBulletinBoardClient: {}", new Date());
|
||||
|
||||
return new LocalBulletinBoardClient(server, THREAD_NUM, SUBSCRIPTION_DELAY);
|
||||
}
|
||||
|
||||
/**
|
||||
* Initialize CachedBulletinBoardClient client that communicates with LocalBulletinBoardClient
|
||||
* @throws InstantiationException
|
||||
* @throws IllegalAccessException
|
||||
* @throws CommunicationException
|
||||
* @throws SQLException
|
||||
*/
|
||||
private void CommunicatorSetup() throws InstantiationException, IllegalAccessException, CommunicationException, SQLException {
|
||||
localBulletinBoardClient = CreateLocalBulletinBoardClient();
|
||||
}
|
||||
|
||||
/**
|
||||
* Sets the signer to be instance of ECDSASignature
|
||||
*/
|
||||
private void SetSigner(){
|
||||
try {
|
||||
ECDSASignature signer = new ECDSASignature();
|
||||
InputStream keyStream = getClass().getResourceAsStream(KEYFILE_EXAMPLE);
|
||||
char[] password = KEYFILE_PASSWORD.toCharArray();
|
||||
|
||||
KeyStore.Builder keyStore = signer.getPKCS12KeyStoreBuilder(keyStream, password);
|
||||
signer.loadSigningCertificate(keyStore);
|
||||
signer.loadVerificationCertificates(getClass().getResourceAsStream(CERT1_PEM_EXAMPLE));
|
||||
|
||||
keyStream.close();
|
||||
this.signer = signer;
|
||||
logger.info("Have set new signer: {}", new Date());
|
||||
}
|
||||
catch (Exception e){
|
||||
assert false : "The signers creation failed ";
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Initializes the needed params for all the tests
|
||||
* @throws SQLException
|
||||
* @throws InstantiationException
|
||||
* @throws CommunicationException
|
||||
* @throws IllegalAccessException
|
||||
*/
|
||||
@Before
|
||||
public void setUp() throws SQLException, InstantiationException, CommunicationException, IllegalAccessException {
|
||||
SetSigner();
|
||||
CommunicatorSetup();
|
||||
jobSemaphore = new Semaphore(0);
|
||||
logger.info("Ended the setup preparations: {}", new Date());
|
||||
}
|
||||
|
||||
private AsyncRegistry GetRegistry()
|
||||
{
|
||||
AsyncRegistry registry = new AsyncRegistry();
|
||||
registry.init(signer, localBulletinBoardClient);
|
||||
logger.info("Created new AsyncRegistry: {}", new Date());
|
||||
return registry;
|
||||
}
|
||||
|
||||
/**
|
||||
* Generates random string 32 chars length
|
||||
* @return String object
|
||||
*/
|
||||
private String generateString()
|
||||
{
|
||||
return new BigInteger(130, random).toString(32);
|
||||
}
|
||||
|
||||
/**
|
||||
* Checks if the creation of the registry have been successful
|
||||
*/
|
||||
@Test
|
||||
public void simpleRegistryCreation() {
|
||||
try {
|
||||
logger.info("Testing registry creation: {}", new Date());
|
||||
GetRegistry();
|
||||
logger.info("Registry creation succeed: {} \n\n", new Date());
|
||||
} catch (Exception e) {
|
||||
assert false : "While creating the registry exception have been thrown " + e;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Counts the amount of messages from messages that have all the wanted tags inside
|
||||
* @param messages List<VoterRegistryMessage>
|
||||
* @param tags List<RegistryTags>
|
||||
* @return integer that represent the amount of messages with wanted tags
|
||||
*/
|
||||
private int countMessagesWithTags(List<BulletinBoardMessage> messages, List<String> tags)
|
||||
{
|
||||
int counter = 0 ;
|
||||
|
||||
for (BulletinBoardMessage message : messages) {
|
||||
int wantedTagsCounter = 0;
|
||||
|
||||
for (String tag : tags) {
|
||||
if(findTagWithPrefix(message, tag)!=null){
|
||||
wantedTagsCounter++;
|
||||
}
|
||||
}
|
||||
|
||||
if(wantedTagsCounter == tags.size())
|
||||
{
|
||||
counter++;
|
||||
}
|
||||
}
|
||||
logger.info("Counted {} messages with all wanted tags from {} given messages: {}",
|
||||
counter,
|
||||
messages.size(),
|
||||
new Date());
|
||||
return counter;
|
||||
}
|
||||
|
||||
/**
|
||||
* Reads messages from localBulletinBoardClient by given tags and return the callback handler
|
||||
* object
|
||||
*
|
||||
* @param tags list of strings that represents tags
|
||||
* @return DummyBulletinBoardCallBackHandler which method will be called
|
||||
*/
|
||||
private DummyBulletinBoardCallBackHandler readMessagesByTags(List<String> tags)
|
||||
{
|
||||
MessageFilterList filters = MessageCollectionUtils.generateFiltersFromTags(tags, logger);
|
||||
DummyBulletinBoardCallBackHandler bulletinHandler = new DummyBulletinBoardCallBackHandler();
|
||||
localBulletinBoardClient.readMessages(filters, bulletinHandler);
|
||||
return bulletinHandler;
|
||||
}
|
||||
|
||||
/**
|
||||
* Test that add voter creates new correct bulletin board message and adds the voter
|
||||
*/
|
||||
@Test
|
||||
public void testAddVoter() throws InterruptedException, SignatureException {
|
||||
logger.info("Testing registry adding voter functionality: {}", new Date());
|
||||
|
||||
DummyRegistryCallBackHandler<Boolean> handler = new DummyRegistryCallBackHandler<>();
|
||||
|
||||
String id = generateString();
|
||||
String data = generateString();
|
||||
VoterInfo voterInfo = VoterInfo.newBuilder().setId(VoterID.newBuilder().setId(id)).setInfo(data).build();
|
||||
|
||||
AsyncRegistry registry = GetRegistry();
|
||||
registry.addVoter(voterInfo, handler);
|
||||
logger.info("Tried to add next voter to registry: id: {} {}",
|
||||
voterInfo.getId().getId(),
|
||||
new Date());
|
||||
|
||||
jobSemaphore.acquire();
|
||||
assertEquals(1, handler.counter );
|
||||
|
||||
List<String> tags = new ArrayList<String>(){{ add(RegistryTags.VOTER_ENTRY_TAG);}};
|
||||
DummyBulletinBoardCallBackHandler bulletinHandler = readMessagesByTags(tags);
|
||||
|
||||
|
||||
jobSemaphore.acquire();
|
||||
logger.info("Got add voter messages that have been added lately to the server: {} {}",
|
||||
GetListOfTags(bulletinHandler.messages, RegistryTags.ID_TAG),
|
||||
new Date());
|
||||
|
||||
tags.clear();
|
||||
tags.add(RegistryTags.ID_TAG + id);
|
||||
|
||||
int counter = countMessagesWithTags(bulletinHandler.messages, tags);
|
||||
assert counter == 1 : "The server don't have the new user data.";
|
||||
logger.info("The server had a message with voter data: id: {} data: {} {}", id, data, new Date());
|
||||
logger.info("Ended testing registry adding voter functionality: {}\n\n", new Date());
|
||||
}
|
||||
|
||||
/**
|
||||
* Test that set voted posts creates correct bulletin board message and sets that the user have been voted
|
||||
*/
|
||||
@Test
|
||||
public void testSetVoted() throws InterruptedException, SignatureException {
|
||||
logger.info("Testing registry set voted functionality: {}", new Date());
|
||||
DummyRegistryCallBackHandler<Boolean> handler = new DummyRegistryCallBackHandler<>();
|
||||
|
||||
String id = generateString();
|
||||
VoterID voterInfo = VoterID.newBuilder().setId(id).build();
|
||||
|
||||
AsyncRegistry registry = GetRegistry();
|
||||
registry.setVoted(voterInfo, handler);
|
||||
logger.info("Tried to set that next voter voted : id: {} {}",
|
||||
voterInfo.getId(),
|
||||
new Date());
|
||||
|
||||
jobSemaphore.acquire();
|
||||
assertEquals(1, handler.counter );
|
||||
|
||||
List<String> tags = new ArrayList<String>(){{ add(RegistryTags.VOTE_ACTION_TAG);}};
|
||||
DummyBulletinBoardCallBackHandler bulletinHandler = readMessagesByTags(tags);
|
||||
|
||||
jobSemaphore.acquire();
|
||||
logger.info("Got set voted messages that have been added lately to the server: {} {} ",
|
||||
GetListOfTags(bulletinHandler.messages, RegistryTags.ID_TAG),
|
||||
new Date());
|
||||
|
||||
tags.clear();
|
||||
tags.add(RegistryTags.ID_TAG + id);
|
||||
|
||||
int counter = countMessagesWithTags(bulletinHandler.messages, tags);
|
||||
assert counter == 1 : "The server don't have the new user id.";
|
||||
logger.info("The server had a message with voter data: id: {} {}", id, new Date());
|
||||
logger.info("Ended testing registry set voted functionality: {}\n\n", new Date());
|
||||
}
|
||||
|
||||
/**
|
||||
* Test that get groups retrieves the right groups the user are in
|
||||
*/
|
||||
@Test
|
||||
public void testSetVoterGroups() throws InterruptedException, SignatureException, IOException, ClassNotFoundException {
|
||||
logger.info("Testing registry set voter groups functionality: {}", new Date());
|
||||
|
||||
DummyRegistryCallBackHandler<Boolean> handler = new DummyRegistryCallBackHandler<>();
|
||||
|
||||
String voterId = generateString();
|
||||
String groupId1 = generateString();
|
||||
VoterRegistry.VoterRegistryMessage voterInfo = VoterRegistry.VoterRegistryMessage.newBuilder()
|
||||
.setVoterID(VoterID.newBuilder().setId(voterId))
|
||||
.addGroupID(GroupID.newBuilder().setId(groupId1)).build();
|
||||
|
||||
AsyncRegistry registry = GetRegistry();
|
||||
registry.setVoterGroups(voterInfo, handler);
|
||||
logger.info("Tried to set voter groups : id: {} groupId: {} {}",
|
||||
voterId,
|
||||
groupId1,
|
||||
new Date());
|
||||
|
||||
jobSemaphore.acquire();
|
||||
assertEquals("The callback handler hasn't been called yet", 1, handler.counter);
|
||||
|
||||
List<String> tags = new ArrayList<String>(){{add(RegistryTags.ADD_TO_GROUP_TAG);
|
||||
add(RegistryTags.ID_TAG + voterId);}};
|
||||
DummyBulletinBoardCallBackHandler bulletinHandler = readMessagesByTags(tags);
|
||||
|
||||
jobSemaphore.acquire();
|
||||
logger.info("Got set voter groups messages that have been added lately to the server: {} {} ",
|
||||
GetListOfTags(bulletinHandler.messages, RegistryTags.ID_TAG),
|
||||
new Date());
|
||||
|
||||
BulletinBoardMessage latestMessage = getLatestMessage(bulletinHandler.messages);
|
||||
|
||||
assert findTagWithPrefix(latestMessage, RegistryTags.ID_TAG).equals(voterId) :
|
||||
"The latest message recieved is not of our voter";
|
||||
|
||||
logger.info("The server had a message of our voter, data: id: {} {}",
|
||||
findTagWithPrefix(latestMessage, RegistryTags.ID_TAG), new Date());
|
||||
|
||||
VoterRegistry.VoterRegistryMessage voterRegistryMessage =
|
||||
VoterRegistry.VoterRegistryMessage.parseFrom(latestMessage.getMsg().getData());
|
||||
|
||||
List<GroupID> groupsIds = voterRegistryMessage.getGroupIDList();
|
||||
|
||||
assert groupsIds.get(0).getId().equals(groupId1) : "The latest message doesn't have the voter group";
|
||||
logger.info("The server had a message with voter data: groupId: {} {}",
|
||||
groupsIds.get(0).getId(), new Date());
|
||||
logger.info("Ended testing registry set voter groups functionality: {}\n\n", new Date());
|
||||
}
|
||||
|
||||
/**
|
||||
* Test that remove from group creates correct bulletin board message and removes the user from a group
|
||||
*/
|
||||
@Test
|
||||
public void testGetGroups() throws InterruptedException, SignatureException, IOException {
|
||||
logger.info("Testing registry get voter groups functionality: {}", new Date());
|
||||
DummyRegistryCallBackHandler<Boolean> handler =
|
||||
new DummyRegistryCallBackHandler<>();
|
||||
|
||||
String voterId = generateString();
|
||||
String groupId1 = generateString();
|
||||
String groupId2 = generateString();
|
||||
VoterRegistry.VoterRegistryMessage voterInfo = VoterRegistry.VoterRegistryMessage.newBuilder()
|
||||
.setVoterID(VoterID.newBuilder().setId(voterId))
|
||||
.addGroupID(GroupID.newBuilder().setId(groupId1))
|
||||
.addGroupID(GroupID.newBuilder().setId(groupId2)).build();
|
||||
|
||||
AsyncRegistry registry = GetRegistry();
|
||||
registry.setVoterGroups(voterInfo, handler);
|
||||
logger.info("Tried to set voter groups : id: {} groupId 1: {} groupId 2: {} {}",
|
||||
voterId,
|
||||
groupId1,
|
||||
groupId2,
|
||||
new Date());
|
||||
|
||||
jobSemaphore.acquire();
|
||||
assertEquals("The callback handler hasn't been called yet", 1, handler.counter );
|
||||
|
||||
DummyRegistryCallBackHandler<List<GroupID>> groupsHandler = new DummyRegistryCallBackHandler<>();
|
||||
registry.getGroups(VoterID.newBuilder().setId(voterId).build(), groupsHandler);
|
||||
|
||||
jobSemaphore.acquire(1);
|
||||
List<GroupID> userGroups = groupsHandler.data;
|
||||
|
||||
logger.info("Got get voter groups messages that have been added lately to the server: {}",
|
||||
new Date());
|
||||
|
||||
assert userGroups.contains(GroupID.newBuilder().setId(groupId1).build()) :
|
||||
"The simple voter registry object does not retrieved the first user groups";
|
||||
|
||||
assert userGroups.contains(GroupID.newBuilder().setId(groupId2).build()) :
|
||||
"The simple voter registry object does not retrieved the second user groups";
|
||||
|
||||
logger.info("The server had a message with wanted data: groupId 1: {} groupId 2: {} {}",
|
||||
groupId1, groupId2, new Date());
|
||||
logger.info("Ended testing registry get voter groups functionality: {}\n\n", new Date());
|
||||
}
|
||||
|
||||
/**
|
||||
* Test that the personal data outputted about the user is right
|
||||
*/
|
||||
@Test
|
||||
public void testGetVoter() throws InterruptedException, SignatureException {
|
||||
logger.info("Testing registry get voter groups functionality: {}", new Date());
|
||||
DummyRegistryCallBackHandler<Boolean> handler =
|
||||
new DummyRegistryCallBackHandler<>();
|
||||
|
||||
String id = generateString();
|
||||
String data = generateString();
|
||||
VoterInfo voterInfo = VoterInfo.newBuilder().
|
||||
setId(VoterID.newBuilder().setId(id)).setInfo(data).build();
|
||||
|
||||
AsyncRegistry registry = GetRegistry();
|
||||
registry.addVoter(voterInfo, handler);
|
||||
|
||||
logger.info("Tried to get voter with data: id: {} groupId 1: {} groupId 2: {} {}",
|
||||
id, data, new Date());
|
||||
|
||||
jobSemaphore.acquire();
|
||||
assertEquals("The callback handler hasn't been called yet", 1, handler.counter );
|
||||
|
||||
DummyRegistryCallBackHandler<VoterInfo> personalHandler = new DummyRegistryCallBackHandler<>();
|
||||
registry.getVoter(VoterID.newBuilder().setId(id).build(), personalHandler);
|
||||
|
||||
jobSemaphore.acquire(1);
|
||||
|
||||
logger.info("Got get voter messages that have been added lately to the server: {} {}",
|
||||
personalHandler.data.getId(),
|
||||
new Date());
|
||||
|
||||
assertEquals("The voter id doesn't match the created on ",
|
||||
id, personalHandler.data.getId().getId());
|
||||
String personalData = personalHandler.data.getInfo();
|
||||
assertTrue("The voter personal data can't be found.", data.equals(personalData));
|
||||
|
||||
logger.info("The server had a message with wanted data: if: {} personal data: {} {}",
|
||||
personalHandler.data.getId().getId(), personalData, new Date());
|
||||
logger.info("Ended testing registry get voter functionality: {}\n\n", new Date());
|
||||
}
|
||||
|
||||
/**
|
||||
* Tests that the hasVoted method of registry works
|
||||
* @throws InterruptedException
|
||||
*/
|
||||
@Test
|
||||
public void testHasVoted () throws InterruptedException, SignatureException {
|
||||
logger.info("Testing registry has voted functionality: {}", new Date());
|
||||
|
||||
DummyRegistryCallBackHandler<Boolean> handler = new DummyRegistryCallBackHandler<>();
|
||||
String id = generateString();
|
||||
VoterID voterInfo = VoterID.newBuilder().setId(id).build();
|
||||
|
||||
AsyncRegistry registry = GetRegistry();
|
||||
registry.setVoted(voterInfo, handler);
|
||||
|
||||
logger.info("Tried to set voted with data: id: {} groupId 1: {} {}",
|
||||
id, new Date());
|
||||
|
||||
jobSemaphore.acquire();
|
||||
assertEquals("The callback handler hasn't been called yet", 1, handler.counter);
|
||||
DummyRegistryCallBackHandler<Boolean> personalHandler = new DummyRegistryCallBackHandler<>();
|
||||
registry.hasVoted(VoterID.newBuilder().setId(id).build(), personalHandler);
|
||||
|
||||
jobSemaphore.acquire(1);
|
||||
|
||||
logger.info("Got has voted messages that have been added lately to the server: {} {}",
|
||||
personalHandler.data,
|
||||
new Date());
|
||||
assertTrue("The voter hasn't voted yet.", personalHandler.data);
|
||||
|
||||
logger.info("Ended testing registry has voted functionality: {}\n\n", new Date());
|
||||
}
|
||||
}
|
||||
|
Loading…
Reference in New Issue