# Count things

`POST /api/2/search/things/count`

This resource can be used to count things.

The parameter `filter` is not mandatory. If it is not set there is
returned the total amount of things which the logged in user is allowed
to read.

To search for nested properties, we use JSON Pointer notation
(RFC-6901). See the following example how to search for the sub property
`location` of the parent property `attributes` with a forward slash as
separator:

```eq(attributes/location,"kitchen")```

Authentication (security requirement alternatives):

```json
[
  {
    "OpenIDConnect": []
  },
  {
    "NginxBasic": []
  },
  {
    "Bearer": []
  }
]
```

- OpenIDConnect: openIdConnect. OpenID Connect Discovery URL. The placeholder is replaced by Swagger UI when configured.
- NginxBasic: http (basic). Eclipse Ditto sandbox demo user (demo1 ... demo9) + password (demo)
- Bearer: http (bearer). A JSON Web Token issued by a supported OAuth 2.0 Identity Provider.

Request body: application/x-www-form-urlencoded

Type: object

- `filter` (optional)
  Reference: [SearchFilterProperty](https://sourcey-ditto.pages.dev/http-api-doc/models/searchfilterproperty.md); Type: SearchFilterProperty
  
  
  #### Filter predicates:
  
  * ```eq({property},{value})```  (i.e. equal to the given value)
  
  * ```ne({property},{value})```  (i.e. not equal to the given value)
  
  * ```gt({property},{value})```  (i.e. greater than the given value)
  
  * ```ge({property},{value})```  (i.e. equal to the given value or greater than it)
  
  * ```lt({property},{value})```  (i.e. lower than the given value or equal to it)
  
  * ```le({property},{value})```  (i.e. lower than the given value)
  
  * ```in({property},{value},{value},...)```  (i.e. contains at least one of the values listed)
  
  * ```like({property},{value})```  (i.e. contains values similar to the expressions listed)
  
  * ```ilike({property},{value})```  (i.e. contains values similar and case insensitive to the expressions listed)
  
  * ```exists({property})```  (i.e. all things in which the given path exists)
  
  * ```empty({property})```  (i.e. all things in which the given path is absent, null, an empty array, an empty object or an empty string)
  
  
  Note: When using filter operations, only things with the specified properties are returned.
  For example, the filter `ne(attributes/owner, "SID123")` will only return things that do have
  the `owner` attribute.
  
  
  #### Logical operations:
  
  
  * ```and({query},{query},...)```
  
  * ```or({query},{query},...)```
  
  * ```not({query})```
  
  
  #### Examples:
  
  * ```eq(attributes/location,"kitchen")```
  
  * ```ge(thingId,"myThing1")```
  
  * ```gt(_created,"2020-08-05T12:17")```
  
  * ```exists(features/featureId)```
  
  * ```empty(attributes/tags)```
  
  * ```and(eq(attributes/location,"kitchen"),eq(attributes/color,"red"))```
  
  * ```or(eq(attributes/location,"kitchen"),eq(attributes/location,"living-room"))```
  
  * ```like(attributes/key1,"known-chars-at-start*")```
  
  * ```like(attributes/key1,"*known-chars-at-end")```
  
  * ```like(attributes/key1,"*known-chars-in-between*")```
  
  * ```like(attributes/key1,"just-som?-char?-unkn?wn")```
  
  The `like` filters with the wildcard `*` at the beginning can slow down your search request.

- `namespaces` (optional)
  Reference: [NamespaceProperty](https://sourcey-ditto.pages.dev/http-api-doc/models/namespaceproperty.md); Type: NamespaceProperty
  
  A comma-separated list of namespaces. This list is used to limit the query to things in the given namespaces
  only.
  
  
  #### Examples:
  
  * `?namespaces=com.example.namespace`
  
  * `?namespaces=com.example.namespace1,com.example.namespace2`

```json
{
  "filter": "and(like(definition,\"*test*\"))",
  "namespaces": "org.eclipse.ditto,foo.bar"
}
```

Responses:

- 200: A number indicating the amount of matched things

Content type: application/json

Type: integer

- 400: The request could not be completed. A provided parameter is in a
wrong format.

Content type: application/json

Type: AdvancedError

Schema: [AdvancedError](https://sourcey-ditto.pages.dev/http-api-doc/models/advancederror.md)

- `status` (required)
  Type: integer
  
  The HTTP status of the error

- `error` (required)
  Type: string
  
  The error code of the occurred exception

- `message` (required)
  Type: string
  
  The message of the error - what went wrong

- `description` (optional)
  Type: string
  
  A description how to fix the error or more details

- `href` (optional)
  Type: string
  
  A link to further information about the error and how to fix it

- 401: The request could not be completed due to missing authentication.

Content type: application/json

Type: AdvancedError

Schema: [AdvancedError](https://sourcey-ditto.pages.dev/http-api-doc/models/advancederror.md)

- `status` (required)
  Type: integer
  
  The HTTP status of the error

- `error` (required)
  Type: string
  
  The error code of the occurred exception

- `message` (required)
  Type: string
  
  The message of the error - what went wrong

- `description` (optional)
  Type: string
  
  A description how to fix the error or more details

- `href` (optional)
  Type: string
  
  A link to further information about the error and how to fix it

- 403: The request could not be completed due to an invalid authentication.

Content type: application/json

Type: AdvancedError

Schema: [AdvancedError](https://sourcey-ditto.pages.dev/http-api-doc/models/advancederror.md)

- `status` (required)
  Type: integer
  
  The HTTP status of the error

- `error` (required)
  Type: string
  
  The error code of the occurred exception

- `message` (required)
  Type: string
  
  The message of the error - what went wrong

- `description` (optional)
  Type: string
  
  A description how to fix the error or more details

- `href` (optional)
  Type: string
  
  A link to further information about the error and how to fix it

- 504: The request ran out of time to execute on the the back-end. Optimize your query and try again.

Content type: application/json

Type: AdvancedError

Schema: [AdvancedError](https://sourcey-ditto.pages.dev/http-api-doc/models/advancederror.md)

- `status` (required)
  Type: integer
  
  The HTTP status of the error

- `error` (required)
  Type: string
  
  The error code of the occurred exception

- `message` (required)
  Type: string
  
  The message of the error - what went wrong

- `description` (optional)
  Type: string
  
  A description how to fix the error or more details

- `href` (optional)
  Type: string
  
  A link to further information about the error and how to fix it

## Examples

### cURL

```bash
curl -X POST 'https://ditto.eclipseprojects.io/api/2/search/things/count' \
  -H 'Authorization: Bearer YOUR_TOKEN' \
  -H 'Content-Type: application/x-www-form-urlencoded' \
  --data-raw 'filter=and%28like%28definition%2C%22%2Atest%2A%22%29%29&namespaces=org.eclipse.ditto%2Cfoo.bar'
```

### JavaScript

```javascript
const response = await fetch('https://ditto.eclipseprojects.io/api/2/search/things/count', {
  method: 'POST',
  headers: {
    'Authorization': 'Bearer YOUR_TOKEN',
    'Content-Type': 'application/x-www-form-urlencoded',
  },
  body: 'filter=and%28like%28definition%2C%22%2Atest%2A%22%29%29&namespaces=org.eclipse.ditto%2Cfoo.bar',
});

const data = await response.text();
```

### Python

```python
import requests

response = requests.post(
    'https://ditto.eclipseprojects.io/api/2/search/things/count',
    data='filter=and%28like%28definition%2C%22%2Atest%2A%22%29%29&namespaces=org.eclipse.ditto%2Cfoo.bar'.encode('utf-8'),
    headers={
        'Authorization': 'Bearer YOUR_TOKEN',
        'Content-Type': 'application/x-www-form-urlencoded',
    },
)
print(response.text)
```
