Callback handler

The document editing service informs the document storage service about the status of the document editing using the callbackUrl from JavaScript API. The document editing service use the POST request with the information in body.

Parameters and their description:

ParameterDescriptionTypePresence
actionsDefines the object received when the user takes an action with the document. The type field value can have the following values:
  • 0 - the user disconnects from the document co-editing,
  • 1 - the new user connects to the document co-editing,
  • 2 - the user clicks the forcesave button.
The userid field value is the user identifier.
array of objectoptional
changeshistoryDefines the array of objects with the document changes history. The object is present when the status value is equal to 2 or 3 only. Must be sent as a property changes of the object sent as the argument to the refreshHistory method. Removed since version 4.2, please use history instead.array of objectoptional
changesurlDefines the link to the file with the document editing data used to track and display the document changes history. The link is present when the status value is equal to 2 or 3 only. The file must be saved and its address must be sent as changesUrl parameter using the setHistoryData method to show the changes corresponding to the specific document version.stringoptional
filetypeDefines an extension of the document that is downloaded from the link specified with the url parameter. The file type is OOXML by default but if the assemblyFormatAsOrigin server setting is enabled, the file will be saved in its original format.stringoptional
forcesavetypeDefines the type of initiator when the force saving request is performed. Can have the following values:
  • 0 - the force saving request is performed to the command service,
  • 1 - the force saving request is performed each time the saving is done (e.g. the Save button is clicked), which is only available when the forcesave option is set to true.
  • 2 - the force saving request is performed by timer with the settings from the server config.
The type is present when the status value is equal to 6 or 7 only.
integeroptional
historyDefines the object with the document changes history. The object is present when the status value is equal to 2 or 3 only. It contains the object changes and serverVersion, which must be sent as properties changes and serverVersion of the object sent as the argument to the refreshHistory method.objectoptional
keyDefines the edited document identifier.stringrequired
statusDefines the status of the document. Can have the following values:
  • 1 - document is being edited,
  • 2 - document is ready for saving,
  • 3 - document saving error has occurred,
  • 4 - document is closed with no changes,
  • 6 - document is being edited, but the current document state is saved,
  • 7 - error has occurred while force saving the document.
integerrequired
urlDefines the link to the edited document to be saved with the document storage service. The link is present when the status value is equal to 2, 3, 6 or 7 only.stringoptional
userdataDefines the custom information sent to the command service in case it was present in the request.stringoptional
usersDefines the list of the identifiers of the users who opened the document for editing; when the document has been changed the users will return the identifier of the user who was the last to edit the document (for status 2 and status 6 replies).array of stringoptional

Since version 5.5, callbackUrl is selected depending on the status of the request. Starting from version 4.4 to version 5.5, callbackUrl is used from the last user who joined the co-editing. Prior to version 4.4, when co-editing, callbackUrl is used from the user who first opened the file for editing.

Since version 7.0, callbackUrl is used from the last tab of the same user. Prior to version 7.0, callbackUrl from the first user tab was used.

Possible document statuses and their description

StatusDescription
Status 1

It is received every user connection to or disconnection from document co-editing. Their callbackUrl is used.

Please note that the status 1 can be also received when the user is returned to the document with no changes after the Internet problems. This situation can be described as follows:

  • When the user opens a document, the status 1 is sent.
  • If the Internet connection is lost and the user has not made any changes to the document, the status 4 is sent. An error is displayed on the screen and the document is opened in the viewer.
  • Within 100 seconds, the Internet connection is restored, the user is reconnected to the document and the status 1 is sent again.
  • Now the user can continue to edit the document. The status 2 or 4 will be received depending on whether the user made any changes to the document or not.
Status 2 (3)

It is received 10 seconds after the document is closed for editing with the identifier of the user who was the last to send the changes to the document editing service. The callbackUrl from the user who made the last changes to the file is used.

Status 4

It is received after the document is closed for editing with no changes by the last user. Their callbackUrl is used.

Status 6 (7)

It is received when the force saving request is performed.

The callbackUrl depends on forcesavetype parameter:

  • If forcesavetype parameter is set to 1, the callbackUrl from the user who clicked the Save button is used.
  • If forcesavetype parameter is set to 0 or 2, the callbackUrl from the user who made the last changes to the file is used.

Starting from version 5.5 to version 6.1, the callbackUrl from the user who made the last changes to the file is always used.

Sample of JSON object sent to the “callbackUrl” address by document editing service when two users are co-editing the document

  1. {
  2. "actions": [{"type": 1, "userid": "78e1e841"}],
  3. "key": "Khirz6zTPdfd7",
  4. "status": 1,
  5. "users": ["6d5a81d0", "78e1e841"]
  6. }

Sample of JSON object sent to the “callbackUrl” address by document editing service when the user changed the document and closed it for editing

  1. {
  2. "actions": [{"type": 0, "userid": "78e1e841"}],
  3. "changesurl": "https://documentserver/url-to-changes.zip",
  4. "history": {
  5. "changes": changes,
  6. "serverVersion": serverVersion
  7. },
  8. "filetype": "docx",
  9. "key": "Khirz6zTPdfd7",
  10. "status": 2,
  11. "url": "https://documentserver/url-to-edited-document.docx",
  12. "users": ["6d5a81d0"]
  13. }

Sample of JSON object sent to the “callbackUrl” address by document editing service when the last user closed the document for editing without changes

  1. {
  2. "key": "Khirz6zTPdfd7",
  3. "status": 4
  4. }

