diff --git a/.gitignore b/.gitignore
index 9d7f06a3a8648cd33f8496a7c0921eb6811c5f04..22c1c2a58466d13424047fcba0f493355df6bcf4 100644
--- a/.gitignore
+++ b/.gitignore
@@ -10,6 +10,7 @@ env_configs
 .vscode/
 .env
 .idea/
+builds/
 config/
 run_EnvSuitPipeline.py
 custom_plotting.py
diff --git a/.gitlab-ci.yml b/.gitlab-ci.yml
index 3e792092277c9aa7ba0bf09643f4af6ffee68bb0..29c01b3a12b20c0173df6584abc40138d2c3beb4 100644
--- a/.gitlab-ci.yml
+++ b/.gitlab-ci.yml
@@ -59,10 +59,10 @@ test:
     - python -m coverage html -d $CI_PROJECT_DIR/coverage
     - cd $CI_PROJECT_DIR/tests/integration
     - python3 -m coverage run -m unittest test_deposition.py
-    - python3 -m unittest test_deposition.py
-    - python3 -m unittest test_env_suit.py
-    - python3 -m unittest test_survey.py
-    - python3 -m unittest test_advisory.py
+    - python3 -m coverage run -m unittest test_deposition.py
+    - python3 -m coverage run -m unittest test_env_suit.py
+    - python3 -m coverage run -m unittest test_survey.py
+    - python3 -m coverage run -m unittest test_advisory.py
     - python -m coverage report
     - python -m coverage html -d $CI_PROJECT_DIR/coverage
     - ls
