File size: 4,368 Bytes
3fd3eea
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
#!/bin/bash
# ─────────────────────────────────────────────────────────────────────────────
#  refresh_sources.sh β€” Standalone refresh script
#
#  Can be called:
#    1. At boot (from init_clickhouse.sh)
#    2. On-demand (from gateway.py when you hit /api/refresh)
#    3. Periodically (from background loop)
#
#  Actions:
#    β€’ git clone (first run) or git pull (subsequent) for each source
#    β€’ CREATE OR REPLACE VIEW for each defined view
# ─────────────────────────────────────────────────────────────────────────────
set -e

CONFIG="/app/sources.yaml"
USER_FILES="/app/ch/user_files"
CH_URL="http://127.0.0.1:8123"

# Optional argument: "sync_only" = just git pull, no view creation
# (used by background loop to avoid hammering ClickHouse with DDL)
MODE="${1:-full}"

SOURCE_COUNT=$(yq '.sources | length' "$CONFIG")

echo "{"
echo "  \"mode\": \"$MODE\","
echo "  \"source_count\": $SOURCE_COUNT,"
echo "  \"sources\": ["

for i in $(seq 0 $((SOURCE_COUNT - 1))); do
  NAME=$(yq ".sources[$i].name" "$CONFIG")
  REPO_URL=$(yq ".sources[$i].repo_url" "$CONFIG")
  LOCAL_DIR=$(yq ".sources[$i].local_dir" "$CONFIG")
  CLONE_DEPTH=$(yq ".sources[$i].clone_depth // 1" "$CONFIG")
  BRANCH=$(yq ".sources[$i].branch // \"\"" "$CONFIG")

  TARGET="$USER_FILES/$LOCAL_DIR"

  BRANCH_FLAG=""
  if [ -n "$BRANCH" ] && [ "$BRANCH" != "null" ] && [ "$BRANCH" != "" ]; then
    BRANCH_FLAG="--branch $BRANCH"
  fi

  # ── Git sync ──
  GIT_STATUS="unknown"
  GIT_OUTPUT=""
  if [ ! -d "$TARGET" ]; then
    GIT_OUTPUT=$(git clone --depth "$CLONE_DEPTH" $BRANCH_FLAG "$REPO_URL" "$TARGET" 2>&1) || true
    GIT_STATUS="cloned"
  else
    GIT_OUTPUT=$(cd "$TARGET" && git fetch --depth 1 origin && git reset --hard origin/$(git rev-parse --abbrev-ref HEAD) 2>&1) || true
    GIT_STATUS="pulled"
  fi

  LATEST_COMMIT=$(cd "$TARGET" && git log -1 --format='%h %s' 2>/dev/null || echo "unknown")

  # ── Trailing comma handling ──
  COMMA=","
  if [ $i -eq $((SOURCE_COUNT - 1)) ] && [ "$MODE" = "sync_only" ]; then
    COMMA=""
  fi

  # ── View creation (only in "full" mode) ──
  VIEWS_JSON=""
  if [ "$MODE" = "full" ]; then
    NUM_VIEWS=$(yq ".sources[$i].views | length" "$CONFIG")
    VIEWS_JSON="\"views\": ["

    for v in $(seq 0 $((NUM_VIEWS - 1))); do
      VIEW_NAME=$(yq ".sources[$i].views[$v].view_name" "$CONFIG")
      FILE_GLOB=$(yq ".sources[$i].views[$v].file_glob" "$CONFIG")
      FORMAT=$(yq ".sources[$i].views[$v].format // \"Parquet\"" "$CONFIG")
      NUM_COLS=$(yq ".sources[$i].views[$v].columns | length // 0" "$CONFIG")

      FULL_GLOB="${LOCAL_DIR}/${FILE_GLOB}"

      # Build SELECT clause β€” explicit columns if defined, else SELECT *
      if [ "$NUM_COLS" -gt 0 ] 2>/dev/null; then
        COLS=""
        for c in $(seq 0 $((NUM_COLS - 1))); do
          COL=$(yq ".sources[$i].views[$v].columns[$c]" "$CONFIG")
          if [ -z "$COLS" ]; then
            COLS="$COL"
          else
            COLS="$COLS, $COL"
          fi
        done
        SELECT_CLAUSE="SELECT ${COLS}"
      else
        SELECT_CLAUSE="SELECT *"
      fi

      SQL="CREATE OR REPLACE VIEW ${VIEW_NAME} AS ${SELECT_CLAUSE} FROM file('${FULL_GLOB}', ${FORMAT})"

      VIEW_STATUS="ok"
      if ! curl -sf "$CH_URL" --data "$SQL" 2>/dev/null; then
        VIEW_STATUS="error"
      fi

      VIEW_COMMA=","
      if [ $v -eq $((NUM_VIEWS - 1)) ]; then
        VIEW_COMMA=""
      fi

      VIEWS_JSON="${VIEWS_JSON}{\"name\":\"${VIEW_NAME}\",\"glob\":\"${FULL_GLOB}\",\"select\":\"${SELECT_CLAUSE}\",\"status\":\"${VIEW_STATUS}\"}${VIEW_COMMA}"
    done

    VIEWS_JSON="${VIEWS_JSON}]"
  fi

  # Determine trailing comma for this source
  COMMA=","
  if [ $i -eq $((SOURCE_COUNT - 1)) ]; then
    COMMA=""
  fi

  if [ "$MODE" = "full" ]; then
    echo "    {\"name\":\"$NAME\",\"git_status\":\"$GIT_STATUS\",\"latest_commit\":\"$LATEST_COMMIT\",$VIEWS_JSON}$COMMA"
  else
    echo "    {\"name\":\"$NAME\",\"git_status\":\"$GIT_STATUS\",\"latest_commit\":\"$LATEST_COMMIT\"}$COMMA"
  fi
done

echo "  ]"
echo "}"