We are currently solving the following issue within our repository. Here is the issue text:
--- BEGIN ISSUE ---
Datastore dump results are not the same as data in database
### CKAN Version if known (or site URL)
2.7.2

### Please describe the expected behaviour
Downloaded dataset is not consistent with the actual data! 

### Please describe the actual behaviour
We've upserted data using datastore api. The data is shown correctly in data explorer, Table view, API call or even querying postgres, But the data in downloaded csv file is different! Total number of records are the same but in csv we have random number of duplicates and missing data.

### What steps can be taken to reproduce the issue? 
Upsert data using API. Download the CSV file using URL. Filter and compare downloaded data and data shown in data explorer or table view.

--- END ISSUE ---

Below are some code segments, each from a relevant file. One or more of these files may contain bugs.
--- BEGIN FILES ---
Path: `ckanext/datastore/controller.py`
Content:
```
1 # encoding: utf-8
2 
3 from ckan.plugins.toolkit import (
4     Invalid,
5     ObjectNotFound,
6     NotAuthorized,
7     get_action,
8     get_validator,
9     _,
10     request,
11     response,
12     BaseController,
13     abort,
14     render,
15     c,
16     h,
17 )
18 from ckanext.datastore.writer import (
19     csv_writer,
20     tsv_writer,
21     json_writer,
22     xml_writer,
23 )
24 from ckan.logic import (
25     tuplize_dict,
26     parse_params,
27 )
28 import ckan.lib.navl.dictization_functions as dict_fns
29 
30 from itertools import izip_longest
31 
32 int_validator = get_validator('int_validator')
33 boolean_validator = get_validator('boolean_validator')
34 
35 DUMP_FORMATS = 'csv', 'tsv', 'json', 'xml'
36 PAGINATE_BY = 32000
37 
38 
39 class DatastoreController(BaseController):
40     def dump(self, resource_id):
41         try:
42             offset = int_validator(request.GET.get('offset', 0), {})
43         except Invalid as e:
44             abort(400, u'offset: ' + e.error)
45         try:
46             limit = int_validator(request.GET.get('limit'), {})
47         except Invalid as e:
48             abort(400, u'limit: ' + e.error)
49         bom = boolean_validator(request.GET.get('bom'), {})
50         fmt = request.GET.get('format', 'csv')
51 
52         if fmt not in DUMP_FORMATS:
53             abort(400, _(
54                 u'format: must be one of %s') % u', '.join(DUMP_FORMATS))
55 
56         try:
57             dump_to(
58                 resource_id,
59                 response,
60                 fmt=fmt,
61                 offset=offset,
62                 limit=limit,
63                 options={u'bom': bom})
64         except ObjectNotFound:
65             abort(404, _('DataStore resource not found'))
66 
67     def dictionary(self, id, resource_id):
68         u'''data dictionary view: show/edit field labels and descriptions'''
69 
70         try:
71             # resource_edit_base template uses these
72             c.pkg_dict = get_action('package_show')(
73                 None, {'id': id})
74             c.resource = get_action('resource_show')(
75                 None, {'id': resource_id})
76             rec = get_action('datastore_search')(None, {
77                 'resource_id': resource_id,
78                 'limit': 0})
79         except (ObjectNotFound, NotAuthorized):
80             abort(404, _('Resource not found'))
81 
82         fields = [f for f in rec['fields'] if not f['id'].startswith('_')]
83 
84         if request.method == 'POST':
85             data = dict_fns.unflatten(tuplize_dict(parse_params(
86                 request.params)))
87             info = data.get(u'info')
88             if not isinstance(info, list):
89                 info = []
90             info = info[:len(fields)]
91 
92             get_action('datastore_create')(None, {
93                 'resource_id': resource_id,
94                 'force': True,
95                 'fields': [{
96                     'id': f['id'],
97                     'type': f['type'],
98                     'info': fi if isinstance(fi, dict) else {}
99                     } for f, fi in izip_longest(fields, info)]})
100 
101             h.flash_success(_('Data Dictionary saved. Any type overrides will '
102                               'take effect when the resource is next uploaded '
103                               'to DataStore'))
104             h.redirect_to(
105                 controller='ckanext.datastore.controller:DatastoreController',
106                 action='dictionary',
107                 id=id,
108                 resource_id=resource_id)
109 
110         return render(
111             'datastore/dictionary.html',
112             extra_vars={'fields': fields})
113 
114 
115 def dump_to(resource_id, output, fmt, offset, limit, options):
116     if fmt == 'csv':
117         writer_factory = csv_writer
118         records_format = 'csv'
119     elif fmt == 'tsv':
120         writer_factory = tsv_writer
121         records_format = 'tsv'
122     elif fmt == 'json':
123         writer_factory = json_writer
124         records_format = 'lists'
125     elif fmt == 'xml':
126         writer_factory = xml_writer
127         records_format = 'objects'
128 
129     def start_writer(fields):
130         bom = options.get(u'bom', False)
131         return writer_factory(output, fields, resource_id, bom)
132 
133     def result_page(offs, lim):
134         return get_action('datastore_search')(None, {
135             'resource_id': resource_id,
136             'limit':
137                 PAGINATE_BY if limit is None
138                 else min(PAGINATE_BY, lim),
139             'offset': offs,
140             'records_format': records_format,
141             'include_total': 'false',  # XXX: default() is broken
142         })
143 
144     result = result_page(offset, limit)
145 
146     with start_writer(result['fields']) as wr:
147         while True:
148             if limit is not None and limit <= 0:
149                 break
150 
151             records = result['records']
152 
153             wr.write_records(records)
154 
155             if records_format == 'objects' or records_format == 'lists':
156                 if len(records) < PAGINATE_BY:
157                     break
158             elif not records:
159                 break
160 
161             offset += PAGINATE_BY
162             if limit is not None:
163                 limit -= PAGINATE_BY
164                 if limit <= 0:
165                     break
166 
167             result = result_page(offset, limit)
168
```
--- END FILES ---

