Пример #1
0
def api_list_subject_events():
    """
    :rtype: Response
    :return the list of subjects in json format
    """
    # from sqlalchemy.sql import text
    from collections import namedtuple

    if 'POST' == request.method:
        subject_id = utils.get_safe_int(request.form.get('subject_id'))
    else:
        subject_id = utils.get_safe_int(request.args.get('subject_id'))

    query = """
SELECT
    evtID AS id
    , evtRedcapArm AS redcap_arm
    , evtRedcapEvent AS redcap_event
    , evtDayOffset AS day_offset
    , COUNT(sfID) AS total_files
    , GROUP_CONCAT(sfFileName) AS file_names
FROM
     Event
    JOIN SubjectFile USING(evtID)
WHERE
    sbjID = :subject_id
GROUP BY
    evtID
    """
    # print subject_id, query
    result = db.session.execute(query, {'subject_id': subject_id})
    Event = namedtuple('Event', result.keys())
    events = [Event(*r) for r in result.fetchall()]
    events_ser = [i._asdict() for i in events]
    return utils.jsonify_success({'subject_events': events_ser})
Пример #2
0
def find_subject():
    """
    Side effect: This function will synchronize the list of subjects in the
    local database with REDCap by sending a REDCap API call
    if the local database contains no entries.

    :rtype: Response
    :return the list of subjects in json format
    """
    invalid_id = -1

    if 'POST' == request.method:
        search_id = utils.get_safe_int(request.form['name'], invalid_id,
                                       invalid_id)
    else:
        search_id = utils.get_safe_int(request.args.get('name'), invalid_id,
                                       invalid_id)

    matching = []

    if search_id != invalid_id:
        # @TODO: optimize to return one column by default
        # http://stackoverflow.com/questions/7533146/how-do-i-select-additional-manual-values-along-with-an-sqlalchemy-query
        subject_list = SubjectEntity.query.filter(
            SubjectEntity.redcap_id.like("%{}%".format(search_id))).all()
        matching = [subject.redcap_id for subject in subject_list]

        if len(matching) == 0:
            api_import_redcap_subjects()

    return utils.jsonify_success({'subjects': matching})
Пример #3
0
def find_subject():
    """
    Side effect: This function will synchronize the list of subjects in the
    local database with REDCap by sending a REDCap API call
    if the local database contains no entries.

    :rtype: Response
    :return the list of subjects in json format
    """
    invalid_id = -1

    if 'POST' == request.method:
        search_id = utils.get_safe_int(request.form['name'],
                                       invalid_id, invalid_id)
    else:
        search_id = utils.get_safe_int(request.args.get('name'),
                                       invalid_id,
                                       invalid_id)

    matching = []

    if search_id != invalid_id:
        # @TODO: optimize to return one column by default
        # http://stackoverflow.com/questions/7533146/how-do-i-select-additional-manual-values-along-with-an-sqlalchemy-query
        subject_list = SubjectEntity.query.filter(
            SubjectEntity.redcap_id.like("%{}%".format(search_id))
        ).all()
        matching = [subject.redcap_id for subject in subject_list]

        if len(matching) == 0:
            api_import_redcap_subjects()

    return utils.jsonify_success({'subjects': matching})
Пример #4
0
def api_list_subject_events():
    """
    :rtype: Response
    :return the list of subjects in json format
    """
    # from sqlalchemy.sql import text
    from collections import namedtuple

    if 'POST' == request.method:
        subject_id = utils.get_safe_int(request.form.get('subject_id'))
    else:
        subject_id = utils.get_safe_int(request.args.get('subject_id'))

    query = """
SELECT
    evtID AS id
    , evtRedcapArm AS redcap_arm
    , evtRedcapEvent AS redcap_event
    , evtDayOffset AS day_offset
    , COUNT(sfID) AS total_files
    , GROUP_CONCAT(sfFileName) AS file_names
FROM
     Event
    JOIN SubjectFile USING(evtID)
WHERE
    sbjID = :subject_id
GROUP BY
    evtID
    """
    # print subject_id, query
    result = db.session.execute(query, {'subject_id': subject_id})
    Event = namedtuple('Event', result.keys())
    events = [Event(*r) for r in result.fetchall()]
    events_ser = [i._asdict() for i in events]
    return utils.jsonify_success({'subject_events': events_ser})