diff --git a/EWSMemoryHandler.py b/EWSMemoryHandler.py
new file mode 100644
index 0000000000000000000000000000000000000000..cd305e27ee78e321d4ce2ee807150e2bc110fa05
--- /dev/null
+++ b/EWSMemoryHandler.py
@@ -0,0 +1,33 @@
+from logging import LogRecord, Handler, ERROR
+from logging.handlers import MemoryHandler
+from typing import Optional
+
+
+class EWSMemoryHandler(MemoryHandler):
+
+    def __init__(self, capacity: int, flushLevel: int = ..., target: Optional[Handler] = ..., flushOnClose: bool = ...) -> None:
+        super().__init__(capacity, flushLevel, target, flushOnClose)
+        self.target = target
+
+    def flush(self) -> None:
+        self.acquire()
+        try:
+            if self.target:
+                merged_messages = ""
+                for record in self.buffer:
+                    # self.target.handle(record)
+                    # print(record.message)
+                    merged_messages += record.message + "\n"
+
+                if merged_messages is not "":
+                    print(f"BEGIN:{merged_messages}:END")
+                    merged_record = LogRecord("merged_record", ERROR, "pathname", 0, merged_messages, None, )
+                    self.target.handle(merged_record)
+
+            self.buffer = []
+        finally:
+            self.release()
+
+
+    def shouldFlush(self, record: LogRecord) -> bool:
+        return False
diff --git a/configs/config_SouthAsia_fc_lbdev.json b/configs/config_SouthAsia_fc_lbdev.json
new file mode 100644
index 0000000000000000000000000000000000000000..aefb28419d6f132110f3ac0eaad3d85829b64e55
--- /dev/null
+++ b/configs/config_SouthAsia_fc_lbdev.json
@@ -0,0 +1,18 @@
+{
+    "RegionName" : "SouthAsia",
+    "SubRegionNames" : ["SouthAsia"],
+    "StartTime" : "?",
+    "StartString" : "?",
+    "WorkspacePathout" : "/media/scratch/lb584_scratch/projects/ews/ews_coordinator/",
+    "WorkspacePath" : "not_set",
+    "ServerPath" : "not_set",
+    "ServerName" : "no_upload",
+    "ServerKey" : "not_set",
+    "Survey" : {
+        "ProcessPreJob" : "process_pre_job_survey",
+        "ProcessInJob" : "do_nothing",
+        "ProcessEWSPlotting" : "do_nothing",
+        "ServerCredentialsFile" : "do_nothing",
+        "ServerPathExtra" : "do_nothing"
+    }
+}
\ No newline at end of file
diff --git a/configs/docker/build/conda-env-py3EWS-withbuilds.yml b/configs/docker/build/conda-env-py3EWS-withbuilds.yml
new file mode 100644
index 0000000000000000000000000000000000000000..91e247f14dab77470c02844f0fb6891b58748a7e
--- /dev/null
+++ b/configs/docker/build/conda-env-py3EWS-withbuilds.yml
@@ -0,0 +1,185 @@
+name: /storage/app/EWS/envs/conda/py3EWS
+channels:
+  - conda-forge
+  - defaults
+dependencies:
+  - _libgcc_mutex=0.1=main
+  - _openmp_mutex=4.5=1_gnu
+  - affine=2.3.1=pyhd8ed1ab_0
+  - antlr-python-runtime=4.7.2=py39hf3d152e_1003
+  - attrs=21.4.0=pyhd8ed1ab_0
+  - boost-cpp=1.74.0=h312852a_4
+  - branca=0.5.0=pyhd8ed1ab_0
+  - brotlipy=0.7.0=py39h27cfd23_1003
+  - bzip2=1.0.8=h7f98852_4
+  - c-ares=1.17.1=h7f98852_1
+  - ca-certificates=2022.5.18=ha878542_0
+  - cairo=1.16.0=h6cf1ce9_1008
+  - cartopy=0.20.0=py39h2103e0b_0
+  - certifi=2022.5.18=py39hf3d152e_0
+  - cf-units=3.0.1=py39hce5d2b2_2
+  - cffi=1.15.0=py39hd667e15_1
+  - cfitsio=3.470=hb418390_7
+  - cftime=1.6.0=py39hd257fcd_1
+  - charset-normalizer=2.0.4=pyhd3eb1b0_0
+  - click=7.1.2=pyh9f0ad1d_0
+  - click-plugins=1.1.1=py_0
+  - cligj=0.7.2=pyhd8ed1ab_1
+  - cloudpickle=2.0.0=pyhd8ed1ab_0
+  - conda=4.12.0=py39hf3d152e_0
+  - conda-content-trust=0.1.1=pyhd3eb1b0_0
+  - conda-package-handling=1.7.3=py39h27cfd23_1
+  - contextily=1.0.1=py_0
+  - cryptography=36.0.0=py39h9ce1e76_0
+  - curl=7.78.0=hea6ffbf_0
+  - cycler=0.11.0=pyhd8ed1ab_0
+  - dask-core=2022.5.0=pyhd8ed1ab_0
+  - expat=2.4.1=h9c3ff4c_0
+  - fiona=1.8.20=py39h427c1bf_1
+  - folium=0.12.1.post1=pyhd8ed1ab_1
+  - fontconfig=2.13.1=hba837de_1005
+  - freetype=2.10.4=h0708190_1
+  - freexl=1.0.6=h7f98852_0
+  - fsspec=2022.3.0=pyhd8ed1ab_0
+  - gdal=3.3.1=py39h409cc32_1
+  - geographiclib=1.52=pyhd8ed1ab_0
+  - geopandas=0.10.2=pyhd8ed1ab_1
+  - geopandas-base=0.10.2=pyha770c72_1
+  - geopy=2.2.0=pyhd8ed1ab_0
+  - geos=3.9.1=h9c3ff4c_2
+  - geotiff=1.6.0=h4f31c25_6
+  - gettext=0.19.8.1=h0b5b191_1005
+  - giflib=5.2.1=h36c2ea0_2
+  - hdf4=4.2.15=h10796ff_3
+  - hdf5=1.10.6=nompi_h6a2412b_1114
+  - icu=68.1=h58526e2_0
+  - idna=3.3=pyhd3eb1b0_0
+  - iris=3.2.1=pyhd8ed1ab_0
+  - jbig=2.1=h7f98852_2003
+  - jinja2=3.1.2=pyhd8ed1ab_0
+  - joblib=1.1.0=pyhd8ed1ab_0
+  - jpeg=9d=h36c2ea0_0
+  - json-c=0.15=h98cffda_0
+  - kealib=1.4.14=hcc255d8_2
+  - kiwisolver=1.3.1=py39h1a9c180_1
+  - krb5=1.19.2=hcc1bbae_0
+  - lcms2=2.12=hddcbb42_0
+  - ld_impl_linux-64=2.35.1=h7274673_9
+  - lerc=2.2.1=h9c3ff4c_0
+  - libblas=3.9.0=11_linux64_openblas
+  - libcblas=3.9.0=11_linux64_openblas
+  - libcurl=7.78.0=h2574ce0_0
+  - libdap4=3.20.6=hd7c4107_2
+  - libdeflate=1.7=h7f98852_5
+  - libedit=3.1.20191231=he28a2e2_2
+  - libev=4.33=h516909a_1
+  - libffi=3.3=he6710b0_2
+  - libgcc-ng=11.2.0=h1234567_0
+  - libgdal=3.3.1=h8f005ca_1
+  - libgfortran-ng=12.1.0=h69a702a_16
+  - libgfortran5=12.1.0=hdcd56e2_16
+  - libglib=2.68.3=h3e27bee_0
+  - libgomp=11.2.0=h1234567_0
+  - libiconv=1.16=h516909a_0
+  - libkml=1.3.0=h238a007_1014
+  - liblapack=3.9.0=11_linux64_openblas
+  - libnetcdf=4.8.0=nompi_hcd642e3_103
+  - libnghttp2=1.43.0=h812cca2_0
+  - libopenblas=0.3.17=pthreads_h8fe5266_1
+  - libpng=1.6.37=h21135ba_2
+  - libpq=13.3=hd57d9b9_0
+  - librttopo=1.1.0=h1185371_6
+  - libspatialindex=1.9.3=h9c3ff4c_4
+  - libspatialite=5.0.1=h8694cbe_5
+  - libssh2=1.9.0=ha56f1ee_6
+  - libstdcxx-ng=12.1.0=ha89aaad_16
+  - libtiff=4.3.0=hf544144_1
+  - libuuid=2.32.1=h7f98852_1000
+  - libwebp-base=1.2.0=h7f98852_2
+  - libxcb=1.13=h7f98852_1003
+  - libxml2=2.9.12=h72842e0_0
+  - libxslt=1.1.33=h15afd5d_2
+  - libzip=1.8.0=h4de3113_0
+  - locket=1.0.0=pyhd8ed1ab_0
+  - lxml=4.6.3=py39h107f48f_0
+  - lz4-c=1.9.3=h9c3ff4c_1
+  - mapclassify=2.4.3=pyhd8ed1ab_0
+  - markupsafe=2.0.1=py39h3811e60_0
+  - matplotlib-base=3.4.2=py39h2fa2bec_0
+  - mercantile=1.2.1=pyhd8ed1ab_0
+  - munch=2.5.0=py_0
+  - ncurses=6.3=h7f8727e_2
+  - netcdf4=1.5.7=nompi_py39hc6dca20_100
+  - networkx=2.8.1=pyhd8ed1ab_0
+  - numpy=1.21.1=py39hdbf815f_0
+  - olefile=0.46=pyh9f0ad1d_1
+  - openjpeg=2.4.0=hb52868f_1
+  - openssl=1.1.1o=h166bdaf_0
+  - packaging=21.3=pyhd8ed1ab_0
+  - pandas=1.3.1=py39hde0f152_0
+  - partd=1.2.0=pyhd8ed1ab_0
+  - pcre=8.45=h9c3ff4c_0
+  - pillow=8.3.1=py39ha612740_0
+  - pip=21.2.4=py39h06a4308_0
+  - pixman=0.40.0=h36c2ea0_0
+  - poppler=21.03.0=h93df280_0
+  - poppler-data=0.4.11=hd8ed1ab_0
+  - postgresql=13.3=h2510834_0
+  - proj=8.0.1=h277dcde_0
+  - pthread-stubs=0.4=h36c2ea0_1001
+  - pycosat=0.6.3=py39h27cfd23_0
+  - pycparser=2.21=pyhd3eb1b0_0
+  - pyopenssl=21.0.0=pyhd3eb1b0_1
+  - pyparsing=3.0.9=pyhd8ed1ab_0
+  - pyproj=3.1.0=py39ha9a7ae0_3
+  - pyshp=2.3.0=pyhd8ed1ab_0
+  - pysocks=1.7.1=py39h06a4308_0
+  - python=3.9.7=h12debd9_1
+  - python-dateutil=2.8.2=pyhd8ed1ab_0
+  - python-docx=0.8.11=pyhd8ed1ab_0
+  - python-xxhash=3.0.0=py39hb9d737c_1
+  - python_abi=3.9=2_cp39
+  - pytz=2022.1=pyhd8ed1ab_0
+  - pyyaml=6.0=py39hb9d737c_4
+  - rasterio=1.2.6=py39hbc4e497_2
+  - readline=8.1.2=h7f8727e_1
+  - requests=2.27.1=pyhd3eb1b0_0
+  - rtree=1.0.0=py39hb102c33_1
+  - ruamel_yaml=0.15.100=py39h27cfd23_0
+  - scikit-learn=0.24.2=py39h4dfa638_0
+  - scipy=1.7.0=py39hee8e79c_1
+  - setuptools=58.0.4=py39h06a4308_0
+  - shapely=1.7.1=py39ha61afbd_5
+  - six=1.16.0=pyhd3eb1b0_0
+  - snuggs=1.4.7=py_0
+  - sqlite=3.37.0=hc218d9a_0
+  - threadpoolctl=3.1.0=pyh8a188c0_0
+  - tiledb=2.3.2=he87e0bf_0
+  - tk=8.6.11=h1ccaba5_0
+  - toolz=0.11.2=pyhd8ed1ab_0
+  - tornado=6.1=py39h3811e60_1
+  - tqdm=4.62.3=pyhd3eb1b0_1
+  - tzcode=2021a=h7f98852_2
+  - tzdata=2021e=hda174b7_0
+  - udunits2=2.2.27.27=hc3e0081_3
+  - urllib3=1.26.7=pyhd3eb1b0_0
+  - wheel=0.37.1=pyhd3eb1b0_0
+  - xerces-c=3.2.3=h9d8b166_2
+  - xorg-kbproto=1.0.7=h7f98852_1002
+  - xorg-libice=1.0.10=h7f98852_0
+  - xorg-libsm=1.2.3=hd9c2040_1000
+  - xorg-libx11=1.7.2=h7f98852_0
+  - xorg-libxau=1.0.9=h7f98852_0
+  - xorg-libxdmcp=1.1.3=h7f98852_0
+  - xorg-libxext=1.3.4=h7f98852_1
+  - xorg-libxrender=0.9.10=h7f98852_1003
+  - xorg-renderproto=0.11.1=h7f98852_1002
+  - xorg-xextproto=7.3.0=h7f98852_1002
+  - xorg-xproto=7.0.31=h7f98852_1007
+  - xxhash=0.8.0=h7f98852_3
+  - xyzservices=2022.4.0=pyhd8ed1ab_0
+  - xz=5.2.5=h7b6447c_0
+  - yaml=0.2.5=h7b6447c_0
+  - zlib=1.2.11=h7f8727e_4
+  - zstd=1.5.0=ha95c52a_0
+prefix: /storage/app/EWS/envs/conda/py3EWS
diff --git a/configs/docker/run/launchDocker.sh b/configs/docker/run/launchDocker.sh
new file mode 100755
index 0000000000000000000000000000000000000000..839257344d83c057701da760833998553ce9c231
--- /dev/null
+++ b/configs/docker/run/launchDocker.sh
@@ -0,0 +1 @@
+sudo docker run -it -v "/media/scratch/lb584_scratch/projects/ews_aws/ews_3/code:/storage/app/EWS_prod/code" -v "/media/scratch/lb584_scratch/projects/ews_aws/ews_3/regions:/storage/app/EWS_prod/regions" -v "/media/scratch/lb584_scratch/projects/ews_aws/ews_3/envs/credentials:/storage/app/EWS_prod/envs/credentials" -w "/storage/app/EWS_prod/code" ews_coordinator
diff --git a/coordinator/ProcessorDeposition.py b/coordinator/ProcessorDeposition.py
index cd4860510198a00cb472bbd114578841d9f0b9bf..07bcd0020cf65ebe97ae7ac2bada46f45cc1e8e9 100644
--- a/coordinator/ProcessorDeposition.py
+++ b/coordinator/ProcessorDeposition.py
@@ -37,11 +37,12 @@ def process_in_job_dep(jobPath,status,config,component):
 
     # TODO: perform ssh file transfer in python instead of subprocess
     server_name: str = config['ServerName']
