Creating a ScriptableObject from AssetPostprocessor

I have an asset pack that I am using for my game and would like to create a ScriptableObject from an AssetPostprocessor.

I’ve started with a simple version of this so that I can iron out any issues.
Here is my PostProcessor code:

public class SOCreator : AssetPostprocessor
    {
        private void OnPostprocessPrefab(GameObject g)
        {
            // Ignored scenarios
            if (!assetPath.StartsWith("Assets/Asset Pack/- Prefabs/"))
                return;
            if (!assetPath.EndsWith(".prefab"))
                return;
            if (!assetPath.EndsWith("stone-a.prefab"))
                return;
           
            var myData = ScriptableObject.CreateInstance<MyData>();
            myData .prefab = g;
            myData .id = myData .prefab.name;
            AssetDatabase.CreateAsset(myData , "Assets/_SO/Asset Pack/" + myData .id + ".asset");
        }

    }

I am not having issues with creating the asset, but I get a warning that makes me think I should be doing this differently:

Calls to “AssetDatabase.CreateAsset” are restricted during asset importing. AssetDatabase.CreateAsset() was called as part of running an import. Please make sure this function is not called from ScriptedImporters or PostProcessors, as it is a source of non-determinism and will be disallowed in a forthcoming release.

Is there a way I should be doing this that will be more future proofed, or is this just not something I should be doing?

Use OnPostprocessAllAssets because in this method the import has completed and the AssetDatabase can be used normally.

Note that if you are likely going to create several assets in a single import step, make sure to use Start/StopAssetEditing enclosed in try/finally to significantly speed up the process.

2 Likes