#include <bits/stdc++.h>
using namespace std;
mt19937 Rand(time(0));
const int maxn = 600 + 5;
const long long maxc = 1e9 + 7;
vector<pair<int, int>> adj[maxn];
int n, numNode, s, t, m, nteam, k;
int Start[maxn], idone[maxn], idtwo[maxn], a[maxn];
int d[maxn][maxn];
void dijkstra(int s, int d[]) {
  d[s] = 0;
  priority_queue<pair<int, int>, vector<pair<int, int>>,
                 greater<pair<int, int>>>
      q;
  q.push({0, s});
  while (!q.empty()) {
    int u = q.top().second;
    int du = q.top().first;
    q.pop();
    if (du != d[u]) continue;
    for (__typeof((adj[u]).begin()) it = (adj[u]).begin(); it != (adj[u]).end();
         ++it) {
      if (d[it->first] > d[u] + it->second) {
        d[it->first] = d[u] + it->second;
        q.push({d[it->first], it->first});
      }
    }
  }
}
struct MaxFlow {
  vector<vector<int>> adj;
  struct edge {
    int u, v, cap, flow;
  };
  vector<edge> Edge;
  vector<int> trace;
  int n, s, t, max_flow;
  void init(int n, int s, int t) {
    this->n = n, this->s = s, this->t = t;
    this->max_flow = 0;
    Edge.clear();
    adj.assign(n + 1, vector<int>());
  }
  void add_edge(int u, int v, int cap, int flow = 0) {
    adj[u].push_back(Edge.size());
    Edge.push_back({u, v, cap, flow});
    adj[v].push_back(Edge.size());
    Edge.push_back({v, u, 0, 0});
  }
  bool find_path() {
    trace.assign(n + 1, -1);
    trace[s] = 0;
    queue<int> q;
    q.push(s);
    while (!q.empty()) {
      int u = q.front();
      q.pop();
      for (auto i : adj[u])
        if (Edge[i].cap - Edge[i].flow > 0) {
          int v = Edge[i].v;
          if (trace[v] == -1) {
            q.push(v);
            trace[v] = i;
          }
        }
    }
    return trace[t] != -1;
  }
  void inc_flow() {
    int delta = 1e9;
    for (int u = t; u != s; u = Edge[trace[u]].u) {
      delta = min(delta, Edge[trace[u]].cap - Edge[trace[u]].flow);
    }
    for (int u = t; u != s; u = Edge[trace[u]].u) {
      Edge[trace[u]].flow += delta;
      Edge[trace[u] ^ 1].flow -= delta;
    }
    max_flow += delta;
  }
  int getMaxFlow() {
    while (find_path()) inc_flow();
    return max_flow;
  }
} mf;
bool check(int lim) {
  mf.init(numNode, s, t);
  for (int u = (1); u <= (n); ++u)
    for (int v = (1); v <= (n); ++v)
      if (d[u][v] <= lim) {
        mf.add_edge(idone[u], idtwo[v], 1);
      }
  for (int u = (1); u <= (n); ++u) mf.add_edge(s, idone[u], a[u]);
  for (int u = (1); u <= (n); ++u) mf.add_edge(idtwo[u], t, 1);
  return mf.getMaxFlow() >= k;
}
void solve() {
  for (int i = (1); i <= (n); ++i) idone[i] = ++numNode;
  for (int i = (1); i <= (n); ++i) idtwo[i] = ++numNode;
  s = ++numNode, t = ++numNode;
  int l = -1, r = 1731312;
  while (r - l > 1) {
    int mid = (l + r) >> 1;
    if (check(mid))
      r = mid;
    else
      l = mid;
  }
  cout << (r == 1731312 ? -1 : r);
}
int main() {
  ios_base::sync_with_stdio(0);
  cin.tie(0);
  cout.tie(0);
  cin >> n >> m >> nteam >> k;
  for (int i = (1); i <= (nteam); ++i) cin >> Start[i], a[Start[i]]++;
  while (m--) {
    int u, v, c;
    cin >> u >> v >> c;
    adj[u].push_back({v, c});
    adj[v].push_back({u, c});
  }
  memset(d, (60), sizeof(d));
  for (int i = (1); i <= (n); ++i)
    if (a[i]) dijkstra(i, d[i]);
  solve();
  return 0;
}