-    machine_seperator: str = ":"
-    if not server_name:
-        machine_seperator = ""
+    if server_name == "":
+        cmd_scp = ["scp", f"{file_path}/{file_name}.tar.gz", jobPath]
+    else:
+        cmd_scp = ["scp", "-i", config['ServerKey'], "-o", "StrictHostKeyChecking=no",
+                   f"{server_name}:{file_path}/{file_name}.tar.gz", jobPath]
 
-    cmd_scp = ["scp", "-i", config['ServerKey'], "-o", "StrictHostKeyChecking=no", f"{server_name}{machine_seperator}{file_path}/{file_name}.tar.gz", jobPath]
     description_short = 'dep scp'
     description_long = 'scp from server to job directory'
     subprocess_and_log(cmd_scp, description_short, description_long)
diff --git a/coordinator/ProcessorEnvironment.py b/coordinator/ProcessorEnvironment.py
index e39386e84fe821ffd739080663f3e86c27aa57e7..5e96960a473253f498c320afa92f71be47dbf916 100644
--- a/coordinator/ProcessorEnvironment.py
+++ b/coordinator/ProcessorEnvironment.py
@@ -40,11 +40,12 @@ def process_in_job_env2_0(jobPath,status,config,component):
 
     # TODO: perform ssh file transfer in python instead of subprocess
     server_name: str = config['ServerName']