Пример #5
0
def api_list_logs():
    """
    Render the specified page of event logs
    @TODO: show user-specific logs for non-admins?

    :rtype: string
    :return the json list of logs
    """
    if 'POST' == request.method:
        per_page = get_safe_int(request.form.get('per_page'))
        page_num = get_safe_int(request.form.get('page_num'))
    else:
        per_page = get_safe_int(request.args.get('per_page'))
        page_num = get_safe_int(request.args.get('page_num'))

    """
    pagination = LogEntity.query.paginate(page_num, per_page, False)
    items = [i.serialize() for i in pagination.items]
    app.logger.debug("per_page: {}, page_num: {}".format(per_page, page_num))
    return jsonify_success(dict(total_pages=pagination.pages,
                                list_of_events=items))
    """
    logs, total_pages = log_manager.get_logs(per_page, page_num)
    # logs_list = [x.to_visible() for x in logs]
    return jsonify_success(dict(list_of_events=logs, total_pages=total_pages))
Пример #6
0
def download_file():
    """ Download a file using the database id """

    if 'POST' == request.method:
        file_id = utils.get_safe_int(request.form['file_id'])
    else:
        file_id = utils.get_safe_int(request.args.get('file_id'))

    subject_file = SubjectFileEntity.get_by_id(file_id)
    file_path = subject_file.get_full_path(
        app.config['REDIDROPPER_UPLOAD_SAVED_DIR'])
    LogEntity.file_downloaded(session['uuid'], file_path)
    return send_file(file_path, as_attachment=True)
Пример #7
0
def download_file():
    """ Download a file using the database id """

    if 'POST' == request.method:
        file_id = utils.get_safe_int(request.form['file_id'])
    else:
        file_id = utils.get_safe_int(request.args.get('file_id'))

    subject_file = SubjectFileEntity.get_by_id(file_id)
    file_path = subject_file.get_full_path(
        app.config['REDIDROPPER_UPLOAD_SAVED_DIR'])
    LogEntity.file_downloaded(session['uuid'], file_path)
    return send_file(file_path, as_attachment=True)
Пример #8
0
def api_list_subjects():
    """
    Render the table of subjects and their file counts

    :rtype: Response
    :return json
    """
    per_page = get_safe_int(request.form.get('per_page'))
    page_num = get_safe_int(request.form.get('page_num'))

    total_pages, list_of_subjects = \
        subject_manager.get_subjects_on_page(per_page, page_num)
    return jsonify(total_pages=total_pages, list_of_subjects=list_of_subjects)
Пример #9
0
def api_list_logs(per_page, page_num):
    """
    @app.route('/api/list_logs/<per_page>/<page_num>', methods=['GET', 'POST'])
    @app.route('/api/list_logs/<per_page>', defaults={'page_num': 1})
    Render the specified page of event logs
    @TODO: show user-specific logs for non-admins?

    :rtype: string
    :return the json list of logs
    """
    per_page = get_safe_int(per_page)
    page_num = get_safe_int(page_num)
    logs, total_pages = log_manager.get_logs(per_page, page_num)
    # logs_list = [x.to_visible() for x in logs]
    return jsonify(list_of_events=logs, total_pages=total_pages)
Пример #10
0
def api_send_verification_email():
    """
    @TODO: allow POST only
    @TODO: Send Verification Email to user_id

    :rtype: Response
    :return the success or failed in json format
    """
    user_id = get_safe_int(request.form.get('user_id'))
    user = UserEntity.get_by_id(user_id)
    user = UserEntity.get_by_id(1)
    user.email = app.config['MAIL_SENDER_SUPPORT']

    try:
        emails.send_verification_email(user)
        return jsonify_success({"message": "Verification email was sent."})
    except Exception as exc:
        details = "Connection config: {}/{}:{}".format(
            app.config['MAIL_USERNAME'], app.config['MAIL_SERVER'],
            app.config['MAIL_PORT'])
        app.logger.debug(details)
        return jsonify_error({
            "message":
            "Unable to send email due: {} {}".format(exc, details)
        })
Пример #11
0
def api_list_subject_event_files():
    """
    :rtype: Response
    :return the list of subjects in json format
    """

    if 'POST' == request.method:
        subject_id = utils.get_safe_int(request.form.get('subject_id'))
        event_id = utils.get_safe_int(request.form.get('event_id'))
    else:
        subject_id = utils.get_safe_int(request.args.get('subject_id'))
        event_id = utils.get_safe_int(request.args.get('event_id'))

    files = SubjectFileEntity \
        .query.filter_by(subject_id=subject_id,
                         event_id=event_id).all()
    files_ser = [i.serialize() for i in files]
    return utils.jsonify_success({'subject_event_files': files_ser})
Пример #12
0
def api_list_users():
    """
    Retrieve the users cached in the local database
    :rtype: Response
    :return
    """
    if 'POST' == request.method:
        per_page = utils.get_safe_int(request.form.get('per_page'))
        page_num = utils.get_safe_int(request.form.get('page_num'))
    else:
        per_page = utils.get_safe_int(request.args.get('per_page'))
        page_num = utils.get_safe_int(request.args.get('page_num'))

    pagination = UserEntity.query.order_by(
        db.desc(UserEntity.id)).paginate(page_num, per_page, False)
    items = [i.serialize() for i in pagination.items]
    return utils.jsonify_success(
        {"total_pages": pagination.pages, "list_of_users": items})
Пример #13
0
def api_list_users():
    """
    Retrieve the users cached in the local database
    :rtype: Response
    :return
    """
    if 'POST' == request.method:
        per_page = utils.get_safe_int(request.form.get('per_page'))
        page_num = utils.get_safe_int(request.form.get('page_num'))
    else:
        per_page = utils.get_safe_int(request.args.get('per_page'))
        page_num = utils.get_safe_int(request.args.get('page_num'))

    pagination = UserEntity.query.order_by(
        db.desc(UserEntity.id)).paginate(page_num, per_page, False)
    items = [i.serialize() for i in pagination.items]
    return utils.jsonify_success(
        {"total_pages": pagination.pages, "list_of_users": items})
Пример #14
0
def api_list_subject_event_files():
    """
    :rtype: Response
    :return the list of subjects in json format
    """

    if 'POST' == request.method:
        subject_id = utils.get_safe_int(request.form.get('subject_id'))
        event_id = utils.get_safe_int(request.form.get('event_id'))
    else:
        subject_id = utils.get_safe_int(request.args.get('subject_id'))
        event_id = utils.get_safe_int(request.args.get('event_id'))

    files = SubjectFileEntity \
        .query.filter_by(subject_id=subject_id,
                         event_id=event_id).all()
    files_ser = [i.serialize() for i in files]
    return utils.jsonify_success({'subject_event_files': files_ser})
Пример #15
0
def api_list_logs():
    """
    Render the specified page of event logs
    @TODO: show user-specific logs for non-admins?

    :rtype: string
    :return the json list of logs
    """
    if 'POST' == request.method:
        per_page = utils.get_safe_int(request.form.get('per_page'))
        page_num = utils.get_safe_int(request.form.get('page_num'))
    else:
        per_page = utils.get_safe_int(request.args.get('per_page'))
        page_num = utils.get_safe_int(request.args.get('page_num'))

    logs, total_pages = LogEntity.get_logs(per_page, page_num)

    return utils.jsonify_success(
        dict(list_of_events=logs, total_pages=total_pages))
Пример #16
0
def api_list_users():
    """
    @TODo: use the page_num in the query
    :rtype: Response
    :return
    """
    if 'POST' == request.method:
        per_page = get_safe_int(request.form.get('per_page'))
        page_num = get_safe_int(request.form.get('page_num'))
    else:
        per_page = get_safe_int(request.args.get('per_page'))
        page_num = get_safe_int(request.args.get('page_num'))

    # users = UserEntity.query.filter(UserEntity.id >= 14).all()
    pagination = UserEntity.query.order_by(
        db.desc(UserEntity.id)).paginate(page_num, per_page, False)
    items = [i.serialize() for i in pagination.items]
    return jsonify_success({"total_pages": pagination.pages,
                            "list_of_users": items})
Пример #17
0
def api_list_logs():
    """
    Render the specified page of event logs
    @TODO: show user-specific logs for non-admins?

    :rtype: string
    :return the json list of logs
    """
    if 'POST' == request.method:
        per_page = utils.get_safe_int(request.form.get('per_page'))
        page_num = utils.get_safe_int(request.form.get('page_num'))
    else:
        per_page = utils.get_safe_int(request.args.get('per_page'))
        page_num = utils.get_safe_int(request.args.get('page_num'))

    logs, total_pages = LogEntity.get_logs(per_page, page_num)

    return utils.jsonify_success(
        dict(list_of_events=logs, total_pages=total_pages))
