IGH_UpgradeObject not called to Upgrade

Is there some extra step to make sure Grasshopper calls my upgrade object?

Currently I have a very simple one:

public class CSLoadTransferSurfaceComponentUpgrader : IGH_UpgradeObject
{
    public CSLoadTransferSurfaceComponentUpgrader() { }
    public DateTime Version
    {
        get { return new DateTime(2020, 6, 26, 14, 00, 00); }
    }
    public Guid UpgradeFrom
    {
        get { return new Guid("80c3b6c7-e2a6-4eef-a16c-c73b88148389"); }
    }
    public Guid UpgradeTo
    {
        get { return new Guid("9c821071-2228-4290-8a8a-ac6df7ee29ab"); }
    }

    public IGH_DocumentObject Upgrade(IGH_DocumentObject target, GH_Document document)
    {
        IGH_Component newComp = GH_UpgradeUtil.SwapComponents((IGH_Component)target, UpgradeTo, false);
        if (newComp == null) { return null; }

        GH_UpgradeUtil.MigrateInputParameters((IGH_Component)target, newComp, new int[] {0,1,2,3,4,5 }, new int[] { 0, 1, 2, 3, 4, 5 });
        GH_UpgradeUtil.MigrateOutputParameters((IGH_Component)target, newComp, new int[] { 0 }, new int[] { 0 });

        return newComp;
    }
}

I can see, that it’s constructor, and the UpgradeFrom getter is called by GH, and double-triple checked that the guid is correctly the same as the obsolete component’s one, but the Upgrade method never gets called, and the file loads in with the obsolete components, shown with an “old” sticker over the icon.
(the upgrader only cuts of input parameters that are no longer used)

Edit: I just realized that this is a manually initiated feature by the user, not automatically done in the background on file loading. Calling it from the GUI works correctly.

2 Likes

@DavidRutten is it possible to call the UpgradeAllComponents method in a document through code without hitting the context menu button → GUI?

Or should i make some reflection to iterate over all classes with that interface and set it up from scratch?

There is no tool for auto-upgrading all components. Sorry.

  1. Get list of all document objects
  2. Use each objects GUID to find the newest relevant IGH_UpgradeObject (I believe it returns the most recent one based on the IGH_UpgradeObject.Version date if you have multiple existing upgrade options defined for the GUID)
  3. If the returned IGH_UpgradeObject is not null, call IGH_UpgradeObject.Upgrade(docObject, doc)

Just tested it using a quick ghPython script and works like a charm

import Grasshopper

doc = ghenv.Component.OnPingDocument()
components = [obj for obj in doc.Objects]

for comp in components:
    upgrader = Grasshopper.Instances.ComponentServer.FindUpgrader(comp.ComponentGuid)
    if (upgrader):
        upgrader.Upgrade(comp, doc)
1 Like

Exactly my kind of solution! Thanks for beating me to it :wink: