Return Customers = 1%. Is that good?

August 16th, 2010

One of the things that made it easy for me to get started as an online bookseller on Amazon was the fact that I didn’t need to advertise in order to sell a book. Sure, I had to do a decent job of describing the condition, but beyond that, practically nothing. 96,837 sales (mostly on Amazon) and 9 years later, it remains true. I advertise to get books, but not to sell books, and they sell at a good pace. Now, I do work hard to satisfy customers, which results in an exceptionally high seller rating and almost certainly increased sales. If customers are generally satisfied with Amazon, they’ll keep coming back, and that’s good for our business. But, how many buyers come back to me, specifically? Like, none. Well, hyperbole gets the best of me! 1,028 of 95,297 customers came back at a later date to make another purchase. That’s 1%!

I’m sitting here thinking 1% is pretty awful. I go to wordle and type in “one percent” and hit randomize about a hundred times until something coolish appears. A two word wordle only gets so cool.

Wordle: one percent

At which point my son enters the room and asks me what “one percent” is. I explain it to him and he says, “1%! That’s not bad, for us. That’s one person every 2 days!” Which is correct, but is it good?

16 Tons of Books Hauled by Bicycle

January 25th, 2009

Six days a week, 52 weeks a year, and sometimes more than once a day, HD Hauling trucks over to our place, loads as many 12 bins on to a trailer, and hauls them to the Post Office loading dock. Sounds mundane, and it certainly would be if not for the fact the the hauling is done by a guy on a bike.

I am very proud of the fact that our book shipments are hauled to the Post Office by bicycle trailer. Practically everyone I know says they have seen the Books by Chance logo on the back of a bike trailer going up and down Liberty Street in Ann Arbor. It sets a good example. It gets people talking and thinking. And on days when it is pouring rain, or bitterly cold with blowing snow, it is amazing and awe inspiring.

Twitter is a text based communication tool that makes it possible for a person to easily communicate with hundreds, or even thousands, of people wherever they are. It is social, mostly ambient, and sometimes direct, communication. I’ve connected with other book sellers as far away as Germany. I also met Homeless Dave via Twitter, a guy in my neighborhood I had yet to meet. He was twittering about his new bike trailer, and so I asked him if he could haul books on it. To make a long story short, Dave took my books (and me!) for a ride on his trailer, he put me on his teeter totter and questioned me, he made a business of hauling stuff by bike, and he’s been hauling our books ever since.

Dave took this photo of me and it is on his site with others.
Photo of me and my book packages on Dave's bike trailer.

16 Tons: A Twittersation

It was the last day of 2008 when Homeless Dave sent this tweet

celebrating last bike cart delivery of 2008; http://booksbychance.com a great client; my est. tonnage for year: 16; another day older

To which I replied

@homelessdave Yay!!! 16 tons! Wow. You’ve been incredibly reliable, hauling our books year round! Thanks!

And then Dave wrote

@jweise 16 tons estimate based on 100 lbs x 6 days x 52 weeks; please don’t ruin fantasy by running a query ;-) I like TN Ernie’s number

To which I simply said

@homelessdave I like your math. http://www.youtube.com/watch?v=NBkrAESUbyI

The thing is, I really did like Dave’s math. I was pretty sure it was right. I had to run the query on our postage log that includes the weight of every package we ship.

Packages: 23,057
Postal Bins: 2096 (2lbs each)
Tons: 16.0312

If you break it down by week, it looks like this…

If you aren’t impressed enough already by the daring feats of Homeless Dave, check out the way Dave has brought local news back home with the creation of The Ann Arbor Chronicle.

Making the Chart

This is where I diverge and show the MySQL query I used to generate the data for the chart. I estimated 11 packages per postal bin. Each postal bin weighs 2 lbs. To get totals for the year, just remove the parts that mention week, emphasized in the statement.