Пример #18
0
def api_list_users():
    """
    @TODo: use the page_num in the query
    :rtype: Response
    :return
    """
    per_page = get_safe_int(request.form.get('per_page'))
    page_num = get_safe_int(request.form.get('page_num'))
    app.logger.debug("Show page {} of users".format(page_num))

    users = UserEntity.query.all()
    # users = UserEntity.query.filter(UserEntity.id >= 14).all()

    if users is None:
        return make_response(pack_error("no users found"))

    list_of_users = [i.serialize() for i in users]
    total_pages = math.ceil(len(list_of_users)/float(per_page))
    data = {"total_pages": total_pages, "list_of_users": list_of_users}
    return make_response(pack_success_result(data))
Пример #19
0
def api_list_users():
    """
    @TODo: use the page_num in the query
    :rtype: Response
    :return
    """
    if 'POST' == request.method:
        per_page = get_safe_int(request.form.get('per_page'))
        page_num = get_safe_int(request.form.get('page_num'))
    else:
        per_page = get_safe_int(request.args.get('per_page'))
        page_num = get_safe_int(request.args.get('page_num'))

    # users = UserEntity.query.filter(UserEntity.id >= 14).all()
    pagination = UserEntity.query.order_by(db.desc(UserEntity.id)).paginate(
        page_num, per_page, False)
    items = [i.serialize() for i in pagination.items]
    return jsonify_success({
        "total_pages": pagination.pages,
        "list_of_users": items
    })
Пример #20
0
def api_deactivate_account():
    """
    De-activate an user.
    @TODO: should change expiration date too?

    :rtype: Response
    :return the success or failed in json format
    """
    user_id = get_safe_int(request.form.get('user_id'))
    user = UserEntity.get_by_id(user_id)
    user = UserEntity.update(user, active=False)
    return jsonify_success({"message": "User deactivated."})
Пример #21
0
def api_deactivate_account():
    """
    De-activate an user.
    @TODO: should change expiration date too?

    :rtype: Response
    :return the success or failed in json format
    """
    user_id = get_safe_int(request.form.get('user_id'))
    user = UserEntity.get_by_id(user_id)
    user = UserEntity.update(user, active=False)
    return jsonify_success({"message": "User deactivated."})
Пример #22
0
def api_list_local_subjects():
    """
    Render the table of subjects and their file counts

    @see http://pythonhosted.org/Flask-SQLAlchemy/api.html
        #flask.ext.sqlalchemy.BaseQuery.paginate
    paginate(page, per_page=20, error_out=True)

    :rtype: Response
    :return json
    """
    if 'POST' == request.method:
        per_page = utils.get_safe_int(request.form.get('per_page'))
        page_num = utils.get_safe_int(request.form.get('page_num'))
    else:
        per_page = utils.get_safe_int(request.args.get('per_page'))
        page_num = utils.get_safe_int(request.args.get('page_num'))

    pagination = SubjectEntity.query.paginate(page_num, per_page, False)
    items = [i.serialize() for i in pagination.items]
    return utils.jsonify_success(
        dict(total_pages=pagination.pages, list_of_subjects=items))
Пример #23
0
def api_list_local_subjects():
    """
    Render the table of subjects and their file counts

    @see http://pythonhosted.org/Flask-SQLAlchemy/api.html
        #flask.ext.sqlalchemy.BaseQuery.paginate
    paginate(page, per_page=20, error_out=True)

    :rtype: Response
    :return json
    """
    if 'POST' == request.method:
        per_page = utils.get_safe_int(request.form.get('per_page'))
        page_num = utils.get_safe_int(request.form.get('page_num'))
    else:
        per_page = utils.get_safe_int(request.args.get('per_page'))
        page_num = utils.get_safe_int(request.args.get('page_num'))

    pagination = SubjectEntity.query.paginate(page_num, per_page, False)
    items = [i.serialize() for i in pagination.items]
    return utils.jsonify_success(
        dict(total_pages=pagination.pages, list_of_subjects=items))
Пример #24
0
def api_activate_account():
    """
    Activate an user.
    @TODO: should change expiration date too?

    :rtype: Response
    :return the success or failed in json format
    """
    user_id = utils.get_safe_int(request.form.get('user_id'))
    user = UserEntity.get_by_id(user_id)
    user = UserEntity.update(user, active=True)
    LogEntity.account_modified(session['uuid'],
                               "User activated: {}".format(user))
    return utils.jsonify_success({"message": "User activated."})
