xiangjx commited on
Commit
a4b044c
·
verified ·
1 Parent(s): 047c4f8

Fix RNA conditioning, MUSK encoder init, and text/inference mismatch

Browse files
Files changed (1) hide show
  1. pipeline.py +59 -33
pipeline.py CHANGED
@@ -7,29 +7,17 @@ import math
7
  import numpy as np
8
  from PIL import Image
9
  from diffusers import DiffusionPipeline, AutoencoderKL
10
- from dictdot import dictdot
11
  import gc
12
 
13
- from models.autoencoder import vae_models
14
- from samplers import euler_sampler, euler_maruyama_sampler
 
 
 
15
 
16
  def denormalize_latents(latents, latents_scale, latents_bias):
17
  return latents / latents_scale + latents_bias
18
 
19
- try:
20
- from models.sit import SiT_models
21
- except ImportError:
22
- # Fallback for published structure where sit is in transformer/
23
- from transformer.sit import SiT_models
24
-
25
- try:
26
- from models.projection_loss import CosineProjectionLoss
27
- except ImportError:
28
- try:
29
- from transformer.projection_loss import CosineProjectionLoss
30
- except ImportError:
31
- pass # Might not be needed for inference
32
-
33
  # Must match the training-time order (train.py / generate.py); the checkpoint's
34
  # modality_embedding has one row per entry.
35
  MODALITY_ORDER = ("text", "image", "st", "st_meta")
@@ -69,7 +57,19 @@ class SiTPipeline(DiffusionPipeline):
69
  else:
70
  # Legacy/Experiment loading logic
71
  device = kwargs.get("device", torch.device("cuda" if torch.cuda.is_available() else "cpu"))
72
-
 
 
 
 
 
 
 
 
 
 
 
 
73
  # 1. Determine Layout and Load Config
74
  # Check for published config first (sit_config.json)
75
  published_config_path = os.path.join(pretrained_model_path, "sit_config.json")
@@ -306,32 +306,56 @@ class SiTPipeline(DiffusionPipeline):
306
  ])
307
  print("MUSK encoder loaded successfully.")
308
 
309
- def _ensure_musk_encoder(self):
310
  """
311
- Load MUSK on first use when the pipeline was built by the standard
312
- DiffusionPipeline.from_pretrained route, which bypasses our from_pretrained.
 
 
 
313
  """
314
- if self.musk_encoder is not None:
315
- return
 
316
 
317
  # diffusers records where the pipeline came from after instantiation.
318
- model_root = getattr(self.config, "_name_or_path", None)
319
- if not model_root:
320
  raise RuntimeError(
321
- "MUSK encoder not initialized and the model path is unknown. "
322
- "Call pipeline.load_musk_encoder('/path/to/snapshot') explicitly."
323
  )
324
 
325
- if not os.path.isdir(model_root):
326
- # It's a Hub repo id; fetch the assets the encoder needs.
 
327
  from huggingface_hub import snapshot_download
328
- model_root = snapshot_download(
329
- repo_id=model_root,
330
  repo_type="model",
331
- allow_patterns=["musk/**", "musk_weights/**"],
332
  )
333
 
334
- self.load_musk_encoder(model_root, device=self.device)
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
335
 
336
  def to(self, *args, **kwargs):
337
  super().to(*args, **kwargs)
@@ -437,6 +461,8 @@ class SiTPipeline(DiffusionPipeline):
437
  cls_latents=cls_latents,
438
  )
439
 
 
 
440
  if mode == "sde":
441
  latents = euler_maruyama_sampler(**sampling_kwargs).to(torch.float32)
442
  elif mode == "ode":
 
7
  import numpy as np
8
  from PIL import Image
9
  from diffusers import DiffusionPipeline, AutoencoderKL
 
10
  import gc
11
 
