#include <bits/stdc++.h>
using namespace std;
int n, m, ans[500005], cnt, tr[500005];
long long mu[500005];
vector<pair<int, int> > ke[500005];
struct node {
  int num0;
  bool f;
  long long val;
  node *lc, *rc;
  node(int num0 = 1) : num0(num0) {
    f = 0;
    val = 0;
    lc = rc = NULL;
  }
};
struct tt {
  node *cur;
  int u;
  tt(node *cur = NULL, int u = 0) : cur(cur), u(u) {}
};
void push(int l, int r, node *cur) {
  if (!cur->f) return;
  if (cur->lc == NULL) cur->lc = new node((l + r) / 2 - l + 1);
  if (cur->rc == NULL) cur->rc = new node(r - (l + r) / 2);
  cur->lc->f = cur->rc->f = 1;
  cur->f = 0;
  cur->lc->val = cur->rc->val = 0;
}
bool compare(int l, int r, node *a, node *b) {
  if (a->val == b->val) return 0;
  if (l == r) return a->val == 0;
  push(l, r, a);
  push(l, r, b);
  if (a->rc->val == b->rc->val) return compare(l, (l + r) / 2, a->lc, b->lc);
  return compare((l + r) / 2 + 1, r, a->rc, b->rc);
}
class cmp {
 public:
  bool operator()(tt a, tt b) { return !compare(0, 500005, a.cur, b.cur); }
};
priority_queue<tt, vector<tt>, cmp> q;
vector<node *> d, root;
void setup() {
  cin >> n >> m;
  for (int i = 1; i <= m; ++i) {
    int u, v, w;
    cin >> u >> v >> w;
    ke[u].push_back(make_pair(v, w));
    ke[v].push_back(make_pair(u, w));
  }
}
node *build(int l, int r) {
  node *newnode = new node(r - l + 1);
  if (l == r) return newnode;
  newnode->lc = build(l, (l + r) / 2);
  newnode->rc = build((l + r) / 2 + 1, r);
  return newnode;
}
void init() {
  mu[0] = 1;
  for (int i = 1; i <= 500005 - 5; ++i) mu[i] = (mu[i - 1] << 1) % 1000000007;
  for (int i = 1; i <= n + 1; ++i) d.push_back(NULL);
}
int get0(int l, int r, node *cur, int x, int y) {
  if (l > y || r < x) return 0;
  if (x <= l && r <= y) return cur->num0;
  push(l, r, cur);
  return get0(l, (l + r) / 2, cur->lc, x, y) +
         get0((l + r) / 2 + 1, r, cur->rc, x, y);
}
int find0(int l, int r, node *cur, int x) {
  if (l == r) return l;
  push(l, r, cur);
  if (cur->rc->num0 >= x) return find0((l + r) / 2 + 1, r, cur->rc, x);
  return find0(l, (l + r) / 2, cur->lc, x - cur->rc->num0);
}
node *update(int l, int r, node *cur, int x, int y) {
  node *newnode = new node(r - l + 1);
  if (l == r && r == y) {
    newnode->num0 = 0;
    newnode->val = 1;
    return newnode;
  }
  if (x <= l && r < y) {
    newnode->val = 0;
    newnode->f = 1;
    return newnode;
  }
  push(l, r, cur);
  if (l > y || (l + r) / 2 < x)
    newnode->lc = cur->lc;
  else
    newnode->lc = update(l, (l + r) / 2, cur->lc, x, y);
  if ((l + r) / 2 + 1 > y || r < x)
    newnode->rc = cur->rc;
  else
    newnode->rc = update((l + r) / 2 + 1, r, cur->rc, x, y);
  newnode->num0 = newnode->lc->num0 + newnode->rc->num0;
  newnode->val = ((newnode->rc->val * mu[(l + r) / 2 - l + 1]) % 1000000007 +
                  newnode->lc->val) %
                 1000000007;
  return newnode;
}
void work() {
  int s, t;
  cin >> s >> t;
  init();
  root.push_back(d[s] = build(0, 500005));
  q.push(tt(d[s], s));
  while (q.size()) {
    node *cur = q.top().cur;
    int u = q.top().u;
    q.pop();
    if (d[u] != cur) continue;
    if (u == t) {
      while (u != s) {
        ans[++cnt] = u;
        u = tr[u];
      }
      cout << cur->val << '\n' << cnt + 1 << '\n' << s << " ";
      for (int i = cnt; i > 0; --i) cout << ans[i] << " ";
      return;
    }
    for (int i = 0; i < ke[u].size(); ++i) {
      int v = ke[u][i].first;
      int w = ke[u][i].second;
      int pos0 = find0(0, 500005, d[u], get0(0, 500005, d[u], w, 500005));
      node *gt = update(0, 500005, d[u], w, pos0);
      if (d[v] != NULL)
        if (!compare(0, 500005, gt, d[v])) continue;
      d[v] = gt;
      tr[v] = u;
      q.push(tt(d[v], v));
    }
  }
  cout << -1;
}
int main() {
  ios_base::sync_with_stdio(0);
  cin.tie();
  cout.tie();
  setup();
  work();
}