Пример #25
0
def api_expire_account():
    """
    Change the `User.usrAccessExpiresAt` to today's date and 00:00:00 time
    effectively blocking the user access.

    :rtype: Response
    :return the success or failed in json format
    """
    user_id = get_safe_int(request.form.get('user_id'))
    user = UserEntity.get_by_id(user_id)
    today = datetime.today()
    today_start = datetime(today.year, today.month, today.day)
    user = UserEntity.update(user, access_expires_at=today_start)
    return jsonify_success({"message": "User access was expired."})
Пример #26
0
def api_expire_account():
    """
    Change the `User.usrAccessExpiresAt` to today's date and 00:00:00 time
    effectively blocking the user access.

    :rtype: Response
    :return the success or failed in json format
    """
    user_id = get_safe_int(request.form.get('user_id'))
    user = UserEntity.get_by_id(user_id)
    today = datetime.today()
    today_start = datetime(today.year, today.month, today.day)
    user = UserEntity.update(user, access_expires_at=today_start)
    return jsonify_success({"message": "User access was expired."})
Пример #27
0
def api_activate_account():
    """
    Activate an user.
    @TODO: should change expiration date too?

    :rtype: Response
    :return the success or failed in json format
    """
    user_id = utils.get_safe_int(request.form.get('user_id'))
    user = UserEntity.get_by_id(user_id)
    user = UserEntity.update(user, active=True)
    LogEntity.account_modified(session['uuid'],
                               "User activated: {}".format(user))
    return utils.jsonify_success({"message": "User activated."})
Пример #28
0
def api_list_logs():
    """
    Render the specified page of event logs
    @TODO: show user-specific logs for non-admins?

    :rtype: string
    :return the json list of logs
    """
    if 'POST' == request.method:
        per_page = get_safe_int(request.form.get('per_page'))
        page_num = get_safe_int(request.form.get('page_num'))
    else:
        per_page = get_safe_int(request.args.get('per_page'))
        page_num = get_safe_int(request.args.get('page_num'))
    """
    pagination = LogEntity.query.paginate(page_num, per_page, False)
    items = [i.serialize() for i in pagination.items]
    app.logger.debug("per_page: {}, page_num: {}".format(per_page, page_num))
    return jsonify_success(dict(total_pages=pagination.pages,
                                list_of_events=items))
    """
    logs, total_pages = log_manager.get_logs(per_page, page_num)
    # logs_list = [x.to_visible() for x in logs]
    return jsonify_success(dict(list_of_events=logs, total_pages=total_pages))
Пример #29
0
def api_expire_account():
    """
    Change the `User.usrAccessExpiresAt` to today's date and 00:00:00 time
    effectively blocking the user access.

    :rtype: Response
    :return the success or failed in json format
    """
    user_id = utils.get_safe_int(request.form.get('user_id'))
    user = UserEntity.get_by_id(user_id)
    today = datetime.today()
    today_start = datetime(today.year, today.month, today.day)
    user = UserEntity.update(user, access_expires_at=today_start)
    # @TODO: add dedicated log type
    LogEntity.account_modified(
        session['uuid'], "User access was expired. {}".format(user.email))
    return utils.jsonify_success({"message": "User access was expired."})
Пример #30
0
def api_expire_account():
    """
    Change the `User.usrAccessExpiresAt` to today's date and 00:00:00 time
    effectively blocking the user access.

    :rtype: Response
    :return the success or failed in json format
    """
    user_id = utils.get_safe_int(request.form.get('user_id'))
    user = UserEntity.get_by_id(user_id)
    today = datetime.today()
    today_start = datetime(today.year, today.month, today.day)
    user = UserEntity.update(user, access_expires_at=today_start)
    # @TODO: add dedicated log type
    LogEntity.account_modified(session['uuid'],
                               "User access was expired. {}".format(user.email))
    return utils.jsonify_success({"message": "User access was expired."})
Пример #31
0
def api_send_verification_email():
    """
    @TODO: Send Verification Email to user_id

    :rtype: Response
    :return the success or failed in json format
    """
    user_id = utils.get_safe_int(request.form.get('user_id'))
    user = UserEntity.get_by_id(user_id)

    try:
        emails.send_verification_email(user)
        return utils.jsonify_success(
            {"message": "Verification email was sent."})
    except Exception as exc:
        details = "Connection config: {}/{}:{}".format(
            app.config['MAIL_USERNAME'],
            app.config['MAIL_SERVER'],
            app.config['MAIL_PORT'])
        app.logger.debug(details)
        return utils.jsonify_error(
            {"message": "Unable to send email due: {} {}".format(exc, details)})