1

I've got race participant data in some documents, organized by race stage, runner position, and the time the runner passed through the stage.

I need to find a particular bib (?key=357) and grab the last time it went through a stage (doc.bib_data[i].time), which stage it was (id) and the position (i).

If I specify a particular bib_data array index, I get results, but if I loop through the bib_data, I don't get any results, even if I don't filter for anything.

VIEW with a specific index, to show what the document data looks like:

function (doc, meta) {
  emit(doc.bib_data[2].bib,doc.bib_data[2].time);
}

RESULT:

{
 "id": "007",
 "key": "357",
 "value": "1910:38",
 "doc": {
  "_id": "007",
  "_rev": "4-bdce057c8ad2ce975b9ffca9eb9dfd82",
  "ew_ham": "KM6WKA",
  "stage_ew_ham": "KK6DA",
  "bib_data": {
   "1": {
    "bib": "45",
    "time": "1910:35"
   },
   "2": {
    "bib": "357",
    "time": "1910:38"
   },
   "3": {
    "bib": "22",
    "time": "1910:40"
   }
  }
 }
}

How do I get results ONLY for "bib:357"?

I need to collect the stage, the position and the time, i.e. ["007","2","1910:38"]

   "2": {
    "bib": "357",
    "time": "1910:38"
   },

Here's my current QUERY:

http://[IP_ADDR]:5984/[DB_NAME]/_design/[DESIGN_DOC]/_view/[VIEW_NAME]?key=123

And my VIEW that attempts to loop through bib_data:

function (doc, meta) {
  for(i=0;i<doc.bib_data.length;i++) {
    if(doc.bib_data[i].bib) {
      emit( i, doc.bib_data[i].bib, doc.bib_data[i].time );
    }
  }
}

Which returns no results.

1 Answer 1

1

The view code

function(doc, meta) {
  for (i = 0; i < doc.bib_data.length; i++) {
    if (doc.bib_data[i].bib) {
      emit(i, doc.bib_data[i].bib, doc.bib_data[i].time);
    }
  }
}

Is totally incorrect as it is an attempt to index iterate bib_data as if it were an array but it's an object. So fix that first [1]:

function (doc) {
  for (var key in doc.bib_data) {
    if (doc.bib_data.hasOwnProperty(key)) {
      var item = doc.bib_data[key];
      /* do something with the bib item. */
    }
  }
}

Now it's time to emit the data of interest. It's not super clear what is desired from your post, but here's a start, noting I am emitting what appear to be numbers as numbers not strings:

function (doc) {
  for (var key in doc.bib_data) {
    if (doc.bib_data.hasOwnProperty(key)) {
      var item = doc.bib_data[key];
      if(item.bib) {
        emit([parseInt(item.bib), parseInt(key), item.time]);
      }
    }
  }
}

Given the doc you posted as the only doc in the database with design doc and view name as bib using cURL:

curl -G <url to db>/_design/bib/_view/bib

will return

{ "total_rows":3,"offset":0,"rows":[
  {"id": "007", "key": [22,3,"1910:40"], "value": null},
  {"id": "007", "key": [45,1,"1910:35"], "value": null},
  {"id": "007", "key": [357,2,"1910:38"], "value": null}
]}

Because the bib view is generating a complex key one must query[2] using start_key and end_key. So to get view documents with a bib of 357

 curl -G <url to db>/_design/bib/_view/bib -d "start_key=[357]" -d "end_key=[357,{}]"

will return

{"total_rows":3,"offset":2,"rows":[
{"id":"007","key":[357,2,"1910:38"],"value":null}
]}

I am not seeing much utility with incorporating the index/key - maybe you want this instead?

emit([parseInt(item.bib), item.time], parseInt(key));


1 Iterate through object properties
2 /{db}/_design/{ddoc}/_view/{view}

Sign up to request clarification or add additional context in comments.

2 Comments

Thank you, RamblinRose! You really cleared it up, for me.
To expand on my comment: You cleared it up for me in that I'm working with an object, rather than an array, and in helping me to understand the couchdb syntax for getting at what I needed. I'm a bit of an idiot for not seeing the object notation ... In re: index/key: That's the Stage indicator. So ... 09m = 1 mile out from the Stage, 09k = 200 meters out and 009 = the Stage marker. I want to pull the most-recent entry in the doc to be able to see where the runner was last recorded. Thanks, again.

Your Answer

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

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.