vancauwe commited on
Commit
3ae828c
·
1 Parent(s): 161d75f

feat: json schema set-up

Browse files
app/assets/config/config_dropdown_circumstances.json CHANGED
@@ -4,7 +4,9 @@
4
  "road vehicle":
5
  {
6
 
7
- "Options": ["highway", "main road", "secondary road", "local road/path/trail", "parking lot", "other", "unknown"],
 
 
8
  "Open": "Infrastructure number"
9
 
10
  },
@@ -21,20 +23,26 @@
21
  {
22
  "hunting":
23
  {
24
- "Options": ["shooting", "bow", "falconry", "hounds hunting", "digging up", "other", "unknown"]
 
 
25
  },
26
  "trap":
27
  {
28
- "Options": ["killing trap", "pole trap", "trap cage", "corvids nasse", "net", "cage trap", "fall-trap", "glue trap", "insect trap", "other", "unknown"]
 
 
29
  },
30
  "poisoning": {},
31
  "removal or direct capture":
32
  {
33
- "Options": ["gassing", "raptor captured at nest", "brood destruction", "traffic/trade", "capture accident", "scientific sample", "other", "unknown"]
 
34
  },
35
  "fishing":
36
  {
37
- "Options": ["drowned/tangled", "beached with capture indications", "other", "unknown"]
 
38
  },
39
  "other": {},
40
  "unknown": {}
@@ -44,7 +52,9 @@
44
  "pylone and electric grid":
45
  {
46
 
47
- "Options": ["electric line", "pole/pylon", "other", "unknown"],
 
 
48
  "Extra":
49
  {
50
  "Cause": ["collision", "electrocution", "unknown"]
@@ -53,24 +63,34 @@
53
  "windfarm": {},
54
  "other collision":
55
  {
56
- "Options": ["window", "building", "lighthouse", "cable", "wire fence/barbed wire", "other crash", "unknown"]
 
 
57
  },
58
  "fall":
59
  {
60
- "Options": ["chimney", "empty pole", "hole/well", "other", "unknown"]
 
 
61
  },
62
  "development work":
63
  {
64
- "Options": ["transport infrastructure", "building", "other", "unknown"]
 
 
65
  },
66
  "pollution / contamination":
67
  {
68
- "Options": ["oil pollution", "chemical pollution", "heavy metals", "light", "noise", "plastic ingestion", "other", "unknown"]
 
69
  },
70
  "agricultural net protection": {},
71
  "vegetal / forest work":
72
  {
73
- "Options": ["clearing/mowing/plowing", "tree felling/pruning", "other", "unknown"]
 
 
 
74
  },
75
  "other": {},
76
  "unknown": {}
@@ -79,22 +99,30 @@
79
  {
80
  "predation":
81
  {
82
- "Options": ["cat", "dog", "rooster/hen", "other domestic animal", "wild birds", "wild mammal", "other", "unknown"]
 
 
83
  },
84
  "weather":
85
  {
86
- "Options": ["cold wave", "drought", "hail", "lightening", "storm", "other", "unknown"]
 
 
87
  },
88
  "natural disaster":
89
  {
90
- "Options": ["fire", "avalanche", "rock fall", "mudslide", "volcanic eruption/ashes", "other", "unknown"]
 
 
91
  },
92
  "nest fall": {},
93
  "stranding due to exhaustion": {},
94
  "disease/parasite": {},
95
  "accidental drowing":
96
  {
97
- "Options": ["drinking trough", "pool", "storm pool", "irrigation pool", "natural pool", "flood", "other container", "unknown"]
 
 
98
  },
99
  "other": {},
100
  "unknown": {}
 
4
  "road vehicle":
5
  {
6
 
7
+ "Options": {
8
+ "road_type" : ["highway", "main road", "secondary road", "local road/path/trail", "parking lot", "other", "unknown"]
9
+ },
10
  "Open": "Infrastructure number"
11
 
12
  },
 
23
  {
24
  "hunting":
25
  {
26
+ "Options": {
27
+ "method" : ["shooting", "bow", "falconry", "hounds hunting", "digging up", "other", "unknown"]
28
+ }
29
  },
30
  "trap":
31
  {
32
+ "Options": {
33
+ "method": ["killing trap", "pole trap", "trap cage", "corvids nasse", "net", "cage trap", "fall-trap", "glue trap", "insect trap", "other", "unknown"]
34
+ }
35
  },
36
  "poisoning": {},
37
  "removal or direct capture":
38
  {
39
+ "Options": {"method": ["gassing", "raptor captured at nest", "brood destruction", "traffic/trade", "capture accident", "scientific sample", "other", "unknown"]
40
+ }
41
  },
42
  "fishing":
43
  {
44
+ "Options": {"method" : ["drowned/tangled", "beached with capture indications", "other", "unknown"]
45
+ }
46
  },
47
  "other": {},
48
  "unknown": {}
 
52
  "pylone and electric grid":
53
  {
54
 
55
+ "Options": {
56
+ "infrastructure" : ["electric line", "pole/pylon", "other", "unknown"]
57
+ },
58
  "Extra":
59
  {
60
  "Cause": ["collision", "electrocution", "unknown"]
 
63
  "windfarm": {},
64
  "other collision":
65
  {
66
+ "Options": {
67
+ "object": ["window", "building", "lighthouse", "cable", "wire fence/barbed wire", "other crash", "unknown"]
68
+ }
69
  },
70
  "fall":
71
  {
72
+ "Options": {
73
+ "location": ["chimney", "empty pole", "hole/well", "other", "unknown"]
74
+ }
75
  },
76
  "development work":
77
  {
78
+ "Options": {
79
+ "work_type" : ["transport infrastructure", "building", "other", "unknown"]
80
+ }
81
  },
82
  "pollution / contamination":
83
  {
84
+ "Options": {
85
+ "pollution_type" : ["oil pollution", "chemical pollution", "heavy metals", "light", "noise", "plastic ingestion", "other", "unknown"]
86
  },
87
  "agricultural net protection": {},
88
  "vegetal / forest work":
89
  {
90
+ "Options": {
91
+ "work_type" : ["clearing/mowing/plowing", "tree felling/pruning", "other", "unknown"]
92
+ }
93
+ }
94
  },
95
  "other": {},
96
  "unknown": {}
 
99
  {
100
  "predation":
101
  {
102
+ "Options": {
103
+ "predator" : ["cat", "dog", "rooster/hen", "other domestic animal", "wild birds", "wild mammal", "other", "unknown"]
104
+ }
105
  },
106
  "weather":
107
  {
108
+ "Options": {
109
+ "condition" : ["cold wave", "drought", "hail", "lightening", "storm", "other", "unknown"]
110
+ }
111
  },
112
  "natural disaster":
113
  {
114
+ "Options": {
115
+ "disaster" : ["fire", "avalanche", "rock fall", "mudslide", "volcanic eruption/ashes", "other", "unknown"]
116
+ }
117
  },
118
  "nest fall": {},
119
  "stranding due to exhaustion": {},
120
  "disease/parasite": {},
121
  "accidental drowing":
122
  {
123
+ "Options": {
124
+ "drowning_location" : ["drinking trough", "pool", "storm pool", "irrigation pool", "natural pool", "flood", "other container", "unknown"]
125
+ }
126
  },
127
  "other": {},
128
  "unknown": {}
app/assets/json_tmp/tmp_wounded_dead.json ADDED
@@ -0,0 +1 @@
 
 
1
+ {}
app/behavior/behavior_checkbox.py CHANGED
@@ -2,7 +2,7 @@ import gradio as gr
2
  from utils.utils_config import get_custom_config_dropdowns
3
  from utils.utils_checkbox import create_checkbox
4
  from utils.utils_visible import set_visible
5
- from utils.utils_json import add_data_to_individual
6
 
7
  def on_select_behavior(behavior_checkbox):
8
  add_data_to_individual("behavior", behavior_checkbox)
 
2
  from utils.utils_config import get_custom_config_dropdowns
3
  from utils.utils_checkbox import create_checkbox
4
  from utils.utils_visible import set_visible
5
+ from validation_submission.add_json import add_data_to_individual
6
 
7
  def on_select_behavior(behavior_checkbox):
8
  add_data_to_individual("behavior", behavior_checkbox)
app/behavior/class_behavior.py CHANGED
@@ -63,4 +63,4 @@ BehaviorType = Union[
63
 
64
  # Main class that logs multiple behaviors
65
  class Behaviors(BaseModel):
66
- observed_behaviors: List[BehaviorType]
 
63
 
64
  # Main class that logs multiple behaviors
65
  class Behaviors(BaseModel):
66
+ observed_behaviors: List[BehaviorType] = Field(..., discriminator='type')
app/circumstances/circumstances.py CHANGED
@@ -1,8 +1,10 @@
1
  import gradio as gr
2
  import os
3
- from utils.utils_visible import set_visible
4
  from dotenv import load_dotenv
5
- import os
 
 
 
6
  load_dotenv()
7
  PATH = os.getcwd() + "/"
8
  PATH_ASSETS = os.getenv('PATH_ASSETS')
@@ -13,6 +15,9 @@ CAUSE_COL_WIDTH = "50px"
13
 
14
  def show_circumstances(choice):
15
  visible = set_visible(choice)
 
 
 
16
  button_collision, button_deliberate_destruction, button_indirect_destruction, button_natural_cause, dropdown, dropdown_level2, openfield_level2, dropdown_extra_level2 = create_circumstances(visible)
17
  return button_collision, button_deliberate_destruction, button_indirect_destruction, button_natural_cause, dropdown, dropdown_level2, openfield_level2, dropdown_extra_level2
18
 
 
1
  import gradio as gr
2
  import os
 
3
  from dotenv import load_dotenv
4
+
5
+ from utils.utils_visible import set_visible
6
+ from validation_submission.add_json import add_data_tmp
7
+
8
  load_dotenv()
9
  PATH = os.getcwd() + "/"
10
  PATH_ASSETS = os.getenv('PATH_ASSETS')
 
15
 
16
  def show_circumstances(choice):
17
  visible = set_visible(choice)
18
+ add_data_tmp("wounded_dead",
19
+ "circumstance_radio",
20
+ True)
21
  button_collision, button_deliberate_destruction, button_indirect_destruction, button_natural_cause, dropdown, dropdown_level2, openfield_level2, dropdown_extra_level2 = create_circumstances(visible)
22
  return button_collision, button_deliberate_destruction, button_indirect_destruction, button_natural_cause, dropdown, dropdown_level2, openfield_level2, dropdown_extra_level2
23
 
app/circumstances/circumstances_dropdowns.py CHANGED
@@ -1,6 +1,6 @@
1
  import gradio as gr
2
  from utils.utils_config import get_custom_config_dropdowns
3
- from utils.utils_json import add_data_to_individual
4
 
5
  #--------------------------------------------------------- LEVEL 1 DROPDOWNS
6
  def retrieve_config_options(label, dropdown_config):
@@ -23,28 +23,29 @@ def create_dropdown_level1(label):
23
 
24
  def dropdown_collision():
25
  label = "Collision with a means of transport"
26
- add_data_to_individual("circumstance", label)
27
  return create_dropdown_level1(label)
28
 
29
  def dropdown_deliberate_destruction():
30
  label = "Destruction / Deliberatly removed"
31
- add_data_to_individual("circumstance", label)
32
  return create_dropdown_level1(label)
33
 
34
  def dropdown_indirect_destruction():
35
  label = "Indirect destruction"
36
- add_data_to_individual("circumstance", label)
37
  return create_dropdown_level1(label)
38
 
39
  def dropdown_natural_cause():
40
  label = "Natural cause"
41
- add_data_to_individual("circumstance", label)
42
  return create_dropdown_level1(label)
43
 
44
 
45
  #--------------------------------------------------------- LEVEL 2 DROPDOWNS
46
  def get_options(value):
47
  value = value.lower()
 
48
  options_dropdown= None
49
  open_field = None
50
  extras = None
@@ -54,7 +55,9 @@ def get_options(value):
54
  nested_dict = sub_dict.get(value)
55
  if nested_dict is not None:
56
  if "Options" in nested_dict.keys():
57
- options_dropdown = nested_dict["Options"]
 
 
58
  options_dropdown = [option.title() for option in options_dropdown]
59
  if "Open" in nested_dict.keys():
60
  open_field = nested_dict["Open"]
@@ -64,12 +67,18 @@ def get_options(value):
64
  extras_label = key
65
  extras = val
66
  extras = [extra.title() for extra in extras]
67
- return options_dropdown, open_field, extras, extras_label
68
 
69
 
70
  def on_select(evt: gr.SelectData): # SelectData is a subclass of EventData
71
- add_data_to_individual("circumstance_dropdown_level1", evt.value)
72
- options_dropdown, open_field, extras, extras_label = get_options(evt.value)
 
 
 
 
 
 
73
  if options_dropdown is not None:
74
  dropdown_level2 = gr.Dropdown(choices=options_dropdown, label=evt.value, interactive=True, visible=True)
75
  else:
@@ -87,10 +96,16 @@ def on_select(evt: gr.SelectData): # SelectData is a subclass of EventData
87
  return dropdown_level2, openfield_level2, dropdown_extra_level2
88
 
89
  def on_select_dropdown_level2(evt: gr.SelectData):
90
- add_data_to_individual("circumstance_dropdown_level2", evt.value)
 
 
91
 
92
  def on_select_openfield_level2(evt: gr.SelectData):
93
- add_data_to_individual("circumstance_openfield_level2", evt.value)
 
 
94
 
95
  def on_select_dropdown_extra_level2(evt: gr.SelectData):
96
- add_data_to_individual("circumstance_dropdown_extra_level2", evt.value)
 
 
 
1
  import gradio as gr
2
  from utils.utils_config import get_custom_config_dropdowns
3
+ from validation_submission.add_json import add_data_tmp
4
 
5
  #--------------------------------------------------------- LEVEL 1 DROPDOWNS
6
  def retrieve_config_options(label, dropdown_config):
 
23
 
24
  def dropdown_collision():
25
  label = "Collision with a means of transport"
26
+ add_data_tmp("wounded_dead", "circumstance", label.lower())
27
  return create_dropdown_level1(label)
28
 
29
  def dropdown_deliberate_destruction():
30
  label = "Destruction / Deliberatly removed"
31
+ add_data_tmp("wounded_dead", "circumstance", label.lower())
32
  return create_dropdown_level1(label)
33
 
34
  def dropdown_indirect_destruction():
35
  label = "Indirect destruction"
36
+ add_data_tmp("wounded_dead", "circumstance", label.lower())
37
  return create_dropdown_level1(label)
38
 
39
  def dropdown_natural_cause():
40
  label = "Natural cause"
41
+ add_data_tmp("wounded_dead", "circumstance", label.lower())
42
  return create_dropdown_level1(label)
43
 
44
 
45
  #--------------------------------------------------------- LEVEL 2 DROPDOWNS
46
  def get_options(value):
47
  value = value.lower()
48
+ options_label = None
49
  options_dropdown= None
50
  open_field = None
51
  extras = None
 
55
  nested_dict = sub_dict.get(value)
56
  if nested_dict is not None:
57
  if "Options" in nested_dict.keys():
58
+ options_dict = nested_dict["Options"]
59
+ options_label = list(options_dict.keys())[0]
60
+ options_dropdown = list(options_dict.values())[0]
61
  options_dropdown = [option.title() for option in options_dropdown]
62
  if "Open" in nested_dict.keys():
63
  open_field = nested_dict["Open"]
 
67
  extras_label = key
68
  extras = val
69
  extras = [extra.title() for extra in extras]
70
+ return options_label, options_dropdown, open_field, extras, extras_label
71
 
72
 
73
  def on_select(evt: gr.SelectData): # SelectData is a subclass of EventData
74
+ options_label, options_dropdown, open_field, extras, extras_label = get_options(evt.value)
75
+ add_data_tmp("wounded_dead",
76
+ "cirumstance_type",
77
+ {"type": (evt.value).lower(),
78
+ "option_dropdown_label" : options_label.lower() if options_label is not None else 'NA',
79
+ "open_field_label" : open_field.lower() if open_field is not None else 'NA',
80
+ "extra_label": extras_label.lower() if extras_label is not None else 'NA'
81
+ })
82
  if options_dropdown is not None:
83
  dropdown_level2 = gr.Dropdown(choices=options_dropdown, label=evt.value, interactive=True, visible=True)
84
  else:
 
96
  return dropdown_level2, openfield_level2, dropdown_extra_level2
97
 
98
  def on_select_dropdown_level2(evt: gr.SelectData):
99
+ add_data_tmp("wounded_dead",
100
+ "circumstance_option_dropdown",
101
+ evt.value)
102
 
103
  def on_select_openfield_level2(evt: gr.SelectData):
104
+ add_data_tmp("wounded_dead",
105
+ "circumstance_open_field",
106
+ evt.value)
107
 
108
  def on_select_dropdown_extra_level2(evt: gr.SelectData):
109
+ add_data_tmp("wounded_dead",
110
+ "circumstance_extra",
111
+ evt.value)
app/circumstances/class_circumstance.py CHANGED
@@ -22,10 +22,10 @@ class BoatCollision(CircumstanceTypeBase):
22
  type: Literal['boat']
23
 
24
  class OtherTransportCollision(CircumstanceTypeBase):
25
- type: Literal['other']
26
 
27
  class UnknownTransportCollision(CircumstanceTypeBase):
28
- type: Literal['unknown']
29
 
30
  # Destruction / Deliberately removed
31
  class HuntingDestruction(CircumstanceTypeBase):
@@ -48,10 +48,10 @@ class FishingDestruction(CircumstanceTypeBase):
48
  method: Literal['drowned/tangled', 'beached with capture indications', 'other', 'unknown']
49
 
50
  class OtherDestruction(CircumstanceTypeBase):
51
- type: Literal['other']
52
 
53
  class UnknownDestruction(CircumstanceTypeBase):
54
- type: Literal['unknown']
55
 
56
  # Indirect destruction
57
  class PylonElectricGridDestruction(CircumstanceTypeBase):
@@ -86,10 +86,10 @@ class VegetalForestWorkDestruction(CircumstanceTypeBase):
86
  work_type: Literal['clearing/mowing/plowing', 'tree felling/pruning', 'other', 'unknown']
87
 
88
  class OtherIndirectDestruction(CircumstanceTypeBase):
89
- type: Literal['other']
90
 
91
  class UnknownIndirectDestruction(CircumstanceTypeBase):
92
- type: Literal['unknown']
93
 
94
  # Natural cause
95
  class Predation(CircumstanceTypeBase):
@@ -118,10 +118,10 @@ class AccidentalDrowning(CircumstanceTypeBase):
118
  drowning_location: Literal['drinking trough', 'pool', 'storm pool', 'irrigation pool', 'natural pool', 'flood', 'other container', 'unknown']
119
 
120
  class OtherNaturalCause(CircumstanceTypeBase):
121
- type: Literal['other']
122
 
123
  class UnknownNaturalCause(CircumstanceTypeBase):
124
- type: Literal['unknown']
125
 
126
  # Unknown cause
127
  class UnknownCircumstance(CircumstanceTypeBase):
@@ -168,4 +168,17 @@ CircumstanceType = Union[
168
  class Circumstances(BaseModel):
169
  circumstance: str # e.g., "COLLISION"
170
  circumstance_radio: str # e.g., "Yes"
171
- circumstance_type: CircumstanceType = Field(..., discriminator='type')
 
 
 
 
 
 
 
 
 
 
 
 
 
 
22
  type: Literal['boat']
23
 
24
  class OtherTransportCollision(CircumstanceTypeBase):
25
+ type: Literal['other transport collision']
26
 
27
  class UnknownTransportCollision(CircumstanceTypeBase):
28
+ type: Literal['unknown transport collision']
29
 
30
  # Destruction / Deliberately removed
31
  class HuntingDestruction(CircumstanceTypeBase):
 
48
  method: Literal['drowned/tangled', 'beached with capture indications', 'other', 'unknown']
49
 
50
  class OtherDestruction(CircumstanceTypeBase):
51
+ type: Literal['other destruction']
52
 
53
  class UnknownDestruction(CircumstanceTypeBase):
54
+ type: Literal['unknown destruction']
55
 
56
  # Indirect destruction
57
  class PylonElectricGridDestruction(CircumstanceTypeBase):
 
86
  work_type: Literal['clearing/mowing/plowing', 'tree felling/pruning', 'other', 'unknown']
87
 
88
  class OtherIndirectDestruction(CircumstanceTypeBase):
89
+ type: Literal['other indirect desctruction']
90
 
91
  class UnknownIndirectDestruction(CircumstanceTypeBase):
92
+ type: Literal['unknown indirect desctruction']
93
 
94
  # Natural cause
95
  class Predation(CircumstanceTypeBase):
 
118
  drowning_location: Literal['drinking trough', 'pool', 'storm pool', 'irrigation pool', 'natural pool', 'flood', 'other container', 'unknown']
119
 
120
  class OtherNaturalCause(CircumstanceTypeBase):
121
+ type: Literal['other natural cause']
122
 
123
  class UnknownNaturalCause(CircumstanceTypeBase):
124
+ type: Literal['unknown natural cause']
125
 
126
  # Unknown cause
127
  class UnknownCircumstance(CircumstanceTypeBase):
 
168
  class Circumstances(BaseModel):
169
  circumstance: str # e.g., "COLLISION"
170
  circumstance_radio: str # e.g., "Yes"
171
+ circumstance_type: CircumstanceType = Field(..., discriminator='type')
172
+
173
+
174
+ # Example usage
175
+ # json_data = {
176
+ # "circumstance": "COLLISION",
177
+ # "circumstance_radio": "Yes",
178
+ # "circumstance_type": {
179
+ # "type": "Train",
180
+ # "infrastructure_number": "56"
181
+ # }
182
+ # }
183
+ # circumstance_instance = Circumstance(**json_data)
184
+ # circumstance_schema = Circumstance.schema_json(indent=2)
app/classes.py CHANGED
@@ -8,7 +8,7 @@ from follow_up.class_follow_up import FollowUpEvents
8
  from geolocalisation.class_geolocalisation import Geolocalisation
9
 
10
  class Wounded(BaseModel):
11
- circumstances: List[Circumstances]
12
  behaviors: List[Behaviors]
13
  physical_anomalies: List[PhysicalAnomaly]
14
  follow_up_events: List[FollowUpEvents]
@@ -28,15 +28,3 @@ class Report(BaseModel):
28
  wounded: Optional[Wounded] = None
29
  dead_state: bool
30
  dead: Optional[Dead] = None
31
-
32
- # Example usage
33
- # json_data = {
34
- # "circumstance": "COLLISION",
35
- # "circumstance_radio": "Yes",
36
- # "circumstance_type": {
37
- # "type": "Train",
38
- # "infrastructure_number": "56"
39
- # }
40
- # }
41
- # circumstance_instance = Circumstance(**json_data)
42
- # circumstance_schema = Circumstance.schema_json(indent=2)
 
8
  from geolocalisation.class_geolocalisation import Geolocalisation
9
 
10
  class Wounded(BaseModel):
11
+ circumstances: Circumstances
12
  behaviors: List[Behaviors]
13
  physical_anomalies: List[PhysicalAnomaly]
14
  follow_up_events: List[FollowUpEvents]
 
28
  wounded: Optional[Wounded] = None
29
  dead_state: bool
30
  dead: Optional[Dead] = None
 
 
 
 
 
 
 
 
 
 
 
 
app/dead.py CHANGED
@@ -1,12 +1,12 @@
1
  import gradio as gr
2
  from circumstances.circumstances import create_circumstances
3
  from follow_up.followup_events import create_followup_dropdowns, create_followup_open
4
- from utils.utils_json import add_data_to_individual
5
 
6
  def show_section_dead(visible):
7
  if visible==True:
8
- add_data_to_individual("dead", "True")
9
- add_data_to_individual("wounded", "False")
10
 
11
  with gr.Column(visible=visible, elem_id="dead") as section_dead:
12
  gr.Markdown("# Dead Animal")
 
1
  import gradio as gr
2
  from circumstances.circumstances import create_circumstances
3
  from follow_up.followup_events import create_followup_dropdowns, create_followup_open
4
+ from validation_submission.add_json import add_data_to_individual
5
 
6
  def show_section_dead(visible):
7
  if visible==True:
8
+ add_data_to_individual("dead_bool", "True")
9
+ add_data_to_individual("wounded_bool", "False")
10
 
11
  with gr.Column(visible=visible, elem_id="dead") as section_dead:
12
  gr.Markdown("# Dead Animal")
app/follow_up/followup_events.py CHANGED
@@ -1,6 +1,6 @@
1
  import gradio as gr
2
  from utils.utils_config import get_custom_config_dropdowns
3
- from utils.utils_json import add_data_to_individual
4
 
5
  def create_followup_dropdowns(visible, elem_id):
6
  followup_config = get_custom_config_dropdowns("config_followup.json")
 
1
  import gradio as gr
2
  from utils.utils_config import get_custom_config_dropdowns
3
+ from validation_submission.add_json import add_data_to_individual
4
 
5
  def create_followup_dropdowns(visible, elem_id):
6
  followup_config = get_custom_config_dropdowns("config_followup.json")
app/gallery.py CHANGED
@@ -2,10 +2,13 @@ import gradio as gr
2
  import pandas as pd
3
  import numpy as np
4
  from dotenv import load_dotenv
 
5
 
6
  from utils.utils_config import load_config
7
- from utils.utils_json import get_json_one_individual, save_to_all_individuals
8
- import os
 
 
9
 
10
  load_dotenv()
11
  PATH = os.getcwd() + "/"
@@ -87,6 +90,7 @@ def set_gallery_size(len_animals):
87
  return num_cols, num_rows
88
 
89
  def save_individual_to_gallery(gallery):
 
90
  one_individual = get_json_one_individual()
91
  fields = get_fields()
92
  one_individual_matched = match_data_to_fields(fields, one_individual)
 
2
  import pandas as pd
3
  import numpy as np
4
  from dotenv import load_dotenv
5
+ import os
6
 
7
  from utils.utils_config import load_config
8
+ from validation_submission.get_json import get_json_one_individual
9
+ from validation_submission.submission import save_to_all_individuals
10
+ from validation_submission.validation import validate_individual
11
+
12
 
13
  load_dotenv()
14
  PATH = os.getcwd() + "/"
 
90
  return num_cols, num_rows
91
 
92
  def save_individual_to_gallery(gallery):
93
+ validate_individual()
94
  one_individual = get_json_one_individual()
95
  fields = get_fields()
96
  one_individual_matched = match_data_to_fields(fields, one_individual)
app/geolocalisation/maps.py CHANGED
@@ -1,9 +1,26 @@
1
  from geopy.geocoders import Nominatim
2
  import gradio as gr
3
- from utils.utils_json import add_data_to_individual
4
-
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
5
  def get_location(address):
6
- # try:
7
  # calling the Nominatim tool
8
  loc = Nominatim(user_agent="GetLoc")
9
 
@@ -15,8 +32,8 @@ def get_location(address):
15
  lon = getLoc.longitude
16
 
17
  # Save values
18
- add_data_to_individual("latitude", lat)
19
- add_data_to_individual("longitude", lon)
20
 
21
  #display location processing
22
  value = "Latitude = " + str(lat) + "\n" + "Longitude = " + str(lon)
@@ -25,9 +42,9 @@ def get_location(address):
25
  value=value)
26
  return identified_location
27
 
28
- # except:
29
- # error = "Please try another less precise location."
30
- # identified_location= gr.Textbox(visible=True, interactive=False,
31
- # label="Identified GPS Location",
32
- # value=error)
33
- # return identified_location
 
1
  from geopy.geocoders import Nominatim
2
  import gradio as gr
3
+ from app.validation_submission.utils_json import add_data_to_individual
4
+ from geolocalisation.class_geolocalisation import Geolocalisation
5
+
6
+
7
+ def create_geolocalisation_object(lat, long, name):
8
+ try:
9
+ geolocalisation = Geolocalisation(
10
+ longitude={"type": "longitude", "value": long},
11
+ latitude={"type": "latitude", "value": lat},
12
+ name=name
13
+ )
14
+ except:
15
+ print("Pydantic Error for Geolocalisation")
16
+ return geolocalisation
17
+
18
+ def save_geolocalisation_to_json(geolocalisation):
19
+ geo_dict = geolocalisation.dict()
20
+ add_data_to_individual("geolocalisation", geo_dict)
21
+
22
  def get_location(address):
23
+ try:
24
  # calling the Nominatim tool
25
  loc = Nominatim(user_agent="GetLoc")
26
 
 
32
  lon = getLoc.longitude
33
 
34
  # Save values
35
+ geolocalisation = create_geolocalisation_object(lat, lon, address)
36
+ save_geolocalisation_to_json(geolocalisation)
37
 
38
  #display location processing
39
  value = "Latitude = " + str(lat) + "\n" + "Longitude = " + str(lon)
 
42
  value=value)
43
  return identified_location
44
 
45
+ except:
46
+ error = "Please try another less precise location."
47
+ identified_location= gr.Textbox(visible=True, interactive=False,
48
+ label="Identified GPS Location",
49
+ value=error)
50
+ return identified_location
app/gradio_test/test_selectdata_event.py ADDED
@@ -0,0 +1,16 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ import gradio as gr
2
+
3
+ with gr.Blocks() as demo:
4
+ table = gr.Dataframe([[1, 2, 3], [4, 5, 6]])
5
+ #gallery = gr.Gallery([("cat.jpg", "Cat"), ("dog.jpg", "Dog")])
6
+ textbox = gr.Textbox("Hello World!")
7
+ statement = gr.Textbox()
8
+
9
+ def on_select(evt: gr.SelectData):
10
+ return gr.Textbox(f"You selected {evt.value} at {evt.index} from {evt.target}")
11
+
12
+ table.select(on_select, inputs=[table], outputs=[statement])
13
+ #gallery.select(on_select, gallery, statement)
14
+ textbox.select(on_select, inputs=[textbox], outputs=[statement])
15
+
16
+ demo.launch(server_name="0.0.0.0", server_port=3131)
app/{tests.py → gradio_test/tests_delete_gallery.py} RENAMED
File without changes
app/main_multianimal.py CHANGED
@@ -1,7 +1,8 @@
1
  import gradio as gr
2
  from gradio_modal import Modal
3
 
4
- from utils.utils_json import *
 
5
  from gallery import save_individual_to_gallery
6
  from geolocalisation.maps import get_location
7
  from functools import partial
@@ -15,9 +16,16 @@ from behavior.behavior_checkbox import show_behavior, on_select_behavior
15
  from follow_up.followup_events import save_fe
16
  from styling.style import *
17
  from styling.theme import theme, css
 
18
 
19
  with gr.Blocks(theme=theme, css=css) as demo:
20
  create_json_all_individuals()
 
 
 
 
 
 
21
  with gr.Row():
22
  show_modal = gr.Button("Add an Animal", scale=3)
23
  submit_button = gr.Button("Submit All Animals", scale=1)
@@ -33,8 +41,8 @@ with gr.Blocks(theme=theme, css=css) as demo:
33
  # Intro Text
34
  with gr.Row():
35
  with gr.Column(scale=1):
36
- title = gr.Markdown("# Welcome to Digiwild", label="Title")
37
- description = gr.Markdown("Please record your wildlife observations here !", label="description")
38
 
39
  # ---------------------------------------------------------
40
  # Camera
@@ -256,6 +264,7 @@ with gr.Blocks(theme=theme, css=css) as demo:
256
  # Event Functions of the landing page buttons
257
  show_modal.click(lambda: Modal(visible=True), None, modal)
258
  show_modal.click(create_json_one_individual)
 
259
  #submit_button.click(save_and_rest_df, inputs=[df], outputs=[df])
260
  submit_button.click(save_individual_to_gallery)
261
 
 
1
  import gradio as gr
2
  from gradio_modal import Modal
3
 
4
+ from validation_submission.create_json import create_json_all_individuals, create_json_one_individual, create_tmp
5
+ from validation_submission.add_json import add_data_to_individual
6
  from gallery import save_individual_to_gallery
7
  from geolocalisation.maps import get_location
8
  from functools import partial
 
16
  from follow_up.followup_events import save_fe
17
  from styling.style import *
18
  from styling.theme import theme, css
19
+ from classes import Report
20
 
21
  with gr.Blocks(theme=theme, css=css) as demo:
22
  create_json_all_individuals()
23
+ # ---------------------------------------------------------
24
+ # Intro Text
25
+ with gr.Row():
26
+ with gr.Column(scale=1):
27
+ title = gr.Markdown("# Welcome to Digiwild", label="Title")
28
+ description = gr.Markdown("Please record your wildlife observations here !", label="description")
29
  with gr.Row():
30
  show_modal = gr.Button("Add an Animal", scale=3)
31
  submit_button = gr.Button("Submit All Animals", scale=1)
 
41
  # Intro Text
42
  with gr.Row():
43
  with gr.Column(scale=1):
44
+ title = gr.Markdown("# Animal Report", label="Title")
45
+ description = gr.Markdown("Please record your observation here.", label="description")
46
 
47
  # ---------------------------------------------------------
48
  # Camera
 
264
  # Event Functions of the landing page buttons
265
  show_modal.click(lambda: Modal(visible=True), None, modal)
266
  show_modal.click(create_json_one_individual)
267
+ show_modal.click(create_tmp)
268
  #submit_button.click(save_and_rest_df, inputs=[df], outputs=[df])
269
  submit_button.click(save_individual_to_gallery)
270
 
app/physical/class_physical.py CHANGED
@@ -75,4 +75,4 @@ AnomalyType = Union[
75
 
76
  # Main PhysicalAnomaly class that logs anomalies across different body parts
77
  class PhysicalAnomaly(BaseModel):
78
- body_part_anomalies: List[AnomalyType] # List of anomalies across different body parts
 
75
 
76
  # Main PhysicalAnomaly class that logs anomalies across different body parts
77
  class PhysicalAnomaly(BaseModel):
78
+ body_part_anomalies: List[AnomalyType] = Field(..., discriminator='type')
app/physical/physical_checkbox.py CHANGED
@@ -1,7 +1,7 @@
1
  import gradio as gr
2
  from utils.utils_config import get_custom_config_dropdowns
3
  from utils.utils_checkbox import create_checkbox
4
- from utils.utils_json import add_data_to_individual
5
  #---------------------------------------------------------
6
  def get_body_parts():
7
  dropdown_config = get_custom_config_dropdowns("config_checkbox_physical.json")
 
1
  import gradio as gr
2
  from utils.utils_config import get_custom_config_dropdowns
3
  from utils.utils_checkbox import create_checkbox
4
+ from validation_submission.add_json import add_data_to_individual
5
  #---------------------------------------------------------
6
  def get_body_parts():
7
  dropdown_config = get_custom_config_dropdowns("config_checkbox_physical.json")
app/utils/utils_json.py DELETED
@@ -1,42 +0,0 @@
1
- import json
2
- import gradio as gr
3
-
4
- def create_json_one_individual(one_individual={}):
5
- # Serializing json
6
- one_individual = json.dumps(one_individual)
7
- with open("data/one_individual.json", "w") as outfile:
8
- outfile.write(one_individual)
9
- def create_json_all_individuals(all_individuals={}):
10
- all_individuals = json.dumps(all_individuals)
11
- with open("data/all_individuals.json", "w") as outfile:
12
- outfile.write(all_individuals)
13
-
14
- def add_data_to_individual(key, value):
15
- with open("data/one_individual.json", 'r') as openfile:
16
- one_individual = json.load(openfile)
17
- one_individual[key] = value
18
- create_json_one_individual(one_individual)
19
-
20
- def get_json_one_individual():
21
- with open("data/one_individual.json", 'r') as openfile:
22
- one_individual = json.load(openfile)
23
- return one_individual
24
-
25
- def get_json_all_individuals():
26
- with open("data/all_individuals.json", "r") as openfile:
27
- all_individuals = json.load(openfile)
28
- return all_individuals
29
-
30
- def save_to_all_individuals(one_individual):
31
- all_individuals = get_json_all_individuals()
32
- all_individuals[str(len(all_individuals))] = one_individual
33
- all_individuals_for_json = json.dumps(all_individuals)
34
- with open("data/all_individuals.json", "w") as outfile:
35
- outfile.write(all_individuals_for_json)
36
- return all_individuals
37
-
38
- # def save_all_individuals(df):
39
- # all_individuals = df.to_json(orient="records")
40
- # with open("data/all_individuals.json", "w") as outfile:
41
- # outfile.write(all_individuals)
42
-
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
app/validation_submission/__init__.py ADDED
File without changes
app/validation_submission/add_json.py ADDED
@@ -0,0 +1,15 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ from validation_submission.create_json import create_json_one_individual, create_tmp
2
+ import json
3
+
4
+ def add_data_to_individual(key, value):
5
+ with open("data/one_individual.json", 'r') as openfile:
6
+ one_individual = json.load(openfile)
7
+ one_individual[key] = value
8
+ create_json_one_individual(one_individual)
9
+
10
+ def add_data_tmp(tmp_name, key, value):
11
+ with open(f"app/assets/json_tmp/tmp_{tmp_name}.json", 'r') as openfile:
12
+ tmp = json.load(openfile)
13
+ tmp[key] = value
14
+ create_tmp(tmp_name, tmp)
15
+
app/validation_submission/create_json.py ADDED
@@ -0,0 +1,16 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ import json
2
+
3
+ def create_json_one_individual(one_individual={}):
4
+ one_individual = json.dumps(one_individual)
5
+ with open("data/one_individual.json", "w") as outfile:
6
+ outfile.write(one_individual)
7
+
8
+ def create_json_all_individuals(all_individuals={}):
9
+ all_individuals = json.dumps(all_individuals)
10
+ with open("data/all_individuals.json", "w") as outfile:
11
+ outfile.write(all_individuals)
12
+
13
+ def create_tmp(tmp_name, tmp={}):
14
+ tmp = json.dumps(tmp)
15
+ with open(f"app/assets/json_tmp/tmp_{tmp_name}.json", "w") as outfile:
16
+ outfile.write(tmp)
app/validation_submission/get_json.py ADDED
@@ -0,0 +1,16 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ import json
2
+
3
+ def get_json_one_individual():
4
+ with open("data/one_individual.json", 'r') as openfile:
5
+ one_individual = json.load(openfile)
6
+ return one_individual
7
+
8
+ def get_json_all_individuals():
9
+ with open("data/all_individuals.json", "r") as openfile:
10
+ all_individuals = json.load(openfile)
11
+ return all_individuals
12
+
13
+ def get_json_tmp(tmp_name):
14
+ with open(f"app/assets/json_tmp/tmp_{tmp_name}.json", "r") as openfile:
15
+ tmp_json = json.load(openfile)
16
+ return tmp_json
app/validation_submission/submission.py ADDED
@@ -0,0 +1,10 @@
 
 
 
 
 
 
 
 
 
 
 
1
+ import json
2
+ from validation_submission.get_json import get_json_all_individuals
3
+
4
+ def save_to_all_individuals(one_individual):
5
+ all_individuals = get_json_all_individuals()
6
+ all_individuals[str(len(all_individuals))] = one_individual
7
+ all_individuals_for_json = json.dumps(all_individuals)
8
+ with open("data/all_individuals.json", "w") as outfile:
9
+ outfile.write(all_individuals_for_json)
10
+ return all_individuals
app/validation_submission/validation.py ADDED
@@ -0,0 +1,44 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ from validation_submission.get_json import get_json_tmp, get_json_one_individual
2
+ from classes import Report
3
+ from circumstances.class_circumstance import Circumstance
4
+
5
+ def get_fields(data_dict, keyword):
6
+ extract = {}
7
+ for key, val in data_dict.items():
8
+ if keyword in key:
9
+ extract[key] = val
10
+ return extract
11
+
12
+ def validate_individual():
13
+ data = get_json_tmp("wounded_dead")
14
+ validate_circumstance(data)
15
+ validate_behavior(data)
16
+ validate_physical(data)
17
+ validate_follow_up(data)
18
+ validate_individual()
19
+ pass
20
+
21
+
22
+ def validate_circumstance(data):
23
+ circumstance_raw = get_fields(data, "circumstance")
24
+ circumstance_formatted = process_circumstance(circumstance_raw)
25
+ if not Circumstance(circumstance_formatted).validate():
26
+ print("Validation failed for the circumstance.")
27
+ pass
28
+ def process_circumstance(data):
29
+ pass
30
+
31
+ def validate_behavior(data):
32
+ pass
33
+
34
+ def validate_physical(data):
35
+ pass
36
+
37
+ def validate_follow_up(data):
38
+ pass
39
+
40
+ def validate_individual():
41
+ individual = get_json_one_individual()
42
+ if not Report(individual).validate():
43
+ print("Validation failed for creating the individual report.")
44
+ pass
app/wounded.py CHANGED
@@ -4,12 +4,12 @@ from physical.physical_select_animal import create_bird_anatomy
4
  from physical.physical_checkbox import process_body_parts
5
  from behavior.behavior_checkbox import create_behavior_checkbox
6
  from follow_up.followup_events import create_followup_dropdowns, create_followup_open
7
- from utils.utils_json import add_data_to_individual
8
 
9
  def show_section_wounded(visible):
10
  if visible==True:
11
- add_data_to_individual("wounded", "True")
12
- add_data_to_individual("dead", "False")
13
 
14
  with gr.Column(visible=visible, elem_id="wounded") as wounded_section:
15
  gr.Markdown("# Wounded Animal")
 
4
  from physical.physical_checkbox import process_body_parts
5
  from behavior.behavior_checkbox import create_behavior_checkbox
6
  from follow_up.followup_events import create_followup_dropdowns, create_followup_open
7
+ from validation_submission.add_json import add_data_to_individual
8
 
9
  def show_section_wounded(visible):
10
  if visible==True:
11
+ add_data_to_individual("wounded_bool", "True")
12
+ add_data_to_individual("dead_bool", "False")
13
 
14
  with gr.Column(visible=visible, elem_id="wounded") as wounded_section:
15
  gr.Markdown("# Wounded Animal")