All Downloads are FREE. Search and download functionalities are using the official Maven repository.

com.parse.ParseObjectCoder Maven / Gradle / Ivy

Go to download

A library that gives you access to the powerful Parse cloud platform from your Android app.

There is a newer version: 1.17.3
Show newest version
/*
 * Copyright (c) 2015-present, Parse, LLC.
 * All rights reserved.
 *
 * This source code is licensed under the BSD-style license found in the
 * LICENSE file in the root directory of this source tree. An additional grant
 * of patent rights can be found in the PATENTS file in the same directory.
 */
package com.parse;

import org.json.JSONException;
import org.json.JSONObject;

import java.util.Iterator;

/**
 * Handles encoding/decoding ParseObjects to/from REST JSON.
 */
/** package */ class ParseObjectCoder {

  private static final String KEY_OBJECT_ID = "objectId";
  private static final String KEY_CLASS_NAME = "className";
  private static final String KEY_ACL = "ACL";
  private static final String KEY_CREATED_AT = "createdAt";
  private static final String KEY_UPDATED_AT = "updatedAt";

  private static final ParseObjectCoder INSTANCE = new ParseObjectCoder();
  public static ParseObjectCoder get() {
    return INSTANCE;
  }

  /* package */ ParseObjectCoder() {
    // do nothing
  }

  /**
   * Converts a {@code ParseObject.State} to REST JSON for saving.
   *
   * Only dirty keys from {@code operations} are represented in the data. Non-dirty keys such as
   * {@code updatedAt}, {@code createdAt}, etc. are not included.
   *
   * @param state
   *          {@link ParseObject.State} of the type of {@link ParseObject} that will be returned.
   *          Properties are completely ignored.
   * @param operations
   *          Dirty operations that are to be saved.
   * @param encoder
   *          Encoder instance that will be used to encode the request.
   * @return
   *          A REST formatted {@link JSONObject} that will be used for saving.
   */
  public  JSONObject encode(
      T state, ParseOperationSet operations, ParseEncoder encoder) {
    JSONObject objectJSON = new JSONObject();

    try {
      // Serialize the data
      for (String key : operations.keySet()) {
        ParseFieldOperation operation = operations.get(key);
        objectJSON.put(key, encoder.encode(operation));

        // TODO(grantland): Use cached value from hashedObjects if it's a set operation.
      }

      if (state.objectId() != null) {
        objectJSON.put(KEY_OBJECT_ID, state.objectId());
      }
    } catch (JSONException e) {
      throw new RuntimeException("could not serialize object to JSON");
    }

    return objectJSON;
  }

  /**
   * Converts REST JSON response to {@link ParseObject.State.Init}.
   *
   * This returns Builder instead of a State since we'll probably want to set some additional
   * properties on it after decoding such as {@link ParseObject.State.Init#isComplete()}, etc.
   *
   * @param builder
   *          A {@link ParseObject.State.Init} instance that will have the server JSON applied
   *          (mutated) to it. This will generally be a instance created by clearing a mutable
   *          copy of a {@link ParseObject.State} to ensure it's an instance of the correct
   *          subclass: {@code state.newBuilder().clear()}
   * @param json
   *          JSON response in REST format from the server.
   * @param decoder
   *          Decoder instance that will be used to decode the server response.
   * @return
   *          The same Builder instance passed in after the JSON is applied.
   */
  public > T decode(
      T builder, JSONObject json, ParseDecoder decoder) {
    try {
      Iterator keys = json.keys();
      while (keys.hasNext()) {
        String key = (String) keys.next();
        /*
        __type:       Returned by queries and cloud functions to designate body is a ParseObject
        __className:  Used by fromJSON, should be stripped out by the time it gets here...
         */
        if (key.equals("__type") || key.equals(KEY_CLASS_NAME)) {
          continue;
        }
        if (key.equals(KEY_OBJECT_ID)) {
          String newObjectId = json.getString(key);
          builder.objectId(newObjectId);
          continue;
        }
        if (key.equals(KEY_CREATED_AT)) {
          builder.createdAt(ParseDateFormat.getInstance().parse(json.getString(key)));
          continue;
        }
        if (key.equals(KEY_UPDATED_AT)) {
          builder.updatedAt(ParseDateFormat.getInstance().parse(json.getString(key)));
          continue;
        }
        if (key.equals(KEY_ACL)) {
          ParseACL acl = ParseACL.createACLFromJSONObject(json.getJSONObject(key), decoder);
          builder.put(KEY_ACL, acl);
          continue;
        }

        Object value = json.get(key);
        Object decodedObject = decoder.decode(value);
        builder.put(key, decodedObject);
      }

      return builder;
    } catch (JSONException e) {
      throw new RuntimeException(e);
    }
  }
}




© 2015 - 2024 Weber Informatics LLC | Privacy Policy