You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@couchdb.apache.org by kx...@apache.org on 2013/09/28 14:42:31 UTC

[05/50] [abbrv] Better introduction into CouchDB.

http://git-wip-us.apache.org/repos/asf/couchdb/blob/7c4a8c4e/share/doc/src/intro/tour.rst
----------------------------------------------------------------------
diff --git a/share/doc/src/intro/tour.rst b/share/doc/src/intro/tour.rst
new file mode 100644
index 0000000..af91f5e
--- /dev/null
+++ b/share/doc/src/intro/tour.rst
@@ -0,0 +1,534 @@
+.. Licensed under the Apache License, Version 2.0 (the "License"); you may not
+.. use this file except in compliance with the License. You may obtain a copy of
+.. the License at
+..
+..   http://www.apache.org/licenses/LICENSE-2.0
+..
+.. Unless required by applicable law or agreed to in writing, software
+.. distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+.. WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+.. License for the specific language governing permissions and limitations under
+.. the License.
+
+
+.. _intro/tour:
+
+===============
+Getting Started
+===============
+
+In this chapter, we'll take a quick tour of CouchDB's features,
+familiarizing ourselves with Futon, the built-in administration interface.
+We'll create our first document and experiment with CouchDB views.
+
+
+All Systems Are Go!
+===================
+
+We'll have a very quick look at CouchDB's bare-bones Application Programming
+Interface (API) by using the command-line utility curl. Please note that this
+is not the only way of talking to CouchDB. We will show you plenty more
+throughout the rest of the book. What's interesting about curl is that it
+gives you control over raw HTTP requests, and you can see exactly what is
+going on "underneath the hood" of your database.
+
+Make sure CouchDB is still running, and then do::
+
+  curl http://127.0.0.1:5984/
+
+This issues a GET request to your newly installed CouchDB instance.
+
+The reply should look something like:
+
+.. code-block:: javascript
+
+  {
+    "couchdb": "Welcome",
+    "uuid": "85fb71bf700c17267fef77535820e371",
+    "version": "1.4.0",
+    "vendor": {
+        "version": "1.4.0",
+        "name": "The Apache Software Foundation"
+    }
+  }
+
+Not all that spectacular. CouchDB is saying "hello" with the running version
+number.
+
+Next, we can get a list of databases::
+
+  curl -X GET http://127.0.0.1:5984/_all_dbs
+
+All we added to the previous request is the _all_dbs string.
+
+The response should look like::
+
+  ["_replicator","_users"]
+
+Oh, that's right, we didn't create any databases yet! All we see is an empty
+list.
+
+.. note::
+
+  The curl command issues GET requests by default. You can issue POST requests
+  using ``curl -X POST``. To make it easy to work with our terminal history,
+  we usually use the ``-X`` option even when issuing GET requests.
+  If we want to send a POST next time, all we have to change is the method.
+
+  HTTP does a bit more under the hood than you can see in the examples here.
+  If you're interested in every last detail that goes over the wire,
+  pass in the ``-v`` option (e.g., ``curl -vX GET``), which will show you
+  the server curl tries to connect to, the request headers it sends,
+  and response headers it receives back. Great for debugging!
+
+Let's create a database::
+
+  curl -X PUT http://127.0.0.1:5984/baseball
+
+CouchDB will reply with::
+
+  {"ok":true}
+
+Retrieving the list of databases again shows some useful results this time::
+
+  curl -X GET http://127.0.0.1:5984/_all_dbs
+
+::
+
+  ["baseball"]
+
+.. note::
+
+  We should mention JavaScript Object Notation (JSON) here,
+  the data format CouchDB speaks. JSON is a lightweight data interchange format
+  based on JavaScript syntax. Because JSON is natively compatible with
+  JavaScript, your web browser is an ideal client for CouchDB.
+
+  Brackets (``[]``) represent ordered lists, and curly braces (``{}``) represent
+  key/value dictionaries. Keys must be strings, delimited by quotes (``"``),
+  and values can be strings, numbers, booleans, lists,
+  or key/value dictionaries. For a more detailed description of JSON,
+  see Appendix E, JSON Primer.
+
+Let's create another database::
+
+  curl -X PUT http://127.0.0.1:5984/baseball
+
+CouchDB will reply with::
+
+  {"error":"file_exists","reason":"The database could not be created,
+  the file already exists."}
+
+We already have a database with that name, so CouchDB will respond with an
+error. Let's try again with a different database name::
+
+  curl -X PUT http://127.0.0.1:5984/plankton
+
+CouchDB will reply with::
+
+  {"ok":true}
+
+Retrieving the list of databases yet again shows some useful results::
+
+  curl -X GET http://127.0.0.1:5984/_all_dbs
+
+CouchDB will respond with::
+
+  ["baseball", "plankton"]
+
+To round things off, let's delete the second database::
+
+  curl -X DELETE http://127.0.0.1:5984/plankton
+
+CouchDB will reply with::
+
+  {"ok":true}
+
+The list of databases is now the same as it was before::
+
+  curl -X GET http://127.0.0.1:5984/_all_dbs
+
+CouchDB will respond with::
+
+  ["baseball"]
+
+For brevity, we'll skip working with documents, as the next section covers a
+different and potentially easier way of working with CouchDB that should
+provide experience with this. As we work through the example,
+keep in mind that "under the hood" everything is being done by the
+application exactly as you have been doing here manually.
+Everything is done using GET, PUT, POST, and DELETE with a URI.
+
+
+Welcome to Futon
+================
+
+After having seen CouchDB's raw API, let's get our feet wet by playing with
+Futon, the built-in administration interface. Futon provides full access to
+all of CouchDB's features and makes it easy to work with some of the more
+complex ideas involved. With Futon we can create and destroy databases; view
+and edit documents; compose and run MapReduce views; and trigger replication
+between databases.
+
+To load Futon in your browser, visit::
+
+  http://127.0.0.1:5984/_utils/
+
+If you're running version 0.9 or later, you should see something similar to
+:ref:`intro/tour-01`. In later chapters, we'll focus on using CouchDB from
+server-side languages such as Ruby and Python. As such, this chapter is a great
+opportunity to showcase an example of natively serving up a dynamic web
+application using nothing more than CouchDB's integrated web server, something
+you may wish to do with your own applications.
+
+The first thing we should do with a fresh installation of CouchDB is run the
+test suite to verify that everything is working properly. This assures us
+that any problems we may run into aren't due to bothersome issues with our
+setup. By the same token, failures in the Futon test suite are a red flag,
+telling us to double-check our installation before attempting to use a
+potentially broken database server, saving us the confusion when nothing
+seems to be working quite like we expect!
+
+
+.. _intro/tour-01:
+
+.. figure:: ../../images/intro-tour-01.png
+   :align: center
+   :alt: The Futon welcome screen
+
+   Figure 1. The Futon welcome screen
+
+
+Some common network configurations cause the replication test to fail when
+accessed via the localhost address. You can fix this by accessing CouchDB via
+127.0.0.1, e.g. http://127.0.0.1:5984/_utils/.
+
+Navigate to the test suite by clicking "Test Suite" on the Futon sidebar,
+then click "run all" at the top to kick things off. :ref:`intro/tour-02`
+shows the Futon test suite running some tests.
+
+
+.. _intro/tour-02:
+
+.. figure:: ../../images/intro-tour-02.png
+   :align: center
+   :alt: The Futon test suite running some tests
+
+   Figure 2. The Futon test suite running some tests
+
+
+Because the test suite is run from the browser, not only does it test that
+CouchDB is functioning properly, it also verifies that your browser's
+connection to the database is properly configured, which can be very handy
+for diagnosing misbehaving proxies or other HTTP middleware.
+
+If the test suite has an inordinate number of failures,
+you'll need to see the troubleshooting section in Appendix D,
+Installing from Source for the next steps to fix your installation.
+
+Now that the test suite is finished, you've verified that your CouchDB
+installation is successful and you're ready to see what else Futon has to offer.
+
+
+Your First Database and Document
+================================
+
+Creating a database in Futon is simple. From the overview page,
+click "Create Database." When asked for a name, enter hello-world and click
+the Create button.
+
+After your database has been created, Futon will display a list of all its
+documents. This list will start out empty (:ref:`intro/tour-03`), so let's
+create our first document. Click the "New Document" link and then the Create
+button in the pop up. Make sure to leave the document ID blank,
+and CouchDB will generate a UUID for you.
+
+For demoing purposes, having CouchDB assign a UUID is fine. When you write
+your first programs, we recommend assigning your own UUIDs. If your rely on
+the server to generate the UUID and you end up making two POST requests
+because the first POST request bombed out, you might generate two docs and
+never find out about the first one because only the second one will be
+reported back. Generating your own UUIDs makes sure that you'll never end up
+with duplicate documents.
+
+Futon will display the newly created document, with its _id and _rev as the
+only fields. To create a new field, click the "Add Field" button. We'll call
+the new field hello. Click the green check icon (or hit the Enter key) to
+finalize creating the hello field. Double-click the hello field's value
+(default null) to edit it.
+
+You can experiment with other JSON values; e.g., ``[1, 2, "c"]`` or
+``{"foo": "bar"}``. Once you've entered your values into the document,
+make a note of its ``_rev`` attribute and click "Save Document." The result
+should look like :ref:`intro/tour-04` document in Futon".
+
+
+.. _intro/tour-03:
+
+.. figure:: ../../images/intro-tour-03.png
+   :align: center
+   :alt: An empty database in Futon
+
+   Figure 3. An empty database in Futon
+
+
+.. _intro/tour-04:
+
+.. figure:: ../../images/intro-tour-04.png
+   :align: center
+   :alt: A "hello world" document in Futon
+
+   Figure 4. A "hello world" document in Futon
+
+
+You'll notice that the document's _rev has changed. We'll go into more detail
+about this in later chapters, but for now, the important thing to note is
+that _rev acts like a safety feature when saving a document. As long as you
+and CouchDB agree on the most recent _rev of a document, you can successfully 
+save your changes.
+
+Futon also provides a way to display the underlying JSON data,
+which can be more compact and easier to read, depending on what sort of data
+you are dealing with. To see the JSON version of our "hello world" document,
+click the Source tab. The result should look like :ref:`intro/tour-05`.
+
+
+.. _intro/tour-05:
+
+.. figure:: ../../images/intro-tour-05.png
+   :align: center
+   :alt: The JSON source of a "hello world" document in Futon
+
+   Figure 5. The JSON source of a "hello world" document in Futon
+
+
+Running a Query Using MapReduce
+===============================
+
+Traditional relational databases allow you to run any queries you like as
+long as your data is structured correctly. In contrast,
+CouchDB uses predefined map and reduce functions in a style known as
+MapReduce. These functions provide great flexibility because they can adapt
+to variations in document structure, and indexes for each document can be
+computed independently and in parallel. The combination of a map and a reduce
+function is called a view in CouchDB terminology.
+
+For experienced relational database programmers, MapReduce can take some
+getting used to. Rather than declaring which rows from which tables to
+include in a result set and depending on the database to determine the most
+efficient way to run the query, reduce queries are based on simple range
+requests against the indexes generated by your map functions.
+
+Map functions are called once with each document as the argument.
+The function can choose to skip the document altogether or emit one or more
+view rows as key/value pairs. Map functions may not depend on any information
+outside of the document. This independence is what allows CouchDB views to be
+generated incrementally and in parallel.
+
+CouchDB views are stored as rows that are kept sorted by key. This makes
+retrieving data from a range of keys efficient even when there are thousands
+or millions of rows. When writing CouchDB map functions,
+your primary goal is to build an index that stores related data under nearby
+keys.
+
+Before we can run an example MapReduce view, we'll need some data to run it
+on. We'll create documents carrying the price of various supermarket items as
+found at different shops. Let's create documents for apples, oranges,
+and bananas. (Allow CouchDB to generate the _id and _rev fields.) Use Futon
+to create documents that have a final JSON structure that looks like this:
+
+.. code-block:: javascript
+
+  {
+   "_id": "00a271787f89c0ef2e10e88a0c0001f4",
+   "_rev": "1-2628a75ac8c3abfffc8f6e30c9949fd6",
+   "item": "apple",
+   "prices": {
+       "Fresh Mart": 1.59,
+       "Price Max": 5.99,
+       "Apples Express": 0.79
+   }
+  }
+
+This document should look like :ref:`intro/tour-06` when entered into Futon.
+
+
+.. _intro/tour-06:
+
+.. figure:: ../../images/intro-tour-06.png
+   :align: center
+   :alt: An example document with apple prices in Futon
+
+   Figure 6. An example document with apple prices in Futon
+
+
+OK, now that that's done, let's create the document for oranges:
+
+.. code-block:: javascript
+
+  {
+   "_id": "00a271787f89c0ef2e10e88a0c0003f0",
+   "_rev": "1-e9680c5d9a688b4ff8dd68549e8e072c",
+   "item": "orange",
+   "prices": {
+       "Fresh Mart": 1.99,
+       "Price Max": 3.19,
+       "Citrus Circus": 1.09
+   }
+  }
+
+And finally, the document for bananas:
+
+.. code-block:: javascript
+
+  {
+   "_id": "00a271787f89c0ef2e10e88a0c00048b",
+   "_rev": "1-60e25d93dc12884676d037400a6fa189",
+   "item": "banana",
+   "prices": {
+       "Fresh Mart": 1.99,
+       "Price Max": 0.79,
+       "Banana Montana": 4.22
+   }
+  }
+
+Imagine we're catering a big luncheon, but the client is very price-sensitive.
+To find the lowest prices, we're going to create our first view,
+which shows each fruit sorted by price. Click "hello-world" to return to the
+hello-world overview, and then from the "select view" menu choose "Temporary
+view…" to create a new view.
+
+Edit the map function, on the left, so that it looks like the following:
+
+.. code-block:: javascript
+
+  function(doc) {
+    var shop, price, value;
+    if (doc.item && doc.prices) {
+        for (shop in doc.prices) {
+            price = doc.prices[shop];
+            value = [doc.item, shop];
+            emit(price, value);
+        }
+    }
+  }
+
+This is a JavaScript function that CouchDB runs for each of our documents as
+it computes the view. We'll leave the reduce function blank for the time being.
+
+Click "Run" and you should see result rows like in :ref:`intro/tour-08`,
+with the various items sorted by price. This map function could be even more
+useful if it grouped the items by type so that all the prices for bananas were
+next to each other in the result set. CouchDB's key sorting system allows any
+valid JSON object as a key. In this case, we'll emit an array of [item, price]
+so that CouchDB groups by item type and price.
+
+
+.. _intro/tour-08:
+
+.. figure:: ../../images/intro-tour-08.png
+   :align: center
+   :alt: The results of running a view in Futon
+
+   Figure 8. The results of running a view in Futon
+
+
+Let's modify the view function so that it looks like this:
+
+.. code-block:: javascript
+
+  function(doc) {
+    var shop, price, key;
+    if (doc.item && doc.prices) {
+        for (shop in doc.prices) {
+            price = doc.prices[shop];
+            key = [doc.item, price];
+            emit(key, shop);
+        }
+    }
+  }
+
+Here, we first check that the document has the fields we want to use. CouchDB
+recovers gracefully from a few isolated map function failures,
+but when a map function fails regularly (due to a missing required field or
+other JavaScript exception), CouchDB shuts off its indexing to prevent any
+further resource usage. For this reason, it's important to check for the
+existence of any fields before you use them. In this case,
+our map function will skip the first "hello world" document we created
+without emitting any rows or encountering any errors. The result of this
+query should look like :ref:`intro/tour-09`.
+
+
+.. _intro/tour-09:
+
+.. figure:: ../../images/intro-tour-09.png
+   :align: center
+   :alt: The results of running a view after grouping by item type and price
+
+   Figure 9. The results of running a view after grouping by item type and price
+
+
+Once we know we've got a document with an item type and some prices,
+we iterate over the item's prices and emit key/values pairs. The key is an
+array of the item and the price, and forms the basis for CouchDB's sorted
+index. In this case, the value is the name of the shop where the item can be
+found for the listed price.
+
+View rows are sorted by their keys -- in this example, first by item,
+then by price. This method of complex sorting is at the heart of creating
+useful indexes with CouchDB.
+
+MapReduce can be challenging, especially if you've spent years working with
+relational databases. The important things to keep in mind are that map
+functions give you an opportunity to sort your data using any key you choose,
+and that CouchDB's design is focused on providing fast,
+efficient access to data within a range of keys.
+
+
+Triggering Replication
+======================
+
+Futon can trigger replication between two local databases,
+between a local and remote database, or even between two remote databases.
+We'll show you how to replicate data from one local database to another,
+which is a simple way of making backups of your databases as we're working
+through the examples.
+
+First we'll need to create an empty database to be the target of replication.
+Return to the overview and create a database called hello-replication.
+Now click "Replicator" in the sidebar and choose hello-world as the source
+and hello-replication as the target. Click "Replicate" to replicate your
+database. The result should look something like :ref:`intro/tour-10`.
+
+
+.. _intro/tour-10:
+
+.. figure:: ../../images/intro-tour-10.png
+   :align: center
+   :alt: Running database replication in Futon
+
+   Figure 10. Running database replication in Futon
+
+
+.. note::
+
+  For larger databases, replication can take much longer. It is important to
+  leave the browser window open while replication is taking place.
+  As an alternative, you can trigger replication via curl or some other HTTP
+  client that can handle long-running connections. If your client closes the
+  connection before replication finishes, you'll have to retrigger it.
+  Luckily, CouchDB's replication can take over from where it left off
+  instead of starting from scratch.
+
+
+Wrapping Up
+===========
+
+Now that you've seen most of Futon's features, you'll be prepared to dive in
+and inspect your data as we build our example application in the next few
+chapters. Futon's pure JavaScript approach to managing CouchDB shows how it's
+possible to build a fully featured web application using only CouchDB's HTTP
+API and integrated web server.
+
+But before we get there, we'll have another look at CouchDB's HTTP API -- now
+with a magnifying glass. Let's curl up on the couch and relax.

http://git-wip-us.apache.org/repos/asf/couchdb/blob/7c4a8c4e/share/doc/src/intro/why.rst
----------------------------------------------------------------------
diff --git a/share/doc/src/intro/why.rst b/share/doc/src/intro/why.rst
new file mode 100644
index 0000000..1b902d8
--- /dev/null
+++ b/share/doc/src/intro/why.rst
@@ -0,0 +1,315 @@
+.. Licensed under the Apache License, Version 2.0 (the "License"); you may not
+.. use this file except in compliance with the License. You may obtain a copy of
+.. the License at
+..
+..   http://www.apache.org/licenses/LICENSE-2.0
+..
+.. Unless required by applicable law or agreed to in writing, software
+.. distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+.. WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+.. License for the specific language governing permissions and limitations under
+.. the License.
+
+
+.. _intro/why:
+
+============
+Why CouchDB?
+============
+
+Apache CouchDB is one of a new breed of database management systems.
+This chapter explains why there's a need for new systems as well as the
+motivations behind building CouchDB.
+
+As CouchDB developers, we're naturally very excited to be using CouchDB.
+In this chapter we'll share with you the reasons for our enthusiasm.
+We'll show you how CouchDB's schema-free document model is a better fit
+for common applications, how the built-in query engine is a powerful way
+to use and process your data, and how CouchDB's design lends itself
+to modularization and scalability.
+
+
+Relax
+=====
+
+If there's one word to describe CouchDB, it is *relax*. It is in the title of
+this book, it is the byline to CouchDB's official logo,
+and when you start CouchDB, you see::
+
+  Apache CouchDB has started. Time to relax.
+
+Why is relaxation important? Developer productivity roughly doubled in the
+last five years. The chief reason for the boost is more powerful tools that
+are easier to use. Take Ruby on Rails as an example. It is an infinitely
+complex framework, but it's easy to get started with. Rails is a success
+story because of the core design focus on ease of use. This is one reason why
+CouchDB is relaxing: learning CouchDB and understanding its core concepts
+should feel natural to most everybody who has been doing any work on the Web.
+And it is still pretty easy to explain to non-technical people.
+
+Getting out of the way when creative people try to build specialized
+solutions is in itself a core feature and one thing that CouchDB aims to get
+right. We found existing tools too cumbersome to work with during development
+or in production, and decided to focus on making CouchDB easy, even a pleasure,
+to use.
+
+Another area of relaxation for CouchDB users is the production setting.
+If you have a live running application, CouchDB again goes out of its way
+to avoid troubling you. Its internal architecture is fault-tolerant,
+and failures occur in a controlled environment and are dealt with gracefully.
+Single problems do not cascade through an entire server system but stay
+isolated in single requests.
+
+CouchDB's core concepts are simple (yet powerful) and well understood.
+Operations teams (if you have a team; otherwise, that's you) do not have to
+fear random behavior and untraceable errors. If anything should go wrong,
+you can easily find out what the problem is, but these situations are rare.
+
+CouchDB is also designed to handle varying traffic gracefully. For instance,
+if a website is experiencing a sudden spike in traffic, CouchDB will generally
+absorb a lot of concurrent requests without falling over. It may take a little
+more time for each request, but they all get answered. When the spike is over,
+CouchDB will work with regular speed again.
+
+The third area of relaxation is growing and shrinking the underlying hardware
+of your application. This is commonly referred to as scaling. CouchDB enforces
+a set of limits on the programmer. On first look, CouchDB might seem
+inflexible, but some features are left out by design for the simple reason
+that if CouchDB supported them, it would allow a programmer to create
+applications that couldn't deal with scaling up or down.
+
+.. note::
+  CouchDB doesn't let you do things that would get you in trouble later on.
+  This sometimes means you'll have to unlearn best practices you might have
+  picked up in your current or past work.
+
+
+A Different Way to Model Your Data
+==================================
+
+We believe that CouchDB will drastically change the way you build
+document-based applications. CouchDB combines an intuitive document storage
+model with a powerful query engine in a way that's so simple you'll probably
+be tempted to ask, “Why has no one built something like this before?”
+
+    Django may be built for the Web, but CouchDB is built of the Web. I've
+    never seen software that so completely embraces the philosophies behind
+    HTTP. CouchDB makes Django look old-school in the same way that Django
+    makes ASP look outdated.
+
+    -- Jacob Kaplan-Moss, Django developer
+
+CouchDB's design borrows heavily from web architecture and the concepts of
+resources, methods, and representations. It augments this with powerful ways
+to query, map, combine, and filter your data. Add fault tolerance, extreme
+scalability, and incremental replication, and CouchDB defines a sweet spot
+for document databases.
+
+
+A Better Fit for Common Applications
+====================================
+
+We write software to improve our lives and the lives of others. Usually this
+involves taking some mundane information such as contacts, invoices,
+or receipts and manipulating it using a computer application. CouchDB is a
+great fit for common applications like this because it embraces the natural
+idea of evolving, self-contained documents as the very core of its data model.
+
+
+Self-Contained Data
+-------------------
+
+An invoice contains all the pertinent information about a single transaction
+the seller, the buyer, the date, and a list of the items or services sold.
+As shown in :ref:`intro/why-01`, there's no abstract reference on this
+piece of paper that points to some other piece of paper with the seller's
+name and address. Accountants appreciate the simplicity of having everything
+in one place. And given the choice, programmers appreciate that, too.
+
+
+.. _intro/why-01:
+
+.. figure:: ../../images/intro-why-01.png
+   :align: center
+   :alt: Self-contained documents
+
+   Figure 1. Self-contained documents
+
+
+Yet using references is exactly how we model our data in a relational
+database! Each invoice is stored in a table as a row that refers to other
+rows in other tables one row for seller information, one for the buyer,
+one row for each item billed, and more rows still to describe the item
+details, manufacturer details, and so on and so forth.
+
+This isn't meant as a detraction of the relational model, which is widely
+applicable and extremely useful for a number of reasons. Hopefully, though, it
+illustrates the point that sometimes your model may not “fit” your data
+in the way it occurs in the real world.
+
+Let's take a look at the humble contact database to illustrate a different
+way of modeling data, one that more closely “fits” its real-world counterpart
+-- a pile of business cards. Much like our invoice example, a business card
+contains all the important information, right there on the cardstock.
+We call this “self-contained” data, and it's an important concept
+in understanding document databases like CouchDB.
+
+
+Syntax and Semantics
+--------------------
+
+Most business cards contain roughly the same information -- someone's identity,
+an affiliation, and some contact information. While the exact form of this
+information can vary between business cards, the general information being
+conveyed remains the same, and we're easily able to recognize it as a
+business card. In this sense, we can describe a business card as a *real-world
+document*.
+
+Jan's business card might contain a phone number but no fax number,
+whereas J. Chris's business card contains both a phone and a fax number. Jan
+does not have to make his lack of a fax machine explicit by writing something
+as ridiculous as “Fax: None” on the business card. Instead, simply omitting
+a fax number implies that he doesn't have one.
+
+We can see that real-world documents of the same type, such as business cards,
+tend to be very similar in *semantics* -- the sort of information they carry,
+but can vary hugely in *syntax*, or how that information is structured. As human
+beings, we're naturally comfortable dealing with this kind of variation.
+
+While a traditional relational database requires you to model your data
+*up front*, CouchDB's schema-free design unburdens you with a powerful way to
+aggregate your data *after the fact*, just like we do with real-world
+documents. We'll look in depth at how to design applications with this
+underlying storage paradigm.
+
+
+Building Blocks for Larger Systems
+==================================
+
+CouchDB is a storage system useful on its own. You can build many applications
+with the tools CouchDB gives you. But CouchDB is designed with a bigger picture
+in mind. Its components can be used as building blocks that solve storage
+problems in slightly different ways for larger and more complex systems.
+
+Whether you need a system that's crazy fast but isn't too concerned with
+reliability (think logging), or one that guarantees storage in two or more
+physically separated locations for reliability, but you're willing to take a
+performance hit, CouchDB lets you build these systems.
+
+There are a multitude of knobs you could turn to make a system work better in
+one area, but you'll affect another area when doing so. One example would be
+the CAP theorem discussed in the next chapter. To give you an idea of other
+things that affect storage systems, see :ref:`Figure 2 <intro/why-figure-02>`
+and :ref:`Figure 3 <intro/why-figure-03>`.
+
+By reducing latency for a given system (and that is true not only for storage
+systems), you affect concurrency and throughput capabilities.
+
+
+.. _intro/why-figure-02:
+
+.. figure:: ../../images/intro-why-02.png
+   :align: center
+   :alt: Throughput, latency, or concurrency
+
+   Figure 2. Throughput, latency, or concurrency
+
+
+.. _intro/why-figure-03:
+
+.. figure:: ../../images/intro-why-03.png
+   :align: center
+   :alt: Scaling: read requests, write requests, or data
+
+   Figure 3. Scaling: read requests, write requests, or data
+
+
+When you want to scale out, there are three distinct issues to deal with:
+scaling read requests, write requests, and data. Orthogonal to all three and
+to the items shown in :ref:`Figure 2 <intro/why-figure-02>` and :ref:`Figure 3
+<intro/why-figure-03>` are many more attributes like reliability or simplicity.
+You can draw many of these graphs that show how different features or attributes
+pull into different directions and thus shape the system they describe.
+
+CouchDB is very flexible and gives you enough building blocks to create a
+system shaped to suit your exact problem. That's not saying that CouchDB can
+be bent to solve any problem -- CouchDB is no silver bullet -- but in the
+area of data storage, it can get you a long way.
+
+
+CouchDB Replication
+===================
+
+CouchDB replication is one of these building blocks. Its fundamental function
+is to synchronize two or more CouchDB databases. This may sound simple,
+but the simplicity is key to allowing replication to solve a number of
+problems: reliably synchronize databases between multiple machines for
+redundant data storage; distribute data to a cluster of CouchDB instances
+that share a subset of the total number of requests that hit the cluster
+(load balancing); and distribute data between physically distant locations,
+such as one office in New York and another in Tokyo.
+
+CouchDB replication uses the same REST API all clients use. HTTP is
+ubiquitous and well understood. Replication works incrementally; that is,
+if during replication anything goes wrong, like dropping your network
+connection, it will pick up where it left off the next time it runs. It also
+only transfers data that is needed to synchronize databases.
+
+A core assumption CouchDB makes is that things can go wrong,
+like network connection troubles, and it is designed for graceful error
+recovery instead of assuming all will be well. The replication system's
+incremental design shows that best. The ideas behind “things that can go
+wrong” are embodied in the `Fallacies of Distributed Computing`_:
+
+- The network is reliable.
+- Latency is zero.
+- Bandwidth is infinite.
+- The network is secure.
+- Topology doesn't change.
+- There is one administrator.
+- Transport cost is zero.
+- The network is homogeneous.
+
+Existing tools often try to hide the fact that there is a network and that
+any or all of the previous conditions don't exist for a particular system.
+This usually results in fatal error scenarios when something finally goes
+wrong. In contrast, CouchDB doesn't try to hide the network; it just handles
+errors gracefully and lets you know when actions on your end are required.
+
+.. _Fallacies of Distributed Computing: http://en.wikipedia.org/wiki/Fallacies_of_Distributed_Computing
+
+
+Local Data Is King
+==================
+
+CouchDB takes quite a few lessons learned from the Web,
+but there is one thing that could be improved about the Web: latency.
+Whenever you have to wait for an application to respond or a website to
+render, you almost always wait for a network connection that isn't as fast as
+you want it at that point. Waiting a few seconds instead of milliseconds
+greatly affects user experience and thus user satisfaction.
+
+What do you do when you are offline? This happens all the time -- your DSL or
+cable provider has issues, or your iPhone, G1, or Blackberry has no bars,
+and no connectivity means no way to get to your data.
+
+CouchDB can solve this scenario as well, and this is where scaling is
+important again. This time it is scaling down. Imagine CouchDB installed on
+phones and other mobile devices that can synchronize data with centrally
+hosted CouchDBs when they are on a network. The synchronization is not bound
+by user interface constraints like subsecond response times. It is easier to
+tune for high bandwidth and higher latency than for low bandwidth and very
+low latency. Mobile applications can then use the local CouchDB to fetch
+data, and since no remote networking is required for that,
+latency is low by default.
+
+Can you really use CouchDB on a phone? Erlang, CouchDB's implementation
+language has been designed to run on embedded devices magnitudes smaller and
+less powerful than today's phones.
+
+
+Wrapping Up
+===========
+
+The next chapter further explores the distributed nature of CouchDB. We
+should have given you enough bites to whet your interest. Let's go!