Skip to content

Commit e164656

Browse files
aw471agautam478
andcommitted
Load the pretrained KumoAnomaly checkpoint
Co-authored-by: Aditi Gautam <adgautam@nvidia.com>
1 parent d92932e commit e164656

2 files changed

Lines changed: 38 additions & 4 deletions

File tree

Lines changed: 32 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,32 @@
1+
# SPDX-FileCopyrightText: Copyright (c) 2026, NVIDIA CORPORATION & AFFILIATES. All rights reserved.
2+
# SPDX-License-Identifier: Apache-2.0
3+
4+
from torch import Tensor
5+
6+
7+
def remap_ckpt(ckpt: dict[str, Tensor]) -> dict[str, Tensor]: # noqa: D103
8+
out = {}
9+
for key, value in ckpt.items():
10+
if key.startswith("diffmodel."):
11+
key = "denoiser." + key.removeprefix("diffmodel.")
12+
for old, new in (
13+
("layers.0.self_attn.in_proj_", "attn.qkv_lin."),
14+
("layers.0.self_attn.out_proj.", "attn.out_lin."),
15+
("layers.0.linear1.", "mlp.0."),
16+
("layers.0.linear2.", "mlp.3."),
17+
("layers.0.norm1.", "attn_residual_norm."),
18+
("layers.0.norm2.", "mlp_residual_norm."),
19+
):
20+
key = key.replace(old, new)
21+
if key in (
22+
"denoiser.input_projection.weight",
23+
"denoiser.output_projection1.weight",
24+
"denoiser.output_projection2.weight",
25+
):
26+
value = value.squeeze(-1) # `Conv1d` to `Linear`.
27+
elif key.startswith(
28+
("embed_layer.", "embed_norm.", "time_embed_norm.")
29+
):
30+
key = "side_embedding." + key
31+
out[key] = value
32+
return out

‎sdm/models/kumo/timeseries/anomaly/model.py‎

Lines changed: 6 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,7 @@
1919
from sdm._warnings import warn_once
2020
from sdm.models import Callback, Model
2121
from sdm.models._huggingface import download_checkpoint
22+
from sdm.models.kumo.timeseries.anomaly.ckpt import remap_ckpt
2223
from sdm.models.kumo.timeseries.anomaly.denoiser import DiffusionDenoiser
2324
from sdm.models.kumo.timeseries.anomaly.embedding import SideEmbedding
2425
from sdm.models.kumo.timeseries.anomaly.recipe import default_recipe
@@ -61,9 +62,9 @@ def __init__(
6162
) -> None:
6263
super().__init__()
6364

64-
self.model = _KumoAnomaly(
65-
device="meta" if pretrained else device,
66-
)
65+
# Build on the target device, since the checkpoint does not contain
66+
# the non-persistent sinusoidal lookup of the step embedding:
67+
self.model = _KumoAnomaly(device=device)
6768

6869
if pretrained:
6970
self._load_from_pretrained(device=device)
@@ -81,7 +82,8 @@ def _load_from_pretrained(
8182
filename="final_model.pth",
8283
revision="226c5003b0582adc1cac433123f47324bfae39f2",
8384
)
84-
torch.load(path, map_location=device, weights_only=True) # TODO
85+
ckpt = torch.load(path, map_location=device, weights_only=True)
86+
self.model.load_state_dict(remap_ckpt(ckpt["model"]))
8587

8688
return self
8789

0 commit comments

Comments
 (0)