#include <bits/stdc++.h>

using namespace std;

typedef long long ll;
typedef long double Double;
#define rep(i, n) for (int i = 0; i < (int)(n); i++)

int log2ceil(int n) {
    --n;
    n |= n >> 16;
    n |= n >> 8;
    n |= n >> 4;
    n |= n >> 2;
    n |= n >> 1;
    return n + 1;
}

template<typename Struct>
class SegmentTreeLazy {
public:
    using Monoid = typename Struct::Monoid;
    using Update = typename Struct::Update;
    using value_type = typename Struct::value_type;
    using update_type = typename Struct::update_type;

private:
    const int n;
    std::vector<value_type> data;
    std::vector<update_type> lazy;
    std::vector<bool> flag;

    void lazyset(int node, const update_type &update) {
        if (node < n) {
            if (flag[node]) {
                lazy[node] = Update::op(update, lazy[node]);
            } else {
                lazy[node] = update;
                flag[node] = true;
            }
        }
        data[node] = Struct::evaluate(update, data[node]);
    }

    void evaluate(int node) {
        if (!flag[node]) return;
        flag[node] = false;
        lazyset(node * 2 + 0, lazy[node]);
        lazyset(node * 2 + 1, lazy[node]);
    }

    void update_sub(int l, int r, int node, int lb, int ub,
                    const update_type &update) {
        if (ub <= l || r <= lb) {
            return;
        }
        if (l <= lb && ub <= r) {
            lazyset(node, update);
            return;
        }
        evaluate(node);
        const int mid = (lb + ub) / 2;
        update_sub(l, r, node * 2 + 0, lb, mid, update);
        update_sub(l, r, node * 2 + 1, mid, ub, update);
        data[node] = Monoid::op(data[node * 2 + 0], data[node * 2 + 1]);
    }

    value_type query_sub(int l, int r, int node, int lb, int ub) {
        if (ub <= l || r <= lb) return Monoid::id();
        if (l <= lb && ub <= r) {
            return data[node];
        }
        evaluate(node);
        const int mid = (lb + ub) / 2;
        value_type lval = query_sub(l, r, node * 2 + 0, lb, mid);
        value_type rval = query_sub(l, r, node * 2 + 1, mid, ub);
        return Monoid::op(lval, rval);
    }

public:
    SegmentTreeLazy(int count, const value_type &init = Monoid::id()) :
            n(log2ceil(count)), data(n * 2), lazy(n), flag(n, false) {
        fill(begin(data) + n, end(data), init);
        for (int i = n - 1; i >= 1; i--) {
            data[i] = Monoid::op(data[i * 2 + 0], data[i * 2 + 1]);
        }
    };

    void update(int l, int r, const update_type &f) {
        update_sub(l, r, 1, 0, n, f);
    }

    value_type query(int l, int r) {
        return query_sub(l, r, 1, 0, n);

    }
};

// RMQ
struct RMQMonoid {
    using value_type = ll;

    static value_type id() { return 1000000000000000000ll; }

    static value_type op(const value_type &l, const value_type &r) {
        return std::min(l, r);
    }
};

// LeftHandSide
struct LazyEval {
    using value_type = ll;

    static value_type op(const value_type &l, const value_type &r) {
        return std::min(l, r);
    }
};

struct RangeUpdateRMQ {
    using Monoid = RMQMonoid;
    using Update = LazyEval;
    using value_type = typename Monoid::value_type;
    using update_type = typename Update::value_type;

    static value_type evaluate(const update_type &update, const value_type &v) {
        return min(update, v);
    }
};


// RMQ
struct RMQ {
    using value_type = ll;

    static value_type id() { return 1000000000000000000ll; }

    static value_type op(const value_type &l, const value_type &r) {
        return std::min(l, r);
    }
};

struct P {
    friend bool operator<(const P &lhs, const P &rhs) {
        return lhs.l < rhs.l;
    }

    ll l, r;
    ll c;
};


void solve(long long N, long long M, std::vector<long long> L,
           std::vector<long long> R, std::vector<long long> C) {
    vector<P> ps;

    for (int i = 0; i < M; i++) {
        ps.push_back({L[i] - 1, R[i], C[i]});
    }

    SegmentTreeLazy<RangeUpdateRMQ> seg(N);
    sort(ps.begin(), ps.end());

    seg.update(0, 1, 0);
    for (auto p : ps) {
        ll v = seg.query(p.l, p.r);
        seg.update(p.l, p.r, v + p.c);
    }
    if (seg.query(N - 1, N) == 1000000000000000000ll) {
        cout << -1 << endl;
    } else {
        cout << seg.query(N - 1, N) << endl;
    }


}

int main() {
    long long N;
    scanf("%lld", &N);
    long long M;
    scanf("%lld", &M);
    std::vector<long long> L(M);
    std::vector<long long> R(M);
    std::vector<long long> C(M);
    for (int i = 0; i < M; i++) {
        scanf("%lld", &L[i]);
        scanf("%lld", &R[i]);
        scanf("%lld", &C[i]);
    }
    solve(N, M, std::move(L), std::move(R), std::move(C));
    return 0;
}


Measured memory_bytes: 8560