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

Docker related support enhanced #2

Open
wants to merge 8 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
4 changes: 4 additions & 0 deletions .env.db-sample
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
# db related environment variables
POSTGRES_DB=clix_dashboard_db
POSTGRES_USER=admin_clixdata
POSTGRES_PASSWORD=clixdata
30 changes: 30 additions & 0 deletions .env.dev-sample
Original file line number Diff line number Diff line change
@@ -0,0 +1,30 @@
# Include db related environment variables via sourcing ./.env.db
./.env.db-sample

#Hint to assgin values to following variables:
# DB_HOST: db service name in case of docker-compose and db container name in case of docker run
# DB_PORT: db container port (inside container one not the host one)
# DATABASE_URL: 'postgres+psycopg2://<db_username>:<db_userpassword>@<db_host>:<db_port>/<db_databasename>'
# FLASK_ENV: production in prod senario and development in dev senarios
# prod senario: production
# dev senario: development
# FLASK_APP_FOLDER: location (root directory) of the App or Application orProject
# prod senario: /home/clix_dashboard_backend/app
# dev senario: /usr/src/clix/app
# SECRET_KEY: Generate and assign value to the variable

# App related environment variables
DB_HOST=clix_dashboard_postgres
DB_PORT=5432
DATABASE_URL=postgresql://admin_clixdata:clixdata@clix_dashboard_postgres:5432/clix_dashboard_db
FLASK_APP_FOLDER=/home/clix_dashboard_backend/app
FLASK_ENV=development
SECRET_KEY=your_secret_key
FLASK_APP=/home/clix_dashboard_backend/clix_dashboard_backend.py

# variables from config.py of backend
#TESTING : Use can't get
#DATABASE_TEST_URL : Not assigned anywhere
#STATIC_FOLDER : (worth assigning in config.py, not needed here)
#MEDIA_FOLDER : (worth assigning in config.py, not needed here)
#DEBUG : (worth assigning in config.py, not needed here)
31 changes: 31 additions & 0 deletions .env.prod-sample
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
# Include db related environment variables via sourcing ./.env.db
./.env.db-sample

#Hint to assgin values to following variables:
# DB_HOST: db service name in case of docker-compose and db container name in case of docker run
# DB_PORT: db container port (inside container one not the host one)
# DATABASE_URL: 'postgres+psycopg2://<db_username>:<db_userpassword>@<db_host>:<db_port>/<db_databasename>'
# FLASK_ENV: production in prod senario and development in dev senarios
# prod senario: production
# dev senario: development
# FLASK_APP_FOLDER: location (root directory) of the App or Application orProject
# prod senario: /home/clix_dashboard_backend/app
# dev senario: /usr/src/clix/app
# SECRET_KEY: Generate and assign value to the variable

# App related environment variables
DB_HOST=clix_dashboard_postgres
DB_PORT=5432
DATABASE_URL=postgresql://$POSTGRES_USER:$POSTGRES_PASSWORD@$DB_HOST:$DB_PORT/$POSTGRES_DB
clix_dashboard_db
FLASK_APP_FOLDER=/home/clix_dashboard_backend/app
FLASK_ENV=production
SECRET_KEY=your_secret_key
FLASK_APP=/home/clix_dashboard_backend/clix_dashboard_backend.py

# variables from config.py of backend
#TESTING : Use can't get
#DATABASE_TEST_URL : Not assigned anywhere
#STATIC_FOLDER : (worth assigning in config.py, not needed here)
#MEDIA_FOLDER : (worth assigning in config.py, not needed here)
#DEBUG : (worth assigning in config.py, not needed here)
66 changes: 20 additions & 46 deletions Dockerfile
Original file line number Diff line number Diff line change
@@ -1,53 +1,27 @@
FROM python:3.6-alpine
# pull official base image
FROM python:3.8.0-alpine

#RUN useradd -r -u 900 -m -c "clix_dashboard_backend account" -d /home/clix_dashboard_backend -s /bin/false clix_dashboard_backend
RUN adduser -D clix_dashboard_backend
# set environment variables
ENV PYTHONDONTWRITEBYTECODE 1
ENV PYTHONUNBUFFERED 1

WORKDIR /home/clix_dashboard_backend

COPY requirements.txt requirements.txt

RUN python -m venv venv
RUN apk add --no-cache --virtual .build-deps \
gcc \
python3-dev \
musl-dev \
postgresql-dev \
libffi-dev \
py-cffi \
&& venv/bin/pip install --no-cache-dir -r requirements.txt \
&& apk del --no-cache .build-deps
RUN apk --no-cache add libpq
#RUN venv/bin/pip install --no-cache-dir -r requirements.txt
#RUN apk update && apk add postgresql-dev gcc python3-dev musl-dev
#RUN venv/bin/pip install --no-cache-dir gunicorn psycopg2

