Skip to content

Commit

Permalink
Add basic test-harness prototype
Browse files Browse the repository at this point in the history
  • Loading branch information
Schwartz-Matthew-bah committed Jan 22, 2019
1 parent 7e35539 commit e6f5d6e
Show file tree
Hide file tree
Showing 5 changed files with 116 additions and 0 deletions.
9 changes: 9 additions & 0 deletions test-harness/Dockerfile
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
FROM python:latest

RUN pip3 install requests
RUN pip3 install kafka-python

WORKDIR /home/test-harness
COPY . /home/test-harness

CMD python main.py
102 changes: 102 additions & 0 deletions test-harness/main.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,102 @@
import threading
import requests
import time
import queue
import json
from kafka import KafkaConsumer

class TestCase:
def __init__(self, input, expectedOutput):
self.input = input
self.expectedOutput = expectedOutput

mcin = str(input['tim']['msgCnt'])
mcout = str(expectedOutput['payload']['data']['MessageFrame']['value']['TravelerInformation']['msgCnt'])
assert mcin == mcout, "Message count input and output do not match: input=%s, output=%s" % (mcin, mcout)
self.msgCnt = mcin

def compare(actualOutput):
assert str(self.expectedOutput) == str(actualOutput), "Input file does not match expected output: expected <%s> but got <%s>" % (str(self.expectedOutput), str(actualOutput))

def sendRESTRequest(body):
response=requests.post('https://10.6.180.147:8080/tim', data = body)
print("Response code: " + str(response.status_code))

def listenToKafkaTopic(topic, msgQueue, expectedMsgCount):
print("Listening on topic: " + topic)
consumer=KafkaConsumer(topic, bootstrap_servers="10.6.180.147:9092")
msgsReceived=0
for msg in consumer:
msgsReceived += 1
print(str(msgsReceived))
msgQueue.put(msg)
if msgsReceived >= expectedMsgCount:
return

def createOutputList(fileDict):
outputList=[]
for infile, outfile in fileDict.items():
outfileData=json.load(open(outfile, 'r').read())
outputList.append(outfileData)
return outputList

def findOutputFile(msgCnt, fileDict):
for outfile in fileDict.queue:
if json.loads(outfile.value)['payload']['data']['MessageFrame']['value']['TravelerInformation']['msgCnt'] == msgCnt:
return outfile
return None

def validate(testCaseList, actualMsgQueue):
assert len(testCaseList) == actualMsgQueue.qsize(), "Input list length does not match output list length, input: %d, output: %d" % (len(testCaseList), actualMsgQueue.qsize())
for msg in actualMsgQueue.queue:
# Find corresponding output file
msgCnt=json.loads(msg.value)['payload']['data']['MessageFrame']['value']['TravelerInformation']['msgCnt']
expectedOutputFile=findOutputFile(msgCnt, actualMsgQueue)
assert expectedOutputFile != None, "Unable to find matching output file for input file msgCnt=%s" % str(msgCnt)
assert str(msg) == str(expectedOutputFile), "Input file does not match expected output: expected <%s> but got <%s>" % (str(msg), str(expectedOutputFile))

def main():
print("Test routine started...")
testFileDict={
"tim1_input.json": "tim1_output.json"
}
timBroadcastTopic='topic.J2735TimBroadcastJson'
msgQueue=queue.Queue()

# Create a kafka consumer and wait for it to connect
kafkaListenerThread=threading.Thread(target=listenToKafkaTopic,args=(timBroadcastTopic,msgQueue, len(testFileDict)),)
kafkaListenerThread.start()
time.sleep(5)

# Create test cases
print("Creating test cases...")
tcList = []
for inputFilename, expectedOutputFilename in testFileDict.items():
inputData = json.loads(open(inputFilename, 'r').read())
expectedOutputData = json.loads(open(expectedOutputFilename, 'r').read())
tc = TestCase(inputData, expectedOutputData)
tcList.append(tc)

print("Test cases created.")

# Send test data
for index, testCase in enumerate(tcList, start=1):
print("Sending REST request for test case %d/%d" % (index, len(tcList)))
sendRESTRequest(json.dumps(testCase.input))

# Perform validation
print("Request sending complete.")

print("Waiting for all messages to be received...")
kafkaListenerThread.join()
print("All messages received.")

print("Validating output...")
validate(tcList, msgQueue)
print("Output validated.")

print("All tests have passed")
print("End.")

