Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Alexander rubin dm code challenge #49

Open
wants to merge 3 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion Dockerfile
Original file line number Diff line number Diff line change
Expand Up @@ -36,7 +36,7 @@ RUN pip install --no-cache-dir -r requirements.txt

# Install Node requirements
COPY ./package.json /app/package.json
RUN npm install
# RUN npm install
Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

For some reason docker build fails on this step and I couldn't figure out how to solve it. Commenting it out didn't break the app, so this is my Dockerfile solution for now.


# Copy the contents of the current host directory (i.e., our app code) into
# the container.
Expand Down
47 changes: 45 additions & 2 deletions parserator_web/static/js/index.js
Original file line number Diff line number Diff line change
@@ -1,2 +1,45 @@
/* TODO: Flesh this out to connect the form to the API and render results
in the #address-results div. */
document.addEventListener('DOMContentLoaded', function() {
document.querySelector('form').addEventListener('submit', function(event) {
event.preventDefault();

var address = document.querySelector('#address').value;

fetch('/api/parse?address=' + encodeURIComponent(address), {
headers: {
'X-CSRFToken': document.querySelector('[name=csrfmiddlewaretoken]').value
}
})
.then(response => response.json())
.then(data => {
var resultsDiv = document.getElementById('address-results');
var resultsTableBody = resultsDiv.querySelector('tbody');
var parseType = document.getElementById('parse-type');

resultsTableBody.innerHTML = ''; // Clear previous results

if (data.error) {
resultsDiv.style.display = 'block';
parseType.innerText = 'Error';
resultsTableBody.innerHTML = '<tr><td colspan="2">' + data.error + '</td></tr>';
} else {
resultsDiv.style.display = 'block';
parseType.innerText = data.address_type;

var components = data.address_components;
for (var part in components) {
var row = document.createElement('tr');
var partCell = document.createElement('td');
var tagCell = document.createElement('td');
partCell.innerText = part;
tagCell.innerText = components[part];
row.appendChild(partCell);
row.appendChild(tagCell);
resultsTableBody.appendChild(row);
}
}
})
.catch(error => {
console.error('Error:', error);
});
});
});
27 changes: 19 additions & 8 deletions parserator_web/views.py
Original file line number Diff line number Diff line change
Expand Up @@ -5,20 +5,31 @@
from rest_framework.renderers import JSONRenderer
from rest_framework.exceptions import ParseError


class Home(TemplateView):
template_name = 'parserator_web/index.html'


class AddressParse(APIView):
renderer_classes = [JSONRenderer]

def get(self, request):
# TODO: Flesh out this method to parse an address string using the
# parse() method and return the parsed components to the frontend.
return Response({})
address = request.query_params.get('address', None)
if not address:
raise ParseError("No address provided")

address_components, address_type = self.parse(address)

return Response({
'input_string': address,
'address_components': address_components,
'address_type': address_type
})

def parse(self, address):
# TODO: Implement this method to return the parsed components of a
# given address using usaddress: https://github.com/datamade/usaddress
return address_components, address_type
try:
parsed_address = usaddress.tag(address)
address_components = parsed_address[0]
address_type = parsed_address[1]
except usaddress.RepeatedLabelError as e:
raise ParseError("Invalid address")

return address_components, address_type
11 changes: 10 additions & 1 deletion tests/conftest.py
Original file line number Diff line number Diff line change
@@ -1 +1,10 @@
# Define test fixtures here.
import os
import sys
import django

# Add the parent directory to the sys.path
sys.path.insert(0, os.path.abspath(os.path.join(os.path.dirname(__file__), '..')))

def pytest_configure():
os.environ['DJANGO_SETTINGS_MODULE'] = 'parserator_web.settings'
django.setup()
39 changes: 33 additions & 6 deletions tests/test_views.py
Original file line number Diff line number Diff line change
@@ -1,15 +1,42 @@
import pytest
from rest_framework.test import APIClient

@pytest.fixture
def client():
return APIClient()

def test_api_parse_succeeds(client):
# TODO: Finish this test. Send a request to the API and confirm that the
# data comes back in the appropriate format.
# Send a request to the API with a valid address
address_string = '123 main st chicago il'
pytest.fail()
response = client.get('/api/parse/', {'address': address_string})

# Check if the response status code is 200 OK
assert response.status_code == 200

# Check if the response contains the expected data
data = response.json()
assert 'input_string' in data
assert data['input_string'] == address_string
assert 'address_components' in data
assert 'address_type' in data

# Check some known components (example, update as needed)
assert 'AddressNumber' in data['address_components']
assert data['address_components']['AddressNumber'] == '123'
assert 'PlaceName' in data['address_components']
assert data['address_components']['PlaceName'] == 'chicago'
assert 'StateName' in data['address_components']
assert data['address_components']['StateName'] == 'il'

def test_api_parse_raises_error(client):
# TODO: Finish this test. The address_string below will raise a
# RepeatedLabelError, so ParseAddress.parse() will not be able to parse it.
# Send a request to the API with an invalid address
address_string = '123 main st chicago il 123 main st'
pytest.fail()
response = client.get('/api/parse/', {'address': address_string})

# Check if the response status code is 400 Bad Request
assert response.status_code == 400

# Check if the response contains the error message
data = response.json()
assert 'detail' in data
assert data['detail'] == 'Invalid address'