Start Release branch for 5.1.0

This commit is contained in:
jamesagnew
2020-05-29 10:26:09 -04:00
parent 0430a539ff
commit 8aa322caf1
12 changed files with 286 additions and 117 deletions

View File

@@ -1,6 +1,8 @@
package ca.uhn.fhir.jpa.starter;
import ca.uhn.fhir.context.FhirVersionEnum;
import ca.uhn.fhir.jpa.empi.config.EmpiConsumerConfig;
import ca.uhn.fhir.jpa.empi.config.EmpiSubmitterConfig;
import ca.uhn.fhir.jpa.subscription.channel.config.SubscriptionChannelConfig;
import ca.uhn.fhir.jpa.subscription.match.config.SubscriptionProcessorConfig;
import ca.uhn.fhir.jpa.subscription.match.config.WebsocketDispatcherConfig;
@@ -28,13 +30,19 @@ public class ApplicationContext extends AnnotationConfigWebApplicationContext {
}
if (HapiProperties.getSubscriptionEmailEnabled()
|| HapiProperties.getSubscriptionRestHookEnabled()
|| HapiProperties.getSubscriptionWebsocketEnabled()) {
|| HapiProperties.getSubscriptionRestHookEnabled()
|| HapiProperties.getSubscriptionWebsocketEnabled()) {
register(SubscriptionSubmitterConfig.class);
register(SubscriptionProcessorConfig.class);
register(SubscriptionChannelConfig.class);
}
if (HapiProperties.getEmpiEnabled()) {
register(EmpiSubmitterConfig.class);
register(EmpiConsumerConfig.class);
register(EmpiConfig.class);
}
}
}

View File

@@ -0,0 +1,23 @@
package ca.uhn.fhir.jpa.starter;
import ca.uhn.fhir.empi.api.IEmpiSettings;
import ca.uhn.fhir.empi.rules.config.EmpiSettings;
import com.google.common.base.Charsets;
import org.apache.commons.io.IOUtils;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.core.io.DefaultResourceLoader;
import org.springframework.core.io.Resource;
import java.io.IOException;
@Configuration
public class EmpiConfig {
@Bean
IEmpiSettings empiSettings() throws IOException {
DefaultResourceLoader resourceLoader = new DefaultResourceLoader();
Resource resource = resourceLoader.getResource("empi-rules.json");
String json = IOUtils.toString(resource.getInputStream(), Charsets.UTF_8);
return new EmpiSettings().setEnabled(HapiProperties.getEmpiEnabled()).setScriptText(json);
}
}

View File

