diff --git a/apidoc/api_data.js b/apidoc/api_data.js deleted file mode 100644 index 362debb7..00000000 --- a/apidoc/api_data.js +++ /dev/null @@ -1 +0,0 @@ -define({ "api": [ { "type": "get", "url": "/users/:id", "title": "Request User information", "name": "GetUser", "group": "Users", "header": { "fields": { "Header": [ { "group": "Header", "type": "String", "optional": false, "field": "X-Access-Token", "description": "
Optional access token if authentication is enabled
" } ] }, "examples": [ { "title": "Header-Example:", "content": "{\n \"X-Access-Token\": \"59fc66a03e54454869460e45\"\n}", "type": "json" } ] }, "parameter": { "fields": { "Parameter": [ { "group": "Parameter", "type": "Number", "optional": false, "field": "id", "description": "Users unique ID.
" } ] } }, "success": { "fields": { "Success 200": [ { "group": "Success 200", "type": "Boolean", "optional": false, "field": "success", "description": "Indicates successful response
" }, { "group": "Success 200", "type": "String", "optional": false, "field": "id", "description": "Users unique ID (24 byte hex)
" }, { "group": "Success 200", "type": "String", "optional": false, "field": "username", "description": "Username of the User
" }, { "group": "Success 200", "type": "String", "optional": false, "field": "name", "description": "Name of the User
" }, { "group": "Success 200", "type": "String", "optional": false, "field": "address", "description": "Main email address of the User
" }, { "group": "Success 200", "type": "Number", "optional": false, "field": "retention", "description": "Default retention time in ms. false
if not enabled
List of enabled 2FA methods
" }, { "group": "Success 200", "type": "Boolean", "optional": false, "field": "encryptMessages", "description": "If true
then received messages are encrypted
If true
then forwarded messages are encrypted
Public PGP key for the User that is used for encryption
" }, { "group": "Success 200", "type": "Object[]", "optional": false, "field": "keyInfo", "description": "Information about public key or false
if key is not available
Name listed in public key
" }, { "group": "Success 200", "type": "String", "optional": false, "field": "keyInfo.address", "description": "E-mail address listed in public key
" }, { "group": "Success 200", "type": "String", "optional": false, "field": "keyInfo.fingerprint", "description": "Fingerprint of the public key
" }, { "group": "Success 200", "type": "String[]", "optional": false, "field": "forward", "description": "A list of email addresses to forward all incoming emails
" }, { "group": "Success 200", "type": "String[]", "optional": false, "field": "targetUrl", "description": "An URL to post all incoming emails
" }, { "group": "Success 200", "type": "Object[]", "optional": false, "field": "limits", "description": "Account limits and usage
" }, { "group": "Success 200", "type": "Object[]", "optional": false, "field": "limits.quota", "description": "Quota usage limits
" }, { "group": "Success 200", "type": "Number", "optional": false, "field": "limits.quota.allowed", "description": "Allowed quota of the user in bytes
" }, { "group": "Success 200", "type": "Number", "optional": false, "field": "limits.quota.used", "description": "Space used in bytes
" }, { "group": "Success 200", "type": "Object[]", "optional": false, "field": "limits.recipients", "description": "Sending quota
" }, { "group": "Success 200", "type": "Number", "optional": false, "field": "limits.recipients.allowed", "description": "How many messages per 24 hour can be sent
" }, { "group": "Success 200", "type": "Number", "optional": false, "field": "limits.recipients.used", "description": "How many messages are sent during current 24 hour period
" }, { "group": "Success 200", "type": "Number", "optional": false, "field": "limits.recipients.ttl", "description": "Time until the end of current 24 hour period
" }, { "group": "Success 200", "type": "Object[]", "optional": false, "field": "limits.forwards", "description": "Forwarding quota
" }, { "group": "Success 200", "type": "Number", "optional": false, "field": "limits.forwards.allowed", "description": "How many messages per 24 hour can be forwarded
" }, { "group": "Success 200", "type": "Number", "optional": false, "field": "limits.forwards.used", "description": "How many messages are forwarded during current 24 hour period
" }, { "group": "Success 200", "type": "Number", "optional": false, "field": "limits.forwards.ttl", "description": "Time until the end of current 24 hour period
" }, { "group": "Success 200", "type": "String[]", "optional": false, "field": "tags", "description": "List of tags associated with the User
" }, { "group": "Success 200", "type": "Boolean", "optional": false, "field": "hasPasswordSet", "description": "If true
then the User has a password set and can authenticate
Is the account activated
" }, { "group": "Success 200", "type": "Boolean", "optional": false, "field": "disabled", "description": "If true
then the user can not authenticate or receive any new mail
Description of the error
" } ] }, "examples": [ { "title": "Error-Response:", "content": "HTTP/1.1 200 OK\n{\n \"error\": \"This user does not exist\"\n}", "type": "json" } ] }, "examples": [ { "title": "Example usage:", "content": "curl -i http://localhost:8080/users/59fc66a03e54454869460e45", "type": "curl" } ], "version": "0.0.0", "filename": "lib/api/users.js", "groupTitle": "Users" } ] }); diff --git a/apidoc/api_data.json b/apidoc/api_data.json deleted file mode 100644 index b24c9c4e..00000000 --- a/apidoc/api_data.json +++ /dev/null @@ -1 +0,0 @@ -[ { "type": "get", "url": "/users/:id", "title": "Request User information", "name": "GetUser", "group": "Users", "header": { "fields": { "Header": [ { "group": "Header", "type": "String", "optional": false, "field": "X-Access-Token", "description": "Optional access token if authentication is enabled
" } ] }, "examples": [ { "title": "Header-Example:", "content": "{\n \"X-Access-Token\": \"59fc66a03e54454869460e45\"\n}", "type": "json" } ] }, "parameter": { "fields": { "Parameter": [ { "group": "Parameter", "type": "Number", "optional": false, "field": "id", "description": "Users unique ID.
" } ] } }, "success": { "fields": { "Success 200": [ { "group": "Success 200", "type": "Boolean", "optional": false, "field": "success", "description": "Indicates successful response
" }, { "group": "Success 200", "type": "String", "optional": false, "field": "id", "description": "Users unique ID (24 byte hex)
" }, { "group": "Success 200", "type": "String", "optional": false, "field": "username", "description": "Username of the User
" }, { "group": "Success 200", "type": "String", "optional": false, "field": "name", "description": "Name of the User
" }, { "group": "Success 200", "type": "String", "optional": false, "field": "address", "description": "Main email address of the User
" }, { "group": "Success 200", "type": "Number", "optional": false, "field": "retention", "description": "Default retention time in ms. false
if not enabled
List of enabled 2FA methods
" }, { "group": "Success 200", "type": "Boolean", "optional": false, "field": "encryptMessages", "description": "If true
then received messages are encrypted
If true
then forwarded messages are encrypted
Public PGP key for the User that is used for encryption
" }, { "group": "Success 200", "type": "Object[]", "optional": false, "field": "keyInfo", "description": "Information about public key or false
if key is not available
Name listed in public key
" }, { "group": "Success 200", "type": "String", "optional": false, "field": "keyInfo.address", "description": "E-mail address listed in public key
" }, { "group": "Success 200", "type": "String", "optional": false, "field": "keyInfo.fingerprint", "description": "Fingerprint of the public key
" }, { "group": "Success 200", "type": "String[]", "optional": false, "field": "forward", "description": "A list of email addresses to forward all incoming emails
" }, { "group": "Success 200", "type": "String[]", "optional": false, "field": "targetUrl", "description": "An URL to post all incoming emails
" }, { "group": "Success 200", "type": "Object[]", "optional": false, "field": "limits", "description": "Account limits and usage
" }, { "group": "Success 200", "type": "Object[]", "optional": false, "field": "limits.quota", "description": "Quota usage limits
" }, { "group": "Success 200", "type": "Number", "optional": false, "field": "limits.quota.allowed", "description": "Allowed quota of the user in bytes
" }, { "group": "Success 200", "type": "Number", "optional": false, "field": "limits.quota.used", "description": "Space used in bytes
" }, { "group": "Success 200", "type": "Object[]", "optional": false, "field": "limits.recipients", "description": "Sending quota
" }, { "group": "Success 200", "type": "Number", "optional": false, "field": "limits.recipients.allowed", "description": "How many messages per 24 hour can be sent
" }, { "group": "Success 200", "type": "Number", "optional": false, "field": "limits.recipients.used", "description": "How many messages are sent during current 24 hour period
" }, { "group": "Success 200", "type": "Number", "optional": false, "field": "limits.recipients.ttl", "description": "Time until the end of current 24 hour period
" }, { "group": "Success 200", "type": "Object[]", "optional": false, "field": "limits.forwards", "description": "Forwarding quota
" }, { "group": "Success 200", "type": "Number", "optional": false, "field": "limits.forwards.allowed", "description": "How many messages per 24 hour can be forwarded
" }, { "group": "Success 200", "type": "Number", "optional": false, "field": "limits.forwards.used", "description": "How many messages are forwarded during current 24 hour period
" }, { "group": "Success 200", "type": "Number", "optional": false, "field": "limits.forwards.ttl", "description": "Time until the end of current 24 hour period
" }, { "group": "Success 200", "type": "String[]", "optional": false, "field": "tags", "description": "List of tags associated with the User
" }, { "group": "Success 200", "type": "Boolean", "optional": false, "field": "hasPasswordSet", "description": "If true
then the User has a password set and can authenticate
Is the account activated
" }, { "group": "Success 200", "type": "Boolean", "optional": false, "field": "disabled", "description": "If true
then the user can not authenticate or receive any new mail
Description of the error
" } ] }, "examples": [ { "title": "Error-Response:", "content": "HTTP/1.1 200 OK\n{\n \"error\": \"This user does not exist\"\n}", "type": "json" } ] }, "examples": [ { "title": "Example usage:", "content": "curl -i http://localhost:8080/users/59fc66a03e54454869460e45", "type": "curl" } ], "version": "0.0.0", "filename": "lib/api/users.js", "groupTitle": "Users" } ] diff --git a/docs/api_data.js b/docs/api_data.js new file mode 100644 index 00000000..16a37075 --- /dev/null +++ b/docs/api_data.js @@ -0,0 +1 @@ +define({ "api": [ { "type": "delete", "url": "/users/:id", "title": "Delete an User", "name": "DeleteUser", "group": "Users", "header": { "fields": { "Header": [ { "group": "Header", "type": "String", "optional": false, "field": "X-Access-Token", "description": "Optional access token if authentication is enabled
" } ] }, "examples": [ { "title": "Header-Example:", "content": "{\n \"X-Access-Token\": \"59fc66a03e54454869460e45\"\n}", "type": "json" } ] }, "parameter": { "fields": { "Parameter": [ { "group": "Parameter", "type": "String", "optional": false, "field": "id", "description": "Users unique ID.
" }, { "group": "Parameter", "type": "String", "optional": true, "field": "sess", "description": "Session identifier for the logs
" }, { "group": "Parameter", "type": "String", "optional": true, "field": "ip", "description": "IP address for the logs
" } ] } }, "success": { "fields": { "Success 200": [ { "group": "Success 200", "type": "Boolean", "optional": false, "field": "success", "description": "Indicates successful response
" } ] }, "examples": [ { "title": "Success-Response:", "content": "HTTP/1.1 200 OK\n{\n \"success\": true\n}", "type": "json" } ] }, "error": { "fields": { "Error 4xx": [ { "group": "Error 4xx", "optional": false, "field": "error", "description": "Description of the error
" } ] }, "examples": [ { "title": "Error-Response:", "content": "HTTP/1.1 200 OK\n{\n \"error\": \"This user does not exist\"\n}", "type": "json" } ] }, "examples": [ { "title": "Example usage:", "content": "curl -i -XDELETE http://localhost:8080/users/5a1bda70bfbd1442cd96c6f0?ip=127.0.0.1", "type": "curl" } ], "version": "0.0.0", "filename": "lib/api/users.js", "groupTitle": "Users" }, { "type": "get", "url": "/users/:id", "title": "Request User information", "name": "GetUser", "group": "Users", "header": { "fields": { "Header": [ { "group": "Header", "type": "String", "optional": false, "field": "X-Access-Token", "description": "Optional access token if authentication is enabled
" } ] }, "examples": [ { "title": "Header-Example:", "content": "{\n \"X-Access-Token\": \"59fc66a03e54454869460e45\"\n}", "type": "json" } ] }, "parameter": { "fields": { "Parameter": [ { "group": "Parameter", "type": "String", "optional": false, "field": "id", "description": "Users unique ID.
" } ] } }, "success": { "fields": { "Success 200": [ { "group": "Success 200", "type": "Boolean", "optional": false, "field": "success", "description": "Indicates successful response
" }, { "group": "Success 200", "type": "String", "optional": false, "field": "id", "description": "Users unique ID (24 byte hex)
" }, { "group": "Success 200", "type": "String", "optional": false, "field": "username", "description": "Username of the User
" }, { "group": "Success 200", "type": "String", "optional": false, "field": "name", "description": "Name of the User
" }, { "group": "Success 200", "type": "String", "optional": false, "field": "address", "description": "Main email address of the User
" }, { "group": "Success 200", "type": "Number", "optional": false, "field": "retention", "description": "Default retention time in ms. false
if not enabled
List of enabled 2FA methods
" }, { "group": "Success 200", "type": "Boolean", "optional": false, "field": "encryptMessages", "description": "If true
then received messages are encrypted
If true
then forwarded messages are encrypted
Public PGP key for the User that is used for encryption
" }, { "group": "Success 200", "type": "Object", "optional": false, "field": "keyInfo", "description": "Information about public key or false
if key is not available
Name listed in public key
" }, { "group": "Success 200", "type": "String", "optional": false, "field": "keyInfo.address", "description": "E-mail address listed in public key
" }, { "group": "Success 200", "type": "String", "optional": false, "field": "keyInfo.fingerprint", "description": "Fingerprint of the public key
" }, { "group": "Success 200", "type": "String[]", "optional": false, "field": "forward", "description": "A list of email addresses to forward all incoming emails
" }, { "group": "Success 200", "type": "String", "optional": false, "field": "targetUrl", "description": "An URL to post all incoming emails
" }, { "group": "Success 200", "type": "Object", "optional": false, "field": "limits", "description": "Account limits and usage
" }, { "group": "Success 200", "type": "Object", "optional": false, "field": "limits.quota", "description": "Quota usage limits
" }, { "group": "Success 200", "type": "Number", "optional": false, "field": "limits.quota.allowed", "description": "Allowed quota of the user in bytes
" }, { "group": "Success 200", "type": "Number", "optional": false, "field": "limits.quota.used", "description": "Space used in bytes
" }, { "group": "Success 200", "type": "Object", "optional": false, "field": "limits.recipients", "description": "Sending quota
" }, { "group": "Success 200", "type": "Number", "optional": false, "field": "limits.recipients.allowed", "description": "How many messages per 24 hour can be sent
" }, { "group": "Success 200", "type": "Number", "optional": false, "field": "limits.recipients.used", "description": "How many messages are sent during current 24 hour period
" }, { "group": "Success 200", "type": "Number", "optional": false, "field": "limits.recipients.ttl", "description": "Time until the end of current 24 hour period
" }, { "group": "Success 200", "type": "Object", "optional": false, "field": "limits.forwards", "description": "Forwarding quota
" }, { "group": "Success 200", "type": "Number", "optional": false, "field": "limits.forwards.allowed", "description": "How many messages per 24 hour can be forwarded
" }, { "group": "Success 200", "type": "Number", "optional": false, "field": "limits.forwards.used", "description": "How many messages are forwarded during current 24 hour period
" }, { "group": "Success 200", "type": "Number", "optional": false, "field": "limits.forwards.ttl", "description": "Time until the end of current 24 hour period
" }, { "group": "Success 200", "type": "String[]", "optional": false, "field": "tags", "description": "List of tags associated with the User
" }, { "group": "Success 200", "type": "Boolean", "optional": false, "field": "hasPasswordSet", "description": "If true
then the User has a password set and can authenticate
Is the account activated
" }, { "group": "Success 200", "type": "Boolean", "optional": false, "field": "disabled", "description": "If true
then the user can not authenticate or receive any new mail
Description of the error
" } ] }, "examples": [ { "title": "Error-Response:", "content": "HTTP/1.1 200 OK\n{\n \"error\": \"This user does not exist\"\n}", "type": "json" } ] }, "examples": [ { "title": "Example usage:", "content": "curl -i http://localhost:8080/users/59fc66a03e54454869460e45", "type": "curl" } ], "version": "0.0.0", "filename": "lib/api/users.js", "groupTitle": "Users" }, { "type": "get", "url": "/users", "title": "List registered Users", "name": "GetUsers", "group": "Users", "header": { "fields": { "Header": [ { "group": "Header", "type": "String", "optional": false, "field": "X-Access-Token", "description": "Optional access token if authentication is enabled
" } ] }, "examples": [ { "title": "Header-Example:", "content": "{\n \"X-Access-Token\": \"59fc66a03e54454869460e45\"\n}", "type": "json" } ] }, "parameter": { "fields": { "Parameter": [ { "group": "Parameter", "type": "String", "optional": true, "field": "query", "description": "Partial match of username or default email address
" }, { "group": "Parameter", "type": "String", "optional": true, "field": "tags", "description": "Comma separated list of tags. The User must have at least one to be set
" }, { "group": "Parameter", "type": "String", "optional": true, "field": "requiredTags", "description": "Comma separated list of tags. The User must have all listed tags to be set
" }, { "group": "Parameter", "type": "Number", "optional": true, "field": "limit", "defaultValue": "20", "description": "How many records to return
" }, { "group": "Parameter", "type": "Number", "optional": true, "field": "page", "defaultValue": "1", "description": "Current page number. Informational only, page numbers start from 1
" }, { "group": "Parameter", "type": "Number", "optional": true, "field": "next", "description": "Cursor value for next page, retrieved from nextCursor
response value
Cursor value for previous page, retrieved from previousCursor
response value
Indicates successful response
" }, { "group": "Success 200", "type": "Number", "optional": false, "field": "total", "description": "How many results were found
" }, { "group": "Success 200", "type": "Number", "optional": false, "field": "page", "description": "Current page number. Derived from page
query argument
Either a cursor string or false if there are not any previous results
" }, { "group": "Success 200", "type": "String", "optional": false, "field": "nextCursor", "description": "Either a cursor string or false if there are not any next results
" }, { "group": "Success 200", "type": "Object[]", "optional": false, "field": "results", "description": "User listing
" }, { "group": "Success 200", "type": "String", "optional": false, "field": "results.id", "description": "Users unique ID (24 byte hex)
" }, { "group": "Success 200", "type": "String", "optional": false, "field": "results.username", "description": "Username of the User
" }, { "group": "Success 200", "type": "String", "optional": false, "field": "results.name", "description": "Name of the User
" }, { "group": "Success 200", "type": "String", "optional": false, "field": "results.address", "description": "Main email address of the User
" }, { "group": "Success 200", "type": "String[]", "optional": false, "field": "results.tags", "description": "List of tags associated with the User'
" }, { "group": "Success 200", "type": "String[]", "optional": false, "field": "results.forward", "description": "A list of email addresses to forward all incoming emails
" }, { "group": "Success 200", "type": "Boolean", "optional": false, "field": "results.encryptMessages", "description": "If true
then received messages are encrypted
If true
then forwarded messages are encrypted
Quota usage limits
" }, { "group": "Success 200", "type": "Number", "optional": false, "field": "results.quota.allowed", "description": "Allowed quota of the user in bytes
" }, { "group": "Success 200", "type": "Number", "optional": false, "field": "results.quota.used", "description": "Space used in bytes
" }, { "group": "Success 200", "type": "Boolean", "optional": false, "field": "results.hasPasswordSet", "description": "If true
then the User has a password set and can authenticate
Is the account activated
" }, { "group": "Success 200", "type": "Boolean", "optional": false, "field": "results.disabled", "description": "If true
then the user can not authenticate or receive any new mail
Description of the error
" } ] }, "examples": [ { "title": "Error-Response:", "content": "HTTP/1.1 200 OK\n{\n \"error\": \"Database error\"\n}", "type": "json" } ] }, "examples": [ { "title": "Example usage:", "content": "curl -i http://localhost:8080/users", "type": "curl" } ], "version": "0.0.0", "filename": "lib/api/users.js", "groupTitle": "Users" }, { "type": "post", "url": "/users", "title": "Create new user", "name": "PostUser", "group": "Users", "header": { "fields": { "Header": [ { "group": "Header", "type": "String", "optional": false, "field": "X-Access-Token", "description": "Optional access token if authentication is enabled
" } ] }, "examples": [ { "title": "Header-Example:", "content": "{\n \"X-Access-Token\": \"59fc66a03e54454869460e45\"\n}", "type": "json" } ] }, "parameter": { "fields": { "Parameter": [ { "group": "Parameter", "type": "String", "optional": false, "field": "name", "description": "Username of the User
" }, { "group": "Parameter", "type": "String", "optional": false, "field": "password", "description": "New password for the account
" }, { "group": "Parameter", "type": "String", "optional": true, "field": "address", "description": "Default email address for the User (autogenerated if not set)
" }, { "group": "Parameter", "type": "Boolean", "optional": true, "field": "emptyAddress", "description": "If true then do not autogenerate missing email address for the User. Only needed if you want to create an user account that does not have any email address associated
" }, { "group": "Parameter", "type": "Number", "optional": true, "field": "retention", "description": "Default retention time in ms. Set to 0
to disable
If true
then received messages are encrypted
If true
then forwarded messages are encrypted
Public PGP key for the User that is used for encryption. Use empty string to remove the key
" }, { "group": "Parameter", "type": "String", "optional": true, "field": "language", "description": "Language code for the User
" }, { "group": "Parameter", "type": "String[]", "optional": true, "field": "forward", "description": "A list of email addresses to forward all incoming emails
" }, { "group": "Parameter", "type": "String", "optional": true, "field": "targetUrl", "description": "An URL to post all incoming emails
" }, { "group": "Parameter", "type": "Number", "optional": true, "field": "quota", "description": "Allowed quota of the user in bytes
" }, { "group": "Parameter", "type": "Number", "optional": true, "field": "recipients", "description": "How many messages per 24 hour can be sent
" }, { "group": "Parameter", "type": "Number", "optional": true, "field": "forwards", "description": "How many messages per 24 hour can be forwarded
" }, { "group": "Parameter", "type": "Boolean", "optional": true, "field": "disabled", "description": "If true then disables user account (can not login, can not receive messages)
" }, { "group": "Parameter", "type": "String", "optional": true, "field": "sess", "description": "Session identifier for the logs
" }, { "group": "Parameter", "type": "String", "optional": true, "field": "ip", "description": "IP address for the logs
" } ] } }, "success": { "fields": { "Success 200": [ { "group": "Success 200", "type": "Boolean", "optional": false, "field": "success", "description": "Indicates successful response
" }, { "group": "Success 200", "type": "String", "optional": false, "field": "id", "description": "ID for the created User
" } ] }, "examples": [ { "title": "Success-Response:", "content": "HTTP/1.1 200 OK\n{\n \"success\": true,\n \"id\": \"5a1bda70bfbd1442cd96c6f0\"\n}", "type": "json" } ] }, "error": { "fields": { "Error 4xx": [ { "group": "Error 4xx", "optional": false, "field": "error", "description": "Description of the error
" } ] }, "examples": [ { "title": "Error-Response:", "content": "HTTP/1.1 200 OK\n{\n \"error\": \"This username already exists\"\n}", "type": "json" } ] }, "examples": [ { "title": "Example usage:", "content": "curl -i -XPOST http://localhost:8080/users \\\n-H 'Content-type: application/json' \\\n-d '{\n \"username\": \"myuser\",\n \"password\": \"verysecret\",\n \"name\": \"John Doe\"\n}'", "type": "curl" } ], "version": "0.0.0", "filename": "lib/api/users.js", "groupTitle": "Users" }, { "type": "post", "url": "/users/:id/quota/reset", "title": "Recalculate User quota", "name": "PostUserQuota", "group": "Users", "description": "This method recalculates quota usage for an User. Normally not needed, only use it if quota numbers are way off. This method is not transactional, so if the user is currently receiving new messages then the resulting value is not exact.
", "header": { "fields": { "Header": [ { "group": "Header", "type": "String", "optional": false, "field": "X-Access-Token", "description": "Optional access token if authentication is enabled
" } ] }, "examples": [ { "title": "Header-Example:", "content": "{\n \"X-Access-Token\": \"59fc66a03e54454869460e45\"\n}", "type": "json" } ] }, "parameter": { "fields": { "Parameter": [ { "group": "Parameter", "type": "String", "optional": false, "field": "id", "description": "Users unique ID.
" }, { "group": "Parameter", "type": "String", "optional": true, "field": "reason", "description": "Message to be shown to connected IMAP client
" } ] } }, "success": { "fields": { "Success 200": [ { "group": "Success 200", "type": "Boolean", "optional": false, "field": "success", "description": "Indicates successful response
" }, { "group": "Success 200", "type": "Number", "optional": false, "field": "storageUsed", "description": "Calculated quota usage for the user
" } ] }, "examples": [ { "title": "Success-Response:", "content": "HTTP/1.1 200 OK\n{\n \"success\": true,\n \"storageUsed\": 1234567\n}", "type": "json" } ] }, "error": { "fields": { "Error 4xx": [ { "group": "Error 4xx", "optional": false, "field": "error", "description": "Description of the error
" } ] }, "examples": [ { "title": "Error-Response:", "content": "HTTP/1.1 200 OK\n{\n \"error\": \"This user does not exist\"\n}", "type": "json" } ] }, "examples": [ { "title": "Example usage:", "content": "curl -i -XPOST http://localhost:8080/users/59fc66a03e54454869460e45/quota/reset \\\n-H 'Content-type: application/json' \\\n-d '{}'", "type": "curl" } ], "version": "0.0.0", "filename": "lib/api/users.js", "groupTitle": "Users" }, { "type": "put", "url": "/users/:id", "title": "Update User information", "name": "PutUser", "group": "Users", "header": { "fields": { "Header": [ { "group": "Header", "type": "String", "optional": false, "field": "X-Access-Token", "description": "Optional access token if authentication is enabled
" } ] }, "examples": [ { "title": "Header-Example:", "content": "{\n \"X-Access-Token\": \"59fc66a03e54454869460e45\"\n}", "type": "json" } ] }, "parameter": { "fields": { "Parameter": [ { "group": "Parameter", "type": "String", "optional": false, "field": "id", "description": "Users unique ID.
" }, { "group": "Parameter", "type": "String", "optional": true, "field": "name", "description": "Name of the User
" }, { "group": "Parameter", "type": "String", "optional": true, "field": "existingPassword", "description": "If provided then validates against account password before applying any changes
" }, { "group": "Parameter", "type": "String", "optional": true, "field": "password", "description": "New password for the account
" }, { "group": "Parameter", "type": "Number", "optional": true, "field": "retention", "description": "Default retention time in ms. Set to 0
to disable
If true
then received messages are encrypted
If true
then forwarded messages are encrypted
Public PGP key for the User that is used for encryption. Use empty string to remove the key
" }, { "group": "Parameter", "type": "String", "optional": true, "field": "language", "description": "Language code for the User
" }, { "group": "Parameter", "type": "String[]", "optional": true, "field": "forward", "description": "A list of email addresses to forward all incoming emails
" }, { "group": "Parameter", "type": "String", "optional": true, "field": "targetUrl", "description": "An URL to post all incoming emails
" }, { "group": "Parameter", "type": "Number", "optional": true, "field": "quota", "description": "Allowed quota of the user in bytes
" }, { "group": "Parameter", "type": "Number", "optional": true, "field": "recipients", "description": "How many messages per 24 hour can be sent
" }, { "group": "Parameter", "type": "Number", "optional": true, "field": "forwards", "description": "How many messages per 24 hour can be forwarded
" }, { "group": "Parameter", "type": "Boolean", "optional": true, "field": "disabled", "description": "If true then disables user account (can not login, can not receive messages)
" }, { "group": "Parameter", "type": "String", "optional": true, "field": "sess", "description": "Session identifier for the logs
" }, { "group": "Parameter", "type": "String", "optional": true, "field": "ip", "description": "IP address for the logs
" } ] } }, "success": { "fields": { "Success 200": [ { "group": "Success 200", "type": "Boolean", "optional": false, "field": "success", "description": "Indicates successful response
" } ] }, "examples": [ { "title": "Success-Response:", "content": "HTTP/1.1 200 OK\n{\n \"success\": true\n}", "type": "json" } ] }, "error": { "fields": { "Error 4xx": [ { "group": "Error 4xx", "optional": false, "field": "error", "description": "Description of the error
" } ] }, "examples": [ { "title": "Error-Response:", "content": "HTTP/1.1 200 OK\n{\n \"error\": \"This user does not exist\"\n}", "type": "json" } ] }, "examples": [ { "title": "Example usage:", "content": "curl -i -XPUT http://localhost:8080/users/59fc66a03e54454869460e45 \\\n-H 'Content-type: application/json' \\\n-d '{\n \"name\": \"Updated user name\"\n}'", "type": "curl" } ], "version": "0.0.0", "filename": "lib/api/users.js", "groupTitle": "Users" }, { "type": "put", "url": "/users/:id/logout", "title": "Log out User", "name": "PutUserLogout", "group": "Users", "description": "This method logs out all user sessions in IMAP
", "header": { "fields": { "Header": [ { "group": "Header", "type": "String", "optional": false, "field": "X-Access-Token", "description": "Optional access token if authentication is enabled
" } ] }, "examples": [ { "title": "Header-Example:", "content": "{\n \"X-Access-Token\": \"59fc66a03e54454869460e45\"\n}", "type": "json" } ] }, "parameter": { "fields": { "Parameter": [ { "group": "Parameter", "type": "String", "optional": false, "field": "id", "description": "Users unique ID.
" }, { "group": "Parameter", "type": "String", "optional": true, "field": "reason", "description": "Message to be shown to connected IMAP client
" } ] } }, "success": { "fields": { "Success 200": [ { "group": "Success 200", "type": "Boolean", "optional": false, "field": "success", "description": "Indicates successful response
" } ] }, "examples": [ { "title": "Success-Response:", "content": "HTTP/1.1 200 OK\n{\n \"success\": true\n}", "type": "json" } ] }, "error": { "fields": { "Error 4xx": [ { "group": "Error 4xx", "optional": false, "field": "error", "description": "Description of the error
" } ] }, "examples": [ { "title": "Error-Response:", "content": "HTTP/1.1 200 OK\n{\n \"error\": \"This user does not exist\"\n}", "type": "json" } ] }, "examples": [ { "title": "Example usage:", "content": "curl -i -XPUT http://localhost:8080/users/59fc66a03e54454869460e45/logout \\\n-H 'Content-type: application/json' \\\n-d '{\n \"reason\": \"Logout requested from API\"\n}'", "type": "curl" } ], "version": "0.0.0", "filename": "lib/api/users.js", "groupTitle": "Users" }, { "type": "post", "url": "/users/:id/password/reset", "title": "Reset password for an User", "name": "ResetUserPassword", "group": "Users", "description": "This method generates a new temporary password for an User. Additionally it removes all two-factor authentication settings
", "header": { "fields": { "Header": [ { "group": "Header", "type": "String", "optional": false, "field": "X-Access-Token", "description": "Optional access token if authentication is enabled
" } ] }, "examples": [ { "title": "Header-Example:", "content": "{\n \"X-Access-Token\": \"59fc66a03e54454869460e45\"\n}", "type": "json" } ] }, "parameter": { "fields": { "Parameter": [ { "group": "Parameter", "type": "String", "optional": false, "field": "id", "description": "Users unique ID.
" }, { "group": "Parameter", "type": "String", "optional": true, "field": "sess", "description": "Session identifier for the logs
" }, { "group": "Parameter", "type": "String", "optional": true, "field": "ip", "description": "IP address for the logs
" } ] } }, "success": { "fields": { "Success 200": [ { "group": "Success 200", "type": "Boolean", "optional": false, "field": "success", "description": "Indicates successful response
" }, { "group": "Success 200", "type": "String", "optional": false, "field": "password", "description": "Temporary password
" } ] }, "examples": [ { "title": "Success-Response:", "content": "HTTP/1.1 200 OK\n{\n \"success\": true,\n \"password\": \"temporarypass\"\n}", "type": "json" } ] }, "error": { "fields": { "Error 4xx": [ { "group": "Error 4xx", "optional": false, "field": "error", "description": "Description of the error
" } ] }, "examples": [ { "title": "Error-Response:", "content": "HTTP/1.1 200 OK\n{\n \"error\": \"This user does not exist\"\n}", "type": "json" } ] }, "examples": [ { "title": "Example usage:", "content": "curl -i -XPOST http://localhost:8080/users/5a1bda70bfbd1442cd96/password/reset \\\n-H 'Content-type: application/json' \\\n-d '{\n \"ip\": \"127.0.0.1\"\n}'", "type": "curl" } ], "version": "0.0.0", "filename": "lib/api/users.js", "groupTitle": "Users" } ] }); diff --git a/docs/api_data.json b/docs/api_data.json new file mode 100644 index 00000000..32e2e688 --- /dev/null +++ b/docs/api_data.json @@ -0,0 +1 @@ +[ { "type": "delete", "url": "/users/:id", "title": "Delete an User", "name": "DeleteUser", "group": "Users", "header": { "fields": { "Header": [ { "group": "Header", "type": "String", "optional": false, "field": "X-Access-Token", "description": "Optional access token if authentication is enabled
" } ] }, "examples": [ { "title": "Header-Example:", "content": "{\n \"X-Access-Token\": \"59fc66a03e54454869460e45\"\n}", "type": "json" } ] }, "parameter": { "fields": { "Parameter": [ { "group": "Parameter", "type": "String", "optional": false, "field": "id", "description": "Users unique ID.
" }, { "group": "Parameter", "type": "String", "optional": true, "field": "sess", "description": "Session identifier for the logs
" }, { "group": "Parameter", "type": "String", "optional": true, "field": "ip", "description": "IP address for the logs
" } ] } }, "success": { "fields": { "Success 200": [ { "group": "Success 200", "type": "Boolean", "optional": false, "field": "success", "description": "Indicates successful response
" } ] }, "examples": [ { "title": "Success-Response:", "content": "HTTP/1.1 200 OK\n{\n \"success\": true\n}", "type": "json" } ] }, "error": { "fields": { "Error 4xx": [ { "group": "Error 4xx", "optional": false, "field": "error", "description": "Description of the error
" } ] }, "examples": [ { "title": "Error-Response:", "content": "HTTP/1.1 200 OK\n{\n \"error\": \"This user does not exist\"\n}", "type": "json" } ] }, "examples": [ { "title": "Example usage:", "content": "curl -i -XDELETE http://localhost:8080/users/5a1bda70bfbd1442cd96c6f0?ip=127.0.0.1", "type": "curl" } ], "version": "0.0.0", "filename": "lib/api/users.js", "groupTitle": "Users" }, { "type": "get", "url": "/users/:id", "title": "Request User information", "name": "GetUser", "group": "Users", "header": { "fields": { "Header": [ { "group": "Header", "type": "String", "optional": false, "field": "X-Access-Token", "description": "Optional access token if authentication is enabled
" } ] }, "examples": [ { "title": "Header-Example:", "content": "{\n \"X-Access-Token\": \"59fc66a03e54454869460e45\"\n}", "type": "json" } ] }, "parameter": { "fields": { "Parameter": [ { "group": "Parameter", "type": "String", "optional": false, "field": "id", "description": "Users unique ID.
" } ] } }, "success": { "fields": { "Success 200": [ { "group": "Success 200", "type": "Boolean", "optional": false, "field": "success", "description": "Indicates successful response
" }, { "group": "Success 200", "type": "String", "optional": false, "field": "id", "description": "Users unique ID (24 byte hex)
" }, { "group": "Success 200", "type": "String", "optional": false, "field": "username", "description": "Username of the User
" }, { "group": "Success 200", "type": "String", "optional": false, "field": "name", "description": "Name of the User
" }, { "group": "Success 200", "type": "String", "optional": false, "field": "address", "description": "Main email address of the User
" }, { "group": "Success 200", "type": "Number", "optional": false, "field": "retention", "description": "Default retention time in ms. false
if not enabled
List of enabled 2FA methods
" }, { "group": "Success 200", "type": "Boolean", "optional": false, "field": "encryptMessages", "description": "If true
then received messages are encrypted
If true
then forwarded messages are encrypted
Public PGP key for the User that is used for encryption
" }, { "group": "Success 200", "type": "Object", "optional": false, "field": "keyInfo", "description": "Information about public key or false
if key is not available
Name listed in public key
" }, { "group": "Success 200", "type": "String", "optional": false, "field": "keyInfo.address", "description": "E-mail address listed in public key
" }, { "group": "Success 200", "type": "String", "optional": false, "field": "keyInfo.fingerprint", "description": "Fingerprint of the public key
" }, { "group": "Success 200", "type": "String[]", "optional": false, "field": "forward", "description": "A list of email addresses to forward all incoming emails
" }, { "group": "Success 200", "type": "String", "optional": false, "field": "targetUrl", "description": "An URL to post all incoming emails
" }, { "group": "Success 200", "type": "Object", "optional": false, "field": "limits", "description": "Account limits and usage
" }, { "group": "Success 200", "type": "Object", "optional": false, "field": "limits.quota", "description": "Quota usage limits
" }, { "group": "Success 200", "type": "Number", "optional": false, "field": "limits.quota.allowed", "description": "Allowed quota of the user in bytes
" }, { "group": "Success 200", "type": "Number", "optional": false, "field": "limits.quota.used", "description": "Space used in bytes
" }, { "group": "Success 200", "type": "Object", "optional": false, "field": "limits.recipients", "description": "Sending quota
" }, { "group": "Success 200", "type": "Number", "optional": false, "field": "limits.recipients.allowed", "description": "How many messages per 24 hour can be sent
" }, { "group": "Success 200", "type": "Number", "optional": false, "field": "limits.recipients.used", "description": "How many messages are sent during current 24 hour period
" }, { "group": "Success 200", "type": "Number", "optional": false, "field": "limits.recipients.ttl", "description": "Time until the end of current 24 hour period
" }, { "group": "Success 200", "type": "Object", "optional": false, "field": "limits.forwards", "description": "Forwarding quota
" }, { "group": "Success 200", "type": "Number", "optional": false, "field": "limits.forwards.allowed", "description": "How many messages per 24 hour can be forwarded
" }, { "group": "Success 200", "type": "Number", "optional": false, "field": "limits.forwards.used", "description": "How many messages are forwarded during current 24 hour period
" }, { "group": "Success 200", "type": "Number", "optional": false, "field": "limits.forwards.ttl", "description": "Time until the end of current 24 hour period
" }, { "group": "Success 200", "type": "String[]", "optional": false, "field": "tags", "description": "List of tags associated with the User
" }, { "group": "Success 200", "type": "Boolean", "optional": false, "field": "hasPasswordSet", "description": "If true
then the User has a password set and can authenticate
Is the account activated
" }, { "group": "Success 200", "type": "Boolean", "optional": false, "field": "disabled", "description": "If true
then the user can not authenticate or receive any new mail
Description of the error
" } ] }, "examples": [ { "title": "Error-Response:", "content": "HTTP/1.1 200 OK\n{\n \"error\": \"This user does not exist\"\n}", "type": "json" } ] }, "examples": [ { "title": "Example usage:", "content": "curl -i http://localhost:8080/users/59fc66a03e54454869460e45", "type": "curl" } ], "version": "0.0.0", "filename": "lib/api/users.js", "groupTitle": "Users" }, { "type": "get", "url": "/users", "title": "List registered Users", "name": "GetUsers", "group": "Users", "header": { "fields": { "Header": [ { "group": "Header", "type": "String", "optional": false, "field": "X-Access-Token", "description": "Optional access token if authentication is enabled
" } ] }, "examples": [ { "title": "Header-Example:", "content": "{\n \"X-Access-Token\": \"59fc66a03e54454869460e45\"\n}", "type": "json" } ] }, "parameter": { "fields": { "Parameter": [ { "group": "Parameter", "type": "String", "optional": true, "field": "query", "description": "Partial match of username or default email address
" }, { "group": "Parameter", "type": "String", "optional": true, "field": "tags", "description": "Comma separated list of tags. The User must have at least one to be set
" }, { "group": "Parameter", "type": "String", "optional": true, "field": "requiredTags", "description": "Comma separated list of tags. The User must have all listed tags to be set
" }, { "group": "Parameter", "type": "Number", "optional": true, "field": "limit", "defaultValue": "20", "description": "How many records to return
" }, { "group": "Parameter", "type": "Number", "optional": true, "field": "page", "defaultValue": "1", "description": "Current page number. Informational only, page numbers start from 1
" }, { "group": "Parameter", "type": "Number", "optional": true, "field": "next", "description": "Cursor value for next page, retrieved from nextCursor
response value
Cursor value for previous page, retrieved from previousCursor
response value
Indicates successful response
" }, { "group": "Success 200", "type": "Number", "optional": false, "field": "total", "description": "How many results were found
" }, { "group": "Success 200", "type": "Number", "optional": false, "field": "page", "description": "Current page number. Derived from page
query argument
Either a cursor string or false if there are not any previous results
" }, { "group": "Success 200", "type": "String", "optional": false, "field": "nextCursor", "description": "Either a cursor string or false if there are not any next results
" }, { "group": "Success 200", "type": "Object[]", "optional": false, "field": "results", "description": "User listing
" }, { "group": "Success 200", "type": "String", "optional": false, "field": "results.id", "description": "Users unique ID (24 byte hex)
" }, { "group": "Success 200", "type": "String", "optional": false, "field": "results.username", "description": "Username of the User
" }, { "group": "Success 200", "type": "String", "optional": false, "field": "results.name", "description": "Name of the User
" }, { "group": "Success 200", "type": "String", "optional": false, "field": "results.address", "description": "Main email address of the User
" }, { "group": "Success 200", "type": "String[]", "optional": false, "field": "results.tags", "description": "List of tags associated with the User'
" }, { "group": "Success 200", "type": "String[]", "optional": false, "field": "results.forward", "description": "A list of email addresses to forward all incoming emails
" }, { "group": "Success 200", "type": "Boolean", "optional": false, "field": "results.encryptMessages", "description": "If true
then received messages are encrypted
If true
then forwarded messages are encrypted
Quota usage limits
" }, { "group": "Success 200", "type": "Number", "optional": false, "field": "results.quota.allowed", "description": "Allowed quota of the user in bytes
" }, { "group": "Success 200", "type": "Number", "optional": false, "field": "results.quota.used", "description": "Space used in bytes
" }, { "group": "Success 200", "type": "Boolean", "optional": false, "field": "results.hasPasswordSet", "description": "If true
then the User has a password set and can authenticate
Is the account activated
" }, { "group": "Success 200", "type": "Boolean", "optional": false, "field": "results.disabled", "description": "If true
then the user can not authenticate or receive any new mail
Description of the error
" } ] }, "examples": [ { "title": "Error-Response:", "content": "HTTP/1.1 200 OK\n{\n \"error\": \"Database error\"\n}", "type": "json" } ] }, "examples": [ { "title": "Example usage:", "content": "curl -i http://localhost:8080/users", "type": "curl" } ], "version": "0.0.0", "filename": "lib/api/users.js", "groupTitle": "Users" }, { "type": "post", "url": "/users", "title": "Create new user", "name": "PostUser", "group": "Users", "header": { "fields": { "Header": [ { "group": "Header", "type": "String", "optional": false, "field": "X-Access-Token", "description": "Optional access token if authentication is enabled
" } ] }, "examples": [ { "title": "Header-Example:", "content": "{\n \"X-Access-Token\": \"59fc66a03e54454869460e45\"\n}", "type": "json" } ] }, "parameter": { "fields": { "Parameter": [ { "group": "Parameter", "type": "String", "optional": false, "field": "name", "description": "Username of the User
" }, { "group": "Parameter", "type": "String", "optional": false, "field": "password", "description": "New password for the account
" }, { "group": "Parameter", "type": "String", "optional": true, "field": "address", "description": "Default email address for the User (autogenerated if not set)
" }, { "group": "Parameter", "type": "Boolean", "optional": true, "field": "emptyAddress", "description": "If true then do not autogenerate missing email address for the User. Only needed if you want to create an user account that does not have any email address associated
" }, { "group": "Parameter", "type": "Number", "optional": true, "field": "retention", "description": "Default retention time in ms. Set to 0
to disable
If true
then received messages are encrypted
If true
then forwarded messages are encrypted
Public PGP key for the User that is used for encryption. Use empty string to remove the key
" }, { "group": "Parameter", "type": "String", "optional": true, "field": "language", "description": "Language code for the User
" }, { "group": "Parameter", "type": "String[]", "optional": true, "field": "forward", "description": "A list of email addresses to forward all incoming emails
" }, { "group": "Parameter", "type": "String", "optional": true, "field": "targetUrl", "description": "An URL to post all incoming emails
" }, { "group": "Parameter", "type": "Number", "optional": true, "field": "quota", "description": "Allowed quota of the user in bytes
" }, { "group": "Parameter", "type": "Number", "optional": true, "field": "recipients", "description": "How many messages per 24 hour can be sent
" }, { "group": "Parameter", "type": "Number", "optional": true, "field": "forwards", "description": "How many messages per 24 hour can be forwarded
" }, { "group": "Parameter", "type": "Boolean", "optional": true, "field": "disabled", "description": "If true then disables user account (can not login, can not receive messages)
" }, { "group": "Parameter", "type": "String", "optional": true, "field": "sess", "description": "Session identifier for the logs
" }, { "group": "Parameter", "type": "String", "optional": true, "field": "ip", "description": "IP address for the logs
" } ] } }, "success": { "fields": { "Success 200": [ { "group": "Success 200", "type": "Boolean", "optional": false, "field": "success", "description": "Indicates successful response
" }, { "group": "Success 200", "type": "String", "optional": false, "field": "id", "description": "ID for the created User
" } ] }, "examples": [ { "title": "Success-Response:", "content": "HTTP/1.1 200 OK\n{\n \"success\": true,\n \"id\": \"5a1bda70bfbd1442cd96c6f0\"\n}", "type": "json" } ] }, "error": { "fields": { "Error 4xx": [ { "group": "Error 4xx", "optional": false, "field": "error", "description": "Description of the error
" } ] }, "examples": [ { "title": "Error-Response:", "content": "HTTP/1.1 200 OK\n{\n \"error\": \"This username already exists\"\n}", "type": "json" } ] }, "examples": [ { "title": "Example usage:", "content": "curl -i -XPOST http://localhost:8080/users \\\n-H 'Content-type: application/json' \\\n-d '{\n \"username\": \"myuser\",\n \"password\": \"verysecret\",\n \"name\": \"John Doe\"\n}'", "type": "curl" } ], "version": "0.0.0", "filename": "lib/api/users.js", "groupTitle": "Users" }, { "type": "post", "url": "/users/:id/quota/reset", "title": "Recalculate User quota", "name": "PostUserQuota", "group": "Users", "description": "This method recalculates quota usage for an User. Normally not needed, only use it if quota numbers are way off. This method is not transactional, so if the user is currently receiving new messages then the resulting value is not exact.
", "header": { "fields": { "Header": [ { "group": "Header", "type": "String", "optional": false, "field": "X-Access-Token", "description": "Optional access token if authentication is enabled
" } ] }, "examples": [ { "title": "Header-Example:", "content": "{\n \"X-Access-Token\": \"59fc66a03e54454869460e45\"\n}", "type": "json" } ] }, "parameter": { "fields": { "Parameter": [ { "group": "Parameter", "type": "String", "optional": false, "field": "id", "description": "Users unique ID.
" }, { "group": "Parameter", "type": "String", "optional": true, "field": "reason", "description": "Message to be shown to connected IMAP client
" } ] } }, "success": { "fields": { "Success 200": [ { "group": "Success 200", "type": "Boolean", "optional": false, "field": "success", "description": "Indicates successful response
" }, { "group": "Success 200", "type": "Number", "optional": false, "field": "storageUsed", "description": "Calculated quota usage for the user
" } ] }, "examples": [ { "title": "Success-Response:", "content": "HTTP/1.1 200 OK\n{\n \"success\": true,\n \"storageUsed\": 1234567\n}", "type": "json" } ] }, "error": { "fields": { "Error 4xx": [ { "group": "Error 4xx", "optional": false, "field": "error", "description": "Description of the error
" } ] }, "examples": [ { "title": "Error-Response:", "content": "HTTP/1.1 200 OK\n{\n \"error\": \"This user does not exist\"\n}", "type": "json" } ] }, "examples": [ { "title": "Example usage:", "content": "curl -i -XPOST http://localhost:8080/users/59fc66a03e54454869460e45/quota/reset \\\n-H 'Content-type: application/json' \\\n-d '{}'", "type": "curl" } ], "version": "0.0.0", "filename": "lib/api/users.js", "groupTitle": "Users" }, { "type": "put", "url": "/users/:id", "title": "Update User information", "name": "PutUser", "group": "Users", "header": { "fields": { "Header": [ { "group": "Header", "type": "String", "optional": false, "field": "X-Access-Token", "description": "Optional access token if authentication is enabled
" } ] }, "examples": [ { "title": "Header-Example:", "content": "{\n \"X-Access-Token\": \"59fc66a03e54454869460e45\"\n}", "type": "json" } ] }, "parameter": { "fields": { "Parameter": [ { "group": "Parameter", "type": "String", "optional": false, "field": "id", "description": "Users unique ID.
" }, { "group": "Parameter", "type": "String", "optional": true, "field": "name", "description": "Name of the User
" }, { "group": "Parameter", "type": "String", "optional": true, "field": "existingPassword", "description": "If provided then validates against account password before applying any changes
" }, { "group": "Parameter", "type": "String", "optional": true, "field": "password", "description": "New password for the account
" }, { "group": "Parameter", "type": "Number", "optional": true, "field": "retention", "description": "Default retention time in ms. Set to 0
to disable
If true
then received messages are encrypted
If true
then forwarded messages are encrypted
Public PGP key for the User that is used for encryption. Use empty string to remove the key
" }, { "group": "Parameter", "type": "String", "optional": true, "field": "language", "description": "Language code for the User
" }, { "group": "Parameter", "type": "String[]", "optional": true, "field": "forward", "description": "A list of email addresses to forward all incoming emails
" }, { "group": "Parameter", "type": "String", "optional": true, "field": "targetUrl", "description": "An URL to post all incoming emails
" }, { "group": "Parameter", "type": "Number", "optional": true, "field": "quota", "description": "Allowed quota of the user in bytes
" }, { "group": "Parameter", "type": "Number", "optional": true, "field": "recipients", "description": "How many messages per 24 hour can be sent
" }, { "group": "Parameter", "type": "Number", "optional": true, "field": "forwards", "description": "How many messages per 24 hour can be forwarded
" }, { "group": "Parameter", "type": "Boolean", "optional": true, "field": "disabled", "description": "If true then disables user account (can not login, can not receive messages)
" }, { "group": "Parameter", "type": "String", "optional": true, "field": "sess", "description": "Session identifier for the logs
" }, { "group": "Parameter", "type": "String", "optional": true, "field": "ip", "description": "IP address for the logs
" } ] } }, "success": { "fields": { "Success 200": [ { "group": "Success 200", "type": "Boolean", "optional": false, "field": "success", "description": "Indicates successful response
" } ] }, "examples": [ { "title": "Success-Response:", "content": "HTTP/1.1 200 OK\n{\n \"success\": true\n}", "type": "json" } ] }, "error": { "fields": { "Error 4xx": [ { "group": "Error 4xx", "optional": false, "field": "error", "description": "Description of the error
" } ] }, "examples": [ { "title": "Error-Response:", "content": "HTTP/1.1 200 OK\n{\n \"error\": \"This user does not exist\"\n}", "type": "json" } ] }, "examples": [ { "title": "Example usage:", "content": "curl -i -XPUT http://localhost:8080/users/59fc66a03e54454869460e45 \\\n-H 'Content-type: application/json' \\\n-d '{\n \"name\": \"Updated user name\"\n}'", "type": "curl" } ], "version": "0.0.0", "filename": "lib/api/users.js", "groupTitle": "Users" }, { "type": "put", "url": "/users/:id/logout", "title": "Log out User", "name": "PutUserLogout", "group": "Users", "description": "This method logs out all user sessions in IMAP
", "header": { "fields": { "Header": [ { "group": "Header", "type": "String", "optional": false, "field": "X-Access-Token", "description": "Optional access token if authentication is enabled
" } ] }, "examples": [ { "title": "Header-Example:", "content": "{\n \"X-Access-Token\": \"59fc66a03e54454869460e45\"\n}", "type": "json" } ] }, "parameter": { "fields": { "Parameter": [ { "group": "Parameter", "type": "String", "optional": false, "field": "id", "description": "Users unique ID.
" }, { "group": "Parameter", "type": "String", "optional": true, "field": "reason", "description": "Message to be shown to connected IMAP client
" } ] } }, "success": { "fields": { "Success 200": [ { "group": "Success 200", "type": "Boolean", "optional": false, "field": "success", "description": "Indicates successful response
" } ] }, "examples": [ { "title": "Success-Response:", "content": "HTTP/1.1 200 OK\n{\n \"success\": true\n}", "type": "json" } ] }, "error": { "fields": { "Error 4xx": [ { "group": "Error 4xx", "optional": false, "field": "error", "description": "Description of the error
" } ] }, "examples": [ { "title": "Error-Response:", "content": "HTTP/1.1 200 OK\n{\n \"error\": \"This user does not exist\"\n}", "type": "json" } ] }, "examples": [ { "title": "Example usage:", "content": "curl -i -XPUT http://localhost:8080/users/59fc66a03e54454869460e45/logout \\\n-H 'Content-type: application/json' \\\n-d '{\n \"reason\": \"Logout requested from API\"\n}'", "type": "curl" } ], "version": "0.0.0", "filename": "lib/api/users.js", "groupTitle": "Users" }, { "type": "post", "url": "/users/:id/password/reset", "title": "Reset password for an User", "name": "ResetUserPassword", "group": "Users", "description": "This method generates a new temporary password for an User. Additionally it removes all two-factor authentication settings
", "header": { "fields": { "Header": [ { "group": "Header", "type": "String", "optional": false, "field": "X-Access-Token", "description": "Optional access token if authentication is enabled
" } ] }, "examples": [ { "title": "Header-Example:", "content": "{\n \"X-Access-Token\": \"59fc66a03e54454869460e45\"\n}", "type": "json" } ] }, "parameter": { "fields": { "Parameter": [ { "group": "Parameter", "type": "String", "optional": false, "field": "id", "description": "Users unique ID.
" }, { "group": "Parameter", "type": "String", "optional": true, "field": "sess", "description": "Session identifier for the logs
" }, { "group": "Parameter", "type": "String", "optional": true, "field": "ip", "description": "IP address for the logs
" } ] } }, "success": { "fields": { "Success 200": [ { "group": "Success 200", "type": "Boolean", "optional": false, "field": "success", "description": "Indicates successful response
" }, { "group": "Success 200", "type": "String", "optional": false, "field": "password", "description": "Temporary password
" } ] }, "examples": [ { "title": "Success-Response:", "content": "HTTP/1.1 200 OK\n{\n \"success\": true,\n \"password\": \"temporarypass\"\n}", "type": "json" } ] }, "error": { "fields": { "Error 4xx": [ { "group": "Error 4xx", "optional": false, "field": "error", "description": "Description of the error
" } ] }, "examples": [ { "title": "Error-Response:", "content": "HTTP/1.1 200 OK\n{\n \"error\": \"This user does not exist\"\n}", "type": "json" } ] }, "examples": [ { "title": "Example usage:", "content": "curl -i -XPOST http://localhost:8080/users/5a1bda70bfbd1442cd96/password/reset \\\n-H 'Content-type: application/json' \\\n-d '{\n \"ip\": \"127.0.0.1\"\n}'", "type": "curl" } ], "version": "0.0.0", "filename": "lib/api/users.js", "groupTitle": "Users" } ] diff --git a/apidoc/api_project.js b/docs/api_project.js similarity index 82% rename from apidoc/api_project.js rename to docs/api_project.js index 9b42e62a..bdc47b52 100644 --- a/apidoc/api_project.js +++ b/docs/api_project.js @@ -1 +1 @@ -define({ "name": "wildduck", "version": "1.0.0", "description": "WildDuck API docs", "title": "WildDuck API", "url": "http://localhost:8080", "sampleUrl": false, "defaultVersion": "0.0.0", "apidoc": "0.3.0", "generator": { "name": "apidoc", "time": "2017-11-23T14:58:36.161Z", "url": "http://apidocjs.com", "version": "0.17.6" } }); +define({ "name": "wildduck", "version": "1.0.0", "description": "WildDuck API docs", "title": "WildDuck API", "url": "http://localhost:8080", "sampleUrl": false, "defaultVersion": "0.0.0", "apidoc": "0.3.0", "generator": { "name": "apidoc", "time": "2017-11-27T12:20:35.334Z", "url": "http://apidocjs.com", "version": "0.17.6" } }); diff --git a/apidoc/api_project.json b/docs/api_project.json similarity index 82% rename from apidoc/api_project.json rename to docs/api_project.json index 36afa787..bc00e9fa 100644 --- a/apidoc/api_project.json +++ b/docs/api_project.json @@ -1 +1 @@ -{ "name": "wildduck", "version": "1.0.0", "description": "WildDuck API docs", "title": "WildDuck API", "url": "http://localhost:8080", "sampleUrl": false, "defaultVersion": "0.0.0", "apidoc": "0.3.0", "generator": { "name": "apidoc", "time": "2017-11-23T14:58:36.161Z", "url": "http://apidocjs.com", "version": "0.17.6" } } +{ "name": "wildduck", "version": "1.0.0", "description": "WildDuck API docs", "title": "WildDuck API", "url": "http://localhost:8080", "sampleUrl": false, "defaultVersion": "0.0.0", "apidoc": "0.3.0", "generator": { "name": "apidoc", "time": "2017-11-27T12:20:35.334Z", "url": "http://apidocjs.com", "version": "0.17.6" } } diff --git a/apidoc/css/style.css b/docs/css/style.css similarity index 100% rename from apidoc/css/style.css rename to docs/css/style.css diff --git a/apidoc/fonts/glyphicons-halflings-regular.eot b/docs/fonts/glyphicons-halflings-regular.eot similarity index 100% rename from apidoc/fonts/glyphicons-halflings-regular.eot rename to docs/fonts/glyphicons-halflings-regular.eot diff --git a/apidoc/fonts/glyphicons-halflings-regular.svg b/docs/fonts/glyphicons-halflings-regular.svg similarity index 100% rename from apidoc/fonts/glyphicons-halflings-regular.svg rename to docs/fonts/glyphicons-halflings-regular.svg diff --git a/apidoc/fonts/glyphicons-halflings-regular.ttf b/docs/fonts/glyphicons-halflings-regular.ttf similarity index 100% rename from apidoc/fonts/glyphicons-halflings-regular.ttf rename to docs/fonts/glyphicons-halflings-regular.ttf diff --git a/apidoc/fonts/glyphicons-halflings-regular.woff b/docs/fonts/glyphicons-halflings-regular.woff similarity index 100% rename from apidoc/fonts/glyphicons-halflings-regular.woff rename to docs/fonts/glyphicons-halflings-regular.woff diff --git a/apidoc/fonts/glyphicons-halflings-regular.woff2 b/docs/fonts/glyphicons-halflings-regular.woff2 similarity index 100% rename from apidoc/fonts/glyphicons-halflings-regular.woff2 rename to docs/fonts/glyphicons-halflings-regular.woff2 diff --git a/apidoc/img/favicon.ico b/docs/img/favicon.ico similarity index 100% rename from apidoc/img/favicon.ico rename to docs/img/favicon.ico diff --git a/apidoc/index.html b/docs/index.html similarity index 100% rename from apidoc/index.html rename to docs/index.html diff --git a/apidoc/locales/ca.js b/docs/locales/ca.js similarity index 100% rename from apidoc/locales/ca.js rename to docs/locales/ca.js diff --git a/apidoc/locales/de.js b/docs/locales/de.js similarity index 100% rename from apidoc/locales/de.js rename to docs/locales/de.js diff --git a/apidoc/locales/es.js b/docs/locales/es.js similarity index 100% rename from apidoc/locales/es.js rename to docs/locales/es.js diff --git a/apidoc/locales/fr.js b/docs/locales/fr.js similarity index 100% rename from apidoc/locales/fr.js rename to docs/locales/fr.js diff --git a/apidoc/locales/it.js b/docs/locales/it.js similarity index 100% rename from apidoc/locales/it.js rename to docs/locales/it.js diff --git a/apidoc/locales/locale.js b/docs/locales/locale.js similarity index 100% rename from apidoc/locales/locale.js rename to docs/locales/locale.js diff --git a/apidoc/locales/nl.js b/docs/locales/nl.js similarity index 100% rename from apidoc/locales/nl.js rename to docs/locales/nl.js diff --git a/apidoc/locales/pl.js b/docs/locales/pl.js similarity index 100% rename from apidoc/locales/pl.js rename to docs/locales/pl.js diff --git a/apidoc/locales/pt_br.js b/docs/locales/pt_br.js similarity index 100% rename from apidoc/locales/pt_br.js rename to docs/locales/pt_br.js diff --git a/apidoc/locales/ro.js b/docs/locales/ro.js similarity index 100% rename from apidoc/locales/ro.js rename to docs/locales/ro.js diff --git a/apidoc/locales/ru.js b/docs/locales/ru.js similarity index 100% rename from apidoc/locales/ru.js rename to docs/locales/ru.js diff --git a/apidoc/locales/tr.js b/docs/locales/tr.js similarity index 100% rename from apidoc/locales/tr.js rename to docs/locales/tr.js diff --git a/apidoc/locales/vi.js b/docs/locales/vi.js similarity index 100% rename from apidoc/locales/vi.js rename to docs/locales/vi.js diff --git a/apidoc/locales/zh.js b/docs/locales/zh.js similarity index 100% rename from apidoc/locales/zh.js rename to docs/locales/zh.js diff --git a/apidoc/locales/zh_cn.js b/docs/locales/zh_cn.js similarity index 100% rename from apidoc/locales/zh_cn.js rename to docs/locales/zh_cn.js diff --git a/apidoc/main.js b/docs/main.js similarity index 100% rename from apidoc/main.js rename to docs/main.js diff --git a/apidoc/utils/handlebars_helper.js b/docs/utils/handlebars_helper.js similarity index 100% rename from apidoc/utils/handlebars_helper.js rename to docs/utils/handlebars_helper.js diff --git a/apidoc/utils/send_sample_request.js b/docs/utils/send_sample_request.js similarity index 100% rename from apidoc/utils/send_sample_request.js rename to docs/utils/send_sample_request.js diff --git a/apidoc/vendor/bootstrap.min.css b/docs/vendor/bootstrap.min.css similarity index 100% rename from apidoc/vendor/bootstrap.min.css rename to docs/vendor/bootstrap.min.css diff --git a/apidoc/vendor/bootstrap.min.js b/docs/vendor/bootstrap.min.js similarity index 100% rename from apidoc/vendor/bootstrap.min.js rename to docs/vendor/bootstrap.min.js diff --git a/apidoc/vendor/diff_match_patch.min.js b/docs/vendor/diff_match_patch.min.js similarity index 100% rename from apidoc/vendor/diff_match_patch.min.js rename to docs/vendor/diff_match_patch.min.js diff --git a/apidoc/vendor/handlebars.min.js b/docs/vendor/handlebars.min.js similarity index 100% rename from apidoc/vendor/handlebars.min.js rename to docs/vendor/handlebars.min.js diff --git a/apidoc/vendor/jquery.min.js b/docs/vendor/jquery.min.js similarity index 100% rename from apidoc/vendor/jquery.min.js rename to docs/vendor/jquery.min.js diff --git a/apidoc/vendor/list.min.js b/docs/vendor/list.min.js similarity index 100% rename from apidoc/vendor/list.min.js rename to docs/vendor/list.min.js diff --git a/apidoc/vendor/lodash.custom.min.js b/docs/vendor/lodash.custom.min.js similarity index 100% rename from apidoc/vendor/lodash.custom.min.js rename to docs/vendor/lodash.custom.min.js diff --git a/apidoc/vendor/path-to-regexp/LICENSE b/docs/vendor/path-to-regexp/LICENSE similarity index 100% rename from apidoc/vendor/path-to-regexp/LICENSE rename to docs/vendor/path-to-regexp/LICENSE diff --git a/apidoc/vendor/path-to-regexp/index.js b/docs/vendor/path-to-regexp/index.js similarity index 100% rename from apidoc/vendor/path-to-regexp/index.js rename to docs/vendor/path-to-regexp/index.js diff --git a/apidoc/vendor/polyfill.js b/docs/vendor/polyfill.js similarity index 100% rename from apidoc/vendor/polyfill.js rename to docs/vendor/polyfill.js diff --git a/apidoc/vendor/prettify.css b/docs/vendor/prettify.css similarity index 100% rename from apidoc/vendor/prettify.css rename to docs/vendor/prettify.css diff --git a/apidoc/vendor/prettify/lang-Splus.js b/docs/vendor/prettify/lang-Splus.js similarity index 100% rename from apidoc/vendor/prettify/lang-Splus.js rename to docs/vendor/prettify/lang-Splus.js diff --git a/apidoc/vendor/prettify/lang-aea.js b/docs/vendor/prettify/lang-aea.js similarity index 100% rename from apidoc/vendor/prettify/lang-aea.js rename to docs/vendor/prettify/lang-aea.js diff --git a/apidoc/vendor/prettify/lang-agc.js b/docs/vendor/prettify/lang-agc.js similarity index 100% rename from apidoc/vendor/prettify/lang-agc.js rename to docs/vendor/prettify/lang-agc.js diff --git a/apidoc/vendor/prettify/lang-apollo.js b/docs/vendor/prettify/lang-apollo.js similarity index 100% rename from apidoc/vendor/prettify/lang-apollo.js rename to docs/vendor/prettify/lang-apollo.js diff --git a/apidoc/vendor/prettify/lang-basic.js b/docs/vendor/prettify/lang-basic.js similarity index 100% rename from apidoc/vendor/prettify/lang-basic.js rename to docs/vendor/prettify/lang-basic.js diff --git a/apidoc/vendor/prettify/lang-cbm.js b/docs/vendor/prettify/lang-cbm.js similarity index 100% rename from apidoc/vendor/prettify/lang-cbm.js rename to docs/vendor/prettify/lang-cbm.js diff --git a/apidoc/vendor/prettify/lang-cl.js b/docs/vendor/prettify/lang-cl.js similarity index 100% rename from apidoc/vendor/prettify/lang-cl.js rename to docs/vendor/prettify/lang-cl.js diff --git a/apidoc/vendor/prettify/lang-clj.js b/docs/vendor/prettify/lang-clj.js similarity index 100% rename from apidoc/vendor/prettify/lang-clj.js rename to docs/vendor/prettify/lang-clj.js diff --git a/apidoc/vendor/prettify/lang-css.js b/docs/vendor/prettify/lang-css.js similarity index 100% rename from apidoc/vendor/prettify/lang-css.js rename to docs/vendor/prettify/lang-css.js diff --git a/apidoc/vendor/prettify/lang-dart.js b/docs/vendor/prettify/lang-dart.js similarity index 100% rename from apidoc/vendor/prettify/lang-dart.js rename to docs/vendor/prettify/lang-dart.js diff --git a/apidoc/vendor/prettify/lang-el.js b/docs/vendor/prettify/lang-el.js similarity index 100% rename from apidoc/vendor/prettify/lang-el.js rename to docs/vendor/prettify/lang-el.js diff --git a/apidoc/vendor/prettify/lang-erl.js b/docs/vendor/prettify/lang-erl.js similarity index 100% rename from apidoc/vendor/prettify/lang-erl.js rename to docs/vendor/prettify/lang-erl.js diff --git a/apidoc/vendor/prettify/lang-erlang.js b/docs/vendor/prettify/lang-erlang.js similarity index 100% rename from apidoc/vendor/prettify/lang-erlang.js rename to docs/vendor/prettify/lang-erlang.js diff --git a/apidoc/vendor/prettify/lang-fs.js b/docs/vendor/prettify/lang-fs.js similarity index 100% rename from apidoc/vendor/prettify/lang-fs.js rename to docs/vendor/prettify/lang-fs.js diff --git a/apidoc/vendor/prettify/lang-go.js b/docs/vendor/prettify/lang-go.js similarity index 100% rename from apidoc/vendor/prettify/lang-go.js rename to docs/vendor/prettify/lang-go.js diff --git a/apidoc/vendor/prettify/lang-hs.js b/docs/vendor/prettify/lang-hs.js similarity index 100% rename from apidoc/vendor/prettify/lang-hs.js rename to docs/vendor/prettify/lang-hs.js diff --git a/apidoc/vendor/prettify/lang-lasso.js b/docs/vendor/prettify/lang-lasso.js similarity index 100% rename from apidoc/vendor/prettify/lang-lasso.js rename to docs/vendor/prettify/lang-lasso.js diff --git a/apidoc/vendor/prettify/lang-lassoscript.js b/docs/vendor/prettify/lang-lassoscript.js similarity index 100% rename from apidoc/vendor/prettify/lang-lassoscript.js rename to docs/vendor/prettify/lang-lassoscript.js diff --git a/apidoc/vendor/prettify/lang-latex.js b/docs/vendor/prettify/lang-latex.js similarity index 100% rename from apidoc/vendor/prettify/lang-latex.js rename to docs/vendor/prettify/lang-latex.js diff --git a/apidoc/vendor/prettify/lang-lgt.js b/docs/vendor/prettify/lang-lgt.js similarity index 100% rename from apidoc/vendor/prettify/lang-lgt.js rename to docs/vendor/prettify/lang-lgt.js diff --git a/apidoc/vendor/prettify/lang-lisp.js b/docs/vendor/prettify/lang-lisp.js similarity index 100% rename from apidoc/vendor/prettify/lang-lisp.js rename to docs/vendor/prettify/lang-lisp.js diff --git a/apidoc/vendor/prettify/lang-ll.js b/docs/vendor/prettify/lang-ll.js similarity index 100% rename from apidoc/vendor/prettify/lang-ll.js rename to docs/vendor/prettify/lang-ll.js diff --git a/apidoc/vendor/prettify/lang-llvm.js b/docs/vendor/prettify/lang-llvm.js similarity index 100% rename from apidoc/vendor/prettify/lang-llvm.js rename to docs/vendor/prettify/lang-llvm.js diff --git a/apidoc/vendor/prettify/lang-logtalk.js b/docs/vendor/prettify/lang-logtalk.js similarity index 100% rename from apidoc/vendor/prettify/lang-logtalk.js rename to docs/vendor/prettify/lang-logtalk.js diff --git a/apidoc/vendor/prettify/lang-ls.js b/docs/vendor/prettify/lang-ls.js similarity index 100% rename from apidoc/vendor/prettify/lang-ls.js rename to docs/vendor/prettify/lang-ls.js diff --git a/apidoc/vendor/prettify/lang-lsp.js b/docs/vendor/prettify/lang-lsp.js similarity index 100% rename from apidoc/vendor/prettify/lang-lsp.js rename to docs/vendor/prettify/lang-lsp.js diff --git a/apidoc/vendor/prettify/lang-lua.js b/docs/vendor/prettify/lang-lua.js similarity index 100% rename from apidoc/vendor/prettify/lang-lua.js rename to docs/vendor/prettify/lang-lua.js diff --git a/apidoc/vendor/prettify/lang-matlab.js b/docs/vendor/prettify/lang-matlab.js similarity index 100% rename from apidoc/vendor/prettify/lang-matlab.js rename to docs/vendor/prettify/lang-matlab.js diff --git a/apidoc/vendor/prettify/lang-ml.js b/docs/vendor/prettify/lang-ml.js similarity index 100% rename from apidoc/vendor/prettify/lang-ml.js rename to docs/vendor/prettify/lang-ml.js diff --git a/apidoc/vendor/prettify/lang-mumps.js b/docs/vendor/prettify/lang-mumps.js similarity index 100% rename from apidoc/vendor/prettify/lang-mumps.js rename to docs/vendor/prettify/lang-mumps.js diff --git a/apidoc/vendor/prettify/lang-n.js b/docs/vendor/prettify/lang-n.js similarity index 100% rename from apidoc/vendor/prettify/lang-n.js rename to docs/vendor/prettify/lang-n.js diff --git a/apidoc/vendor/prettify/lang-nemerle.js b/docs/vendor/prettify/lang-nemerle.js similarity index 100% rename from apidoc/vendor/prettify/lang-nemerle.js rename to docs/vendor/prettify/lang-nemerle.js diff --git a/apidoc/vendor/prettify/lang-pascal.js b/docs/vendor/prettify/lang-pascal.js similarity index 100% rename from apidoc/vendor/prettify/lang-pascal.js rename to docs/vendor/prettify/lang-pascal.js diff --git a/apidoc/vendor/prettify/lang-proto.js b/docs/vendor/prettify/lang-proto.js similarity index 100% rename from apidoc/vendor/prettify/lang-proto.js rename to docs/vendor/prettify/lang-proto.js diff --git a/apidoc/vendor/prettify/lang-r.js b/docs/vendor/prettify/lang-r.js similarity index 100% rename from apidoc/vendor/prettify/lang-r.js rename to docs/vendor/prettify/lang-r.js diff --git a/apidoc/vendor/prettify/lang-rd.js b/docs/vendor/prettify/lang-rd.js similarity index 100% rename from apidoc/vendor/prettify/lang-rd.js rename to docs/vendor/prettify/lang-rd.js diff --git a/apidoc/vendor/prettify/lang-rkt.js b/docs/vendor/prettify/lang-rkt.js similarity index 100% rename from apidoc/vendor/prettify/lang-rkt.js rename to docs/vendor/prettify/lang-rkt.js diff --git a/apidoc/vendor/prettify/lang-rust.js b/docs/vendor/prettify/lang-rust.js similarity index 100% rename from apidoc/vendor/prettify/lang-rust.js rename to docs/vendor/prettify/lang-rust.js diff --git a/apidoc/vendor/prettify/lang-s.js b/docs/vendor/prettify/lang-s.js similarity index 100% rename from apidoc/vendor/prettify/lang-s.js rename to docs/vendor/prettify/lang-s.js diff --git a/apidoc/vendor/prettify/lang-scala.js b/docs/vendor/prettify/lang-scala.js similarity index 100% rename from apidoc/vendor/prettify/lang-scala.js rename to docs/vendor/prettify/lang-scala.js diff --git a/apidoc/vendor/prettify/lang-scm.js b/docs/vendor/prettify/lang-scm.js similarity index 100% rename from apidoc/vendor/prettify/lang-scm.js rename to docs/vendor/prettify/lang-scm.js diff --git a/apidoc/vendor/prettify/lang-sql.js b/docs/vendor/prettify/lang-sql.js similarity index 100% rename from apidoc/vendor/prettify/lang-sql.js rename to docs/vendor/prettify/lang-sql.js diff --git a/apidoc/vendor/prettify/lang-ss.js b/docs/vendor/prettify/lang-ss.js similarity index 100% rename from apidoc/vendor/prettify/lang-ss.js rename to docs/vendor/prettify/lang-ss.js diff --git a/apidoc/vendor/prettify/lang-swift.js b/docs/vendor/prettify/lang-swift.js similarity index 100% rename from apidoc/vendor/prettify/lang-swift.js rename to docs/vendor/prettify/lang-swift.js diff --git a/apidoc/vendor/prettify/lang-tcl.js b/docs/vendor/prettify/lang-tcl.js similarity index 100% rename from apidoc/vendor/prettify/lang-tcl.js rename to docs/vendor/prettify/lang-tcl.js diff --git a/apidoc/vendor/prettify/lang-tex.js b/docs/vendor/prettify/lang-tex.js similarity index 100% rename from apidoc/vendor/prettify/lang-tex.js rename to docs/vendor/prettify/lang-tex.js diff --git a/apidoc/vendor/prettify/lang-vb.js b/docs/vendor/prettify/lang-vb.js similarity index 100% rename from apidoc/vendor/prettify/lang-vb.js rename to docs/vendor/prettify/lang-vb.js diff --git a/apidoc/vendor/prettify/lang-vbs.js b/docs/vendor/prettify/lang-vbs.js similarity index 100% rename from apidoc/vendor/prettify/lang-vbs.js rename to docs/vendor/prettify/lang-vbs.js diff --git a/apidoc/vendor/prettify/lang-vhd.js b/docs/vendor/prettify/lang-vhd.js similarity index 100% rename from apidoc/vendor/prettify/lang-vhd.js rename to docs/vendor/prettify/lang-vhd.js diff --git a/apidoc/vendor/prettify/lang-vhdl.js b/docs/vendor/prettify/lang-vhdl.js similarity index 100% rename from apidoc/vendor/prettify/lang-vhdl.js rename to docs/vendor/prettify/lang-vhdl.js diff --git a/apidoc/vendor/prettify/lang-wiki.js b/docs/vendor/prettify/lang-wiki.js similarity index 100% rename from apidoc/vendor/prettify/lang-wiki.js rename to docs/vendor/prettify/lang-wiki.js diff --git a/apidoc/vendor/prettify/lang-xq.js b/docs/vendor/prettify/lang-xq.js similarity index 100% rename from apidoc/vendor/prettify/lang-xq.js rename to docs/vendor/prettify/lang-xq.js diff --git a/apidoc/vendor/prettify/lang-xquery.js b/docs/vendor/prettify/lang-xquery.js similarity index 100% rename from apidoc/vendor/prettify/lang-xquery.js rename to docs/vendor/prettify/lang-xquery.js diff --git a/apidoc/vendor/prettify/lang-yaml.js b/docs/vendor/prettify/lang-yaml.js similarity index 100% rename from apidoc/vendor/prettify/lang-yaml.js rename to docs/vendor/prettify/lang-yaml.js diff --git a/apidoc/vendor/prettify/lang-yml.js b/docs/vendor/prettify/lang-yml.js similarity index 100% rename from apidoc/vendor/prettify/lang-yml.js rename to docs/vendor/prettify/lang-yml.js diff --git a/apidoc/vendor/prettify/prettify.css b/docs/vendor/prettify/prettify.css similarity index 100% rename from apidoc/vendor/prettify/prettify.css rename to docs/vendor/prettify/prettify.css diff --git a/apidoc/vendor/prettify/prettify.js b/docs/vendor/prettify/prettify.js similarity index 100% rename from apidoc/vendor/prettify/prettify.js rename to docs/vendor/prettify/prettify.js diff --git a/apidoc/vendor/prettify/run_prettify.js b/docs/vendor/prettify/run_prettify.js similarity index 100% rename from apidoc/vendor/prettify/run_prettify.js rename to docs/vendor/prettify/run_prettify.js diff --git a/apidoc/vendor/require.min.js b/docs/vendor/require.min.js similarity index 100% rename from apidoc/vendor/require.min.js rename to docs/vendor/require.min.js diff --git a/apidoc/vendor/semver.min.js b/docs/vendor/semver.min.js similarity index 100% rename from apidoc/vendor/semver.min.js rename to docs/vendor/semver.min.js diff --git a/apidoc/vendor/webfontloader.js b/docs/vendor/webfontloader.js similarity index 100% rename from apidoc/vendor/webfontloader.js rename to docs/vendor/webfontloader.js diff --git a/lib/api/addresses.js b/lib/api/addresses.js index 14d2b58f..11ee7db8 100644 --- a/lib/api/addresses.js +++ b/lib/api/addresses.js @@ -1,6 +1,6 @@ 'use strict'; -const Joi = require('joi'); +const Joi = require('../joi'); const MongoPaging = require('mongo-cursor-pagination-node6'); const ObjectID = require('mongodb').ObjectID; const tools = require('../tools'); @@ -20,11 +20,11 @@ module.exports = (db, server) => { .max(250), next: Joi.string() .empty('') - .alphanum() + .mongoCursor() .max(1024), previous: Joi.string() .empty('') - .alphanum() + .mongoCursor() .max(1024), page: Joi.number().default(1) }); @@ -160,87 +160,97 @@ module.exports = (db, server) => { return next(); } - db.users.collection('users').findOne({ - _id: user - }, { - fields: { - address: true - } - }, (err, userData) => { - if (err) { - res.json({ - error: 'MongoDB Error: ' + err.message - }); - return next(); - } - if (!userData) { - res.json({ - error: 'This user does not exist' - }); - return next(); - } - - db.users.collection('addresses').findOne({ - addrview: address.substr(0, address.indexOf('@')).replace(/\./g, '') + address.substr(address.indexOf('@')) - }, (err, addressData) => { + db.users.collection('users').findOne( + { + _id: user + }, + { + fields: { + address: true + } + }, + (err, userData) => { if (err) { res.json({ error: 'MongoDB Error: ' + err.message }); return next(); } - if (addressData) { + if (!userData) { res.json({ - error: 'This email address already exists' + error: 'This user does not exist' }); return next(); } - // insert alias address to email address registry - db.users.collection('addresses').insertOne({ - user, - address, - addrview: address.substr(0, address.indexOf('@')).replace(/\./g, '') + address.substr(address.indexOf('@')), - created: new Date() - }, (err, r) => { - if (err) { - res.json({ - error: 'MongoDB Error: ' + err.message - }); - return next(); - } + db.users.collection('addresses').findOne( + { + addrview: address.substr(0, address.indexOf('@')).replace(/\./g, '') + address.substr(address.indexOf('@')) + }, + (err, addressData) => { + if (err) { + res.json({ + error: 'MongoDB Error: ' + err.message + }); + return next(); + } + if (addressData) { + res.json({ + error: 'This email address already exists' + }); + return next(); + } - let insertId = r.insertedId; - - let done = () => { - // ignore potential user update error - res.json({ - success: !!insertId, - id: insertId - }); - return next(); - }; - - if (!userData.address || main) { - // register this address as the default address for that user - return db.users.collection('users').findOneAndUpdate( + // insert alias address to email address registry + db.users.collection('addresses').insertOne( { - _id: user + user, + address, + addrview: address.substr(0, address.indexOf('@')).replace(/\./g, '') + address.substr(address.indexOf('@')), + created: new Date() }, - { - $set: { - address + (err, r) => { + if (err) { + res.json({ + error: 'MongoDB Error: ' + err.message + }); + return next(); } - }, - {}, - done + + let insertId = r.insertedId; + + let done = () => { + // ignore potential user update error + res.json({ + success: !!insertId, + id: insertId + }); + return next(); + }; + + if (!userData.address || main) { + // register this address as the default address for that user + return db.users.collection('users').findOneAndUpdate( + { + _id: user + }, + { + $set: { + address + } + }, + {}, + done + ); + } + + done(); + } ); } - - done(); - }); - }); - }); + ); + } + ); }); server.get('/users/:user/addresses', (req, res, next) => { @@ -268,60 +278,64 @@ module.exports = (db, server) => { let user = new ObjectID(result.value.user); - db.users.collection('users').findOne({ - _id: user - }, { - fields: { - address: true - } - }, (err, userData) => { - if (err) { - res.json({ - error: 'MongoDB Error: ' + err.message - }); - return next(); - } - if (!userData) { - res.json({ - error: 'This user does not exist' - }); - return next(); - } - - db.users - .collection('addresses') - .find({ - user - }) - .sort({ - addrview: 1 - }) - .toArray((err, addresses) => { - if (err) { - res.json({ - error: 'MongoDB Error: ' + err.message - }); - return next(); - } - - if (!addresses) { - addresses = []; - } - + db.users.collection('users').findOne( + { + _id: user + }, + { + fields: { + address: true + } + }, + (err, userData) => { + if (err) { res.json({ - success: true, - - results: addresses.map(address => ({ - id: address._id, - address: address.address, - main: address.address === userData.address, - created: address.created - })) + error: 'MongoDB Error: ' + err.message }); - return next(); - }); - }); + } + if (!userData) { + res.json({ + error: 'This user does not exist' + }); + return next(); + } + + db.users + .collection('addresses') + .find({ + user + }) + .sort({ + addrview: 1 + }) + .toArray((err, addresses) => { + if (err) { + res.json({ + error: 'MongoDB Error: ' + err.message + }); + return next(); + } + + if (!addresses) { + addresses = []; + } + + res.json({ + success: true, + + results: addresses.map(address => ({ + id: address._id, + address: address.address, + main: address.address === userData.address, + created: address.created + })) + }); + + return next(); + }); + } + ); }); server.get('/users/:user/addresses/:address', (req, res, next) => { @@ -355,55 +369,62 @@ module.exports = (db, server) => { let user = new ObjectID(result.value.user); let address = new ObjectID(result.value.address); - db.users.collection('users').findOne({ - _id: user - }, { - fields: { - address: true - } - }, (err, userData) => { - if (err) { - res.json({ - error: 'MongoDB Error: ' + err.message - }); - return next(); - } - if (!userData) { - res.json({ - error: 'This user does not exist' - }); - return next(); - } - - db.users.collection('addresses').findOne({ - _id: address, - user - }, (err, addressData) => { + db.users.collection('users').findOne( + { + _id: user + }, + { + fields: { + address: true + } + }, + (err, userData) => { if (err) { res.json({ error: 'MongoDB Error: ' + err.message }); return next(); } - if (!addressData) { - res.status(404); + if (!userData) { res.json({ - error: 'Invalid or unknown address' + error: 'This user does not exist' }); return next(); } - res.json({ - success: true, - id: addressData._id, - address: addressData.address, - main: addressData.address === userData.address, - created: addressData.created - }); + db.users.collection('addresses').findOne( + { + _id: address, + user + }, + (err, addressData) => { + if (err) { + res.json({ + error: 'MongoDB Error: ' + err.message + }); + return next(); + } + if (!addressData) { + res.status(404); + res.json({ + error: 'Invalid or unknown address' + }); + return next(); + } - return next(); - }); - }); + res.json({ + success: true, + id: addressData._id, + address: addressData.address, + main: addressData.address === userData.address, + created: addressData.created + }); + + return next(); + } + ); + } + ); }); server.put('/users/:user/addresses/:address', (req, res, next) => { @@ -448,75 +469,87 @@ module.exports = (db, server) => { return next(); } - db.users.collection('users').findOne({ - _id: user - }, { - fields: { - address: true - } - }, (err, userData) => { - if (err) { - res.json({ - error: 'MongoDB Error: ' + err.message - }); - return next(); - } - if (!userData) { - res.json({ - error: 'This user does not exist' - }); - return next(); - } - - db.users.collection('addresses').findOne({ - _id: address - }, (err, addressData) => { + db.users.collection('users').findOne( + { + _id: user + }, + { + fields: { + address: true + } + }, + (err, userData) => { if (err) { res.json({ error: 'MongoDB Error: ' + err.message }); return next(); } - - if (!addressData || addressData.user.toString() !== user.toString()) { - res.status(404); + if (!userData) { res.json({ - error: 'Invalid or unknown email address identifier' + error: 'This user does not exist' }); return next(); } - if (addressData.address === userData.address) { - res.json({ - error: 'Selected address is already the main email address for the user' - }); - return next(); - } + db.users.collection('addresses').findOne( + { + _id: address + }, + (err, addressData) => { + if (err) { + res.json({ + error: 'MongoDB Error: ' + err.message + }); + return next(); + } - // insert alias address to email address registry - db.users.collection('users').findOneAndUpdate({ - _id: user - }, { - $set: { - address: addressData.address - } - }, { - returnOriginal: false - }, (err, r) => { - if (err) { - res.json({ - error: 'MongoDB Error: ' + err.message - }); - return next(); - } + if (!addressData || addressData.user.toString() !== user.toString()) { + res.status(404); + res.json({ + error: 'Invalid or unknown email address identifier' + }); + return next(); + } - res.json({ - success: !!r.value - }); - return next(); - }); - }); - }); + if (addressData.address === userData.address) { + res.json({ + error: 'Selected address is already the main email address for the user' + }); + return next(); + } + + // insert alias address to email address registry + db.users.collection('users').findOneAndUpdate( + { + _id: user + }, + { + $set: { + address: addressData.address + } + }, + { + returnOriginal: false + }, + (err, r) => { + if (err) { + res.json({ + error: 'MongoDB Error: ' + err.message + }); + return next(); + } + + res.json({ + success: !!r.value + }); + return next(); + } + ); + } + ); + } + ); }); server.del('/users/:user/addresses/:address', (req, res, next) => { @@ -550,68 +583,78 @@ module.exports = (db, server) => { let user = new ObjectID(result.value.user); let address = new ObjectID(result.value.address); - db.users.collection('users').findOne({ - _id: user - }, { - fields: { - address: true - } - }, (err, userData) => { - if (err) { - res.json({ - error: 'MongoDB Error: ' + err.message - }); - return next(); - } - if (!userData) { - res.json({ - error: 'This user does not exist' - }); - return next(); - } - - db.users.collection('addresses').findOne({ - _id: address - }, (err, addressData) => { + db.users.collection('users').findOne( + { + _id: user + }, + { + fields: { + address: true + } + }, + (err, userData) => { if (err) { res.json({ error: 'MongoDB Error: ' + err.message }); return next(); } - - if (!addressData || addressData.user.toString() !== user.toString()) { - res.status(404); + if (!userData) { res.json({ - error: 'Invalid or unknown email address identifier' + error: 'This user does not exist' }); return next(); } - if (addressData.address === userData.address) { - res.json({ - error: 'Trying to delete main address. Set a new main address first' - }); - return next(); - } + db.users.collection('addresses').findOne( + { + _id: address + }, + (err, addressData) => { + if (err) { + res.json({ + error: 'MongoDB Error: ' + err.message + }); + return next(); + } - // delete address from email address registry - db.users.collection('addresses').deleteOne({ - _id: address - }, (err, r) => { - if (err) { - res.json({ - error: 'MongoDB Error: ' + err.message - }); - return next(); + if (!addressData || addressData.user.toString() !== user.toString()) { + res.status(404); + res.json({ + error: 'Invalid or unknown email address identifier' + }); + return next(); + } + + if (addressData.address === userData.address) { + res.json({ + error: 'Trying to delete main address. Set a new main address first' + }); + return next(); + } + + // delete address from email address registry + db.users.collection('addresses').deleteOne( + { + _id: address + }, + (err, r) => { + if (err) { + res.json({ + error: 'MongoDB Error: ' + err.message + }); + return next(); + } + + res.json({ + success: !!r.deletedCount + }); + return next(); + } + ); } - - res.json({ - success: !!r.deletedCount - }); - return next(); - }); - }); - }); + ); + } + ); }); }; diff --git a/lib/api/auth.js b/lib/api/auth.js index 58849a8d..c3230e0d 100644 --- a/lib/api/auth.js +++ b/lib/api/auth.js @@ -1,6 +1,6 @@ 'use strict'; -const Joi = require('joi'); +const Joi = require('../joi'); const MongoPaging = require('mongo-cursor-pagination-node6'); const ObjectID = require('mongodb').ObjectID; @@ -114,11 +114,11 @@ module.exports = (db, server, userHandler) => { .max(250), next: Joi.string() .empty('') - .alphanum() + .mongoCursor() .max(1024), previous: Joi.string() .empty('') - .alphanum() + .mongoCursor() .max(1024), page: Joi.number() .empty('') diff --git a/lib/api/messages.js b/lib/api/messages.js index f9028192..d346c0c5 100644 --- a/lib/api/messages.js +++ b/lib/api/messages.js @@ -1,7 +1,7 @@ 'use strict'; const log = require('npmlog'); -const Joi = require('joi'); +const Joi = require('../joi'); const MongoPaging = require('mongo-cursor-pagination-node6'); const addressparser = require('addressparser'); const ObjectID = require('mongodb').ObjectID; @@ -36,11 +36,11 @@ module.exports = (db, server, messageHandler) => { .default('desc'), next: Joi.string() .empty('') - .alphanum() + .mongoCursor() .max(1024), previous: Joi.string() .empty('') - .alphanum() + .mongoCursor() .max(1024), page: Joi.number() .empty('') @@ -256,11 +256,11 @@ module.exports = (db, server, messageHandler) => { .max(250), next: Joi.string() .empty('') - .alphanum() + .mongoCursor() .max(1024), previous: Joi.string() .empty('') - .alphanum() + .mongoCursor() .max(1024), page: Joi.number().default(1) }); @@ -1486,11 +1486,11 @@ module.exports = (db, server, messageHandler) => { .max(250), next: Joi.string() .empty('') - .alphanum() + .mongoCursor() .max(1024), previous: Joi.string() .empty('') - .alphanum() + .mongoCursor() .max(1024), order: Joi.any() .empty('') @@ -2036,11 +2036,11 @@ module.exports = (db, server, messageHandler) => { .default('desc'), next: Joi.string() .empty('') - .alphanum() + .mongoCursor() .max(1024), previous: Joi.string() .empty('') - .alphanum() + .mongoCursor() .max(1024), page: Joi.number() .empty('') diff --git a/lib/api/users.js b/lib/api/users.js index dfd6854b..4e5a7df7 100644 --- a/lib/api/users.js +++ b/lib/api/users.js @@ -1,7 +1,7 @@ 'use strict'; const config = require('wild-config'); -const Joi = require('joi'); +const Joi = require('../joi'); const MongoPaging = require('mongo-cursor-pagination-node6'); const ObjectID = require('mongodb').ObjectID; const tools = require('../tools'); @@ -11,6 +11,85 @@ const addressparser = require('addressparser'); const libmime = require('libmime'); module.exports = (db, server, userHandler) => { + /** + * @api {get} /users List registered Users + * @apiName GetUsers + * @apiGroup Users + * @apiHeader {String} X-Access-Token Optional access token if authentication is enabled + * @apiHeaderExample {json} Header-Example: + * { + * "X-Access-Token": "59fc66a03e54454869460e45" + * } + * + * @apiParam {String} [query] Partial match of username or default email address + * @apiParam {String} [tags] Comma separated list of tags. The User must have at least one to be set + * @apiParam {String} [requiredTags] Comma separated list of tags. The User must have all listed tags to be set + * @apiParam {Number} [limit=20] How many records to return + * @apiParam {Number} [page=1] Current page number. Informational only, page numbers start from 1 + * @apiParam {Number} [next] Cursor value for next page, retrieved fromnextCursor
response value
+ * @apiParam {Number} [previous] Cursor value for previous page, retrieved from previousCursor
response value
+ *
+ * @apiSuccess {Boolean} success Indicates successful response
+ * @apiSuccess {Number} total How many results were found
+ * @apiSuccess {Number} page Current page number. Derived from page
query argument
+ * @apiSuccess {String} previousCursor Either a cursor string or false if there are not any previous results
+ * @apiSuccess {String} nextCursor Either a cursor string or false if there are not any next results
+ * @apiSuccess {Object[]} results User listing
+ * @apiSuccess {String} results.id Users unique ID (24 byte hex)
+ * @apiSuccess {String} results.username Username of the User
+ * @apiSuccess {String} results.name Name of the User
+ * @apiSuccess {String} results.address Main email address of the User
+ * @apiSuccess {String[]} results.tags List of tags associated with the User'
+ * @apiSuccess {String[]} results.forward A list of email addresses to forward all incoming emails
+ * @apiSuccess {Boolean} results.encryptMessages If true
then received messages are encrypted
+ * @apiSuccess {Boolean} results.encryptForwarded If true
then forwarded messages are encrypted
+ * @apiSuccess {Object} results.quota Quota usage limits
+ * @apiSuccess {Number} results.quota.allowed Allowed quota of the user in bytes
+ * @apiSuccess {Number} results.quota.used Space used in bytes
+ * @apiSuccess {Boolean} results.hasPasswordSet If true
then the User has a password set and can authenticate
+ * @apiSuccess {Boolean} results.activated Is the account activated
+ * @apiSuccess {Boolean} results.disabled If true
then the user can not authenticate or receive any new mail
+ *
+ * @apiError error Description of the error
+ *
+ * @apiExample {curl} Example usage:
+ * curl -i http://localhost:8080/users
+ *
+ * @apiSuccessExample {json} Success-Response:
+ * HTTP/1.1 200 OK
+ * {
+ * "success": true,
+ * "total": 1,
+ * "page": 1,
+ * "previousCursor": false,
+ * "nextCursor": false,
+ * "results": [
+ * {
+ * "id": "59cb948ad80a820b68f05230",
+ * "username": "myuser",
+ * "name": "John Doe",
+ * "address": "john@example.com",
+ * "tags": [],
+ * "forward": [],
+ * "encryptMessages": false,
+ * "encryptForwarded": false,
+ * "quota": {
+ * "allowed": 1073741824,
+ * "used": 17799833
+ * },
+ * "hasPasswordSet": true,
+ * "activated": true,
+ * "disabled": false
+ * }
+ * ]
+ * }
+ *
+ * @apiErrorExample {json} Error-Response:
+ * HTTP/1.1 200 OK
+ * {
+ * "error": "Database error"
+ * }
+ */
server.get({ name: 'users', path: '/users' }, (req, res, next) => {
res.charSet('utf-8');
@@ -33,11 +112,11 @@ module.exports = (db, server, userHandler) => {
.max(250),
next: Joi.string()
.empty('')
- .alphanum()
+ .mongoCursor()
.max(1024),
previous: Joi.string()
.empty('')
- .alphanum()
+ .mongoCursor()
.max(1024),
page: Joi.number().default(1)
});
@@ -197,6 +276,62 @@ module.exports = (db, server, userHandler) => {
});
});
+ /**
+ * @api {post} /users Create new user
+ * @apiName PostUser
+ * @apiGroup Users
+ * @apiHeader {String} X-Access-Token Optional access token if authentication is enabled
+ * @apiHeaderExample {json} Header-Example:
+ * {
+ * "X-Access-Token": "59fc66a03e54454869460e45"
+ * }
+ *
+ * @apiParam {String} name Username of the User
+ * @apiParam {String} [name] Name of the User
+ * @apiParam {String} password New password for the account
+ * @apiParam {String} [address] Default email address for the User (autogenerated if not set)
+ * @apiParam {Boolean} [emptyAddress] If true then do not autogenerate missing email address for the User. Only needed if you want to create an user account that does not have any email address associated
+ * @apiParam {Number} [retention] Default retention time in ms. Set to 0
to disable
+ * @apiParam {Boolean} [encryptMessages] If true
then received messages are encrypted
+ * @apiParam {Boolean} [encryptForwarded] If true
then forwarded messages are encrypted
+ * @apiParam {String} [pubKey] Public PGP key for the User that is used for encryption. Use empty string to remove the key
+ * @apiParam {String} [language] Language code for the User
+ * @apiParam {String[]} [forward] A list of email addresses to forward all incoming emails
+ * @apiParam {String} [targetUrl] An URL to post all incoming emails
+ * @apiParam {Number} [quota] Allowed quota of the user in bytes
+ * @apiParam {Number} [recipients] How many messages per 24 hour can be sent
+ * @apiParam {Number} [forwards] How many messages per 24 hour can be forwarded
+ * @apiParam {Boolean} [disabled] If true then disables user account (can not login, can not receive messages)
+ * @apiParam {String} [sess] Session identifier for the logs
+ * @apiParam {String} [ip] IP address for the logs
+ *
+ * @apiSuccess {Boolean} success Indicates successful response
+ * @apiSuccess {String} id ID for the created User
+ *
+ * @apiError error Description of the error
+ *
+ * @apiExample {curl} Example usage:
+ * curl -i -XPOST http://localhost:8080/users \
+ * -H 'Content-type: application/json' \
+ * -d '{
+ * "username": "myuser",
+ * "password": "verysecret",
+ * "name": "John Doe"
+ * }'
+ *
+ * @apiSuccessExample {json} Success-Response:
+ * HTTP/1.1 200 OK
+ * {
+ * "success": true,
+ * "id": "5a1bda70bfbd1442cd96c6f0"
+ * }
+ *
+ * @apiErrorExample {json} Error-Response:
+ * HTTP/1.1 200 OK
+ * {
+ * "error": "This username already exists"
+ * }
+ */
server.post('/users', (req, res, next) => {
res.charSet('utf-8');
@@ -336,7 +471,7 @@ module.exports = (db, server, userHandler) => {
* "X-Access-Token": "59fc66a03e54454869460e45"
* }
*
- * @apiParam {Number} id Users unique ID.
+ * @apiParam {String} id Users unique ID.
*
* @apiSuccess {Boolean} success Indicates successful response
* @apiSuccess {String} id Users unique ID (24 byte hex)
@@ -348,21 +483,21 @@ module.exports = (db, server, userHandler) => {
* @apiSuccess {Boolean} encryptMessages If true
then received messages are encrypted
* @apiSuccess {Boolean} encryptForwarded If true
then forwarded messages are encrypted
* @apiSuccess {String} pubKey Public PGP key for the User that is used for encryption
- * @apiSuccess {Object[]} keyInfo Information about public key or false
if key is not available
+ * @apiSuccess {Object} keyInfo Information about public key or false
if key is not available
* @apiSuccess {String} keyInfo.name Name listed in public key
* @apiSuccess {String} keyInfo.address E-mail address listed in public key
* @apiSuccess {String} keyInfo.fingerprint Fingerprint of the public key
* @apiSuccess {String[]} forward A list of email addresses to forward all incoming emails
- * @apiSuccess {String[]} targetUrl An URL to post all incoming emails
- * @apiSuccess {Object[]} limits Account limits and usage
- * @apiSuccess {Object[]} limits.quota Quota usage limits
+ * @apiSuccess {String} targetUrl An URL to post all incoming emails
+ * @apiSuccess {Object} limits Account limits and usage
+ * @apiSuccess {Object} limits.quota Quota usage limits
* @apiSuccess {Number} limits.quota.allowed Allowed quota of the user in bytes
* @apiSuccess {Number} limits.quota.used Space used in bytes
- * @apiSuccess {Object[]} limits.recipients Sending quota
+ * @apiSuccess {Object} limits.recipients Sending quota
* @apiSuccess {Number} limits.recipients.allowed How many messages per 24 hour can be sent
* @apiSuccess {Number} limits.recipients.used How many messages are sent during current 24 hour period
* @apiSuccess {Number} limits.recipients.ttl Time until the end of current 24 hour period
- * @apiSuccess {Object[]} limits.forwards Forwarding quota
+ * @apiSuccess {Object} limits.forwards Forwarding quota
* @apiSuccess {Number} limits.forwards.allowed How many messages per 24 hour can be forwarded
* @apiSuccess {Number} limits.forwards.used How many messages are forwarded during current 24 hour period
* @apiSuccess {Number} limits.forwards.ttl Time until the end of current 24 hour period
@@ -536,6 +671,57 @@ module.exports = (db, server, userHandler) => {
);
});
+ /**
+ * @api {put} /users/:id Update User information
+ * @apiName PutUser
+ * @apiGroup Users
+ * @apiHeader {String} X-Access-Token Optional access token if authentication is enabled
+ * @apiHeaderExample {json} Header-Example:
+ * {
+ * "X-Access-Token": "59fc66a03e54454869460e45"
+ * }
+ *
+ * @apiParam {String} id Users unique ID.
+ * @apiParam {String} [name] Name of the User
+ * @apiParam {String} [existingPassword] If provided then validates against account password before applying any changes
+ * @apiParam {String} [password] New password for the account
+ * @apiParam {Number} [retention] Default retention time in ms. Set to 0
to disable
+ * @apiParam {Boolean} [encryptMessages] If true
then received messages are encrypted
+ * @apiParam {Boolean} [encryptForwarded] If true
then forwarded messages are encrypted
+ * @apiParam {String} [pubKey] Public PGP key for the User that is used for encryption. Use empty string to remove the key
+ * @apiParam {String} [language] Language code for the User
+ * @apiParam {String[]} [forward] A list of email addresses to forward all incoming emails
+ * @apiParam {String} [targetUrl] An URL to post all incoming emails
+ * @apiParam {Number} [quota] Allowed quota of the user in bytes
+ * @apiParam {Number} [recipients] How many messages per 24 hour can be sent
+ * @apiParam {Number} [forwards] How many messages per 24 hour can be forwarded
+ * @apiParam {Boolean} [disabled] If true then disables user account (can not login, can not receive messages)
+ * @apiParam {String} [sess] Session identifier for the logs
+ * @apiParam {String} [ip] IP address for the logs
+ *
+ * @apiSuccess {Boolean} success Indicates successful response
+ *
+ * @apiError error Description of the error
+ *
+ * @apiExample {curl} Example usage:
+ * curl -i -XPUT http://localhost:8080/users/59fc66a03e54454869460e45 \
+ * -H 'Content-type: application/json' \
+ * -d '{
+ * "name": "Updated user name"
+ * }'
+ *
+ * @apiSuccessExample {json} Success-Response:
+ * HTTP/1.1 200 OK
+ * {
+ * "success": true
+ * }
+ *
+ * @apiErrorExample {json} Error-Response:
+ * HTTP/1.1 200 OK
+ * {
+ * "error": "This user does not exist"
+ * }
+ */
server.put('/users/:user', (req, res, next) => {
res.charSet('utf-8');
@@ -667,6 +853,43 @@ module.exports = (db, server, userHandler) => {
});
});
+ /**
+ * @api {put} /users/:id/logout Log out User
+ * @apiName PutUserLogout
+ * @apiGroup Users
+ * @apiDescription This method logs out all user sessions in IMAP
+ * @apiHeader {String} X-Access-Token Optional access token if authentication is enabled
+ * @apiHeaderExample {json} Header-Example:
+ * {
+ * "X-Access-Token": "59fc66a03e54454869460e45"
+ * }
+ *
+ * @apiParam {String} id Users unique ID.
+ * @apiParam {String} [reason] Message to be shown to connected IMAP client
+ *
+ * @apiSuccess {Boolean} success Indicates successful response
+ *
+ * @apiError error Description of the error
+ *
+ * @apiExample {curl} Example usage:
+ * curl -i -XPUT http://localhost:8080/users/59fc66a03e54454869460e45/logout \
+ * -H 'Content-type: application/json' \
+ * -d '{
+ * "reason": "Logout requested from API"
+ * }'
+ *
+ * @apiSuccessExample {json} Success-Response:
+ * HTTP/1.1 200 OK
+ * {
+ * "success": true
+ * }
+ *
+ * @apiErrorExample {json} Error-Response:
+ * HTTP/1.1 200 OK
+ * {
+ * "error": "This user does not exist"
+ * }
+ */
server.put('/users/:user/logout', (req, res, next) => {
res.charSet('utf-8');
@@ -712,6 +935,44 @@ module.exports = (db, server, userHandler) => {
});
});
+ /**
+ * @api {post} /users/:id/quota/reset Recalculate User quota
+ * @apiName PostUserQuota
+ * @apiGroup Users
+ * @apiDescription This method recalculates quota usage for an User. Normally not needed, only use it if quota numbers are way off.
+ * This method is not transactional, so if the user is currently receiving new messages then the resulting value is not exact.
+ * @apiHeader {String} X-Access-Token Optional access token if authentication is enabled
+ * @apiHeaderExample {json} Header-Example:
+ * {
+ * "X-Access-Token": "59fc66a03e54454869460e45"
+ * }
+ *
+ * @apiParam {String} id Users unique ID.
+ * @apiParam {String} [reason] Message to be shown to connected IMAP client
+ *
+ * @apiSuccess {Boolean} success Indicates successful response
+ * @apiSuccess {Number} storageUsed Calculated quota usage for the user
+ *
+ * @apiError error Description of the error
+ *
+ * @apiExample {curl} Example usage:
+ * curl -i -XPOST http://localhost:8080/users/59fc66a03e54454869460e45/quota/reset \
+ * -H 'Content-type: application/json' \
+ * -d '{}'
+ *
+ * @apiSuccessExample {json} Success-Response:
+ * HTTP/1.1 200 OK
+ * {
+ * "success": true,
+ * "storageUsed": 1234567
+ * }
+ *
+ * @apiErrorExample {json} Error-Response:
+ * HTTP/1.1 200 OK
+ * {
+ * "error": "This user does not exist"
+ * }
+ */
server.post('/users/:user/quota/reset', (req, res, next) => {
res.charSet('utf-8');
@@ -844,6 +1105,48 @@ module.exports = (db, server, userHandler) => {
);
});
+ /**
+ * @api {post} /users/:id/password/reset Reset password for an User
+ * @apiName ResetUserPassword
+ * @apiGroup Users
+ * @apiDescription This method generates a new temporary password for an User.
+ * Additionally it removes all two-factor authentication settings
+ *
+ * @apiHeader {String} X-Access-Token Optional access token if authentication is enabled
+ * @apiHeaderExample {json} Header-Example:
+ * {
+ * "X-Access-Token": "59fc66a03e54454869460e45"
+ * }
+ *
+ * @apiParam {String} id Users unique ID.
+ * @apiParam {String} [sess] Session identifier for the logs
+ * @apiParam {String} [ip] IP address for the logs
+ *
+ * @apiSuccess {Boolean} success Indicates successful response
+ * @apiSuccess {String} password Temporary password
+ *
+ * @apiError error Description of the error
+ *
+ * @apiExample {curl} Example usage:
+ * curl -i -XPOST http://localhost:8080/users/5a1bda70bfbd1442cd96/password/reset \
+ * -H 'Content-type: application/json' \
+ * -d '{
+ * "ip": "127.0.0.1"
+ * }'
+ *
+ * @apiSuccessExample {json} Success-Response:
+ * HTTP/1.1 200 OK
+ * {
+ * "success": true,
+ * "password": "temporarypass"
+ * }
+ *
+ * @apiErrorExample {json} Error-Response:
+ * HTTP/1.1 200 OK
+ * {
+ * "error": "This user does not exist"
+ * }
+ */
server.post('/users/:user/password/reset', (req, res, next) => {
res.charSet('utf-8');
@@ -889,6 +1192,39 @@ module.exports = (db, server, userHandler) => {
});
});
+ /**
+ * @api {delete} /users/:id Delete an User
+ * @apiName DeleteUser
+ * @apiGroup Users
+ * @apiHeader {String} X-Access-Token Optional access token if authentication is enabled
+ * @apiHeaderExample {json} Header-Example:
+ * {
+ * "X-Access-Token": "59fc66a03e54454869460e45"
+ * }
+ *
+ * @apiParam {String} id Users unique ID.
+ * @apiParam {String} [sess] Session identifier for the logs
+ * @apiParam {String} [ip] IP address for the logs
+ *
+ * @apiSuccess {Boolean} success Indicates successful response
+ *
+ * @apiError error Description of the error
+ *
+ * @apiExample {curl} Example usage:
+ * curl -i -XDELETE http://localhost:8080/users/5a1bda70bfbd1442cd96c6f0?ip=127.0.0.1
+ *
+ * @apiSuccessExample {json} Success-Response:
+ * HTTP/1.1 200 OK
+ * {
+ * "success": true
+ * }
+ *
+ * @apiErrorExample {json} Error-Response:
+ * HTTP/1.1 200 OK
+ * {
+ * "error": "This user does not exist"
+ * }
+ */
server.del('/users/:user', (req, res, next) => {
res.charSet('utf-8');
diff --git a/lib/joi.js b/lib/joi.js
new file mode 100644
index 00000000..d3aa4931
--- /dev/null
+++ b/lib/joi.js
@@ -0,0 +1,37 @@
+'use strict';
+
+const EJSON = require('mongodb-extended-json');
+const Joi = require('joi');
+const customJoi = Joi.extend(joi => ({
+ base: joi.string(),
+ name: 'string',
+ language: {
+ base64url: 'needs to be a base64 URL',
+ ejson: 'needs to be an extended JSON object'
+ },
+ pre(value, state, options) {
+ if (options.convert && this._flags.round) {
+ return Math.round(value); // Change the value
+ }
+ return value; // Keep the value as it was
+ },
+ rules: [
+ {
+ name: 'mongoCursor',
+ validate(params, value, state, options) {
+ if (/[^a-zA-Z0-9\-_]/.test(value)) {
+ return this.createError('string.base64url', { v: value }, state, options);
+ }
+ try {
+ EJSON.parse(value);
+ } catch (E) {
+ return this.createError('string.ejson', { v: value }, state, options);
+ }
+
+ return value; // Everything is OK
+ }
+ }
+ ]
+}));
+
+module.exports = customJoi;
diff --git a/package.json b/package.json
index 45994cf6..2ba4ecbc 100644
--- a/package.json
+++ b/package.json
@@ -6,12 +6,9 @@
"scripts": {
"toc": "markdown-toc -i docs/api.md",
"test": "mongo --eval 'db.dropDatabase()' wildduck-test && redis-cli -n 13 flushdb && NODE_ENV=test grunt",
- "apidoc": "apidoc -i lib/api/ -o apidoc/"
+ "apidoc": "apidoc -i lib/api/ -o docs/"
},
- "keywords": [
- "imap",
- "mail server"
- ],
+ "keywords": ["imap", "mail server"],
"author": "Andris Reinman",
"license": "EUPL-1.1",
"devDependencies": {
@@ -53,6 +50,7 @@
"mobileconfig": "2.1.0",
"mongo-cursor-pagination-node6": "5.0.0",
"mongodb": "2.2.33",
+ "mongodb-extended-json": "^1.10.0",
"nodemailer": "4.4.0",
"npmlog": "4.1.2",
"openpgp": "2.5.13",