Skip to content

Instantly share code, notes, and snippets.

@kalda341
Created November 18, 2019 21:37
Show Gist options
  • Save kalda341/4ac54513fd36d5ee9fdd5a2467232874 to your computer and use it in GitHub Desktop.
Save kalda341/4ac54513fd36d5ee9fdd5a2467232874 to your computer and use it in GitHub Desktop.
from django.db import transaction
from .models import Project as ProjectModel
from .errors import RevisionError, check_user_organisation
from . import project_file_services
def to_model(project):
return ProjectModel(
id=project.id,
revision=project.revision,
data=project.data,
organisation_id=project.organisation_id,
)
def from_model(model, files=None):
return Project(
id=model.id,
revision=model.revision,
data=model.data,
organisation_id=model.organisation_id,
files=files,
)
def queryset_for_user(user):
return ProjectModel.objects.filter(organisation_id=user.organisation_id)
def load_project_as_user(user, id):
check_user_organisation(user)
model = queryset_for_user(user).get(id=id)
files = project_file_services.load_files_for_project_as_user(
user=user, project_id=id
)
return from_model(model, files=files)
def load_projects_as_user(user):
check_user_organisation(user)
models = queryset_for_user(user).all()
return map(from_model, models)
def create_project_as_user(project, user):
check_user_organisation(user)
if project.id is not None:
raise ValueError("Cannot create project with id")
if project.revision != 0:
raise ValueError("Cannot create project with non-zero revision")
model = to_model(project)
model.organisation_id = user.organisation_id
model.revision += 1
model.save()
# There are no files because we just created it
return from_model(model, files=[])
def update_project_as_user(project, user):
check_user_organisation(user)
if project.id is None:
raise ValueError("Cannot update project without id")
if project.revision is None or project.revision < 1:
raise ValueError(
"Project revision must be greater than or equal to 1 to update"
)
with transaction.atomic():
model = queryset_for_user(user).select_for_update().get(id=project.id)
if model.revision != project.revision:
raise RevisionError("Revision is incorrect. Update blocked.")
# Only the data field can be updated
model.data = project.data
model.revision += 1
model.save()
files = project_file_services.load_files_for_project_as_user(
user=user, project_id=project.id
)
return from_model(model, files=files)
class Project:
def __init__(self, data, id=None, organisation_id=None, files=None, revision=0):
self.id = id
self.revision = revision
self.data = data
self.organisation_id = organisation_id
self.files = files
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment