import com.google.protobuf.InvalidProtocolBufferException; import junit.framework.TestCase; import meerkat.RegistryMessages; import meerkat.SimpleRegistry; import meerkat.VoterRegistry; import meerkat.VoterRegistryMessage; import meerkat.bulletinboard.BulletinBoardClient; import meerkat.bulletinboard.ThreadedBulletinBoardClient; import meerkat.crypto.concrete.ECDSASignature; import meerkat.protobuf.BulletinBoardAPI; import meerkat.protobuf.Voting; import util.RegistryTags; import java.io.InputStream; import java.math.BigInteger; import java.security.KeyStore; import java.security.SecureRandom; import java.util.ArrayList; import java.util.List; import java.util.concurrent.Semaphore; import static util.CollectionMessagesUtils.ConvertToVoterRegistryMessages; /** * TODO: Have to do more relevant prints (print what happens) * TODO: repair all the other methods */ /** * 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 extends TestCase { private ECDSASignature signer; private BulletinBoardClient communicator; private SecureRandom random = new SecureRandom(); public static String KEYFILE_EXAMPLE = "/certs/enduser-certs/user1-key-with-password-secret.p12"; public static String KEYFILE_PASSWORD = "secret"; Semaphore jobSemaphore; class DummyRegistryCallBackHandler implements VoterRegistry.RegistryCallBack{ public int counter; public T data; public DummyRegistryCallBackHandler() { counter=0; } @Override public void HandleResult(T result) { counter++; data = result; jobSemaphore.release(); } } public class DummyBulletinBoardCallBackHandler implements BulletinBoardClient.ClientCallback> { public List messages; @Override public void handleCallback(List msg) { messages = msg; jobSemaphore.release(); } @Override public void handleFailure(Throwable t) throws Throwable { messages = null; jobSemaphore.release(); throw t; } } /** * Creates the communication object (the bulletinBoardClient) */ private void CommunicatorSetup() { communicator = new ThreadedBulletinBoardClient(); String BULLETIN_BOARD_SERVER_ADDRESS = "http://localhost:8081"; communicator.init(Voting.BulletinBoardClientParams.newBuilder() .addBulletinBoardAddress(BULLETIN_BOARD_SERVER_ADDRESS) .setMinRedundancy((float) 1.0) .build()); } /** * Creates the signer object which is the ECDSASignature */ private void SetSigner(){ try { signer = new ECDSASignature(); InputStream keyStream = getClass().getResourceAsStream(KEYFILE_EXAMPLE); char[] password = KEYFILE_PASSWORD.toCharArray(); KeyStore.Builder keyStore = signer.getPKCS12KeyStoreBuilder(keyStream, password); signer.loadSigningCertificate(keyStore); keyStream.close(); } catch (Exception e){ assert false : "The signer creation failed "; } } /** * Initialize SimpleRegistry object */ public void setUp() { SetSigner(); CommunicatorSetup(); jobSemaphore = new Semaphore(0); } /** * Checks if the creation of the registry have been successful */ public void testSimpleRegistryCreation() { try { new SimpleRegistry(signer, communicator); } catch (Exception e) { assert false : "While creating the SimpleRegistry exception have been thrown " + e; } } /** * Counts the amount of messages from messages that have all the wanted tags inside * @param messages List * @param tags List * @return integer that represent the amount of messages with wanted tags */ private int countMessagesWithTags(List messages, List tags) { int counter = 0 ; for (VoterRegistryMessage message :messages) { int wantedTagsCounter = 0; for (String tag : tags) { if(message.GetWantedTagFromBasicMessage(tag)!=null){ wantedTagsCounter++; } } if(wantedTagsCounter == tags.size()) { counter++; } } return counter; } /** * Test that add voter creates new correct bulletin board message and adds the voter */ public void testAddVoter() throws InvalidProtocolBufferException, InterruptedException { DummyRegistryCallBackHandler handler = new DummyRegistryCallBackHandler<>(); RegistryMessages.VoterInfo voterInfo = RegistryMessages.VoterInfo.newBuilder(). setId(RegistryMessages.VoterID.newBuilder() .setId(new BigInteger(130, random).toString(32))) .setInfo(new BigInteger(130, random).toString(32)).build(); SimpleRegistry registry = new SimpleRegistry(signer, communicator); registry.AddVoter(voterInfo, handler); jobSemaphore.acquire(); assertEquals(handler.counter , 1); List tags = new ArrayList(){{ add(RegistryTags.VOTER_ENTRY_TAG.toString());}}; BulletinBoardAPI.MessageFilterList filters = registry.GetRelevantMessagesFilters(tags); DummyBulletinBoardCallBackHandler bulletinHandler = new DummyBulletinBoardCallBackHandler(); communicator.readMessages(filters, bulletinHandler); jobSemaphore.acquire(); int counter = countMessagesWithTags(ConvertToVoterRegistryMessages(bulletinHandler.messages), tags); assert counter == 1 : "The server don't have the new user data."; } /** * Test that set voted posts creates correct bulletin board message and sets that the user have been voted */ public void testSetVoted() throws InvalidProtocolBufferException, InterruptedException { DummyRegistryCallBackHandler handler = new DummyRegistryCallBackHandler<>(); RegistryMessages.VoterID voterInfo = RegistryMessages.VoterID.newBuilder() .setId(new BigInteger(130, random).toString(32)).build(); SimpleRegistry registry = new SimpleRegistry(signer, communicator); registry.SetVoted(voterInfo, handler); jobSemaphore.acquire(); assertEquals(handler.counter , 0); List tags = new ArrayList(){{ add(RegistryTags.VOTE_ACTION_TAG.toString());}}; BulletinBoardAPI.MessageFilterList filters = registry.GetRelevantMessagesFilters(tags); DummyBulletinBoardCallBackHandler bulletinHandler = new DummyBulletinBoardCallBackHandler(); communicator.readMessages(filters, bulletinHandler); jobSemaphore.acquire(); int counter = countMessagesWithTags(ConvertToVoterRegistryMessages(bulletinHandler.messages), tags); assert counter == 1 : "The server don't have the new user id."; } /** * Test that get groups retrieves the right groups the user are in */ public void testAddToGroup() throws InvalidProtocolBufferException, InterruptedException { DummyRegistryCallBackHandler handler = new DummyRegistryCallBackHandler<>(); RegistryMessages.VoterGroup voterInfo = RegistryMessages.VoterGroup.newBuilder() .setVoterId(RegistryMessages.VoterID.newBuilder() .setId((new BigInteger(130, random).toString(32)))) .setGroupId(RegistryMessages.GroupID.newBuilder() .setId((new BigInteger(130, random).toString(32)))).build(); SimpleRegistry registry = new SimpleRegistry(signer, communicator); registry.AddToGroup(voterInfo, handler); jobSemaphore.acquire(); assertEquals(handler.counter , 0); List tags = new ArrayList(){{ add(RegistryTags.GROUP_ACTION_TAG .toString() + RegistryTags.ADD_TO_GROUP_TAG.toString());}}; BulletinBoardAPI.MessageFilterList filters = registry.GetRelevantMessagesFilters(tags); DummyBulletinBoardCallBackHandler bulletinHandler = new DummyBulletinBoardCallBackHandler(); communicator.readMessages(filters, bulletinHandler); jobSemaphore.acquire(); int counter = countMessagesWithTags(ConvertToVoterRegistryMessages(bulletinHandler.messages), tags); assert counter == 1 : "The server don't have the new user added to group."; } /** * Test that remove from group creates correct bulletin board message and removes the user from a group */ public void testGetGroups() throws InvalidProtocolBufferException, InterruptedException { DummyRegistryCallBackHandler> handler = new DummyRegistryCallBackHandler<>(); RegistryMessages.VoterGroup voterInfo = RegistryMessages.VoterGroup.newBuilder() .setVoterId(RegistryMessages.VoterID.newBuilder() .setId((new BigInteger(130, random).toString(32)))) .setGroupId(RegistryMessages.GroupID.newBuilder() .setId((new BigInteger(130, random).toString(32)))).build(); SimpleRegistry registry = new SimpleRegistry(signer, communicator); registry.AddToGroup(voterInfo, handler); jobSemaphore.acquire(); assertEquals(handler.counter , 0); List tags = new ArrayList(){{ add(RegistryTags.GROUP_ACTION_TAG .toString() + RegistryTags.ADD_TO_GROUP_TAG.toString());}}; BulletinBoardAPI.MessageFilterList filters = registry.GetRelevantMessagesFilters(tags); DummyBulletinBoardCallBackHandler bulletinHandler = new DummyBulletinBoardCallBackHandler(); communicator.readMessages(filters, bulletinHandler); jobSemaphore.acquire(); List voterMessages = ConvertToVoterRegistryMessages(handler.data); assertTrue(voterMessages.get(0).GetWantedTagFromBasicMessage(RegistryTags.ID_TAG.toString()).contains(voterInfo.getVoterId().getId())); } /** * Test that the personal data outputted about the user is right */ public void testGetPersonalIDDetails() throws InvalidProtocolBufferException, InterruptedException { DummyRegistryCallBackHandler> handler = new DummyRegistryCallBackHandler<>(); String id = new BigInteger(130, random).toString(32); String data = new BigInteger(130, random).toString(32); RegistryMessages.VoterInfo voterInfo = RegistryMessages.VoterInfo.newBuilder(). setId(RegistryMessages.VoterID.newBuilder().setId(id)).setInfo(data).build(); SimpleRegistry registry = new SimpleRegistry(signer, communicator); registry.AddVoter(voterInfo, handler); jobSemaphore.acquire(); assertEquals(handler.counter , 0); List tags = new ArrayList(){{ add(RegistryTags.VOTER_ENTRY_TAG.toString());}}; BulletinBoardAPI.MessageFilterList filters = registry.GetRelevantMessagesFilters(tags); DummyBulletinBoardCallBackHandler bulletinHandler = new DummyBulletinBoardCallBackHandler(); communicator.readMessages(filters, bulletinHandler); jobSemaphore.acquire(); List voterMessages = ConvertToVoterRegistryMessages(handler.data); int counter = countMessagesWithTags(voterMessages, new ArrayList(){{add(id);add(data);}}); assert counter == 1 : "The method doesnt retreived the wanted information."; } }