-    machine_seperator: str = ":"
-    if not server_name:
-        machine_seperator = ""
+    if server_name == "":
+        cmd_scp: list = ["scp", f"{file_path}/{file_name}.tar.gz", jobPath]
+    else:
+        cmd_scp: list = ["scp", "-i", config['ServerKey'], "-o", "StrictHostKeyChecking=no",
+                         f"{config['ServerName']}:{file_path}/{file_name}.tar.gz", jobPath]
 
-    cmd_scp: list = ["scp","-i",config['ServerKey'],"-o","StrictHostKeyChecking=no",f"{config['ServerName']}{machine_seperator}{file_path}/{file_name}.tar.gz", jobPath]
     description_short = 'env2 scp'
     description_long = 'Copying file from remote server to job directory'
     # lawrence comment in/out
diff --git a/coordinator/ProcessorServer.py b/coordinator/ProcessorServer.py
index 1ef1cebb1dacf0e70463fc9ae9d95e1050d12c02..d8aad9beb9c856fa595d36d30633ce1b12f66879 100644
--- a/coordinator/ProcessorServer.py
+++ b/coordinator/ProcessorServer.py
@@ -37,28 +37,26 @@ def process_pre_job_server_download(input_args: dict):
 
         file_path = Template(config[component]['ServerPathTemplate']).substitute(**config)
         file_name = Template(config[component]['InputFileTemplate']).substitute(**config)
-        file_path_full = f"{file_path}/{file_name}.tar.gz"
-        logger.info(f"Checking for existence of {file_path_full}")
+        logger.info(f"Checking for existence of {file_path}/{file_name}.tar.gz")
 
         timenow = datetime.datetime.now(tz=datetime.timezone.utc).time()
 
-        # test whether the file exists (if not, returns error code 1)
-        # and test whether the tar file is complete (if not, error code is 2)
-        cmd_ssh = [
-                "ssh",
-                "-i",
-                config['ServerKey'],
-                "-o",
-                "StrictHostKeyChecking=no",
-                config['ServerName'],
-                f"test -f {file_path_full} && tar -tzf {file_path_full} >/dev/null"]
+        server_name: str = config['ServerName']
+        full_file_path = f"{file_path}/{file_name}.tar.gz"
+        if server_name == "":
+            cmd_check_file = [f"test -f {full_file_path} && tar -tzf {full_file_path} > /dev/null"]
+            run_in_shell: bool = True
+        else:
+            cmd_check_file = ["ssh", "-i", config['ServerKey'], "-o", "StrictHostKeyChecking=no", server_name,
+                              f"test -f {full_file_path} && tar -tzf {full_file_path} >/dev/null"]
+            run_in_shell: bool = False
 
         description_short = 'subprocess_ssh'
