<?xml version="1.0" encoding="UTF-8"?>
<?xml-stylesheet type="text/xsl" media="screen" href="/~d/styles/rss2full.xsl"?><?xml-stylesheet type="text/css" media="screen" href="http://feeds.feedburner.com/~d/styles/itemcontent.css"?><rss xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:feedburner="http://rssnamespace.org/feedburner/ext/1.0" version="2.0" xml:base="http://developer.bazaarvoice.com">
<channel>
 <title>Bazaarvoice's Developer Program blogs</title>
 <link>http://developer.bazaarvoice.com/blog</link>
 <description />
 <language>en</language>
<atom10:link xmlns:atom10="http://www.w3.org/2005/Atom" rel="self" type="application/rss+xml" href="http://feeds.feedburner.com/BazaarvoiceDeveloper" /><feedburner:info uri="bazaarvoicedeveloper" /><atom10:link xmlns:atom10="http://www.w3.org/2005/Atom" rel="hub" href="http://pubsubhubbub.appspot.com/" /><feedburner:browserFriendly></feedburner:browserFriendly><item>
 <title>Bazaarvoice developer portal moving to Mashery effective 3/1/13</title>
 <link>http://developer.bazaarvoice.com/bazaarvoice-developer-portal-moving-mashery-effective-3113</link>
 <description>&lt;p&gt;We are pleased to announce that on March 1, 2013, we are moving our developer portal hosting to Mashery.&lt;/p&gt;&lt;p&gt;What does this mean to you, our developer community:&lt;/p&gt;&lt;ul&gt;&lt;li&gt;None of your existing API keys will be affected by this transition. They will continue to work without interruption.&lt;/li&gt;&lt;li&gt;You no longer need to log in to see API documentation or any public content on the site.&lt;/li&gt;&lt;li&gt;To request a new API key, you will need to register with a Mashery ID (or use your existing one if you access other Mashery-powered APIs). Your current Bazaarvoice developer portal ID will no longer work after March 1st.&lt;/li&gt;&lt;li&gt;There is no change to the developer portal URL (&lt;a href="http://developer.bazaarvoice.com" target="_blank"&gt;http://developer.bazaarvoice.com&lt;/a&gt;).&lt;/li&gt;&lt;/ul&gt;&lt;p&gt;We know that the increased security and faster key generation will enhance your development experience. As always, thank you for developing on the Bazaarvoice platform. We look forward to seeing your applications.&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;</description>
 <comments>http://developer.bazaarvoice.com/bazaarvoice-developer-portal-moving-mashery-effective-3113#comments</comments>
 <pubDate>Fri, 08 Feb 2013 20:21:00 +0000</pubDate>
 <dc:creator>craig.gilchrist</dc:creator>
 <guid isPermaLink="false">875 at http://developer.bazaarvoice.com</guid>
</item>
<item>
 <title>Announcing the iOS SDK version 2</title>
 <link>http://developer.bazaarvoice.com/announcing-ios-sdk-version-2</link>
 <description>&lt;p&gt;Seven months ago we launched the first Bazaarvoice mobile SDK for iOS, which now generates millions of requests per week. Since the launch, we’ve worked to guide adoption, add features, and improve usability for our clients. We’re incredibly excited about the direction the SDKs have taken, but now we're taking it to the next level.&lt;/p&gt;&lt;p&gt;Today, we’re pleased to announce version 2 of the Bazaarvoice iOS SDK. One of our primary goals is to make it as simple as possible to go from downloading a Bazaarvoice SDK to displaying and submitting content in your application. The new iOS SDK was rewritten from scratch to take into account everything we have learned to date.&lt;/p&gt;&lt;p&gt;It is simpler, removes several common configuration stumbling blocks, eliminates external dependencies, provides more guidance to developers that are new to the Bazaarvoice platform, and is generally easier to use. For clients that are new to the Bazaarvoice iOS SDK, v2 should make it easier to get up and running. For clients that are already using the SDK, we did our best to minimize the overhead in updating to the new version. Among the improvements in v2 are the following:&lt;/p&gt;&lt;p&gt;&lt;strong&gt;Fewer Steps to Get Started&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;The new SDK is written in such a way that it no longer requires tinkering with build settings or messing with arc compatibility libraries in order to get up and running. Integration should be as simple as copying the bv-ios-static-libary folder into your project. From there, we provide documentation and a number of examples to illustrate how to make calls via the SDK.&lt;/p&gt;&lt;p&gt;Behind the scenes, v2 utilizes the native JSON parsing library introduced with iOS 5. Consequently, the Bazzaarvoice SDK no longer officially supports iOS 4, which we estimate makes up less than 4% of the iPhone market. This decision comes with the advantage that we are no longer reliant on the SBJSON library. Previously, this library caused issues with collisions or the library being included twice.&lt;/p&gt;&lt;p&gt;&lt;strong&gt;Fewer Classes&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;V1 of the iOS SDK relied greatly on subclassing in order organize the various types of API calls. While good intentioned, some clients found the structure confusing, particularly when getting up to speed. With v2 of the SDK, there are just 3 types of requests: BVGet, BVPost, and BVMediaPost, which correspond to fetching BV content, submitting content, and submitting media respectively. In v1, the client would do the following to fetch reviews:&lt;/p&gt;&lt;code&gt;BVDisplayReview *showDisplayRequest = [[BVDisplayReview alloc] init]; showDisplayRequest.delegate = self; [showDisplayRequest startAsynchRequest];&lt;/code&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;In v2, the request looks like this:&lt;/p&gt;&lt;code&gt;BVGet *reviewsRequest = [[BVGet alloc] initWithType:BVGetTypeReviews]; [reviewsRequest sendRequestWithDelegate:self];&lt;/code&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;Though syntactically similar, we hope that the new approach will help developers avoid getting bogged down by a confusing class structure.&lt;/p&gt;&lt;p&gt;&lt;strong&gt;Better Guidance for Developers&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Some requests in v1 of the iOS SDK required the developer to understand the mechanics of our underlying API. For instance, to add a sort parameter on included products, the code would look like this:&lt;/p&gt;&lt;code&gt;[showDisplayRequest.parameters.sortType addKey:@"products" andValue:@"id:asc"];&lt;/code&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;The developer would need to understand the colon and "asc" syntax of the Bazaarvoice API. With v2, we did everything we could to abstract these details. The same filter now looks like this:&lt;/p&gt;&lt;code&gt;[showDisplayRequest addSortOnIncludedType:BVIncludeTypeProducts attribute:@"Id" ascending:YES];&lt;/code&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;We provide enumerated types for parameters wherever possible, which allows developers to quickly find valid values. It also helps avoid typos and makes debugging easier.&lt;/p&gt;&lt;p&gt;All in all, we believe v2 of the Bazaarvoice iOS SDK represents a large improvement over v1. We're looking forward to seeing what clients build on top of our platform. Click &lt;a href="http://developer.bazaarvoice.com/bazaarvoice-ios-sdk" target="_blank"&gt;here&lt;/a&gt; if you are interested in more information about the Bazaarvoice iOS SDK and a link to the GitHub repository.&lt;/p&gt;</description>
 <comments>http://developer.bazaarvoice.com/announcing-ios-sdk-version-2#comments</comments>
 <pubDate>Tue, 22 Jan 2013 19:09:53 +0000</pubDate>
 <dc:creator>alex.medearis</dc:creator>
 <guid isPermaLink="false">874 at http://developer.bazaarvoice.com</guid>
</item>
<item>
 <title>Platform API release notes, version 5.4</title>
 <link>http://developer.bazaarvoice.com/platform-api-release-notes-version-54</link>
 <description>&lt;p&gt;We are pleased to announce that the following functionality has been developed for version 5.4:&lt;/p&gt;&lt;ul&gt;&lt;li&gt;Submission forms pre-filled for non-anonymous users&lt;/li&gt;&lt;li&gt;Full text search on all UGC and on includes&lt;/li&gt;&lt;li&gt;Product family queries&lt;/li&gt;&lt;li&gt;Photo upload accepts URLs&lt;/li&gt;&lt;li&gt;Brightcove Smart Player Javascript integration&lt;/li&gt;&lt;li&gt;Story rating field exposed&amp;nbsp;in the response&lt;/li&gt;&lt;li&gt;Special product attributes exposed in the response&lt;/li&gt;&lt;li&gt;New filtering capabilities&lt;/li&gt;&lt;/ul&gt;&lt;p&gt;More detailed information on each of these items is listed below. For complete documentation, refer to the &lt;a href="http://developer.bazaarvoice.com/api"&gt;Platform API documentation, version 5.4&lt;/a&gt;.&lt;/p&gt;&lt;p&gt;&lt;strong&gt;Submission forms pre-filled for non-anonymous users&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;When submitting content, the values of all known submission fields are now returned in the submission response fields. This only affects submissions where the user is not anonymous and the user/userid parameter is provided with the GET request.&lt;/p&gt;&lt;p&gt;&lt;strong&gt;Full text search on all UGC and on includes&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;The following content types were added to the existing search capabilities:&lt;/p&gt;&lt;ul&gt;&lt;li&gt;reviews&lt;/li&gt;&lt;li&gt;answers&lt;/li&gt;&lt;li&gt;comments (story and review)&lt;/li&gt;&lt;li&gt;stories&lt;/li&gt;&lt;/ul&gt;&lt;p&gt;All content is now searchable. For a list of all the fields that are searched for any given content type, see the &lt;a href="http://developer.bazaarvoice.com/api/basics"&gt;API Basics&lt;/a&gt; page.&lt;/p&gt;&lt;p&gt;&lt;strong&gt;Product family queries&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;When filtering by product id, all content from that product's product family is also returned by default. There is a new excludeFamily&amp;nbsp;parameter that you can set to not return product family content. For examples and full documentation, see the &lt;a href="http://developer.bazaarvoice.com/api/5/4/product-display"&gt;Product Display&lt;/a&gt; method page.&lt;/p&gt;&lt;p&gt;&lt;strong&gt;Photo upload accepts URLs&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;The uploadphoto endpoint now accepts HTTP URLs of images in addition to locally stored photos from the client side. For examples and full documentation, see the &lt;a href="http://developer.bazaarvoice.com/api/5/4/photo-submission"&gt;Photo Submission&lt;/a&gt; method page.&lt;/p&gt;&lt;p&gt;&lt;strong&gt;Brightcove Smart Player Javascript integration&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Brightcove videos can be loaded in a variety of ways. The information necessary to load these videos in the browser is now returned in the Videos block of the response elements. See the &lt;a href="http://developer.bazaarvoice.com/api/basics"&gt;API Basics&lt;/a&gt; page for details on the new response items that were added to support Brightcove videos.&lt;/p&gt;&lt;p&gt;&lt;strong&gt;Story rating field exposed in the response&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;The story display response has a new block called "StoryRating" that contains two fields:&lt;/p&gt;&lt;ul&gt;&lt;li&gt;Average score - average of the rating feedback score displayed for each story ID&lt;/li&gt;&lt;li&gt;Range - range of the average score&lt;/li&gt;&lt;/ul&gt;&lt;p&gt;&lt;strong&gt;Special product attributes exposed in the response&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;The product display response has new fields for each of the following five product attributes:&lt;/p&gt;&lt;ul&gt;&lt;li&gt;EANs&lt;/li&gt;&lt;li&gt;UPCs&lt;/li&gt;&lt;li&gt;ISBNs&lt;/li&gt;&lt;li&gt;ModelNumbers&lt;/li&gt;&lt;li&gt;ManufacturerPartNumbers&lt;/li&gt;&lt;/ul&gt;&lt;p&gt;&lt;strong&gt;New filtering capabilities&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;The following new filters are available:&lt;/p&gt;&lt;ul&gt;&lt;li&gt;Affiliation filter on reviews&lt;/li&gt;&lt;li&gt;Brand answer filters on questions and answers&lt;/li&gt;&lt;li&gt;Brand external ID filter for reviews, stories, questions, and products&lt;/li&gt;&lt;li&gt;Content locale filter inline ratings (statistics.json)&lt;/li&gt;&lt;/ul&gt;&lt;p&gt;For more information, see the appropriate method's documentation.&lt;/p&gt;</description>
 <comments>http://developer.bazaarvoice.com/platform-api-release-notes-version-54#comments</comments>
 <pubDate>Mon, 14 Jan 2013 20:57:34 +0000</pubDate>
 <dc:creator>craig.gilchrist</dc:creator>
 <guid isPermaLink="false">873 at http://developer.bazaarvoice.com</guid>
</item>
<item>
 <title>Interns and graduates - Keys to job search success</title>
 <link>http://developer.bazaarvoice.com/interns-and-graduates-keys-job-search-success</link>
 <description>&lt;p&gt;Bazaarvoice R&amp;amp;D had a great year of intensive university recruiting with 12 interns joining our teams last summer and working side-by-side with the developers on our products. We have further expanded the program this year to accommodate two co-op positions for students from the University of Waterloo. The influx of fresh ideas and additional energy from these students has been great for the whole organization!&lt;/p&gt;&lt;p&gt;For many students, looking for an internship or graduate employment may be their first time experiencing the interview process and creating resumes, and I’d like to offer some advice for those of you in this position. These guidelines are intended to help you think about how to present your capabilities in the best possible light, and in my experience, apply to tech interviews at most companies.&lt;/p&gt;&lt;p&gt;&lt;strong&gt;What we’re looking for&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;For new graduate and internship positions, it often surprises students that tech companies are, in general, less focused on them knowing &lt;em&gt;specific&lt;/em&gt; technologies or languages. They are more focused on determining whether you have:&lt;/p&gt;&lt;ul&gt;&lt;li&gt;solid CS fundamentals (data structures, algorithms, etc.)&lt;/li&gt;&lt;li&gt;passion for problem-solving and software development&lt;/li&gt;&lt;li&gt;an ability to learn quickly&lt;/li&gt;&lt;/ul&gt;&lt;p&gt;It is generally expected that you have confidence in at least one programming language, with a solid grip on its syntax and common usage. It is also helpful for you to demonstrate an understanding of object-oriented concepts and design but, again, this can be independent of any specific language.&lt;/p&gt;&lt;p&gt;&lt;strong&gt;Resumes&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Your resume is a critical chance to sell the reader on your abilities. While it can be uncomfortable to ‘toot your own horn’ it is important that you use your resume to try to differentiate yourself from the sea of other candidates. A dry list of courses or projects is unlikely to do this, so it really is worth investing a lot of thought in expressing on the resume what was particularly interesting, important, or impressive about what you did.&lt;/p&gt;&lt;ul&gt;&lt;li&gt;Definitely include details of any side projects that you’ve worked on, and don’t be afraid to demo them if you get the chance (mobile apps, websites, etc.).&amp;nbsp; Some students are embarrassed because they are just hobby-projects and not commercial-grade applications – this doesn’t matter!&lt;/li&gt;&lt;li&gt;Include details of anything that you are proud of, or that you did differently or better than others.&lt;/li&gt;&lt;li&gt;If you mention group/team projects be sure to make it clear what YOU did, rather than just talking about what the team did.&amp;nbsp; Which bits were you responsible for?&lt;/li&gt;&lt;li&gt;Don’t emphasize anything on your resume that you are not prepared for a detailed technical discussion on.&amp;nbsp; For example, if you make a point of calling out a multi-threaded, C-programming project, you should be confident talking about threading, and being able to do impromptu coding on a whiteboard using threads.&amp;nbsp; We’re not expecting perfection, but are looking for a solid grasp on fundamentals and syntax.&lt;/li&gt;&lt;li&gt;Leave out cryptic course numbers – it's unlikely that the person reading your resume knows what ‘CS252’ means, but they will understand ‘Data Structures’.&lt;/li&gt;&lt;li&gt;Make sure you have good contact info – we do occasionally see resumes with no contact info, or where the contact info had typos.&lt;/li&gt;&lt;/ul&gt;&lt;p&gt;&lt;strong&gt;Interview technique&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;While an interview can be nerve-wracking, interviewers love to see people do well and are there to be supportive.&lt;/p&gt;&lt;ul&gt;&lt;li&gt;Coding on a whiteboard is difficult (but the interviewer knows that) - a large chunk of most technical interviews is problem-solving or coding on a whiteboard.&amp;nbsp; Interviewers are very understanding that coding on a whiteboard is not easy, so don’t worry about building neat code from the outset.&lt;/li&gt;&lt;li&gt;&lt;span style="font-family: 'Courier New'; mso-fareast-font-family: 'Courier New';"&gt;&lt;span style="mso-list: Ignore;"&gt;&lt;span style="font: 7.0pt 'Times New Roman';"&gt;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;Don’t rush to put code on the board – think about the problem, ask clarifying questions, and maybe jot a few examples down to help you get oriented.&lt;/li&gt;&lt;li&gt;Talk through what you are thinking – a large part of a technical interview is understanding how the person is thinking, even if you’re running through approaches to eliminate.&amp;nbsp; Getting to an answer is only part of what the interviewer is looking for, and they want to see what your thought process is.&lt;/li&gt;&lt;li&gt;&lt;span style="font-family: 'Courier New'; mso-fareast-font-family: 'Courier New';"&gt;&lt;span style="mso-list: Ignore;"&gt;&lt;span style="font: 7.0pt 'Times New Roman';"&gt;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;Ask for help (but not too quickly!) – it’s OK that you don’t know everything, and sometimes get stuck.&amp;nbsp; If you get stuck, explain what you are stuck on and the interviewer will be prepared to guide you.&lt;/li&gt;&lt;li&gt;&lt;span style="font-family: 'Courier New'; mso-fareast-font-family: 'Courier New';"&gt;&lt;span style="mso-list: Ignore;"&gt;&lt;span style="font: 7.0pt 'Times New Roman';"&gt;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;Use what you are familiar with – you will likely be asked to code in the language you are most comfortable with.&amp;nbsp; Do it!&amp;nbsp; Some students think the interviewer is ‘expecting’ them to use a certain language because it’s one we used at the hiring company, but that’s not the case.&lt;/li&gt;&lt;li&gt;Perfection is not required - while no interviewer is ever going to complain if you do everything perfectly, forgetting a little piece of syntax, or a particular library function name is not fatal. It's more important that you write code that is easy to follow and logically reasoned through. Also remember it’s OK to ask for help if you are truly stuck. At the same time, if your syntax is &lt;em&gt;way&lt;/em&gt; off, and you’re asking for help on every line of code then you’re probably not demonstrating the level of mastery that is expected.&lt;/li&gt;&lt;li&gt;Consider bringing a laptop if you have code to show – while the interviewer may choose to focus on whiteboard problem-solving, it is a nice option to be able to offer showing them code you’ve written.&amp;nbsp; Be sure to bring your best examples; ones that show off your strengths or originality.&amp;nbsp; Make sure it is code you know inside-out as you will likely be questioned in detail about why you did things a certain way.&lt;/li&gt;&lt;li&gt;Come prepared with questions for the interviewer – the interview is an opportunity for you to get to know the company in more detail, and see if it’s somewhere you’d like to work.&amp;nbsp;&amp;nbsp; Think about the things that are important to you, and that you’d use to decide between different employment/internship offers.&amp;nbsp;&lt;/li&gt;&lt;/ul&gt;&lt;p&gt;Over my career I’ve found that these rules of thumb apply well in all technical interview/application processes, and hopefully they are useful guidance for students out there. Any other advice from readers?&lt;/p&gt;</description>
 <comments>http://developer.bazaarvoice.com/interns-and-graduates-keys-job-search-success#comments</comments>
 <pubDate>Fri, 28 Sep 2012 16:17:27 +0000</pubDate>
 <dc:creator>chris.norris</dc:creator>
 <guid isPermaLink="false">769 at http://developer.bazaarvoice.com</guid>
</item>
<item>
 <title>5 Ways to Improve Your Mobile Submission Form</title>
 <link>http://developer.bazaarvoice.com/5-ways-improve-your-mobile-submission-form</link>
 <description>&lt;p&gt;Here at Bazaarvoice, we’re constantly focused on improving the user experience for our products. &amp;nbsp;From the initial email invitation, to the submission form, to the way in which reviews are presented, we want to make sure that our interfaces are as flexible and intuitive as possible. &amp;nbsp;&lt;/p&gt;&lt;p&gt;Part of my job on the mobile team at Bazaarvoice is to make sure that our products reflect best practices when displayed on mobile devices. &amp;nbsp;In reality, that means running hands-on user tests, A/B testing different designs, and gathering detailed information about the way in which users interact with our products. &amp;nbsp;&lt;/p&gt;&lt;p&gt;Recently, we ran a test with &lt;a href="http://www.buckle.com/"&gt;Buckle&lt;/a&gt;, one of our partner clients, to experiment with various mobile-friendly submission forms. &amp;nbsp;What follows are some of the takeaways from those experiments.&lt;/p&gt;&lt;p&gt;&lt;strong&gt;1. &amp;nbsp;Handle Landscape Mode Gracefully&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;It is important that users are able to navigate forms easily while in landscape mode. &amp;nbsp;It becomes particularly important to support landscape for form fields that solicit text input. &amp;nbsp;We found that mobile users will, on average, input about 20% fewer words in their reviews than desktop users, so the last thing we want to do is to make it even more difficult to enter text. &amp;nbsp;Many users prefer to type in landscape mode as it provides for a larger keyboard.&lt;/p&gt;&lt;p style="text-align: center;"&gt;&lt;img src="http://mobile.bazaarvoice.com/alexblog/landscape.png" alt="Landscape Mode" width="554" height="286" /&gt;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;2. Make Interactions Easy&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Generally, a desktop user with a mouse can interact much more precisely than a mobile user with a clumsy finger. &amp;nbsp;Therefore, it is important to make sure that elements are large enough to be either clicked or tapped. &amp;nbsp;Apple recommends that tappable elements be &lt;a href="http://developer.apple.com/library/ios/#documentation/userexperience/conceptual/mobilehig/UEBestPractices/UEBestPractices.html"&gt;at least 44x44 pixels&lt;/a&gt;.&amp;nbsp; In our experimental form, we &lt;a href="http://www.screwdefaultbuttons.com/"&gt;intentionally oversized&lt;/a&gt;&amp;nbsp;our radio buttons, selection drop-downs and sliders to make the form easier to interact with and to prevent form errors.&lt;/p&gt;&lt;p&gt;Additionally, mobile devices provide a number of different keyboard layouts for different types of inputs. &amp;nbsp;For instance, an &lt;a href="http://www.w3schools.com/html5/html5_form_input_types.asp"&gt;input type&lt;/a&gt; of “email” might surface the @ symbol to make it more readily accessible. &amp;nbsp;In order to take advantage of the various keyboard layouts, be sure to properly specify the input type on your form elements.&lt;/p&gt;&lt;p style="text-align: center;"&gt;&lt;img src="http://mobile.bazaarvoice.com/alexblog/emailinput.png" alt="Email Input Keyboard iOS" width="553" height="293" /&gt;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;3. Snappy Over Flashy&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;The first version of our experimental form involved a heavy amount of JavaScript to do things like alpha animations and transforms. &amp;nbsp;While our animations generally ran smoothly on a desktop, they became sluggish on the iPhone and lower end Android devices. &amp;nbsp;&lt;/p&gt;&lt;p&gt;When designing for mobile, be sure to prioritize function over flashiness. &amp;nbsp;Slick animations can greatly improve the usability and “wow” factor of a site, but they should be used sparingly. &amp;nbsp;If necessary, use &lt;a href="http://www.html5rocks.com/en/tutorials/speed/html5/"&gt;hardware-accelerated transforms&lt;/a&gt; to minimize sluggishness.&lt;/p&gt;&lt;p&gt;&lt;strong&gt;4. Choose The Most Efficient Form Path&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Overall, our goal is to allow the user to complete our form in the quickest, simplest manner possible. &amp;nbsp;In our testing, we found that a surprising number of users preferred to navigate and exit form elements via the “done” button rather than using the next/previous buttons. &amp;nbsp;This has several interesting consequences. &amp;nbsp;&lt;/p&gt;&lt;p&gt;First, short forms are better than tall forms. &amp;nbsp;While some users “tab” through fields, most users scroll. &amp;nbsp; By minimizing the vertical spacing between elements, users do not need to scroll as far to get to the next field. &amp;nbsp;&lt;/p&gt;&lt;p&gt;Second, for most users, the interaction with a select element will involve 3 clicks: open, select, and done. &amp;nbsp;Therefore, if a user is selecting between just a few options, it is better to use oversized radio buttons than select elements.&lt;/p&gt;&lt;p&gt;&lt;strong&gt;5. Provide Instant Feedback&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;If a user submits an invalid form value such as a malformed email address, provide a clear error message that instructs the user how to fix the error. &amp;nbsp;If possible, provide an error near the offending field. &amp;nbsp;Additionally, once the form field becomes valid, notify the user immediately rather than requiring the user to submit the form again.&amp;nbsp;&lt;/p&gt;&lt;p style="text-align: center;"&gt;&lt;img src="http://mobile.bazaarvoice.com/alexblog/error.png" alt="Descriptive Form Error" width="296" height="558" /&gt;&lt;/p&gt;&lt;p&gt;For our experimental form, we used the &lt;a href="http://docs.jquery.com/Plugins/Validation"&gt;JQuery validation library&lt;/a&gt;, which makes basic form validation dead simple. &amp;nbsp;Since it is all client side, it makes validation snappy as well.&lt;/p&gt;&lt;p&gt;Our tests are ongoing, so be on the lookout for more updates soon. &amp;nbsp;Until then, hopefully these insights will be valuable to others as the Internet becomes more mobile-friendly.&lt;/p&gt;&lt;div&gt;&amp;nbsp;&lt;/div&gt;</description>
 <comments>http://developer.bazaarvoice.com/5-ways-improve-your-mobile-submission-form#comments</comments>
 <pubDate>Thu, 13 Sep 2012 19:54:46 +0000</pubDate>
 <dc:creator>alex.medearis</dc:creator>
 <guid isPermaLink="false">767 at http://developer.bazaarvoice.com</guid>
</item>
<item>
 <title>SELECT developers FROM Bazaarvoice UNION SELECT flags FROM Stripe_CTF;</title>
 <link>http://developer.bazaarvoice.com/select-developers-bazaarvoice-union-select-flags-stripectf</link>
 <description>&lt;p&gt;Stripe (&lt;a href="https://stripe.com/"&gt;https://stripe.com/&lt;/a&gt;) held their second capture the flag event, this time the CTF was dedicated to web-based vulnerabilities and exploits. &amp;nbsp;As a new Security Engineer here at BV the timing of this was perfect. &amp;nbsp;It allowed me to use it as a vehicle for awareness and to ramp up curiosity, interest and even excitement for web application security (webappsec).&lt;/p&gt;&lt;p&gt;Let’s start with some definitions to get us all on the same page.&lt;/p&gt;&lt;p&gt;Capture the flag is a traditional outdoor game where two teams each have a flag and the objective is to capture the other team's flag, located at the team's base. &amp;nbsp;In computer security the flag is a piece of data stored somewhere on a vulnerable computer and the goal is to use tools and know how to “hack” the machine to find the flag.&lt;/p&gt;&lt;p&gt;Webappsec is the acronym for Web Application Security a branch of Information Security that deals specifically with security of websites and web applications. &amp;nbsp;In my opinion there is more to it than just that. &amp;nbsp;As we see from the OWASP Top 10 (&lt;a href="https://www.owasp.org/index.php/Category:OWASP_Top_Ten_Project"&gt;https://www.owasp.org/index.php/Category:OWASP_Top_Ten_Project&lt;/a&gt;) and the emerging DevOps movement, web developers are doing more than just coding. &amp;nbsp;They are now configuring full stacks to support their applications. &amp;nbsp;So, webappsec needs to encompass more than just the application. &amp;nbsp;It has to deal with developer and management education, configuration management, networking security, OS hardening, just to name a few areas, and of course not to forget the code.&lt;/p&gt;&lt;p&gt;Now that we know what CTF and webappsec are lets move on to the details of the event.&lt;/p&gt;&lt;p&gt;The CTF started on Wednesday, August 22nd, 2PM CDT today at 2PM CDT and ran for a week until Wednesday, August 29th, 2012 2PM CDT. &amp;nbsp;One week == Seven Days == 168 hours and, for me at least, this was not enough. &amp;nbsp;This capture the flag included 9 levels (0-8) to conquer before arriving at the actual flag. &amp;nbsp;Each level was progressively more difficult and when completed provided you with the password for the next level.&lt;/p&gt;&lt;p&gt;The CTF was very challenging, yet no security specific training/knowledge was needed in order to participate. &amp;nbsp;In my opinion the minimum requirements to participate and find it fun and enjoyable was some knowledge of web application programming and a willingness to learn and research possible vulnerabilities and potential exploits.&lt;/p&gt;&lt;p&gt;In total about 15 or so Bazaarvoice cohorts tried their hand at the CTF. &amp;nbsp;Four actually captured the flag! &amp;nbsp;When did they have the time? &amp;nbsp;Well, we used our 20% time while at work and personal time when away from work. &amp;nbsp;Late nights, lunch hours, weekend, etc.…believe me once you get started you are hooked. &amp;nbsp;You end up thinking about it all day. &amp;nbsp;You think about the level you are on, how to solve it and whether the previous levels offer up any hints or possible staging areas for potential exploits. &amp;nbsp;If you are anything like me, first a developer at heart then a security professional, this type of activity is a great way to test out your chops and have some fun while learning new things and potentially bringing some of the lessons back to your teams. &amp;nbsp;This is the perfect avenue for awareness – code wins after all!&lt;/p&gt;&lt;p&gt;Here are quotes from some of the BV participants:&lt;/p&gt;&lt;blockquote&gt;&lt;p&gt;I got to 8 last night. I don't think I'll get it in the next 4 hours, but it was a fun challenge.&amp;nbsp;– Cory&lt;/p&gt;&lt;/blockquote&gt;&lt;blockquote&gt;&lt;p&gt;Made it to level 8 last night, but not until after midnight. Don't think I'll be finishing, but it was fun all the same. &amp;nbsp;Level 8 is really interesting, and I look forward to hearing how folks finished it. – RC&lt;/p&gt;&lt;/blockquote&gt;&lt;blockquote&gt;&lt;p&gt;I've been having a lot of fun with it. – Jeremy&lt;/p&gt;&lt;/blockquote&gt;&lt;p&gt;Overall everyone that tried it had a good time with it no matter how far they actually got.&amp;nbsp;&lt;/p&gt;&lt;p&gt;All in all a total of four BVers completed the CTF and captured the final flag!&lt;/p&gt;&lt;p&gt;&lt;strong&gt;&lt;br /&gt;&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;Congratulations&lt;/strong&gt; to the following BVers for&amp;nbsp;successfully capturing the flag:&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;div style="padding-left: 30px;"&gt;Brandon Beck -&amp;nbsp;&lt;a href="https://stripe-ctf.com/progress/Brandon%20Beck"&gt;https://stripe-ctf.com/progress/Brandon%20Beck&lt;/a&gt;&lt;/div&gt;&lt;div style="padding-left: 30px;"&gt;Jeremy Shoemaker -&amp;nbsp;&lt;a href="https://stripe-ctf.com/progress/jshoemaker"&gt;https://stripe-ctf.com/progress/jshoemaker&lt;/a&gt;&lt;/div&gt;&lt;div style="padding-left: 30px;"&gt;Tom Grochowicz -&amp;nbsp;&lt;a href="https://stripe-ctf.com/progress/tgrochowicz"&gt;https://stripe-ctf.com/progress/tgrochowicz&lt;/a&gt;&lt;/div&gt;&lt;div style="padding-left: 30px;"&gt;Nathaniel Bauernfeind -&amp;nbsp;&lt;a href="https://stripe-ctf.com/progress/Nefarious%20Zhen"&gt;https://stripe-ctf.com/progress/Nefarious%20Zhen&lt;/a&gt;&lt;/div&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;p&gt;For their last CTF Stripe made available the solutions and a working VM with each level. &amp;nbsp;I hope they do the same for this one; this will give everyone the opportunity to learn and see what vulnerabilities were found and how they were exploited in order to complete each level and eventually capture the flag.&lt;/p&gt;&lt;p&gt;For now I leave you with a quote which I think embodies web application security, its education and use in the development community:&lt;/p&gt;&lt;blockquote&gt;&lt;p&gt;Secure programming is a mind-set. It may start with a week or two of training, but it will require constant reinforcement. - Karl Keller, President of IS Power&amp;nbsp;&lt;/p&gt;&lt;/blockquote&gt;&lt;p&gt;&amp;nbsp;As with many things here at Bazaarvoice, the education and growth of our developers and their skills often take on a fun and enjoyable approach.&lt;/p&gt;</description>
 <comments>http://developer.bazaarvoice.com/select-developers-bazaarvoice-union-select-flags-stripectf#comments</comments>
 <category domain="http://developer.bazaarvoice.com/category/tags/ctf">ctf</category>
 <category domain="http://developer.bazaarvoice.com/category/tags/security">security</category>
 <category domain="http://developer.bazaarvoice.com/category/tags/stripe">stripe</category>
 <category domain="http://developer.bazaarvoice.com/category/tags/webappsec">webappsec</category>
 <pubDate>Wed, 05 Sep 2012 20:04:01 +0000</pubDate>
 <dc:creator>jay.paz</dc:creator>
 <guid isPermaLink="false">766 at http://developer.bazaarvoice.com</guid>
</item>
<item>
 <title>Platform API release notes, version 5.3</title>
 <link>http://developer.bazaarvoice.com/platform-api-release-notes-version-53</link>
 <description>&lt;p&gt;We are pleased to announce that the following functionality has been developed for version 5.3:&lt;/p&gt;&lt;ul&gt;&lt;li&gt;Hosted authentication - email&lt;/li&gt;&lt;li&gt;Feedback submission for comments&lt;/li&gt;&lt;li&gt;RatingDistribution (Histogram data) and SecondaryRatingsAverages added to review statistics&lt;/li&gt;&lt;li&gt;Time zone changed to UTC&lt;/li&gt;&lt;li&gt;Error codes added to form errors&lt;/li&gt;&lt;li&gt;Syndication attribution on reviews&lt;/li&gt;&lt;/ul&gt;&lt;p&gt;More detailed information on each of these items is listed below. For complete documentation, refer to the &lt;a href="http://developer.bazaarvoice.com/api"&gt;Platform API documentation, version 5.3&lt;/a&gt;.&lt;/p&gt;&lt;p&gt;&lt;strong&gt;Hosted authentication - email&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Hosted email authentication can be used during submission to confirm the identity of a content submitter. When submitting content for the first time, a user receives an email containing a link. When the link is clicked, the user is directed to a landing page that calls back to the API to confirm their identity. This call results in the generation of an encrypted user token that can be used in subsequent submission calls. Depending on your configuration, the submitter's content might not be accepted until the confirmation call is submitted. In order to use this feature, you must have&amp;nbsp;hosted authentication enabled for your submission process. If you need&amp;nbsp;more information, read the &lt;em&gt;"Bazaarvoice hosted authentication reference&amp;nbsp;guide"&amp;nbsp;&lt;/em&gt;and the submission method&amp;nbsp;documentation for details on the required parameters.&lt;/p&gt;&lt;p&gt;&lt;strong&gt;Feedback submission for comments&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Feedback submission for review comments and story comments is now supported in addition to the existing support for feedback submission on reviews, questions, answers, and stories. For complete documentation, see the &lt;a href="http://developer.bazaarvoice.com/api/5/3/feedback-submission"&gt;Feedback Submission&lt;/a&gt; method page.&lt;/p&gt;&lt;p&gt;&lt;strong&gt;RatingDistribution and SecondaryRatingsAverages added to review statistics&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;New RatingDistribution and SecondaryRatingsAverages&amp;nbsp;blocks have been added to the ReviewStatistics block. You can now see the distribution of ratings for each product, which allows you to construct a rating histogram. You can also see&amp;nbsp;the average rating of your secondary rating dimensions for reviews&amp;nbsp;in relation&amp;nbsp;to products and authors.&amp;nbsp;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;Time zone changed to UTC&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;The API now returns all time data using UTC (+00:00) to avoid the confusion of multiple time zones. The date format has not changed.&lt;/p&gt;&lt;p&gt;&lt;strong&gt;Error codes added to form errors&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;The API response has been updated to return error codes in addition to the existing error message for all form errors.&amp;nbsp;A complete listing of the error codes can be found in each submission method.&lt;/p&gt;&lt;p&gt;&lt;strong&gt;Syndication attribution on reviews&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;All reviews have an "isSyndicated" field set to true or false. If the review is syndicated, a SyndicationSource block is displayed with details of where the review is being syndicated from. Syndicated content can only be returned if the API key is configured to show syndicated content.&lt;/p&gt;</description>
 <comments>http://developer.bazaarvoice.com/platform-api-release-notes-version-53#comments</comments>
 <pubDate>Fri, 03 Aug 2012 17:49:18 +0000</pubDate>
 <dc:creator>craig.gilchrist</dc:creator>
 <guid isPermaLink="false">761 at http://developer.bazaarvoice.com</guid>
</item>
<item>
 <title>Platform API Release Notes, Version 5.2</title>
 <link>http://developer.bazaarvoice.com/platform-api-release-notes-version-52</link>
 <description>&lt;p&gt;We are pleased to announce that the following functionality has been developed for version 5.2:&lt;/p&gt;&lt;ul&gt;&lt;li&gt;Helpfulness and inappropriate content feedback submission enabled&lt;/li&gt;&lt;li&gt;ContentLocale no longer filtered implicitly by default&lt;/li&gt;&lt;li&gt;Product and category attributes populated as a map&lt;/li&gt;&lt;li&gt;Hosted video submission and display updated&lt;/li&gt;&lt;li&gt;Inline ratings data exposed for product-based review statistics&lt;/li&gt;&lt;/ul&gt;&lt;p&gt;More detailed information on each of these items is listed below. For complete documentation, refer to the &lt;a href="http://developer.bazaarvoice.com/api"&gt;Platform API Documentation, version 5.2&lt;/a&gt;.&lt;/p&gt;&lt;p&gt;&lt;strong&gt;Helpfulness and inappropriate feedback&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Submission of helpfulness votes and inappropriate feedback&amp;nbsp;can now be done through the API. The response for the user-generated content has also been updated to display the actual inappropriate&amp;nbsp;feedback and total vote and feedback counts. In order for&amp;nbsp;inappropriate&amp;nbsp;feedback to be populated, the API key must be updated.&lt;/p&gt;&lt;p&gt;&lt;strong&gt;Implicit default ContentLocale filter removed&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;There is no longer any implicit ContentLocale filter if none is specified as an argument. If no filter is provided, all content will be returned, regardless of what locale the content is in.&amp;nbsp;There is a default locale defined for every API key. Prior to version 5.2, if the locale parameter was used, it caused an implied ContentLocale filter to be used.&lt;/p&gt;&lt;p&gt;Note that version 5.2 does not change the behavior of explicitly supplied ContentLocale filters. In addition, you can now ask for labels in any locale and specify a different content locale. Therefore, if you request a locale of en_US and a ContentLocale of fr_FR, you get English labels and French content.&lt;/p&gt;&lt;p&gt;&lt;strong&gt;Product and category attributes&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Products and categories now have a new attributes field populated. This field contains a map of attributes provided to Bazaarvoice&amp;nbsp;from a product feed import.&lt;/p&gt;&lt;p&gt;&lt;strong&gt;Hosted video submission and display&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Video elements of all content now contain URLs that can be used to embed the video into an HTML page. Bazaarvoice provides boilerplate HTML tags for use with embedding these videos. For more information, see the &lt;a href="http://developer.bazaarvoice.com/api/basics#video"&gt;API Basics&lt;/a&gt; page.&lt;/p&gt;&lt;p&gt;&lt;strong&gt;Inline ratings data&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;A new method has been created to provide a quick way to access inline ratings data for products. For complete documentation, see the &lt;a href="http://developer.bazaarvoice.com/api/5/2/statistics-display"&gt;Statistics Display&lt;/a&gt; method page.&lt;/p&gt;</description>
 <comments>http://developer.bazaarvoice.com/platform-api-release-notes-version-52#comments</comments>
 <pubDate>Fri, 01 Jun 2012 17:18:09 +0000</pubDate>
 <dc:creator>craig.gilchrist</dc:creator>
 <guid isPermaLink="false">657 at http://developer.bazaarvoice.com</guid>
</item>
<item>
 <title>Scaling on Mysql: Sometimes you've gotta break a few eggs</title>
 <link>http://developer.bazaarvoice.com/scaling-mysql-sometimes-youve-gotta-break-few-eggs</link>
 <description>&lt;p&gt;We recently delivered this presentation titled "How to Scale Big on MySQL? Break a Few Rules!" as part of Database Week here in New York City. The presentation is a lighthearted, and informative take on how Bazaarvoice Engineering has been able to take MySQL to billions of requests per month. The slides and video are available over at &lt;a href="http://www.leadit.us/hands-on-tech/How-to-Scale-Big-on-MySQL-Break-a-Few-Rules"&gt;LeadIt.us&lt;/a&gt;. In the presentation we cover denormalization, query planning, partitioning, MySQL replication, InfoBright's take on a data storage, and thinking beyond the RDBMS. Overall the presentation is a little over an hour, and is littered with great questions. I had a great time delivering the presentation, and I got a lot of very good feedback so I hope it proves useful for you as well.&lt;/p&gt;</description>
 <comments>http://developer.bazaarvoice.com/scaling-mysql-sometimes-youve-gotta-break-few-eggs#comments</comments>
 <pubDate>Thu, 03 May 2012 13:20:03 +0000</pubDate>
 <dc:creator>rcjohnson</dc:creator>
 <guid isPermaLink="false">564 at http://developer.bazaarvoice.com</guid>
</item>
<item>
 <title>MongoDB Arrays and Atomicity</title>
 <link>http://developer.bazaarvoice.com/mongodb-arrays-and-atomicity</link>
 <description>&lt;p&gt;Over time, even technologies that are tried and true begin to show their age. This is especially true for data stores as the shear amount of data explodes and site traffic increases. Because of this, we are continually working with new technologies to determine whether they have a place in our primary stack.&lt;/p&gt;&lt;p&gt;To that end, we began using &lt;a href="http://www.mongodb.org/" target="_blank" title="MongoDB Home"&gt;MongoDB&lt;/a&gt; for one of our new internal systems several months ago. Its quick setup and ease of use make it a great data store for starting a new project that's constantly in flux. Its robustness and scalability make it a worthy contender for our primary data store, if it should prove capable of handling our use cases.&lt;/p&gt;&lt;p&gt;Being traditionally a MySQL shop, our team is used to working with databases in a certain way. When we write code that interacts with the DB, we use transactions and &lt;a href="http://dev.mysql.com/doc/refman/5.5/en/innodb-locking-reads.html" target="_blank" title="SELECT ... FOR UPDATE"&gt;locks&lt;/a&gt; rather liberally. Therefore using MongoDB is a rather significant paradigm shift for our developers.&lt;/p&gt;&lt;p&gt;Though MongoDB doesn't have true &lt;a href="http://en.wikipedia.org/wiki/ACID" target="_blank" title="ACID on Wikipedia"&gt;ACID compliance&lt;/a&gt;, it does support atomic updates to an individual object. And because a "single" object in Mongo can actually be quite complex, this is sufficient for many operations. For example, for the following complex object, setting values, incrementing numbers, adding and removing items from an array, can all be done at the same time atomically:&lt;/p&gt;&lt;p&gt;&lt;img src="http://developer.bazaarvoice.com/files/images/MongoDBArrays-Complex%20Object.png" alt="Complex Object" width="404" height="463" /&gt;&lt;/p&gt;&lt;pre&gt;db.employees.update(
  {_id: ObjectId("4e5e4c0e945a66e30892e4e3")},
  {$set: {firstName: "Bobby", lastName: "Schmidt"}}
);
&lt;/pre&gt;&lt;p&gt;Even setting values of child objects can be done atomically:&lt;/p&gt;&lt;pre&gt;db.employees.update(
  {_id: ObjectId("4e5e4c0e945a66e30892e4e3")},
  {$set: {"position.title": "Software Developer", "position.id": 1015}}
)
&lt;/pre&gt;&lt;p&gt;In fact, individual items in an array can be changed:&lt;/p&gt;&lt;pre&gt;db.employees.update(
  {_id: ObjectId("4e5e4c0e945a66e30892e4e3")},
  {$set: {"employmentHistory.0.company": "Google, Inc."}}
);
&lt;/pre&gt;&lt;p&gt;However, one thing you may notice is that the code above to modify a specific item in the array requires us to know the specific index of the item in the array we wish to modify. That seems simple, because we can pull down the object, find the index of the item, and then change it. The difficulty with this is that other operations on an array do not necessarily guarantee that the order of the elements will be the same. For example, if an item in an array is removed and then added later, it will always be appended to the array. The only way to keep an array in a particular order is to $set it (replacing all the objects in it), which for a large array may not have the best performance.&lt;/p&gt;&lt;p&gt;This problem is best demonstrated with the following race conditions:&lt;/p&gt;&lt;p&gt;&lt;img src="http://developer.bazaarvoice.com/files/images/MongoDBArrays-readpullset.png" alt="Read, Pull, Set" width="694" height="269" /&gt;&lt;/p&gt;&lt;p&gt;One solution to this problem is to &lt;em&gt;$pull&lt;/em&gt; a particular item from the array, change it, and then &lt;em&gt;$push&lt;/em&gt; it back onto the array. In order to avoid the race condition above, we decided that this was a safer solution. After all, these two operations should be doable atomically.&lt;/p&gt;&lt;pre&gt;db.employees.update(
  {_id: ObjectId("4e5e4c0e945a66e30892e4e3")},
  {$pull: {badges: {type: "TOP_EMPLOYEE"}}, $push: {badges: {type: "TOP_EMPLOYEE", date: null}}}
);
&lt;/pre&gt;&lt;p&gt;So, what's the problem? The issue is that MongoDB doesn't allow multiple operations on the same property in the same update call. This means that the two operations must happen in two individually atomic operations. Therefore it's possible for the following to occur:&lt;/p&gt;&lt;p&gt;&lt;img src="http://developer.bazaarvoice.com/files/images/MongoDBArrays-pullpullpushpush.png" alt="Pull, Pull, Push, Push" width="693" height="382" /&gt;&lt;/p&gt;&lt;p&gt;That is bad enough, but it can be dealt with by updating an object only if it is in the correct state. Unfortunately, the following can happen as well:&lt;/p&gt;&lt;p&gt;&lt;img src="http://developer.bazaarvoice.com/files/images/MongoDBArrays-pullreadpush.png" alt="Read, Pull, Set" /&gt;&lt;/p&gt;&lt;p&gt;That looks very odd to the reader, because at one moment it would see the item, then the next read would lose it, and then it would come back. To an end user that's bad enough, but to another system that is taking actions based on the data, the results can be inconsistent at best, and deleterious at worst.&lt;/p&gt;&lt;p&gt;What we really want is the ability to modify an item (or items) in an array by query, effectively &lt;em&gt;$set&lt;/em&gt; with &lt;em&gt;$pull&lt;/em&gt; semantics:&lt;/p&gt;&lt;pre&gt;db.employees.update(
  {_id: ObjectId("4e5e4c0e945a66e30892e4e3")},
  {$update: {badges: {$query: {type: "TOP_EMPLOYEE"}, $set: {date: null}}}}
);
&lt;/pre&gt;&lt;p&gt;Since that's &lt;a href="https://jira.mongodb.org/browse/SERVER-2476" title="Related MongoDB JIRA Issue"&gt;not yet supported&lt;/a&gt; by MongoDB, we decided to use a map. This makes a lot of sense for our use case since the structure happened to be a map in Java. Because MongoDB uses JSON-like structures, the map is an object just like any other, and the keys are simply the property names of the object.&lt;/p&gt;&lt;p&gt;&lt;img src="http://developer.bazaarvoice.com/files/images/MongoDBArrays-Complex%20Object%20with%20Map.png" alt="Complex Object with Map" width="400" height="463" /&gt;&lt;/p&gt;&lt;p&gt;This means that individual elements can be accessed and updated from the map:&lt;/p&gt;&lt;pre&gt;db.employees.update(
  {_id: ObjectId("4e5e4c0e945a66e30892e4e3")},
  {$set: {"badges.TOP_EMPLOYEE.date": null}}
);
&lt;/pre&gt;&lt;p&gt;This seems like a rather elegant solution, so why didn't we start out this way? One pretty major problem: if you don't know all of the possible keys to the map, there is no good way to index the fields for faster querying. Indexes to child objects in MongoDB are created using dot notation, just like the query syntax. This works really well with arrays because MongoDB supports indexing fields of objects in arrays just like any other child object field. But for a map, the key is part of the path to the child field, so each key is another index:&lt;/p&gt;&lt;pre&gt;// Simple fields
db.employees.ensureIndex({lastName: 1, firstName: 1})

// Child object fields
db.employees.ensureIndex({"position.id": 1})

// Array object fields
db.employees.ensureIndex({"employmentHistory.company": 1})

// Map fields, treating map values like child objects
db.employees.ensureIndex({"badges.TOP_EMPLOYEE.date": 1})
&lt;/pre&gt;&lt;p&gt;For our purposes, we are actually able to index every key individually, and treat the map as an object with known properties.&lt;/p&gt;&lt;p&gt;The sinister part of all of this is that you won't normally run into any problems while doing typical testing of the system. And in the case of the pull/read/push diagram above, even typical load testing wouldn't necessarily exhibit the problem unless the reader is checking every response and looking for inconsistencies between subsequent reads. In a complex system, where data is expected to change constantly, this can be a difficult bug to notice, and even more difficult to track down the root cause.&lt;/p&gt;&lt;p&gt;There are ways to make MongoDB work really well as the primary store, especially since there are so many ways to update individual records &lt;a href="http://www.mongodb.org/display/DOCS/Atomic+Operations" target="_blank" title="MongoDB Atomic Operations"&gt;atomically&lt;/a&gt;. However, working with MongoDB and other NoSQL solutions requires a shift in how developers think about their data storage and the way they write their query/update logic. So far it's been a joy to use, and getting better all the time as we learn to avoid these types of problems in the future.&lt;/p&gt;</description>
 <comments>http://developer.bazaarvoice.com/mongodb-arrays-and-atomicity#comments</comments>
 <category domain="http://developer.bazaarvoice.com/category/tags/database">database</category>
 <pubDate>Wed, 18 Apr 2012 13:30:33 +0000</pubDate>
 <dc:creator>michael.norman</dc:creator>
 <guid isPermaLink="false">553 at http://developer.bazaarvoice.com</guid>
</item>
</channel>
</rss>
