ritianyu commited on
Commit
5d0d869
·
1 Parent(s): 2044b1c
Files changed (4) hide show
  1. .gitattributes +2 -0
  2. InfiniDepth/utils/hf_demo_utils.py +112 -27
  3. README.md +6 -0
  4. app.py +2 -1
.gitattributes CHANGED
@@ -2,3 +2,5 @@
2
  *.png filter=lfs diff=lfs merge=lfs -text
3
  *.npz filter=lfs diff=lfs merge=lfs -text
4
  *.npy filter=lfs diff=lfs merge=lfs -text
 
 
 
2
  *.png filter=lfs diff=lfs merge=lfs -text
3
  *.npz filter=lfs diff=lfs merge=lfs -text
4
  *.npy filter=lfs diff=lfs merge=lfs -text
5
+ # checkpoints/depth/*.ckpt filter=lfs diff=lfs merge=lfs -text
6
+ # checkpoints/depth/*.pt filter=lfs diff=lfs merge=lfs -text
InfiniDepth/utils/hf_demo_utils.py CHANGED
@@ -1,6 +1,7 @@
1
  import os
2
  import tempfile
3
  from dataclasses import dataclass
 
4
  from typing import Any, Optional
5
 
6
  import cv2
@@ -23,12 +24,109 @@ from .sampling_utils import make_2d_uniform_coord
23
  from .vis_utils import clip_outliers_by_percentile, colorize_depth_maps
24
 
25
 
 
 
 
 
 
 
 
 
 
26
  DEFAULT_MODEL_PATHS = {
27
- "InfiniDepth": "checkpoints/depth/infinidepth.ckpt",
28
- "InfiniDepth_DC": "checkpoints/depth/infinidepth_dc.ckpt",
29
  }
30
- os.environ.setdefault("INFINIDEPTH_MOGE2_PRETRAINED", "checkpoints/depth/moge2.pt")
31
- DEFAULT_MOGE2_PRETRAINED = os.getenv("INFINIDEPTH_MOGE2_PRETRAINED", "Ruicheng/moge-2-vitl-normal")
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
32
 
33
 
34
  @dataclass
@@ -106,12 +204,13 @@ def _resolve_depth_inputs(
106
  device: torch.device,
107
  ) -> tuple[torch.Tensor, torch.Tensor, torch.Tensor, torch.Tensor, str]:
108
  input_depth_path = depth_path if depth_path else None
 
109
  gt_depth, prompt_depth, gt_depth_mask, used_input_depth = prepare_metric_depth_inputs(
110
  input_depth_path=input_depth_path,
111
  input_size=input_size,
112
  image=image,
113
  device=device,
114
- moge2_pretrained=DEFAULT_MOGE2_PRETRAINED,
115
  depth_load_kwargs={"enable_noise_filter": False},
116
  )
117
  prompt_mask = prompt_depth > 0
@@ -185,31 +284,17 @@ def resolve_checkpoint_path(model_type: str) -> str:
185
  if model_type not in DEFAULT_MODEL_PATHS:
186
  raise ValueError(f"Unsupported model_type: {model_type}")
187
 
188
- local_path = DEFAULT_MODEL_PATHS[model_type]
189
- if os.path.exists(local_path):
190
- Log.info(f"Using local checkpoint for {model_type}: {local_path}")
191
- return local_path
192
-
193
  repo_id = os.getenv("INFINIDEPTH_CKPT_REPO")
194
- if not repo_id:
195
- raise FileNotFoundError(
196
- f"Local checkpoint not found at {local_path}, and env INFINIDEPTH_CKPT_REPO is not set for HF Hub download."
197
- )
198
-
199
- filename_key = "INFINIDEPTH_RGB_CKPT" if model_type == "InfiniDepth" else "INFINIDEPTH_DC_CKPT"
200
- default_name = os.path.basename(local_path)
201
- filename = os.getenv(filename_key, default_name)
202
- Log.info(
203
- f"Downloading checkpoint for {model_type} from Hugging Face Hub: repo_id={repo_id}, filename={filename}"
204
- )
205
-
206
- downloaded = hf_hub_download(
207
- repo_id=repo_id,
208
  filename=filename,
209
- local_dir=os.path.dirname(local_path),
210
- local_dir_use_symlinks=False,
 
211
  )
212
- return downloaded
213
 
214
 
