Skip to content

Commit

Permalink
Merge branch 'main' into dmalone/officer-search-fix
Browse files Browse the repository at this point in the history
  • Loading branch information
DMalone87 committed Mar 11, 2024
2 parents bdcaf15 + 61b444e commit b94e0d1
Show file tree
Hide file tree
Showing 35 changed files with 1,583 additions and 103 deletions.
2 changes: 1 addition & 1 deletion .github/workflows/aws-ecs-deploy-backend.yml
Original file line number Diff line number Diff line change
Expand Up @@ -70,7 +70,7 @@ jobs:
id: login-ecr
uses: aws-actions/amazon-ecr-login@v2
- name: Build & Push Image to ECR
uses: kciter/aws-ecr-action@v4
uses: kciter/aws-ecr-action@v5
with:
access_key_id: ${{ secrets.AWS_ACCESS_KEY_ID }}
secret_access_key: ${{ secrets.AWS_SECRET_ACCESS_KEY }}
Expand Down
2 changes: 1 addition & 1 deletion .github/workflows/aws-ecs-deploy-frontend.yml
Original file line number Diff line number Diff line change
Expand Up @@ -74,7 +74,7 @@ jobs:
id: login-ecr
uses: aws-actions/amazon-ecr-login@v2
- name: Build & Push Image to ECR
uses: kciter/aws-ecr-action@v4
uses: kciter/aws-ecr-action@v5
with:
access_key_id: ${{ secrets.AWS_ACCESS_KEY_ID }}
secret_access_key: ${{ secrets.AWS_SECRET_ACCESS_KEY }}
Expand Down
2 changes: 1 addition & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -42,7 +42,7 @@ MIXPANEL_TOKEN=your_mixpanel_token
> **Note**
> When running locally, you may need to update one of the ports in the `.env` file if it conflicts with another application on your machine.
3. Build and run the project with `docker-compose build; docker-compose up -d; docker-compose logs -f app`
3. Build and run the project with `docker-compose build && docker-compose up -d && docker-compose logs -f`

## Installation (Frontend Only)

Expand Down
20 changes: 18 additions & 2 deletions backend/config.py
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
import os
from dotenv import load_dotenv
from datetime import timedelta

if os.environ.get("FLASK_ENV") != "production":
load_dotenv()

Expand All @@ -23,6 +22,11 @@ class Config(object):
POSTGRES_DB = os.environ.get("POSTGRES_DB", "police_data")

# Flask-Mail SMTP server settings
"""
Config settings for email sending
Put all of the information in your dotenv
config file
"""
MAIL_SERVER = os.environ.get("MAIL_SERVER")
MAIL_PORT = os.environ.get("MAIL_PORT")
MAIL_USE_SSL = bool(os.environ.get("MAIL_USE_SSL"))
Expand All @@ -31,9 +35,21 @@ class Config(object):
MAIL_PASSWORD = os.environ.get("MAIL_PASSWORD")
MAIL_DEFAULT_SENDER = os.environ.get(
"MAIL_DEFAULT_SENDER",
"National Police Data Coalition <{email}>".format(email=MAIL_USERNAME),
"National Police Data Coalition <{email}>".format(
email=MAIL_USERNAME),
)

"""
Testing configurations with Mailtrap Email testing, all the configurations
will be different--go to mailtrap for more information
"""
# MAIL_SERVER = 'sandbox.smtp.mailtrap.io'
# MAIL_PORT = 2525
# MAIL_USERNAME = '30a682ceaa0416'
# MAIL_PASSWORD = 'dbf502527604b1'
# MAIL_USE_TLS = True
# MAIL_USE_SSL = False

# Flask-User settings
USER_APP_NAME = (
"Police Data Trust" # Shown in and email templates and page footers
Expand Down
42 changes: 42 additions & 0 deletions backend/database/models/partner.py
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,41 @@ def get_value(self):
return 5


class Invitation(db.Model):
id = db.Column(db.Integer, primary_key=True, autoincrement=True)
partner_id = db.Column(
db.Integer, db.ForeignKey('partner.id'), primary_key=True)
user_id = db.Column(db.Integer, db.ForeignKey('user.id'), primary_key=True)
role = db.Column(db.Enum(MemberRole), nullable=False)
is_accepted = db.Column(db.Boolean, default=False)
# default to not accepted invite

def serialize(self):
return {
'id': self.id,
'partner_id': self.partner_id,
'user_id': self.user_id,
'role': self.role,
'is_accepted': self.is_accepted,
}


class StagedInvitation(db.Model):
id = db.Column(db.Integer, primary_key=True, autoincrement=True)
partner_id = db.Column(
db.Integer, db.ForeignKey('partner.id'), primary_key=True)
email = db.Column(db.String, unique=True, primary_key=True)
role = db.Column(db.Enum(MemberRole), nullable=False)

def serialize(self):
return {
'id': self.id,
'partner_id': self.partner_id,
'email': self.email,
'role': self.role
}


class PartnerMember(db.Model, CrudMixin):
def __init__(self, **kwargs):
super().__init__(**kwargs)
Expand All @@ -51,6 +86,13 @@ def create(self, refresh: bool = True):
self.date_joined = datetime.now()
return super().create(refresh)

def __repr__(self):
"""Represent instance as a unique string."""
return f"<PartnerMember( \
id={self.id}, \
partner_id={self.partner_id}, \
user_id={self.user_id})>"


class Partner(db.Model, CrudMixin):
def __init__(self, **kwargs):
Expand Down
1 change: 1 addition & 0 deletions backend/dto/__init__.py
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
# flake8: noqa: F401
from .user.register_user import RegisterUserDTO
from .user.login_user import LoginUserDTO
from .user.invite_user import InviteUserDTO
15 changes: 15 additions & 0 deletions backend/dto/user/invite_user.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
from pydantic import BaseModel, EmailStr
from enum import Enum


class MemberRole(str, Enum):
ADMIN = "Administrator"
PUBLISHER = "Publisher"
MEMBER = "Member"
SUBSCRIBER = "Subscriber"


class InviteUserDTO(BaseModel):
partner_id: int
email: EmailStr
role: MemberRole
19 changes: 18 additions & 1 deletion backend/routes/auth.py
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@
from pydantic.main import BaseModel
from ..auth import min_role_required, user_manager
from ..mixpanel.mix import track_to_mp
from ..database import User, UserRole, db
from ..database import User, UserRole, db, Invitation, StagedInvitation
from ..dto import LoginUserDTO, RegisterUserDTO
from ..schemas import UserSchema, validate

Expand Down Expand Up @@ -87,6 +87,23 @@ def register():
db.session.add(user)
db.session.commit()
token = create_access_token(identity=user.id)

"""
code to handle adding staged_invitations-->invitations for users
who have just signed up for NPDC
"""
staged_invite = StagedInvitation.query.filter_by(email=user.email).all()
if staged_invite is not None and len(staged_invite) > 0:
for instance in staged_invite:
new_invitation = Invitation(
user_id=user.id,
role=instance.role,
partner_id=instance.partner_id)
db.session.add(new_invitation)
db.session.commit()
StagedInvitation.query.filter_by(email=user.email).delete()
db.session.commit()

resp = jsonify(
{
"status": "ok",
Expand Down
Loading

0 comments on commit b94e0d1

Please sign in to comment.