import { Component } from '../../lib/vues6/vues6.js'
import { session } from '../service/Session.service.js'
import { location_service } from '../service/Location.service.js'
import { password_service } from '../service/Password.service.js'

const template = `
<div class="coreid-auth-page col-lg-6 col-md-8 col-sm-10 col-xs-12 offset-lg-3 offset-md-2 offset-sm-1 offset-xs-0 text-left">
    <div v-if="ready" class="coreid-auth-page-inner">
        <div class="coreid-header font-weight-light">{{ app_name }}</div>
        <span v-if="step === 0">
            <div class="coreid-message">
                {{ t['password.reset_prompt'].replace('APP_NAME', app_name) }}
                <span v-if="has_mfa">
                    <br><br>
                    {{ t['password.reset_invalidates'] }}
                </span>
            </div>
        </span>
        <span v-if="step === 1">
            <div class="form-group">
                <label for="coreid-password-reset-input-step-1">{{ t['password.enter_new_pw'] }}</label>
                <input
                    id="coreid-password-reset-input-step-1"
                    type="password"
                    v-model="password"
                    :placeholder="t['password.new_password']"
                    class="form-control"
                    @keyup="on_key_up"
                    :disabled="loading"
                    name="password"
                    ref="input_1"
                >
            </div>
            <div>
                <div class="other-message" v-if="step_1_calc_time">{{ t['password.calc_time'].replace('CALC_TIME', step_1_calc_time) }}</div>
                <div class="error-message" v-if="step_1_problem">{{ step_1_problem }}.</div>
            </div>
        </span>
        <span v-if="step === 2">
            <div class="form-group">
                <label for="coreid-password-reset-input-step-1">{{ t['password.confirm'] }}</label>
                <input
                    id="coreid-password-reset-input-step-2"
                    type="password"
                    v-model="confirm_password"
                    :placeholder="t['password.confirm_password']"
                    class="form-control"
                    @keyup="on_key_up"
                    :disabled="loading"
                    name="password_confirmation"
                    ref="input_2"
                >
            </div>
        </span>
        <div v-if="error_message" class="error-message">{{ error_message }}</div>
        <div v-if="other_message" class="other-message">{{ other_message }}</div>
        <div class="buttons text-right pad-top">
            <button
                type="button"
                class="btn btn-primary"
                @click="back_click"
                :disabled="loading"
            >{{ t['common.cancel'] }}</button>
            <button
                type="button"
                class="btn btn-primary"
                @click="continue_click"
                :disabled="loading || (step === 1 && !step_1_valid) || (step === 2 && !step_2_valid)"
            >{{ step === 2 ? t['password.change'] : t['common.continue'] }}</button>
        </div>
        <div class="coreid-loading-spinner" v-if="loading"><div class="inner"></div></div>
    </div>
</div>
`

export default class PasswordResetComponent extends Component {
    static get selector() { return 'coreid-password-reset-page' }
    static get template() { return template }
    static get props() { return ['app_name'] }

    constructor() {
        super()

        this.step = 0
        this.loading = false
        this.has_mfa = false

        this.error_message = ''
        this.other_message = ''

        this.step_1_valid = false
        this.step_1_calc_time = ''
        this.step_1_problem = ''

        this.step_2_valid = false

        this.password = ''
        this.confirm_password = ''
        this.t = {}
        this.ready = false
    }

    async vue_on_create() {
        this.has_mfa = !!session.get('user.has_mfa')

        this.t = await T(
            'password.reset_prompt',
            'password.reset_invalidates',
            'password.enter_new_pw',
            'password.calc_time',
            'password.confirm',
            'password.new_password',
            'password.confirm_password',
            'password.change',
            'password.reset_success',
            'common.unknown_error',
            'common.continue',
            'common.cancel'
        )

        this.ready = true
    }

    async back_click() {
        this.loading = true
        this.error_message = this.other_message = ''
        if ( this.step === 0 ) {
            await location_service.redirect('/dash/profile', 1500)
        } else {
            this.step -= 1
            this.loading = false
        }
    }

    async continue_click() {
        this.loading = true
        if ( this.step === 0 ) {
            this.step += 1
            this.error_message = this.other_message = ''
            this.loading = false
            this.$nextTick(() => {
                this.$refs.input_1.focus()
            })
        } else if ( this.step === 1 ) {
            if ( this.step_1_valid ) {
                this.step += 1
                this.error_message = this.other_message = ''
                this.$nextTick(() => {
                    this.$refs.input_2.focus()
                })
            }
            this.loading = false
        } else if ( this.step === 2 ) {
            if ( this.step_2_valid ) {
                try {
                    await password_service.reset(this.password)
                    this.other_message = this.t['password.reset_success']
                    await location_service.redirect('/dash/profile', 5000)
                } catch (e) {
                    let message = this.t['common.unknown_error']
                    if ( e.response && e.response.data && e.response.data.message ) {
                        message = e.response.data.message
                    }

                    this.error_message = message
                    this.loading = false
                }
            }

            this.loading = false
        }
    }

    on_key_up(event) {
        if ( this.step === 1 ) {
            const result = zxcvbn(this.password)
            this.step_1_calc_time = result.crack_times_display.offline_slow_hashing_1e4_per_second
            this.step_1_problem = result.feedback.warning
            this.step_1_valid = result.score >= 3 // TODO make this configurable
        } else if ( this.step === 2 ) {
            this.step_2_valid = this.password === this.confirm_password
        }

        if ( event.keyCode === 13 ) {
            // Enter was pressed
            event.preventDefault()
            event.stopPropagation()
            return this.continue_click()
        }
    }
}
