#!/usr/bin/env python
# -*- coding: utf-8 -*-
##
#
# Vaisala software source code file
#
# Copyright (c) Vaisala Oyj 2015. All rights reserved.
#
##

"""
Command-line tool for adding a new map layer to radarsw.

Example:

With Legend
rsw-layer-add -n 'Lightning' -u '/lightning' -l 'lightning:ltg_combined_25' -s http://tstorm-manager-eb-dev.bouds.vaisala.com/geolegends/ltg_combined_25.sld -m ltg_combined_25,ltg_types

If an error is presented about a missing 'requests' library, try:
pip install requests (Linux, Windows)
or
yum install python-requests (Linux)
or see:
http://docs.python-requests.org/en/latest/user/install/
"""

import sys
import argparse
import requests
import json


LOGIN_LOC="/login"
LOGOUT_LOC="/logout"
ADD_LAYER_LOC="/configure/addLayer"
COOKIE_PARAM_NAME="set-cookie"
XSRF_PARAM_NAME="xsrfToken"


def dbg(msg):
    if debug:
        print(msg)


def get_args():
    parser = argparse.ArgumentParser("rsw-layer-add", formatter_class=argparse.ArgumentDefaultsHelpFormatter)
    parser.add_argument("-a", "--appurl", help="Application URL.", default="localhost:34080")
    parser.add_argument("-p", "--adminpass", help="Admin password.", default="admin123")
    parser.add_argument("-r", "--adminuser", help="Admin username.", default="admin")
    parser.add_argument("-n", "--layername", help="Name of layer to be added.")
    parser.add_argument("-u", "--layerurl", help="URL of layer to be added.")
    parser.add_argument("-l", "--layer", help="Layer to be added.")
    parser.add_argument("-s", "--sldurl", help="Layer style. SLD url.")
    parser.add_argument("-m", "--sldnames", help="Layer style names.")
    parser.add_argument("-d", "--debug", dest="debug", action="store_true", help="Enable debug messages")
    return parser.parse_args()


def is_response_ok(response):
    return response.status_code == requests.codes.ok


def process_appurl(appurl):
    if not appurl.startswith("http://") and not appurl.startswith("https://"):
        return "http://" + appurl
    return appurl


def extract_xsrf_token(body):
    return json.loads(body)[XSRF_PARAM_NAME];


def login(appurl, adminuser, adminpass):
    req_params = {"username":adminuser,"password":adminpass}
    dbg("Making login request to {0} with params {1}".format(appurl + LOGIN_LOC, req_params))
    res = requests.post(appurl + LOGIN_LOC, params=req_params)
    dbg("Login response:")
    dbg("status: {0}".format(res.status_code))
    dbg("reason: {0}".format(res.reason))
    dbg("headers: {0}".format(res.headers))
    dbg("body: {0}".format(res.content))
    return res


def logout(appurl, xsrftoken, cookies):
    req_params = {"token":xsrftoken}
    dbg("Making logout request to {0} with params {1}".format(appurl + LOGOUT_LOC, req_params))
    res = requests.post(appurl + LOGOUT_LOC, params=req_params, cookies=dict(cookies))
    dbg("Logout response:")
    dbg("status: {0}".format(res.status_code))
    dbg("reason: {0}".format(res.reason))
    dbg("headers: {0}".format(res.headers))
    dbg("body: {0}".format(res.content))
    return res


def add_layer(appurl, layername, layerurl, layer, sldurl, sldnames, xsrftoken, cookies):
    req_params = {"layerName":layername,"url":layerurl,"layer":layer,"sldUrl":sldurl,"sldNames":sldnames,"token":xsrftoken}
    dbg("Making add layer request to {0} with params {1}".format(appurl + ADD_LAYER_LOC, req_params))
    res = requests.post(appurl + ADD_LAYER_LOC, params=req_params, cookies=dict(cookies))
    dbg("Add layer response:")
    dbg("status: {0}".format(res.status_code))
    dbg("reason: {0}".format(res.reason))
    dbg("headers: {0}".format(res.headers))
    dbg("body: {0}".format(res.content))
    return res


def main():
    args = get_args()
    global debug
    debug = args.debug
    appurl = process_appurl(args.appurl)

    print("Attempting to log in to the application...")
    login_res = login(appurl, args.adminuser, args.adminpass)
    if not is_response_ok(login_res):
        print("Failed to login to application ({0} {1}), exiting...".format(
            login_res.status_code, login_res.reason))
        sys.exit(1)
    print("Successfully logged in to application.")

    print("Attempting to add layer...")
    try:
        token = extract_xsrf_token(login_res.content)
        dbg("xsrfToken: {0}".format(token))
        layer_res = add_layer(appurl, args.layername, args.layerurl,
                              args.layer, args.sldurl, args.sldnames,
                              token, login_res.cookies)
        if is_response_ok(layer_res):
            print("Successfully added layer.")
        else:
            print("Failed to add layer ({0} {1}), exiting...".format(
                layer_res.status_code, layer_res.reason))
    except Exception as e:
        print("Unexpected error during add layer operation: {}".format(e))
    finally:
        print("Attempting to log out...")
        logout_res = logout(appurl, token, login_res.cookies)
        if not is_response_ok(logout_res):
            print("Failed to log out ({0} {1})".format(logout_res.status_code, logout_res.reason))
            sys.exit(1)
        print("Successfully logged out.")


if __name__ == '__main__':
    main()
