diff --git a/mutalyzer/config/default_settings.py b/mutalyzer/config/default_settings.py index 00dc9b2e8070f55b18bd47d9a384bcc7e9fa98cf..c01d47a56c9494da32fc32313be35e4275ced23a 100644 --- a/mutalyzer/config/default_settings.py +++ b/mutalyzer/config/default_settings.py @@ -25,6 +25,9 @@ CACHE_DIR = '/tmp' # Maximum size for uploaded and downloaded files (in bytes). MAX_FILE_SIZE = 10 * 1048576 # 10 MB +# Maximum sequence length for description extractor (in bases). +EXTRACTOR_MAX_INPUT_LENGTH = 50 * 1000 # 50 Kbp + # The WSGI application runs behind a reverse proxy (e.g., nginx using # proxy_pass). This needs to be set if the application is mapped to a URL # other than / or a different HTTP scheme is used by the reverse proxy. diff --git a/mutalyzer/services/rpc.py b/mutalyzer/services/rpc.py index 6fce0a8faed1640b1882a31528973aaf0e5b1fcb..d0315fd138ab47ae6de018e663675ef3ec41b66f 100644 --- a/mutalyzer/services/rpc.py +++ b/mutalyzer/services/rpc.py @@ -1242,10 +1242,11 @@ class MutalyzerService(ServiceBase): stats.increment_counter('description-extractor/webservice') - if not settings.TESTING and (len(reference) > 1000 or - len(observed) > 1000): + if (len(reference) > settings.EXTRACTOR_MAX_INPUT_LENGTH or + len(observed) > settings.EXTRACTOR_MAX_INPUT_LENGTH): raise Fault('EMAXSIZE', - 'Input sequences are restricted to 1000bp.') + 'Input sequences are restricted to {} bp.' + .format(settings.EXTRACTOR_MAX_INPUT_LENGTH)) allele = extractor.describe_dna(reference, observed) diff --git a/mutalyzer/website/templates/description-extractor.html b/mutalyzer/website/templates/description-extractor.html index ec096feb6083d6b315fab809407e02b8404ebba1..631de1d4796f38dfae44f8dfb513c0053451a473 100644 --- a/mutalyzer/website/templates/description-extractor.html +++ b/mutalyzer/website/templates/description-extractor.html @@ -7,7 +7,7 @@ <p class="alert alert-warning"> Please note that this is an experimental service and we are currently limiting -input sequences to 1000bp. +input sequences to {{ '{:,}'.format(extractor_max_input_length) }} bp. </p> <p> @@ -88,7 +88,7 @@ Please supply a reference sequence and an observed sequence. <div class="form-group"> <label for="reference_accession_number">Reference accession number</label> <input type="text" name="reference_accession_number" id="reference_accession_number" value="{{ reference_accession_number }}" class="form-control form-pre" placeholder="Reference accession number"> - <p>Example: <code class="example-input" data-for="reference_accession_number">NM_198697.1</code></p> + <p>Example: <code class="example-input" data-for="reference_accession_number">NM_004006.1</code></p> </div> </div> </div> @@ -143,7 +143,7 @@ Please supply a reference sequence and an observed sequence. <div class="form-group"> <label for="sample_accession_number">Sample accession number</label> <input type="text" name="sample_accession_number" id="sample_accession_number" value="{{ sample_accession_number }}" class="form-control form-pre" placeholder="Sample accession number"> - <p>Example: <code class="example-input" data-for="sample_accession_number">NM_198697.2</code></p> + <p>Example: <code class="example-input" data-for="sample_accession_number">NM_004006.2</code></p> </div> </div> </div> diff --git a/mutalyzer/website/views.py b/mutalyzer/website/views.py index 830781b656a56f24ac124ebea403937912807da6..bc0a339ebe3d16f3a7124d2699d2e8c5baa96d0c 100644 --- a/mutalyzer/website/views.py +++ b/mutalyzer/website/views.py @@ -682,7 +682,8 @@ def description_extractor(): """ Description extractor loader form. """ - return render_template('description-extractor.html') + return render_template('description-extractor.html', + extractor_max_input_length=settings.EXTRACTOR_MAX_INPUT_LENGTH) @website.route('/description-extractor', methods=['POST']) @@ -788,9 +789,11 @@ def description_extractor_submit(): raw_vars = None if r and s: - if not settings.TESTING and (len(r) > 1000 or len(s) > 1000): + if (len(r) > settings.EXTRACTOR_MAX_INPUT_LENGTH or + len(s) > settings.EXTRACTOR_MAX_INPUT_LENGTH): output.addMessage(__file__, 3, 'EMAXSIZE', - 'Input sequences are restricted to 1000bp.') + 'Input sequences are restricted to {:,} bp.' + .format(settings.EXTRACTOR_MAX_INPUT_LENGTH)) else: raw_vars = extractor.describe_dna(r, s) @@ -801,6 +804,7 @@ def description_extractor_submit(): 'Finished Description Extract request') return render_template('description-extractor.html', + extractor_max_input_length=settings.EXTRACTOR_MAX_INPUT_LENGTH, reference_sequence=reference_sequence or '', sample_sequence=sample_sequence or '', reference_accession_number=reference_accession_number or '', diff --git a/tests/test_services_json.py b/tests/test_services_json.py index 843ca8ea5c3340dc268c440ab0d0075188e95c4d..259fad6bbbd9417c2ec078ba2f5ab32fb7217ced 100644 --- a/tests/test_services_json.py +++ b/tests/test_services_json.py @@ -12,6 +12,7 @@ from spyne.server.null import NullServer import mutalyzer from mutalyzer import announce +from mutalyzer.config import settings from mutalyzer import Scheduler from mutalyzer.services.json import application @@ -298,3 +299,21 @@ class TestServicesJson(MutalyzerTest): 'sample_start_offset': 0, 'sample_end_offset': 0}], 'description': '[5_6insTT;17del;26A>C;35dup]'} + + def test_description_extract_ref_too_long(self): + """ + Test output of descriptionExtract with too long reference sequence. + """ + with pytest.raises(Fault): + self._call('descriptionExtract', + 'A' * (settings.EXTRACTOR_MAX_INPUT_LENGTH + 1), + 'A') + + def test_description_extract_sample_too_long(self): + """ + Test output of descriptionExtract with too long sample sequence. + """ + with pytest.raises(Fault): + self._call('descriptionExtract', + 'A' * (settings.EXTRACTOR_MAX_INPUT_LENGTH), + 'A' * (settings.EXTRACTOR_MAX_INPUT_LENGTH + 1)) diff --git a/tests/test_website.py b/tests/test_website.py index bb3ff5afe3aee57617e41891bde28f9d8a5099b5..3392d1faa4ec1391797627f881a46003f7f590dc 100644 --- a/tests/test_website.py +++ b/tests/test_website.py @@ -17,6 +17,7 @@ from Bio import Entrez import lxml.html from mutalyzer import announce, Scheduler +from mutalyzer.config import settings from mutalyzer.db import models from mutalyzer.website import create_app @@ -178,6 +179,34 @@ class TestWebsite(MutalyzerTest): 'sample_file': (open(path), 'extractor_input.txt')}) assert '[5_6insTT;17del;26A>C;35dup]' in r.data + def test_description_extractor_ref_too_long(self): + """ + Submit a reference sequence exceeding the maximum length to the variant + description extractor. + """ + r = self.app.post('/description-extractor', data={ + 'reference_method': 'raw_method', + 'sample_method': 'raw_method', + 'reference_sequence': 'A' * (settings.EXTRACTOR_MAX_INPUT_LENGTH + 1), + 'sample_sequence': 'A'}) + assert '2_{}del'.format(settings.EXTRACTOR_MAX_INPUT_LENGTH + 1) not in r.data + assert 'Input sequences are restricted to ' in r.data + assert '1 Error, 0 Warnings.' in r.data + + def test_description_extractor_sample_too_long(self): + """ + Submit a sample sequence exceeding the maximum length to the variant + description extractor. + """ + r = self.app.post('/description-extractor', data={ + 'reference_method': 'raw_method', + 'sample_method': 'raw_method', + 'reference_sequence': 'A' * (settings.EXTRACTOR_MAX_INPUT_LENGTH), + 'sample_sequence': 'A' * (settings.EXTRACTOR_MAX_INPUT_LENGTH + 1)}) + assert '{}dup'.format(settings.EXTRACTOR_MAX_INPUT_LENGTH) not in r.data + assert 'Input sequences are restricted to ' in r.data + assert '1 Error, 0 Warnings.' in r.data + def test_checksyntax_valid(self): """ Submit the check syntax form with a valid variant.