if __name__ == "__main__":
main()
3 changes: 3 additions & 0 deletions test-harness/run.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
#!/bin/sh
docker build -t ode-test-harness .
docker run ode-test-harness
1 change: 1 addition & 0 deletions test-harness/tim1_input.json
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
{"request": {"rsus": [{"rsuIndex": "9","rsuTarget": "127.0.0.1","rsuUsername": "uuuuuuuu","rsuPassword": "pppppppp","rsuRetries": "1","rsuTimeout": "2500"}],"snmp": {"rsuid": "00000083","msgid": "31","mode": "1","channel": "178","interval": "2","deliverystart": "2018-06-01T17:47:11-05:00","deliverystop": "2019-01-01T17:47:11-05:15","enable": "1","status": "4"}},"tim": {"msgCnt": "1","timeStamp": "2017-03-13T01:07:11-05:00","packetID": "EC9C236B0000000000","urlB": "null","dataframes": [{"sspTimRights": "0","frameType": "advisory","msgId": {"roadSignID": {"position": {"latitude": "42.678473","longitude": "-102.782775","elevation": "912.1432"},"viewAngle": "1010101010101010","mutcdCode": "warning","crc": "F1A7"}},"startDateTime": "2017-12-01T17:47:11-05:00","durationTime": "22","priority": "0","sspLocationRights": "3","regions": [{"name": "bob","regulatorID": "23","segmentID": "33","anchorPosition": {"latitude": "42.278473","longitude": "-102.782775","elevation": "912.1432"},"laneWidth": "7","directionality": "3","closedPath": "false","direction": "1010101010101010","description": "geometry","geometry": {"direction": "1010101010101010","extent": "1","laneWidth": "33","circle": {"position": {"latitude": "42.678473","longitude": "-102.782775","elevation": "912.1432"},"radius": "15","units": "7"}}}],"sspMsgTypes": "2","sspMsgContent": "3","content": "Advisory","items": ["125","some text","250","'98765"],"url": "null"}]}}
1 change: 1 addition & 0 deletions test-harness/tim1_output.json
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
{"metadata":{"request":{"ode":{"verb":"POST","version":3},"rsus":{"rsus":{"rsuTarget":"127.0.0.1","rsuUsername":"uuuuuuuu","rsuRetries":1,"rsuTimeout":2500,"rsuPassword":"*","rsuIndex":9}},"snmp":{"mode":1,"deliverystop":"2019-01-01T17:47:11-05:15","rsuid":"00000083","deliverystart":"2018-06-01T17:47:11-05:00","enable":1,"channel":178,"msgid":31,"interval":2,"status":4}},"recordGeneratedBy":"TMC","schemaVersion":6,"payloadType":"us.dot.its.jpo.ode.model.OdeTimPayload","serialId":{"recordId":0,"serialNumber":42,"streamId":"03965238-88a3-4f2b-a6d9-27501936514f","bundleSize":1,"bundleId":42},"sanitized":false,"recordGeneratedAt":"2017-03-13T06:07:11Z","odeReceivedAt":"2019-01-18T17:12:30.511Z"},"payload":{"data":{"MessageFrame":{"messageId":31,"value":{"TravelerInformation":{"timeStamp":102607,"packetID":"EC9C236B0000000000","urlB":null,"dataFrames":{"TravelerDataFrame":{"regions":{"GeographicalPath":{"closedPath":{"false":""},"anchor":{"elevation":9121,"lat":422784730,"long":-1027827750},"name":"bob","laneWidth":700,"directionality":{"both":""},"description":{"geometry":{"extent":1,"laneWidth":3300,"circle":{"center":{"elevation":9121,"lat":426784730,"long":-1027827750},"units":{"mile":""},"radius":15},"direction":1010101010101010}},"id":{"id":33,"region":23},"direction":1010101010101010}},"duratonTime":22,"sspMsgRights1":2,"sspMsgRights2":3,"startYear":2017,"msgId":{"roadSignID":{"crc":"F1A7","viewAngle":1010101010101010,"mutcdCode":{"warning":""},"position":{"elevation":9121,"lat":426784730,"long":-1027827750}}},"priority":0,"content":{"advisory":{"SEQUENCE":[{"item":{"itis":125}},{"item":{"text":"some text"}},{"item":{"itis":250}},{"item":{"text":98765}}]}},"url":null,"sspTimRights":0,"sspLocationRights":3,"frameType":{"advisory":""},"startTime":482327}},"msgCnt":1}}}},"dataType":"TravelerInformation"}}

0 comments on commit e6f5d6e

Please sign in to comment.