UniqueInstanceStateController.js 4.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212
  1. /**
  2. * Copyright (c) 2015-present, Parse, LLC.
  3. * All rights reserved.
  4. *
  5. * This source code is licensed under the BSD-style license found in the
  6. * LICENSE file in the root directory of this source tree. An additional grant
  7. * of patent rights can be found in the PATENTS file in the same directory.
  8. *
  9. * @flow
  10. */
  11. import * as ObjectStateMutations from './ObjectStateMutations';
  12. import TaskQueue from './TaskQueue';
  13. /*:: import type { Op } from './ParseOp';*/
  14. /*:: import type ParseObject from './ParseObject';*/
  15. /*:: import type { AttributeMap, ObjectCache, OpsMap, State } from './ObjectStateMutations';*/
  16. let objectState = new WeakMap();
  17. export function getState(obj
  18. /*: ParseObject*/
  19. )
  20. /*: ?State*/
  21. {
  22. const classData = objectState.get(obj);
  23. return classData || null;
  24. }
  25. export function initializeState(obj
  26. /*: ParseObject*/
  27. , initial
  28. /*:: ?: State*/
  29. )
  30. /*: State*/
  31. {
  32. let state = getState(obj);
  33. if (state) {
  34. return state;
  35. }
  36. if (!initial) {
  37. initial = {
  38. serverData: {},
  39. pendingOps: [{}],
  40. objectCache: {},
  41. tasks: new TaskQueue(),
  42. existed: false
  43. };
  44. }
  45. state = initial;
  46. objectState.set(obj, state);
  47. return state;
  48. }
  49. export function removeState(obj
  50. /*: ParseObject*/
  51. )
  52. /*: ?State*/
  53. {
  54. const state = getState(obj);
  55. if (state === null) {
  56. return null;
  57. }
  58. objectState.delete(obj);
  59. return state;
  60. }
  61. export function getServerData(obj
  62. /*: ParseObject*/
  63. )
  64. /*: AttributeMap*/
  65. {
  66. const state = getState(obj);
  67. if (state) {
  68. return state.serverData;
  69. }
  70. return {};
  71. }
  72. export function setServerData(obj
  73. /*: ParseObject*/
  74. , attributes
  75. /*: AttributeMap*/
  76. ) {
  77. const serverData = initializeState(obj).serverData;
  78. ObjectStateMutations.setServerData(serverData, attributes);
  79. }
  80. export function getPendingOps(obj
  81. /*: ParseObject*/
  82. )
  83. /*: Array<OpsMap>*/
  84. {
  85. const state = getState(obj);
  86. if (state) {
  87. return state.pendingOps;
  88. }
  89. return [{}];
  90. }
  91. export function setPendingOp(obj
  92. /*: ParseObject*/
  93. , attr
  94. /*: string*/
  95. , op
  96. /*: ?Op*/
  97. ) {
  98. const pendingOps = initializeState(obj).pendingOps;
  99. ObjectStateMutations.setPendingOp(pendingOps, attr, op);
  100. }
  101. export function pushPendingState(obj
  102. /*: ParseObject*/
  103. ) {
  104. const pendingOps = initializeState(obj).pendingOps;
  105. ObjectStateMutations.pushPendingState(pendingOps);
  106. }
  107. export function popPendingState(obj
  108. /*: ParseObject*/
  109. )
  110. /*: OpsMap*/
  111. {
  112. const pendingOps = initializeState(obj).pendingOps;
  113. return ObjectStateMutations.popPendingState(pendingOps);
  114. }
  115. export function mergeFirstPendingState(obj
  116. /*: ParseObject*/
  117. ) {
  118. const pendingOps = getPendingOps(obj);
  119. ObjectStateMutations.mergeFirstPendingState(pendingOps);
  120. }
  121. export function getObjectCache(obj
  122. /*: ParseObject*/
  123. )
  124. /*: ObjectCache*/
  125. {
  126. const state = getState(obj);
  127. if (state) {
  128. return state.objectCache;
  129. }
  130. return {};
  131. }
  132. export function estimateAttribute(obj
  133. /*: ParseObject*/
  134. , attr
  135. /*: string*/
  136. )
  137. /*: mixed*/
  138. {
  139. const serverData = getServerData(obj);
  140. const pendingOps = getPendingOps(obj);
  141. return ObjectStateMutations.estimateAttribute(serverData, pendingOps, obj.className, obj.id, attr);
  142. }
  143. export function estimateAttributes(obj
  144. /*: ParseObject*/
  145. )
  146. /*: AttributeMap*/
  147. {
  148. const serverData = getServerData(obj);
  149. const pendingOps = getPendingOps(obj);
  150. return ObjectStateMutations.estimateAttributes(serverData, pendingOps, obj.className, obj.id);
  151. }
  152. export function commitServerChanges(obj
  153. /*: ParseObject*/
  154. , changes
  155. /*: AttributeMap*/
  156. ) {
  157. const state = initializeState(obj);
  158. ObjectStateMutations.commitServerChanges(state.serverData, state.objectCache, changes);
  159. }
  160. export function enqueueTask(obj
  161. /*: ParseObject*/
  162. , task
  163. /*: () => Promise*/
  164. )
  165. /*: Promise*/
  166. {
  167. const state = initializeState(obj);
  168. return state.tasks.enqueue(task);
  169. }
  170. export function duplicateState(source
  171. /*: ParseObject*/
  172. , dest
  173. /*: ParseObject*/
  174. )
  175. /*: void*/
  176. {
  177. const oldState = initializeState(source);
  178. const newState = initializeState(dest);
  179. for (const key in oldState.serverData) {
  180. newState.serverData[key] = oldState.serverData[key];
  181. }
  182. for (let index = 0; index < oldState.pendingOps.length; index++) {
  183. for (const key in oldState.pendingOps[index]) {
  184. newState.pendingOps[index][key] = oldState.pendingOps[index][key];
  185. }
  186. }
  187. for (const key in oldState.objectCache) {
  188. newState.objectCache[key] = oldState.objectCache[key];
  189. }
  190. newState.existed = oldState.existed;
  191. }
  192. export function clearAllState() {
  193. objectState = new WeakMap();
  194. }