Details

    • Type: New Feature
    • Status: Resolved
    • Priority: Major - P3
    • Resolution: Fixed
    • Affects Version/s: 2.1.1
    • Fix Version/s: 3.1.6
    • Component/s: Aggregation Framework
    • Labels:
      None
    • Backwards Compatibility:
      Minor Change

      Description

      Aggregation $project stage should support $slice operator on array fields similar to $slice in projection and syntax similar to aggregation $substr operator:

      { "$project" : { "newArray" : { "$slice" : [ "$oldarray" , 10, 4 ] } } }
      

      The above would take 4 elements from oldarray starting at position 10 (akin to "skipping first ten elements, as position is 0 based).

      Original description:

      If I have a document with an array of values in it, I would like to be able to project a slice of those values while aggregating.

      { title: "A doc",
        intervals: [
          { value: 1, foo: true, bar: false },
          { value: 2, foo: false, bar: true },
          { value: 3, foo: true, bar: false}
        ]
      }
      

      $project with a $slice should work as expected:

      { $project : {
          title: 1,
          fewerIntervals: {intervals:{$slice:2}}
        }
      }
      

      results in a pipelined document =>

      { title: "A doc",
        fewerIntervals: [
          { value: 1, foo: true, bar: false },
          { value: 2, foo: false, bar: true }
        ]
      }
      

      Similarly, the remainder of the existing $slice syntax should work as expected.

      { $project : {
          title: 1,
          fewerIntervals: {intervals:{$slice:[1,1]}}
        }
      }
      

      should produce

      { title: "A doc",
        fewerIntervals: [
          { value: 2, foo: false, bar: true }
        ]
      }
      

        Issue Links

          Activity

          Hide
          SamV Sam Verschueren added a comment -

          Is there a workaround for this issue? I have a lot of data and I only need the 10 first elements in the array when I aggregate.

          Show
          SamV Sam Verschueren added a comment - Is there a workaround for this issue? I have a lot of data and I only need the 10 first elements in the array when I aggregate.
          Hide
          yoo yogesh added a comment -

          Any one found solution regarding this ?

          Show
          yoo yogesh added a comment - Any one found solution regarding this ?
          Hide
          ramon.fernandez Ramon Fernandez added a comment -

          All, as you can see in the "Fix Version/s" field this functionality has been scheduled for the upcoming development release 3.1.4, due in the coming weeks. At the time of this writing this feature is in code review, so we expect to be able to merge the code into master very soon.

          Regards,
          Ramón.

          Show
          ramon.fernandez Ramon Fernandez added a comment - All, as you can see in the "Fix Version/s" field this functionality has been scheduled for the upcoming development release 3.1.4, due in the coming weeks. At the time of this writing this feature is in code review, so we expect to be able to merge the code into master very soon. Regards, Ramón.
          Hide
          xgen-internal-githook Githook User added a comment -

          Author:

          {u'username': u'cswanson310', u'name': u'Charlie Swanson', u'email': u'charlie.swanson@mongodb.com'}

          Message: SERVER-6074 Add $slice aggregation expression
          Branch: master
          https://github.com/mongodb/mongo/commit/1e1bbec4cb0d9b8b418f9564dafba52d5e7417dd

          Show
          xgen-internal-githook Githook User added a comment - Author: {u'username': u'cswanson310', u'name': u'Charlie Swanson', u'email': u'charlie.swanson@mongodb.com'} Message: SERVER-6074 Add $slice aggregation expression Branch: master https://github.com/mongodb/mongo/commit/1e1bbec4cb0d9b8b418f9564dafba52d5e7417dd
          Hide
          charlie.swanson Charlie Swanson added a comment -

          The new operator is called $slice. It takes either 2 or 3 arguments. In the two argument form, the first argument is the array to slice, and the second argument is the count of the number of elements to slice (positive or negative). Here are some examples of the two argument form:

          > db.foo.drop()
          > db.foo.insert({})
          > db.foo.aggregate([{$project: {_id: 0, slice: {$slice: [[0,1,2,3], 2]}}}])
          { "slice" : [ 0, 1 ] }
          > db.foo.aggregate([{$project: {_id: 0, slice: {$slice: [[0,1,2,3], -2]}}}])
          { "slice" : [ 2, 3 ] }
          

          In the three argument form, the first argument is the array to slice, the second argument is the index from which to start the slice, and the third argument is the count of the number of elements to slice. Here are some examples of the three argument form:

          > db.foo.aggregate([{$project: {_id: 0, slice: {$slice: [[0,1,2,3], 1, 2]}}}])
          { "slice" : [ 1, 2 ] }
          > db.foo.aggregate([{$project: {_id: 0, slice: {$slice: [[0,1,2,3], -2, 1]}}}])
          { "slice" : [ 2 ] }
          > db.foo.aggregate([{$project: {_id: 0, slice: {$slice: [[0,1,2,3], -2, 10]}}}])
          { "slice" : [ 2, 3 ] }
          

          See the test in the commit for more details.

          Show
          charlie.swanson Charlie Swanson added a comment - The new operator is called $slice . It takes either 2 or 3 arguments. In the two argument form, the first argument is the array to slice, and the second argument is the count of the number of elements to slice (positive or negative). Here are some examples of the two argument form: > db.foo.drop() > db.foo.insert({}) > db.foo.aggregate([{$project: {_id: 0, slice: {$slice: [[0,1,2,3], 2]}}}]) { "slice" : [ 0, 1 ] } > db.foo.aggregate([{$project: {_id: 0, slice: {$slice: [[0,1,2,3], -2]}}}]) { "slice" : [ 2, 3 ] } In the three argument form, the first argument is the array to slice, the second argument is the index from which to start the slice, and the third argument is the count of the number of elements to slice. Here are some examples of the three argument form: > db.foo.aggregate([{$project: {_id: 0, slice: {$slice: [[0,1,2,3], 1, 2]}}}]) { "slice" : [ 1, 2 ] } > db.foo.aggregate([{$project: {_id: 0, slice: {$slice: [[0,1,2,3], -2, 1]}}}]) { "slice" : [ 2 ] } > db.foo.aggregate([{$project: {_id: 0, slice: {$slice: [[0,1,2,3], -2, 10]}}}]) { "slice" : [ 2, 3 ] } See the test in the commit for more details.

            People

            • Votes:
              58 Vote for this issue
              Watchers:
              48 Start watching this issue

              Dates

              • Created:
                Updated:
                Resolved:
                Days since reply:
                6 weeks, 4 days ago
                Date of 1st Reply:

                Agile