215
  def run_single_image_demo(
 
1
  import os
2
  import tempfile
3
  from dataclasses import dataclass
4
+ from pathlib import Path
5
  from typing import Any, Optional
6
 
7
  import cv2
 
24
  from .vis_utils import clip_outliers_by_percentile, colorize_depth_maps
25
 
26
 
27
+ PROJECT_ROOT = Path(__file__).resolve().parents[2]
28
+ REPO_CKPT_ROOT = PROJECT_ROOT / "checkpoints" / "depth"
29
+ SPACE_RUNTIME = bool(os.getenv("SPACE_ID"))
30
+ HF_LOCAL_FILES_ONLY = os.getenv("INFINIDEPTH_HF_LOCAL_FILES_ONLY", "1" if SPACE_RUNTIME else "0") == "1"
31
+
32
+ DEFAULT_MODEL_FILENAMES = {
33
+ "InfiniDepth": os.getenv("INFINIDEPTH_RGB_CKPT", "infinidepth.ckpt"),
34
+ "InfiniDepth_DC": os.getenv("INFINIDEPTH_DC_CKPT", "infinidepth_dc.ckpt"),
35
+ }
36
  DEFAULT_MODEL_PATHS = {
37
+ model_type: (REPO_CKPT_ROOT / filename).as_posix()
38
+ for model_type, filename in DEFAULT_MODEL_FILENAMES.items()
39
  }
40
+ DEFAULT_MOGE2_FILENAME = os.getenv("INFINIDEPTH_MOGE2_FILENAME", "moge2.pt")
41
+ DEFAULT_MOGE2_LOCAL_PATH = REPO_CKPT_ROOT / DEFAULT_MOGE2_FILENAME
42
+ os.environ.setdefault("INFINIDEPTH_MOGE2_PRETRAINED", DEFAULT_MOGE2_LOCAL_PATH.as_posix())
43
+
44
+
45
+ def _resolve_hub_artifact(
46
+ repo_id: Optional[str],
47
+ filename: str,
48
+ artifact_label: str,
49
+ repo_type: str = "model",
50
+ ) -> str:
51
+ if not repo_id:
52
+ raise FileNotFoundError(
53
+ f"{artifact_label} is not available locally, and the env var pointing to the Hugging Face repo is not set. "
54
+ f"Configure the repo env var and add the file to `preload_from_hub`: {filename}."
55
+ )
56
+
57
+ Log.info(
58
+ f"Resolving {artifact_label} from Hugging Face cache: repo_id={repo_id}, "
59
+ f"filename={filename}, repo_type={repo_type}, local_files_only={HF_LOCAL_FILES_ONLY}"
60
+ )
61
+ return hf_hub_download(
62
+ repo_id=repo_id,
63
+ filename=filename,
64
+ repo_type=repo_type,
65
+ local_files_only=HF_LOCAL_FILES_ONLY,
66
+ )
67
+
68
+
69
+ def _resolve_local_or_hub_artifact(
70
+ local_path: Path,
71
+ filename: str,
72
+ repo_id: Optional[str],
73
+ artifact_label: str,
74
+ repo_type: str = "model",
75
+ ) -> str:
76
+ if local_path.exists():
77
+ Log.info(f"Using local {artifact_label}: {local_path}")
78
+ return local_path.as_posix()
79
+ return _resolve_hub_artifact(
80
+ repo_id=repo_id,
81
+ filename=filename,
82
+ artifact_label=artifact_label,
83
+ repo_type=repo_type,
84
+ )
85
+
86
+
87
+ def resolve_moge2_pretrained() -> str:
88
+ configured = os.getenv("INFINIDEPTH_MOGE2_PRETRAINED", DEFAULT_MOGE2_LOCAL_PATH.as_posix())
89
+ configured_path = Path(configured)
90
+ if configured_path.exists():
91
+ Log.info(f"Using configured MoGe-2 weights: {configured_path}")
92
+ return configured_path.as_posix()
93
+
94
+ if configured != DEFAULT_MOGE2_LOCAL_PATH.as_posix():
95
+ if configured.count("/") == 1 and configured_path.suffix == "":
96
+ repo_type = os.getenv("INFINIDEPTH_MOGE2_REPO_TYPE", "model")
97
+ Log.info(
98
+ f"Resolving MoGe-2 repo from INFINIDEPTH_MOGE2_PRETRAINED via Hugging Face cache: "
99
+ f"repo_id={configured}, filename={DEFAULT_MOGE2_FILENAME}, "
100
+ f"repo_type={repo_type}, local_files_only={HF_LOCAL_FILES_ONLY}"
101
+ )
102
+ return hf_hub_download(
103
+ repo_id=configured,
104
+ filename=DEFAULT_MOGE2_FILENAME,
105
+ repo_type=repo_type,
106
+ local_files_only=HF_LOCAL_FILES_ONLY,
107
+ )
108
+ Log.info(f"Using non-local MoGe-2 source from INFINIDEPTH_MOGE2_PRETRAINED: {configured}")
109
+ return configured
110
+
111
+ repo_id = os.getenv("INFINIDEPTH_MOGE2_REPO", os.getenv("INFINIDEPTH_CKPT_REPO"))
112
+ repo_type = os.getenv("INFINIDEPTH_MOGE2_REPO_TYPE", os.getenv("INFINIDEPTH_CKPT_REPO_TYPE", "model"))
113
+ return _resolve_local_or_hub_artifact(
114
+ local_path=DEFAULT_MOGE2_LOCAL_PATH,
115
+ filename=DEFAULT_MOGE2_FILENAME,
116
+ repo_id=repo_id,
117
+ artifact_label="MoGe-2 checkpoint",
118
+ repo_type=repo_type,
119
+ )
120
+
121
+
122
+ def prepare_runtime_assets() -> None:
123
+ Log.info(
124
+ f"Preparing runtime assets: checkpoint_root={REPO_CKPT_ROOT}, "
125
+ f"space_runtime={SPACE_RUNTIME}, hf_local_files_only={HF_LOCAL_FILES_ONLY}"
126
+ )
127
+ for model_type in DEFAULT_MODEL_FILENAMES:
128
+ resolve_checkpoint_path(model_type)
129
+ resolve_moge2_pretrained()
130
 
131
 
132
  @dataclass
 
204
  device: torch.device,
205
  ) -> tuple[torch.Tensor, torch.Tensor, torch.Tensor, torch.Tensor, str]:
206
  input_depth_path = depth_path if depth_path else None
207
+ moge2_pretrained = resolve_moge2_pretrained()
208
  gt_depth, prompt_depth, gt_depth_mask, used_input_depth = prepare_metric_depth_inputs(
209
  input_depth_path=input_depth_path,
210
  input_size=input_size,
211
  image=image,
212
  device=device,
213
+ moge2_pretrained=moge2_pretrained,
214
  depth_load_kwargs={"enable_noise_filter": False},
215
  )
216
  prompt_mask = prompt_depth > 0
 
284
  if model_type not in DEFAULT_MODEL_PATHS:
285
  raise ValueError(f"Unsupported model_type: {model_type}")
286
 
287
+ local_path = Path(DEFAULT_MODEL_PATHS[model_type])
 
 
 
 
288
  repo_id = os.getenv("INFINIDEPTH_CKPT_REPO")
289
+ repo_type = os.getenv("INFINIDEPTH_CKPT_REPO_TYPE", "model")
290
+ filename = DEFAULT_MODEL_FILENAMES[model_type]
291
+ return _resolve_local_or_hub_artifact(
292
+ local_path=local_path,
 
 
 
 
 
 
 
 
 
 
293
  filename=filename,
294
+ repo_id=repo_id,
295
+ artifact_label=f"{model_type} checkpoint",
296
+ repo_type=repo_type,
297
  )
 
298
 
299
 
300
  def run_single_image_demo(
README.md CHANGED
@@ -6,8 +6,14 @@ colorTo: purple
6
  sdk: gradio
7
  sdk_version: 5.47.2
8
  app_file: app.py
 
 
9
  pinned: false
10
  license: apache-2.0
11
  short_description: InfiniDepth Huggingface Demo
12
  ---
13
  Check out the configuration reference at https://huggingface.co/docs/hub/spaces-config-reference
 
 
 
 
 
6
  sdk: gradio
7
  sdk_version: 5.47.2
8
  app_file: app.py
9
+ preload_from_hub:
10
+ - ritianyu/InfiniDepth infinidepth.ckpt,infinidepth_dc.ckpt,moge2.pt
11
  pinned: false
12
  license: apache-2.0
13
  short_description: InfiniDepth Huggingface Demo
14
  ---
15
  Check out the configuration reference at https://huggingface.co/docs/hub/spaces-config-reference
16
+
17
+ For Hugging Face Spaces, `preload_from_hub` now preloads the three checkpoint files from
18
+ `ritianyu/InfiniDepth` during build time. Set `INFINIDEPTH_CKPT_REPO=ritianyu/InfiniDepth`
19
+ in the Space variables so runtime loading resolves the same cached files.
app.py CHANGED
@@ -22,7 +22,7 @@ import gradio as gr
22
  import numpy as np
23
  from PIL import Image
24
 
25
- from InfiniDepth.utils.hf_demo_utils import ModelCache, run_single_image_demo
26
  from InfiniDepth.utils.logger import Log
27
 
28
  try:
@@ -423,6 +423,7 @@ demo = demo.queue()
423
 
424
 
425
  if __name__ == "__main__":
 
426
  server_name = "0.0.0.0" if os.getenv("SPACE_ID") else "127.0.0.1"
427
  # Hugging Face Spaces with Gradio typically expects port 7860.
428
  # Respect explicit Gradio/PORT env overrides when provided.
 
22
  import numpy as np
23
  from PIL import Image
24
 
25
+ from InfiniDepth.utils.hf_demo_utils import ModelCache, prepare_runtime_assets, run_single_image_demo
26
  from InfiniDepth.utils.logger import Log
27
 
28
  try:
 
423
 
424
 
425
  if __name__ == "__main__":
426
+ prepare_runtime_assets()
427
  server_name = "0.0.0.0" if os.getenv("SPACE_ID") else "127.0.0.1"
428
  # Hugging Face Spaces with Gradio typically expects port 7860.
429
  # Respect explicit Gradio/PORT env overrides when provided.