-        description_long = f"Checking for existence of {file_path_full}"
+        description_long = f"Checking for existence of {file_path}/{file_name}.tar.gz"
 
         status = subprocess_and_log(cmd_ssh,description_short,description_long,check=False)
 
-        if status.returncode in [1,2]:
+        if status.returncode > 0:
 
             # a time check in UTC. If it's late, raise warning, if very late, raise error
 
@@ -95,15 +93,6 @@ def process_pre_job_server_download(input_args: dict):
         elif status.returncode == 0:
             logger.info(f"Data is available for config {i+1} of {len(config_paths)}, calculation shall proceed")
 
-        # silence other return codes
-        # there is a known issue from tests that ssh to a blank server will 
-        # raise error code 255. This is kept silent while we come up with a tidy
-        # solution. This doesn't affect production runs as the error would be 
-        # picked up by the later scp commands.
-        #else:
-        #    logger.error(f"Unexpected return code from ssh command: {status.returncode}")
-        #    endScript(premature=False)
-
     return True
 
 def upload(config,FilesToSend,component):
@@ -132,15 +121,26 @@ def upload(config,FilesToSend,component):
 
     logger.debug("Making path directory on remote server if it doesn't already exist")
 
-    ssh_cmd = ["ssh","-i",config['ServerKey'],"-o","StrictHostKeyChecking=no",config['ServerName'], f"mkdir -p {OutputServerPath}"]
+    server_key = config['ServerKey']
+    if server_key == "":
+        ssh_cmd = ["ssh", f"mkdir -p {OutputServerPath}"]
+        run_in_shell: bool = True
+    else:
+        ssh_cmd = ["ssh", "-i", server_key, "-o", "StrictHostKeyChecking=no", config['ServerName'],
+                   f"mkdir -p {OutputServerPath}"]
+        run_in_shell: bool = False
 
     description_short = 'upload ssh'
     description_long = 'make remote directory'
-    subprocess_and_log(ssh_cmd, description_short, description_long)
+    subprocess_and_log(ssh_cmd, description_short, description_long, shell=run_in_shell)
 
     logger.debug('Sending file(s) to remote server')
 
-    scp_cmd = ["scp","-ri",config['ServerKey'],"-o","StrictHostKeyChecking=no",*FilesToSend, f"{config['ServerName']}:{OutputServerPath}"]
+    if server_key == "":
+        scp_cmd = ["scp", *FilesToSend, {OutputServerPath}]
+    else:
+        scp_cmd = ["scp", "-ri", server_key, "-o", "StrictHostKeyChecking=no", *FilesToSend,
+                   f"{config['ServerName']}:{OutputServerPath}"]
 
     description_short = 'upload scp'
     description_long = 'scp files to remote directory'
diff --git a/coordinator/ProcessorUtils.py b/coordinator/ProcessorUtils.py
index 8ddfa4b0e974e3e9f88cc4b247c61c6b1f6e614d..1b7d01700ffe00b9d2befaf26796af556ff61f85 100644
--- a/coordinator/ProcessorUtils.py
+++ b/coordinator/ProcessorUtils.py
@@ -125,7 +125,7 @@ def get_only_existing_globs(file_globs,inplace=True):
             globs_out += [fg]
         return globs_out
 
