6

Is there a specific method to get attachment/image info in JS? I have an attachment id and before I use any

add_action("wp_ajax_get_image_info", "get_image_info");

I would like to see if there is a native method for doing this trough JS only.

2 Answers 2

17

Long story short, you can get info about an attachment by using wp.media.attachment() function. This will give you complete data as long as this attachment is already loaded by another script or an wp.media() popup.

If the data is not yet loaded, you can load it using .fetch() method on attachment, which works because it is a Backbone.Collection. It is a Collection because an attachment may have multiple selected files in it.

// preload your attachment
wp.media.attachment(ID).fetch().then(function (data) {
  // preloading finished
  // after this you can use your attachment normally
  wp.media.attachment(ID).get('url');
});

Easy way of doing preloading:

function preloadAttachment(ID, callback) {
  // if it doesn't have URL we probably have to preload it
  if (wp.media.attachment(ID).get('url')) {
    wp.media.attachment(ID).fetch().then(function () {
      callback(wp.media.attachment(ID);
    });

    return;
  }

  callback(wp.media.attachment(ID));
}

// USAGE:
preloadAttachment(10, function (attachment) {
  console.log(attachment.get('url'));
  console.log(wp.media.attachment(10).get('url')); // this also works
})

And that's how you will want to go about preloading more than one attachment, in a single AJAX request.

// An array of attachments you may want to preload
var attachment_ids = [10, 11, 12, 13];
wp.media.query({ post__in: attachment_ids })
  .more()
  .then(function () {
    // You attachments here normally
    // You can safely use any of them here
    wp.media.attachment(10).get('url');
  })

Note the fact that the AJAX request performed by wp.media.query() is paginated. If you need a robust solution for loading lots and lots of attachments you should go about parsing each page with hasMore() and more() methods.

Disclaimer:

I have used this method before finding out about wp.media.query but it has the penalty of making one request per preloaded attachment. But it also has a nice feature -- it doesn't make any request if all of the attachments that need to be preloaded are already in the fetched state.

function preloadMultipleAttachments(attachment_ids) {
    // I'd rather use Promise.all() here but they do not work with
    // jQuery deferreds :/
    if (jQuery.when.all===undefined) {
        jQuery.when.all = function(deferreds) {
            var deferred = new jQuery.Deferred();
            $.when.apply(jQuery, deferreds).then(
                function() {
                    deferred.resolve(Array.prototype.slice.call(arguments));
                },
                function() {
                    deferred.fail(Array.prototype.slice.call(arguments));
                });

            return deferred;
        }
    }

    return jQuery.when.all(
        attachment_ids.filter(function (attachment_id) {
            return ! wp.media.attachment(attachment_id).get('url');
        }).map(function (id) {
            return wp.media.attachment(id).fetch();
        })
    );
},
5
  • Can you explain a little bit as how it helps in addition to posting the code
    – bravokeyl
    Commented Aug 30, 2016 at 8:02
  • 1
    @bravokeyl Done. Commented Aug 30, 2016 at 8:15
  • Updated to include a way to preload more than one attachment in a single AJAX request. Will save you some payload passing down the way. Commented Aug 21, 2017 at 6:59
  • @AndreiGlingeanu, Do you know is there way to get attachment by url instead of id. like this wp.media.attachment(url) Commented Jan 23, 2018 at 5:41
  • @TigranBabajanyan just write an AJAX action by yourself & return the correct attachment using wp_prepare_attachment_for_js() Commented Jan 30, 2018 at 22:42
0

Jetpack has a JSON API that allows you to query pretty much everything in a given install. http://jetpack.me/support/json-api/

1
  • we are not jetpack users , Unyson rather than anything else.
    – Benn
    Commented Sep 7, 2016 at 7:31

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.