openapi: 3.0.3 info: title: OpenFairDB API version: 0.12.12 contact: name: slowtec GmbH url: "https://slowtec.de" license: name: AGPLv3 url: "https://github.com/slowtec/openfairdb/blob/main/LICENSE" servers: - url: "https://api.ofdb.io/v0/" description: Public production server - url: "https://dev.ofdb.io/v0/" description: Public unstable development server paths: /search: get: summary: Search for places description: | Query the database for entries/places according to the search criteria and order the top matching results by their total rating in descending order. The default result contains up to 100 entries. Use the `limit` parameter to customize the desired amount. The server may decide to deliver less results than requested up to some internal upper limit (currently 2000). If the review status list is empty or missing only visible places (created, confirmed) are returned. tags: - Search parameters: - $ref: "#/components/parameters/BoundingBox" - $ref: "#/components/parameters/OrgTagFilter" - name: categories in: query schema: type: string description: | Comma-separated list of category identifiers. We currently use the following two: - Initiative (non-commercial): `2cd00bebec0c48ba9db761da48678134` - Company (commercial): `77b3c33a92554bcf8e8c2c86cedd6f6f` - name: text in: query schema: type: string - $ref: "#/components/parameters/IdList" - $ref: "#/components/parameters/TagList" - $ref: "#/components/parameters/ReviewStatusList" - $ref: "#/components/parameters/PaginationLimit" responses: "200": description: Successful response content: application/json: schema: $ref: "#/components/schemas/SearchResponse" /search/duplicates: post: summary: Search for duplicate places description: | Search for similar places that might be duplicates of a given place. Currently only the geographical location and title and are considered to find similar, already existing entries in the database. Returns a list of possible duplicates for the given place. tags: - Search requestBody: required: true content: application/json: schema: $ref: "#/components/schemas/NewEntryWithLicense" responses: "200": description: Successful response content: application/json: schema: type: array items: $ref: "#/components/schemas/SearchEntry" "/entries": post: summary: Create an entry tags: - Entries/Places requestBody: required: true content: application/json: schema: $ref: "#/components/schemas/NewEntryWithLicense" security: - bearerAuth: [] - captchaCookieAuth: [] - jwtAuth: [] - userEmailCookieAuth: [] responses: "200": description: Successful response "/entries/{ids}": get: summary: Get multiple entries tags: - Entries/Places parameters: - $ref: "#/components/parameters/IdListPath" - $ref: "#/components/parameters/OrgTagFilter" responses: "200": description: Successful response content: application/json: schema: type: array items: $ref: "#/components/schemas/Entry" "/entries/{id}": put: summary: Update an entry description: | The edited entry must include the *next version* of this entry in the `version` field, where *next version* = *current version* + 1. tags: - Entries/Places parameters: - $ref: "#/components/parameters/IdPath" requestBody: required: true content: application/json: schema: $ref: "#/components/schemas/NewEntryWithVersion" security: - bearerAuth: [] - captchaCookieAuth: [] - jwtAuth: [] - userEmailCookieAuth: [] responses: "200": description: Successful response /entries/recently-changed: get: summary: Get recently changed entries description: | Get recently changed entries that have been created/updated/archived between since and now. Limitation: Only the most recent 1000 entries are returned and the change history is restricted to the last 100 days. tags: - Entries/Places parameters: - name: since in: query required: false description: Time stamp of the oldest change (inclusive) schema: $ref: "#/components/schemas/UnixTime" - name: until in: query required: false description: Time stamp of the most recent change (exclusive) schema: $ref: "#/components/schemas/UnixTime" - name: with_ratings in: query description: Return entries including their ratings schema: type: boolean - $ref: "#/components/parameters/PaginationLimit" - $ref: "#/components/parameters/PaginationOffset" responses: "200": description: Successful response content: application/json: schema: $ref: "#/components/schemas/Entry" /entries/most-popular-tags: get: summary: Get most popular tags for entries description: | Get most popular tags for entries with their total usage count. Results are sorted in descending order of counts, i.e. most popular tags appear first. A maximum of 1000 tag with their count is returned if no limit is specified. tags: - Entries/Places parameters: - name: min_count in: query required: false description: Minimum count per tag (inclusive) schema: type: integer format: int64 - name: max_count in: query required: false description: Maximum count per tag (inclusive) schema: type: integer format: int64 - $ref: "#/components/parameters/PaginationLimit" - $ref: "#/components/parameters/PaginationOffset" - name: max_cache_age in: query required: false description: | By default, cached data is returned for performance, if the cache is not older than one hour. If you need newer data, you can set the maximum tolerable age of the cache here, in seconds. A value of 0 disables the cache and gets the newest state. schema: type: integer format: int64 responses: "200": description: Successful response content: application/json: schema: $ref: "#/components/schemas/TagCounts" "/places/clearance": get: tags: - Entries/Places summary: List clearance of places description: | Returns a list of places with pending clearance on behalf of the requesting organization in chronological order. Requests must include the API token of the organization. parameters: - $ref: "#/components/parameters/PaginationLimit" - $ref: "#/components/parameters/PaginationOffset" responses: "200": description: Successful response content: application/json: schema: type: array items: $ref: "#/components/schemas/PendingClearanceForPlace" "401": $ref: "#/components/responses/UnauthorizedError" post: tags: - Entries/Places summary: Update clearance of places description: | Update the clearance of multiple places on behalf of the requesting organization. Returns the number of created/updated clearance records. If the given revision matches the current revision of that place then any pending clearance is deleted. Otherwise clearance will remain pending with the given revision stored as the new last cleared revision, i.e. any pending clearance is replaced. Requests must include the API token of the organization. requestBody: required: true content: application/json: schema: type: array items: $ref: "#/components/schemas/ClearanceForPlace" responses: "200": description: Successful response content: application/json: schema: $ref: "#/components/schemas/ResultCount" "401": $ref: "#/components/responses/UnauthorizedError" "/places/clearance/count": get: tags: - Entries/Places summary: Count clearance of places description: | Returns the total number places with pending clearance on behalf of the requesting organization. Requests must include the API token of the organization. responses: "200": description: Successful response content: application/json: schema: $ref: "#/components/schemas/ResultCount" "401": $ref: "#/components/responses/UnauthorizedError" "/places/{id}/history/{revision}": get: tags: - Entries/Places summary: History of place revisions description: | Loads the history of all place revisions including status reviews. Optionally the result can be restricted to a single revision. If no particular revision is requested then all revisions are returned. Results are sorted in descending chronological order of activity time stamps, i.e. the most recent changes appear first. Only users with the role scout or admin are entitled to invoke this function. Organizations must provide their API token for authorization. parameters: - $ref: "#/components/parameters/IdPath" - $ref: "#/components/parameters/OptionalRevisionPath" responses: "200": description: Successful response content: application/json: schema: $ref: "#/components/schemas/PlaceHistory" "401": $ref: "#/components/responses/UnauthorizedError" "/places/{ids}/review": post: tags: - Entries/Places summary: Review multiple places description: | Reviews the latest revision of multiple places at once. An audit log is written into the history of all place revisions. Depending on the review status the affected places might be hidden from search results (archived, rejected) or re-appear (created, confirmed). Only scouts and admins are entitled to invoke this function. parameters: - $ref: "#/components/parameters/IdListPath" requestBody: required: true content: application/json: schema: $ref: "#/components/schemas/Review" responses: "201": description: Created a review for all places. "400": $ref: "#/components/responses/ParameterError" "401": $ref: "#/components/responses/UnauthorizedError" "/places/review-with-token": post: tags: - Entries/Places summary: Review a place by a secret token description: | Reviews a specific revision of a place. If a newer revision already exists, a review is no longer possible. An audit log is written into the history of the place revision. Depending on the review status the affected place might be hidden from search results (archived, rejected) or re-appear (created, confirmed). requestBody: required: true content: application/json: schema: properties: status: $ref: "#/components/schemas/ReviewStatus" token: $ref: "#/components/schemas/ReviewToken" responses: "201": description: Created a review for the place. "400": $ref: "#/components/responses/ParameterError" "401": $ref: "#/components/responses/UnauthorizedError" "/places/not-updated": get: tags: - Entries/Places summary: Get outdated entries description: | Returns a list of places that have not been changed since the given timestamp. Archived and rejected places are ignored. Only scouts and admins are entitled to invoke this function. parameters: - name: since in: query required: false description: The point in time from which the places are to be considered up-to-date. schema: $ref: "#/components/schemas/UnixTime" - $ref: "#/components/parameters/PaginationLimit" - $ref: "#/components/parameters/PaginationOffset" responses: "200": description: Successful response content: application/json: schema: type: array items: type: array minLength: 3 maxLength: 3 items: oneOf: - $ref: "#/components/schemas/PlaceRoot" - $ref: "#/components/schemas/PlaceRevision" - $ref: "#/components/schemas/ReviewStatus" "401": $ref: "#/components/responses/UnauthorizedError" "/ratings/{ids}": get: summary: Get multiple ratings tags: - Ratings parameters: - $ref: "#/components/parameters/IdListPath" responses: "200": description: Successful response content: application/json: schema: $ref: "#/components/schemas/Rating" /categories/: get: summary: Get available categories tags: - Categories responses: "200": description: Successful response content: application/json: schema: type: array items: $ref: "#/components/schemas/Category" "/categories/{ids}": get: summary: Get multiple categories tags: - Categories parameters: - $ref: "#/components/parameters/IdListPath" responses: "200": description: Successful response content: application/json: schema: $ref: "#/components/schemas/Category" /events: get: tags: - Events summary: Search events parameters: - $ref: "#/components/parameters/BoundingBox" - $ref: "#/components/parameters/PaginationLimit" - $ref: "#/components/parameters/EventTagList" - $ref: "#/components/parameters/EventStartMin" - $ref: "#/components/parameters/EventStartMax" - $ref: "#/components/parameters/EventEndMin" - $ref: "#/components/parameters/EventEndMax" - $ref: "#/components/parameters/EventFilterText" - $ref: "#/components/parameters/EventCreatedBy" responses: "200": description: Successful response content: application/json: schema: type: array items: $ref: "#/components/schemas/Event" post: tags: - Events summary: Create a new event description: | Creating new events is only allowed for registered organizations by authorizing themselves with an API token. These organizations must own reserved tags. One or more reserved tags have to be provided upon creation. Otherwise all of the organization's reserved tags are added implicitly to the event. security: - bearerAuth: [] requestBody: required: true content: application/json: schema: $ref: "#/components/schemas/Event" responses: "201": description: Created a new event content: application/json: schema: description: The ID of the created event type: string "401": $ref: "#/components/responses/UnauthorizedError" "/events/{id}": get: summary: Get a single event tags: - Events parameters: - name: id in: path required: true schema: type: string responses: "200": description: Successful response content: application/json: schema: $ref: "#/components/schemas/Event" put: summary: Update an event description: | Events can only be updated by the organization that owns them. Ownership is determined by the event's reserved tags. The updated event must be assigned at least one of the organization's reserved tags. Otherwise all reserved tags of the event are preserved by implicitly re-adding them. tags: - Events security: - bearerAuth: [] parameters: - name: id in: path required: true schema: type: string requestBody: required: true content: application/json: schema: $ref: "#/components/schemas/Event" responses: "200": description: Successfully updated the event "401": $ref: "#/components/responses/UnauthorizedError" delete: summary: Delete an event description: | Events can only be deleted by the organization that owns them. Ownership is determined by the event's reserved tags. tags: - Events security: - bearerAuth: [] parameters: - name: id in: path required: true schema: type: string responses: "200": description: Successfully deleted the event "401": $ref: "#/components/responses/UnauthorizedError" "/events/{ids}/archive": post: tags: - Events summary: Archive multiple events description: | Marks the given events as *archived* and excludes them from all search results. Only scouts and admins are entitled to invoke this function. parameters: - $ref: "#/components/parameters/IdListPath" responses: "204": description: Archived the given events if not already archived. "400": $ref: "#/components/responses/ParameterError" "401": $ref: "#/components/responses/UnauthorizedError" "/login": post: summary: User login tags: - Users requestBody: required: true content: application/json: schema: $ref: "#/components/schemas/Credentials" responses: "200": description: Successful response - the JWT token content: application/json: schema: $ref: "#/components/schemas/JwtToken" "/logout": post: summary: User logout tags: - Users security: - jwtAuth: [] responses: "200": description: Successful response "/users": post: summary: Register a new user tags: - Users requestBody: required: true content: application/json: schema: $ref: "#/components/schemas/NewUser" responses: "200": description: Successful response "/users/current": get: summary: Get the current user tags: - Users security: - jwtAuth: [] responses: "200": description: The current user content: application/json: schema: $ref: "#/components/schemas/User" "/users/reset-password-request": post: summary: Request a password reset tags: - Users requestBody: required: true content: application/json: schema: type: object properties: email: $ref: "#/components/schemas/UserEmail" responses: "200": description: Successful response "/users/reset-password": post: summary: Request a users password tags: - Users requestBody: required: true content: application/json: schema: type: object properties: email: $ref: "#/components/schemas/UserEmail" token: type: string new_password: type: string responses: "200": description: Successful response /users/confirm-email-address: post: summary: Confirm that an email is valid. tags: - Users requestBody: required: true content: application/json: schema: type: object properties: token: type: string responses: "200": description: Successful response /subscribe-to-bbox: post: summary: Subscribe to a bounding box tags: - Subscriptions requestBody: required: true content: application/json: schema: type: array items: $ref: "#/components/schemas/LatLonDeg" example: - lat: 45.3 lng: 8.6 - lat: 48.7 lng: 9.2 responses: "200": description: Successful response /bbox-subscriptions: get: summary: Fetch subscriptions tags: - Subscriptions responses: "200": description: Successful response content: application/json: schema: type: array items: $ref: "#/components/schemas/BboxSubscription" /unsubscribe-all-bboxes: delete: summary: Delete all subscriptions tags: - Subscriptions responses: "200": description: Successful response /tags: get: summary: Get tags tags: - Tags responses: "200": description: Successful response content: application/json: schema: type: array items: type: string /count/entries: get: summary: Get number of entries tags: - Stats responses: "200": description: Successful response content: application/json: schema: type: integer /count/tags: get: summary: Get number of tags tags: - Stats responses: "200": description: Successful response content: application/json: schema: type: integer /server/version: get: summary: Get current server version tags: - Stats responses: "200": description: Successful response content: text/plain: schema: type: string /server/openapi.yaml: get: summary: Download the current API documentation tags: - Stats responses: "200": description: Successful response content: text/yaml: schema: type: string /export/entries.csv: get: summary: Export places as CSV. description: | The CSV export is only available for logged in users with the role _Admin_ or _Scout_. This request supports the same parameters as the corresponding search request. Contact details (email/phone) are only visible for users with the role _Admin_ or _Scout_. Information about who created the current version (created_by) is only visible for users with the role _Admin_ or owners of this entry. **Example**: Export all entries in Germany: `/export/entries.csv?bbox=47.49,0.79,54.63,18.30` tags: - Export parameters: - $ref: "#/components/parameters/BoundingBox" - name: categories in: query schema: type: string description: | Comma-separated list of category identifiers. We currently use the following two: - Initiative (non-commercial): `2cd00bebec0c48ba9db761da48678134` - Company (commercial): `77b3c33a92554bcf8e8c2c86cedd6f6f` - name: text in: query schema: type: string - $ref: "#/components/parameters/IdList" - $ref: "#/components/parameters/TagList" - $ref: "#/components/parameters/ReviewStatusList" - $ref: "#/components/parameters/PaginationLimit" responses: "200": description: Successful response content: text/csv: schema: type: string "401": $ref: "#/components/responses/UnauthorizedError" /export/events.csv: get: summary: Export events as CSV. description: | The CSV export is only available for logged in users with the role _Admin_ or _Scout_. This request supports the same parameters as the corresponding search request. **Example**: Export all events in Germany: `/export/events.csv?bbox=47.49,0.79,54.63,18.30` tags: - Export parameters: - $ref: "#/components/parameters/BoundingBox" - $ref: "#/components/parameters/PaginationLimit" - $ref: "#/components/parameters/EventTagList" - $ref: "#/components/parameters/EventStartMin" - $ref: "#/components/parameters/EventStartMax" - $ref: "#/components/parameters/EventFilterText" - $ref: "#/components/parameters/EventCreatedBy" responses: "200": description: Successful response content: text/csv: schema: type: string "401": $ref: "#/components/responses/UnauthorizedError" /export/events.ical: get: summary: Export events as iCal. description: | The iCal export is only available for logged in users with the role _Admin_ or _Scout_. This request supports the same parameters as the corresponding search request. **Example**: Export all events in Germany: `/export/events.ical?bbox=47.49,0.79,54.63,18.30` tags: - Export parameters: - $ref: "#/components/parameters/BoundingBox" - $ref: "#/components/parameters/PaginationLimit" - $ref: "#/components/parameters/EventTagList" - $ref: "#/components/parameters/EventStartMin" - $ref: "#/components/parameters/EventStartMax" - $ref: "#/components/parameters/EventFilterText" - $ref: "#/components/parameters/EventCreatedBy" responses: "200": description: Successful response content: text/calendar: schema: type: string "401": $ref: "#/components/responses/UnauthorizedError" /captcha: post: summary: Request a new captcha challenge tags: - Captcha responses: "200": description: Successful response content: application/json: schema: $ref: "#/components/schemas/CaptchaToken" "/captcha/{captcha-token}": get: summary: Get the captcha challenge description: | Returns an image with a captcha challenge for the given token. tags: - Captcha parameters: - $ref: "#/components/parameters/CaptchaToken" responses: "200": description: Successful response content: image/png: schema: $ref: "#/components/schemas/CaptchaImage" "404": description: Unknown or expired token "/captcha/{captcha-token}/verify": post: summary: Verify a captcha answer for the given token tags: - Captcha parameters: - $ref: "#/components/parameters/CaptchaToken" requestBody: required: true content: text/plain: schema: $ref: "#/components/schemas/CaptchaAnswer" responses: "200": description: | The answer to the capcha challenge was correct. A token is returned in a cookie named `ofdb-captcha`. You need to include this cookie in subsequent requests. headers: Set-Cookie: schema: type: string example: ofdb-captcha=2f006JTvKBr5KJggwirdTzTssdzschIwThWF8LdqPZTr4wSY6r%2F79ayYNz46NTrKn4VR6KPxpkNeIOoGbA%3D%3D; HttpOnly; Path=/; "400": description: The answer to the capcha challenge was not correct components: schemas: NewEntry: properties: title: type: string description: type: string lat: $ref: "#/components/schemas/Latitude" lng: $ref: "#/components/schemas/Longitude" street: type: string zip: type: string city: type: string country: type: string state: type: string contact_name: $ref: "#/components/schemas/ContactName" email: $ref: "#/components/schemas/ContactEmail" telephone: $ref: "#/components/schemas/ContactPhone" homepage: $ref: "#/components/schemas/Url" opening_hours: $ref: "#/components/schemas/OpeningHours" founded_on: $ref: "#/components/schemas/FoundingDate" categories: type: array items: type: string tags: $ref: "#/components/schemas/TagArray" image_url: $ref: "#/components/schemas/ImageUrl" image_link_url: $ref: "#/components/schemas/ImageLink" links: $ref: "#/components/schemas/CustomLinkList" required: - title - description - lat - lng NewEntryWithLicense: allOf: - $ref: "#/components/schemas/NewEntry" - type: object properties: license: $ref: "#/components/schemas/License" NewEntryWithVersion: allOf: - $ref: "#/components/schemas/NewEntry" - type: object properties: version: type: integer Entry: allOf: - $ref: "#/components/schemas/NewEntryWithLicense" - type: object properties: id: $ref: "#/components/schemas/Id" version: type: integer created: type: integer ratings: type: array items: type: string ImageUrl: description: | The external URL for an image. allOf: - $ref: "#/components/schemas/Url" ImageLink: description: | A hyperlink behind an image that is supposed to be opened when clicking on the image. allOf: - $ref: "#/components/schemas/Url" CustomLink: description: | A custom hyperlink with an optional title and description. properties: url: $ref: "#/components/schemas/Url" title: type: string description: type: string required: - url CustomLinkList: description: | An unordered list of custom links. The ordering of list items may change between different revisions even if this list has not been modified. Don't make any assumptions about a particular ordering! type: array items: $ref: "#/components/schemas/CustomLink" Category: properties: id: $ref: "#/components/schemas/Id" created: type: integer version: type: integer name: type: string Rating: properties: id: $ref: "#/components/schemas/Id" title: type: string created: type: integer value: type: integer context: type: string source: type: string comments: type: array items: $ref: "#/components/schemas/RatingComment" RatingComment: properties: id: $ref: "#/components/schemas/Id" created: $ref: "#/components/schemas/CreatedAt" text: type: string BboxSubscription: properties: id: $ref: "#/components/schemas/Id" south_west_lat: $ref: "#/components/schemas/Latitude" south_west_lng: $ref: "#/components/schemas/Longitude" north_east_lat: $ref: "#/components/schemas/Latitude" north_east_lng: $ref: "#/components/schemas/Longitude" SearchResponse: properties: visible: description: The entries that are in the given bounding box (bbox, area of the map). type: array items: $ref: "#/components/schemas/SearchEntry" invisible: description: Up to 5 entries outside the bbox. type: array items: $ref: "#/components/schemas/SearchEntry" SearchEntry: description: The compact view of an entry as returned in search results. properties: id: $ref: "#/components/schemas/Id" status: $ref: "#/components/schemas/ReviewStatus" lat: $ref: "#/components/schemas/Latitude" lng: $ref: "#/components/schemas/Longitude" title: type: string description: type: string categories: type: array items: type: string tags: $ref: "#/components/schemas/TagArray" ratings: $ref: "#/components/schemas/AvgRatings" PlaceId: description: | The id of a place allOf: - $ref: "#/components/schemas/Id" PendingClearanceForPlace: description: | The compact view of an entry as returned in search results. The field `last_cleared_revision` is missing if no cleared revivision is available, e.g. for newly created entries. properties: place_id: $ref: "#/components/schemas/PlaceId" created_at: $ref: "#/components/schemas/CreatedAt" last_cleared_revision: $ref: "#/components/schemas/Revision" required: - place_id - created_at ClearanceForPlace: description: | Clearance for a selected revision of a place. If the field `cleared_revision` is missing then the current revision is cleared unconditionally. properties: place_id: $ref: "#/components/schemas/PlaceId" cleared_revision: $ref: "#/components/schemas/Revision" required: - place_id AvgRatings: description: All average ratings of an entry. properties: total: type: number diversity: type: number fairness: type: number humanity: type: number renewable: type: number solidarity: type: number transparency: type: number Id: type: string minLength: 32 maxLength: 32 description: | Identifier of a resource example: 7cee99c287094a94acbdcf29ffff2e85 IdArray: type: array items: $ref: "#/components/schemas/Id" Revision: type: integer format: int64 minimum: 0 description: | A revision number example: 23 IdList: type: string description: | Comma-separated list of identifiers example: 7cee99c287094a94acbdcf29ffff2e85,0884c4e86e404072b6874b99b7e32640,ed8a2aef20054102b20950b1b78eb581 TagList: type: string description: | Comma-separated list of tags example: organic,non-profit License: type: string minLength: 1 example: ODbL-1.0 Email: type: string minLength: 3 description: | An e-mail address. example: john.smith@example.com UserEmail: description: | The e-mail address of a user account. allOf: - $ref: "#/components/schemas/Email" ContactName: description: | The name of the contact person. allOf: - $ref: "#/components/schemas/PersonFullName" ContactEmail: description: | An e-mail address to get in contact. allOf: - $ref: "#/components/schemas/Email" PersonFullName: type: string description: | The full name of a person. example: John Smith Title: type: string minLength: 1 example: A non-empty title Description: type: string minLength: 1 example: A non-empty description Street: type: string example: Friedrichsberg 55 City: type: string example: Stuttgart ZipCode: type: string example: 70567 Country: type: string example: Germany State: type: string example: Baden-Württemberg Phone: type: string example: 001 123456789 ContactPhone: description: | An phone number to get in contact. allOf: - $ref: "#/components/schemas/Phone" Tag: type: string minLength: 1 example: non-profit TagArray: type: array items: $ref: "#/components/schemas/Tag" example: [organic, non-profit] Url: type: string minLength: 8 example: https://www.slowtec.de/ Activity: properties: at: $ref: "#/components/schemas/CreatedAt" by: $ref: "#/components/schemas/UserEmail" required: - at ActivityContext: type: string description: | Implicitly recorded context of an activity ActivityComment: type: string description: | Free text that describes the motivation or trigger for an activity example: Action performed, because ... ActivityLog: properties: at: $ref: "#/components/schemas/CreatedAt" by: $ref: "#/components/schemas/UserEmail" ctx: $ref: "#/components/schemas/ActivityContext" comment: $ref: "#/components/schemas/ActivityComment" required: - at Location: properties: deg: $ref: "#/components/schemas/LatLonDeg" adr: $ref: "#/components/schemas/Address" required: - deg Contact: properties: name: $ref: "#/components/schemas/ContactName" phone: $ref: "#/components/schemas/ContactPhone" email: $ref: "#/components/schemas/ContactEmail" Address: properties: street: $ref: "#/components/schemas/Street" city: $ref: "#/components/schemas/City" zip: $ref: "#/components/schemas/ZipCode" country: $ref: "#/components/schemas/Country" state: $ref: "#/components/schemas/State" OpeningHours: type: string minLength: 4 description: | The opening hours in OpenStreetMap format. Specification: https://wiki.openstreetmap.org/wiki/Key:opening_hours Reference implementations: https://github.com/opening-hours/ Generator tool: https://projets.pavie.info/yohours/ The service trims leading/trailing whitespaces and stores values as is. Values are currently not validated against the OSM format syntax! example: 24/7 PlaceLinks: properties: www: $ref: "#/components/schemas/Url" img: $ref: "#/components/schemas/ImageUrl" img_href: $ref: "#/components/schemas/ImageLink" FoundingDate: description: | The date on which an organization, initiative, or company has been founded or established. type: string format: date example: 1945-10-24 LatLonDeg: type: array minLength: 2 maxLength: 2 items: type: number format: double description: | WGS 84 coordinates (latitude, longitude) in degrees example: [48.720334, 9.152239] PlaceRoot: description: | Immutable properties of a place properties: id: $ref: "#/components/schemas/Id" lic: $ref: "#/components/schemas/License" required: - id - lic PlaceRevision: properties: created: $ref: "#/components/schemas/Activity" rev: $ref: "#/components/schemas/Revision" tit: $ref: "#/components/schemas/Title" dsc: $ref: "#/components/schemas/Description" loc: $ref: "#/components/schemas/Location" cnt: $ref: "#/components/schemas/Contact" hrs: $ref: "#/components/schemas/OpeningHours" fnd: $ref: "#/components/schemas/FoundingDate" lnk: $ref: "#/components/schemas/PlaceLinks" tag: $ref: "#/components/schemas/TagArray" required: - created - rev - tit - dsc PlaceRevisionLog: type: array minLength: 2 maxLength: 2 items: oneOf: - $ref: "#/components/schemas/PlaceRevision" - $ref: "#/components/schemas/ReviewStatusLogArray" PlaceRevisionLogArray: type: array items: $ref: "#/components/schemas/PlaceRevisionLog" ReviewStatusLog: properties: rev: $ref: "#/components/schemas/Revision" act: $ref: "#/components/schemas/ActivityLog" status: $ref: "#/components/schemas/ReviewStatus" ReviewStatusLogArray: type: array items: $ref: "#/components/schemas/ReviewStatusLog" PlaceHistory: properties: place: $ref: "#/components/schemas/PlaceRoot" revisions: $ref: "#/components/schemas/PlaceRevisionLogArray" required: - place ResultCount: properties: count: type: integer format: int64 required: - count additionalProperties: false Review: properties: status: $ref: "#/components/schemas/ReviewStatus" comment: $ref: "#/components/schemas/ActivityComment" required: - status ReviewStatus: type: string enum: - created - confirmed - rejected - archived description: | * created = initial status of each revision * confirmed/rejected = after positive/negative review * archived = final status example: rejected ReviewToken: type: string description: | A secret one time token to review a specific place. example: e43e4a348172480c8f48b5b734f591f4ef9d626c42d04dc8bc826087299a7a65372 ReviewStatusList: type: string description: | Comma-separated list of multiple review status names example: created,confirmed UserRole: type: string enum: - guest - user - scout - admin description: | A user's role User: properties: email: $ref: "#/components/schemas/UserEmail" email_confirmed: type: boolean role: $ref: "#/components/schemas/UserRole" required: - email - email_confirmed - role NewUser: properties: email: $ref: "#/components/schemas/UserEmail" password: type: string Credentials: properties: email: $ref: "#/components/schemas/UserEmail" password: type: string Event: properties: id: $ref: "#/components/schemas/Id" title: type: string example: A great event description: type: string example: Detailed description of the event start: $ref: "#/components/schemas/EventTime" end: $ref: "#/components/schemas/EventTime" created_at: $ref: "#/components/schemas/CreatedAt" created_by: type: string description: | The email address of the user who is responsible for the content. This information is only available for authorized organizations. lat: $ref: "#/components/schemas/Latitude" lng: $ref: "#/components/schemas/Longitude" street: type: string zip: type: string city: type: string country: type: string state: type: string email: $ref: "#/components/schemas/ContactEmail" telephone: $ref: "#/components/schemas/ContactPhone" tags: $ref: "#/components/schemas/TagArray" homepage: $ref: "#/components/schemas/Url" registration: type: string enum: - email - telephone - homepage example: telephone description: Type of registration organizer: type: string image_url: $ref: "#/components/schemas/ImageUrl" image_link_url: $ref: "#/components/schemas/ImageLink" UnixTime: type: integer format: int64 description: | Unix time (number of seconds since 00:00::00 1. January, 1970, UTC) example: 1547403509 EventTime: description: | The start/end time of an event. Event times are always specified in UTC, independent of the geographical location and the actual time zone at this location at the given time. Therefore these time stamps should be interpreted as a *naive* date time without any time zone. The calculation of the actual, absolute point that is needed for chronological ordering of events at different geographical locations would require a time zone database to perform this conversion. Frontends should display and edit event times as if the event is located in the UTC time zone, neither taking into account the actual time at the geographical location of the event nor the current local time zone of the client itself! allOf: - $ref: "#/components/schemas/UnixTime" UnixTimeMillis: type: integer format: int64 readOnly: true description: | Precise Unix time (number of milliseconds since 00:00::00.000 1. January, 1970, UTC) for system-generated time stamps example: 1547403509000 CreatedAt: description: | The time at which the corresponding entity or database record has been created, i.e. the first time it has been written. Most entities/records are immutable and never updated. allOf: - $ref: "#/components/schemas/UnixTimeMillis" TagCounts: type: array items: type: array items: oneOf: - type: string - type: integer format: int64 example: [["tag1", 52], ["tag2", 0]] Latitude: type: number format: double minimum: -90.0 maximum: 90.0 example: 37.2 description: Geographic latitude (in degrees) Longitude: type: number format: double minimum: -180.0 maximum: 180.0 example: 120.7 description: Geographic longitude (in degrees) CaptchaToken: type: string description: A unique captcha token example: 863bd305b8294cdcaa17277ffee6ae5a CaptchaAnswer: type: string description: The answer to a given captcha challenge CaptchaImage: description: The capcha image type: string format: binary JwtToken: description: A JWT bearer token to authorize requests - it is currently valid for 24 hours. properties: token: type: string example: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJzdWIiOiJtYWdudXMuaGVyb2xkQHNsb3d0ZWMuZGUiLCJleHAiOjE2MDY4MjIyMTZ9.3lO245XVvqZ16FuKfBtHP7ybSsZZTng6HmPIKK6UBLI" parameters: IdPath: name: id in: path required: true schema: $ref: "#/components/schemas/Id" IdListPath: name: ids in: path required: true schema: $ref: "#/components/schemas/IdList" OptionalRevisionPath: name: revision in: path # TODO: Set required to false when supported by OpenAPI # https://github.com/OAI/OpenAPI-Specification/issues/93 required: true schema: $ref: "#/components/schemas/Revision" BoundingBox: name: bbox in: query description: Bounding Box schema: type: string example: "42.27,-7.97,52.58,38.25" OrgTagFilter: name: org_tag in: query required: false schema: type: string description: | A single hash tag that is moderated by an organization. Results will be filtered according to the current clearance status. Unclear revisions of entries will either be removed or replaced by older, already cleared revisions. Unclear revisions of entries are expected to only exist temporarily for a short time frame until a newer version has been cleared. If the provided hash tag is not moderated by any organization the results will not be filtered by clearance status. Only a single tag can be specified, because filtering according to clearance by multiple organizations could produce ambiguous and conflicting results. Only when used in search requests: The hash tag will be included in the query as a mandatory search criteria like any other tag. Omitting this parameter and instead appending the moderated hash tag as a regular tag to the `tags` parameter will also return unfiltered search results, i.e. current revisions of entries independent of their clearance status. IdList: name: ids in: query required: false schema: $ref: "#/components/schemas/IdList" TagList: name: tags in: query required: false schema: $ref: "#/components/schemas/TagList" EventStartMin: name: start_min in: query description: Filter events by `event.start` >= `start_min` schema: $ref: "#/components/schemas/EventTime" EventStartMax: name: start_max in: query description: Filter events by `event.start` <= `start_max` schema: $ref: "#/components/schemas/EventTime" EventEndMin: name: end_min in: query description: Filter events by `event.end` >= `end_min` schema: $ref: "#/components/schemas/EventTime" EventEndMax: name: end_max in: query description: Filter events by `event.end` <= `end_max` schema: $ref: "#/components/schemas/EventTime" EventFilterText: name: text in: query description: | Filter events by textual terms. Hashtags starting with '#' will be extracted from the given text and handled as tag filters. schema: type: string EventCreatedBy: name: created_by in: query description: | The email address of the event creator. Requests with this parameter will be rejected without a valid API token! schema: $ref: "#/components/schemas/Email" EventTagList: name: tag description: Filter events by tags in: query required: false schema: $ref: "#/components/schemas/TagList" ReviewStatusList: name: status in: query required: false schema: $ref: "#/components/schemas/ReviewStatusList" PaginationLimit: name: limit description: Maximum number of items to return or implicit/unlimited if unspecified. in: query required: false schema: type: integer format: int64 example: 100 PaginationOffset: name: offset description: | Number of items to skip in the result list or 0 if unspecified. The pagination offset is only evaluated in conjunction with the corresponding pagination limit parameter! in: query required: false schema: type: integer format: int64 example: 1000 CaptchaToken: name: captcha-token description: | A unique captcha token in: path required: true schema: type: string securitySchemes: bearerAuth: type: http scheme: bearer captchaCookieAuth: type: apiKey in: cookie name: ofdb-captcha jwtAuth: type: http scheme: bearer bearerFormat: JWT userEmailCookieAuth: type: apiKey in: cookie name: ofdb-user-email responses: ParameterError: description: Parameters are missing or invalid UnauthorizedError: description: Access token is missing or invalid or the user has insufficient permission