Sample of JSON object sent to the “callbackUrl” address by document editing service after the forcesave command had been received

  1. {
  2. "changesurl": "https://documentserver/url-to-changes.zip",
  3. "forcesavetype": 0,
  4. "history": {
  5. "changes": changes,
  6. "serverVersion": serverVersion
  7. },
  8. "filetype": "docx",
  9. "key": "Khirz6zTPdfd7",
  10. "status": 6,
  11. "url": "https://documentserver/url-to-edited-document.docx",
  12. "users": ["6d5a81d0"],
  13. "userdata": "sample userdata"
  14. }

Response from the document storage service

The document storage service must return the following response, otherwise the document editor will display an error message:

  1. {
  2. "error": 0
  3. }

The document manager and document storage service are either included to Community Server or must be implemented by the software integrators who use ONLYOFFICE Document Server on their own server.

.Net (C#) document save example

  1. public class WebEditor : IHttpHandler
  2. {
  3. public void ProcessRequest(HttpContext context)
  4. {
  5. string body;
  6. using (var reader = new StreamReader(context.Request.InputStream))
  7. body = reader.ReadToEnd();
  8. var fileData = new JavaScriptSerializer().Deserialize<Dictionary<string, object>>(body);
  9. if ((int) fileData["status"] == 2)
  10. {
  11. var req = WebRequest.Create((string) fileData["url"]);
  12. using (var stream = req.GetResponse().GetResponseStream())
  13. using (var fs = File.Open(PATH_FOR_SAVE, FileMode.Create))
  14. {
  15. var buffer = new byte[4096];
  16. int readed;
  17. while ((readed = stream.Read(buffer, 0, 4096)) != 0)
  18. fs.Write(buffer, 0, readed);
  19. }
  20. }
  21. context.Response.Write("{\"error\":0}");
  22. }
  23. }

PATH_FOR_SAVE is the absolute path to your computer folder where the file will be saved including the file name.

Java document save example

  1. public class IndexServlet extends HttpServlet {
  2. @Override
  3. protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
  4. PrintWriter writer = response.getWriter();
  5. Scanner scanner = new Scanner(request.getInputStream()).useDelimiter("\\A");
  6. String body = scanner.hasNext() ? scanner.next() : "";
  7. JSONObject jsonObj = (JSONObject) new JSONParser().parse(body);
  8. if((long) jsonObj.get("status") == 2)
  9. {
  10. String downloadUri = (String) jsonObj.get("url");
  11. URL url = new URL(downloadUri);
  12. java.net.HttpURLConnection connection = (java.net.HttpURLConnection) url.openConnection();
  13. InputStream stream = connection.getInputStream();
  14. File savedFile = new File(pathForSave);
  15. try (FileOutputStream out = new FileOutputStream(savedFile)) {
  16. int read;
  17. final byte[] bytes = new byte[1024];
  18. while ((read = stream.read(bytes)) != -1) {
  19. out.write(bytes, 0, read);
  20. }
  21. out.flush();
  22. }
  23. connection.disconnect();
  24. }
  25. writer.write("{\"error\":0}");
  26. }
  27. }

pathForSave is the absolute path to your computer folder where the file will be saved including the file name.

Node.js document save example

  1. var fs = require("fs");
  2. var syncRequest = require("sync-request");
  3. app.post("/track", function (req, res) {
  4. var updateFile = function (response, body, path) {
  5. if (body.status == 2)
  6. {
  7. var file = syncRequest("GET", body.url);
  8. fs.writeFileSync(path, file.getBody());
  9. }
  10. response.write("{\"error\":0}");
  11. response.end();
  12. }
  13. var readbody = function (request, response, path) {
  14. var content = "";
  15. request.on("data", function (data) {
  16. content += data;
  17. });
  18. request.on("end", function () {
  19. var body = JSON.parse(content);
  20. updateFile(response, body, path);
  21. });
  22. }
  23. if (req.body.hasOwnProperty("status")) {
  24. updateFile(res, req.body, pathForSave);
  25. } else {
  26. readbody(req, res, pathForSave)
  27. }
  28. });

pathForSave is the absolute path to your computer folder where the file will be saved including the file name.

PHP document save example

  1. <?php
  2. if (($body_stream = file_get_contents("php://input"))===FALSE){
  3. echo "Bad Request";
  4. }
  5. $data = json_decode($body_stream, TRUE);
  6. if ($data["status"] == 2){
  7. $downloadUri = $data["url"];
  8. if (($new_data = file_get_contents($downloadUri))===FALSE){
  9. echo "Bad Response";
  10. } else {
  11. file_put_contents($path_for_save, $new_data, LOCK_EX);
  12. }
  13. }
  14. echo "{\"error\":0}";
  15. ?>

$path_for_save is the absolute path to your computer folder where the file will be saved including the file name.

Ruby document save example

  1. class ApplicationController < ActionController::Base
  2. def index
  3. body = request.body.read
  4. file_data = JSON.parse(body)
  5. status = file_data["status"].to_i
  6. if status == 2
  7. download_uri = file_data["url"]
  8. uri = URI.parse(download_uri)
  9. http = Net::HTTP.new(uri.host, uri.port)
  10. if download_uri.start_with?("https")
  11. http.use_ssl = true
  12. http.verify_mode = OpenSSL::SSL::VERIFY_NONE
  13. end
  14. req = Net::HTTP::Get.new(uri.request_uri)
  15. res = http.request(req)
  16. data = res.body
  17. File.open(path_for_save, "wb") do |file|
  18. file.write(data)
  19. end
  20. end
  21. render :text => "{\"error\":0}"
  22. end
  23. end

path_for_save is the absolute path to your computer folder where the file will be saved including the file name.