From 9d414f4b92bf04b52b16b18b410980eb65f9b986 Mon Sep 17 00:00:00 2001 From: Brett Costabile Date: Sun, 8 May 2016 22:43:45 -0400 Subject: [PATCH] Data migration to combined app This is an intermediate version for migrating to the new, combined app. --- EVERoachCoach/settings.py.example | 7 +++ orders/__init__.py | 0 orders/admin.py | 3 + orders/apps.py | 7 +++ orders/forms.py | 13 ++++ orders/migrations/0001_initial.py | 29 +++++++++ orders/migrations/__init__.py | 0 orders/models.py | 11 ++++ orders/tests.py | 3 + orders/views.py | 59 +++++++++++++++++++ .../migrations/0002_upgrade_from_v1.py | 55 +++++++++++++++++ stock/__init__.py | 0 stock/admin.py | 3 + stock/apps.py | 7 +++ stock/forms.py | 13 ++++ stock/migrations/0001_initial.py | 25 ++++++++ stock/migrations/__init__.py | 0 stock/models.py | 8 +++ stock/tests.py | 3 + stock/views.py | 45 ++++++++++++++ 20 files changed, 291 insertions(+) create mode 100644 orders/__init__.py create mode 100644 orders/admin.py create mode 100644 orders/apps.py create mode 100644 orders/forms.py create mode 100644 orders/migrations/0001_initial.py create mode 100644 orders/migrations/__init__.py create mode 100644 orders/models.py create mode 100644 orders/tests.py create mode 100644 orders/views.py create mode 100644 rapid_sales_tool/migrations/0002_upgrade_from_v1.py create mode 100644 stock/__init__.py create mode 100644 stock/admin.py create mode 100644 stock/apps.py create mode 100644 stock/forms.py create mode 100644 stock/migrations/0001_initial.py create mode 100644 stock/migrations/__init__.py create mode 100644 stock/models.py create mode 100644 stock/tests.py create mode 100644 stock/views.py diff --git a/EVERoachCoach/settings.py.example b/EVERoachCoach/settings.py.example index d70e99a..140ae34 100644 --- a/EVERoachCoach/settings.py.example +++ b/EVERoachCoach/settings.py.example @@ -40,6 +40,8 @@ INSTALLED_APPS = [ 'django.contrib.staticfiles', 'rapid_sales_tool', 'portal', + 'orders', + 'stock', ] MIDDLEWARE_CLASSES = [ @@ -125,6 +127,11 @@ USE_TZ = True # Static files (CSS, JavaScript, Images) # https://docs.djangoproject.com/en/1.9/howto/static-files/ +# STATIC_ROOT should be set to the directory in which your webserver will be looking for static files. +# i.e. /var/www/example/static/ + +STATIC_ROOT = '' + STATIC_URL = '/static/' SERVICE_NAME = os.environ.get('APP_SERVICE_NAME', '') diff --git a/orders/__init__.py b/orders/__init__.py new file mode 100644 index 0000000..e69de29 diff --git a/orders/admin.py b/orders/admin.py new file mode 100644 index 0000000..8c38f3f --- /dev/null +++ b/orders/admin.py @@ -0,0 +1,3 @@ +from django.contrib import admin + +# Register your models here. diff --git a/orders/apps.py b/orders/apps.py new file mode 100644 index 0000000..f9fdc0c --- /dev/null +++ b/orders/apps.py @@ -0,0 +1,7 @@ +from __future__ import unicode_literals + +from django.apps import AppConfig + + +class OrdersConfig(AppConfig): + name = 'orders' diff --git a/orders/forms.py b/orders/forms.py new file mode 100644 index 0000000..209c058 --- /dev/null +++ b/orders/forms.py @@ -0,0 +1,13 @@ +from django.forms import ModelForm, ModelChoiceField +from django.forms.models import inlineformset_factory +from stock.models import StockItem +from .models import * + +class AddOrderForm(ModelForm): + class Meta: + model = Order + exclude = ('order_price','is_paid') + def __init__(self, *args, **kwargs): + super(AddOrderForm, self).__init__(*args, **kwargs) + self.fields['item'].queryset = StockItem.objects.all() + self.fields['item'].label_from_instance = lambda obj: "%s" % (obj.item_name) \ No newline at end of file diff --git a/orders/migrations/0001_initial.py b/orders/migrations/0001_initial.py new file mode 100644 index 0000000..f822e97 --- /dev/null +++ b/orders/migrations/0001_initial.py @@ -0,0 +1,29 @@ +# -*- coding: utf-8 -*- +# Generated by Django 1.9.3 on 2016-03-27 23:17 +from __future__ import unicode_literals + +from django.db import migrations, models +import django.db.models.deletion + + +class Migration(migrations.Migration): + + initial = True + + dependencies = [ + ('stock', '0001_initial'), + ] + + operations = [ + migrations.CreateModel( + name='Order', + fields=[ + ('id', models.AutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')), + ('customer_name', models.CharField(max_length=64)), + ('item_quantity', models.PositiveIntegerField()), + ('order_price', models.DecimalField(decimal_places=2, max_digits=17)), + ('is_paid', models.BooleanField()), + ('item', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, to='stock.StockItem')), + ], + ), + ] diff --git a/orders/migrations/__init__.py b/orders/migrations/__init__.py new file mode 100644 index 0000000..e69de29 diff --git a/orders/models.py b/orders/models.py new file mode 100644 index 0000000..9ae60f0 --- /dev/null +++ b/orders/models.py @@ -0,0 +1,11 @@ +from __future__ import unicode_literals + +from django.db import models +from stock.models import StockItem + +class Order(models.Model): + customer_name = models.CharField(max_length=64) + item = models.ForeignKey(StockItem, on_delete=models.CASCADE) + item_quantity = models.PositiveIntegerField() + order_price = models.DecimalField(max_digits=17, decimal_places=2) + is_paid = models.BooleanField() \ No newline at end of file diff --git a/orders/tests.py b/orders/tests.py new file mode 100644 index 0000000..7ce503c --- /dev/null +++ b/orders/tests.py @@ -0,0 +1,3 @@ +from django.test import TestCase + +# Create your tests here. diff --git a/orders/views.py b/orders/views.py new file mode 100644 index 0000000..b0f0d64 --- /dev/null +++ b/orders/views.py @@ -0,0 +1,59 @@ +import requests +import json +from decimal import Decimal +from django.conf import settings +from django.core.urlresolvers import reverse +from django.http.response import HttpResponseServerError +from django.template import RequestContext +from django.shortcuts import HttpResponseRedirect, render, get_object_or_404, HttpResponse +from django.forms import modelformset_factory +from .forms import * +from .models import * + +def order(request): + orders = Order.objects.filter(is_paid=False) + for item in orders: + item.markup_price = item.order_price + (item.order_price * Decimal(settings.MARKUP_VALUE)) + if request.method == 'POST': + form = AddOrderForm(request.POST) + if form.is_valid(): + order_instance = form.save(commit=False) + stock_item = order_instance.item + if order_instance.item_quantity <= stock_item.item_count: + order_instance.order_price = order_instance.item_quantity * stock_item.unit_cost + stock_item.item_count -= order_instance.item_quantity + order_instance.is_paid = False + stock_item.save() + form.save() + else: + return HttpResponseServerError(('You cannot order more than is available: {0} units').format(stock_item.item_count)) + return HttpResponseRedirect(reverse(order)) + else: + addOrderForm = AddOrderForm() + return render(request, 'public/orders.html', {'addOrderForm': addOrderForm, 'orders': orders, 'service_name': settings.SERVICE_NAME}, context_instance=RequestContext(request)) + +def cancelOrder(request): + if request.method == 'POST': + response = HttpResponse() + order_id = request.POST['order_id'] + order = get_object_or_404(Order, pk=order_id) + stock_item = order.item + stock_item.item_count += order.item_quantity + stock_item.save() + order.delete() + response.status_code = 200 + return response + else: + Http404("Why are you here?") + +def paidOrder(request): + if request.method == 'POST': + response = HttpResponse() + order_id = request.POST['order_id'] + order = get_object_or_404(Order, pk=order_id) + order.is_paid = True + order.save() + response.status_code = 200 + return response + else: + Http404("Why are you here?") \ No newline at end of file diff --git a/rapid_sales_tool/migrations/0002_upgrade_from_v1.py b/rapid_sales_tool/migrations/0002_upgrade_from_v1.py new file mode 100644 index 0000000..c03c08e --- /dev/null +++ b/rapid_sales_tool/migrations/0002_upgrade_from_v1.py @@ -0,0 +1,55 @@ +# -*- coding: utf-8 -*- +# Generated by Django 1.9.3 on 2016-05-08 23:02 +from __future__ import unicode_literals + +from django.apps import apps as global_apps +from django.db import migrations + +def migrate_stock(apps, schema_editor): + try: + old_stock = apps.get_model("stock", "StockItem") + except LookupError: + print("The Stock app is not installed. Skipping migration step.") + return + + new_stock = apps.get_model("rapid_sales_tool", "StockItem") + new_stock.objects.bulk_create([ + new_stock(pk = old_object.pk, + item_name = old_object.item_name, + item_count = old_object.item_count, + unit_cost = old_object.unit_cost) + for old_object in old_stock.objects.all()]) + +def migrate_orders(apps, schema_editor): + try: + old_orders = apps.get_model("orders", "Order") + except LookupError: + print("The Orders app is not installed. Skipping migration step.") + return + + new_stock = apps.get_model("rapid_sales_tool", "StockItem") + new_orders = apps.get_model("rapid_sales_tool", "Order") + new_orders.objects.bulk_create([ + new_orders(pk = old_object.pk, + customer_name = old_object.customer_name, + item = new_stock(pk=old_object.item.pk), + item_quantity = old_object.item_quantity, + order_price = old_object.order_price, + is_paid = old_object.is_paid) + for old_object in old_orders.objects.all()]) + +class Migration(migrations.Migration): + + dependencies = [ + ('rapid_sales_tool', '0001_initial'), + ] + + operations = [ + migrations.RunPython(migrate_stock, migrations.RunPython.noop), + migrations.RunPython(migrate_orders, migrations.RunPython.noop), + ] + + if global_apps.is_installed('orders'): + dependencies.append(('orders', '0001_initial')) + if global_apps.is_installed('stock'): + dependencies.append(('stock', '0001_initial')) \ No newline at end of file diff --git a/stock/__init__.py b/stock/__init__.py new file mode 100644 index 0000000..e69de29 diff --git a/stock/admin.py b/stock/admin.py new file mode 100644 index 0000000..8c38f3f --- /dev/null +++ b/stock/admin.py @@ -0,0 +1,3 @@ +from django.contrib import admin + +# Register your models here. diff --git a/stock/apps.py b/stock/apps.py new file mode 100644 index 0000000..de8e50c --- /dev/null +++ b/stock/apps.py @@ -0,0 +1,7 @@ +from __future__ import unicode_literals + +from django.apps import AppConfig + + +class StockConfig(AppConfig): + name = 'stock' diff --git a/stock/forms.py b/stock/forms.py new file mode 100644 index 0000000..c2a5bf2 --- /dev/null +++ b/stock/forms.py @@ -0,0 +1,13 @@ +from django import forms +from django.forms import ModelForm +from .models import StockItem + +class AddItemForm(ModelForm): + class Meta: + model = StockItem + fields = '__all__' + +class AddStockForm(ModelForm): + class Meta: + model = StockItem + fields = ['item_count','unit_cost'] \ No newline at end of file diff --git a/stock/migrations/0001_initial.py b/stock/migrations/0001_initial.py new file mode 100644 index 0000000..57d911f --- /dev/null +++ b/stock/migrations/0001_initial.py @@ -0,0 +1,25 @@ +# -*- coding: utf-8 -*- +# Generated by Django 1.9.3 on 2016-03-27 23:17 +from __future__ import unicode_literals + +from django.db import migrations, models + + +class Migration(migrations.Migration): + + initial = True + + dependencies = [ + ] + + operations = [ + migrations.CreateModel( + name='StockItem', + fields=[ + ('id', models.AutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')), + ('item_name', models.CharField(max_length=255)), + ('item_count', models.PositiveIntegerField()), + ('unit_cost', models.DecimalField(decimal_places=2, max_digits=17)), + ], + ), + ] diff --git a/stock/migrations/__init__.py b/stock/migrations/__init__.py new file mode 100644 index 0000000..e69de29 diff --git a/stock/models.py b/stock/models.py new file mode 100644 index 0000000..1cff260 --- /dev/null +++ b/stock/models.py @@ -0,0 +1,8 @@ +from __future__ import unicode_literals + +from django.db import models + +class StockItem(models.Model): + item_name = models.CharField(max_length=255) + item_count = models.PositiveIntegerField() + unit_cost = models.DecimalField(max_digits=17, decimal_places=2) \ No newline at end of file diff --git a/stock/tests.py b/stock/tests.py new file mode 100644 index 0000000..7ce503c --- /dev/null +++ b/stock/tests.py @@ -0,0 +1,3 @@ +from django.test import TestCase + +# Create your tests here. diff --git a/stock/views.py b/stock/views.py new file mode 100644 index 0000000..f041242 --- /dev/null +++ b/stock/views.py @@ -0,0 +1,45 @@ +import requests +from django.conf import settings +from django.core.urlresolvers import reverse +from django.template import RequestContext +from django.shortcuts import HttpResponseRedirect, render, get_object_or_404, HttpResponse +from .forms import * +from .models import * + +def stock(request): + items = StockItem.objects.all() + if request.method == 'POST': + form = AddItemForm(request.POST) + if form.is_valid(): + form.save() + return HttpResponseRedirect(reverse(stock)) + else: + addItemForm = AddItemForm() + addStockForm = AddStockForm() + return render(request, 'public/stock.html', {'addItemForm': addItemForm, 'addStockForm': addStockForm, 'items': items, 'service_name': settings.SERVICE_NAME}, context_instance=RequestContext(request)) + +def editStock(request, stock_id): + stock_item = get_object_or_404(StockItem, pk=stock_id) + item_instance = get_object_or_404(StockItem, pk=stock_id) + if request.method == 'POST': + form = AddStockForm(request.POST, instance=item_instance) + if form.is_valid(): + item_count = form.instance.item_count + stock_item.item_count + unit_cost = ((form.instance.item_count * form.instance.unit_cost) + (stock_item.item_count * stock_item.unit_cost)) / item_count + form.instance.item_count = item_count + form.instance.unit_cost = unit_cost + form.save() + return HttpResponseRedirect(reverse(stock)) + else: + raise Http404("Stock item does not exist") + +def deleteStock(request): + if request.method == 'POST': + response = HttpResponse() + item_id = request.POST['item_id'] + stock_item = get_object_or_404(StockItem, pk=item_id) + stock_item.delete() + response.status_code = 200 + return response + else: + Http404("Why are you here?") \ No newline at end of file