@@ -10,7 +10,6 @@ import ca.uhn.fhir.jpa.subscription.match.deliver.email.IEmailSender;
import ca.uhn.fhir.jpa.subscription.match.deliver.email.JavaMailEmailSender;
import org.apache.commons.dbcp2.BasicDataSource;
import org.hl7.fhir.dstu2.model.Subscription;
import org.springframework.beans.factory.BeanFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
@@ -25,7 +24,7 @@ import java.sql.Driver;
* This is the primary configuration file for the example server
*/
@Configuration
@EnableTransactionManagement()
@EnableTransactionManagement
public class FhirServerConfigCommon {
private static final org.slf4j.Logger ourLog = org.slf4j.LoggerFactory.getLogger(FhirServerConfigCommon.class);
@@ -198,11 +197,10 @@ public class FhirServerConfigCommon {
retVal.setSmtpServerPort(this.emailPort);
retVal.setSmtpServerUsername(this.emailUsername);
retVal.setSmtpServerPassword(this.emailPassword);
// TODO KHS add these when HAPI 4.2.0 is released
// retVal.setAuth(this.emailAuth);
// retVal.setStartTlsEnable(this.emailStartTlsEnable);
// retVal.setStartTlsRequired(this.emailStartTlsRequired);
// retVal.setQuitWait(this.emailQuitWait);
retVal.setAuth(this.emailAuth);
retVal.setStartTlsEnable(this.emailStartTlsEnable);
retVal.setStartTlsRequired(this.emailStartTlsRequired);
retVal.setQuitWait(this.emailQuitWait);
SubscriptionDeliveryHandlerFactory subscriptionDeliveryHandlerFactory = myAppCtx.getBean(SubscriptionDeliveryHandlerFactory.class);
Validate.notNull(subscriptionDeliveryHandlerFactory, "No subscription delivery handler");

View File

@@ -57,6 +57,11 @@ public class HapiProperties {
static final String SUBSCRIPTION_EMAIL_ENABLED = "subscription.email.enabled";
static final String SUBSCRIPTION_RESTHOOK_ENABLED = "subscription.resthook.enabled";
static final String SUBSCRIPTION_WEBSOCKET_ENABLED = "subscription.websocket.enabled";
static final String EMPI_ENABLED = "empi.enabled";
static final String PARTITIONING_ENABLED = "partitioning.enabled";
static final String PARTITIONING_CROSS_PARTITION_REFERENCE_MODE = "partitioning.cross_partition_reference_mode";
private static final String PARTITIONING_INCLUDE_PARTITION_IN_SEARCH_HASHES = "partitioning.partitioning_include_in_search_hashes";
static final String ALLOWED_BUNDLE_TYPES = "allowed_bundle_types";
static final String TEST_PORT = "test.port";
static final String TESTER_CONFIG_REFUSE_TO_FETCH_THIRD_PARTY_URLS = "tester.config.refuse_to_fetch_third_party_urls";
@@ -373,6 +378,22 @@ public class HapiProperties {
return HapiProperties.getBooleanProperty(SUBSCRIPTION_WEBSOCKET_ENABLED, false);
}
public static Boolean getEmpiEnabled() {
return HapiProperties.getBooleanProperty(EMPI_ENABLED, false);
}
public static Boolean getPartitioningEnabled() {
return HapiProperties.getBooleanProperty(PARTITIONING_ENABLED, false);
}
public static String getPartitioningCrossPartitionReferenceMode() {
return HapiProperties.getProperty(PARTITIONING_CROSS_PARTITION_REFERENCE_MODE, "NOT_ALLOWED");
}
public static Boolean getIncludePartitionInSearchHashes() {
return HapiProperties.getBooleanProperty(PARTITIONING_INCLUDE_PARTITION_IN_SEARCH_HASHES, true);
}
public static Boolean getAllowContainsSearches() {
return HapiProperties.getBooleanProperty(ALLOW_CONTAINS_SEARCHES, true);
}

View File

@@ -7,10 +7,11 @@ import ca.uhn.fhir.interceptor.api.IInterceptorService;
import ca.uhn.fhir.jpa.api.config.DaoConfig;
import ca.uhn.fhir.jpa.api.dao.DaoRegistry;
import ca.uhn.fhir.jpa.api.dao.IFhirSystemDao;
import ca.uhn.fhir.jpa.api.rp.ResourceProviderFactory;
import ca.uhn.fhir.jpa.binstore.BinaryStorageInterceptor;
import ca.uhn.fhir.jpa.bulk.BulkDataExportProvider;
import ca.uhn.fhir.jpa.interceptor.CascadingDeleteInterceptor;
import ca.uhn.fhir.jpa.model.config.PartitionSettings;
import ca.uhn.fhir.jpa.partition.PartitionManagementProvider;
import ca.uhn.fhir.jpa.provider.GraphQLProvider;
import ca.uhn.fhir.jpa.provider.JpaConformanceProviderDstu2;
import ca.uhn.fhir.jpa.provider.JpaSystemProviderDstu2;
@@ -35,6 +36,7 @@ import ca.uhn.fhir.rest.server.interceptor.LoggingInterceptor;
import ca.uhn.fhir.rest.server.interceptor.RequestValidatingInterceptor;
import ca.uhn.fhir.rest.server.interceptor.ResponseHighlighterInterceptor;
import ca.uhn.fhir.rest.server.interceptor.ResponseValidatingInterceptor;
import ca.uhn.fhir.rest.server.provider.ResourceProviderFactory;
import ca.uhn.fhir.validation.IValidatorModule;
import ca.uhn.fhir.validation.ResultSeverityEnum;
import org.hl7.fhir.dstu3.model.Bundle;
@@ -318,6 +320,13 @@ public class JpaRestfulServer extends RestfulServer {
registerProvider(appCtx.getBean(BulkDataExportProvider.class));
}
if (HapiProperties.getPartitioningEnabled()) {
PartitionSettings partitionSettings = appCtx.getBean(PartitionSettings.class);
partitionSettings.setPartitioningEnabled(true);
PartitionSettings.CrossPartitionReferenceMode mode = PartitionSettings.CrossPartitionReferenceMode.valueOf(HapiProperties.getPartitioningCrossPartitionReferenceMode());
partitionSettings.setAllowReferencesAcrossPartitions(mode);
partitionSettings.setIncludePartitionInSearchHashes(HapiProperties.getIncludePartitionInSearchHashes());
registerProvider(appCtx.getBean(PartitionManagementProvider.class));
}
}
}

View File

@@ -0,0 +1,35 @@
{
"candidateSearchParams" : [ {
"resourceType" : "Patient",
"searchParam" : "birthdate"
}, {
"resourceType" : "*",
"searchParam" : "identifier"
},{
"resourceType" : "Patient",
"searchParam" : "general-practitioner"
} ],
"candidateFilterSearchParams" : [ {
"resourceType" : "*",
"searchParam" : "active",
"fixedValue" : "true"
} ],
"matchFields" : [ {
"name" : "given-name",
"resourceType" : "*",
"resourcePath" : "name.given",
"metric" : "COSINE",
"matchThreshold" : 0.8
}, {
"name" : "last-name",
"resourceType" : "*",
"resourcePath" : "name.family",
"metric" : "JARO_WINKLER",
"matchThreshold" : 0.8
}],
"matchResultMap" : {
"given-name" : "POSSIBLE_MATCH",
"given-name,last-name" : "MATCH"
},
"eidSystem": "http://company.io/fhir/NamingSystem/custom-eid-system"
}

View File

@@ -149,3 +149,11 @@ email.password=
# Enable Websocket Subscription Channel
subscription.websocket.enabled=false
# EMPI
empi.enabled=false
# Partitioning
partitioning.enabled=false
partitioning.cross_partition_reference_mode=NOT_ALLOWED
partitioning.partitioning_include_in_search_hashes=true

View File

@@ -9,6 +9,25 @@
</encoder>
</appender>
<appender name="EMPI_TROUBLESHOOTING" class="ch.qos.logback.core.rolling.RollingFileAppender">
<filter class="ch.qos.logback.classic.filter.ThresholdFilter"><level>DEBUG</level></filter>
<file>${smile.basedir}/log/empi-troubleshooting.log</file>
<rollingPolicy class="ch.qos.logback.core.rolling.FixedWindowRollingPolicy">
<fileNamePattern>${smile.basedir}/log/empi-troubleshooting.log.%i.gz</fileNamePattern>
<minIndex>1</minIndex>
<maxIndex>9</maxIndex>
</rollingPolicy>
<triggeringPolicy class="ch.qos.logback.core.rolling.SizeBasedTriggeringPolicy">
<maxFileSize>5MB</maxFileSize>
</triggeringPolicy>
<encoder>
<pattern>%d{yyyy-MM-dd HH:mm:ss.SSS} [%thread] %-5level %logger{36} - %msg%n${log.stackfilter.pattern}</pattern>
</encoder>
</appender>
<logger name="ca.uhn.fhir.log.empi_troubleshooting" level="TRACE">
<appender-ref ref="EMPI_TROUBLESHOOTING"/>
</logger>
<root level="INFO">
<appender-ref ref="STDOUT" />
</root>

View File

@@ -8,6 +8,7 @@ import ca.uhn.fhir.rest.client.api.IGenericClient;
import ca.uhn.fhir.rest.client.api.ServerValidationModeEnum;
import ca.uhn.fhir.rest.client.interceptor.LoggingInterceptor;
import ca.uhn.fhir.test.utilities.JettyUtil;
import ca.uhn.fhir.util.BundleUtil;
import org.eclipse.jetty.server.Server;
import org.eclipse.jetty.webapp.WebAppContext;
import org.eclipse.jetty.websocket.api.Session;
@@ -17,6 +18,8 @@ import org.hl7.fhir.instance.model.api.IIdType;
import org.hl7.fhir.r4.model.Bundle;
import org.hl7.fhir.r4.model.Observation;
import org.hl7.fhir.r4.model.Patient;
import org.hl7.fhir.r4.model.Person;
import org.hl7.fhir.r4.model.Reference;
import org.hl7.fhir.r4.model.Subscription;
import org.junit.AfterClass;
import org.junit.BeforeClass;
@@ -24,11 +27,16 @@ import org.junit.Test;
import java.net.URI;
import java.nio.file.Paths;
import java.util.Collection;
import java.util.List;
import java.util.Optional;
import java.util.concurrent.Future;
import java.util.concurrent.TimeUnit;
import static ca.uhn.fhir.util.TestUtil.waitForSize;
import static org.awaitility.Awaitility.await;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertTrue;
public class ExampleServerR4IT {
@@ -43,6 +51,7 @@ public class ExampleServerR4IT {
HapiProperties.setProperty(HapiProperties.DATASOURCE_URL, "jdbc:h2:mem:dbr4");
HapiProperties.setProperty(HapiProperties.FHIR_VERSION, "R4");
HapiProperties.setProperty(HapiProperties.SUBSCRIPTION_WEBSOCKET_ENABLED, "true");
HapiProperties.setProperty(HapiProperties.EMPI_ENABLED, "true");
ourCtx = FhirContext.forR4();
}
@@ -57,9 +66,30 @@ public class ExampleServerR4IT {
Patient pt2 = ourClient.read().resource(Patient.class).withId(id).execute();
assertEquals(methodName, pt2.getName().get(0).getFamily());
// Test EMPI
// Wait until the EMPI message has been processed
await().until(() -> getPeople().size() > 0);
List<Person> persons = getPeople();
// Verify a Person was created that links to our Patient
Optional<String> personLinkToCreatedPatient = persons.stream()
.map(Person::getLink)
.flatMap(Collection::stream)
.map(Person.PersonLinkComponent::getTarget)
.map(Reference::getReference)
.filter(pid -> id.toUnqualifiedVersionless().getValue().equals(pid))
.findAny();
assertTrue(personLinkToCreatedPatient.isPresent());
}
@Test
private List<Person> getPeople() {
Bundle bundle = ourClient.search().forResource(Person.class).cacheControl(new CacheControlDirective().setNoCache(true)).returnBundle(Bundle.class).execute();
return BundleUtil.toListOfResourcesOfType(ourCtx, bundle, Person.class);
}
@Test
public void testWebsocketSubscription() throws Exception {
/*
* Create subscription
@@ -78,7 +108,7 @@ public class ExampleServerR4IT {
IIdType mySubscriptionId = methodOutcome.getId();
// Wait for the subscription to be activated
waitForSize(1, () -> ourClient.search().forResource(Subscription.class).where(Subscription.STATUS.exactly().code("active")).cacheControl(new CacheControlDirective().setNoCache(true)).returnBundle(Bundle.class).execute().getEntry().size());
await().until(() -> activeSubscriptionCount() == 3);
/*
* Attach websocket
@@ -117,7 +147,11 @@ public class ExampleServerR4IT {
ourClient.delete().resourceById(mySubscriptionId).execute();
}
@AfterClass
private int activeSubscriptionCount() {
return ourClient.search().forResource(Subscription.class).where(Subscription.STATUS.exactly().code("active")).cacheControl(new CacheControlDirective().setNoCache(true)).returnBundle(Bundle.class).execute().getEntry().size();
}
@AfterClass
public static void afterClass() throws Exception {
ourServer.stop();
}

View File

@@ -34,132 +34,132 @@ import static org.junit.Assert.assertEquals;
public class ExampleServerR5IT {
private static final org.slf4j.Logger ourLog = org.slf4j.LoggerFactory.getLogger(ExampleServerR5IT.class);
private static IGenericClient ourClient;
private static FhirContext ourCtx;
private static int ourPort;
private static Server ourServer;
private static final org.slf4j.Logger ourLog = org.slf4j.LoggerFactory.getLogger(ExampleServerR5IT.class);
private static IGenericClient ourClient;
private static FhirContext ourCtx;
private static int ourPort;
private static Server ourServer;
static {
HapiProperties.forceReload();
HapiProperties.setProperty(HapiProperties.DATASOURCE_URL, "jdbc:h2:mem:dbr5");
HapiProperties.setProperty(HapiProperties.FHIR_VERSION, "R5");
HapiProperties.setProperty(HapiProperties.SUBSCRIPTION_WEBSOCKET_ENABLED, "true");
ourCtx = FhirContext.forR5();
}
static {
HapiProperties.forceReload();
HapiProperties.setProperty(HapiProperties.DATASOURCE_URL, "jdbc:h2:mem:dbr5");
HapiProperties.setProperty(HapiProperties.FHIR_VERSION, "R5");
HapiProperties.setProperty(HapiProperties.SUBSCRIPTION_WEBSOCKET_ENABLED, "true");
ourCtx = FhirContext.forR5();
}
@Test
public void testCreateAndRead() {
ourLog.info("Base URL is: " + HapiProperties.getServerAddress());
String methodName = "testCreateResourceConditional";
@Test
public void testCreateAndRead() {
ourLog.info("Base URL is: " + HapiProperties.getServerAddress());
String methodName = "testCreateResourceConditional";
Patient pt = new Patient();
pt.addName().setFamily(methodName);
IIdType id = ourClient.create().resource(pt).execute().getId();
Patient pt = new Patient();
pt.addName().setFamily(methodName);
IIdType id = ourClient.create().resource(pt).execute().getId();
Patient pt2 = ourClient.read().resource(Patient.class).withId(id).execute();
assertEquals(methodName, pt2.getName().get(0).getFamily());
}
Patient pt2 = ourClient.read().resource(Patient.class).withId(id).execute();
assertEquals(methodName, pt2.getName().get(0).getFamily());
}
@Test
public void testWebsocketSubscription() throws Exception {
@Test
public void testWebsocketSubscription() throws Exception {
/*
* Create topic
*/
SubscriptionTopic topic = new SubscriptionTopic();
topic.getResourceTrigger().getQueryCriteria().setCurrent("Observation?status=final");
/*
* Create topic
*/
SubscriptionTopic topic = new SubscriptionTopic();
topic.getResourceTrigger().getQueryCriteria().setCurrent("Observation?status=final");
/*
* Create subscription
*/
Subscription subscription = new Subscription();
subscription.getTopic().setResource(topic);
subscription.setReason("Monitor new neonatal function (note, age will be determined by the monitor)");
subscription.setStatus(Enumerations.SubscriptionState.REQUESTED);
/*
* Create subscription
*/
Subscription subscription = new Subscription();
subscription.getTopic().setResource(topic);
subscription.setReason("Monitor new neonatal function (note, age will be determined by the monitor)");
subscription.setStatus(Enumerations.SubscriptionState.REQUESTED);
subscription.getChannelType()
.setSystem("http://terminology.hl7.org/CodeSystem/subscription-channel-type")
.setCode("websocket");
subscription.setContentType("application/json");
subscription.setContentType("application/json");
MethodOutcome methodOutcome = ourClient.create().resource(subscription).execute();
IIdType mySubscriptionId = methodOutcome.getId();
MethodOutcome methodOutcome = ourClient.create().resource(subscription).execute();
IIdType mySubscriptionId = methodOutcome.getId();
// Wait for the subscription to be activated
waitForSize(1, () -> ourClient.search().forResource(Subscription.class).where(Subscription.STATUS.exactly().code("active")).cacheControl(new CacheControlDirective().setNoCache(true)).returnBundle(Bundle.class).execute().getEntry().size());
// Wait for the subscription to be activated
waitForSize(1, () -> ourClient.search().forResource(Subscription.class).where(Subscription.STATUS.exactly().code("active")).cacheControl(new CacheControlDirective().setNoCache(true)).returnBundle(Bundle.class).execute().getEntry().size());
/*
* Attach websocket
*/
/*
* Attach websocket
*/
WebSocketClient myWebSocketClient = new WebSocketClient();
SocketImplementation mySocketImplementation = new SocketImplementation(mySubscriptionId.getIdPart(), EncodingEnum.JSON);
WebSocketClient myWebSocketClient = new WebSocketClient();
SocketImplementation mySocketImplementation = new SocketImplementation(mySubscriptionId.getIdPart(), EncodingEnum.JSON);
myWebSocketClient.start();
URI echoUri = new URI("ws://localhost:" + ourPort + "/hapi-fhir-jpaserver/websocket");
ClientUpgradeRequest request = new ClientUpgradeRequest();
ourLog.info("Connecting to : {}", echoUri);
Future<Session> connection = myWebSocketClient.connect(mySocketImplementation, echoUri, request);
Session session = connection.get(2, TimeUnit.SECONDS);
myWebSocketClient.start();
URI echoUri = new URI("ws://localhost:" + ourPort + "/hapi-fhir-jpaserver/websocket");
ClientUpgradeRequest request = new ClientUpgradeRequest();
ourLog.info("Connecting to : {}", echoUri);
Future<Session> connection = myWebSocketClient.connect(mySocketImplementation, echoUri, request);
Session session = connection.get(2, TimeUnit.SECONDS);
ourLog.info("Connected to WS: {}", session.isOpen());
ourLog.info("Connected to WS: {}", session.isOpen());
/*
* Create a matching resource
*/
Observation obs = new Observation();
obs.setStatus(Enumerations.ObservationStatus.FINAL);
ourClient.create().resource(obs).execute();
/*
* Create a matching resource
*/
Observation obs = new Observation();
obs.setStatus(Enumerations.ObservationStatus.FINAL);
ourClient.create().resource(obs).execute();
// Give some time for the subscription to deliver
Thread.sleep(2000);
// Give some time for the subscription to deliver
Thread.sleep(2000);
/*
* Ensure that we receive a ping on the websocket
*/
waitForSize(1, () -> mySocketImplementation.myPingCount);
/*
* Ensure that we receive a ping on the websocket
*/
waitForSize(1, () -> mySocketImplementation.myPingCount);
/*
* Clean up
*/
ourClient.delete().resourceById(mySubscriptionId).execute();
}
/*
* Clean up
*/
ourClient.delete().resourceById(mySubscriptionId).execute();
}
@AfterClass
public static void afterClass() throws Exception {
ourServer.stop();
}
@AfterClass
public static void afterClass() throws Exception {
ourServer.stop();
}
@BeforeClass
public static void beforeClass() throws Exception {
String path = Paths.get("").toAbsolutePath().toString();
@BeforeClass
public static void beforeClass() throws Exception {
String path = Paths.get("").toAbsolutePath().toString();
ourLog.info("Project base path is: {}", path);
ourLog.info("Project base path is: {}", path);
ourServer = new Server(0);
ourServer = new Server(0);
WebAppContext webAppContext = new WebAppContext();
webAppContext.setContextPath("/hapi-fhir-jpaserver");
webAppContext.setDisplayName("HAPI FHIR");
webAppContext.setDescriptor(path + "/src/main/webapp/WEB-INF/web.xml");
webAppContext.setResourceBase(path + "/target/hapi-fhir-jpaserver-starter");
webAppContext.setParentLoaderPriority(true);
WebAppContext webAppContext = new WebAppContext();
webAppContext.setContextPath("/hapi-fhir-jpaserver");
webAppContext.setDisplayName("HAPI FHIR");
webAppContext.setDescriptor(path + "/src/main/webapp/WEB-INF/web.xml");
webAppContext.setResourceBase(path + "/target/hapi-fhir-jpaserver-starter");
webAppContext.setParentLoaderPriority(true);
ourServer.setHandler(webAppContext);
ourServer.start();
ourServer.setHandler(webAppContext);
ourServer.start();
ourPort = JettyUtil.getPortForStartedServer(ourServer);
ourPort = JettyUtil.getPortForStartedServer(ourServer);
ourCtx.getRestfulClientFactory().setServerValidationMode(ServerValidationModeEnum.NEVER);
ourCtx.getRestfulClientFactory().setSocketTimeout(1200 * 1000);
String ourServerBase = "http://localhost:" + ourPort + "/hapi-fhir-jpaserver/fhir/";
ourCtx.getRestfulClientFactory().setServerValidationMode(ServerValidationModeEnum.NEVER);
ourCtx.getRestfulClientFactory().setSocketTimeout(1200 * 1000);
String ourServerBase = "http://localhost:" + ourPort + "/hapi-fhir-jpaserver/fhir/";
ourClient = ourCtx.newRestfulGenericClient(ourServerBase);
ourClient.registerInterceptor(new LoggingInterceptor(true));
}
ourClient = ourCtx.newRestfulGenericClient(ourServerBase);
ourClient.registerInterceptor(new LoggingInterceptor(true));
}
public static void main(String[] theArgs) throws Exception {
ourPort = 8080;
beforeClass();
}
public static void main(String[] theArgs) throws Exception {
ourPort = 8080;
beforeClass();
}
}