I'm using the FlickrNet c# library that so far is proving a massive hit.
However, I've got one problem. I can get all photos for a user id but I can't get the set name that a specific photo belongs to without doing another api call. This separate call is giving me massive performance issues. The homepage takes 30 seconds to load 40 images. This will only increase.
I need to get the set name for each photo as I'm using isotope to display the images.
I'm simply grabbing the images from the api and binding them to a repeater.
Here's my code.
C#
Flickr f = FlickrManager.GetAuthInstance();
protected void Page_Load(object sender, EventArgs e)
{
string userID = f.PeopleFindByEmail("me@yahoo.com").UserId;
PhotoSearchOptions options = new PhotoSearchOptions
{
UserId = userID,
Extras = PhotoSearchExtras.AllUrls | PhotoSearchExtras.Description | PhotoSearchExtras.Tags,
SortOrder = PhotoSearchSortOrder.Relevance,
};
var photos = f.PhotosSearch(options);
rptPhotos.DataSource = photos;
rptPhotos.DataBind();
}
protected string GetSetNameForImageID(string imageID)
{
var sets = f.PhotosGetAllContexts(imageID).Sets;
return sets[0].Title.ToLower().Replace(" ", "-");
}
HTML
<asp:Repeater runat="server" ID="rptPhotos">
<ItemTemplate>
<section class="<%# GetSetNameForImageID( Convert.ToString( Eval("PhotoID") ) ) %> item">
<%--<a href="@Url.Action("Image", "Home", new {id = item.PhotoId})">--%>
<a href="/View.aspx?pid=<%# DataBinder.Eval(Container.DataItem, "PhotoID") %>">
<div>
<div class="item_hover">
<header>
<span>D</span>
<%--<p title="@item.Description" class="tiptip">_</p> --%>
<p title="<%# DataBinder.Eval(Container.DataItem, "Description") %>" class="tiptip">_</p>
<hgroup>
<%--<h2>@item.Title</h2>
<h3>@item.Tags[0]</h3>--%>
<h2><%# DataBinder.Eval(Container.DataItem, "Title") %></h2>
<h3><%# DataBinder.Eval(Container.DataItem, "Tags[0]") %></h3>
</hgroup>
</header>
</div>
<%--<img src="@item.Small320Url" alt="Video sit amet consectetur" />--%>
<img src="<%# DataBinder.Eval(Container.DataItem, "Small320Url") %>" alt="Video sit amet consectetur" />
</div>
</a>
</section>
</ItemTemplate>
</asp:Repeater>
Is there a quicker way of getting the set name for each image without the GetSetNameForImageID and subsequent api call?
One thing I noticed about the PhotosGetAllContexts
is that the Sets
property you are using is a collection of ContextSet
objects, which in turn store a PhotoSetId
and a Title
.
What about combining the PhotosetsGetList and PhotosetsGetPhotos methods? I think you could use these two to avoid the overhead you are currently experiencing with the PhotosGetAllContexts
method.
Disclaimer: not tested code.
var photoSets = f.PhotosetsGetList(userId);
Dictionary<string, List<Photo>> photoSetPhotoMap = new Dictionary<string, List<Photo>>();
foreach (var photoSet in photoSets)
{
var photoSetPhotos = f.PhotosetsGetPhotos(photoSet.PhotosetId,
PhotoSearchExtras.AllUrls | PhotoSearchExtras.Description | PhotoSearchExtras.Tags);
photoSetPhotoMap.Add(photoSet.PhotosetId, photoSetPhotos.ToList());
}
var photos =
from kvp in photoSetPhotoMap
from photo in kvp.Value
select new
{
SetTitle = kvp.Key, PhotoId = photo.PhotoId, Description = photo.Description,
PhotoTitle = photo.Title, Tags = photo.Tags[0], Small320Url = photo.Small320Url
};
rptPhotos.DataSource = photos;
rptPhotos.DataBind();
I think the main difficulty you will have with this approach is implementing paging effectively - depending on the size of a photoset (you can determine this by the NumberOfPhotos
property) you will likely run across scenarios where a page cuts off halfway through a photoset.
To solve this I would suggest using the NumberOfPhotos
property to calculate the total number of photos and then using your page size multiplied by the page number to figure out how many and which PhotoSets
you need to get to fulfill the request.