select week(t_create) as `week`, count(*)/11*2/2000+sum(WeightOz)/16/2000 as `tonnage`, count(*) as `packages`, count(*)/11 as `bins`, count(*)/11*2/2000 as `postal bins tons`, count(*)/11*7/2000 as `bin tons`, sum(WeightOz)/16/2000 as 'tons' from postage where year(t_create)='2008' group by week(t_create);

Distribution of Used Item Sales on Amazon, Abebooks, and Alibris for Books by Chance LLC in 2007-2008.

January 23rd, 2009

At Books by Chance LLC, our entire inventory is online. That’s the only way we sell. (OK, so, occassionally the neighbor kids come by and buy affordable gifts for their parents.) Our used items include books, CDs, and DVDs, but most are books. I have automated the uploading of listings to online services, which include Amazon, Alibris, and Abebooks. Most of our listings appear on all three sites, though some are only on one or two. Pricing is also automated, with prices being reviewed and updated on all sites at least once a day. We base prices almost exclusively on comparable listings at Amazon.

It is worth noting that Alibris enforces a minimum price of $1.99 on all items, and at Abebooks we choose to not go lower than $3.99. Amazon does not enforce a minimum price except for “collectible” items, but we hold out at $1.99 for awhile before dropping to $1.49, and eventually lower. These are just differences that come in to play for sellers like us who are willing to sell some items on the low end.

We actually started selling on Alibris to see if we could get $1.99 for items going for much less on Amazon. It turned out we could, and in fact we can get $1.99 on Amazon for those items as well. That’s worth of another post.

Our inventory tends toward books newer than 1970 and of wide variety, but generally does not contain items considered antique or collectible.

Amazon, Abebooks, Alibris and others have been compared far and wide and my feeling is that the each has strengths and weaknesses that serve different markets and suite different sellers. My preference is for Amazon, and I have built my business on their robust data services. I put as much of our inventory on each site as possible and reasonable (e.g., Abebooks customers tend not to be interested in buying CDs and DVDs, so we don’t force the issue.)

Over the course of 2007 and 2008 we sold over 40,000 items. 80% of those sold on Amazon.com, accounting for 81% of gross sales (shipping excluded). Alibris accounted for 11%, and Abebooks 8%.

Pie Chart: Books by Chance LLC Distribution of Used Item Sales (2007-2008)

We also offer our books on our own site, Books by Chance which accounted for 0% of sales in 2007-2008. We sold a small number of items on our own site, but not enough to count when compared to the big guys.

Making the Chart

I collect all sales information in a single MySQL table. I use the first few characters of the order_id to tell which service/site the item sold on (i.e., Amazon=058, Alibris=ali, Abebooks=abe). To get percentages, I had to insert into the formula the TOTALNUMBERSOLD and TOTAL_DOLLARS_SOLD. There is a way to have MySQL calculate these values on the fly, but I didn’t feel it was worth the trouble in this case.

select `#`, case when `venue`='058' then 'Amazon.com' when `venue`='abe' then 'Abebooks.com' when `venue`='ali' then 'Alibris.com' end as `service`, `$` from (select if ((left(order_id,3)!='abe' and left(order_id,3)!='ali' and left(order_id,3)!='058'), 'oth', left(order_id,3)) as `venue`, round(count(left(order_id,3))/TOTAL_NUMBER_SOLD*100) as `#`, round(sum(price)/TOTAL_DOLLARS_SOLD*100) as `$` from sold where year(payments_date)>=2007 and year(payments_date)<=2008 and sku>0 and (left(order_id,3)='abe' or left(order_id,3)='ali' or left(order_id,3)='058') group by if ((left(order_id,3)!='abe' and left(order_id,3)!='ali' and left(order_id,3)!='058'), 'oth', left(order_id,3))) as `t1`;

Tricks for Controlling Expedited and International Shipping Options in Amazon Marketplace

January 18th, 2009

To Expedite or Not To Expedite

One of the things I really like about selling used books on Amazon, compared to other sites, is that I can decide, on a per item basis, whether or not to offer expedited and international shipping.

