docs.unity3d.com
Search Results for

    Show / Hide Table of Contents

    Use case: Replace uploaded file content

    You can use the Unity Cloud Assets package to upload new content for a file.

    Note

    Once a file is uploaded, its content cannot be modified. If you want to change the content of a file, you must:

    1. Remove all references to this file, effectively deleting it.
    2. You may upload a new file with the same name.

    The SDK supports different workflows for users with different roles.

    Organization or Asset Manager Project role Upload file content
    Asset Management Viewer no
    Asset Management Consumer no
    Asset Management Contributor yes
    Organization Owner yes

    Before you start

    Before you start, you must:

    1. Set up a Unity scene in the Unity Editor with an Organization and Project browser. See Get started with Assets for more information.

    2. Have some assets in the cloud. There are several ways to do so:

      • You can create assets through the Get started with Assets.
      • You can create assets through the dashboard, see the Managing assets on the dashboard documentation.

    You should also have uploaded files to an asset, see the Create files use case.

    How do I...?

    List the files of an asset

    By default, when you get an asset, the files associated with are not included in the response. To get files associated to an asset, follow these steps:

    1. Open the AssetManagementBehaviour script you created.
    2. Add the following code to the end of the class:
    
    CancellationTokenSource m_DatasetCancellationSource;
    CancellationTokenSource m_FileCancellationSource;
    
    public IEnumerable<IDataset> Datasets { get; private set; }
    
    public IDataset CurrentDataset { get; set; }
    
    public IEnumerable<IFile> Files { get; private set; }
    
    public IFile CurrentFile { get; set; }
    
    public async Task GetDataSetsAsync()
    {
        CleanFileCancellation();
        Files = null;
    
        CleanDatasetCancellation();
        Datasets = null;
    
        if (CurrentAsset == null) return;
    
        m_DatasetCancellationSource = new CancellationTokenSource();
        var token = m_DatasetCancellationSource.Token;
    
        var datasets = new List<IDataset>();
        var datasetList = CurrentAsset.ListDatasetsAsync(Range.All, token);
        await foreach (var dataset in datasetList)
        {
            if (token.IsCancellationRequested) break;
    
            datasets.Add(dataset);
        }
    
        if (token.IsCancellationRequested) return;
    
        Datasets = datasets;
        CleanDatasetCancellation();
    }
    
    public async Task GetFilesAsync()
    {
        CleanFileCancellation();
    
        Files = null;
    
        if (CurrentDataset == null) return;
    
        m_FileCancellationSource = new CancellationTokenSource();
        var token = m_FileCancellationSource.Token;
    
        var files = new List<IFile>();
        var fileList = CurrentDataset.ListFilesAsync(Range.All, token);
        await foreach (var file in fileList)
        {
            files.Add(file);
        }
    
        Files = files;
        CleanFileCancellation();
    }
    
    void CleanDatasetCancellation()
    {
        if (m_DatasetCancellationSource != null)
        {
            m_DatasetCancellationSource.Cancel();
            m_DatasetCancellationSource.Dispose();
        }
    
        m_DatasetCancellationSource = null;
    }
    
    void CleanFileCancellation()
    {
        if (m_FileCancellationSource != null)
        {
            m_FileCancellationSource.Cancel();
            m_FileCancellationSource.Dispose();
        }
    
        m_FileCancellationSource = null;
    }
    
    

    The code snippet populates the Files property of the selected asset.

    Replace a file

    To replace the content of a file, follow these steps:

    1. Open the AssetManagementBehaviour script you created.
    2. Add the following code to the end of the class:
    
    CancellationTokenSource m_CancellationTokenSource;
    
    public bool CanCancel => m_CancellationTokenSource is {IsCancellationRequested: false};
    
    class LogProgress : IProgress<HttpProgress>
    {
        public void Report(HttpProgress value)
        {
            if (!value.UploadProgress.HasValue) return;
    
            Debug.Log($"Upload progress: {value.UploadProgress * 100} %");
        }
    }
    
    public async Task ReplaceFileAsync(IFile file, MemoryStream memoryStream)
    {
        await file.UploadAsync(memoryStream, new LogProgress(), GetCancellationToken());
    }
    
    public void Cancel()
    {
        if (m_CancellationTokenSource != null)
        {
            m_CancellationTokenSource.Cancel();
            m_CancellationTokenSource.Dispose();
        }
    
        m_CancellationTokenSource = null;
    }
    
    CancellationToken GetCancellationToken()
    {
        Cancel();
    
        m_CancellationTokenSource = new CancellationTokenSource();
        return m_CancellationTokenSource.Token;
    }
    
    

    The code snippet does the following:

    • Removes the file from each dataset it is referenced in.
    • Creates and uploads the file as a new file to one of the datasets.
    • Adds a reference to the new file in each dataset the old file was referenced in.

    Add the UI for re-uploading file content

    To create UI for re-uploading file content, follow these steps:

    1. In your Unity Project window, go to Assets > Scripts.
    2. Select and hold the Assets/Scripts folder.
    3. Go to Create > C# Script. Name your script UseCaseFileReuploadExampleUI.
    4. Open the UseCaseFileReuploadExampleUI script you created and replace the contents of the file with the following code sample:
    
    using System;
    using System.Collections.Generic;
    using System.IO;
    using System.Linq;
    using System.Threading;
    using System.Threading.Tasks;
    using Unity.Cloud.Assets;
    using Unity.Cloud.Common;
    using UnityEditor;
    using UnityEngine;
    
    public class UseCaseFileReuploadExampleUI : IAssetManagementUI
    {
        readonly AssetManagementBehaviour m_Behaviour;
    
        public UseCaseFileReuploadExampleUI(AssetManagementBehaviour behaviour)
        {
            m_Behaviour = behaviour;
        }
    
        public void OnGUI() { }
    }
    
    
    1. In the same script, replace the OnGUI function with the following code:
    
    IAsset m_CurrentAsset;
    
    Dictionary<DatasetId, bool> m_Expanded = new();
    
    public void OnGUI()
    {
        if (!m_Behaviour.IsProjectSelected) return;
    
        if (m_Behaviour.CurrentAsset == null)
        {
            GUILayout.Label(" ! No asset selected !");
            return;
        }
    
        if (m_CurrentAsset != m_Behaviour.CurrentAsset)
        {
            m_CurrentAsset = m_Behaviour.CurrentAsset;
            m_Behaviour.DatasetFiles.Clear();
            _ = m_Behaviour.GetDataSetsAsync();
        }
    
        if (m_Behaviour.Datasets == null)
        {
            GUILayout.Label("Loading datasets...");
            return;
        }
    
        GUILayout.BeginVertical();
    
        if (GUILayout.Button("Refresh", GUILayout.Width(60)))
        {
            _ = m_Behaviour.GetDataSetsAsync();
        }
    
        GUILayout.Space(5f);
    
        DisplayDatasets(m_Behaviour.Datasets.ToArray());
    
        GUILayout.EndVertical();
    }
    
    void DisplayDatasets(IReadOnlyCollection<IDataset> datasets)
    {
        if (datasets.Count == 0)
        {
            GUILayout.Label("No datasets.");
        }
    
        foreach (var dataset in datasets)
        {
            GUILayout.BeginHorizontal();
    
            GUILayout.Label($"{dataset.Name}");
    
            var expanded = m_Expanded.GetValueOrDefault(dataset.Descriptor.DatasetId);
            if (GUILayout.Button(expanded ? "-" : "+", GUILayout.Width(20f)))
            {
                expanded = !expanded;
                m_Expanded[dataset.Descriptor.DatasetId] = expanded;
    
                if (!expanded)
                {
                    m_Behaviour.DatasetFiles.Remove(dataset.Descriptor.DatasetId);
                }
            }
    
            GUILayout.EndHorizontal();
    
            if (expanded)
            {
                GUILayout.BeginHorizontal();
    
                GUILayout.Space(25);
    
                DisplayFiles(dataset.Descriptor.DatasetId);
    
                GUILayout.EndHorizontal();
            }
        }
    }
    
    void DisplayFiles(DatasetId datasetId)
    {
        if (!m_Behaviour.DatasetFiles.ContainsKey(datasetId))
        {
            _ = m_Behaviour.GetFilesAsync(datasetId);
        }
    
        var files = m_Behaviour.DatasetFiles.GetValueOrDefault(datasetId);
    
        if (files == null)
        {
            GUILayout.Label("Loading files...");
            return;
        }
    
        var enumerable = files.ToArray();
        if (!enumerable.Any())
        {
            GUILayout.Label("No files.");
            return;
        }
    
        GUILayout.BeginVertical();
    
        foreach (var file in enumerable)
        {
            GUILayout.BeginHorizontal();
    
            GUILayout.Label($"{file.Descriptor.Path}");
    
            GUILayout.Space(5f);
    
            if (GUILayout.Button("Upload new content", GUILayout.Width(150)))
            {
                var path = EditorUtility.OpenFilePanel("Choose a file to upload.", Environment.GetFolderPath(Environment.SpecialFolder.MyDocuments), "");
                if (!string.IsNullOrEmpty(path))
                {
                    var memoryStream = new MemoryStream(File.ReadAllBytes(path));
                    _ = m_Behaviour.ReplaceFileAsync(file, memoryStream);
                }
            }
    
            GUILayout.EndHorizontal();
        }
    
        GUILayout.EndVertical();
    }
    
    
    1. Open the AssetManagementUI script you created and replace the contents of the Awake function with the following code:
    
    m_UI.Add(new OrganizationSelectionExampleUI(m_Behaviour));
    m_UI.Add(new ProjectSelectionExampleUI(m_Behaviour));
    m_UI.Add(new AssetSelectionExampleUI(m_Behaviour));
    m_UI.Add(new UseCaseFileReuploadExampleUI(m_Behaviour));
    
    

    The script does the following:

    • Displays a text field to enter a path to a file to upload.
    • Displays a list of the selected asset's files with a button to replace the file.
    • Displays a button to cancel the request once started.
    In This Article
    Back to top
    Copyright © 2024 Unity Technologies — Trademarks and terms of use
    • Legal
    • Privacy Policy
    • Cookie Policy
    • Do Not Sell or Share My Personal Information
    • Your Privacy Choices (Cookie Settings)