-def subprocess_and_log(cmd,description_short,description_long,check=True,log_type='error',**kwargs):
+def subprocess_and_log(cmd,description_short,description_long,check=True,log_type='error', shell: bool = False, **kwargs):
     '''Run a shell command (described by a comma separated list) and send stdout
     and stderr to logfile, and raise any exception.
     
@@ -140,6 +140,7 @@ def subprocess_and_log(cmd,description_short,description_long,check=True,log_typ
         process = subprocess.run(
                 cmd,
                 check=check,
+                shell=shell,
                 stdout = subprocess.PIPE,
                 stderr = subprocess.STDOUT,
                 **kwargs)
diff --git a/test.py b/test.py
new file mode 100644
index 0000000000000000000000000000000000000000..4eea79c6df740898a2ff564c0ac6a1cef093f739
--- /dev/null
+++ b/test.py
@@ -0,0 +1,4 @@
+from test2 import function
+
+if __name__ == '__main__':
+    function()
\ No newline at end of file
diff --git a/test2.py b/test2.py
new file mode 100644
index 0000000000000000000000000000000000000000..dec137b1379ab91c5a0b50e9ebe1d3d019c569bc
--- /dev/null
+++ b/test2.py
@@ -0,0 +1,23 @@
+import iris
+from iris.cube import CubeList
+
+
+# cube_wildcard = "/media/scratch/lb584_scratch/projects/ews_local_prod/regions/EastAfrica/workspace/ENVIRONMENT_2.0_20220730/NAME_Met_as_netcdf/*.nc"
+# cubes: CubeList = iris.load(cube_wildcard)
+# all_timepoints_present: bool = True
+# for cube in cubes:
+#     coord = cube.coord("time")
+#     timepoints = coord.shape[0]
+#     if timepoints != 57:
+#         all_timepoints_present = False
+#         break
+#     i = 0
+
+def function():
+    print("doing function thing")
+    if __name__ == '__main__':
+        print("doing main thing")
+
+
+if __name__ == '__main__':
+    function()
diff --git a/tests/integration/depo_asserts.py b/tests/integration/depo_asserts.py
new file mode 100644
index 0000000000000000000000000000000000000000..29ec5358ca0787d208f97bd852c7653f586a9de1
--- /dev/null
+++ b/tests/integration/depo_asserts.py
@@ -0,0 +1,61 @@
+import os
+import unittest
+
+from integration.integration_test_utils import IntegrationTestUtils
+from integration.test_deposition import TestDeposition
+
+
+class DepoAsserts(TestDeposition):
+
+
+    def test_standard_run_input_status_success(self):
+        status_file_path = os.path.join(TestDeposition.TEST_OUT_PATH, TestDeposition.TEST_JOB_DIR, "STATUS_SUCCESS")
+        success_file_exists: bool = os.path.isfile(status_file_path)
+        self.assertTrue(success_file_exists)
+
+
+    def test_standard_run_input_all_regions_ran(self):
+        """
+        working on the assumption that if there are images for each region, it must have run through
+        (at least past the region iteration)
+        """
+
+        east_africa_image_path = os.path.join(TestDeposition.TEST_OUT_PATH, TestDeposition.TEST_JOB_DIR,
+                                              "plotting", "eastafrica", "images", "Weekly",
+                                              "deposition_eastafrica_leaf_rust_total_202210010000_202210080000_map.png")
+        ethiopia_image_path = os.path.join(TestDeposition.TEST_OUT_PATH, TestDeposition.TEST_JOB_DIR,
+                                           "plotting", "ethiopia", "images", "Weekly",
+                                           "deposition_ethiopia_leaf_rust_total_202210010000_202210080000_map.png")
+
+        ea_file_exists: bool = os.path.isfile(east_africa_image_path)
+        eth_file_exists: bool = os.path.isfile(ethiopia_image_path)
+        self.assertTrue(ea_file_exists)
+        self.assertTrue(eth_file_exists)
+
+
+    def test_standard_run_all_input_csvs_produced(self):
+        east_africa_csv_path = os.path.join(TestDeposition.TEST_OUT_PATH, TestDeposition.TEST_JOB_DIR,
+                                            "plotting", "eastafrica", "input_csvs", "*.csv")
+        ethiopia_csv_path = os.path.join(TestDeposition.TEST_OUT_PATH, TestDeposition.TEST_JOB_DIR,
+                                         "plotting", "ethiopia", "input_csvs", "*.csv")
+
+        ea_csv_count: int = IntegrationTestUtils.count_files_in_wildcard(east_africa_csv_path)
+        eth_csv_count: int = IntegrationTestUtils.count_files_in_wildcard(ethiopia_csv_path)
+        self.assertEqual(9, ea_csv_count)
+        self.assertEqual(27, eth_csv_count)
+
+
+    def test_standard_run_all_images_produced(self):
+        east_africa_image_path = os.path.join(TestDeposition.TEST_OUT_PATH, TestDeposition.TEST_JOB_DIR,
+                                              "plotting", "eastafrica", "images", "Weekly", "*.png")
+        ethiopia_image_path = os.path.join(TestDeposition.TEST_OUT_PATH, TestDeposition.TEST_JOB_DIR,
+                                           "plotting", "ethiopia", "images", "Weekly", "*.png")
+
+        ea_csv_count: int = IntegrationTestUtils.count_files_in_wildcard(east_africa_image_path)
+        eth_csv_count: int = IntegrationTestUtils.count_files_in_wildcard(ethiopia_image_path)
+        self.assertEqual(3, ea_csv_count)
+        self.assertEqual(6, eth_csv_count)
+
+
+if __name__ == '__main__':
+    unittest.main()
diff --git a/tests/integration/sub_test.py b/tests/integration/sub_test.py
new file mode 100644
index 0000000000000000000000000000000000000000..5dfdd4a2c5728ebee98d8be3aebd6e281de66651
--- /dev/null
+++ b/tests/integration/sub_test.py
@@ -0,0 +1,23 @@
+import unittest
+
+from integration.test_test import MyTestCase
+
+
+class SubTest(unittest.TestCase):
+
+    def __init__(self, methodName: str = ...) -> None:
+        super().__init__(methodName)
+        print("RUNNING SETUP")
+
+    def test_1(self):
+        self.assertEqual(True, True)  # add assertion here
+
+    def test_2(self):
+        self.assertEqual(True, True)  # add assertion here
+
+    def test_3(self):
+        self.assertEqual(True, True)  # add assertion here
+
+
+if __name__ == '__main__':
+    unittest.main()
diff --git a/tests/integration/test_advisory.py b/tests/integration/test_advisory.py
index cfa8d7240f0e3f48e17cbf664ebf6e23e1c628ac..a5bde542faf57542efa0d0d7517ad645105dbdaf 100644
--- a/tests/integration/test_advisory.py
+++ b/tests/integration/test_advisory.py
@@ -1,4 +1,5 @@
 import copy
+import glob
 import os
 import unittest
 
@@ -67,6 +68,29 @@ class TestAdvisory(unittest.TestCase):
         self.assertTrue(ea_file_exists)
         self.assertTrue(eth_file_exists)
 
+    def test_standard_run_input_images_produced(self):
+
+        east_africa_image_wildcard = os.path.join(TestAdvisory.TEST_OUT_PATH, TestAdvisory.TEST_JOB_DIR,
+                                                  "images",
+                                                  "*eastafrica*.png")
+        ethiopia_image_wildcard = os.path.join(TestAdvisory.TEST_OUT_PATH, TestAdvisory.TEST_JOB_DIR,
+                                               "images",
+                                               "*ethiopia*.png")
+
+        africa_image_count: int = len(glob.glob(east_africa_image_wildcard))
+        ethiopia_image_count: int = len(glob.glob(ethiopia_image_wildcard))
+        self.assertEqual(3, africa_image_count)
+        self.assertEqual(3, ethiopia_image_count)
+
+    def test_standard_run_input_shapefiles_produced(self):
+
+        east_africa_image_wildcard = os.path.join(TestAdvisory.TEST_OUT_PATH, TestAdvisory.TEST_JOB_DIR,
+                                                  "images",
+                                                  "*eastafrica*.shp")
+
+        africa_image_count: int = len(glob.glob(east_africa_image_wildcard))
+        self.assertEqual(3, africa_image_count)
+
 
 if __name__ == '__main__':
     unittest.main()
diff --git a/tests/integration/test_env_suit.py b/tests/integration/test_env_suit.py
index b51487f95d455b64ae5ba871c828f6089ca7956c..5b6e1ad9673bafe72b3d7dbf42d222e97b2128f1 100644
--- a/tests/integration/test_env_suit.py
+++ b/tests/integration/test_env_suit.py
@@ -20,7 +20,7 @@ class TestEnvSuit(unittest.TestCase):
     @staticmethod
     def write_temp_run_config_file():
         nowstring: str = IntegrationTestUtils.get_now_string()
-        prefix: str = "temp_depo_" + nowstring
+        prefix: str = "temp_env_" + nowstring
         # prefix: str = ""
 
         default_config = IntegrationTestUtils.DEFAULT_CONFIG_FILE_PATH
diff --git a/tests/integration/test_epi.py b/tests/integration/test_epi.py
new file mode 100644
index 0000000000000000000000000000000000000000..18d406d9c5879288bd4f2cc864b5a10743efac48
--- /dev/null
+++ b/tests/integration/test_epi.py
@@ -0,0 +1,72 @@
+import copy
+import os
+import unittest
+
+from integration.integration_test_utils import IntegrationTestUtils
+
+
+class TestEpi(unittest.TestCase):
+
+    TEST_OUT_PATH: str = "not_set"
+    TEST_START_DATE: str = '20221001'
+    TEST_JOB_DIR: str = "SUMMARY_" + TEST_START_DATE
+
+    @classmethod
+    def setUpClass(cls) -> None:
+        TestEpi.write_temp_run_config_files()
+        TestEpi.unpack_dependencies()
+        TestEpi.run_advisory_pipeline()
+
+
+    @staticmethod
+    def write_temp_run_config_files():
+        nowstring: str = IntegrationTestUtils.get_now_string()
+        prefix: str = "temp_epi_" + nowstring
+        # prefix: str = ""
+
+        default_config = IntegrationTestUtils.DEFAULT_CONFIG_FILE_PATH
+        default_config_dict: dict = IntegrationTestUtils.load_json_file(default_config)
+        run_dict: dict = copy.deepcopy(default_config_dict)
+        TestEpi.TEST_OUT_PATH = run_dict['WorkspacePathout'] + prefix + os.sep
+        run_dict['WorkspacePathout'] = TestEpi.TEST_OUT_PATH
+        run_dict['WorkspacePath'] = TestEpi.TEST_OUT_PATH
+        run_dict['ServerName'] = ''  # nothing, as local machine
+
+        IntegrationTestUtils.write_json_file(run_dict, IntegrationTestUtils.TEMP_CONFIG_FILE_PATH)
+
+
+    @staticmethod
+    def unpack_dependencies():
+        IntegrationTestUtils.unpack_zip(IntegrationTestUtils.EXAMPLE_SURVEY_FILE_PATH, TestEpi.TEST_OUT_PATH)
+        IntegrationTestUtils.unpack_zip(IntegrationTestUtils.EXAMPLE_DEPO_FILE_PATH, TestEpi.TEST_OUT_PATH)
+        IntegrationTestUtils.unpack_zip(IntegrationTestUtils.EXAMPLE_ENV_SUIT_FILE_PATH, TestEpi.TEST_OUT_PATH)
+
+
+    @staticmethod
+    def run_advisory_pipeline():
+        component = 'Epidemiology'
+        IntegrationTestUtils.run_pipeline(component, TestEpi.TEST_START_DATE)
+
+
+    def test_standard_run_input_status_success(self):
+        status_file_path = os.path.join(TestEpi.TEST_OUT_PATH, TestEpi.TEST_JOB_DIR, "STATUS_SUCCESS")
+        success_file_exists: bool = os.path.isfile(status_file_path)
+        self.assertTrue(success_file_exists)
+
+    def test_standard_run_input_all_docs_produced(self):
+
+        east_africa_image_path = os.path.join(TestEpi.TEST_OUT_PATH, TestEpi.TEST_JOB_DIR,
+                                              "tight-layout",
+                                              "wheat_rust_advisory_template_EastAfrica_20221001.docx")
+        ethiopia_image_path = os.path.join(TestEpi.TEST_OUT_PATH, TestEpi.TEST_JOB_DIR,
+                                           "tight-layout",
+                                           "wheat_rust_advisory_template_Ethiopia_20221001.docx")
+
+        ea_file_exists: bool = os.path.isfile(east_africa_image_path)
+        eth_file_exists: bool = os.path.isfile(ethiopia_image_path)
+        self.assertTrue(ea_file_exists)
+        self.assertTrue(eth_file_exists)
+
+
+if __name__ == '__main__':
+    unittest.main()
diff --git a/tests/integration/test_test.py b/tests/integration/test_test.py
new file mode 100644
index 0000000000000000000000000000000000000000..286267bf64390bd292f4f540ade818074a563471
--- /dev/null
+++ b/tests/integration/test_test.py
@@ -0,0 +1,8 @@
+import unittest
+
+
+class MyTestCase(unittest.TestCase):
+
+    def setUp(self) -> None:
+        print("running setup")
+
diff --git a/tests/test_data/test_deployment/regions/EastAfrica/resources/coordinator/configs/.gitignore b/tests/test_data/test_deployment/regions/EastAfrica/resources/coordinator/configs/.gitignore
new file mode 100644
index 0000000000000000000000000000000000000000..e69de29bb2d1d6434b8b29ae775ad8c2e48c5391
diff --git a/tests/test_data/test_deployment/regions/EastAfrica/resources/coordinator/configs/config_EastAfrica_fc_live.json b/tests/test_data/test_deployment/regions/EastAfrica/resources/coordinator/configs/config_EastAfrica_fc_live.json
index 12cf38253f1968c179f5332c4da2632cf472a7dd..366f6a606a11305b4470b38fdf63036a0195802c 100644
--- a/tests/test_data/test_deployment/regions/EastAfrica/resources/coordinator/configs/config_EastAfrica_fc_live.json
+++ b/tests/test_data/test_deployment/regions/EastAfrica/resources/coordinator/configs/config_EastAfrica_fc_live.json
@@ -8,7 +8,7 @@
     "ResourcesPath" : "../test_data/test_deployment/regions/EastAfrica/resources/",
     "ServerPath" : "/storage/moved/Ethiopia/",
     "ServerName" : "ewsmanager@willow.csx.cam.ac.uk",
-    "ServerKey" : "../test_data/test_deployment/regions/EastAfrica/resources/coordinator/configs/ssh_key_willow",
+    "ServerKey" : "not used, set to empty string in tests",
     "Survey" : {
         "ProcessPreJob" : "process_pre_job_survey",
         "ProcessInJob" : "process_in_job_survey",
@@ -148,7 +148,7 @@
     },
     "Epidemiology" : {
         "DiseaseNames" : ["StemRust"],
-        "CalculationSpanDays" : ["20220501",5],
+        "CalculationSpanDays" : [0,1],
         "TimeStep_hours": "3",
         "ProcessPreJob" : "process_pre_job_epi",
         "ProcessInJob" : "process_in_job_epi",
@@ -220,7 +220,7 @@
         "ProcessPreJob" : "query_past_successes",
         "ProcessInJob" : "process_in_job_advisory",
         "ProcessEWSPlotting" : "do_nothing",
-        "seasonStartString" : "20220501",
+        "seasonStartString" : "20210901",
         "Environment" : {
             "SuccessFileTemplate" : "${WorkspacePath}ENVIRONMENT_2.0_${StartString}/STATUS_SUCCESS",
             "DataPathTemplate" : "${WorkspacePath}/ENVIRONMENT_2.0_${dateString}/plotting/${SubRegionNameLower}/input_csvs/",
@@ -270,7 +270,7 @@
             }
         },
         "Surveys" : {
-            "variety_names_tidy_fn" : "/media/scratch/lb584_scratch/projects/ews_local_prod/regions/EastAfrica/resources/advisory_builder/configs/config_EastAfrica_variety_names_tidy.json",
+            "variety_names_tidy_fn" : "../test_data/test_deployment/regions/EastAfrica/resources/advisory_builder/configs/config_EastAfrica_variety_names_tidy.json",
             "CountryColumnName" : "surveyor_infromation-country",
             "EastAfrica" : {
                 "ShapeFilenameAdmin0" : "../test_data/test_deployment/regions/EastAfrica/resources/advisory_builder/assets/EthKen_admin0.shp",
diff --git a/wind_precip_20220730.png b/wind_precip_20220730.png
new file mode 100644
index 0000000000000000000000000000000000000000..dad499b3eefbde14494b9049b6574a87d9dd9774
Binary files /dev/null and b/wind_precip_20220730.png differ