Amazon Marketplace Shipping Rates are fixed, meaning the rate is the same regardless of the size of the book. This is fine, but it can be a bummer when a customer chooses expedited or international shipping for a large or heavy item. You can easily loose money on the transaction. However, if the item fits in a US Postal Service Priority Mail flat rate envelope, you can be sure the cost of shipping will not undo your profit. The challenge is to only offer expedited and international shipping on items you know will fit in a flat rate envelope.

The “Ziplock” Bag Solution

Years ago, when just starting out in the used book business, I made a decision to put each book in a plastic “ziplock” bag. Why?

  1. To protect the books from dust, humidity, and shelf wear.
  2. To contain the allergens often found in older books.
  3. To have a way to place an inventory number on the item without putting a sticker directly on the book.

I fretted about what size to use. I did not want the hassle of sorting different sizes. I decided 9″x12″ would work well in most cases, and ordered 2,000 bags online. I have never bought another size. What about larger books? Well, here is the hidden beauty of the 9″x12″ bag! It turns out that if a book fits in a 9″x12″ “ziplock” bag, it also fits in a US Postal Service Priority Mail flat rate envelope! There are occasional exceptions, but not enough to justify a smaller bag.

When a book does not fit in 9″x12″ bag, we put it on an oversize shelf, not in a bag, and mark it as “oversize” in the inventory record. This information is then used to enable/disable expedited and international shipping in the records we upload to Amazon.

The Flat Rate Formula

I bet “ziplock” bags are not a solution that will work well for all used book sellers. I also employ a simple formula to estimate whether a book will fit in a US Postal Service Priority Mail flat rate envelope. It requires that you have length, width and height dimensions. You add the greatest and least of these measurements together and if the total is less than 11 inches, the book will fit in a flat rate envelope, and can even be wrapped at least once in 3/16″ bubblewrap!

Examples:

height: 3″, length: 9″, width: 7″
9″ (greatest) + 3″ (Least) = 12″
Too big!!!

height: 1″, length: 6″, width: 8″
8″ (greatest) + 1″ (least) = 9″
Fits!!!

I love this equation because it very rarely (if ever) fails and it is very simple.

Amazon provides dimensions for most books on their web site and also via the Amazon Web Service (AWS). Here is a specific example of product info that includes product dimensions in the AWS documentation. Sometimes the size data are missing or wrong, but they are correct most of the time, and certainly often enough to be useful.

I use the equation above again at order fulfillment time to recommend appropriate packaging and calculate postage regardless of the shipping method. It works great and is a huge time saver.

I bought my last batch of bags from Comet Supply. I got a great price of $18.96 for 1000 bags (July 2008). In fact, I remember thinking at the time that the price was too good to be true, so I am not too surprised that the price has gone up considerably. It never hurts to shop around. I recommend 2 MIL plastic for durability. I use the bags over and over again.

The Flat Rate Formula in MySQL

I’m sure you could figure this out on your own. MySQL has “greatest” and “least” functions that make it really easy to use the flat rate formula in MySQL.

greatest(Height, Length, Width) + Least(Height, Length, Width)

Amazon Sales Rank as an Indicator of Sales Potential for Used Books, CDs, and DVDs

January 15th, 2009

Amazon has a ranking system for the products they offer. Rankings for books currently go from 1 to over 7 million, with 1, of course, being the best. We’re #1! When deciding whether or not to inventory a used book, CD, or DVD, we consider several factors, perhaps the most important being the Amazon Sales Rank. I have compiled our sales data for the last three years (2006-2008) to create the charts below. To help you gauge the scale of the dataset, I’ll just tell you we sold over 50,000 individual inventory items, almost entirely used.

You can see we sold 90% of items with an Amazon Sales Rank ranging from 1 to 500,000 at the time we listed the item. The percentage of items sold drops off steadily as as the Amazon Sales Rank increases (worsens). We sold only 5% of the items we listed having a rank from 6.5 million to 7 million.

