Spaces:
Configuration error
Configuration error
Update app.py
Browse files
app.py
CHANGED
@@ -339,12 +339,12 @@ lottie_farm = load_lottie_url('https://assets5.lottiefiles.com/packages/lf20_yst
|
|
339 |
lottie_analysis = load_lottie_url('https://assets3.lottiefiles.com/packages/lf20_qp1q7mct.json')
|
340 |
lottie_report = load_lottie_url('https://assets9.lottiefiles.com/packages/lf20_vwcugezu.json')
|
341 |
|
342 |
-
# Create session state for storing data
|
343 |
if 'heights_df' not in st.session_state:
|
344 |
st.session_state.heights_df = pd.DataFrame(columns=[
|
345 |
-
'
|
346 |
-
'
|
347 |
-
'
|
348 |
])
|
349 |
|
350 |
# Main header
|
@@ -381,18 +381,18 @@ if selected == "داشبورد":
|
|
381 |
st.markdown(f'<div class="metric-card"><div class="metric-value">{active_farms}</div><div class="metric-label">مزارع فعال</div></div>', unsafe_allow_html=True)
|
382 |
|
383 |
with col3:
|
384 |
-
avg_height = st.session_state.heights_df['
|
385 |
st.markdown(f'<div class="metric-card"><div class="metric-value">{avg_height:.1f} cm</div><div class="metric-label">میانگین ارتفاع</div></div>', unsafe_allow_html=True)
|
386 |
|
387 |
with col4:
|
388 |
-
avg_moisture = st.session_state.heights_df['
|
389 |
st.markdown(f'<div class="metric-card"><div class="metric-value">{avg_moisture:.1f}%</div><div class="metric-label">میانگین رطوبت</div></div>', unsafe_allow_html=True)
|
390 |
|
391 |
tab1, tab2 = st.tabs(["نمای کلی", "نمودارها"])
|
392 |
|
393 |
with tab1:
|
394 |
st.markdown("### اطلاعات کلی مزارع")
|
395 |
-
total_area = farm_df['مساحت'].astype(float).sum() if 'مساحت' in farm_df.columns else 0
|
396 |
col1, col2, col3 = st.columns(3)
|
397 |
col1.metric("تعداد کل مزارع", f"{len(farm_df)}")
|
398 |
col2.metric("مساحت کل (هکتار)", f"{total_area:.2f}")
|
@@ -400,7 +400,7 @@ if selected == "داشبورد":
|
|
400 |
|
401 |
with tab2:
|
402 |
if not st.session_state.heights_df.empty:
|
403 |
-
fig = px.line(st.session_state.heights_df, x='
|
404 |
st.plotly_chart(fig, use_container_width=True)
|
405 |
else:
|
406 |
st.warning("دادهای برای نمایش وجود ندارد.")
|
@@ -445,38 +445,56 @@ elif selected == "ورود اطلاعات":
|
|
445 |
|
446 |
with tab1:
|
447 |
st.markdown("### ورود دادههای مزارع")
|
448 |
-
|
449 |
-
|
450 |
-
|
451 |
-
|
452 |
-
|
453 |
-
|
454 |
-
|
455 |
-
|
456 |
-
|
457 |
-
|
458 |
-
|
459 |
-
|
460 |
-
|
461 |
-
|
462 |
-
|
463 |
-
|
464 |
-
|
465 |
-
|
466 |
-
|
467 |
-
|
468 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
469 |
|
470 |
-
|
471 |
-
|
472 |
-
|
473 |
-
|
474 |
-
|
475 |
-
'Groundwater2': [groundwater2], 'Sheath_Moisture': [sheath_moisture], 'Nitrogen': [nitrogen],
|
476 |
-
'Variety': [variety], 'Age': [age], 'Area': [area], 'Channel': [channel],
|
477 |
-
'Administration': [administration]
|
478 |
-
})
|
479 |
-
st.session_state.heights_df = pd.concat([st.session_state.heights_df, new_data], ignore_index=True)
|
480 |
st.success("دادهها با موفقیت ثبت شدند!")
|
481 |
|
482 |
with tab2:
|
@@ -489,12 +507,12 @@ elif selected == "ورود اطلاعات":
|
|
489 |
|
490 |
# Column mapping based on sample file
|
491 |
column_mapping = {
|
492 |
-
'Unnamed: 0': '
|
493 |
-
'ارتفاع هفته جاری مزرعه': '
|
494 |
-
'ایستگاه 3': '
|
495 |
-
'چاهک 1': '
|
496 |
-
'نیتروژن فعلی': '
|
497 |
-
'کانال': '
|
498 |
}
|
499 |
|
500 |
df = df.rename(columns=column_mapping)
|
@@ -518,19 +536,25 @@ elif selected == "ورود اطلاعات":
|
|
518 |
except:
|
519 |
return date_str
|
520 |
|
521 |
-
df['
|
522 |
-
df['
|
523 |
|
524 |
# Ensure numeric columns
|
525 |
-
numeric_cols = ['
|
526 |
-
'
|
527 |
-
'
|
528 |
for col in numeric_cols:
|
529 |
df[col] = pd.to_numeric(df[col], errors='coerce')
|
530 |
|
531 |
# Select only expected columns
|
532 |
df = df[expected_columns]
|
533 |
|
|
|
|
|
|
|
|
|
|
|
|
|
534 |
# Append to session state
|
535 |
st.session_state.heights_df = pd.concat([st.session_state.heights_df, df], ignore_index=True)
|
536 |
st.success("دادهها از فایل با موفقیت بارگذاری شدند!")
|
@@ -549,11 +573,11 @@ elif selected == "تحلیل دادهها":
|
|
549 |
st.markdown("## تحلیل دادهها")
|
550 |
if not st.session_state.heights_df.empty:
|
551 |
st.markdown("### تحلیل رشد")
|
552 |
-
fig = px.line(st.session_state.heights_df, x='
|
553 |
st.plotly_chart(fig, use_container_width=True)
|
554 |
|
555 |
st.markdown("### تحلیل رطوبت")
|
556 |
-
fig = px.scatter(st.session_state.heights_df, x='
|
557 |
st.plotly_chart(fig, use_container_width=True)
|
558 |
else:
|
559 |
st.warning("دادهای برای تحلیل وجود ندارد.")
|
@@ -564,14 +588,14 @@ elif selected == "گزارشگیری":
|
|
564 |
if not st.session_state.heights_df.empty:
|
565 |
st.markdown("### گزارش کلی")
|
566 |
col1, col2, col3 = st.columns(3)
|
567 |
-
col1.metric("میانگین ارتفاع", f"{st.session_state.heights_df['
|
568 |
-
col2.metric("میانگین رطوبت", f"{st.session_state.heights_df['
|
569 |
-
col3.metric("میانگین نیتروژن", f"{st.session_state.heights_df['
|
570 |
|
571 |
-
fig = px.bar(st.session_state.heights_df, x='
|
572 |
st.plotly_chart(fig, use_container_width=True)
|
573 |
|
574 |
-
csv = st.session_state.heights_df.to_csv(index=False).encode('utf-8')
|
575 |
st.download_button("دانلود دادهها به صورت CSV", csv, "heights_data.csv", "text/csv")
|
576 |
else:
|
577 |
st.warning("دادهای برای گزارشگیری وجود ندارد.")
|
|
|
339 |
lottie_analysis = load_lottie_url('https://assets3.lottiefiles.com/packages/lf20_qp1q7mct.json')
|
340 |
lottie_report = load_lottie_url('https://assets9.lottiefiles.com/packages/lf20_vwcugezu.json')
|
341 |
|
342 |
+
# Create session state for storing data with Persian column names
|
343 |
if 'heights_df' not in st.session_state:
|
344 |
st.session_state.heights_df = pd.DataFrame(columns=[
|
345 |
+
'ردیف', 'هفته', 'تاریخ قرائت', 'ارتفاع هفته جاری مزرعه', 'ایستگاه 1', 'ایستگاه 2', 'ایستگاه 3',
|
346 |
+
'ایستگاه 4', 'ایستگاه 5', 'چاهک 1', 'چاهک 2', 'رطوبت غلاف فعلی', 'نیتروژن فعلی',
|
347 |
+
'واریته', 'سن', 'مساحت داشت', 'کانال', 'اداره'
|
348 |
])
|
349 |
|
350 |
# Main header
|
|
|
381 |
st.markdown(f'<div class="metric-card"><div class="metric-value">{active_farms}</div><div class="metric-label">مزارع فعال</div></div>', unsafe_allow_html=True)
|
382 |
|
383 |
with col3:
|
384 |
+
avg_height = st.session_state.heights_df['ارتفاع هفته جاری مزرعه'].mean() if not st.session_state.heights_df.empty else 0
|
385 |
st.markdown(f'<div class="metric-card"><div class="metric-value">{avg_height:.1f} cm</div><div class="metric-label">میانگین ارتفاع</div></div>', unsafe_allow_html=True)
|
386 |
|
387 |
with col4:
|
388 |
+
avg_moisture = st.session_state.heights_df['رطوبت غلاف فعلی'].mean() if not st.session_state.heights_df.empty else 0
|
389 |
st.markdown(f'<div class="metric-card"><div class="metric-value">{avg_moisture:.1f}%</div><div class="metric-label">میانگین رطوبت</div></div>', unsafe_allow_html=True)
|
390 |
|
391 |
tab1, tab2 = st.tabs(["نمای کلی", "نمودارها"])
|
392 |
|
393 |
with tab1:
|
394 |
st.markdown("### اطلاعات کلی مزارع")
|
395 |
+
total_area = farm_df['مساحت داشت'].astype(float).sum() if 'مساحت داشت' in farm_df.columns else 0
|
396 |
col1, col2, col3 = st.columns(3)
|
397 |
col1.metric("تعداد کل مزارع", f"{len(farm_df)}")
|
398 |
col2.metric("مساحت کل (هکتار)", f"{total_area:.2f}")
|
|
|
400 |
|
401 |
with tab2:
|
402 |
if not st.session_state.heights_df.empty:
|
403 |
+
fig = px.line(st.session_state.heights_df, x='هفته', y='ارتفاع هفته جاری مزرعه', title='روند ارتفاع هفتگی', labels={'هفته': 'هفته', 'ارتفاع هفته جاری مزرعه': 'ارتفاع (سانتیمتر)'})
|
404 |
st.plotly_chart(fig, use_container_width=True)
|
405 |
else:
|
406 |
st.warning("دادهای برای نمایش وجود ندارد.")
|
|
|
445 |
|
446 |
with tab1:
|
447 |
st.markdown("### ورود دادههای مزارع")
|
448 |
+
# Initialize an empty DataFrame for manual entry if not already present
|
449 |
+
if 'manual_entry_df' not in st.session_state:
|
450 |
+
st.session_state.manual_entry_df = pd.DataFrame(columns=[
|
451 |
+
'ردیف', 'هفته', 'تاریخ قرائت', 'ایستگاه 1', 'ایستگاه 2', 'ایستگاه 3',
|
452 |
+
'ایستگاه 4', 'ایستگاه 5', 'ارتفاع هفته جاری مزرعه', 'چاهک 1', 'چاهک 2',
|
453 |
+
'رطوبت غلاف فعلی', 'نیتروژن فعلی', 'واریته', 'سن', 'مساحت داشت', 'کانال', 'اداره'
|
454 |
+
])
|
455 |
+
|
456 |
+
# Use data_editor for interactive table entry
|
457 |
+
edited_df = st.data_editor(
|
458 |
+
st.session_state.manual_entry_df,
|
459 |
+
num_rows="dynamic", # Allow dynamic rows
|
460 |
+
column_config={
|
461 |
+
'ردیف': st.column_config.TextColumn("ردیف", required=True),
|
462 |
+
'هفته': st.column_config.NumberColumn("هفته", min_value=1, max_value=52, step=1, required=True),
|
463 |
+
'تاریخ قرائت': st.column_config.DateColumn("تاریخ قرائت", format="YYYY-MM-DD", required=True),
|
464 |
+
'ایستگاه 1': st.column_config.NumberColumn("ایستگاه 1", min_value=0.0, step=0.1, required=True),
|
465 |
+
'ایستگاه 2': st.column_config.NumberColumn("ایستگاه 2", min_value=0.0, step=0.1, required=True),
|
466 |
+
'ایستگاه 3': st.column_config.NumberColumn("ایستگاه 3", min_value=0.0, step=0.1, required=True),
|
467 |
+
'ایستگاه 4': st.column_config.NumberColumn("ایستگاه 4", min_value=0.0, step=0.1, required=True),
|
468 |
+
'ایستگاه 5': st.column_config.NumberColumn("ایستگاه 5", min_value=0.0, step=0.1, required=True),
|
469 |
+
'ارتفاع هفته جاری مزرعه': st.column_config.NumberColumn("ارتفاع هفته جاری مزرعه", min_value=0.0, step=0.1, required=True),
|
470 |
+
'چاهک 1': st.column_config.NumberColumn("چاهک 1", min_value=0.0, step=0.1, required=True),
|
471 |
+
'چاهک 2': st.column_config.NumberColumn("چاهک 2", min_value=0.0, step=0.1, required=True),
|
472 |
+
'رطوبت غلاف فعلی': st.column_config.NumberColumn("رطوبت غلاف فعلی", min_value=0.0, max_value=100.0, step=0.1, required=True),
|
473 |
+
'نیتروژن فعلی': st.column_config.NumberColumn("نیتروژن فعلی", min_value=0.0, step=0.1, required=True),
|
474 |
+
'واریته': st.column_config.TextColumn("واریته", required=True),
|
475 |
+
'سن': st.column_config.TextColumn("سن", required=True),
|
476 |
+
'مساحت داشت': st.column_config.NumberColumn("مساحت داشت", min_value=0.0, step=0.1, required=True),
|
477 |
+
'کانال': st.column_config.NumberColumn("کانال", min_value=0, step=1, required=True),
|
478 |
+
'اداره': st.column_config.NumberColumn("اداره", min_value=0, step=1, required=True),
|
479 |
+
},
|
480 |
+
use_container_width=True,
|
481 |
+
hide_index=True
|
482 |
+
)
|
483 |
+
|
484 |
+
# Update session state with edited data and save to heights_df
|
485 |
+
if not edited_df.empty and not edited_df.isna().all().all():
|
486 |
+
st.session_state.manual_entry_df = edited_df
|
487 |
+
# Calculate average height for each row
|
488 |
+
for index, row in edited_df.iterrows():
|
489 |
+
stations = [row[f'ایستگاه {i}'] for i in range(1, 6) if pd.notna(row[f'ایستگاه {i}'])]
|
490 |
+
if stations:
|
491 |
+
edited_df.loc[index, 'ارتفاع هفته جاری مزرعه'] = round(sum(stations) / len(stations), 1)
|
492 |
|
493 |
+
# Add valid rows to heights_df
|
494 |
+
valid_rows = edited_df.dropna(how='any')
|
495 |
+
if not valid_rows.empty:
|
496 |
+
st.session_state.heights_df = pd.concat([st.session_state.heights_df, valid_rows], ignore_index=True)
|
497 |
+
st.session_state.manual_entry_df = pd.DataFrame(columns=st.session_state.manual_entry_df.columns) # Clear after saving
|
|
|
|
|
|
|
|
|
|
|
498 |
st.success("دادهها با موفقیت ثبت شدند!")
|
499 |
|
500 |
with tab2:
|
|
|
507 |
|
508 |
# Column mapping based on sample file
|
509 |
column_mapping = {
|
510 |
+
'Unnamed: 0': 'ردیف', 'هفته': 'هفته', 'تاریخ قرائت': 'تاریخ قرائت',
|
511 |
+
'ارتفاع هفته جاری مزرعه': 'ارتفاع هفته جاری مزرعه', 'ایستگاه 1': 'ایستگاه 1', 'ایستگاه 2': 'ایستگاه 2',
|
512 |
+
'ایستگاه 3': 'ایستگاه 3', 'ایستگاه 4': 'ایستگاه 4', 'ایستگاه 5': 'ایستگاه 5',
|
513 |
+
'چاهک 1': 'چاهک 1', 'چاهک 2': 'چاهک 2', 'رطوبت غلاف فعلی': 'رطوبت غلاف فعلی',
|
514 |
+
'نیتروژن فعلی': 'نیتروژن فعلی', 'واریته': 'واریته', 'سن': 'سن', 'مساحت داشت': 'مساحت داشت',
|
515 |
+
'کانال': 'کانال', 'اداره': 'اداره'
|
516 |
}
|
517 |
|
518 |
df = df.rename(columns=column_mapping)
|
|
|
536 |
except:
|
537 |
return date_str
|
538 |
|
539 |
+
df['تاریخ قرائت'] = df['تاریخ قرائت'].apply(convert_persian_date)
|
540 |
+
df['تاریخ قرائت'] = pd.to_datetime(df['تاریخ قرائت'], errors='coerce')
|
541 |
|
542 |
# Ensure numeric columns
|
543 |
+
numeric_cols = ['هفته', 'ارتفاع هفته جاری مزرعه', 'ایستگاه 1', 'ایستگاه 2', 'ایستگاه 3',
|
544 |
+
'ایستگاه 4', 'ایستگاه 5', 'چاهک 1', 'چاهک 2', 'رطوبت غلاف فعلی',
|
545 |
+
'نیتروژن فعلی', 'مساحت داشت', 'کانال', 'اداره']
|
546 |
for col in numeric_cols:
|
547 |
df[col] = pd.to_numeric(df[col], errors='coerce')
|
548 |
|
549 |
# Select only expected columns
|
550 |
df = df[expected_columns]
|
551 |
|
552 |
+
# Calculate average height if stations are provided
|
553 |
+
for index, row in df.iterrows():
|
554 |
+
stations = [row[f'ایستگاه {i}'] for i in range(1, 6) if pd.notna(row[f'ایستگاه {i}'])]
|
555 |
+
if stations:
|
556 |
+
df.loc[index, 'ارتفاع هفته جاری مزرعه'] = round(sum(stations) / len(stations), 1)
|
557 |
+
|
558 |
# Append to session state
|
559 |
st.session_state.heights_df = pd.concat([st.session_state.heights_df, df], ignore_index=True)
|
560 |
st.success("دادهها از فایل با موفقیت بارگذاری شدند!")
|
|
|
573 |
st.markdown("## تحلیل دادهها")
|
574 |
if not st.session_state.heights_df.empty:
|
575 |
st.markdown("### تحلیل رشد")
|
576 |
+
fig = px.line(st.session_state.heights_df, x='هفته', y='ارتفاع هفته جاری مزرعه', color='ردیف', title='رشد مزارع بر اساس هفته')
|
577 |
st.plotly_chart(fig, use_container_width=True)
|
578 |
|
579 |
st.markdown("### تحلیل رطوبت")
|
580 |
+
fig = px.scatter(st.session_state.heights_df, x='رطوبت غلاف فعلی', y='ارتفاع هفته جاری مزرعه', color='ردیف', title='رابطه رطوبت و ارتفاع')
|
581 |
st.plotly_chart(fig, use_container_width=True)
|
582 |
else:
|
583 |
st.warning("دادهای برای تحلیل وجود ندارد.")
|
|
|
588 |
if not st.session_state.heights_df.empty:
|
589 |
st.markdown("### گزارش کلی")
|
590 |
col1, col2, col3 = st.columns(3)
|
591 |
+
col1.metric("میانگین ارتفاع", f"{st.session_state.heights_df['ارتفاع هفته جاری مزرعه'].mean():.2f} cm")
|
592 |
+
col2.metric("میانگین رطوبت", f"{st.session_state.heights_df['رطوبت غلاف فعلی'].mean():.2f}%")
|
593 |
+
col3.metric("میانگین نیتروژن", f"{st.session_state.heights_df['نیتروژن فعلی'].mean():.2f}")
|
594 |
|
595 |
+
fig = px.bar(st.session_state.heights_df, x='واریته', y='ارتفاع هفته جاری مزرعه', title='ارتفاع بر اساس واریته')
|
596 |
st.plotly_chart(fig, use_container_width=True)
|
597 |
|
598 |
+
csv = st.session_state.heights_df.to_csv(index=False, encoding='utf-8-sig').encode('utf-8')
|
599 |
st.download_button("دانلود دادهها به صورت CSV", csv, "heights_data.csv", "text/csv")
|
600 |
else:
|
601 |
st.warning("دادهای برای گزارشگیری وجود ندارد.")
|