COPY app app
COPY migrations migrations
COPY SchoolImages SchoolImages
COPY clix_dashboard_backend.py config.py entrypoint.sh ./
# install psycopg2 dependencies
RUN apk update \
&& apk add --no-cache gcc python3-dev musl-dev postgresql-dev libffi-dev py-cffi libpq \
&& mkdir /home/clix_dashboard_backend

ARG DOCKER_UID

RUN apk --no-cache add shadow && \
usermod -u ${DOCKER_UID} clix_dashboard_backend \
&& groupmod -g ${DOCKER_UID} clix_dashboard_backend \
&& echo "Set clix_dashboard_backend's uid to ${DOCKER_UID}"


RUN chmod a+x entrypoint.sh
# set work directory
WORKDIR /home/clix_dashboard_backend

ENV FLASK_APP clix_dashboard_backend.py
# copy project code and required file as well as directories
COPY ./app/ /home/clix_dashboard_backend/app/

RUN chown -R clix_dashboard_backend:clix_dashboard_backend ./
USER clix_dashboard_backend
# copy project code and required file as well as directories
COPY ./requirements.txt ./clix_dashboard_backend.py ./config.py ./entrypoint.sh /home/clix_dashboard_backend/

EXPOSE 5000
#CMD ["flask", "run"]
#RUN source venv/bin/activate \
# && flask db init --directory migration \
# && mkdir migrations \
# && mv migration/* migrations/ \
# && deactivate
# install dependencies
RUN pip install --upgrade pip \
&& pip install -r requirements.txt

ENTRYPOINT ["./entrypoint.sh"]
# run entrypoint.sh
ENTRYPOINT ["sh", "/home/clix_dashboard_backend/entrypoint.sh"]
75 changes: 75 additions & 0 deletions Dockerfile.prod
Original file line number Diff line number Diff line change
@@ -0,0 +1,75 @@
# Ref: https://testdriven.io/blog/dockerizing-flask-with-postgres-gunicorn-and-nginx/
# : https://github.com/testdrivenio/flask-on-docker

###########
# BUILDER #
###########

# pull official base image
FROM python:3.8.0-alpine as builder

# set environment variables
ENV PYTHONDONTWRITEBYTECODE 1
ENV PYTHONUNBUFFERED 1

# install psycopg2 dependencies
RUN apk update \
&& apk add --no-cache gcc python3-dev musl-dev postgresql-dev libffi-dev py-cffi libpq \
&& mkdir /home/clix_dashboard_backend

# set work directory
WORKDIR /home/clix_dashboard_backend

# copy project code and required file as well as directories
COPY ./app/ /home/clix_dashboard_backend/app/

# copy project code and required file as well as directories
COPY ./requirements.txt ./clix_dashboard_backend.py ./config.py ./entrypoint.sh /home/clix_dashboard_backend/

# lint
RUN pip install --upgrade pip \
&& pip install flake8
RUN flake8 --ignore=E501,F401 .

# install dependencies
RUN pip wheel --no-cache-dir --no-deps --wheel-dir /home/clix_dashboard_backend/wheels -r requirements.txt


####################
# FINAL PROD IMAGE #
####################

# pull official base image
FROM python:3.8.0-alpine

# create directory for the app user
RUN mkdir -p /home/clix_dashboard_backend

# create the clix_dashboard_backend user
RUN addgroup -S clix_dashboard_backend && adduser -S clix_dashboard_backend -G clix_dashboard_backend

# create the appropriate directories
ENV CUSER_HOME=/home/clix_dashboard_backend/
WORKDIR $CUSER_HOME

# install dependencies
RUN apk update && apk add libpq
COPY --from=builder /home/clix_dashboard_backend/wheels /wheels
COPY --from=builder /home/clix_dashboard_backend/requirements.txt .
RUN pip install --upgrade pip \
&& pip install --no-cache /wheels/*

# copy project code and required file as well as directories
COPY ./app/ /home/clix_dashboard_backend/app/

# copy project code and required file as well as directories
COPY ./requirements.txt ./clix_dashboard_backend.py ./config.py ./entrypoint.sh /home/clix_dashboard_backend/

# chown all the files to the clix_dashboard_backend user
RUN chown -R clix_dashboard_backend:clix_dashboard_backend $CUSER_HOME

# change to the clix_dashboard_backend user
USER clix_dashboard_backend

# run entrypoint.prod.sh
ENTRYPOINT ["sh", "/home/clix_dashboard_backend/entrypoint.prod.sh"]
29 changes: 17 additions & 12 deletions clix_dashboard_backend.py
Original file line number Diff line number Diff line change
Expand Up @@ -14,18 +14,23 @@ def make_shell_context():
# return dataupload.upload_schooldata(schooldata, db = db)

@app.cli.command()
@click.option('--username', help='To create admin user for clix_dashboard_backend, done during initial setup')
def create_admin(username):
print('Creating Admin User for CLIx_dashboard_backend\n')
print('Enter Password for UserName: {}'.format(username))
passwd = input()
print('Enter emailID:')
email = input()
adminuser = User(username=username, password=passwd)
#adminuser.set_password(password=passwd)
@click.option('--username', help='Username to create admin user for clix_dashboard_backend (mostly used during initial setup) {Mandatory}')
@click.option('--password', help='Password to create admin user for clix_dashboard_backend (mostly used during initial setup)')
@click.option('--email', help='Email to create admin user for clix_dashboard_backend (mostly used during initial setup)')
def create_admin(username, password = "", email = ""):
print('Creating Admin User(', username, ') for CLIx_dashboard_backend\n')

if not password:
print('Enter Password for UserName( {}'.format(username), "):")
password = input()

if not email:
print('Enter emailID:')
email = input()

adminuser = User(username=username, password=password)
#adminuser.set_password(password=password)
db.session.add(adminuser)
db.session.commit()
print('Congratulations, you are now a admin user for CLIx Daashboard Backend!')
return None


return None
9 changes: 2 additions & 7 deletions config.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,18 +3,13 @@


class Config(object):
POSTGRES_USER = '<db user name>'
POSTGRES_PASSWORD = '<db user password>'
POSTGRES_PORT = '<db port>'
SECRET_KEY = os.environ.get('SECRET_KEY') or 'you-will-never-guess'
SQLALCHEMY_DATABASE_URI = os.environ.get('DATABASE_URL') or \
'postgres+psycopg2://<db admin user>:<db admin password>@172.17.0.1:<available port>/clix_dashboard_db'
SECRET_KEY = os.environ.get('SECRET_KEY')
SQLALCHEMY_DATABASE_URI = os.environ.get('DATABASE_URL')
SQLALCHEMY_TRACK_MODIFICATIONS = False
POSTS_PER_PAGE = 20
BCRYPT_LOG_ROUNDS = 13
UPLOAD_FOLDER = basedir + '/SchoolImages'


class BaseConfig:
"""Base configuration"""
TESTING = False
Expand Down
26 changes: 11 additions & 15 deletions create_school_ro_users.py
Original file line number Diff line number Diff line change
@@ -1,14 +1,11 @@
from app import app
from config import Config

# TO get all the relevant credentials for postgresql backend

DB_TYPE = 'postgresql'
DB_DRIVER = 'psycopg2'
DB_USER = Config.POSTGRES_USER
DB_PASS = Config.POSTGRES_PASSWORD
DB_HOST = '172.17.0.1'
DB_PORT = Config.POSTGRES_PORT
DB_USER = 'admin_clixdata'
DB_PASS = 'clixdata'
DB_HOST = 'clix_dashboard_postgres'
DB_PORT = '5432'
DB_NAME = 'clix_dashboard_db'
POOL_SIZE = 50
SQLALCHEMY_DATABASE_URI = '%s+%s://%s:%s@%s:%s/%s' % (DB_TYPE, DB_DRIVER, DB_USER,
Expand All @@ -24,7 +21,7 @@
Engine = create_engine(SQLALCHEMY_DATABASE_URI, pool_size=POOL_SIZE, max_overflow=0)
connec = Engine.connect()

# Code to delete rows specific to a state
# Code to delete rows specific to a state
#'''
#select * from metric1 where substring(split_part(school_server_code, '-', 2) from 1 for 2) = 'tg';
#'''
Expand All @@ -46,9 +43,9 @@ def create_ro_school_admins(school_admins):
'''

try:
create_role = """ CREATE ROLE readaccess;
GRANT USAGE ON SCHEMA public TO readaccess;
GRANT SELECT ON ALL TABLES IN SCHEMA public TO readaccess;
create_role = """ CREATE ROLE readaccess;
GRANT USAGE ON SCHEMA public TO readaccess;
GRANT SELECT ON ALL TABLES IN SCHEMA public TO readaccess;
ALTER DEFAULT PRIVILEGES IN SCHEMA public GRANT SELECT ON TABLES TO readaccess;
"""

Expand All @@ -61,8 +58,8 @@ def create_ro_school_admins(school_admins):

for each in school_admins:
user = each
assign_users = """ CREATE USER {0} WITH PASSWORD 'clixdata';
GRANT readaccess TO {0};
assign_users = """ CREATE USER {0} WITH PASSWORD 'clixdata';
GRANT readaccess TO {0};
""".format(user)

list_users = """SELECT u.usename AS "User Name" FROM pg_catalog.pg_user u;
Expand Down Expand Up @@ -97,5 +94,4 @@ def create_school_users(schools):

if __name__ == '__main__':
create_ro_school_admins(get_all_schools())
create_school_users(get_all_schools())

create_school_users(get_all_schools())
1 change: 0 additions & 1 deletion docker-entrypoint-initdb.d/init_db.sql

This file was deleted.

Loading