Percentage of Items Sold Grouped by Amazon Sales Rank

The most popular books tend to have low prices in the used market. There is generally high demand and high supply. When lots of people buy the book new, there will inevitably be lots of used copies available, and used prices will drop rapidly as sellers jockey to make the sale.

The next chart is similar to the chart above, but additionally shows what percentage of total sales came from each Amazon Sales Rank grouping. Items with an Amazon Sales Rank of 500,000 or better accounted for 62% of items sold, and 53% of sales in dollars. Notice that for items ranked from 500,001 to 1 million, percentages for number sold and sales in dollars equal out at 17%, and in groupings beyond that the dollars out pace number sold.

Percentage of Items Sold Grouped by Amazon Sales Rank

We tend to allow relatively inexpensive items in to our inventory as long as the item has a good sales rank. We also allow items in to our inventory without such a good sales rank as long as the price is high enough to justify the effort it takes to list the item, and the shelf space to store it for possibly an extended period of time.

We have very intentionally chosen to concentrate our efforts on the 2 or so million highest ranked books. We routinely pass-up books that, based on data we have collected, have very little chance of selling. We prefer to channel items that are less likely to sell back to our clients or the Ann Arbor Reuse Center than to have them languish on our shelves unread. Which raises the question, how long does it take an item to sell?

We sell books, CDs, and DVDs on consignment, which requires tracking each item very carefully. We know exactly when an item is listed, and when it sells. Therefore, we can easily report on how many days it takes, and we can group the items by Amazon Sales Rank.

Average Number of Days for an Item to Sell Grouped by Amazon Sales Rank

Like all of the charts in this post, the above is based on our used book sales from 2006-2008.

The surprising thing about the “days to sell” chart is that items in the middle ranks took the longest to sell. I am not yet sure what to make of this. It might help to break the data down by year (I took a quick look at just 2006-2007, and the pattern is the same). Don’t let that distract you though. Items with an Amazon Sales Rank better than 500,000 on average sell in about 30 days. That’s a pretty useful piece of information.

Results, of course, may vary. You also have to consider condition, customer feedback rating, and selling venues (for us that is Amazon, Alibris, Abebooks, Books by Chance).

The data used in this post include sales of books, CDs, DVDS, audio books on cassette, and VHS. Amazon has separate rankings for books, music, and movies and the range of rank values varies for each from 1 to N. I lumped everything together. We sell primarily books, and the vast majority of our sales occur on Amazon.

The following table shows numeric data for the first two charts.

Amazon Sales Rank % sold % of Total # Sold % of Total $ Sold
1-500000 90 62.60 53.08
500001-1000000 82 16.63 16.65
1000001-1500000 75 7.72 9.29
1500001-2000000 65 4.34 5.89
2000001-2500000 54 2.33 3.21
2500001-3000000 47 1.29 1.97
3000001-3500000 43 0.89 1.56
3500001-4000000 36 0.46 0.85
4000001-4500000 34 0.27 0.65
4500001-5000000 31 0.14 0.41
5000001-5500000 20 0.06 0.16
5500001-6000000 18 0.03 0.06
6000001-6500000 16 0.01 0.06
6500001-7000000 5 0.00 0.00

One final point. I omitted items that were unranked at the time listed. We sold 34% of items that were unranked at the time of listing, and they sold on average in 242 days. That’s a pretty good percentage. Unranked items are wildcards, generally worth the risk if the price is decently high. The thing to watch out for, however, is other editions of the same title that have low prices and good sales ranks.

Making the Charts

The following MySQL command shows how I generated the data for the last chart “Average Number of Days for an Item to Sell Grouped by Amazon Sales Rank”. Of course, this is what worked for my inventory database, and the way I have it set up. There are just two tables at play. One that holds the inventory, and another with sales information. The best trick here is the one used to calculate the age. You’ll see the number 86,400. That’s the number of seconds in a day. Inventory items without an Amazon Sales Rank, or with a rank over 7 million were omitted. Also of interest may be the calculations used to cluster sales by rank in increments of 500,000.

