Spaces:
Sleeping
Sleeping
File size: 7,231 Bytes
7d11191 e7dbf80 7d11191 e7dbf80 7d11191 4f1311e e7dbf80 7d11191 4f1311e 7d11191 4f1311e 7d11191 e7dbf80 4f1311e cf5b48d 4f1311e cf5b48d 4f1311e 7d11191 4f1311e cf5b48d 4f1311e cf5b48d 4f1311e cf5b48d 4f1311e 7d11191 4f1311e 7d11191 cf5b48d 4f1311e 7d11191 cf5b48d 4f1311e 7d11191 4f1311e e7dbf80 1aa73ec f5aeb1a 4f1311e f5aeb1a e7dbf80 4f1311e 1aa73ec 4f1311e cf5b48d 4f1311e 1aa73ec 4f1311e cf5b48d 4f1311e e7dbf80 4f1311e cf5b48d 4f1311e cf5b48d 4f1311e 7d11191 4f1311e 7d11191 4f1311e cf5b48d e7dbf80 7d11191 f5aeb1a | 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 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 | import gradio as gr
import pandas as pd
import os
from translator_utils import process_rows, revert_rows, download_dataset, LOCAL_FILENAME, ENV_HF_TOKEN, read_csv_robust
def load_data():
"""Load the dataset safely using robust reader."""
if not os.path.exists(LOCAL_FILENAME):
try:
download_dataset()
except:
return pd.DataFrame()
df = read_csv_robust(LOCAL_FILENAME)
if df.empty:
return df
try:
if 'Judul_Inggris' not in df.columns:
df['Judul_Inggris'] = ""
if 'Isi_Inggris' not in df.columns:
df['Isi_Inggris'] = ""
df = df.fillna("")
return df
except:
return pd.DataFrame()
def force_refresh_data():
"""Forces a re-download and reload of the data."""
try:
download_dataset(force=True)
return load_data(), "Data refreshed successfully."
except Exception as e:
return pd.DataFrame(), f"Failed to refresh data: {e}"
def get_pending_data(full_df):
"""Filter for rows that are NOT fully translated."""
if full_df.empty:
return full_df
mask = (full_df['Judul_Inggris'].str.strip() == "") | (full_df['Isi_Inggris'].str.strip() == "")
df_view = full_df[mask].copy()
df_view.reset_index(inplace=True)
df_view.rename(columns={'index': 'ID'}, inplace=True)
df_view.insert(0, "Select", False)
return df_view
def get_history_data(full_df, date_filter=""):
"""Filter for rows that ARE fully translated."""
if full_df.empty:
return full_df
mask = (full_df['Judul_Inggris'].str.strip() != "") & (full_df['Isi_Inggris'].str.strip() != "")
df_view = full_df[mask].copy()
df_view.reset_index(inplace=True)
df_view.rename(columns={'index': 'ID'}, inplace=True)
if date_filter:
df_view = df_view[df_view['Tanggal'].str.contains(date_filter, case=False, na=False)]
# Add 'Select' column for Revert functionality
df_view.insert(0, "Select", False)
return df_view
def on_translate_selected(df_data, token, progress=gr.Progress()):
"""Callback when user clicks 'Translate Selected'."""
selected_rows = df_data[df_data["Select"] == True]
if selected_rows.empty:
return gr.DataFrame(), gr.DataFrame(), "No rows selected!"
try:
indices = selected_rows['ID'].tolist()
indices = [int(i) for i in indices]
except KeyError:
return gr.DataFrame(), gr.DataFrame(), "Error: ID column missing."
updated_df, msg = process_rows(indices, token=token, progress=progress)
pending = get_pending_data(updated_df)
history = get_history_data(updated_df)
return pending, history, msg
def on_revert_selected(df_data, token, progress=gr.Progress()):
"""Callback when user clicks 'Revert Selected'."""
selected_rows = df_data[df_data["Select"] == True]
if selected_rows.empty:
return gr.DataFrame(), gr.DataFrame(), "No rows selected!"
try:
indices = selected_rows['ID'].tolist()
indices = [int(i) for i in indices]
except KeyError:
return gr.DataFrame(), gr.DataFrame(), "Error: ID column missing."
# Call revert
updated_df, msg = revert_rows(indices, token=token, progress=progress)
# Refresh views
pending = get_pending_data(updated_df)
history = get_history_data(updated_df)
return pending, history, msg
def filter_history(date_input):
df = load_data()
return get_history_data(df, date_input)
def refresh_views():
df, msg = force_refresh_data()
pending = get_pending_data(df)
history = get_history_data(df)
return pending, history, msg
def auto_select_pending(df_view):
"""Automatically selects the first 10 rows in the pending view."""
if df_view.empty:
return df_view, "No rows to select."
# Set 'Select' to True for the first 10 rows
limit = min(10, len(df_view))
df_view.loc[:limit-1, "Select"] = True
return df_view, f"Auto-selected top {limit} rows."
# CSS to ensure columns are readable
custom_css = """
/* Fix minimum width for content columns */
table td:nth-child(5), table td:nth-child(6), table td:nth-child(7), table td:nth-child(8) {
min-width: 300px !important;
white-space: pre-wrap !important;
}
/* Ensure row ID is small */
table td:nth-child(2) {
width: 50px !important;
}
"""
with gr.Blocks(title="Auto AI News Translator") as app:
gr.Markdown("# Auto AI News Translator")
gr.Markdown("Translate news from Indonesian to English (with Chunking). Select rows to translate.")
# Inject default value from Env Var
hf_token = gr.Textbox(
label="HF Token (Optional for Persistence)",
placeholder="hf_... (Leave empty if set in ENV)",
type="password",
value=ENV_HF_TOKEN
)
with gr.Row():
status_output = gr.Textbox(label="Status", value="Ready", interactive=False, scale=4)
refresh_btn = gr.Button("🔄 Refresh Data (Force Redownload)", scale=1)
with gr.Tabs():
with gr.TabItem("Translate Pending"):
gr.Markdown("Select rows to translate and click Submit.")
with gr.Row():
auto_select_btn = gr.Button("Auto-Select Next 10", size="sm")
translate_btn = gr.Button("Translate Selected Rows", variant="primary")
pending_df_comp = gr.DataFrame(
value=get_pending_data(load_data()),
label="Pending Translations",
interactive=True,
wrap=True,
datatype=["bool", "number"] + ["str"] * 6
)
auto_select_btn.click(
fn=auto_select_pending,
inputs=[pending_df_comp],
outputs=[pending_df_comp, status_output]
)
with gr.TabItem("History (Revert Supported)"):
gr.Markdown("Select rows to delete translation and move back to Pending.")
date_filter = gr.Textbox(label="Filter by Date (YYYY-MM-DD)")
# History now has checkbox
history_df_comp = gr.DataFrame(
value=get_history_data(load_data()),
label="Translation History",
interactive=True,
wrap=True,
datatype=["bool", "number"] + ["str"] * 6
)
with gr.Row():
date_filter.change(fn=filter_history, inputs=[date_filter], outputs=[history_df_comp])
revert_btn = gr.Button("Revert Selected (Delete & Move to Pending)", variant="stop")
translate_btn.click(
fn=on_translate_selected,
inputs=[pending_df_comp, hf_token],
outputs=[pending_df_comp, history_df_comp, status_output]
)
revert_btn.click(
fn=on_revert_selected,
inputs=[history_df_comp, hf_token],
outputs=[pending_df_comp, history_df_comp, status_output]
)
refresh_btn.click(
fn=refresh_views,
outputs=[pending_df_comp, history_df_comp, status_output]
)
if __name__ == "__main__":
app.launch(css=custom_css)
|