Expand my Community achievements bar.

Dive into Adobe Summit 2024! Explore curated list of AEM sessions & labs, register, connect with experts, ask questions, engage, and share insights. Don't miss the excitement.
SOLVED

Retrieving and Creating Asset Relations via the APIs

Avatar

Level 2

Hi there,

We're building an integration between Adobe Assets (6.5) and an accessibility provider where we'll send them the binaries and then they return, later, 3 different binaries with various accessibility files in. Getting the assets from AEM to them is trivial, uploading the assets to AEM in return via the HTTP API and then upload metadata is similarly trivial, but are there API methods for exporting Related Assets and then Creating or Updating Related Assets, i.e. this section:

 

pcardno_0-1673008484427.png

 

I can't find anything in the API documentation about how to handle exporting or creating those relationships.

 

Thank you!

 

 

Paul.

 

1 Accepted Solution

Avatar

Correct answer by
Community Advisor

Hi @pcardno,

In general HTTP Asset API is not supporting either listing of relationships, or managing (adding, removing) relationship between the assets.

I would suggest to explore below options.

  1. Write your own servlet that will handle what you need using Asset Java api (mainly Asset, AssetManager, AssetRelation). Here is a very simple code snippet that is setting relationship between 2 assets.
    import com.adobe.granite.asset.api.Asset;
    import com.adobe.granite.asset.api.AssetManager;
    
    AssetManager assetManager = resourceResolver.adaptTo(AssetManager.class);
    if (assetManager != null) {
        Asset asset = assetManager.getAsset("/content/dam/we-retail-screens/usa.png");
        
        /**
         * First param represents relation type/name - possible values seources, derived, others
         * Second param represents path to asset that will be related to given asset
         */
        asset.addRelation("others", "/content/dam/we-retail-screens/we-retail-instore-logo.png");
        resourceResolver.commit();
    
    }​
  2. You can try to utilize OOTB ManageReferencesServlet, in general this servlet is use when you managing relation via GUI. It base on manageReferences selector, and supports 2 HTTP methods: GET and POST. GET will allow you to list information about relation for given asset(s), POST is used do manipulate relation (add, remove).
    // GET
    /content/dam/we-retail-screens/usa.manageReferences.png?item=/content/dam/we-retail-screens/usa.png​

    You should simply use manageReferences selector and item param, one request can contain multiple item parameters, e.g

    /content/dam/we-retail-screens/usa.manageReferences.png?item=/content/dam/we-retail-screens/usa.png&item=/content/dam/we-retail-screens/italy.png

    For POST I would suggest to experiment with network tab from dev tools in the browser, and maybe record POST request to get better idea/understanding what data/format is sent. You can expect that information about relation will be passed via JSON param that could look like this:

    "{\"/content/dam/we-retail-screens/usa.png\":{\"name\":\"usa.png\",\"sources\":{},\"derived\":{\"/content/dam/we-retail-screens/italy.png\":{\"name\":\"\"}},\"others\":{\"/content/dam/we-retail-screens/we-retail-instore-logo.png\":{\"name\":\"we-retail-instore-logo.png\"}},\"relationName\":\"derived\"},\"/content/dam/we-retail-screens/italy.png\":{\"name\":\"italy.png\",\"sources\":{\"/content/dam/we-retail-screens/usa.png\":{\"name\":\"\"}},\"derived\":{},\"others\":{},\"relationName\":\"sources\"}}"

Please be aware that if you will go with approach number 2 you will also need to make sure to assure some authentication - because ManageReferencesServlet is not available publically - you have to be logged in to use it.

Saying that, I would rather recommend option 1, mainly because it will give you full control of  HTTP contract of your endpoint etc (what methods, params you will use etc) and backend implementation - especially that Java Asset api gives you all you need. The other thing is that if you will use option 2, there is a chance something will change in the future in terms of ManageReferencesServlet contract and your solution will stop working.

View solution in original post

3 Replies

Avatar

Correct answer by
Community Advisor

Hi @pcardno,

In general HTTP Asset API is not supporting either listing of relationships, or managing (adding, removing) relationship between the assets.

I would suggest to explore below options.

  1. Write your own servlet that will handle what you need using Asset Java api (mainly Asset, AssetManager, AssetRelation). Here is a very simple code snippet that is setting relationship between 2 assets.
    import com.adobe.granite.asset.api.Asset;
    import com.adobe.granite.asset.api.AssetManager;
    
    AssetManager assetManager = resourceResolver.adaptTo(AssetManager.class);
    if (assetManager != null) {
        Asset asset = assetManager.getAsset("/content/dam/we-retail-screens/usa.png");
        
        /**
         * First param represents relation type/name - possible values seources, derived, others
         * Second param represents path to asset that will be related to given asset
         */
        asset.addRelation("others", "/content/dam/we-retail-screens/we-retail-instore-logo.png");
        resourceResolver.commit();
    
    }​
  2. You can try to utilize OOTB ManageReferencesServlet, in general this servlet is use when you managing relation via GUI. It base on manageReferences selector, and supports 2 HTTP methods: GET and POST. GET will allow you to list information about relation for given asset(s), POST is used do manipulate relation (add, remove).
    // GET
    /content/dam/we-retail-screens/usa.manageReferences.png?item=/content/dam/we-retail-screens/usa.png​

    You should simply use manageReferences selector and item param, one request can contain multiple item parameters, e.g

    /content/dam/we-retail-screens/usa.manageReferences.png?item=/content/dam/we-retail-screens/usa.png&item=/content/dam/we-retail-screens/italy.png

    For POST I would suggest to experiment with network tab from dev tools in the browser, and maybe record POST request to get better idea/understanding what data/format is sent. You can expect that information about relation will be passed via JSON param that could look like this:

    "{\"/content/dam/we-retail-screens/usa.png\":{\"name\":\"usa.png\",\"sources\":{},\"derived\":{\"/content/dam/we-retail-screens/italy.png\":{\"name\":\"\"}},\"others\":{\"/content/dam/we-retail-screens/we-retail-instore-logo.png\":{\"name\":\"we-retail-instore-logo.png\"}},\"relationName\":\"derived\"},\"/content/dam/we-retail-screens/italy.png\":{\"name\":\"italy.png\",\"sources\":{\"/content/dam/we-retail-screens/usa.png\":{\"name\":\"\"}},\"derived\":{},\"others\":{},\"relationName\":\"sources\"}}"

Please be aware that if you will go with approach number 2 you will also need to make sure to assure some authentication - because ManageReferencesServlet is not available publically - you have to be logged in to use it.

Saying that, I would rather recommend option 1, mainly because it will give you full control of  HTTP contract of your endpoint etc (what methods, params you will use etc) and backend implementation - especially that Java Asset api gives you all you need. The other thing is that if you will use option 2, there is a chance something will change in the future in terms of ManageReferencesServlet contract and your solution will stop working.

Avatar

Level 2

Thank you so much - I really appreciate the level of thought and detail that you've put into this, that's super helpful! I'm going to take a look into Option 2 as that looks like a great way of getting to this. 

 

Thank you again!

Avatar

Level 1

Hi 

Is there any possible to download Related Assets?