12
+ # NOTE: the repo's own modules (samplers.py, models/, musk/) are deliberately NOT
13
+ # imported at module scope. When loaded via custom_pipeline, diffusers copies only
14
+ # this file into its modules cache, so those imports would fail for anyone whose
15
+ # working directory doesn't happen to contain them. They are imported lazily once
16
+ # _snapshot_root() has put the downloaded snapshot on sys.path.
17
 
18
  def denormalize_latents(latents, latents_scale, latents_bias):
19
  return latents / latents_scale + latents_bias
20
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
21
  # Must match the training-time order (train.py / generate.py); the checkpoint's
22
  # modality_embedding has one row per entry.
23
  MODALITY_ORDER = ("text", "image", "st", "st_meta")
 
57
  else:
58
  # Legacy/Experiment loading logic
59
  device = kwargs.get("device", torch.device("cuda" if torch.cuda.is_available() else "cpu"))
60
+
61
+ # This layout builds the model from source, so make the bundled modules importable.
62
+ legacy_root = os.path.abspath(pretrained_model_path)
63
+ if legacy_root not in sys.path:
64
+ sys.path.append(legacy_root)
65
+ from dictdot import dictdot
66
+ from models.autoencoder import vae_models
67
+ try:
68
+ from models.sit import SiT_models
69
+ except ImportError:
70
+ # Published structure keeps sit in transformer/
71
+ from transformer.sit import SiT_models
72
+
73
  # 1. Determine Layout and Load Config
74
  # Check for published config first (sit_config.json)
75
  published_config_path = os.path.join(pretrained_model_path, "sit_config.json")
 
306
  ])
307
  print("MUSK encoder loaded successfully.")
308
 
309
+ def _snapshot_root(self):
310
  """
311
+ Local directory holding the bundled code and assets (samplers.py, models/,
312
+ musk/, musk_weights/), with that directory added to sys.path.
313
+
314
+ Under custom_pipeline, only pipeline.py lands in the diffusers modules cache,
315
+ so the rest has to be located explicitly rather than imported as siblings.
316
  """
317
+ cached = getattr(self, "_resolved_root", None)
318
+ if cached:
319
+ return cached
320
 
321
  # diffusers records where the pipeline came from after instantiation.
322
+ root = getattr(self.config, "_name_or_path", None)
323
+ if not root:
324
  raise RuntimeError(
325
+ "Cannot locate the model snapshot (no _name_or_path). Load the pipeline "
326
+ "with SiTPipeline.from_pretrained('/path/to/snapshot')."
327
  )
328
 
329
+ if not os.path.isdir(root):
330
+ # It's a Hub repo id; fetch the code/assets (weights are already cached
331
+ # by from_pretrained, and this resolves to the same snapshot directory).
332
  from huggingface_hub import snapshot_download
333
+ root = snapshot_download(
334
+ repo_id=root,
335
  repo_type="model",
336
+ allow_patterns=["*.py", "models/**", "musk/**", "musk_weights/**"],
337
  )
338
 
339
+ root = os.path.abspath(root)
340
+ if root not in sys.path:
341
+ sys.path.append(root)
342
+ self._resolved_root = root
343
+ return root
344
+
345
+ def _load_samplers(self):
346
+ self._snapshot_root()
347
+ from samplers import euler_sampler, euler_maruyama_sampler
348
+ return euler_sampler, euler_maruyama_sampler
349
+
350
+ def _ensure_musk_encoder(self):
351
+ """
352
+ Load MUSK on first use when the pipeline was built by the standard
353
+ DiffusionPipeline.from_pretrained route, which bypasses our from_pretrained.
354
+ """
355
+ if self.musk_encoder is not None:
356
+ return
357
+
358
+ self.load_musk_encoder(self._snapshot_root(), device=self.device)
359
 
360
  def to(self, *args, **kwargs):
361
  super().to(*args, **kwargs)
 
461
  cls_latents=cls_latents,
462
  )
463
 
464
+ euler_sampler, euler_maruyama_sampler = self._load_samplers()
465
+
466
  if mode == "sde":
467
  latents = euler_maruyama_sampler(**sampling_kwargs).to(torch.float32)
468
  elif mode == "ode":