Please first localize the bug based on the issue statement, and then generate a patch according to the `git diff` format fenced by three backticks.

Here is an example:

```diff
diff --git a/examples/server_async.py b/examples/server_async.py
--- a/examples/server_async.py
+++ b/examples/server_async.py
@@ -313,4 +313,4 @@
 
 
 if __name__ == "__main__":
-    asyncio.run(run_async_server("."), debug=True)
+    asyncio.run(run_async_server(), debug=True)
diff --git a/examples/server_sync.py b/examples/server_sync.py
--- a/examples/server_sync.py
+++ b/examples/server_sync.py
@@ -313,5 +313,5 @@
 
 
 if __name__ == "__main__":
-    server = run_sync_server(".")
+    server = run_sync_server()
     server.shutdown()

```

diff --git a/ckanext/datastore/controller.py b/ckanext/datastore/controller.py
--- a/ckanext/datastore/controller.py
+++ b/ckanext/datastore/controller.py
@@ -137,6 +137,7 @@
                 PAGINATE_BY if limit is None
                 else min(PAGINATE_BY, lim),
             'offset': offs,
+            'sort': '_id',
             'records_format': records_format,
             'include_total': 'false',  # XXX: default() is broken
         })

{"golden_diff": "diff --git a/ckanext/datastore/controller.py b/ckanext/datastore/controller.py\n--- a/ckanext/datastore/controller.py\n+++ b/ckanext/datastore/controller.py\n@@ -137,6 +137,7 @@\n                 PAGINATE_BY if limit is None\n                 else min(PAGINATE_BY, lim),\n             'offset': offs,\n+            'sort': '_id',\n             'records_format': records_format,\n             'include_total': 'false',  # XXX: default() is broken\n         })\n", "issue": "Datastore dump results are not the same as data in database\n### CKAN Version if known (or site URL)\r\n2.7.2\r\n\r\n### Please describe the expected behaviour\r\nDownloaded dataset is not consistent with the actual data! \r\n\r\n### Please describe the actual behaviour\r\nWe've upserted data using datastore api. The data is shown correctly in data explorer, Table view, API call or even querying postgres, But the data in downloaded csv file is different! Total number of records are the same but in csv we have random number of duplicates and missing data.\r\n\r\n### What steps can be taken to reproduce the issue? \r\nUpsert data using API. Download the CSV file using URL. Filter and compare downloaded data and data shown in data explorer or table view.\n", "before_files": [{"content": "# encoding: utf-8\n\nfrom ckan.plugins.toolkit import (\n    Invalid,\n    ObjectNotFound,\n    NotAuthorized,\n    get_action,\n    get_validator,\n    _,\n    request,\n    response,\n    BaseController,\n    abort,\n    render,\n    c,\n    h,\n)\nfrom ckanext.datastore.writer import (\n    csv_writer,\n    tsv_writer,\n    json_writer,\n    xml_writer,\n)\nfrom ckan.logic import (\n    tuplize_dict,\n    parse_params,\n)\nimport ckan.lib.navl.dictization_functions as dict_fns\n\nfrom itertools import izip_longest\n\nint_validator = get_validator('int_validator')\nboolean_validator = get_validator('boolean_validator')\n\nDUMP_FORMATS = 'csv', 'tsv', 'json', 'xml'\nPAGINATE_BY = 32000\n\n\nclass DatastoreController(BaseController):\n    def dump(self, resource_id):\n        try:\n            offset = int_validator(request.GET.get('offset', 0), {})\n        except Invalid as e:\n            abort(400, u'offset: ' + e.error)\n        try:\n            limit = int_validator(request.GET.get('limit'), {})\n        except Invalid as e:\n            abort(400, u'limit: ' + e.error)\n        bom = boolean_validator(request.GET.get('bom'), {})\n        fmt = request.GET.get('format', 'csv')\n\n        if fmt not in DUMP_FORMATS:\n            abort(400, _(\n                u'format: must be one of %s') % u', '.join(DUMP_FORMATS))\n\n        try:\n            dump_to(\n                resource_id,\n                response,\n                fmt=fmt,\n                offset=offset,\n                limit=limit,\n                options={u'bom': bom})\n        except ObjectNotFound:\n            abort(404, _('DataStore resource not found'))\n\n    def dictionary(self, id, resource_id):\n        u'''data dictionary view: show/edit field labels and descriptions'''\n\n        try:\n            # resource_edit_base template uses these\n            c.pkg_dict = get_action('package_show')(\n                None, {'id': id})\n            c.resource = get_action('resource_show')(\n                None, {'id': resource_id})\n            rec = get_action('datastore_search')(None, {\n                'resource_id': resource_id,\n                'limit': 0})\n        except (ObjectNotFound, NotAuthorized):\n            abort(404, _('Resource not found'))\n\n        fields = [f for f in rec['fields'] if not f['id'].startswith('_')]\n\n        if request.method == 'POST':\n            data = dict_fns.unflatten(tuplize_dict(parse_params(\n                request.params)))\n            info = data.get(u'info')\n            if not isinstance(info, list):\n                info = []\n            info = info[:len(fields)]\n\n            get_action('datastore_create')(None, {\n                'resource_id': resource_id,\n                'force': True,\n                'fields': [{\n                    'id': f['id'],\n                    'type': f['type'],\n                    'info': fi if isinstance(fi, dict) else {}\n                    } for f, fi in izip_longest(fields, info)]})\n\n            h.flash_success(_('Data Dictionary saved. Any type overrides will '\n                              'take effect when the resource is next uploaded '\n                              'to DataStore'))\n            h.redirect_to(\n                controller='ckanext.datastore.controller:DatastoreController',\n                action='dictionary',\n                id=id,\n                resource_id=resource_id)\n\n        return render(\n            'datastore/dictionary.html',\n            extra_vars={'fields': fields})\n\n\ndef dump_to(resource_id, output, fmt, offset, limit, options):\n    if fmt == 'csv':\n        writer_factory = csv_writer\n        records_format = 'csv'\n    elif fmt == 'tsv':\n        writer_factory = tsv_writer\n        records_format = 'tsv'\n    elif fmt == 'json':\n        writer_factory = json_writer\n        records_format = 'lists'\n    elif fmt == 'xml':\n        writer_factory = xml_writer\n        records_format = 'objects'\n\n    def start_writer(fields):\n        bom = options.get(u'bom', False)\n        return writer_factory(output, fields, resource_id, bom)\n\n    def result_page(offs, lim):\n        return get_action('datastore_search')(None, {\n            'resource_id': resource_id,\n            'limit':\n                PAGINATE_BY if limit is None\n                else min(PAGINATE_BY, lim),\n            'offset': offs,\n            'records_format': records_format,\n            'include_total': 'false',  # XXX: default() is broken\n        })\n\n    result = result_page(offset, limit)\n\n    with start_writer(result['fields']) as wr:\n        while True:\n            if limit is not None and limit <= 0:\n                break\n\n            records = result['records']\n\n            wr.write_records(records)\n\n            if records_format == 'objects' or records_format == 'lists':\n                if len(records) < PAGINATE_BY:\n                    break\n            elif not records:\n                break\n\n            offset += PAGINATE_BY\n            if limit is not None:\n                limit -= PAGINATE_BY\n                if limit <= 0:\n                    break\n\n            result = result_page(offset, limit)\n", "path": "ckanext/datastore/controller.py"}], "after_files": [{"content": "# encoding: utf-8\n\nfrom ckan.plugins.toolkit import (\n    Invalid,\n    ObjectNotFound,\n    NotAuthorized,\n    get_action,\n    get_validator,\n    _,\n    request,\n    response,\n    BaseController,\n    abort,\n    render,\n    c,\n    h,\n)\nfrom ckanext.datastore.writer import (\n    csv_writer,\n    tsv_writer,\n    json_writer,\n    xml_writer,\n)\nfrom ckan.logic import (\n    tuplize_dict,\n    parse_params,\n)\nimport ckan.lib.navl.dictization_functions as dict_fns\n\nfrom itertools import izip_longest\n\nint_validator = get_validator('int_validator')\nboolean_validator = get_validator('boolean_validator')\n\nDUMP_FORMATS = 'csv', 'tsv', 'json', 'xml'\nPAGINATE_BY = 32000\n\n\nclass DatastoreController(BaseController):\n    def dump(self, resource_id):\n        try:\n            offset = int_validator(request.GET.get('offset', 0), {})\n        except Invalid as e:\n            abort(400, u'offset: ' + e.error)\n        try:\n            limit = int_validator(request.GET.get('limit'), {})\n        except Invalid as e:\n            abort(400, u'limit: ' + e.error)\n        bom = boolean_validator(request.GET.get('bom'), {})\n        fmt = request.GET.get('format', 'csv')\n\n        if fmt not in DUMP_FORMATS:\n            abort(400, _(\n                u'format: must be one of %s') % u', '.join(DUMP_FORMATS))\n\n        try:\n            dump_to(\n                resource_id,\n                response,\n                fmt=fmt,\n                offset=offset,\n                limit=limit,\n                options={u'bom': bom})\n        except ObjectNotFound:\n            abort(404, _('DataStore resource not found'))\n\n    def dictionary(self, id, resource_id):\n        u'''data dictionary view: show/edit field labels and descriptions'''\n\n        try:\n            # resource_edit_base template uses these\n            c.pkg_dict = get_action('package_show')(\n                None, {'id': id})\n            c.resource = get_action('resource_show')(\n                None, {'id': resource_id})\n            rec = get_action('datastore_search')(None, {\n                'resource_id': resource_id,\n                'limit': 0})\n        except (ObjectNotFound, NotAuthorized):\n            abort(404, _('Resource not found'))\n\n        fields = [f for f in rec['fields'] if not f['id'].startswith('_')]\n\n        if request.method == 'POST':\n            data = dict_fns.unflatten(tuplize_dict(parse_params(\n                request.params)))\n            info = data.get(u'info')\n            if not isinstance(info, list):\n                info = []\n            info = info[:len(fields)]\n\n            get_action('datastore_create')(None, {\n                'resource_id': resource_id,\n                'force': True,\n                'fields': [{\n                    'id': f['id'],\n                    'type': f['type'],\n                    'info': fi if isinstance(fi, dict) else {}\n                    } for f, fi in izip_longest(fields, info)]})\n\n            h.flash_success(_('Data Dictionary saved. Any type overrides will '\n                              'take effect when the resource is next uploaded '\n                              'to DataStore'))\n            h.redirect_to(\n                controller='ckanext.datastore.controller:DatastoreController',\n                action='dictionary',\n                id=id,\n                resource_id=resource_id)\n\n        return render(\n            'datastore/dictionary.html',\n            extra_vars={'fields': fields})\n\n\ndef dump_to(resource_id, output, fmt, offset, limit, options):\n    if fmt == 'csv':\n        writer_factory = csv_writer\n        records_format = 'csv'\n    elif fmt == 'tsv':\n        writer_factory = tsv_writer\n        records_format = 'tsv'\n    elif fmt == 'json':\n        writer_factory = json_writer\n        records_format = 'lists'\n    elif fmt == 'xml':\n        writer_factory = xml_writer\n        records_format = 'objects'\n\n    def start_writer(fields):\n        bom = options.get(u'bom', False)\n        return writer_factory(output, fields, resource_id, bom)\n\n    def result_page(offs, lim):\n        return get_action('datastore_search')(None, {\n            'resource_id': resource_id,\n            'limit':\n                PAGINATE_BY if limit is None\n                else min(PAGINATE_BY, lim),\n            'offset': offs,\n            'sort': '_id',\n            'records_format': records_format,\n            'include_total': 'false',  # XXX: default() is broken\n        })\n\n    result = result_page(offset, limit)\n\n    with start_writer(result['fields']) as wr:\n        while True:\n            if limit is not None and limit <= 0:\n                break\n\n            records = result['records']\n\n            wr.write_records(records)\n\n            if records_format == 'objects' or records_format == 'lists':\n                if len(records) < PAGINATE_BY:\n                    break\n            elif not records:\n                break\n\n            offset += PAGINATE_BY\n            if limit is not None:\n                limit -= PAGINATE_BY\n                if limit <= 0:\n                    break\n\n            result = result_page(offset, limit)\n", "path": "ckanext/datastore/controller.py"}]}