Aggregation $out stage creates collection, all queries return TypeError: db.collection.. is not a function

My goal is to create a materialized view using an aggregation on an existing collection. I was following this presentation - Materialized Pre-Aggregations for Exploratory Analytics Queries. There’s an accompanying Github repo

I’ve tried these approaches:

  1. MongoDB Compass Aggregation Pipeline Builder
  2. mongosh shell

Both created a collection, which I verified via the Compass UI, the Atlas UI and the mongosh shell. It’s visible when running the command db.getCollectionNames and getCollectionInfos and it’s visible in both Compass and Atlas.


Collection info from mongosh terminal

Running db.stats.findOne() outputs this:
TypeError: db.stats.findOne is not a function

This is the pipeline

[
  {
    $addFields:
      {
        processed: {
          $dateFromString: {
            dateString: {
              $replaceOne: {
                input:
                  "$__dc_process.last_updated",
                find: "@",
                replacement: "",
              },
            },
          },
        },
      },
  },
  {
    $sort:
      {
        processed: -1,
      },
  },
  {
    $group:
      {
        _id: {
          "campaign": "$_projectId",
          "bot": "$bot",
          "render-status": "$render-status",
          "stream-status": "$stream.status",
          "processor": "$__dc_process.satellite",
        },
        "total": {
          $count: {},
        },
        "last_updated": {
          $first: "$processed",
        },
        "last_updated_job": {
          $first: "$$ROOT",
        },
      },
  },
  {
    $out: "stats",
  },
]

I’ve tried disconnecting and reconnecting the shell. In the UI for Compass and Atlas, querying does work and returns a result.

I’m not really sure if the fact that the group stage is not first has any effect? The presenter notes that you should not do any filtering beforehand, but I haven’t done that here.

Any advice?

You chose a collection name, stats, that collide with a function of the db object. This means you will not be able to use the short cut db.stats to get the collection. You will need to use the getCollection() function like:

db.getCollection( "stats" ).findOne()
2 Likes

That was it!!! The above command works perfectly, and I’ll be more careful when naming next time.

1 Like

I prefer to use getCollection in the code. I use the short-cut only in mongosh. So most of the time, special names, like names with dash or names with space, are not an issue.

This topic was automatically closed 5 days after the last reply. New replies are no longer allowed.