select concat(round(floor(skuinventory.salesrank_orig/500000)*1000000/2)+1, '-', round(floor(skuinventory.salesrank_orig/500000)*1000000/2+500000)) as `Amazon Sales Rank`, floor(avg(if(sale_status='sold', @age:=(unix_timestamp(sold.payments_date) - unix_timestamp(skuinventory.t_create))/86400, NULL))) as `# Days` from skuinventory left join sold on skuinventory.sku=sold.sku where year(t_create)>=2006 and year(t_create)<=2008 and salesrank_orig<7000000 and salesrank_orig is not NULL group by floor(skuinventory.salesrank_orig/500000);

Not a Big Surprise: Used Book Sales Slumped in Late 2008 Despite Steady Inventory

January 4th, 2009

My previous post took a look at how sales dropped off during the distraction of the presidential election and in the wake of a serious economic downturn. There could, of course, be other reasons for the slump in sales, so I thought I would take a look at the size of our inventory during the same period. A good portion of our inventory turns over fairly quickly, and if the flow of incoming inventory slows down, sales will too. Historically we have sold about 50% of newly listed items within a couple of months. The summer of 2008 we received used books in record numbers and our inventory grew steadily. Even during August, our best month of sales, the size of our inventory remained fairly constant since more items were added on a daily basis.

The following chart shows the number of items we sold compared to the size of our inventory. I should note that each year August is our best month, so the red spike is not surprising.

2008 Number of Items Sold Compared to Inventory Size

Compare the above to 2007 below. The size of our used book inventory grew rapidly, and sales grew as well. Similar to 2008, there is a spike in August, however, above average sales through October and November, and then another spike around the holidays. Overall, sales in the fourth quarter of 2007 were strong.

2007 Number of Items Sold Compared to Inventory Size

I might as well round this out with charts back to 2004 starting with 2006, which looks a lot like 2007, which I think helps validate the data.

2006 Number of Items Sold Compared to Inventory Size

2005 is also similar to 2007 and 2006, but notice that there is a fairly significant dip in early November, though not nearly as severe as the election dip in 2008.

2005 Number of Items Sold Compared to Inventory Size

2004, like 2008, featured a presidential election in the U.S., and so one might expect to see a similar sort of dip around November. Unfortunately, the chart for 2004 is not very informative, though it is interesting and worthy of deeper exploration in a future posting. Our business was in a different phase of development in 2004. If I recall correctly, we expunged a fair amount of inventory and replaced it with better stuff as we shifted toward strictly selling on consignment. The size of our inventory dropped linearly until late in the year when it started to grow again. Notice how sales were relatively consistent across the year despite the decreasing in amount of stock. We were getting wiser about what would sell.

2004 Number of Items Sold Compared to Inventory Size

Making The Charts (For the Hardy Geeks)

The data for these charts were tricky to compile because it was necessary to know the size of the inventory on each day of the year. Realizing it would be necessary to iterate over every day of the year, I resorted to writing a Perl script to do the following for a specified year. (The actual Perl script is a quick hack  specific to my own situation and too ugly to share, but here is the gist, including the relevant MySQL statements.)

  1. Generated a list of dates for the entire year. Knowing that I have sold at least 1 book every day of the year for the last several years, I simply grabbed dates from my table of sold items as follows.
    select left(payments_date,10) as `date` from `sold` where year(payments_date)='2008' group by left(payments_date,10)
  2. For each date count the number of items sold. Treat “$date” as psuedo-code for a variable equal to any date in the set.
    select count(*) from sold where left(payments_date,10) <= '$date';
  3. For each date get the size of the inventory on that date.select count(*) from `inventory` where left(t_create,10) <= '$date';
  4. For each date subtract the number of items sold from the number of inventory items to get the number of items in the inventory on that date. Keep a tally of all daily inventory size calculations so an average can be calculated after looping over all dates.
  5. At this point, there is a list of the number of items sold and the size of the inventory for every day plus a sum total of all daily inventory sizes.
  6. Calculate the average number of sold items per day.
    select avg(`count`) as `avg  sold` from (select count(*) as `count` from sold where year(payments_date)='2008' group by left(payments_date,10)) as `t1`;
  7. Calculate the average daily inventory size by dividing the sum total of inventory sizes by the number of days.
  8. Loop over the list to compute daily inventory size and items sold as a percentage of the average, printing the results as tab delimited text.
  9. Load the output into a Google Docs spreadsheet and generate a chart.

Apparent Affect of 2008 Presidential Election on Used Book Sales

January 2nd, 2009

This being my first post, let me share a few basic facts about my experience selling used books. I started in 2001, and I’ve sold over 60,000 books, practically all online through Amazon, Alibris, and Abebooks. My business, Books by Chance, has a fairly unique business model in that we sell strictly on consignment, and we sell a broad range of common books.

2008 started well enough, our offerings grew substantially over the summer, and sales spiked in the August “back to school rush” as expected. When growing rapidly, it can be a bit hard to estimate the vitality of the market, but with the economy stumbling it seemed likely sales were not what they could be. The housing bubble burst, the stock market sank. People clamped down on their spending and watched anxiously as we approached the presidential election. It was right around election day when sales bottomed out.

The following graph shows how our sales varied through the course of the year, expressed in terms relative to an average day of sales in 2008. I find the apparent impact of the election on used book sales fascinating. Sales dropped to half the norm.

Chart of 2008 Used Book Sales

In response to Ed’s comment, I have added the following chart, which is the same as the previous chart, but aggregated by week. Only full weeks of the year are included (first and last weeks omitted).

Chart of 2008 Used Book Sales By Week

To help bridge the gap between 2008 and 2004, I have added the charts for 2007, 2006, and 2005.

Chart of 2007 Used Book Sales By Week

Chart of 2006 Used Book Sales By Week

Chart of 2005 Used Book Sales By Week

Taking a look at 2004, when we also had a presidential election in the U.S., there is not an obvious dip in sales around the polling date. Overall, the year looks relatively consistent.

Chart of 2004 Used Book Sales

Again, in response to Ed’s comment, I have added the following chart, which is the same as the previous chart, but aggregated by week. Only full weeks of the year are included (first and last weeks omitted).

Chart of 2004 Used Book Sales by Week

Making The Charts (For the Hardy Geeks)

As if this were not geeky enough, here are details about how I made the above charts.

I have a table holding sales transactions called “sold”, and a table for my inventory called “skuinventory”.

The first step was to calculate daily averages for gross sales (AVGDAILYGROSS) and number of items sold (AVGNUMBERSOLDPERDAY).

select avg(price), avg(count) from (select left(payments_date,10) as `date`, sum(price) as price, count(*) as count from sold where sku > 0 and year(payments_date)=2008 group by left(payments_date,10) ) as `t1`;

Next I used the following query (which includes a subquery) I generated the final data set which I charted using a Google Docs spreadsheet.

select left(payments_date,10) as `date`, round(sum(price)/AVGDAILYGROSS*100) as `$`, round(count(*)/AVGNUMBERSOLDPERDAY*100) as `#` from sold where sku > 0 and year(payments_date)=2008 group by left(payments_date,10);

When asked if I could aggregate the data by week, rather than by day, I altered the query to use the MySQL “week” function. This introduced a minor problem in that the first and last week of the year often do not include 7 days, which threw the chart off a bit on each end. So, I decided to only use full weeks.

select concat(month(payments_date), '/', day(payments_date), ' (week ', week(payments_date), ')') as `date`, round(sum(price)/AVGDAILYGROSS/7*100) as `$`, round(count(sku)/AVGNUMBERSOLDPERDAY/7*100) as `#` from sold where sku > 0 and year(payments_date)=2008 and week(payments_date)>=1 and week(payments_date)<=51 group by week(payments_date);