@yorkie-js/react 0.7.5 → 0.7.7
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/yorkie-js-react.es.js +955 -261
- package/dist/yorkie-js-react.es.js.map +1 -1
- package/dist/yorkie-js-react.js +955 -261
- package/dist/yorkie-js-react.js.map +1 -1
- package/package.json +2 -2
|
@@ -5790,7 +5790,7 @@ function createGrpcWebTransport(options) {
|
|
|
5790
5790
|
}
|
|
5791
5791
|
};
|
|
5792
5792
|
}
|
|
5793
|
-
const file_src_api_yorkie_v1_resources = /* @__PURE__ */ fileDesc("CiFzcmMvYXBpL3lvcmtpZS92MS9yZXNvdXJjZXMucHJvdG8SCXlvcmtpZS52MSKuAQoIU25hcHNob3QSJAoEcm9vdBgBIAEoCzIWLnlvcmtpZS52MS5KU09ORWxlbWVudBI1CglwcmVzZW5jZXMYAiADKAsyIi55b3JraWUudjEuU25hcHNob3QuUHJlc2VuY2VzRW50cnkaRQoOUHJlc2VuY2VzRW50cnkSCwoDa2V5GAEgASgJEiIKBXZhbHVlGAIgASgLMhMueW9ya2llLnYxLlByZXNlbmNlOgI4ASL7AQoKQ2hhbmdlUGFjaxIUCgxkb2N1bWVudF9rZXkYASABKAkSKQoKY2hlY2twb2ludBgCIAEoCzIVLnlvcmtpZS52MS5DaGVja3BvaW50EhAKCHNuYXBzaG90GAMgASgMEiIKB2NoYW5nZXMYBCADKAsyES55b3JraWUudjEuQ2hhbmdlEjAKEW1pbl9zeW5jZWRfdGlja2V0GAUgASgLMhUueW9ya2llLnYxLlRpbWVUaWNrZXQSEgoKaXNfcmVtb3ZlZBgGIAEoCBIwCg52ZXJzaW9uX3ZlY3RvchgHIAEoCzIYLnlvcmtpZS52MS5WZXJzaW9uVmVjdG9yIpgBCgZDaGFuZ2USHwoCaWQYASABKAsyEy55b3JraWUudjEuQ2hhbmdlSUQSDwoHbWVzc2FnZRgCIAEoCRIoCgpvcGVyYXRpb25zGAMgAygLMhQueW9ya2llLnYxLk9wZXJhdGlvbhIyCg9wcmVzZW5jZV9jaGFuZ2UYBCABKAsyGS55b3JraWUudjEuUHJlc2VuY2VDaGFuZ2UihwEKCENoYW5nZUlEEhIKCmNsaWVudF9zZXEYASABKA0SEgoKc2VydmVyX3NlcRgCIAEoAxIPCgdsYW1wb3J0GAMgASgDEhAKCGFjdG9yX2lkGAQgASgMEjAKDnZlcnNpb25fdmVjdG9yGAUgASgLMhgueW9ya2llLnYxLlZlcnNpb25WZWN0b3IidAoNVmVyc2lvblZlY3RvchI0CgZ2ZWN0b3IYASADKAsyJC55b3JraWUudjEuVmVyc2lvblZlY3Rvci5WZWN0b3JFbnRyeRotCgtWZWN0b3JFbnRyeRILCgNrZXkYASABKAkSDQoFdmFsdWUYAiABKAM6AjgBItkaCglPcGVyYXRpb24SJwoDc2V0GAEgASgLMhgueW9ya2llLnYxLk9wZXJhdGlvbi5TZXRIABInCgNhZGQYAiABKAsyGC55b3JraWUudjEuT3BlcmF0aW9uLkFkZEgAEikKBG1vdmUYAyABKAsyGS55b3JraWUudjEuT3BlcmF0aW9uLk1vdmVIABItCgZyZW1vdmUYBCABKAsyGy55b3JraWUudjEuT3BlcmF0aW9uLlJlbW92ZUgAEikKBGVkaXQYBSABKAsyGS55b3JraWUudjEuT3BlcmF0aW9uLkVkaXRIABIrCgVzdHlsZRgHIAEoCzIaLnlvcmtpZS52MS5PcGVyYXRpb24uU3R5bGVIABIxCghpbmNyZWFzZRgIIAEoCzIdLnlvcmtpZS52MS5PcGVyYXRpb24uSW5jcmVhc2VIABIyCgl0cmVlX2VkaXQYCSABKAsyHS55b3JraWUudjEuT3BlcmF0aW9uLlRyZWVFZGl0SAASNAoKdHJlZV9zdHlsZRgKIAEoCzIeLnlvcmtpZS52MS5PcGVyYXRpb24uVHJlZVN0eWxlSAASMgoJYXJyYXlfc2V0GAsgASgLMh0ueW9ya2llLnYxLk9wZXJhdGlvbi5BcnJheVNldEgAGp0BCgNTZXQSMAoRcGFyZW50X2NyZWF0ZWRfYXQYASABKAsyFS55b3JraWUudjEuVGltZVRpY2tldBILCgNrZXkYAiABKAkSKwoFdmFsdWUYAyABKAsyHC55b3JraWUudjEuSlNPTkVsZW1lbnRTaW1wbGUSKgoLZXhlY3V0ZWRfYXQYBCABKAsyFS55b3JraWUudjEuVGltZVRpY2tldBrAAQoDQWRkEjAKEXBhcmVudF9jcmVhdGVkX2F0GAEgASgLMhUueW9ya2llLnYxLlRpbWVUaWNrZXQSLgoPcHJldl9jcmVhdGVkX2F0GAIgASgLMhUueW9ya2llLnYxLlRpbWVUaWNrZXQSKwoFdmFsdWUYAyABKAsyHC55b3JraWUudjEuSlNPTkVsZW1lbnRTaW1wbGUSKgoLZXhlY3V0ZWRfYXQYBCABKAsyFS55b3JraWUudjEuVGltZVRpY2tldBq/AQoETW92ZRIwChFwYXJlbnRfY3JlYXRlZF9hdBgBIAEoCzIVLnlvcmtpZS52MS5UaW1lVGlja2V0Ei4KD3ByZXZfY3JlYXRlZF9hdBgCIAEoCzIVLnlvcmtpZS52MS5UaW1lVGlja2V0EikKCmNyZWF0ZWRfYXQYAyABKAsyFS55b3JraWUudjEuVGltZVRpY2tldBIqCgtleGVjdXRlZF9hdBgEIAEoCzIVLnlvcmtpZS52MS5UaW1lVGlja2V0GpEBCgZSZW1vdmUSMAoRcGFyZW50X2NyZWF0ZWRfYXQYASABKAsyFS55b3JraWUudjEuVGltZVRpY2tldBIpCgpjcmVhdGVkX2F0GAIgASgLMhUueW9ya2llLnYxLlRpbWVUaWNrZXQSKgoLZXhlY3V0ZWRfYXQYAyABKAsyFS55b3JraWUudjEuVGltZVRpY2tldBrZAwoERWRpdBIwChFwYXJlbnRfY3JlYXRlZF9hdBgBIAEoCzIVLnlvcmtpZS52MS5UaW1lVGlja2V0EiQKBGZyb20YAiABKAsyFi55b3JraWUudjEuVGV4dE5vZGVQb3MSIgoCdG8YAyABKAsyFi55b3JraWUudjEuVGV4dE5vZGVQb3MSUwoXY3JlYXRlZF9hdF9tYXBfYnlfYWN0b3IYBCADKAsyMi55b3JraWUudjEuT3BlcmF0aW9uLkVkaXQuQ3JlYXRlZEF0TWFwQnlBY3RvckVudHJ5Eg8KB2NvbnRlbnQYBSABKAkSKgoLZXhlY3V0ZWRfYXQYBiABKAsyFS55b3JraWUudjEuVGltZVRpY2tldBI9CgphdHRyaWJ1dGVzGAcgAygLMikueW9ya2llLnYxLk9wZXJhdGlvbi5FZGl0LkF0dHJpYnV0ZXNFbnRyeRpRChhDcmVhdGVkQXRNYXBCeUFjdG9yRW50cnkSCwoDa2V5GAEgASgJEiQKBXZhbHVlGAIgASgLMhUueW9ya2llLnYxLlRpbWVUaWNrZXQ6AjgBGjEKD0F0dHJpYnV0ZXNFbnRyeRILCgNrZXkYASABKAkSDQoFdmFsdWUYAiABKAk6AjgBGukDCgVTdHlsZRIwChFwYXJlbnRfY3JlYXRlZF9hdBgBIAEoCzIVLnlvcmtpZS52MS5UaW1lVGlja2V0EiQKBGZyb20YAiABKAsyFi55b3JraWUudjEuVGV4dE5vZGVQb3MSIgoCdG8YAyABKAsyFi55b3JraWUudjEuVGV4dE5vZGVQb3MSPgoKYXR0cmlidXRlcxgEIAMoCzIqLnlvcmtpZS52MS5PcGVyYXRpb24uU3R5bGUuQXR0cmlidXRlc0VudHJ5EioKC2V4ZWN1dGVkX2F0GAUgASgLMhUueW9ya2llLnYxLlRpbWVUaWNrZXQSVAoXY3JlYXRlZF9hdF9tYXBfYnlfYWN0b3IYBiADKAsyMy55b3JraWUudjEuT3BlcmF0aW9uLlN0eWxlLkNyZWF0ZWRBdE1hcEJ5QWN0b3JFbnRyeRIcChRhdHRyaWJ1dGVzX3RvX3JlbW92ZRgHIAMoCRoxCg9BdHRyaWJ1dGVzRW50cnkSCwoDa2V5GAEgASgJEg0KBXZhbHVlGAIgASgJOgI4ARpRChhDcmVhdGVkQXRNYXBCeUFjdG9yRW50cnkSCwoDa2V5GAEgASgJEiQKBXZhbHVlGAIgASgLMhUueW9ya2llLnYxLlRpbWVUaWNrZXQ6AjgBGqQBCghJbmNyZWFzZRIwChFwYXJlbnRfY3JlYXRlZF9hdBgBIAEoCzIVLnlvcmtpZS52MS5UaW1lVGlja2V0EisKBXZhbHVlGAIgASgLMhwueW9ya2llLnYxLkpTT05FbGVtZW50U2ltcGxlEioKC2V4ZWN1dGVkX2F0GAMgASgLMhUueW9ya2llLnYxLlRpbWVUaWNrZXQSDQoFYWN0b3IYBCABKAkakwMKCFRyZWVFZGl0EjAKEXBhcmVudF9jcmVhdGVkX2F0GAEgASgLMhUueW9ya2llLnYxLlRpbWVUaWNrZXQSIAoEZnJvbRgCIAEoCzISLnlvcmtpZS52MS5UcmVlUG9zEh4KAnRvGAMgASgLMhIueW9ya2llLnYxLlRyZWVQb3MSVwoXY3JlYXRlZF9hdF9tYXBfYnlfYWN0b3IYBCADKAsyNi55b3JraWUudjEuT3BlcmF0aW9uLlRyZWVFZGl0LkNyZWF0ZWRBdE1hcEJ5QWN0b3JFbnRyeRImCghjb250ZW50cxgFIAMoCzIULnlvcmtpZS52MS5UcmVlTm9kZXMSEwoLc3BsaXRfbGV2ZWwYByABKAUSKgoLZXhlY3V0ZWRfYXQYBiABKAsyFS55b3JraWUudjEuVGltZVRpY2tldBpRChhDcmVhdGVkQXRNYXBCeUFjdG9yRW50cnkSCwoDa2V5GAEgASgJEiQKBXZhbHVlGAIgASgLMhUueW9ya2llLnYxLlRpbWVUaWNrZXQ6AjgBGu0DCglUcmVlU3R5bGUSMAoRcGFyZW50X2NyZWF0ZWRfYXQYASABKAsyFS55b3JraWUudjEuVGltZVRpY2tldBIgCgRmcm9tGAIgASgLMhIueW9ya2llLnYxLlRyZWVQb3MSHgoCdG8YAyABKAsyEi55b3JraWUudjEuVHJlZVBvcxJCCgphdHRyaWJ1dGVzGAQgAygLMi4ueW9ya2llLnYxLk9wZXJhdGlvbi5UcmVlU3R5bGUuQXR0cmlidXRlc0VudHJ5EioKC2V4ZWN1dGVkX2F0GAUgASgLMhUueW9ya2llLnYxLlRpbWVUaWNrZXQSHAoUYXR0cmlidXRlc190b19yZW1vdmUYBiADKAkSWAoXY3JlYXRlZF9hdF9tYXBfYnlfYWN0b3IYByADKAsyNy55b3JraWUudjEuT3BlcmF0aW9uLlRyZWVTdHlsZS5DcmVhdGVkQXRNYXBCeUFjdG9yRW50cnkaMQoPQXR0cmlidXRlc0VudHJ5EgsKA2tleRgBIAEoCRINCgV2YWx1ZRgCIAEoCToCOAEaUQoYQ3JlYXRlZEF0TWFwQnlBY3RvckVudHJ5EgsKA2tleRgBIAEoCRIkCgV2YWx1ZRgCIAEoCzIVLnlvcmtpZS52MS5UaW1lVGlja2V0OgI4ARrAAQoIQXJyYXlTZXQSMAoRcGFyZW50X2NyZWF0ZWRfYXQYASABKAsyFS55b3JraWUudjEuVGltZVRpY2tldBIpCgpjcmVhdGVkX2F0GAIgASgLMhUueW9ya2llLnYxLlRpbWVUaWNrZXQSKwoFdmFsdWUYAyABKAsyHC55b3JraWUudjEuSlNPTkVsZW1lbnRTaW1wbGUSKgoLZXhlY3V0ZWRfYXQYBCABKAsyFS55b3JraWUudjEuVGltZVRpY2tldEIGCgRib2R5IsUBChFKU09ORWxlbWVudFNpbXBsZRIpCgpjcmVhdGVkX2F0GAEgASgLMhUueW9ya2llLnYxLlRpbWVUaWNrZXQSJwoIbW92ZWRfYXQYAiABKAsyFS55b3JraWUudjEuVGltZVRpY2tldBIpCgpyZW1vdmVkX2F0GAMgASgLMhUueW9ya2llLnYxLlRpbWVUaWNrZXQSIgoEdHlwZRgEIAEoDjIULnlvcmtpZS52MS5WYWx1ZVR5cGUSDQoFdmFsdWUYBSABKAwinwsKC0pTT05FbGVtZW50EjgKC2pzb25fb2JqZWN0GAEgASgLMiEueW9ya2llLnYxLkpTT05FbGVtZW50LkpTT05PYmplY3RIABI2Cgpqc29uX2FycmF5GAIgASgLMiAueW9ya2llLnYxLkpTT05FbGVtZW50LkpTT05BcnJheUgAEjUKCXByaW1pdGl2ZRgDIAEoCzIgLnlvcmtpZS52MS5KU09ORWxlbWVudC5QcmltaXRpdmVIABIrCgR0ZXh0GAUgASgLMhsueW9ya2llLnYxLkpTT05FbGVtZW50LlRleHRIABIxCgdjb3VudGVyGAYgASgLMh4ueW9ya2llLnYxLkpTT05FbGVtZW50LkNvdW50ZXJIABIrCgR0cmVlGAcgASgLMhsueW9ya2llLnYxLkpTT05FbGVtZW50LlRyZWVIABquAQoKSlNPTk9iamVjdBIhCgVub2RlcxgBIAMoCzISLnlvcmtpZS52MS5SSFROb2RlEikKCmNyZWF0ZWRfYXQYAiABKAsyFS55b3JraWUudjEuVGltZVRpY2tldBInCghtb3ZlZF9hdBgDIAEoCzIVLnlvcmtpZS52MS5UaW1lVGlja2V0EikKCnJlbW92ZWRfYXQYBCABKAsyFS55b3JraWUudjEuVGltZVRpY2tldBqtAQoJSlNPTkFycmF5EiEKBW5vZGVzGAEgAygLMhIueW9ya2llLnYxLlJHQU5vZGUSKQoKY3JlYXRlZF9hdBgCIAEoCzIVLnlvcmtpZS52MS5UaW1lVGlja2V0EicKCG1vdmVkX2F0GAMgASgLMhUueW9ya2llLnYxLlRpbWVUaWNrZXQSKQoKcmVtb3ZlZF9hdBgEIAEoCzIVLnlvcmtpZS52MS5UaW1lVGlja2V0Gr0BCglQcmltaXRpdmUSIgoEdHlwZRgBIAEoDjIULnlvcmtpZS52MS5WYWx1ZVR5cGUSDQoFdmFsdWUYAiABKAwSKQoKY3JlYXRlZF9hdBgDIAEoCzIVLnlvcmtpZS52MS5UaW1lVGlja2V0EicKCG1vdmVkX2F0GAQgASgLMhUueW9ya2llLnYxLlRpbWVUaWNrZXQSKQoKcmVtb3ZlZF9hdBgFIAEoCzIVLnlvcmtpZS52MS5UaW1lVGlja2V0GqkBCgRUZXh0EiIKBW5vZGVzGAEgAygLMhMueW9ya2llLnYxLlRleHROb2RlEikKCmNyZWF0ZWRfYXQYAiABKAsyFS55b3JraWUudjEuVGltZVRpY2tldBInCghtb3ZlZF9hdBgDIAEoCzIVLnlvcmtpZS52MS5UaW1lVGlja2V0EikKCnJlbW92ZWRfYXQYBCABKAsyFS55b3JraWUudjEuVGltZVRpY2tldBrYAQoHQ291bnRlchIiCgR0eXBlGAEgASgOMhQueW9ya2llLnYxLlZhbHVlVHlwZRINCgV2YWx1ZRgCIAEoDBIpCgpjcmVhdGVkX2F0GAMgASgLMhUueW9ya2llLnYxLlRpbWVUaWNrZXQSJwoIbW92ZWRfYXQYBCABKAsyFS55b3JraWUudjEuVGltZVRpY2tldBIpCgpyZW1vdmVkX2F0GAUgASgLMhUueW9ya2llLnYxLlRpbWVUaWNrZXQSFQoNaGxsX3JlZ2lzdGVycxgHIAEoDEoECAYQBxqpAQoEVHJlZRIiCgVub2RlcxgBIAMoCzITLnlvcmtpZS52MS5UcmVlTm9kZRIpCgpjcmVhdGVkX2F0GAIgASgLMhUueW9ya2llLnYxLlRpbWVUaWNrZXQSJwoIbW92ZWRfYXQYAyABKAsyFS55b3JraWUudjEuVGltZVRpY2tldBIpCgpyZW1vdmVkX2F0GAQgASgLMhUueW9ya2llLnYxLlRpbWVUaWNrZXRCBgoEYm9keSI/CgdSSFROb2RlEgsKA2tleRgBIAEoCRInCgdlbGVtZW50GAIgASgLMhYueW9ya2llLnYxLkpTT05FbGVtZW50IlQKB1JHQU5vZGUSIAoEbmV4dBgBIAEoCzISLnlvcmtpZS52MS5SR0FOb2RlEicKB2VsZW1lbnQYAiABKAsyFi55b3JraWUudjEuSlNPTkVsZW1lbnQiWAoITm9kZUF0dHISDQoFdmFsdWUYASABKAkSKQoKdXBkYXRlZF9hdBgCIAEoCzIVLnlvcmtpZS52MS5UaW1lVGlja2V0EhIKCmlzX3JlbW92ZWQYAyABKAgilAIKCFRleHROb2RlEiEKAmlkGAEgASgLMhUueW9ya2llLnYxLlRleHROb2RlSUQSDQoFdmFsdWUYAiABKAkSKQoKcmVtb3ZlZF9hdBgDIAEoCzIVLnlvcmtpZS52MS5UaW1lVGlja2V0EioKC2luc19wcmV2X2lkGAQgASgLMhUueW9ya2llLnYxLlRleHROb2RlSUQSNwoKYXR0cmlidXRlcxgFIAMoCzIjLnlvcmtpZS52MS5UZXh0Tm9kZS5BdHRyaWJ1dGVzRW50cnkaRgoPQXR0cmlidXRlc0VudHJ5EgsKA2tleRgBIAEoCRIiCgV2YWx1ZRgCIAEoCzITLnlvcmtpZS52MS5Ob2RlQXR0cjoCOAEiRwoKVGV4dE5vZGVJRBIpCgpjcmVhdGVkX2F0GAEgASgLMhUueW9ya2llLnYxLlRpbWVUaWNrZXQSDgoGb2Zmc2V0GAIgASgFIrMDCghUcmVlTm9kZRIhCgJpZBgBIAEoCzIVLnlvcmtpZS52MS5UcmVlTm9kZUlEEgwKBHR5cGUYAiABKAkSDQoFdmFsdWUYAyABKAkSKQoKcmVtb3ZlZF9hdBgEIAEoCzIVLnlvcmtpZS52MS5UaW1lVGlja2V0EioKC2luc19wcmV2X2lkGAUgASgLMhUueW9ya2llLnYxLlRyZWVOb2RlSUQSKgoLaW5zX25leHRfaWQYBiABKAsyFS55b3JraWUudjEuVHJlZU5vZGVJRBINCgVkZXB0aBgHIAEoBRI3CgphdHRyaWJ1dGVzGAggAygLMiMueW9ya2llLnYxLlRyZWVOb2RlLkF0dHJpYnV0ZXNFbnRyeRIqCgttZXJnZWRfZnJvbRgJIAEoCzIVLnlvcmtpZS52MS5UcmVlTm9kZUlEEigKCW1lcmdlZF9hdBgKIAEoCzIVLnlvcmtpZS52MS5UaW1lVGlja2V0GkYKD0F0dHJpYnV0ZXNFbnRyeRILCgNrZXkYASABKAkSIgoFdmFsdWUYAiABKAsyEy55b3JraWUudjEuTm9kZUF0dHI6AjgBIjEKCVRyZWVOb2RlcxIkCgdjb250ZW50GAEgAygLMhMueW9ya2llLnYxLlRyZWVOb2RlIkcKClRyZWVOb2RlSUQSKQoKY3JlYXRlZF9hdBgBIAEoCzIVLnlvcmtpZS52MS5UaW1lVGlja2V0Eg4KBm9mZnNldBgCIAEoBSJjCgdUcmVlUG9zEigKCXBhcmVudF9pZBgBIAEoCzIVLnlvcmtpZS52MS5UcmVlTm9kZUlEEi4KD2xlZnRfc2libGluZ19pZBgCIAEoCzIVLnlvcmtpZS52MS5UcmVlTm9kZUlEImsKBFVzZXISCgoCaWQYASABKAkSFQoNYXV0aF9wcm92aWRlchgCIAEoCRIQCgh1c2VybmFtZRgDIAEoCRIuCgpjcmVhdGVkX2F0GAQgASgLMhouZ29vZ2xlLnByb3RvYnVmLlRpbWVzdGFtcCKJAQoGTWVtYmVyEgoKAmlkGAEgASgJEhIKCnByb2plY3RfaWQYAiABKAkSDwoHdXNlcl9pZBgDIAEoCRIQCgh1c2VybmFtZRgEIAEoCRIMCgRyb2xlGAUgASgJEi4KCmludml0ZWRfYXQYBiABKAsyGi5nb29nbGUucHJvdG9idWYuVGltZXN0YW1wIukGCgdQcm9qZWN0EgoKAmlkGAEgASgJEgwKBG5hbWUYAiABKAkSEgoKcHVibGljX2tleRgDIAEoCRISCgpzZWNyZXRfa2V5GAQgASgJEhgKEGF1dGhfd2ViaG9va191cmwYBSABKAkSHAoUYXV0aF93ZWJob29rX21ldGhvZHMYBiADKAkSIAoYYXV0aF93ZWJob29rX21heF9yZXRyaWVzGBEgASgEEiYKHmF1dGhfd2ViaG9va19taW5fd2FpdF9pbnRlcnZhbBgSIAEoCRImCh5hdXRoX3dlYmhvb2tfbWF4X3dhaXRfaW50ZXJ2YWwYEyABKAkSJAocYXV0aF93ZWJob29rX3JlcXVlc3RfdGltZW91dBgUIAEoCRIZChFldmVudF93ZWJob29rX3VybBgHIAEoCRIcChRldmVudF93ZWJob29rX2V2ZW50cxgIIAMoCRIhChlldmVudF93ZWJob29rX21heF9yZXRyaWVzGBUgASgEEicKH2V2ZW50X3dlYmhvb2tfbWluX3dhaXRfaW50ZXJ2YWwYFiABKAkSJwofZXZlbnRfd2ViaG9va19tYXhfd2FpdF9pbnRlcnZhbBgXIAEoCRIlCh1ldmVudF93ZWJob29rX3JlcXVlc3RfdGltZW91dBgYIAEoCRIjChtjbGllbnRfZGVhY3RpdmF0ZV90aHJlc2hvbGQYCSABKAkSGgoSc25hcHNob3RfdGhyZXNob2xkGBkgASgDEhkKEXNuYXBzaG90X2ludGVydmFsGBogASgDEiQKHG1heF9zdWJzY3JpYmVyc19wZXJfZG9jdW1lbnQYCiABKAUSJAocbWF4X2F0dGFjaG1lbnRzX3Blcl9kb2N1bWVudBgLIAEoBRIdChVtYXhfc2l6ZV9wZXJfZG9jdW1lbnQYDyABKAUSGAoQcmVtb3ZlX29uX2RldGFjaBgQIAEoCBIdChVhdXRvX3JldmlzaW9uX2VuYWJsZWQYGyABKAgSFwoPYWxsb3dlZF9vcmlnaW5zGA4gAygJEi4KCmNyZWF0ZWRfYXQYDCABKAsyGi5nb29nbGUucHJvdG9idWYuVGltZXN0YW1wEi4KCnVwZGF0ZWRfYXQYDSABKAsyGi5nb29nbGUucHJvdG9idWYuVGltZXN0YW1wIi8KC01ldHJpY1BvaW50EhEKCXRpbWVzdGFtcBgBIAEoAxINCgV2YWx1ZRgCIAEoBSKjDAoWVXBkYXRhYmxlUHJvamVjdEZpZWxkcxIqCgRuYW1lGAEgASgLMhwuZ29vZ2xlLnByb3RvYnVmLlN0cmluZ1ZhbHVlEjYKEGF1dGhfd2ViaG9va191cmwYAiABKAsyHC5nb29nbGUucHJvdG9idWYuU3RyaW5nVmFsdWUSUgoUYXV0aF93ZWJob29rX21ldGhvZHMYAyABKAsyNC55b3JraWUudjEuVXBkYXRhYmxlUHJvamVjdEZpZWxkcy5BdXRoV2ViaG9va01ldGhvZHMSPgoYYXV0aF93ZWJob29rX21heF9yZXRyaWVzGAwgASgLMhwuZ29vZ2xlLnByb3RvYnVmLlVJbnQ2NFZhbHVlEkQKHmF1dGhfd2ViaG9va19taW5fd2FpdF9pbnRlcnZhbBgNIAEoCzIcLmdvb2dsZS5wcm90b2J1Zi5TdHJpbmdWYWx1ZRJECh5hdXRoX3dlYmhvb2tfbWF4X3dhaXRfaW50ZXJ2YWwYDiABKAsyHC5nb29nbGUucHJvdG9idWYuU3RyaW5nVmFsdWUSQgocYXV0aF93ZWJob29rX3JlcXVlc3RfdGltZW91dBgPIAEoCzIcLmdvb2dsZS5wcm90b2J1Zi5TdHJpbmdWYWx1ZRI3ChFldmVudF93ZWJob29rX3VybBgEIAEoCzIcLmdvb2dsZS5wcm90b2J1Zi5TdHJpbmdWYWx1ZRJSChRldmVudF93ZWJob29rX2V2ZW50cxgFIAEoCzI0LnlvcmtpZS52MS5VcGRhdGFibGVQcm9qZWN0RmllbGRzLkV2ZW50V2ViaG9va0V2ZW50cxI/ChlldmVudF93ZWJob29rX21heF9yZXRyaWVzGBAgASgLMhwuZ29vZ2xlLnByb3RvYnVmLlVJbnQ2NFZhbHVlEkUKH2V2ZW50X3dlYmhvb2tfbWluX3dhaXRfaW50ZXJ2YWwYESABKAsyHC5nb29nbGUucHJvdG9idWYuU3RyaW5nVmFsdWUSRQofZXZlbnRfd2ViaG9va19tYXhfd2FpdF9pbnRlcnZhbBgSIAEoCzIcLmdvb2dsZS5wcm90b2J1Zi5TdHJpbmdWYWx1ZRJDCh1ldmVudF93ZWJob29rX3JlcXVlc3RfdGltZW91dBgTIAEoCzIcLmdvb2dsZS5wcm90b2J1Zi5TdHJpbmdWYWx1ZRI3ChJzbmFwc2hvdF90aHJlc2hvbGQYFCABKAsyGy5nb29nbGUucHJvdG9idWYuSW50NjRWYWx1ZRI2ChFzbmFwc2hvdF9pbnRlcnZhbBgVIAEoCzIbLmdvb2dsZS5wcm90b2J1Zi5JbnQ2NFZhbHVlEkEKG2NsaWVudF9kZWFjdGl2YXRlX3RocmVzaG9sZBgGIAEoCzIcLmdvb2dsZS5wcm90b2J1Zi5TdHJpbmdWYWx1ZRJBChxtYXhfc3Vic2NyaWJlcnNfcGVyX2RvY3VtZW50GAcgASgLMhsuZ29vZ2xlLnByb3RvYnVmLkludDMyVmFsdWUSQQocbWF4X2F0dGFjaG1lbnRzX3Blcl9kb2N1bWVudBgIIAEoCzIbLmdvb2dsZS5wcm90b2J1Zi5JbnQzMlZhbHVlEjoKFW1heF9zaXplX3Blcl9kb2N1bWVudBgKIAEoCzIbLmdvb2dsZS5wcm90b2J1Zi5JbnQzMlZhbHVlEjQKEHJlbW92ZV9vbl9kZXRhY2gYCyABKAsyGi5nb29nbGUucHJvdG9idWYuQm9vbFZhbHVlEjkKFWF1dG9fcmV2aXNpb25fZW5hYmxlZBgWIAEoCzIaLmdvb2dsZS5wcm90b2J1Zi5Cb29sVmFsdWUSSQoPYWxsb3dlZF9vcmlnaW5zGAkgASgLMjAueW9ya2llLnYxLlVwZGF0YWJsZVByb2plY3RGaWVsZHMuQWxsb3dlZE9yaWdpbnMaJQoSQXV0aFdlYmhvb2tNZXRob2RzEg8KB21ldGhvZHMYASADKAkaJAoSRXZlbnRXZWJob29rRXZlbnRzEg4KBmV2ZW50cxgBIAMoCRohCg5BbGxvd2VkT3JpZ2lucxIPCgdvcmlnaW5zGAEgAygJIqcDCg9Eb2N1bWVudFN1bW1hcnkSCgoCaWQYASABKAkSCwoDa2V5GAIgASgJEgwKBHJvb3QYAyABKAkSGAoQYXR0YWNoZWRfY2xpZW50cxgHIAEoBRIpCg1kb2N1bWVudF9zaXplGAggASgLMhIueW9ya2llLnYxLkRvY1NpemUSEgoKc2NoZW1hX2tleRgJIAEoCRI8CglwcmVzZW5jZXMYCiADKAsyKS55b3JraWUudjEuRG9jdW1lbnRTdW1tYXJ5LlByZXNlbmNlc0VudHJ5Ei4KCmNyZWF0ZWRfYXQYBCABKAsyGi5nb29nbGUucHJvdG9idWYuVGltZXN0YW1wEi8KC2FjY2Vzc2VkX2F0GAUgASgLMhouZ29vZ2xlLnByb3RvYnVmLlRpbWVzdGFtcBIuCgp1cGRhdGVkX2F0GAYgASgLMhouZ29vZ2xlLnByb3RvYnVmLlRpbWVzdGFtcBpFCg5QcmVzZW5jZXNFbnRyeRILCgNrZXkYASABKAkSIgoFdmFsdWUYAiABKAsyEy55b3JraWUudjEuUHJlc2VuY2U6AjgBItoBCg5QcmVzZW5jZUNoYW5nZRIyCgR0eXBlGAEgASgOMiQueW9ya2llLnYxLlByZXNlbmNlQ2hhbmdlLkNoYW5nZVR5cGUSJQoIcHJlc2VuY2UYAiABKAsyEy55b3JraWUudjEuUHJlc2VuY2UibQoKQ2hhbmdlVHlwZRIbChdDSEFOR0VfVFlQRV9VTlNQRUNJRklFRBAAEhMKD0NIQU5HRV9UWVBFX1BVVBABEhYKEkNIQU5HRV9UWVBFX0RFTEVURRACEhUKEUNIQU5HRV9UWVBFX0NMRUFSEAMiZAoIUHJlc2VuY2USKwoEZGF0YRgBIAMoCzIdLnlvcmtpZS52MS5QcmVzZW5jZS5EYXRhRW50cnkaKwoJRGF0YUVudHJ5EgsKA2tleRgBIAEoCRINCgV2YWx1ZRgCIAEoCToCOAEiNAoOQ2hhbm5lbFN1bW1hcnkSCwoDa2V5GAEgASgJEhUKDXNlc3Npb25fY291bnQYAiABKAUiNAoKQ2hlY2twb2ludBISCgpzZXJ2ZXJfc2VxGAEgASgDEhIKCmNsaWVudF9zZXEYAiABKA0iYQoLVGV4dE5vZGVQb3MSKQoKY3JlYXRlZF9hdBgBIAEoCzIVLnlvcmtpZS52MS5UaW1lVGlja2V0Eg4KBm9mZnNldBgCIAEoBRIXCg9yZWxhdGl2ZV9vZmZzZXQYAyABKAUiQgoKVGltZVRpY2tldBIPCgdsYW1wb3J0GAEgASgDEhEKCWRlbGltaXRlchgCIAEoDRIQCghhY3Rvcl9pZBgDIAEoDCIuCgxEb2NFdmVudEJvZHkSDQoFdG9waWMYASABKAkSDwoHcGF5bG9hZBgCIAEoDCJrCghEb2NFdmVudBIlCgR0eXBlGAEgASgOMhcueW9ya2llLnYxLkRvY0V2ZW50VHlwZRIRCglwdWJsaXNoZXIYAiABKAkSJQoEYm9keRgDIAEoCzIXLnlvcmtpZS52MS5Eb2NFdmVudEJvZHki1gEKDENoYW5uZWxFdmVudBIqCgR0eXBlGAEgASgOMhwueW9ya2llLnYxLkNoYW5uZWxFdmVudC5UeXBlEhEKCXB1Ymxpc2hlchgCIAEoCRIVCg1zZXNzaW9uX2NvdW50GAMgASgDEgsKA3NlcRgEIAEoAxINCgV0b3BpYxgFIAEoCRIPCgdwYXlsb2FkGAYgASgMIkMKBFR5cGUSFAoQVFlQRV9VTlNQRUNJRklFRBAAEhEKDVRZUEVfUFJFU0VOQ0UQARISCg5UWVBFX0JST0FEQ0FTVBACIiYKCERhdGFTaXplEgwKBGRhdGEYASABKAUSDAoEbWV0YRgCIAEoBSJNCgdEb2NTaXplEiEKBGxpdmUYASABKAsyEy55b3JraWUudjEuRGF0YVNpemUSHwoCZ2MYAiABKAsyEy55b3JraWUudjEuRGF0YVNpemUikQEKBlNjaGVtYRIKCgJpZBgBIAEoCRIMCgRuYW1lGAIgASgJEg8KB3ZlcnNpb24YAyABKAUSDAoEYm9keRgEIAEoCRIeCgVydWxlcxgFIAMoCzIPLnlvcmtpZS52MS5SdWxlEi4KCmNyZWF0ZWRfYXQYBiABKAsyGi5nb29nbGUucHJvdG9idWYuVGltZXN0YW1wIlAKDFRyZWVOb2RlUnVsZRIRCglub2RlX3R5cGUYASABKAkSDwoHY29udGVudBgCIAEoCRINCgVtYXJrcxgDIAEoCRINCgVncm91cBgEIAEoCSJPCgRSdWxlEgwKBHBhdGgYASABKAkSDAoEdHlwZRgCIAEoCRIrCgp0cmVlX25vZGVzGAMgAygLMhcueW9ya2llLnYxLlRyZWVOb2RlUnVsZSKDAQoPUmV2aXNpb25TdW1tYXJ5EgoKAmlkGAEgASgJEg0KBWxhYmVsGAIgASgJEhMKC2Rlc2NyaXB0aW9uGAMgASgJEhAKCHNuYXBzaG90GAQgASgJEi4KCmNyZWF0ZWRfYXQYBSABKAsyGi5nb29nbGUucHJvdG9idWYuVGltZXN0YW1wKvwCCglWYWx1ZVR5cGUSEwoPVkFMVUVfVFlQRV9OVUxMEAASFgoSVkFMVUVfVFlQRV9CT09MRUFOEAESFgoSVkFMVUVfVFlQRV9JTlRFR0VSEAISEwoPVkFMVUVfVFlQRV9MT05HEAMSFQoRVkFMVUVfVFlQRV9ET1VCTEUQBBIVChFWQUxVRV9UWVBFX1NUUklORxAFEhQKEFZBTFVFX1RZUEVfQllURVMQBhITCg9WQUxVRV9UWVBFX0RBVEUQBxIaChZWQUxVRV9UWVBFX0pTT05fT0JKRUNUEAgSGQoVVkFMVUVfVFlQRV9KU09OX0FSUkFZEAkSEwoPVkFMVUVfVFlQRV9URVhUEAoSGgoWVkFMVUVfVFlQRV9JTlRFR0VSX0NOVBALEhcKE1ZBTFVFX1RZUEVfTE9OR19DTlQQDBITCg9WQUxVRV9UWVBFX1RSRUUQDRIgChxWQUxVRV9UWVBFX0lOVEVHRVJfREVEVVBfQ05UEA4iBAgPEA8qpgEKDERvY0V2ZW50VHlwZRIjCh9ET0NfRVZFTlRfVFlQRV9ET0NVTUVOVF9DSEFOR0VEEAASIwofRE9DX0VWRU5UX1RZUEVfRE9DVU1FTlRfV0FUQ0hFRBABEiUKIURPQ19FVkVOVF9UWVBFX0RPQ1VNRU5UX1VOV0FUQ0hFRBACEiUKIURPQ19FVkVOVF9UWVBFX0RPQ1VNRU5UX0JST0FEQ0FTVBADQkUKEWRldi55b3JraWUuYXBpLnYxUAFaLmdpdGh1Yi5jb20veW9ya2llLXRlYW0veW9ya2llL2FwaS95b3JraWUvdjE7djFiBnByb3RvMw", [file_google_protobuf_timestamp, file_google_protobuf_wrappers]);
|
|
5793
|
+
const file_src_api_yorkie_v1_resources = /* @__PURE__ */ fileDesc("CiFzcmMvYXBpL3lvcmtpZS92MS9yZXNvdXJjZXMucHJvdG8SCXlvcmtpZS52MSKuAQoIU25hcHNob3QSJAoEcm9vdBgBIAEoCzIWLnlvcmtpZS52MS5KU09ORWxlbWVudBI1CglwcmVzZW5jZXMYAiADKAsyIi55b3JraWUudjEuU25hcHNob3QuUHJlc2VuY2VzRW50cnkaRQoOUHJlc2VuY2VzRW50cnkSCwoDa2V5GAEgASgJEiIKBXZhbHVlGAIgASgLMhMueW9ya2llLnYxLlByZXNlbmNlOgI4ASL7AQoKQ2hhbmdlUGFjaxIUCgxkb2N1bWVudF9rZXkYASABKAkSKQoKY2hlY2twb2ludBgCIAEoCzIVLnlvcmtpZS52MS5DaGVja3BvaW50EhAKCHNuYXBzaG90GAMgASgMEiIKB2NoYW5nZXMYBCADKAsyES55b3JraWUudjEuQ2hhbmdlEjAKEW1pbl9zeW5jZWRfdGlja2V0GAUgASgLMhUueW9ya2llLnYxLlRpbWVUaWNrZXQSEgoKaXNfcmVtb3ZlZBgGIAEoCBIwCg52ZXJzaW9uX3ZlY3RvchgHIAEoCzIYLnlvcmtpZS52MS5WZXJzaW9uVmVjdG9yIpgBCgZDaGFuZ2USHwoCaWQYASABKAsyEy55b3JraWUudjEuQ2hhbmdlSUQSDwoHbWVzc2FnZRgCIAEoCRIoCgpvcGVyYXRpb25zGAMgAygLMhQueW9ya2llLnYxLk9wZXJhdGlvbhIyCg9wcmVzZW5jZV9jaGFuZ2UYBCABKAsyGS55b3JraWUudjEuUHJlc2VuY2VDaGFuZ2UihwEKCENoYW5nZUlEEhIKCmNsaWVudF9zZXEYASABKA0SEgoKc2VydmVyX3NlcRgCIAEoAxIPCgdsYW1wb3J0GAMgASgDEhAKCGFjdG9yX2lkGAQgASgMEjAKDnZlcnNpb25fdmVjdG9yGAUgASgLMhgueW9ya2llLnYxLlZlcnNpb25WZWN0b3IidAoNVmVyc2lvblZlY3RvchI0CgZ2ZWN0b3IYASADKAsyJC55b3JraWUudjEuVmVyc2lvblZlY3Rvci5WZWN0b3JFbnRyeRotCgtWZWN0b3JFbnRyeRILCgNrZXkYASABKAkSDQoFdmFsdWUYAiABKAM6AjgBItkaCglPcGVyYXRpb24SJwoDc2V0GAEgASgLMhgueW9ya2llLnYxLk9wZXJhdGlvbi5TZXRIABInCgNhZGQYAiABKAsyGC55b3JraWUudjEuT3BlcmF0aW9uLkFkZEgAEikKBG1vdmUYAyABKAsyGS55b3JraWUudjEuT3BlcmF0aW9uLk1vdmVIABItCgZyZW1vdmUYBCABKAsyGy55b3JraWUudjEuT3BlcmF0aW9uLlJlbW92ZUgAEikKBGVkaXQYBSABKAsyGS55b3JraWUudjEuT3BlcmF0aW9uLkVkaXRIABIrCgVzdHlsZRgHIAEoCzIaLnlvcmtpZS52MS5PcGVyYXRpb24uU3R5bGVIABIxCghpbmNyZWFzZRgIIAEoCzIdLnlvcmtpZS52MS5PcGVyYXRpb24uSW5jcmVhc2VIABIyCgl0cmVlX2VkaXQYCSABKAsyHS55b3JraWUudjEuT3BlcmF0aW9uLlRyZWVFZGl0SAASNAoKdHJlZV9zdHlsZRgKIAEoCzIeLnlvcmtpZS52MS5PcGVyYXRpb24uVHJlZVN0eWxlSAASMgoJYXJyYXlfc2V0GAsgASgLMh0ueW9ya2llLnYxLk9wZXJhdGlvbi5BcnJheVNldEgAGp0BCgNTZXQSMAoRcGFyZW50X2NyZWF0ZWRfYXQYASABKAsyFS55b3JraWUudjEuVGltZVRpY2tldBILCgNrZXkYAiABKAkSKwoFdmFsdWUYAyABKAsyHC55b3JraWUudjEuSlNPTkVsZW1lbnRTaW1wbGUSKgoLZXhlY3V0ZWRfYXQYBCABKAsyFS55b3JraWUudjEuVGltZVRpY2tldBrAAQoDQWRkEjAKEXBhcmVudF9jcmVhdGVkX2F0GAEgASgLMhUueW9ya2llLnYxLlRpbWVUaWNrZXQSLgoPcHJldl9jcmVhdGVkX2F0GAIgASgLMhUueW9ya2llLnYxLlRpbWVUaWNrZXQSKwoFdmFsdWUYAyABKAsyHC55b3JraWUudjEuSlNPTkVsZW1lbnRTaW1wbGUSKgoLZXhlY3V0ZWRfYXQYBCABKAsyFS55b3JraWUudjEuVGltZVRpY2tldBq/AQoETW92ZRIwChFwYXJlbnRfY3JlYXRlZF9hdBgBIAEoCzIVLnlvcmtpZS52MS5UaW1lVGlja2V0Ei4KD3ByZXZfY3JlYXRlZF9hdBgCIAEoCzIVLnlvcmtpZS52MS5UaW1lVGlja2V0EikKCmNyZWF0ZWRfYXQYAyABKAsyFS55b3JraWUudjEuVGltZVRpY2tldBIqCgtleGVjdXRlZF9hdBgEIAEoCzIVLnlvcmtpZS52MS5UaW1lVGlja2V0GpEBCgZSZW1vdmUSMAoRcGFyZW50X2NyZWF0ZWRfYXQYASABKAsyFS55b3JraWUudjEuVGltZVRpY2tldBIpCgpjcmVhdGVkX2F0GAIgASgLMhUueW9ya2llLnYxLlRpbWVUaWNrZXQSKgoLZXhlY3V0ZWRfYXQYAyABKAsyFS55b3JraWUudjEuVGltZVRpY2tldBrZAwoERWRpdBIwChFwYXJlbnRfY3JlYXRlZF9hdBgBIAEoCzIVLnlvcmtpZS52MS5UaW1lVGlja2V0EiQKBGZyb20YAiABKAsyFi55b3JraWUudjEuVGV4dE5vZGVQb3MSIgoCdG8YAyABKAsyFi55b3JraWUudjEuVGV4dE5vZGVQb3MSUwoXY3JlYXRlZF9hdF9tYXBfYnlfYWN0b3IYBCADKAsyMi55b3JraWUudjEuT3BlcmF0aW9uLkVkaXQuQ3JlYXRlZEF0TWFwQnlBY3RvckVudHJ5Eg8KB2NvbnRlbnQYBSABKAkSKgoLZXhlY3V0ZWRfYXQYBiABKAsyFS55b3JraWUudjEuVGltZVRpY2tldBI9CgphdHRyaWJ1dGVzGAcgAygLMikueW9ya2llLnYxLk9wZXJhdGlvbi5FZGl0LkF0dHJpYnV0ZXNFbnRyeRpRChhDcmVhdGVkQXRNYXBCeUFjdG9yRW50cnkSCwoDa2V5GAEgASgJEiQKBXZhbHVlGAIgASgLMhUueW9ya2llLnYxLlRpbWVUaWNrZXQ6AjgBGjEKD0F0dHJpYnV0ZXNFbnRyeRILCgNrZXkYASABKAkSDQoFdmFsdWUYAiABKAk6AjgBGukDCgVTdHlsZRIwChFwYXJlbnRfY3JlYXRlZF9hdBgBIAEoCzIVLnlvcmtpZS52MS5UaW1lVGlja2V0EiQKBGZyb20YAiABKAsyFi55b3JraWUudjEuVGV4dE5vZGVQb3MSIgoCdG8YAyABKAsyFi55b3JraWUudjEuVGV4dE5vZGVQb3MSPgoKYXR0cmlidXRlcxgEIAMoCzIqLnlvcmtpZS52MS5PcGVyYXRpb24uU3R5bGUuQXR0cmlidXRlc0VudHJ5EioKC2V4ZWN1dGVkX2F0GAUgASgLMhUueW9ya2llLnYxLlRpbWVUaWNrZXQSVAoXY3JlYXRlZF9hdF9tYXBfYnlfYWN0b3IYBiADKAsyMy55b3JraWUudjEuT3BlcmF0aW9uLlN0eWxlLkNyZWF0ZWRBdE1hcEJ5QWN0b3JFbnRyeRIcChRhdHRyaWJ1dGVzX3RvX3JlbW92ZRgHIAMoCRoxCg9BdHRyaWJ1dGVzRW50cnkSCwoDa2V5GAEgASgJEg0KBXZhbHVlGAIgASgJOgI4ARpRChhDcmVhdGVkQXRNYXBCeUFjdG9yRW50cnkSCwoDa2V5GAEgASgJEiQKBXZhbHVlGAIgASgLMhUueW9ya2llLnYxLlRpbWVUaWNrZXQ6AjgBGqQBCghJbmNyZWFzZRIwChFwYXJlbnRfY3JlYXRlZF9hdBgBIAEoCzIVLnlvcmtpZS52MS5UaW1lVGlja2V0EisKBXZhbHVlGAIgASgLMhwueW9ya2llLnYxLkpTT05FbGVtZW50U2ltcGxlEioKC2V4ZWN1dGVkX2F0GAMgASgLMhUueW9ya2llLnYxLlRpbWVUaWNrZXQSDQoFYWN0b3IYBCABKAkakwMKCFRyZWVFZGl0EjAKEXBhcmVudF9jcmVhdGVkX2F0GAEgASgLMhUueW9ya2llLnYxLlRpbWVUaWNrZXQSIAoEZnJvbRgCIAEoCzISLnlvcmtpZS52MS5UcmVlUG9zEh4KAnRvGAMgASgLMhIueW9ya2llLnYxLlRyZWVQb3MSVwoXY3JlYXRlZF9hdF9tYXBfYnlfYWN0b3IYBCADKAsyNi55b3JraWUudjEuT3BlcmF0aW9uLlRyZWVFZGl0LkNyZWF0ZWRBdE1hcEJ5QWN0b3JFbnRyeRImCghjb250ZW50cxgFIAMoCzIULnlvcmtpZS52MS5UcmVlTm9kZXMSEwoLc3BsaXRfbGV2ZWwYByABKAUSKgoLZXhlY3V0ZWRfYXQYBiABKAsyFS55b3JraWUudjEuVGltZVRpY2tldBpRChhDcmVhdGVkQXRNYXBCeUFjdG9yRW50cnkSCwoDa2V5GAEgASgJEiQKBXZhbHVlGAIgASgLMhUueW9ya2llLnYxLlRpbWVUaWNrZXQ6AjgBGu0DCglUcmVlU3R5bGUSMAoRcGFyZW50X2NyZWF0ZWRfYXQYASABKAsyFS55b3JraWUudjEuVGltZVRpY2tldBIgCgRmcm9tGAIgASgLMhIueW9ya2llLnYxLlRyZWVQb3MSHgoCdG8YAyABKAsyEi55b3JraWUudjEuVHJlZVBvcxJCCgphdHRyaWJ1dGVzGAQgAygLMi4ueW9ya2llLnYxLk9wZXJhdGlvbi5UcmVlU3R5bGUuQXR0cmlidXRlc0VudHJ5EioKC2V4ZWN1dGVkX2F0GAUgASgLMhUueW9ya2llLnYxLlRpbWVUaWNrZXQSHAoUYXR0cmlidXRlc190b19yZW1vdmUYBiADKAkSWAoXY3JlYXRlZF9hdF9tYXBfYnlfYWN0b3IYByADKAsyNy55b3JraWUudjEuT3BlcmF0aW9uLlRyZWVTdHlsZS5DcmVhdGVkQXRNYXBCeUFjdG9yRW50cnkaMQoPQXR0cmlidXRlc0VudHJ5EgsKA2tleRgBIAEoCRINCgV2YWx1ZRgCIAEoCToCOAEaUQoYQ3JlYXRlZEF0TWFwQnlBY3RvckVudHJ5EgsKA2tleRgBIAEoCRIkCgV2YWx1ZRgCIAEoCzIVLnlvcmtpZS52MS5UaW1lVGlja2V0OgI4ARrAAQoIQXJyYXlTZXQSMAoRcGFyZW50X2NyZWF0ZWRfYXQYASABKAsyFS55b3JraWUudjEuVGltZVRpY2tldBIpCgpjcmVhdGVkX2F0GAIgASgLMhUueW9ya2llLnYxLlRpbWVUaWNrZXQSKwoFdmFsdWUYAyABKAsyHC55b3JraWUudjEuSlNPTkVsZW1lbnRTaW1wbGUSKgoLZXhlY3V0ZWRfYXQYBCABKAsyFS55b3JraWUudjEuVGltZVRpY2tldEIGCgRib2R5IsUBChFKU09ORWxlbWVudFNpbXBsZRIpCgpjcmVhdGVkX2F0GAEgASgLMhUueW9ya2llLnYxLlRpbWVUaWNrZXQSJwoIbW92ZWRfYXQYAiABKAsyFS55b3JraWUudjEuVGltZVRpY2tldBIpCgpyZW1vdmVkX2F0GAMgASgLMhUueW9ya2llLnYxLlRpbWVUaWNrZXQSIgoEdHlwZRgEIAEoDjIULnlvcmtpZS52MS5WYWx1ZVR5cGUSDQoFdmFsdWUYBSABKAwinwsKC0pTT05FbGVtZW50EjgKC2pzb25fb2JqZWN0GAEgASgLMiEueW9ya2llLnYxLkpTT05FbGVtZW50LkpTT05PYmplY3RIABI2Cgpqc29uX2FycmF5GAIgASgLMiAueW9ya2llLnYxLkpTT05FbGVtZW50LkpTT05BcnJheUgAEjUKCXByaW1pdGl2ZRgDIAEoCzIgLnlvcmtpZS52MS5KU09ORWxlbWVudC5QcmltaXRpdmVIABIrCgR0ZXh0GAUgASgLMhsueW9ya2llLnYxLkpTT05FbGVtZW50LlRleHRIABIxCgdjb3VudGVyGAYgASgLMh4ueW9ya2llLnYxLkpTT05FbGVtZW50LkNvdW50ZXJIABIrCgR0cmVlGAcgASgLMhsueW9ya2llLnYxLkpTT05FbGVtZW50LlRyZWVIABquAQoKSlNPTk9iamVjdBIhCgVub2RlcxgBIAMoCzISLnlvcmtpZS52MS5SSFROb2RlEikKCmNyZWF0ZWRfYXQYAiABKAsyFS55b3JraWUudjEuVGltZVRpY2tldBInCghtb3ZlZF9hdBgDIAEoCzIVLnlvcmtpZS52MS5UaW1lVGlja2V0EikKCnJlbW92ZWRfYXQYBCABKAsyFS55b3JraWUudjEuVGltZVRpY2tldBqtAQoJSlNPTkFycmF5EiEKBW5vZGVzGAEgAygLMhIueW9ya2llLnYxLlJHQU5vZGUSKQoKY3JlYXRlZF9hdBgCIAEoCzIVLnlvcmtpZS52MS5UaW1lVGlja2V0EicKCG1vdmVkX2F0GAMgASgLMhUueW9ya2llLnYxLlRpbWVUaWNrZXQSKQoKcmVtb3ZlZF9hdBgEIAEoCzIVLnlvcmtpZS52MS5UaW1lVGlja2V0Gr0BCglQcmltaXRpdmUSIgoEdHlwZRgBIAEoDjIULnlvcmtpZS52MS5WYWx1ZVR5cGUSDQoFdmFsdWUYAiABKAwSKQoKY3JlYXRlZF9hdBgDIAEoCzIVLnlvcmtpZS52MS5UaW1lVGlja2V0EicKCG1vdmVkX2F0GAQgASgLMhUueW9ya2llLnYxLlRpbWVUaWNrZXQSKQoKcmVtb3ZlZF9hdBgFIAEoCzIVLnlvcmtpZS52MS5UaW1lVGlja2V0GqkBCgRUZXh0EiIKBW5vZGVzGAEgAygLMhMueW9ya2llLnYxLlRleHROb2RlEikKCmNyZWF0ZWRfYXQYAiABKAsyFS55b3JraWUudjEuVGltZVRpY2tldBInCghtb3ZlZF9hdBgDIAEoCzIVLnlvcmtpZS52MS5UaW1lVGlja2V0EikKCnJlbW92ZWRfYXQYBCABKAsyFS55b3JraWUudjEuVGltZVRpY2tldBrYAQoHQ291bnRlchIiCgR0eXBlGAEgASgOMhQueW9ya2llLnYxLlZhbHVlVHlwZRINCgV2YWx1ZRgCIAEoDBIpCgpjcmVhdGVkX2F0GAMgASgLMhUueW9ya2llLnYxLlRpbWVUaWNrZXQSJwoIbW92ZWRfYXQYBCABKAsyFS55b3JraWUudjEuVGltZVRpY2tldBIpCgpyZW1vdmVkX2F0GAUgASgLMhUueW9ya2llLnYxLlRpbWVUaWNrZXQSFQoNaGxsX3JlZ2lzdGVycxgHIAEoDEoECAYQBxqpAQoEVHJlZRIiCgVub2RlcxgBIAMoCzITLnlvcmtpZS52MS5UcmVlTm9kZRIpCgpjcmVhdGVkX2F0GAIgASgLMhUueW9ya2llLnYxLlRpbWVUaWNrZXQSJwoIbW92ZWRfYXQYAyABKAsyFS55b3JraWUudjEuVGltZVRpY2tldBIpCgpyZW1vdmVkX2F0GAQgASgLMhUueW9ya2llLnYxLlRpbWVUaWNrZXRCBgoEYm9keSI/CgdSSFROb2RlEgsKA2tleRgBIAEoCRInCgdlbGVtZW50GAIgASgLMhYueW9ya2llLnYxLkpTT05FbGVtZW50Iu4BCgdSR0FOb2RlEiAKBG5leHQYASABKAsyEi55b3JraWUudjEuUkdBTm9kZRInCgdlbGVtZW50GAIgASgLMhYueW9ya2llLnYxLkpTT05FbGVtZW50EjIKE3Bvc2l0aW9uX2NyZWF0ZWRfYXQYAyABKAsyFS55b3JraWUudjEuVGltZVRpY2tldBIwChFwb3NpdGlvbl9tb3ZlZF9hdBgEIAEoCzIVLnlvcmtpZS52MS5UaW1lVGlja2V0EjIKE3Bvc2l0aW9uX3JlbW92ZWRfYXQYBSABKAsyFS55b3JraWUudjEuVGltZVRpY2tldCJYCghOb2RlQXR0chINCgV2YWx1ZRgBIAEoCRIpCgp1cGRhdGVkX2F0GAIgASgLMhUueW9ya2llLnYxLlRpbWVUaWNrZXQSEgoKaXNfcmVtb3ZlZBgDIAEoCCKUAgoIVGV4dE5vZGUSIQoCaWQYASABKAsyFS55b3JraWUudjEuVGV4dE5vZGVJRBINCgV2YWx1ZRgCIAEoCRIpCgpyZW1vdmVkX2F0GAMgASgLMhUueW9ya2llLnYxLlRpbWVUaWNrZXQSKgoLaW5zX3ByZXZfaWQYBCABKAsyFS55b3JraWUudjEuVGV4dE5vZGVJRBI3CgphdHRyaWJ1dGVzGAUgAygLMiMueW9ya2llLnYxLlRleHROb2RlLkF0dHJpYnV0ZXNFbnRyeRpGCg9BdHRyaWJ1dGVzRW50cnkSCwoDa2V5GAEgASgJEiIKBXZhbHVlGAIgASgLMhMueW9ya2llLnYxLk5vZGVBdHRyOgI4ASJHCgpUZXh0Tm9kZUlEEikKCmNyZWF0ZWRfYXQYASABKAsyFS55b3JraWUudjEuVGltZVRpY2tldBIOCgZvZmZzZXQYAiABKAUiswMKCFRyZWVOb2RlEiEKAmlkGAEgASgLMhUueW9ya2llLnYxLlRyZWVOb2RlSUQSDAoEdHlwZRgCIAEoCRINCgV2YWx1ZRgDIAEoCRIpCgpyZW1vdmVkX2F0GAQgASgLMhUueW9ya2llLnYxLlRpbWVUaWNrZXQSKgoLaW5zX3ByZXZfaWQYBSABKAsyFS55b3JraWUudjEuVHJlZU5vZGVJRBIqCgtpbnNfbmV4dF9pZBgGIAEoCzIVLnlvcmtpZS52MS5UcmVlTm9kZUlEEg0KBWRlcHRoGAcgASgFEjcKCmF0dHJpYnV0ZXMYCCADKAsyIy55b3JraWUudjEuVHJlZU5vZGUuQXR0cmlidXRlc0VudHJ5EioKC21lcmdlZF9mcm9tGAkgASgLMhUueW9ya2llLnYxLlRyZWVOb2RlSUQSKAoJbWVyZ2VkX2F0GAogASgLMhUueW9ya2llLnYxLlRpbWVUaWNrZXQaRgoPQXR0cmlidXRlc0VudHJ5EgsKA2tleRgBIAEoCRIiCgV2YWx1ZRgCIAEoCzITLnlvcmtpZS52MS5Ob2RlQXR0cjoCOAEiMQoJVHJlZU5vZGVzEiQKB2NvbnRlbnQYASADKAsyEy55b3JraWUudjEuVHJlZU5vZGUiRwoKVHJlZU5vZGVJRBIpCgpjcmVhdGVkX2F0GAEgASgLMhUueW9ya2llLnYxLlRpbWVUaWNrZXQSDgoGb2Zmc2V0GAIgASgFImMKB1RyZWVQb3MSKAoJcGFyZW50X2lkGAEgASgLMhUueW9ya2llLnYxLlRyZWVOb2RlSUQSLgoPbGVmdF9zaWJsaW5nX2lkGAIgASgLMhUueW9ya2llLnYxLlRyZWVOb2RlSUQiawoEVXNlchIKCgJpZBgBIAEoCRIVCg1hdXRoX3Byb3ZpZGVyGAIgASgJEhAKCHVzZXJuYW1lGAMgASgJEi4KCmNyZWF0ZWRfYXQYBCABKAsyGi5nb29nbGUucHJvdG9idWYuVGltZXN0YW1wIokBCgZNZW1iZXISCgoCaWQYASABKAkSEgoKcHJvamVjdF9pZBgCIAEoCRIPCgd1c2VyX2lkGAMgASgJEhAKCHVzZXJuYW1lGAQgASgJEgwKBHJvbGUYBSABKAkSLgoKaW52aXRlZF9hdBgGIAEoCzIaLmdvb2dsZS5wcm90b2J1Zi5UaW1lc3RhbXAi6QYKB1Byb2plY3QSCgoCaWQYASABKAkSDAoEbmFtZRgCIAEoCRISCgpwdWJsaWNfa2V5GAMgASgJEhIKCnNlY3JldF9rZXkYBCABKAkSGAoQYXV0aF93ZWJob29rX3VybBgFIAEoCRIcChRhdXRoX3dlYmhvb2tfbWV0aG9kcxgGIAMoCRIgChhhdXRoX3dlYmhvb2tfbWF4X3JldHJpZXMYESABKAQSJgoeYXV0aF93ZWJob29rX21pbl93YWl0X2ludGVydmFsGBIgASgJEiYKHmF1dGhfd2ViaG9va19tYXhfd2FpdF9pbnRlcnZhbBgTIAEoCRIkChxhdXRoX3dlYmhvb2tfcmVxdWVzdF90aW1lb3V0GBQgASgJEhkKEWV2ZW50X3dlYmhvb2tfdXJsGAcgASgJEhwKFGV2ZW50X3dlYmhvb2tfZXZlbnRzGAggAygJEiEKGWV2ZW50X3dlYmhvb2tfbWF4X3JldHJpZXMYFSABKAQSJwofZXZlbnRfd2ViaG9va19taW5fd2FpdF9pbnRlcnZhbBgWIAEoCRInCh9ldmVudF93ZWJob29rX21heF93YWl0X2ludGVydmFsGBcgASgJEiUKHWV2ZW50X3dlYmhvb2tfcmVxdWVzdF90aW1lb3V0GBggASgJEiMKG2NsaWVudF9kZWFjdGl2YXRlX3RocmVzaG9sZBgJIAEoCRIaChJzbmFwc2hvdF90aHJlc2hvbGQYGSABKAMSGQoRc25hcHNob3RfaW50ZXJ2YWwYGiABKAMSJAocbWF4X3N1YnNjcmliZXJzX3Blcl9kb2N1bWVudBgKIAEoBRIkChxtYXhfYXR0YWNobWVudHNfcGVyX2RvY3VtZW50GAsgASgFEh0KFW1heF9zaXplX3Blcl9kb2N1bWVudBgPIAEoBRIYChByZW1vdmVfb25fZGV0YWNoGBAgASgIEh0KFWF1dG9fcmV2aXNpb25fZW5hYmxlZBgbIAEoCBIXCg9hbGxvd2VkX29yaWdpbnMYDiADKAkSLgoKY3JlYXRlZF9hdBgMIAEoCzIaLmdvb2dsZS5wcm90b2J1Zi5UaW1lc3RhbXASLgoKdXBkYXRlZF9hdBgNIAEoCzIaLmdvb2dsZS5wcm90b2J1Zi5UaW1lc3RhbXAiLwoLTWV0cmljUG9pbnQSEQoJdGltZXN0YW1wGAEgASgDEg0KBXZhbHVlGAIgASgFIqMMChZVcGRhdGFibGVQcm9qZWN0RmllbGRzEioKBG5hbWUYASABKAsyHC5nb29nbGUucHJvdG9idWYuU3RyaW5nVmFsdWUSNgoQYXV0aF93ZWJob29rX3VybBgCIAEoCzIcLmdvb2dsZS5wcm90b2J1Zi5TdHJpbmdWYWx1ZRJSChRhdXRoX3dlYmhvb2tfbWV0aG9kcxgDIAEoCzI0LnlvcmtpZS52MS5VcGRhdGFibGVQcm9qZWN0RmllbGRzLkF1dGhXZWJob29rTWV0aG9kcxI+ChhhdXRoX3dlYmhvb2tfbWF4X3JldHJpZXMYDCABKAsyHC5nb29nbGUucHJvdG9idWYuVUludDY0VmFsdWUSRAoeYXV0aF93ZWJob29rX21pbl93YWl0X2ludGVydmFsGA0gASgLMhwuZ29vZ2xlLnByb3RvYnVmLlN0cmluZ1ZhbHVlEkQKHmF1dGhfd2ViaG9va19tYXhfd2FpdF9pbnRlcnZhbBgOIAEoCzIcLmdvb2dsZS5wcm90b2J1Zi5TdHJpbmdWYWx1ZRJCChxhdXRoX3dlYmhvb2tfcmVxdWVzdF90aW1lb3V0GA8gASgLMhwuZ29vZ2xlLnByb3RvYnVmLlN0cmluZ1ZhbHVlEjcKEWV2ZW50X3dlYmhvb2tfdXJsGAQgASgLMhwuZ29vZ2xlLnByb3RvYnVmLlN0cmluZ1ZhbHVlElIKFGV2ZW50X3dlYmhvb2tfZXZlbnRzGAUgASgLMjQueW9ya2llLnYxLlVwZGF0YWJsZVByb2plY3RGaWVsZHMuRXZlbnRXZWJob29rRXZlbnRzEj8KGWV2ZW50X3dlYmhvb2tfbWF4X3JldHJpZXMYECABKAsyHC5nb29nbGUucHJvdG9idWYuVUludDY0VmFsdWUSRQofZXZlbnRfd2ViaG9va19taW5fd2FpdF9pbnRlcnZhbBgRIAEoCzIcLmdvb2dsZS5wcm90b2J1Zi5TdHJpbmdWYWx1ZRJFCh9ldmVudF93ZWJob29rX21heF93YWl0X2ludGVydmFsGBIgASgLMhwuZ29vZ2xlLnByb3RvYnVmLlN0cmluZ1ZhbHVlEkMKHWV2ZW50X3dlYmhvb2tfcmVxdWVzdF90aW1lb3V0GBMgASgLMhwuZ29vZ2xlLnByb3RvYnVmLlN0cmluZ1ZhbHVlEjcKEnNuYXBzaG90X3RocmVzaG9sZBgUIAEoCzIbLmdvb2dsZS5wcm90b2J1Zi5JbnQ2NFZhbHVlEjYKEXNuYXBzaG90X2ludGVydmFsGBUgASgLMhsuZ29vZ2xlLnByb3RvYnVmLkludDY0VmFsdWUSQQobY2xpZW50X2RlYWN0aXZhdGVfdGhyZXNob2xkGAYgASgLMhwuZ29vZ2xlLnByb3RvYnVmLlN0cmluZ1ZhbHVlEkEKHG1heF9zdWJzY3JpYmVyc19wZXJfZG9jdW1lbnQYByABKAsyGy5nb29nbGUucHJvdG9idWYuSW50MzJWYWx1ZRJBChxtYXhfYXR0YWNobWVudHNfcGVyX2RvY3VtZW50GAggASgLMhsuZ29vZ2xlLnByb3RvYnVmLkludDMyVmFsdWUSOgoVbWF4X3NpemVfcGVyX2RvY3VtZW50GAogASgLMhsuZ29vZ2xlLnByb3RvYnVmLkludDMyVmFsdWUSNAoQcmVtb3ZlX29uX2RldGFjaBgLIAEoCzIaLmdvb2dsZS5wcm90b2J1Zi5Cb29sVmFsdWUSOQoVYXV0b19yZXZpc2lvbl9lbmFibGVkGBYgASgLMhouZ29vZ2xlLnByb3RvYnVmLkJvb2xWYWx1ZRJJCg9hbGxvd2VkX29yaWdpbnMYCSABKAsyMC55b3JraWUudjEuVXBkYXRhYmxlUHJvamVjdEZpZWxkcy5BbGxvd2VkT3JpZ2lucxolChJBdXRoV2ViaG9va01ldGhvZHMSDwoHbWV0aG9kcxgBIAMoCRokChJFdmVudFdlYmhvb2tFdmVudHMSDgoGZXZlbnRzGAEgAygJGiEKDkFsbG93ZWRPcmlnaW5zEg8KB29yaWdpbnMYASADKAkipwMKD0RvY3VtZW50U3VtbWFyeRIKCgJpZBgBIAEoCRILCgNrZXkYAiABKAkSDAoEcm9vdBgDIAEoCRIYChBhdHRhY2hlZF9jbGllbnRzGAcgASgFEikKDWRvY3VtZW50X3NpemUYCCABKAsyEi55b3JraWUudjEuRG9jU2l6ZRISCgpzY2hlbWFfa2V5GAkgASgJEjwKCXByZXNlbmNlcxgKIAMoCzIpLnlvcmtpZS52MS5Eb2N1bWVudFN1bW1hcnkuUHJlc2VuY2VzRW50cnkSLgoKY3JlYXRlZF9hdBgEIAEoCzIaLmdvb2dsZS5wcm90b2J1Zi5UaW1lc3RhbXASLwoLYWNjZXNzZWRfYXQYBSABKAsyGi5nb29nbGUucHJvdG9idWYuVGltZXN0YW1wEi4KCnVwZGF0ZWRfYXQYBiABKAsyGi5nb29nbGUucHJvdG9idWYuVGltZXN0YW1wGkUKDlByZXNlbmNlc0VudHJ5EgsKA2tleRgBIAEoCRIiCgV2YWx1ZRgCIAEoCzITLnlvcmtpZS52MS5QcmVzZW5jZToCOAEi2gEKDlByZXNlbmNlQ2hhbmdlEjIKBHR5cGUYASABKA4yJC55b3JraWUudjEuUHJlc2VuY2VDaGFuZ2UuQ2hhbmdlVHlwZRIlCghwcmVzZW5jZRgCIAEoCzITLnlvcmtpZS52MS5QcmVzZW5jZSJtCgpDaGFuZ2VUeXBlEhsKF0NIQU5HRV9UWVBFX1VOU1BFQ0lGSUVEEAASEwoPQ0hBTkdFX1RZUEVfUFVUEAESFgoSQ0hBTkdFX1RZUEVfREVMRVRFEAISFQoRQ0hBTkdFX1RZUEVfQ0xFQVIQAyJkCghQcmVzZW5jZRIrCgRkYXRhGAEgAygLMh0ueW9ya2llLnYxLlByZXNlbmNlLkRhdGFFbnRyeRorCglEYXRhRW50cnkSCwoDa2V5GAEgASgJEg0KBXZhbHVlGAIgASgJOgI4ASI0Cg5DaGFubmVsU3VtbWFyeRILCgNrZXkYASABKAkSFQoNc2Vzc2lvbl9jb3VudBgCIAEoBSI0CgpDaGVja3BvaW50EhIKCnNlcnZlcl9zZXEYASABKAMSEgoKY2xpZW50X3NlcRgCIAEoDSJhCgtUZXh0Tm9kZVBvcxIpCgpjcmVhdGVkX2F0GAEgASgLMhUueW9ya2llLnYxLlRpbWVUaWNrZXQSDgoGb2Zmc2V0GAIgASgFEhcKD3JlbGF0aXZlX29mZnNldBgDIAEoBSJCCgpUaW1lVGlja2V0Eg8KB2xhbXBvcnQYASABKAMSEQoJZGVsaW1pdGVyGAIgASgNEhAKCGFjdG9yX2lkGAMgASgMIi4KDERvY0V2ZW50Qm9keRINCgV0b3BpYxgBIAEoCRIPCgdwYXlsb2FkGAIgASgMImsKCERvY0V2ZW50EiUKBHR5cGUYASABKA4yFy55b3JraWUudjEuRG9jRXZlbnRUeXBlEhEKCXB1Ymxpc2hlchgCIAEoCRIlCgRib2R5GAMgASgLMhcueW9ya2llLnYxLkRvY0V2ZW50Qm9keSLWAQoMQ2hhbm5lbEV2ZW50EioKBHR5cGUYASABKA4yHC55b3JraWUudjEuQ2hhbm5lbEV2ZW50LlR5cGUSEQoJcHVibGlzaGVyGAIgASgJEhUKDXNlc3Npb25fY291bnQYAyABKAMSCwoDc2VxGAQgASgDEg0KBXRvcGljGAUgASgJEg8KB3BheWxvYWQYBiABKAwiQwoEVHlwZRIUChBUWVBFX1VOU1BFQ0lGSUVEEAASEQoNVFlQRV9QUkVTRU5DRRABEhIKDlRZUEVfQlJPQURDQVNUEAIiJgoIRGF0YVNpemUSDAoEZGF0YRgBIAEoBRIMCgRtZXRhGAIgASgFIk0KB0RvY1NpemUSIQoEbGl2ZRgBIAEoCzITLnlvcmtpZS52MS5EYXRhU2l6ZRIfCgJnYxgCIAEoCzITLnlvcmtpZS52MS5EYXRhU2l6ZSKRAQoGU2NoZW1hEgoKAmlkGAEgASgJEgwKBG5hbWUYAiABKAkSDwoHdmVyc2lvbhgDIAEoBRIMCgRib2R5GAQgASgJEh4KBXJ1bGVzGAUgAygLMg8ueW9ya2llLnYxLlJ1bGUSLgoKY3JlYXRlZF9hdBgGIAEoCzIaLmdvb2dsZS5wcm90b2J1Zi5UaW1lc3RhbXAiUAoMVHJlZU5vZGVSdWxlEhEKCW5vZGVfdHlwZRgBIAEoCRIPCgdjb250ZW50GAIgASgJEg0KBW1hcmtzGAMgASgJEg0KBWdyb3VwGAQgASgJIk8KBFJ1bGUSDAoEcGF0aBgBIAEoCRIMCgR0eXBlGAIgASgJEisKCnRyZWVfbm9kZXMYAyADKAsyFy55b3JraWUudjEuVHJlZU5vZGVSdWxlIoMBCg9SZXZpc2lvblN1bW1hcnkSCgoCaWQYASABKAkSDQoFbGFiZWwYAiABKAkSEwoLZGVzY3JpcHRpb24YAyABKAkSEAoIc25hcHNob3QYBCABKAkSLgoKY3JlYXRlZF9hdBgFIAEoCzIaLmdvb2dsZS5wcm90b2J1Zi5UaW1lc3RhbXAq/AIKCVZhbHVlVHlwZRITCg9WQUxVRV9UWVBFX05VTEwQABIWChJWQUxVRV9UWVBFX0JPT0xFQU4QARIWChJWQUxVRV9UWVBFX0lOVEVHRVIQAhITCg9WQUxVRV9UWVBFX0xPTkcQAxIVChFWQUxVRV9UWVBFX0RPVUJMRRAEEhUKEVZBTFVFX1RZUEVfU1RSSU5HEAUSFAoQVkFMVUVfVFlQRV9CWVRFUxAGEhMKD1ZBTFVFX1RZUEVfREFURRAHEhoKFlZBTFVFX1RZUEVfSlNPTl9PQkpFQ1QQCBIZChVWQUxVRV9UWVBFX0pTT05fQVJSQVkQCRITCg9WQUxVRV9UWVBFX1RFWFQQChIaChZWQUxVRV9UWVBFX0lOVEVHRVJfQ05UEAsSFwoTVkFMVUVfVFlQRV9MT05HX0NOVBAMEhMKD1ZBTFVFX1RZUEVfVFJFRRANEiAKHFZBTFVFX1RZUEVfSU5URUdFUl9ERURVUF9DTlQQDiIECA8QDyqmAQoMRG9jRXZlbnRUeXBlEiMKH0RPQ19FVkVOVF9UWVBFX0RPQ1VNRU5UX0NIQU5HRUQQABIjCh9ET0NfRVZFTlRfVFlQRV9ET0NVTUVOVF9XQVRDSEVEEAESJQohRE9DX0VWRU5UX1RZUEVfRE9DVU1FTlRfVU5XQVRDSEVEEAISJQohRE9DX0VWRU5UX1RZUEVfRE9DVU1FTlRfQlJPQURDQVNUEANCRQoRZGV2LnlvcmtpZS5hcGkudjFQAVouZ2l0aHViLmNvbS95b3JraWUtdGVhbS95b3JraWUvYXBpL3lvcmtpZS92MTt2MWIGcHJvdG8z", [file_google_protobuf_timestamp, file_google_protobuf_wrappers]);
|
|
5794
5794
|
const SnapshotSchema = /* @__PURE__ */ messageDesc(file_src_api_yorkie_v1_resources, 0);
|
|
5795
5795
|
const ChangePackSchema = /* @__PURE__ */ messageDesc(file_src_api_yorkie_v1_resources, 1);
|
|
5796
5796
|
const ChangeSchema = /* @__PURE__ */ messageDesc(file_src_api_yorkie_v1_resources, 2);
|
|
@@ -7139,6 +7139,13 @@ class Primitive extends CRDTElement {
|
|
|
7139
7139
|
if (this.valueType === 5) {
|
|
7140
7140
|
return `"${escapeString(this.value)}"`;
|
|
7141
7141
|
}
|
|
7142
|
+
if (this.valueType === 6) {
|
|
7143
|
+
const bytes = this.value;
|
|
7144
|
+
return `"${btoa(String.fromCharCode(...bytes))}"`;
|
|
7145
|
+
}
|
|
7146
|
+
if (this.valueType === 7) {
|
|
7147
|
+
return `"${this.value.toISOString()}"`;
|
|
7148
|
+
}
|
|
7142
7149
|
return `${this.value}`;
|
|
7143
7150
|
}
|
|
7144
7151
|
/**
|
|
@@ -7281,19 +7288,54 @@ class Primitive extends CRDTElement {
|
|
|
7281
7288
|
}
|
|
7282
7289
|
}
|
|
7283
7290
|
}
|
|
7291
|
+
class ElementEntry {
|
|
7292
|
+
elem;
|
|
7293
|
+
positionNode;
|
|
7294
|
+
posMovedAt;
|
|
7295
|
+
constructor(elem) {
|
|
7296
|
+
this.elem = elem;
|
|
7297
|
+
}
|
|
7298
|
+
}
|
|
7284
7299
|
class RGATreeListNode extends SplayNode {
|
|
7300
|
+
_elementEntry;
|
|
7301
|
+
_createdAt;
|
|
7302
|
+
_removedAt;
|
|
7285
7303
|
prev;
|
|
7286
7304
|
next;
|
|
7287
|
-
|
|
7288
|
-
|
|
7289
|
-
|
|
7290
|
-
|
|
7305
|
+
constructor(elem, createdAt) {
|
|
7306
|
+
super(elem);
|
|
7307
|
+
this._createdAt = createdAt;
|
|
7308
|
+
}
|
|
7309
|
+
/**
|
|
7310
|
+
* `createWithElement` creates a new node that owns an element.
|
|
7311
|
+
*/
|
|
7312
|
+
static createWithElement(elem) {
|
|
7313
|
+
const entry = new ElementEntry(elem);
|
|
7314
|
+
const node = new RGATreeListNode(elem, elem.getCreatedAt());
|
|
7315
|
+
entry.positionNode = node;
|
|
7316
|
+
node._elementEntry = entry;
|
|
7317
|
+
return node;
|
|
7318
|
+
}
|
|
7319
|
+
/**
|
|
7320
|
+
* `createBarePosition` creates a position node without an element
|
|
7321
|
+
* (used for move).
|
|
7322
|
+
*/
|
|
7323
|
+
static createBarePosition(createdAt) {
|
|
7324
|
+
return new RGATreeListNode(void 0, createdAt);
|
|
7291
7325
|
}
|
|
7292
7326
|
/**
|
|
7293
|
-
* `createAfter` creates a new node
|
|
7327
|
+
* `createAfter` creates a new node with the given element after
|
|
7328
|
+
* the given prev node.
|
|
7294
7329
|
*/
|
|
7295
|
-
static createAfter(prev,
|
|
7296
|
-
const newNode =
|
|
7330
|
+
static createAfter(prev, elem) {
|
|
7331
|
+
const newNode = RGATreeListNode.createWithElement(elem);
|
|
7332
|
+
RGATreeListNode.insertNodeAfter(prev, newNode);
|
|
7333
|
+
return newNode;
|
|
7334
|
+
}
|
|
7335
|
+
/**
|
|
7336
|
+
* `insertNodeAfter` inserts a node after the given prev node.
|
|
7337
|
+
*/
|
|
7338
|
+
static insertNodeAfter(prev, newNode) {
|
|
7297
7339
|
const prevNext = prev.next;
|
|
7298
7340
|
prev.next = newNode;
|
|
7299
7341
|
newNode.prev = prev;
|
|
@@ -7301,26 +7343,41 @@ class RGATreeListNode extends SplayNode {
|
|
|
7301
7343
|
if (prevNext) {
|
|
7302
7344
|
prevNext.prev = newNode;
|
|
7303
7345
|
}
|
|
7304
|
-
return newNode;
|
|
7305
7346
|
}
|
|
7306
7347
|
/**
|
|
7307
|
-
* `remove` removes
|
|
7348
|
+
* `remove` removes the element based on removing time.
|
|
7308
7349
|
*/
|
|
7309
7350
|
remove(removedAt) {
|
|
7310
|
-
|
|
7351
|
+
if (!this._elementEntry) {
|
|
7352
|
+
return false;
|
|
7353
|
+
}
|
|
7354
|
+
return this._elementEntry.elem.remove(removedAt);
|
|
7311
7355
|
}
|
|
7312
7356
|
/**
|
|
7313
|
-
* `getCreatedAt` returns creation time
|
|
7357
|
+
* `getCreatedAt` returns the creation time. For live nodes with
|
|
7358
|
+
* elements, returns the element's createdAt for backward
|
|
7359
|
+
* compatibility.
|
|
7314
7360
|
*/
|
|
7315
7361
|
getCreatedAt() {
|
|
7316
|
-
|
|
7362
|
+
if (this._elementEntry) {
|
|
7363
|
+
return this._elementEntry.elem.getCreatedAt();
|
|
7364
|
+
}
|
|
7365
|
+
return this._createdAt;
|
|
7317
7366
|
}
|
|
7318
7367
|
/**
|
|
7319
|
-
* `getPositionedAt` returns the time
|
|
7320
|
-
*
|
|
7368
|
+
* `getPositionedAt` returns the time this element was positioned.
|
|
7369
|
+
* For live nodes, the position register (posMovedAt) is the source
|
|
7370
|
+
* of truth. For dead nodes (no element), the position node's own
|
|
7371
|
+
* createdAt is used.
|
|
7321
7372
|
*/
|
|
7322
7373
|
getPositionedAt() {
|
|
7323
|
-
|
|
7374
|
+
if (this._elementEntry) {
|
|
7375
|
+
if (this._elementEntry.posMovedAt) {
|
|
7376
|
+
return this._elementEntry.posMovedAt;
|
|
7377
|
+
}
|
|
7378
|
+
return this._elementEntry.elem.getCreatedAt();
|
|
7379
|
+
}
|
|
7380
|
+
return this._createdAt;
|
|
7324
7381
|
}
|
|
7325
7382
|
/**
|
|
7326
7383
|
* `release` releases prev and next node.
|
|
@@ -7337,9 +7394,13 @@ class RGATreeListNode extends SplayNode {
|
|
|
7337
7394
|
}
|
|
7338
7395
|
/**
|
|
7339
7396
|
* `getLength` returns the length of this node.
|
|
7397
|
+
* Dead nodes (no element) return 0, removed elements return 0.
|
|
7340
7398
|
*/
|
|
7341
7399
|
getLength() {
|
|
7342
|
-
|
|
7400
|
+
if (!this._elementEntry || this.isRemoved()) {
|
|
7401
|
+
return 0;
|
|
7402
|
+
}
|
|
7403
|
+
return 1;
|
|
7343
7404
|
}
|
|
7344
7405
|
/**
|
|
7345
7406
|
* `getPrev` returns a previous node.
|
|
@@ -7354,28 +7415,87 @@ class RGATreeListNode extends SplayNode {
|
|
|
7354
7415
|
return this.next;
|
|
7355
7416
|
}
|
|
7356
7417
|
/**
|
|
7357
|
-
* `
|
|
7418
|
+
* `getValue` returns the element value.
|
|
7358
7419
|
*/
|
|
7359
|
-
|
|
7360
|
-
|
|
7420
|
+
getValue() {
|
|
7421
|
+
if (!this._elementEntry) {
|
|
7422
|
+
return this.value;
|
|
7423
|
+
}
|
|
7424
|
+
return this._elementEntry.elem;
|
|
7361
7425
|
}
|
|
7362
7426
|
/**
|
|
7363
|
-
* `
|
|
7427
|
+
* `getElement` returns the element or undefined if dead position.
|
|
7364
7428
|
*/
|
|
7365
|
-
|
|
7366
|
-
this.
|
|
7429
|
+
getElement() {
|
|
7430
|
+
return this._elementEntry?.elem;
|
|
7367
7431
|
}
|
|
7368
7432
|
/**
|
|
7369
|
-
* `
|
|
7433
|
+
* `isRemoved` checks if the value was removed.
|
|
7370
7434
|
*/
|
|
7371
|
-
|
|
7372
|
-
|
|
7435
|
+
isRemoved() {
|
|
7436
|
+
if (!this._elementEntry) {
|
|
7437
|
+
return true;
|
|
7438
|
+
}
|
|
7439
|
+
return this._elementEntry.elem.isRemoved();
|
|
7373
7440
|
}
|
|
7374
7441
|
/**
|
|
7375
|
-
* `
|
|
7442
|
+
* `getElementEntry` returns the element entry.
|
|
7376
7443
|
*/
|
|
7377
|
-
|
|
7378
|
-
return this.
|
|
7444
|
+
getElementEntry() {
|
|
7445
|
+
return this._elementEntry;
|
|
7446
|
+
}
|
|
7447
|
+
/**
|
|
7448
|
+
* `setElementEntry` sets the element entry.
|
|
7449
|
+
*/
|
|
7450
|
+
setElementEntry(entry) {
|
|
7451
|
+
this._elementEntry = entry;
|
|
7452
|
+
}
|
|
7453
|
+
/**
|
|
7454
|
+
* `getPositionCreatedAt` returns the position node's own createdAt.
|
|
7455
|
+
*/
|
|
7456
|
+
getPositionCreatedAt() {
|
|
7457
|
+
return this._createdAt;
|
|
7458
|
+
}
|
|
7459
|
+
/**
|
|
7460
|
+
* `getPositionMovedAt` returns the LWW timestamp of the element's
|
|
7461
|
+
* move into this position. Undefined for insert-created positions.
|
|
7462
|
+
*/
|
|
7463
|
+
getPositionMovedAt() {
|
|
7464
|
+
if (!this._elementEntry) {
|
|
7465
|
+
return void 0;
|
|
7466
|
+
}
|
|
7467
|
+
return this._elementEntry.posMovedAt;
|
|
7468
|
+
}
|
|
7469
|
+
/**
|
|
7470
|
+
* `getRemovedAt` returns the time this dead position node was
|
|
7471
|
+
* removed (for GC).
|
|
7472
|
+
*/
|
|
7473
|
+
getRemovedAt() {
|
|
7474
|
+
return this._removedAt;
|
|
7475
|
+
}
|
|
7476
|
+
/**
|
|
7477
|
+
* `setRemovedAt` sets the removal time of this position node.
|
|
7478
|
+
*/
|
|
7479
|
+
setRemovedAt(removedAt) {
|
|
7480
|
+
this._removedAt = removedAt;
|
|
7481
|
+
}
|
|
7482
|
+
/**
|
|
7483
|
+
* `toIDString` returns a unique identifier for this position node
|
|
7484
|
+
* (for GC).
|
|
7485
|
+
*/
|
|
7486
|
+
toIDString() {
|
|
7487
|
+
return this._createdAt.toIDString();
|
|
7488
|
+
}
|
|
7489
|
+
/**
|
|
7490
|
+
* `getDataSize` returns the data size of this position node
|
|
7491
|
+
* (for GC).
|
|
7492
|
+
*/
|
|
7493
|
+
getDataSize() {
|
|
7494
|
+
let meta = TimeTicketSize;
|
|
7495
|
+
if (this._removedAt) {
|
|
7496
|
+
meta += TimeTicketSize;
|
|
7497
|
+
}
|
|
7498
|
+
return { data: 0, meta };
|
|
7379
7499
|
}
|
|
7380
7500
|
}
|
|
7381
7501
|
class RGATreeList {
|
|
@@ -7383,13 +7503,15 @@ class RGATreeList {
|
|
|
7383
7503
|
last;
|
|
7384
7504
|
nodeMapByIndex;
|
|
7385
7505
|
nodeMapByCreatedAt;
|
|
7506
|
+
elementMapByCreatedAt;
|
|
7386
7507
|
constructor() {
|
|
7387
7508
|
const dummyValue = Primitive.of(0, InitialTimeTicket);
|
|
7388
7509
|
dummyValue.setRemovedAt(InitialTimeTicket);
|
|
7389
|
-
this.dummyHead =
|
|
7510
|
+
this.dummyHead = RGATreeListNode.createWithElement(dummyValue);
|
|
7390
7511
|
this.last = this.dummyHead;
|
|
7391
7512
|
this.nodeMapByIndex = new SplayTree();
|
|
7392
7513
|
this.nodeMapByCreatedAt = /* @__PURE__ */ new Map();
|
|
7514
|
+
this.elementMapByCreatedAt = /* @__PURE__ */ new Map();
|
|
7393
7515
|
this.nodeMapByIndex.insert(this.dummyHead);
|
|
7394
7516
|
this.nodeMapByCreatedAt.set(
|
|
7395
7517
|
this.dummyHead.getCreatedAt().toIDString(),
|
|
@@ -7409,22 +7531,10 @@ class RGATreeList {
|
|
|
7409
7531
|
return this.nodeMapByIndex.length;
|
|
7410
7532
|
}
|
|
7411
7533
|
/**
|
|
7412
|
-
* `findNextBeforeExecutedAt`
|
|
7413
|
-
*
|
|
7414
|
-
* given node and returns the next node.
|
|
7415
|
-
* @returns the next node of the given createdAt and executedAt
|
|
7534
|
+
* `findNextBeforeExecutedAt` walks forward from the given node,
|
|
7535
|
+
* skipping nodes positioned after executedAt (RGA insertion rule).
|
|
7416
7536
|
*/
|
|
7417
|
-
findNextBeforeExecutedAt(
|
|
7418
|
-
let node = this.nodeMapByCreatedAt.get(createdAt.toIDString());
|
|
7419
|
-
if (!node) {
|
|
7420
|
-
throw new YorkieError(
|
|
7421
|
-
Code.ErrInvalidArgument,
|
|
7422
|
-
`cant find the given node: ${createdAt.toIDString()}`
|
|
7423
|
-
);
|
|
7424
|
-
}
|
|
7425
|
-
while (node.getValue().getMovedAt() && node.getValue().getMovedAt().after(executedAt) && node.getMovedFrom()) {
|
|
7426
|
-
node = node.getMovedFrom();
|
|
7427
|
-
}
|
|
7537
|
+
findNextBeforeExecutedAt(node, executedAt) {
|
|
7428
7538
|
while (node.getNext() && node.getNext().getPositionedAt().after(executedAt)) {
|
|
7429
7539
|
node = node.getNext();
|
|
7430
7540
|
}
|
|
@@ -7436,65 +7546,103 @@ class RGATreeList {
|
|
|
7436
7546
|
}
|
|
7437
7547
|
node.release();
|
|
7438
7548
|
this.nodeMapByIndex.delete(node);
|
|
7439
|
-
this.nodeMapByCreatedAt.delete(node.
|
|
7549
|
+
this.nodeMapByCreatedAt.delete(node.getPositionCreatedAt().toIDString());
|
|
7440
7550
|
}
|
|
7441
7551
|
/**
|
|
7442
|
-
* `insertAfter` adds a new node with the value after the given
|
|
7552
|
+
* `insertAfter` adds a new node with the value after the given
|
|
7553
|
+
* position. prevCreatedAt is a position node identity. Looks up
|
|
7554
|
+
* nodeMapByCreatedAt first, then elementMapByCreatedAt for backward
|
|
7555
|
+
* compatibility.
|
|
7443
7556
|
*/
|
|
7444
7557
|
insertAfter(prevCreatedAt, value, executedAt = value.getCreatedAt()) {
|
|
7445
|
-
|
|
7558
|
+
let startNode = this.nodeMapByCreatedAt.get(prevCreatedAt.toIDString());
|
|
7559
|
+
if (!startNode) {
|
|
7560
|
+
const entry = this.elementMapByCreatedAt.get(prevCreatedAt.toIDString());
|
|
7561
|
+
if (entry) {
|
|
7562
|
+
startNode = entry.positionNode;
|
|
7563
|
+
}
|
|
7564
|
+
}
|
|
7565
|
+
if (!startNode) {
|
|
7566
|
+
throw new YorkieError(
|
|
7567
|
+
Code.ErrInvalidArgument,
|
|
7568
|
+
`cant find the given node: ${prevCreatedAt.toIDString()}`
|
|
7569
|
+
);
|
|
7570
|
+
}
|
|
7571
|
+
const prevNode = this.findNextBeforeExecutedAt(startNode, executedAt);
|
|
7446
7572
|
const newNode = RGATreeListNode.createAfter(prevNode, value);
|
|
7447
7573
|
if (prevNode === this.last) {
|
|
7448
7574
|
this.last = newNode;
|
|
7449
7575
|
}
|
|
7450
7576
|
this.nodeMapByIndex.insertAfter(prevNode, newNode);
|
|
7451
|
-
this.nodeMapByCreatedAt.set(
|
|
7577
|
+
this.nodeMapByCreatedAt.set(value.getCreatedAt().toIDString(), newNode);
|
|
7578
|
+
this.elementMapByCreatedAt.set(
|
|
7579
|
+
value.getCreatedAt().toIDString(),
|
|
7580
|
+
newNode.getElementEntry()
|
|
7581
|
+
);
|
|
7452
7582
|
return newNode;
|
|
7453
7583
|
}
|
|
7454
7584
|
/**
|
|
7455
|
-
* `
|
|
7456
|
-
*
|
|
7585
|
+
* `insertPositionAfter` creates a bare position node after
|
|
7586
|
+
* resolving position via forward skip (RGA insertion rule).
|
|
7587
|
+
* Used by moveAfter. prevCreatedAt is a POSITION node identity.
|
|
7588
|
+
*/
|
|
7589
|
+
insertPositionAfter(prevCreatedAt, executedAt) {
|
|
7590
|
+
const startNode = this.nodeMapByCreatedAt.get(prevCreatedAt.toIDString());
|
|
7591
|
+
if (!startNode) {
|
|
7592
|
+
throw new YorkieError(
|
|
7593
|
+
Code.ErrInvalidArgument,
|
|
7594
|
+
`cant find the given node: ${prevCreatedAt.toIDString()}`
|
|
7595
|
+
);
|
|
7596
|
+
}
|
|
7597
|
+
const prevNode = this.findNextBeforeExecutedAt(startNode, executedAt);
|
|
7598
|
+
const newNode = RGATreeListNode.createBarePosition(executedAt);
|
|
7599
|
+
RGATreeListNode.insertNodeAfter(prevNode, newNode);
|
|
7600
|
+
if (prevNode === this.last) {
|
|
7601
|
+
this.last = newNode;
|
|
7602
|
+
}
|
|
7603
|
+
this.nodeMapByIndex.insertAfter(prevNode, newNode);
|
|
7604
|
+
this.nodeMapByCreatedAt.set(executedAt.toIDString(), newNode);
|
|
7605
|
+
return newNode;
|
|
7606
|
+
}
|
|
7607
|
+
/**
|
|
7608
|
+
* `moveAfter` moves the given `createdAt` element after the
|
|
7609
|
+
* `prevCreatedAt` element using LWW position register semantics.
|
|
7610
|
+
* Returns the dead position node (if any) for GC registration.
|
|
7457
7611
|
*/
|
|
7458
7612
|
moveAfter(prevCreatedAt, createdAt, executedAt) {
|
|
7459
|
-
|
|
7460
|
-
if (!prevNode) {
|
|
7613
|
+
if (!this.nodeMapByCreatedAt.has(prevCreatedAt.toIDString())) {
|
|
7461
7614
|
throw new YorkieError(
|
|
7462
7615
|
Code.ErrInvalidArgument,
|
|
7463
7616
|
`cant find the given node: ${prevCreatedAt.toIDString()}`
|
|
7464
7617
|
);
|
|
7465
7618
|
}
|
|
7466
|
-
|
|
7467
|
-
if (!
|
|
7619
|
+
const entry = this.elementMapByCreatedAt.get(createdAt.toIDString());
|
|
7620
|
+
if (!entry) {
|
|
7468
7621
|
throw new YorkieError(
|
|
7469
7622
|
Code.ErrInvalidArgument,
|
|
7470
7623
|
`cant find the given node: ${createdAt.toIDString()}`
|
|
7471
7624
|
);
|
|
7472
7625
|
}
|
|
7473
|
-
if (
|
|
7474
|
-
|
|
7475
|
-
|
|
7476
|
-
this.release(node);
|
|
7477
|
-
node = this.insertAfter(
|
|
7478
|
-
prevNode.getCreatedAt(),
|
|
7479
|
-
node.getValue(),
|
|
7480
|
-
executedAt
|
|
7481
|
-
);
|
|
7482
|
-
node.getValue().setMovedAt(executedAt);
|
|
7483
|
-
node.setMovedFrom(movedFrom);
|
|
7484
|
-
while (nextNode && nextNode.getPositionedAt().after(executedAt)) {
|
|
7485
|
-
prevNode = node;
|
|
7486
|
-
node = nextNode;
|
|
7487
|
-
nextNode = node.getNext();
|
|
7488
|
-
this.release(node);
|
|
7489
|
-
node = this.insertAfter(
|
|
7490
|
-
prevNode.getCreatedAt(),
|
|
7491
|
-
node.getValue(),
|
|
7492
|
-
executedAt
|
|
7493
|
-
);
|
|
7494
|
-
node.getValue().setMovedAt(executedAt);
|
|
7495
|
-
node.setMovedFrom(movedFrom);
|
|
7626
|
+
if (entry.posMovedAt && !executedAt.after(entry.posMovedAt)) {
|
|
7627
|
+
if (this.nodeMapByCreatedAt.has(executedAt.toIDString())) {
|
|
7628
|
+
return void 0;
|
|
7496
7629
|
}
|
|
7630
|
+
const deadPosNode = this.insertPositionAfter(prevCreatedAt, executedAt);
|
|
7631
|
+
deadPosNode.setRemovedAt(executedAt);
|
|
7632
|
+
this.nodeMapByIndex.splayNode(deadPosNode);
|
|
7633
|
+
return deadPosNode;
|
|
7497
7634
|
}
|
|
7635
|
+
const newPosNode = this.insertPositionAfter(prevCreatedAt, executedAt);
|
|
7636
|
+
const oldPosNode = entry.positionNode;
|
|
7637
|
+
oldPosNode.setElementEntry(void 0);
|
|
7638
|
+
oldPosNode.setRemovedAt(executedAt);
|
|
7639
|
+
this.nodeMapByIndex.splayNode(oldPosNode);
|
|
7640
|
+
newPosNode.setElementEntry(entry);
|
|
7641
|
+
entry.positionNode = newPosNode;
|
|
7642
|
+
entry.posMovedAt = executedAt;
|
|
7643
|
+
entry.elem.setMovedAt(executedAt);
|
|
7644
|
+
this.nodeMapByIndex.splayNode(newPosNode);
|
|
7645
|
+
return oldPosNode;
|
|
7498
7646
|
}
|
|
7499
7647
|
/**
|
|
7500
7648
|
* `insert` adds the given element after the last node.
|
|
@@ -7503,34 +7651,53 @@ class RGATreeList {
|
|
|
7503
7651
|
this.insertAfter(this.last.getCreatedAt(), value);
|
|
7504
7652
|
}
|
|
7505
7653
|
/**
|
|
7506
|
-
* `getByID` returns the
|
|
7654
|
+
* `getByID` returns the node of the given creation time.
|
|
7655
|
+
* Checks elementMapByCreatedAt first (for moved elements whose
|
|
7656
|
+
* position node createdAt differs), then nodeMapByCreatedAt.
|
|
7507
7657
|
*/
|
|
7508
7658
|
getByID(createdAt) {
|
|
7659
|
+
const entry = this.elementMapByCreatedAt.get(createdAt.toIDString());
|
|
7660
|
+
if (entry) {
|
|
7661
|
+
return entry.positionNode;
|
|
7662
|
+
}
|
|
7509
7663
|
return this.nodeMapByCreatedAt.get(createdAt.toIDString());
|
|
7510
7664
|
}
|
|
7511
7665
|
/**
|
|
7512
7666
|
* `subPathOf` returns the sub path of the given element.
|
|
7513
7667
|
*/
|
|
7514
7668
|
subPathOf(createdAt) {
|
|
7515
|
-
const
|
|
7516
|
-
if (!
|
|
7517
|
-
|
|
7669
|
+
const entry = this.elementMapByCreatedAt.get(createdAt.toIDString());
|
|
7670
|
+
if (!entry) {
|
|
7671
|
+
const node = this.nodeMapByCreatedAt.get(createdAt.toIDString());
|
|
7672
|
+
if (!node) {
|
|
7673
|
+
return;
|
|
7674
|
+
}
|
|
7675
|
+
return String(this.nodeMapByIndex.indexOf(node));
|
|
7518
7676
|
}
|
|
7519
|
-
return String(this.nodeMapByIndex.indexOf(
|
|
7677
|
+
return String(this.nodeMapByIndex.indexOf(entry.positionNode));
|
|
7520
7678
|
}
|
|
7521
7679
|
/**
|
|
7522
|
-
* `purge` physically purges
|
|
7680
|
+
* `purge` physically purges the given child. Handles both dead
|
|
7681
|
+
* position nodes (GCChild from GCParent path) and CRDTElements
|
|
7682
|
+
* (from CRDTContainer path).
|
|
7523
7683
|
*/
|
|
7524
|
-
purge(
|
|
7525
|
-
|
|
7684
|
+
purge(child) {
|
|
7685
|
+
if (child instanceof RGATreeListNode) {
|
|
7686
|
+
this.release(child);
|
|
7687
|
+
return;
|
|
7688
|
+
}
|
|
7689
|
+
const element = child;
|
|
7690
|
+
const entry = this.elementMapByCreatedAt.get(
|
|
7526
7691
|
element.getCreatedAt().toIDString()
|
|
7527
7692
|
);
|
|
7528
|
-
if (!
|
|
7693
|
+
if (!entry) {
|
|
7529
7694
|
throw new YorkieError(
|
|
7530
7695
|
Code.ErrInvalidArgument,
|
|
7531
7696
|
`fail to find the given createdAt: ${element.getCreatedAt().toIDString()}`
|
|
7532
7697
|
);
|
|
7533
7698
|
}
|
|
7699
|
+
const node = entry.positionNode;
|
|
7700
|
+
this.elementMapByCreatedAt.delete(element.getCreatedAt().toIDString());
|
|
7534
7701
|
this.release(node);
|
|
7535
7702
|
}
|
|
7536
7703
|
/**
|
|
@@ -7541,42 +7708,69 @@ class RGATreeList {
|
|
|
7541
7708
|
return;
|
|
7542
7709
|
}
|
|
7543
7710
|
const node = this.nodeMapByIndex.findForArray(idx);
|
|
7544
|
-
|
|
7545
|
-
return rgaNode;
|
|
7711
|
+
return node;
|
|
7546
7712
|
}
|
|
7547
7713
|
/**
|
|
7548
|
-
* `
|
|
7714
|
+
* `findPrevCreatedAt` returns the position node's createdAt of the
|
|
7715
|
+
* previous element. This returns a position identity suitable for
|
|
7716
|
+
* use as prevCreatedAt in moveAfter.
|
|
7549
7717
|
*/
|
|
7550
|
-
|
|
7551
|
-
|
|
7718
|
+
findPrevCreatedAt(createdAt) {
|
|
7719
|
+
const entry = this.elementMapByCreatedAt.get(createdAt.toIDString());
|
|
7720
|
+
if (!entry) {
|
|
7721
|
+
throw new YorkieError(
|
|
7722
|
+
Code.ErrInvalidArgument,
|
|
7723
|
+
`cant find the given node: ${createdAt.toIDString()}`
|
|
7724
|
+
);
|
|
7725
|
+
}
|
|
7726
|
+
let node = entry.positionNode;
|
|
7552
7727
|
do {
|
|
7553
7728
|
node = node.getPrev();
|
|
7554
|
-
|
|
7555
|
-
|
|
7729
|
+
if (!node.getElementEntry()) {
|
|
7730
|
+
continue;
|
|
7731
|
+
}
|
|
7732
|
+
if (this.dummyHead === node || !node.isRemoved()) {
|
|
7733
|
+
break;
|
|
7734
|
+
}
|
|
7735
|
+
} while (node);
|
|
7736
|
+
return node.getPositionCreatedAt();
|
|
7737
|
+
}
|
|
7738
|
+
/**
|
|
7739
|
+
* `getPrevCreatedAt` returns the position node's createdAt of the
|
|
7740
|
+
* previous element. Delegates to findPrevCreatedAt.
|
|
7741
|
+
*/
|
|
7742
|
+
getPrevCreatedAt(createdAt) {
|
|
7743
|
+
return this.findPrevCreatedAt(createdAt);
|
|
7556
7744
|
}
|
|
7557
7745
|
/**
|
|
7558
7746
|
* `delete` deletes the node of the given creation time.
|
|
7559
7747
|
*/
|
|
7560
7748
|
delete(createdAt, editedAt) {
|
|
7561
|
-
const
|
|
7749
|
+
const entry = this.elementMapByCreatedAt.get(createdAt.toIDString());
|
|
7750
|
+
if (!entry) {
|
|
7751
|
+
throw new YorkieError(
|
|
7752
|
+
Code.ErrInvalidArgument,
|
|
7753
|
+
`cant find the given node: ${createdAt.toIDString()}`
|
|
7754
|
+
);
|
|
7755
|
+
}
|
|
7756
|
+
const node = entry.positionNode;
|
|
7562
7757
|
const alreadyRemoved = node.isRemoved();
|
|
7563
|
-
if (
|
|
7758
|
+
if (entry.elem.remove(editedAt) && !alreadyRemoved) {
|
|
7564
7759
|
this.nodeMapByIndex.splayNode(node);
|
|
7565
7760
|
}
|
|
7566
|
-
return
|
|
7761
|
+
return entry.elem;
|
|
7567
7762
|
}
|
|
7568
7763
|
/**
|
|
7569
7764
|
* `set` sets the given element at the given creation time.
|
|
7570
7765
|
*/
|
|
7571
7766
|
set(createdAt, element, executedAt) {
|
|
7572
|
-
|
|
7573
|
-
if (!node) {
|
|
7767
|
+
if (!this.elementMapByCreatedAt.has(createdAt.toIDString())) {
|
|
7574
7768
|
throw new YorkieError(
|
|
7575
7769
|
Code.ErrInvalidArgument,
|
|
7576
7770
|
`cant find the given node: ${createdAt.toIDString()}`
|
|
7577
7771
|
);
|
|
7578
7772
|
}
|
|
7579
|
-
this.insertAfter(
|
|
7773
|
+
this.insertAfter(createdAt, element, executedAt);
|
|
7580
7774
|
return this.delete(createdAt, executedAt);
|
|
7581
7775
|
}
|
|
7582
7776
|
/**
|
|
@@ -7605,18 +7799,80 @@ class RGATreeList {
|
|
|
7605
7799
|
return this.last.getValue();
|
|
7606
7800
|
}
|
|
7607
7801
|
/**
|
|
7608
|
-
* `getLastCreatedAt` returns the
|
|
7802
|
+
* `getLastCreatedAt` returns the position node's createdAt of the
|
|
7803
|
+
* last node in the linked list. This is a position identity
|
|
7804
|
+
* suitable for use as prevCreatedAt.
|
|
7609
7805
|
*/
|
|
7610
7806
|
getLastCreatedAt() {
|
|
7611
|
-
return this.last.
|
|
7807
|
+
return this.last.getPositionCreatedAt();
|
|
7612
7808
|
}
|
|
7613
7809
|
/**
|
|
7614
|
-
* `
|
|
7615
|
-
*
|
|
7810
|
+
* `posCreatedAt` returns the createdAt of the position node
|
|
7811
|
+
* currently holding the element. Used to convert element identity
|
|
7812
|
+
* to position identity.
|
|
7813
|
+
*/
|
|
7814
|
+
posCreatedAt(elemCreatedAt) {
|
|
7815
|
+
const entry = this.elementMapByCreatedAt.get(elemCreatedAt.toIDString());
|
|
7816
|
+
if (!entry) {
|
|
7817
|
+
throw new YorkieError(
|
|
7818
|
+
Code.ErrInvalidArgument,
|
|
7819
|
+
`cant find the given node: ${elemCreatedAt.toIDString()}`
|
|
7820
|
+
);
|
|
7821
|
+
}
|
|
7822
|
+
return entry.positionNode.getPositionCreatedAt();
|
|
7823
|
+
}
|
|
7824
|
+
/**
|
|
7825
|
+
* `addDeadPosition` appends a dead position node during snapshot
|
|
7826
|
+
* restoration.
|
|
7827
|
+
*/
|
|
7828
|
+
addDeadPosition(posCreatedAt, removedAt) {
|
|
7829
|
+
const node = RGATreeListNode.createBarePosition(posCreatedAt);
|
|
7830
|
+
node.setRemovedAt(removedAt);
|
|
7831
|
+
const prevNode = this.last;
|
|
7832
|
+
RGATreeListNode.insertNodeAfter(prevNode, node);
|
|
7833
|
+
this.last = node;
|
|
7834
|
+
this.nodeMapByIndex.insertAfter(prevNode, node);
|
|
7835
|
+
this.nodeMapByCreatedAt.set(posCreatedAt.toIDString(), node);
|
|
7836
|
+
}
|
|
7837
|
+
/**
|
|
7838
|
+
* `addMovedElement` appends an element with explicit position
|
|
7839
|
+
* identity during snapshot restoration.
|
|
7840
|
+
*/
|
|
7841
|
+
addMovedElement(elem, posCreatedAt, posMovedAt) {
|
|
7842
|
+
const entry = new ElementEntry(elem);
|
|
7843
|
+
entry.posMovedAt = posMovedAt;
|
|
7844
|
+
const node = RGATreeListNode.createBarePosition(posCreatedAt);
|
|
7845
|
+
node.setElementEntry(entry);
|
|
7846
|
+
entry.positionNode = node;
|
|
7847
|
+
const prevNode = this.last;
|
|
7848
|
+
RGATreeListNode.insertNodeAfter(prevNode, node);
|
|
7849
|
+
this.last = node;
|
|
7850
|
+
this.nodeMapByIndex.insertAfter(prevNode, node);
|
|
7851
|
+
this.nodeMapByCreatedAt.set(posCreatedAt.toIDString(), node);
|
|
7852
|
+
this.elementMapByCreatedAt.set(elem.getCreatedAt().toIDString(), entry);
|
|
7853
|
+
}
|
|
7854
|
+
/**
|
|
7855
|
+
* `allNodes` returns all nodes including dead position nodes.
|
|
7856
|
+
*/
|
|
7857
|
+
allNodes() {
|
|
7858
|
+
const nodes = [];
|
|
7859
|
+
let current = this.dummyHead.getNext();
|
|
7860
|
+
while (current) {
|
|
7861
|
+
nodes.push(current);
|
|
7862
|
+
current = current.getNext();
|
|
7863
|
+
}
|
|
7864
|
+
return nodes;
|
|
7865
|
+
}
|
|
7866
|
+
/**
|
|
7867
|
+
* `toTestString` returns a String containing the meta data of the
|
|
7868
|
+
* node id for debugging purpose.
|
|
7616
7869
|
*/
|
|
7617
7870
|
toTestString() {
|
|
7618
7871
|
const json = [];
|
|
7619
7872
|
for (const node of this) {
|
|
7873
|
+
if (!node.getElementEntry()) {
|
|
7874
|
+
continue;
|
|
7875
|
+
}
|
|
7620
7876
|
const elem = `${node.getCreatedAt().toIDString()}:${node.getValue().toJSON()}`;
|
|
7621
7877
|
if (node.isRemoved()) {
|
|
7622
7878
|
json.push(`{${elem}}`);
|
|
@@ -7673,10 +7929,11 @@ class CRDTArray extends CRDTContainer {
|
|
|
7673
7929
|
this.elements.insertAfter(prevCreatedAt, value, executedAt);
|
|
7674
7930
|
}
|
|
7675
7931
|
/**
|
|
7676
|
-
* `moveAfter` moves the given `createdAt` element after the
|
|
7932
|
+
* `moveAfter` moves the given `createdAt` element after the
|
|
7933
|
+
* `prevCreatedAt`. Returns the dead position node for GC.
|
|
7677
7934
|
*/
|
|
7678
7935
|
moveAfter(prevCreatedAt, createdAt, executedAt) {
|
|
7679
|
-
this.elements.moveAfter(prevCreatedAt, createdAt, executedAt);
|
|
7936
|
+
return this.elements.moveAfter(prevCreatedAt, createdAt, executedAt);
|
|
7680
7937
|
}
|
|
7681
7938
|
/**
|
|
7682
7939
|
* `get` returns the element of the given index.
|
|
@@ -7705,11 +7962,20 @@ class CRDTArray extends CRDTContainer {
|
|
|
7705
7962
|
return this.elements.getLast();
|
|
7706
7963
|
}
|
|
7707
7964
|
/**
|
|
7708
|
-
* `getPrevCreatedAt` returns the creation time of the previous
|
|
7965
|
+
* `getPrevCreatedAt` returns the creation time of the previous
|
|
7966
|
+
* node.
|
|
7709
7967
|
*/
|
|
7710
7968
|
getPrevCreatedAt(createdAt) {
|
|
7711
7969
|
return this.elements.getPrevCreatedAt(createdAt);
|
|
7712
7970
|
}
|
|
7971
|
+
/**
|
|
7972
|
+
* `posCreatedAt` returns the createdAt of the position node
|
|
7973
|
+
* currently holding the element. Used to convert element identity
|
|
7974
|
+
* to position identity for moves.
|
|
7975
|
+
*/
|
|
7976
|
+
posCreatedAt(elemCreatedAt) {
|
|
7977
|
+
return this.elements.posCreatedAt(elemCreatedAt);
|
|
7978
|
+
}
|
|
7713
7979
|
/**
|
|
7714
7980
|
* `delete` deletes the element of the given creation time.
|
|
7715
7981
|
*/
|
|
@@ -7723,7 +7989,8 @@ class CRDTArray extends CRDTContainer {
|
|
|
7723
7989
|
return this.elements.deleteByIndex(index, editedAt);
|
|
7724
7990
|
}
|
|
7725
7991
|
/**
|
|
7726
|
-
* `set` sets the given element at the given position of the
|
|
7992
|
+
* `set` sets the given element at the given position of the
|
|
7993
|
+
* creation time.
|
|
7727
7994
|
*/
|
|
7728
7995
|
set(createdAt, value, executedAt) {
|
|
7729
7996
|
return this.elements.set(createdAt, value, executedAt);
|
|
@@ -7741,18 +8008,19 @@ class CRDTArray extends CRDTContainer {
|
|
|
7741
8008
|
return this.elements.length;
|
|
7742
8009
|
}
|
|
7743
8010
|
/**
|
|
7744
|
-
* `[Symbol.iterator]` returns an iterator for the elements in
|
|
8011
|
+
* `[Symbol.iterator]` returns an iterator for the elements in
|
|
8012
|
+
* this array.
|
|
7745
8013
|
*/
|
|
7746
8014
|
*[Symbol.iterator]() {
|
|
7747
8015
|
for (const node of this.elements) {
|
|
7748
|
-
if (!node.isRemoved()) {
|
|
8016
|
+
if (node.getElementEntry() && !node.isRemoved()) {
|
|
7749
8017
|
yield node.getValue();
|
|
7750
8018
|
}
|
|
7751
8019
|
}
|
|
7752
8020
|
}
|
|
7753
8021
|
/**
|
|
7754
|
-
* `toTestString` returns a String containing the meta data of
|
|
7755
|
-
* for debugging purpose.
|
|
8022
|
+
* `toTestString` returns a String containing the meta data of
|
|
8023
|
+
* this value for debugging purpose.
|
|
7756
8024
|
*/
|
|
7757
8025
|
toTestString() {
|
|
7758
8026
|
return this.elements.toTestString();
|
|
@@ -7762,6 +8030,9 @@ class CRDTArray extends CRDTContainer {
|
|
|
7762
8030
|
*/
|
|
7763
8031
|
getDescendants(callback) {
|
|
7764
8032
|
for (const node of this.elements) {
|
|
8033
|
+
if (!node.getElementEntry()) {
|
|
8034
|
+
continue;
|
|
8035
|
+
}
|
|
7765
8036
|
const element = node.getValue();
|
|
7766
8037
|
if (callback(element, this)) {
|
|
7767
8038
|
return;
|
|
@@ -7823,21 +8094,52 @@ class CRDTArray extends CRDTContainer {
|
|
|
7823
8094
|
return this.toJSON();
|
|
7824
8095
|
}
|
|
7825
8096
|
/**
|
|
7826
|
-
* `getElements` returns
|
|
8097
|
+
* `getElements` returns the underlying RGATreeList.
|
|
7827
8098
|
*/
|
|
7828
8099
|
getElements() {
|
|
7829
8100
|
return this.elements;
|
|
7830
8101
|
}
|
|
8102
|
+
/**
|
|
8103
|
+
* `getRGATreeList` returns the underlying RGATreeList (GCParent
|
|
8104
|
+
* for dead positions).
|
|
8105
|
+
*/
|
|
8106
|
+
getRGATreeList() {
|
|
8107
|
+
return this.elements;
|
|
8108
|
+
}
|
|
8109
|
+
/**
|
|
8110
|
+
* `getAllRGANodes` returns all RGA nodes including dead position
|
|
8111
|
+
* nodes.
|
|
8112
|
+
*/
|
|
8113
|
+
getAllRGANodes() {
|
|
8114
|
+
return this.elements.allNodes();
|
|
8115
|
+
}
|
|
7831
8116
|
/**
|
|
7832
8117
|
* `deepcopy` copies itself deeply.
|
|
7833
8118
|
*/
|
|
7834
8119
|
deepcopy() {
|
|
7835
8120
|
const clone = CRDTArray.create(this.getCreatedAt());
|
|
7836
8121
|
for (const node of this.elements) {
|
|
7837
|
-
|
|
7838
|
-
|
|
7839
|
-
|
|
7840
|
-
|
|
8122
|
+
if (!node.getElementEntry()) {
|
|
8123
|
+
const removedAt = node.getRemovedAt();
|
|
8124
|
+
if (removedAt) {
|
|
8125
|
+
clone.elements.addDeadPosition(
|
|
8126
|
+
node.getPositionCreatedAt(),
|
|
8127
|
+
removedAt
|
|
8128
|
+
);
|
|
8129
|
+
}
|
|
8130
|
+
continue;
|
|
8131
|
+
}
|
|
8132
|
+
const value = node.getValue().deepcopy();
|
|
8133
|
+
const posMovedAt = node.getPositionMovedAt();
|
|
8134
|
+
if (posMovedAt) {
|
|
8135
|
+
clone.elements.addMovedElement(
|
|
8136
|
+
value,
|
|
8137
|
+
node.getPositionCreatedAt(),
|
|
8138
|
+
posMovedAt
|
|
8139
|
+
);
|
|
8140
|
+
} else {
|
|
8141
|
+
clone.elements.insertAfter(clone.getLastCreatedAt(), value);
|
|
8142
|
+
}
|
|
7841
8143
|
}
|
|
7842
8144
|
clone.setRemovedAt(this.getRemovedAt());
|
|
7843
8145
|
clone.setMovedAt(this.getMovedAt());
|
|
@@ -8094,6 +8396,9 @@ class SetOperation extends Operation {
|
|
|
8094
8396
|
if (removed) {
|
|
8095
8397
|
root.registerRemovedElement(removed);
|
|
8096
8398
|
}
|
|
8399
|
+
if (value.getRemovedAt()) {
|
|
8400
|
+
root.registerRemovedElement(value);
|
|
8401
|
+
}
|
|
8097
8402
|
return {
|
|
8098
8403
|
opInfos: [
|
|
8099
8404
|
{
|
|
@@ -8186,7 +8491,17 @@ class MoveOperation extends Operation {
|
|
|
8186
8491
|
const array = parentObject;
|
|
8187
8492
|
const reverseOp = this.toReverseOperation(array);
|
|
8188
8493
|
const previousIndex = Number(array.subPathOf(this.createdAt));
|
|
8189
|
-
array.moveAfter(
|
|
8494
|
+
const deadNode = array.moveAfter(
|
|
8495
|
+
this.prevCreatedAt,
|
|
8496
|
+
this.createdAt,
|
|
8497
|
+
this.getExecutedAt()
|
|
8498
|
+
);
|
|
8499
|
+
if (deadNode) {
|
|
8500
|
+
root.registerGCPair({
|
|
8501
|
+
parent: array.getRGATreeList(),
|
|
8502
|
+
child: deadNode
|
|
8503
|
+
});
|
|
8504
|
+
}
|
|
8190
8505
|
const index = Number(array.subPathOf(this.createdAt));
|
|
8191
8506
|
return {
|
|
8192
8507
|
opInfos: [
|
|
@@ -8209,7 +8524,8 @@ class MoveOperation extends Operation {
|
|
|
8209
8524
|
);
|
|
8210
8525
|
}
|
|
8211
8526
|
/**
|
|
8212
|
-
* `getEffectedCreatedAt` returns the creation time of the
|
|
8527
|
+
* `getEffectedCreatedAt` returns the creation time of the
|
|
8528
|
+
* effected element.
|
|
8213
8529
|
*/
|
|
8214
8530
|
getEffectedCreatedAt() {
|
|
8215
8531
|
return this.createdAt;
|
|
@@ -8221,7 +8537,8 @@ class MoveOperation extends Operation {
|
|
|
8221
8537
|
return `${this.getParentCreatedAt().toTestString()}.MOVE`;
|
|
8222
8538
|
}
|
|
8223
8539
|
/**
|
|
8224
|
-
* `getPrevCreatedAt` returns the creation time of previous
|
|
8540
|
+
* `getPrevCreatedAt` returns the creation time of previous
|
|
8541
|
+
* element.
|
|
8225
8542
|
*/
|
|
8226
8543
|
getPrevCreatedAt() {
|
|
8227
8544
|
return this.prevCreatedAt;
|
|
@@ -8233,7 +8550,8 @@ class MoveOperation extends Operation {
|
|
|
8233
8550
|
return this.createdAt;
|
|
8234
8551
|
}
|
|
8235
8552
|
/**
|
|
8236
|
-
* `setPrevCreatedAt` sets the creation time of the previous
|
|
8553
|
+
* `setPrevCreatedAt` sets the creation time of the previous
|
|
8554
|
+
* element.
|
|
8237
8555
|
*/
|
|
8238
8556
|
setPrevCreatedAt(createdAt) {
|
|
8239
8557
|
this.prevCreatedAt = createdAt;
|
|
@@ -10814,6 +11132,32 @@ class IndexTreeNode {
|
|
|
10814
11132
|
}
|
|
10815
11133
|
actualRight.push(child);
|
|
10816
11134
|
}
|
|
11135
|
+
if (versionVector) {
|
|
11136
|
+
const movedToLeft = [];
|
|
11137
|
+
const remaining = [];
|
|
11138
|
+
let boundaryReached = false;
|
|
11139
|
+
for (const child of actualRight) {
|
|
11140
|
+
if (!boundaryReached) {
|
|
11141
|
+
if (child.insPrevID !== void 0 && !child.isText) {
|
|
11142
|
+
remaining.push(child);
|
|
11143
|
+
continue;
|
|
11144
|
+
}
|
|
11145
|
+
const actorID = child.id.getCreatedAt().getActorID();
|
|
11146
|
+
const knownLamport = versionVector.get(actorID);
|
|
11147
|
+
if (knownLamport === void 0 || knownLamport < child.id.getCreatedAt().getLamport()) {
|
|
11148
|
+
movedToLeft.push(child);
|
|
11149
|
+
continue;
|
|
11150
|
+
}
|
|
11151
|
+
}
|
|
11152
|
+
boundaryReached = true;
|
|
11153
|
+
remaining.push(child);
|
|
11154
|
+
}
|
|
11155
|
+
if (movedToLeft.length > 0) {
|
|
11156
|
+
left.push(...movedToLeft);
|
|
11157
|
+
actualRight.length = 0;
|
|
11158
|
+
actualRight.push(...remaining);
|
|
11159
|
+
}
|
|
11160
|
+
}
|
|
10817
11161
|
this._children = left;
|
|
10818
11162
|
clone._children = actualRight;
|
|
10819
11163
|
this.visibleSize = this._children.reduce(
|
|
@@ -11577,7 +11921,7 @@ class CRDTTreeNode extends IndexTreeNode {
|
|
|
11577
11921
|
CRDTTreeNodeID.of(issueTimeTicket(), 0),
|
|
11578
11922
|
this.type,
|
|
11579
11923
|
void 0,
|
|
11580
|
-
|
|
11924
|
+
this.attrs?.deepcopy(),
|
|
11581
11925
|
this.removedAt
|
|
11582
11926
|
);
|
|
11583
11927
|
}
|
|
@@ -11590,8 +11934,14 @@ class CRDTTreeNode extends IndexTreeNode {
|
|
|
11590
11934
|
split.insPrevID = this.id;
|
|
11591
11935
|
if (this.insNextID) {
|
|
11592
11936
|
const insNext = tree.findFloorNode(this.insNextID);
|
|
11593
|
-
insNext.insPrevID = split.id;
|
|
11594
11937
|
split.insNextID = this.insNextID;
|
|
11938
|
+
if (insNext) {
|
|
11939
|
+
insNext.insPrevID = split.id;
|
|
11940
|
+
if (!this.isText && insNext.parent && !insNext.isRemoved && insNext.parent !== split.parent && split.allChildren.length === 0) {
|
|
11941
|
+
split.parent.detachChild(split);
|
|
11942
|
+
insNext.parent.insertBefore(split, insNext);
|
|
11943
|
+
}
|
|
11944
|
+
}
|
|
11595
11945
|
}
|
|
11596
11946
|
this.insNextID = split.id;
|
|
11597
11947
|
tree.registerNode(split);
|
|
@@ -11815,7 +12165,7 @@ class CRDTTree extends CRDTElement {
|
|
|
11815
12165
|
* given node, advancing past element-type split siblings that the editing
|
|
11816
12166
|
* client did not know about (not in versionVector).
|
|
11817
12167
|
*/
|
|
11818
|
-
advancePastUnknownSplitSiblings(node, versionVector) {
|
|
12168
|
+
advancePastUnknownSplitSiblings(node, versionVector, relaxParentCheck = false, skipActorID) {
|
|
11819
12169
|
if (!versionVector || !node) {
|
|
11820
12170
|
return node;
|
|
11821
12171
|
}
|
|
@@ -11825,10 +12175,13 @@ class CRDTTree extends CRDTElement {
|
|
|
11825
12175
|
if (!next || next.isText) {
|
|
11826
12176
|
break;
|
|
11827
12177
|
}
|
|
11828
|
-
if (next.parent !== current.parent) {
|
|
12178
|
+
if (!relaxParentCheck && next.parent !== current.parent) {
|
|
11829
12179
|
break;
|
|
11830
12180
|
}
|
|
11831
12181
|
const actorID = next.id.getCreatedAt().getActorID();
|
|
12182
|
+
if (skipActorID !== void 0 && actorID === skipActorID) {
|
|
12183
|
+
break;
|
|
12184
|
+
}
|
|
11832
12185
|
const knownLamport = versionVector.get(actorID);
|
|
11833
12186
|
if (knownLamport !== void 0 && knownLamport >= next.id.getCreatedAt().getLamport()) {
|
|
11834
12187
|
break;
|
|
@@ -11997,6 +12350,53 @@ class CRDTTree extends CRDTElement {
|
|
|
11997
12350
|
addDataSizes(diff, curr.getDataSize());
|
|
11998
12351
|
}
|
|
11999
12352
|
}
|
|
12353
|
+
if (tokenType === TokenType.Start && versionVector !== void 0) {
|
|
12354
|
+
let current = node;
|
|
12355
|
+
while (current.insNextID) {
|
|
12356
|
+
const next = this.findFloorNode(current.insNextID);
|
|
12357
|
+
if (!next || next.isText) {
|
|
12358
|
+
break;
|
|
12359
|
+
}
|
|
12360
|
+
if (ticketKnown(versionVector, next.id.getCreatedAt())) {
|
|
12361
|
+
break;
|
|
12362
|
+
}
|
|
12363
|
+
const siblingPairs = next.setAttrs(attributes, editedAt);
|
|
12364
|
+
const siblingAffectedAttrs = siblingPairs.reduce(
|
|
12365
|
+
(acc, [, curr]) => {
|
|
12366
|
+
if (curr) {
|
|
12367
|
+
acc[curr.getKey()] = attrs[curr.getKey()];
|
|
12368
|
+
}
|
|
12369
|
+
return acc;
|
|
12370
|
+
},
|
|
12371
|
+
{}
|
|
12372
|
+
);
|
|
12373
|
+
if (Object.keys(siblingAffectedAttrs).length > 0) {
|
|
12374
|
+
const parentOfNext = next.parent;
|
|
12375
|
+
const previousNext = next.prevSibling || parentOfNext;
|
|
12376
|
+
changes.push({
|
|
12377
|
+
type: "style",
|
|
12378
|
+
from: this.toIndex(parentOfNext, previousNext),
|
|
12379
|
+
to: this.toIndex(next, next),
|
|
12380
|
+
fromPath: this.toPath(parentOfNext, previousNext),
|
|
12381
|
+
toPath: this.toPath(next, next),
|
|
12382
|
+
actor: editedAt.getActorID(),
|
|
12383
|
+
value: siblingAffectedAttrs
|
|
12384
|
+
});
|
|
12385
|
+
}
|
|
12386
|
+
for (const [prev] of siblingPairs) {
|
|
12387
|
+
if (prev) {
|
|
12388
|
+
pairs.push({ parent: next, child: prev });
|
|
12389
|
+
}
|
|
12390
|
+
}
|
|
12391
|
+
for (const [key] of Object.entries(attrs)) {
|
|
12392
|
+
const curr = next.attrs?.getNodeMapByKey().get(key);
|
|
12393
|
+
if (curr !== void 0) {
|
|
12394
|
+
addDataSizes(diff, curr.getDataSize());
|
|
12395
|
+
}
|
|
12396
|
+
}
|
|
12397
|
+
current = next;
|
|
12398
|
+
}
|
|
12399
|
+
}
|
|
12000
12400
|
}
|
|
12001
12401
|
}
|
|
12002
12402
|
);
|
|
@@ -12063,6 +12463,43 @@ class CRDTTree extends CRDTElement {
|
|
|
12063
12463
|
toPath: this.toPath(node, node),
|
|
12064
12464
|
value: attributesToRemove
|
|
12065
12465
|
});
|
|
12466
|
+
if (tokenType === TokenType.Start && versionVector !== void 0) {
|
|
12467
|
+
let current = node;
|
|
12468
|
+
while (current.insNextID) {
|
|
12469
|
+
const next = this.findFloorNode(current.insNextID);
|
|
12470
|
+
if (!next || next.isText) {
|
|
12471
|
+
break;
|
|
12472
|
+
}
|
|
12473
|
+
if (ticketKnown(versionVector, next.id.getCreatedAt())) {
|
|
12474
|
+
break;
|
|
12475
|
+
}
|
|
12476
|
+
if (!next.attrs) {
|
|
12477
|
+
next.attrs = new RHT();
|
|
12478
|
+
}
|
|
12479
|
+
let removedAny = false;
|
|
12480
|
+
for (const value of attributesToRemove) {
|
|
12481
|
+
const nodesTobeRemoved = next.attrs.remove(value, editedAt);
|
|
12482
|
+
removedAny = removedAny || nodesTobeRemoved.length > 0;
|
|
12483
|
+
for (const rhtNode of nodesTobeRemoved) {
|
|
12484
|
+
pairs.push({ parent: next, child: rhtNode });
|
|
12485
|
+
}
|
|
12486
|
+
}
|
|
12487
|
+
if (removedAny) {
|
|
12488
|
+
const parentOfNext = next.parent;
|
|
12489
|
+
const previousNext = next.prevSibling || parentOfNext;
|
|
12490
|
+
changes.push({
|
|
12491
|
+
actor: editedAt.getActorID(),
|
|
12492
|
+
type: "removeStyle",
|
|
12493
|
+
from: this.toIndex(parentOfNext, previousNext),
|
|
12494
|
+
to: this.toIndex(next, next),
|
|
12495
|
+
fromPath: this.toPath(parentOfNext, previousNext),
|
|
12496
|
+
toPath: this.toPath(next, next),
|
|
12497
|
+
value: attributesToRemove
|
|
12498
|
+
});
|
|
12499
|
+
}
|
|
12500
|
+
current = next;
|
|
12501
|
+
}
|
|
12502
|
+
}
|
|
12066
12503
|
}
|
|
12067
12504
|
}
|
|
12068
12505
|
);
|
|
@@ -12085,6 +12522,23 @@ class CRDTTree extends CRDTElement {
|
|
|
12085
12522
|
addDataSizes(diff, diffTo, diffFrom);
|
|
12086
12523
|
const fromLeft = fromLeftRaw !== fromParent ? this.advancePastUnknownSplitSiblings(fromLeftRaw, versionVector) : fromLeftRaw;
|
|
12087
12524
|
const toLeft = toLeftRaw !== toParent ? this.advancePastUnknownSplitSiblings(toLeftRaw, versionVector) : toLeftRaw;
|
|
12525
|
+
let collectFromParent = fromParent;
|
|
12526
|
+
let collectFromLeft = fromLeft;
|
|
12527
|
+
if (fromLeft !== fromParent && fromParent !== toParent) {
|
|
12528
|
+
let current = fromLeft;
|
|
12529
|
+
while (current.insNextID) {
|
|
12530
|
+
const next = this.findFloorNode(current.insNextID);
|
|
12531
|
+
if (!next || next.isText) {
|
|
12532
|
+
break;
|
|
12533
|
+
}
|
|
12534
|
+
if (next.parent && next.parent === toParent) {
|
|
12535
|
+
collectFromLeft = next;
|
|
12536
|
+
collectFromParent = toParent;
|
|
12537
|
+
break;
|
|
12538
|
+
}
|
|
12539
|
+
current = next;
|
|
12540
|
+
}
|
|
12541
|
+
}
|
|
12088
12542
|
const fromIdx = this.toIndex(fromParent, fromLeft);
|
|
12089
12543
|
const fromPath = this.toPath(fromParent, fromLeft);
|
|
12090
12544
|
const nodesToBeRemoved = [];
|
|
@@ -12093,8 +12547,8 @@ class CRDTTree extends CRDTElement {
|
|
|
12093
12547
|
const toBeMergedNodes = [];
|
|
12094
12548
|
const preTombstoned = /* @__PURE__ */ new Set();
|
|
12095
12549
|
this.traverseInPosRange(
|
|
12096
|
-
|
|
12097
|
-
|
|
12550
|
+
collectFromParent,
|
|
12551
|
+
collectFromLeft,
|
|
12098
12552
|
toParent,
|
|
12099
12553
|
toLeft,
|
|
12100
12554
|
([node, tokenType], ended) => {
|
|
@@ -12198,9 +12652,20 @@ class CRDTTree extends CRDTElement {
|
|
|
12198
12652
|
let parent = fromParent;
|
|
12199
12653
|
let left = fromLeft;
|
|
12200
12654
|
while (splitCount < splitLevel) {
|
|
12655
|
+
if (left !== parent) {
|
|
12656
|
+
left = this.advancePastUnknownSplitSiblings(
|
|
12657
|
+
left,
|
|
12658
|
+
versionVector,
|
|
12659
|
+
true,
|
|
12660
|
+
editedAt.getActorID()
|
|
12661
|
+
);
|
|
12662
|
+
if (left.parent && left.parent !== parent) {
|
|
12663
|
+
parent = left.parent;
|
|
12664
|
+
}
|
|
12665
|
+
}
|
|
12201
12666
|
parent.split(
|
|
12202
12667
|
this,
|
|
12203
|
-
parent.findOffset(left, true) + 1,
|
|
12668
|
+
left !== parent ? parent.findOffset(left, true) + 1 : 0,
|
|
12204
12669
|
issueTimeTicket,
|
|
12205
12670
|
versionVector
|
|
12206
12671
|
);
|
|
@@ -12807,10 +13272,10 @@ class TreeEditOperation extends Operation {
|
|
|
12807
13272
|
);
|
|
12808
13273
|
this.lastToIdx = preEditFromIdx + removedSize;
|
|
12809
13274
|
let reverseOp;
|
|
12810
|
-
const
|
|
13275
|
+
const isPureSplit = this.splitLevel > 0 && !this.contents?.length && removedNodes.length === 0;
|
|
12811
13276
|
if (this.splitLevel === 0) {
|
|
12812
13277
|
reverseOp = this.toReverseOperation(tree, removedNodes, preEditFromIdx);
|
|
12813
|
-
} else if (
|
|
13278
|
+
} else if (isPureSplit) {
|
|
12814
13279
|
reverseOp = this.toSplitReverseOperation(tree, preEditFromIdx);
|
|
12815
13280
|
}
|
|
12816
13281
|
root.acc(diff);
|
|
@@ -14821,14 +15286,26 @@ function toRHTNodes(rht) {
|
|
|
14821
15286
|
}
|
|
14822
15287
|
return pbRHTNodes;
|
|
14823
15288
|
}
|
|
14824
|
-
function toRGANodes(
|
|
15289
|
+
function toRGANodes(arr) {
|
|
14825
15290
|
const pbRGANodes = [];
|
|
14826
|
-
for (const
|
|
14827
|
-
|
|
14828
|
-
|
|
14829
|
-
|
|
14830
|
-
|
|
14831
|
-
|
|
15291
|
+
for (const rgaNode of arr.getAllRGANodes()) {
|
|
15292
|
+
if (!rgaNode.getElementEntry()) {
|
|
15293
|
+
pbRGANodes.push(
|
|
15294
|
+
create(RGANodeSchema, {
|
|
15295
|
+
positionCreatedAt: toTimeTicket(rgaNode.getPositionCreatedAt()),
|
|
15296
|
+
positionRemovedAt: toTimeTicket(rgaNode.getRemovedAt())
|
|
15297
|
+
})
|
|
15298
|
+
);
|
|
15299
|
+
continue;
|
|
15300
|
+
}
|
|
15301
|
+
const pbNode = create(RGANodeSchema, {
|
|
15302
|
+
element: toElement(rgaNode.getValue())
|
|
15303
|
+
});
|
|
15304
|
+
if (rgaNode.getPositionMovedAt()) {
|
|
15305
|
+
pbNode.positionMovedAt = toTimeTicket(rgaNode.getPositionMovedAt());
|
|
15306
|
+
pbNode.positionCreatedAt = toTimeTicket(rgaNode.getPositionCreatedAt());
|
|
15307
|
+
}
|
|
15308
|
+
pbRGANodes.push(pbNode);
|
|
14832
15309
|
}
|
|
14833
15310
|
return pbRGANodes;
|
|
14834
15311
|
}
|
|
@@ -14928,7 +15405,7 @@ function toArray(arr) {
|
|
|
14928
15405
|
body: {
|
|
14929
15406
|
case: "jsonArray",
|
|
14930
15407
|
value: create(JSONElement_JSONArraySchema, {
|
|
14931
|
-
nodes: toRGANodes(arr
|
|
15408
|
+
nodes: toRGANodes(arr),
|
|
14932
15409
|
createdAt: toTimeTicket(arr.getCreatedAt()),
|
|
14933
15410
|
movedAt: toTimeTicket(arr.getMovedAt()),
|
|
14934
15411
|
removedAt: toTimeTicket(arr.getRemovedAt())
|
|
@@ -15466,7 +15943,32 @@ function fromObject(pbObject) {
|
|
|
15466
15943
|
function fromArray(pbArray) {
|
|
15467
15944
|
const rgaTreeList = new RGATreeList();
|
|
15468
15945
|
for (const pbRGANode of pbArray.nodes) {
|
|
15469
|
-
|
|
15946
|
+
if (!pbRGANode.element) {
|
|
15947
|
+
if (!pbRGANode.positionCreatedAt || !pbRGANode.positionRemovedAt) {
|
|
15948
|
+
throw new YorkieError(
|
|
15949
|
+
Code.ErrInvalidArgument,
|
|
15950
|
+
"dead RGA position node missing position timestamps"
|
|
15951
|
+
);
|
|
15952
|
+
}
|
|
15953
|
+
const posCreatedAt = fromTimeTicket(pbRGANode.positionCreatedAt);
|
|
15954
|
+
const posRemovedAt = fromTimeTicket(pbRGANode.positionRemovedAt);
|
|
15955
|
+
rgaTreeList.addDeadPosition(posCreatedAt, posRemovedAt);
|
|
15956
|
+
continue;
|
|
15957
|
+
}
|
|
15958
|
+
const elem = fromElement(pbRGANode.element);
|
|
15959
|
+
const posMovedAt = fromTimeTicket(pbRGANode.positionMovedAt);
|
|
15960
|
+
if (posMovedAt) {
|
|
15961
|
+
if (!pbRGANode.positionCreatedAt) {
|
|
15962
|
+
throw new YorkieError(
|
|
15963
|
+
Code.ErrInvalidArgument,
|
|
15964
|
+
"moved RGA node missing position_created_at"
|
|
15965
|
+
);
|
|
15966
|
+
}
|
|
15967
|
+
const posCreatedAt = fromTimeTicket(pbRGANode.positionCreatedAt);
|
|
15968
|
+
rgaTreeList.addMovedElement(elem, posCreatedAt, posMovedAt);
|
|
15969
|
+
} else {
|
|
15970
|
+
rgaTreeList.insert(elem);
|
|
15971
|
+
}
|
|
15470
15972
|
}
|
|
15471
15973
|
const arr = new CRDTArray(fromTimeTicket(pbArray.createdAt), rgaTreeList);
|
|
15472
15974
|
arr.setMovedAt(fromTimeTicket(pbArray.movedAt));
|
|
@@ -16254,10 +16756,16 @@ class ArrayProxy {
|
|
|
16254
16756
|
};
|
|
16255
16757
|
} else if (method === "insertAfter") {
|
|
16256
16758
|
return (prevID, value) => {
|
|
16759
|
+
let posCreatedAt;
|
|
16760
|
+
try {
|
|
16761
|
+
posCreatedAt = target.posCreatedAt(prevID);
|
|
16762
|
+
} catch {
|
|
16763
|
+
posCreatedAt = prevID;
|
|
16764
|
+
}
|
|
16257
16765
|
const inserted = ArrayProxy.insertAfterInternal(
|
|
16258
16766
|
context,
|
|
16259
16767
|
target,
|
|
16260
|
-
|
|
16768
|
+
posCreatedAt,
|
|
16261
16769
|
value
|
|
16262
16770
|
);
|
|
16263
16771
|
return toWrappedElement(context, inserted);
|
|
@@ -16442,7 +16950,7 @@ class ArrayProxy {
|
|
|
16442
16950
|
static moveBeforeInternal(context, target, nextCreatedAt, createdAt) {
|
|
16443
16951
|
const ticket = context.issueTimeTicket();
|
|
16444
16952
|
const prevCreatedAt = target.getPrevCreatedAt(nextCreatedAt);
|
|
16445
|
-
target.moveAfter(prevCreatedAt, createdAt, ticket);
|
|
16953
|
+
const deadNode = target.moveAfter(prevCreatedAt, createdAt, ticket);
|
|
16446
16954
|
context.push(
|
|
16447
16955
|
MoveOperation.create(
|
|
16448
16956
|
target.getCreatedAt(),
|
|
@@ -16451,26 +16959,45 @@ class ArrayProxy {
|
|
|
16451
16959
|
ticket
|
|
16452
16960
|
)
|
|
16453
16961
|
);
|
|
16962
|
+
if (deadNode) {
|
|
16963
|
+
context.registerGCPair({
|
|
16964
|
+
parent: target.getRGATreeList(),
|
|
16965
|
+
child: deadNode
|
|
16966
|
+
});
|
|
16967
|
+
}
|
|
16454
16968
|
}
|
|
16455
16969
|
/**
|
|
16456
16970
|
* `moveAfterInternal` moves the given `createdAt` element
|
|
16457
|
-
* after the specific element.
|
|
16971
|
+
* after the specific element. Converts element identity to
|
|
16972
|
+
* position identity for the prevCreatedAt.
|
|
16458
16973
|
*/
|
|
16459
16974
|
static moveAfterInternal(context, target, prevCreatedAt, createdAt) {
|
|
16460
16975
|
const ticket = context.issueTimeTicket();
|
|
16976
|
+
let posCreatedAt;
|
|
16977
|
+
try {
|
|
16978
|
+
posCreatedAt = target.posCreatedAt(prevCreatedAt);
|
|
16979
|
+
} catch {
|
|
16980
|
+
posCreatedAt = prevCreatedAt;
|
|
16981
|
+
}
|
|
16982
|
+
const deadNode = target.moveAfter(posCreatedAt, createdAt, ticket);
|
|
16461
16983
|
context.push(
|
|
16462
16984
|
MoveOperation.create(
|
|
16463
16985
|
target.getCreatedAt(),
|
|
16464
|
-
|
|
16986
|
+
posCreatedAt,
|
|
16465
16987
|
createdAt,
|
|
16466
16988
|
ticket
|
|
16467
16989
|
)
|
|
16468
16990
|
);
|
|
16469
|
-
|
|
16991
|
+
if (deadNode) {
|
|
16992
|
+
context.registerGCPair({
|
|
16993
|
+
parent: target.getRGATreeList(),
|
|
16994
|
+
child: deadNode
|
|
16995
|
+
});
|
|
16996
|
+
}
|
|
16470
16997
|
}
|
|
16471
16998
|
/**
|
|
16472
|
-
* `moveAfterByIndexInternal` moves the given element to its new
|
|
16473
|
-
* after the given previous element.
|
|
16999
|
+
* `moveAfterByIndexInternal` moves the given element to its new
|
|
17000
|
+
* position after the given previous element.
|
|
16474
17001
|
*/
|
|
16475
17002
|
static moveAfterByIndexInternal(context, target, prevIndex, targetIndex) {
|
|
16476
17003
|
const prevElem = target.get(prevIndex);
|
|
@@ -16501,7 +17028,7 @@ class ArrayProxy {
|
|
|
16501
17028
|
static moveFrontInternal(context, target, createdAt) {
|
|
16502
17029
|
const ticket = context.issueTimeTicket();
|
|
16503
17030
|
const head = target.getHead();
|
|
16504
|
-
target.moveAfter(head.getCreatedAt(), createdAt, ticket);
|
|
17031
|
+
const deadNode = target.moveAfter(head.getCreatedAt(), createdAt, ticket);
|
|
16505
17032
|
context.push(
|
|
16506
17033
|
MoveOperation.create(
|
|
16507
17034
|
target.getCreatedAt(),
|
|
@@ -16510,6 +17037,12 @@ class ArrayProxy {
|
|
|
16510
17037
|
ticket
|
|
16511
17038
|
)
|
|
16512
17039
|
);
|
|
17040
|
+
if (deadNode) {
|
|
17041
|
+
context.registerGCPair({
|
|
17042
|
+
parent: target.getRGATreeList(),
|
|
17043
|
+
child: deadNode
|
|
17044
|
+
});
|
|
17045
|
+
}
|
|
16513
17046
|
}
|
|
16514
17047
|
/**
|
|
16515
17048
|
* `moveLastInternal` moves the given `createdAt` element
|
|
@@ -16518,13 +17051,20 @@ class ArrayProxy {
|
|
|
16518
17051
|
static moveLastInternal(context, target, createdAt) {
|
|
16519
17052
|
const ticket = context.issueTimeTicket();
|
|
16520
17053
|
const last = target.getLastCreatedAt();
|
|
16521
|
-
target.moveAfter(last, createdAt, ticket);
|
|
17054
|
+
const deadNode = target.moveAfter(last, createdAt, ticket);
|
|
16522
17055
|
context.push(
|
|
16523
17056
|
MoveOperation.create(target.getCreatedAt(), last, createdAt, ticket)
|
|
16524
17057
|
);
|
|
17058
|
+
if (deadNode) {
|
|
17059
|
+
context.registerGCPair({
|
|
17060
|
+
parent: target.getRGATreeList(),
|
|
17061
|
+
child: deadNode
|
|
17062
|
+
});
|
|
17063
|
+
}
|
|
16525
17064
|
}
|
|
16526
17065
|
/**
|
|
16527
|
-
* `insertAfterInternal` inserts the value after the previously
|
|
17066
|
+
* `insertAfterInternal` inserts the value after the previously
|
|
17067
|
+
* created element.
|
|
16528
17068
|
*/
|
|
16529
17069
|
static insertAfterInternal(context, target, prevCreatedAt, value) {
|
|
16530
17070
|
const createdAt = context.issueTimeTicket();
|
|
@@ -16552,12 +17092,13 @@ class ArrayProxy {
|
|
|
16552
17092
|
`index out of bounds: ${index}`
|
|
16553
17093
|
);
|
|
16554
17094
|
}
|
|
16555
|
-
|
|
16556
|
-
|
|
16557
|
-
target
|
|
16558
|
-
|
|
16559
|
-
|
|
16560
|
-
|
|
17095
|
+
let posCreatedAt;
|
|
17096
|
+
try {
|
|
17097
|
+
posCreatedAt = target.posCreatedAt(prevElem.getCreatedAt());
|
|
17098
|
+
} catch {
|
|
17099
|
+
posCreatedAt = prevElem.getCreatedAt();
|
|
17100
|
+
}
|
|
17101
|
+
ArrayProxy.insertAfterInternal(context, target, posCreatedAt, value);
|
|
16561
17102
|
return target;
|
|
16562
17103
|
}
|
|
16563
17104
|
/**
|
|
@@ -16656,7 +17197,17 @@ class ArrayProxy {
|
|
|
16656
17197
|
}
|
|
16657
17198
|
}
|
|
16658
17199
|
if (items) {
|
|
16659
|
-
let previousID
|
|
17200
|
+
let previousID;
|
|
17201
|
+
if (from === 0) {
|
|
17202
|
+
previousID = target.getHead().getID();
|
|
17203
|
+
} else {
|
|
17204
|
+
const elemID = target.get(from - 1).getID();
|
|
17205
|
+
try {
|
|
17206
|
+
previousID = target.posCreatedAt(elemID);
|
|
17207
|
+
} catch {
|
|
17208
|
+
previousID = elemID;
|
|
17209
|
+
}
|
|
17210
|
+
}
|
|
16660
17211
|
for (const item of items) {
|
|
16661
17212
|
const newElem = ArrayProxy.insertAfterInternal(
|
|
16662
17213
|
context,
|
|
@@ -18006,6 +18557,16 @@ class CRDTRoot {
|
|
|
18006
18557
|
this.registerGCPair(pair);
|
|
18007
18558
|
}
|
|
18008
18559
|
}
|
|
18560
|
+
if (elem instanceof CRDTArray) {
|
|
18561
|
+
for (const node of elem.getAllRGANodes()) {
|
|
18562
|
+
if (!node.getElementEntry() && node.getRemovedAt()) {
|
|
18563
|
+
this.registerGCPair({
|
|
18564
|
+
parent: elem.getRGATreeList(),
|
|
18565
|
+
child: node
|
|
18566
|
+
});
|
|
18567
|
+
}
|
|
18568
|
+
}
|
|
18569
|
+
}
|
|
18009
18570
|
return false;
|
|
18010
18571
|
});
|
|
18011
18572
|
}
|
|
@@ -19092,6 +19653,11 @@ class Document {
|
|
|
19092
19653
|
if (logger.isEnabled(LogLevel.Trivial)) {
|
|
19093
19654
|
logger.trivial(`trying to update a local change: ${this.toJSON()}`);
|
|
19094
19655
|
}
|
|
19656
|
+
const prev = {
|
|
19657
|
+
hadPresence: this.presences.has(actorID),
|
|
19658
|
+
wasOnline: this.status === "attached",
|
|
19659
|
+
presence: this.presences.has(actorID) ? deepcopy(this.presences.get(actorID)) : void 0
|
|
19660
|
+
};
|
|
19095
19661
|
const change = ctx.toChange();
|
|
19096
19662
|
const { opInfos, reverseOps } = change.execute(
|
|
19097
19663
|
this.root,
|
|
@@ -19137,14 +19703,14 @@ class Document {
|
|
|
19137
19703
|
});
|
|
19138
19704
|
}
|
|
19139
19705
|
if (change.hasPresenceChange()) {
|
|
19140
|
-
|
|
19141
|
-
|
|
19142
|
-
|
|
19143
|
-
|
|
19144
|
-
|
|
19145
|
-
|
|
19146
|
-
|
|
19147
|
-
}
|
|
19706
|
+
const presenceEvent = this.reconcilePresence(
|
|
19707
|
+
actorID,
|
|
19708
|
+
prev,
|
|
19709
|
+
OpSource.Local
|
|
19710
|
+
);
|
|
19711
|
+
if (presenceEvent) {
|
|
19712
|
+
event.push(presenceEvent);
|
|
19713
|
+
}
|
|
19148
19714
|
}
|
|
19149
19715
|
this.publish(event);
|
|
19150
19716
|
if (logger.isEnabled(LogLevel.Trivial)) {
|
|
@@ -19628,41 +20194,11 @@ class Document {
|
|
|
19628
20194
|
change.execute(this.clone.root, this.clone.presences, source);
|
|
19629
20195
|
const events = [];
|
|
19630
20196
|
const actorID = change.getID().getActorID();
|
|
19631
|
-
|
|
19632
|
-
|
|
19633
|
-
|
|
19634
|
-
|
|
19635
|
-
|
|
19636
|
-
this.presences.has(actorID) ? {
|
|
19637
|
-
type: "presence-changed",
|
|
19638
|
-
source,
|
|
19639
|
-
value: {
|
|
19640
|
-
clientID: actorID,
|
|
19641
|
-
presence: presenceChange.presence
|
|
19642
|
-
}
|
|
19643
|
-
} : {
|
|
19644
|
-
type: "watched",
|
|
19645
|
-
source: OpSource.Remote,
|
|
19646
|
-
value: {
|
|
19647
|
-
clientID: actorID,
|
|
19648
|
-
presence: presenceChange.presence
|
|
19649
|
-
}
|
|
19650
|
-
}
|
|
19651
|
-
);
|
|
19652
|
-
break;
|
|
19653
|
-
case PresenceChangeType.Clear:
|
|
19654
|
-
events.push({
|
|
19655
|
-
type: "unwatched",
|
|
19656
|
-
source: OpSource.Remote,
|
|
19657
|
-
value: {
|
|
19658
|
-
clientID: actorID,
|
|
19659
|
-
presence: this.getPresence(actorID)
|
|
19660
|
-
}
|
|
19661
|
-
});
|
|
19662
|
-
this.removeOnlineClient(actorID);
|
|
19663
|
-
break;
|
|
19664
|
-
}
|
|
19665
|
-
}
|
|
20197
|
+
const prev = change.hasPresenceChange() ? {
|
|
20198
|
+
hadPresence: this.presences.has(actorID),
|
|
20199
|
+
wasOnline: this.onlineClients.has(actorID),
|
|
20200
|
+
presence: this.presences.has(actorID) ? deepcopy(this.presences.get(actorID)) : void 0
|
|
20201
|
+
} : void 0;
|
|
19666
20202
|
const { opInfos, operations } = change.execute(
|
|
19667
20203
|
this.root,
|
|
19668
20204
|
this.presences,
|
|
@@ -19717,6 +20253,16 @@ class Document {
|
|
|
19717
20253
|
}
|
|
19718
20254
|
);
|
|
19719
20255
|
}
|
|
20256
|
+
if (prev && change.hasPresenceChange()) {
|
|
20257
|
+
const presenceChange = change.getPresenceChange();
|
|
20258
|
+
if (presenceChange.type === PresenceChangeType.Clear) {
|
|
20259
|
+
this.removeOnlineClient(actorID);
|
|
20260
|
+
}
|
|
20261
|
+
const presenceEvent = this.reconcilePresence(actorID, prev, source);
|
|
20262
|
+
if (presenceEvent) {
|
|
20263
|
+
events.push(presenceEvent);
|
|
20264
|
+
}
|
|
20265
|
+
}
|
|
19720
20266
|
if (events.length) {
|
|
19721
20267
|
this.publish(events);
|
|
19722
20268
|
}
|
|
@@ -19745,46 +20291,43 @@ class Document {
|
|
|
19745
20291
|
* `applyDocEvent` applies the given doc event into this document.
|
|
19746
20292
|
*/
|
|
19747
20293
|
applyDocEvent(type, publisher) {
|
|
19748
|
-
const
|
|
20294
|
+
const prev = {
|
|
20295
|
+
hadPresence: this.presences.has(publisher),
|
|
20296
|
+
wasOnline: this.onlineClients.has(publisher),
|
|
20297
|
+
presence: this.presences.has(publisher) ? deepcopy(this.presences.get(publisher)) : void 0
|
|
20298
|
+
};
|
|
19749
20299
|
if (type === DocEventType$1.DOCUMENT_WATCHED) {
|
|
19750
20300
|
if (this.onlineClients.has(publisher) && this.hasPresence(publisher)) {
|
|
19751
20301
|
return;
|
|
19752
20302
|
}
|
|
19753
20303
|
this.addOnlineClient(publisher);
|
|
19754
|
-
if (this.hasPresence(publisher)) {
|
|
19755
|
-
events.push({
|
|
19756
|
-
type: "watched",
|
|
19757
|
-
source: OpSource.Remote,
|
|
19758
|
-
value: {
|
|
19759
|
-
clientID: publisher,
|
|
19760
|
-
presence: this.getPresence(publisher)
|
|
19761
|
-
}
|
|
19762
|
-
});
|
|
19763
|
-
}
|
|
19764
20304
|
} else if (type === DocEventType$1.DOCUMENT_UNWATCHED) {
|
|
19765
|
-
const presence = this.getPresence(publisher);
|
|
19766
20305
|
this.removeOnlineClient(publisher);
|
|
19767
20306
|
this.presences.delete(publisher);
|
|
19768
|
-
if (presence) {
|
|
19769
|
-
events.push({
|
|
19770
|
-
type: "unwatched",
|
|
19771
|
-
source: OpSource.Remote,
|
|
19772
|
-
value: { clientID: publisher, presence }
|
|
19773
|
-
});
|
|
19774
|
-
}
|
|
19775
20307
|
}
|
|
19776
|
-
|
|
19777
|
-
|
|
20308
|
+
const event = this.reconcilePresence(publisher, prev, OpSource.Remote);
|
|
20309
|
+
if (event) {
|
|
20310
|
+
this.publish([event]);
|
|
19778
20311
|
}
|
|
19779
20312
|
}
|
|
19780
20313
|
/**
|
|
19781
20314
|
* `applyStatus` applies the document status into this document.
|
|
19782
20315
|
*/
|
|
19783
20316
|
applyStatus(status) {
|
|
20317
|
+
const actorID = this.changeID.getActorID();
|
|
20318
|
+
const prev = {
|
|
20319
|
+
hadPresence: this.presences.has(actorID),
|
|
20320
|
+
wasOnline: this.status === "attached",
|
|
20321
|
+
presence: this.presences.has(actorID) ? deepcopy(this.presences.get(actorID)) : void 0
|
|
20322
|
+
};
|
|
19784
20323
|
this.status = status;
|
|
19785
20324
|
if (status === "detached") {
|
|
19786
20325
|
this.setActor(InitialActorID);
|
|
19787
20326
|
}
|
|
20327
|
+
const event = this.reconcilePresence(actorID, prev, OpSource.Local);
|
|
20328
|
+
if (event) {
|
|
20329
|
+
this.publish([event]);
|
|
20330
|
+
}
|
|
19788
20331
|
this.publish([
|
|
19789
20332
|
{
|
|
19790
20333
|
source: status === "removed" ? OpSource.Remote : OpSource.Local,
|
|
@@ -19884,6 +20427,57 @@ class Document {
|
|
|
19884
20427
|
removeOnlineClient(clientID) {
|
|
19885
20428
|
this.onlineClients.delete(clientID);
|
|
19886
20429
|
}
|
|
20430
|
+
/**
|
|
20431
|
+
* `reconcilePresence` compares the previous and current state of a client's
|
|
20432
|
+
* presence/online status and returns the appropriate event to emit.
|
|
20433
|
+
*
|
|
20434
|
+
* For remote clients, "online" means the client is in onlineClients.
|
|
20435
|
+
* For self, "online" means the document status is Attached.
|
|
20436
|
+
*
|
|
20437
|
+
* State transition table:
|
|
20438
|
+
* (!hadP || !wasOn) → (hasP && isOn) : watched (remote) or presence-changed (self)
|
|
20439
|
+
* (hadP && wasOn) → (hasP && isOn) : presence-changed
|
|
20440
|
+
* (hadP && wasOn) → (!hasP || !isOn): unwatched (remote only)
|
|
20441
|
+
* otherwise : no event (waiting)
|
|
20442
|
+
*/
|
|
20443
|
+
reconcilePresence(actorID, prev, source) {
|
|
20444
|
+
const isSelf = actorID === this.changeID.getActorID();
|
|
20445
|
+
const hasPresence = this.presences.has(actorID);
|
|
20446
|
+
const isOnline = isSelf ? this.status === "attached" : this.onlineClients.has(actorID);
|
|
20447
|
+
if (!hasPresence || !isOnline) {
|
|
20448
|
+
if (prev.hadPresence && prev.wasOnline && !isSelf) {
|
|
20449
|
+
return {
|
|
20450
|
+
type: "unwatched",
|
|
20451
|
+
source: OpSource.Remote,
|
|
20452
|
+
value: {
|
|
20453
|
+
clientID: actorID,
|
|
20454
|
+
presence: prev.presence
|
|
20455
|
+
}
|
|
20456
|
+
};
|
|
20457
|
+
}
|
|
20458
|
+
return void 0;
|
|
20459
|
+
}
|
|
20460
|
+
const presence = deepcopy(this.presences.get(actorID));
|
|
20461
|
+
if (!prev.hadPresence || !prev.wasOnline) {
|
|
20462
|
+
if (isSelf) {
|
|
20463
|
+
return {
|
|
20464
|
+
type: "presence-changed",
|
|
20465
|
+
source,
|
|
20466
|
+
value: { clientID: actorID, presence }
|
|
20467
|
+
};
|
|
20468
|
+
}
|
|
20469
|
+
return {
|
|
20470
|
+
type: "watched",
|
|
20471
|
+
source: OpSource.Remote,
|
|
20472
|
+
value: { clientID: actorID, presence }
|
|
20473
|
+
};
|
|
20474
|
+
}
|
|
20475
|
+
return {
|
|
20476
|
+
type: "presence-changed",
|
|
20477
|
+
source,
|
|
20478
|
+
value: { clientID: actorID, presence }
|
|
20479
|
+
};
|
|
20480
|
+
}
|
|
19887
20481
|
/**
|
|
19888
20482
|
* `hasPresence` returns whether the given clientID has a presence or not.
|
|
19889
20483
|
*/
|
|
@@ -20045,18 +20639,24 @@ class Document {
|
|
|
20045
20639
|
const ticket = ctx.issueTimeTicket();
|
|
20046
20640
|
op.setExecutedAt(ticket);
|
|
20047
20641
|
if (op instanceof ArraySetOperation) {
|
|
20048
|
-
const
|
|
20642
|
+
const prev2 = op.getCreatedAt();
|
|
20049
20643
|
op.getValue().setCreatedAt(ticket);
|
|
20050
|
-
this.internalHistory.reconcileCreatedAt(
|
|
20644
|
+
this.internalHistory.reconcileCreatedAt(prev2, ticket);
|
|
20051
20645
|
} else if (op instanceof AddOperation) {
|
|
20052
|
-
const
|
|
20646
|
+
const prev2 = op.getValue().getCreatedAt();
|
|
20053
20647
|
op.getValue().setCreatedAt(ticket);
|
|
20054
|
-
this.internalHistory.reconcileCreatedAt(
|
|
20648
|
+
this.internalHistory.reconcileCreatedAt(prev2, ticket);
|
|
20055
20649
|
}
|
|
20056
20650
|
ctx.push(op);
|
|
20057
20651
|
}
|
|
20058
20652
|
const change = ctx.toChange();
|
|
20059
20653
|
change.execute(this.clone.root, this.clone.presences, OpSource.UndoRedo);
|
|
20654
|
+
const actorID = this.changeID.getActorID();
|
|
20655
|
+
const prev = {
|
|
20656
|
+
hadPresence: this.presences.has(actorID),
|
|
20657
|
+
wasOnline: this.status === "attached",
|
|
20658
|
+
presence: this.presences.has(actorID) ? deepcopy(this.presences.get(actorID)) : void 0
|
|
20659
|
+
};
|
|
20060
20660
|
const { opInfos, reverseOps } = change.execute(
|
|
20061
20661
|
this.root,
|
|
20062
20662
|
this.presences,
|
|
@@ -20078,7 +20678,6 @@ class Document {
|
|
|
20078
20678
|
}
|
|
20079
20679
|
this.localChanges.push(change);
|
|
20080
20680
|
this.changeID = ctx.getNextID();
|
|
20081
|
-
const actorID = this.changeID.getActorID();
|
|
20082
20681
|
const events = [];
|
|
20083
20682
|
if (opInfos.length) {
|
|
20084
20683
|
events.push({
|
|
@@ -20095,14 +20694,14 @@ class Document {
|
|
|
20095
20694
|
});
|
|
20096
20695
|
}
|
|
20097
20696
|
if (change.hasPresenceChange()) {
|
|
20098
|
-
|
|
20099
|
-
|
|
20100
|
-
|
|
20101
|
-
|
|
20102
|
-
|
|
20103
|
-
|
|
20104
|
-
|
|
20105
|
-
}
|
|
20697
|
+
const presenceEvent = this.reconcilePresence(
|
|
20698
|
+
actorID,
|
|
20699
|
+
prev,
|
|
20700
|
+
OpSource.UndoRedo
|
|
20701
|
+
);
|
|
20702
|
+
if (presenceEvent) {
|
|
20703
|
+
events.push(presenceEvent);
|
|
20704
|
+
}
|
|
20106
20705
|
}
|
|
20107
20706
|
this.publish(events);
|
|
20108
20707
|
}
|
|
@@ -20118,6 +20717,8 @@ class Attachment {
|
|
|
20118
20717
|
watchStream;
|
|
20119
20718
|
watchLoopTimerID;
|
|
20120
20719
|
watchAbortController;
|
|
20720
|
+
syncPromise;
|
|
20721
|
+
_detaching = false;
|
|
20121
20722
|
constructor(reconnectStreamDelay, resource, resourceID, syncMode) {
|
|
20122
20723
|
this.reconnectStreamDelay = reconnectStreamDelay;
|
|
20123
20724
|
this.resource = resource;
|
|
@@ -20193,6 +20794,49 @@ class Attachment {
|
|
|
20193
20794
|
};
|
|
20194
20795
|
await doLoop();
|
|
20195
20796
|
}
|
|
20797
|
+
/**
|
|
20798
|
+
* `markDetaching` marks this attachment as being in the process of detaching.
|
|
20799
|
+
* Once marked, the sync loop will skip this attachment.
|
|
20800
|
+
*/
|
|
20801
|
+
markDetaching() {
|
|
20802
|
+
this._detaching = true;
|
|
20803
|
+
}
|
|
20804
|
+
/**
|
|
20805
|
+
* `isDetaching` returns whether this attachment is being detached.
|
|
20806
|
+
*/
|
|
20807
|
+
isDetaching() {
|
|
20808
|
+
return this._detaching;
|
|
20809
|
+
}
|
|
20810
|
+
/**
|
|
20811
|
+
* `resetDetaching` resets the detaching flag so the attachment can resume
|
|
20812
|
+
* syncing. Used when a detach RPC fails and the document remains attached.
|
|
20813
|
+
*/
|
|
20814
|
+
resetDetaching() {
|
|
20815
|
+
this._detaching = false;
|
|
20816
|
+
}
|
|
20817
|
+
/**
|
|
20818
|
+
* `setSyncPromise` sets the in-progress sync promise for this attachment.
|
|
20819
|
+
*/
|
|
20820
|
+
setSyncPromise(promise) {
|
|
20821
|
+
this.syncPromise = promise;
|
|
20822
|
+
}
|
|
20823
|
+
/**
|
|
20824
|
+
* `clearSyncPromise` clears the in-progress sync promise.
|
|
20825
|
+
*/
|
|
20826
|
+
clearSyncPromise() {
|
|
20827
|
+
this.syncPromise = void 0;
|
|
20828
|
+
}
|
|
20829
|
+
/**
|
|
20830
|
+
* `waitForSyncComplete` waits for any in-progress sync to complete.
|
|
20831
|
+
*/
|
|
20832
|
+
async waitForSyncComplete() {
|
|
20833
|
+
if (this.syncPromise) {
|
|
20834
|
+
try {
|
|
20835
|
+
await this.syncPromise;
|
|
20836
|
+
} catch {
|
|
20837
|
+
}
|
|
20838
|
+
}
|
|
20839
|
+
}
|
|
20196
20840
|
/**
|
|
20197
20841
|
* `cancelWatchStream` cancels the watch stream.
|
|
20198
20842
|
*/
|
|
@@ -20227,7 +20871,7 @@ function createAuthInterceptor(apiKey, token) {
|
|
|
20227
20871
|
};
|
|
20228
20872
|
}
|
|
20229
20873
|
const name$1 = "@yorkie-js/sdk";
|
|
20230
|
-
const version$1 = "0.7.
|
|
20874
|
+
const version$1 = "0.7.7";
|
|
20231
20875
|
const pkg$1 = {
|
|
20232
20876
|
name: name$1,
|
|
20233
20877
|
version: version$1
|
|
@@ -20542,6 +21186,7 @@ class Client {
|
|
|
20542
21186
|
taskQueue;
|
|
20543
21187
|
processing = false;
|
|
20544
21188
|
keepalive = false;
|
|
21189
|
+
deactivating = false;
|
|
20545
21190
|
/**
|
|
20546
21191
|
* @param rpcAddr - the address of the RPC server.
|
|
20547
21192
|
* @param opts - the options of the client.
|
|
@@ -20611,6 +21256,7 @@ class Client {
|
|
|
20611
21256
|
);
|
|
20612
21257
|
this.id = res.clientId;
|
|
20613
21258
|
this.status = "activated";
|
|
21259
|
+
this.deactivating = false;
|
|
20614
21260
|
this.runSyncLoop();
|
|
20615
21261
|
logger.info(`[AC] c:"${this.getKey()}" activated, id:"${this.id}"`);
|
|
20616
21262
|
if (typeof window !== "undefined") {
|
|
@@ -20639,6 +21285,7 @@ class Client {
|
|
|
20639
21285
|
if (this.status === "deactivated") {
|
|
20640
21286
|
return Promise.resolve();
|
|
20641
21287
|
}
|
|
21288
|
+
this.deactivating = true;
|
|
20642
21289
|
const task = async () => {
|
|
20643
21290
|
try {
|
|
20644
21291
|
await this.rpcClient.deactivateClient(
|
|
@@ -20652,6 +21299,7 @@ class Client {
|
|
|
20652
21299
|
logger.info(`[DC] c"${this.getKey()}" deactivated`);
|
|
20653
21300
|
} catch (err) {
|
|
20654
21301
|
logger.error(`[DC] c:"${this.getKey()}" err :`, err);
|
|
21302
|
+
this.deactivating = false;
|
|
20655
21303
|
await this.handleConnectError(err);
|
|
20656
21304
|
throw err;
|
|
20657
21305
|
}
|
|
@@ -20792,8 +21440,10 @@ class Client {
|
|
|
20792
21440
|
);
|
|
20793
21441
|
}
|
|
20794
21442
|
doc.update((_, p) => p.clear());
|
|
21443
|
+
attachment.markDetaching();
|
|
20795
21444
|
const task = async () => {
|
|
20796
21445
|
try {
|
|
21446
|
+
await attachment.waitForSyncComplete();
|
|
20797
21447
|
const res = await this.rpcClient.detachDocument(
|
|
20798
21448
|
{
|
|
20799
21449
|
clientId: this.id,
|
|
@@ -20812,6 +21462,7 @@ class Client {
|
|
|
20812
21462
|
return doc;
|
|
20813
21463
|
} catch (err) {
|
|
20814
21464
|
logger.error(`[DD] c:"${this.getKey()}" err :`, err);
|
|
21465
|
+
attachment.resetDetaching();
|
|
20815
21466
|
await this.handleConnectError(err);
|
|
20816
21467
|
throw err;
|
|
20817
21468
|
}
|
|
@@ -21378,7 +22029,7 @@ class Client {
|
|
|
21378
22029
|
*/
|
|
21379
22030
|
runSyncLoop() {
|
|
21380
22031
|
const doLoop = async () => {
|
|
21381
|
-
if (!this.isActive()) {
|
|
22032
|
+
if (!this.isActive() || this.deactivating) {
|
|
21382
22033
|
logger.debug(`[SL] c:"${this.getKey()}" exit sync loop`);
|
|
21383
22034
|
this.conditions[
|
|
21384
22035
|
"SyncLoop"
|
|
@@ -21390,43 +22041,62 @@ class Client {
|
|
|
21390
22041
|
await this.enqueueTask(async () => {
|
|
21391
22042
|
const syncs = [];
|
|
21392
22043
|
for (const [, attachment] of this.attachmentMap) {
|
|
22044
|
+
if (this.deactivating) {
|
|
22045
|
+
break;
|
|
22046
|
+
}
|
|
21393
22047
|
if (!attachment.needSync(this.channelHeartbeatInterval)) {
|
|
21394
22048
|
continue;
|
|
21395
22049
|
}
|
|
22050
|
+
if (attachment.isDetaching()) {
|
|
22051
|
+
continue;
|
|
22052
|
+
}
|
|
21396
22053
|
if (attachment.changeEventReceived !== void 0) {
|
|
21397
22054
|
attachment.changeEventReceived = false;
|
|
21398
22055
|
}
|
|
21399
|
-
|
|
21400
|
-
|
|
21401
|
-
|
|
21402
|
-
|
|
21403
|
-
|
|
21404
|
-
|
|
21405
|
-
|
|
21406
|
-
|
|
21407
|
-
|
|
21408
|
-
|
|
22056
|
+
const syncPromise = this.syncInternal(
|
|
22057
|
+
attachment,
|
|
22058
|
+
attachment.syncMode
|
|
22059
|
+
).then(() => {
|
|
22060
|
+
}).catch((e) => {
|
|
22061
|
+
if (isErrorCode(e, Code.ErrUnauthenticated)) {
|
|
22062
|
+
attachment.resource.publish([
|
|
22063
|
+
{
|
|
22064
|
+
type: DocEventType.AuthError,
|
|
22065
|
+
value: {
|
|
22066
|
+
reason: errorMetadataOf(e).reason,
|
|
22067
|
+
method: "PushPull"
|
|
21409
22068
|
}
|
|
21410
|
-
|
|
21411
|
-
|
|
21412
|
-
|
|
21413
|
-
|
|
21414
|
-
|
|
21415
|
-
|
|
21416
|
-
|
|
21417
|
-
|
|
21418
|
-
|
|
22069
|
+
}
|
|
22070
|
+
]);
|
|
22071
|
+
}
|
|
22072
|
+
if (isErrorCode(e, Code.ErrEpochMismatch)) {
|
|
22073
|
+
attachment.resource.publish([
|
|
22074
|
+
{
|
|
22075
|
+
type: DocEventType.EpochMismatch,
|
|
22076
|
+
value: {
|
|
22077
|
+
method: "PushPull"
|
|
21419
22078
|
}
|
|
21420
|
-
|
|
21421
|
-
|
|
21422
|
-
|
|
21423
|
-
|
|
21424
|
-
)
|
|
22079
|
+
}
|
|
22080
|
+
]);
|
|
22081
|
+
}
|
|
22082
|
+
throw e;
|
|
22083
|
+
}).finally(() => {
|
|
22084
|
+
attachment.clearSyncPromise();
|
|
22085
|
+
});
|
|
22086
|
+
attachment.setSyncPromise(syncPromise);
|
|
22087
|
+
syncs.push(syncPromise);
|
|
21425
22088
|
}
|
|
21426
22089
|
await Promise.all(syncs);
|
|
21427
22090
|
setTimeout(doLoop, this.syncLoopDuration);
|
|
21428
22091
|
});
|
|
21429
22092
|
} catch (err) {
|
|
22093
|
+
if (this.deactivating) {
|
|
22094
|
+
this.conditions[
|
|
22095
|
+
"SyncLoop"
|
|
22096
|
+
/* SyncLoop */
|
|
22097
|
+
] = false;
|
|
22098
|
+
return;
|
|
22099
|
+
}
|
|
21430
22100
|
logger.error(`[SL] c:"${this.getKey()}" sync failed:`, err);
|
|
21431
22101
|
if (await this.handleConnectError(err)) {
|
|
21432
22102
|
setTimeout(doLoop, this.retrySyncLoopDelay);
|
|
@@ -21907,8 +22577,11 @@ function isBinData(value) {
|
|
|
21907
22577
|
function isCounter(value) {
|
|
21908
22578
|
return typeof value === "object" && value !== null && value.type === "Counter" && typeof value.value === "object";
|
|
21909
22579
|
}
|
|
22580
|
+
function isDedupCounter(value) {
|
|
22581
|
+
return typeof value === "object" && value !== null && value.type === "DedupCounter" && typeof value.value === "object" && typeof value.registers === "string";
|
|
22582
|
+
}
|
|
21910
22583
|
function isObject(value) {
|
|
21911
|
-
return typeof value === "object" && value !== null && !Array.isArray(value) && !isText(value) && !isTree(value) && !isInt(value) && !isLong(value) && !isDate(value) && !isBinData(value) && !isCounter(value);
|
|
22584
|
+
return typeof value === "object" && value !== null && !Array.isArray(value) && !isText(value) && !isTree(value) && !isInt(value) && !isLong(value) && !isDate(value) && !isBinData(value) && !isCounter(value) && !isDedupCounter(value);
|
|
21912
22585
|
}
|
|
21913
22586
|
function parse(yson) {
|
|
21914
22587
|
try {
|
|
@@ -21924,6 +22597,12 @@ function parse(yson) {
|
|
|
21924
22597
|
}
|
|
21925
22598
|
function preprocessYSON(yson) {
|
|
21926
22599
|
let result = yson;
|
|
22600
|
+
result = result.replace(
|
|
22601
|
+
/DedupCounter\(Int\((-?\d+)\),"([^"]+)"\)/g,
|
|
22602
|
+
(_, value, registers) => {
|
|
22603
|
+
return `{"__yson_type":"DedupCounter","__yson_data":{"__yson_type":"Int","__yson_data":${value}},"__yson_registers":"${registers}"}`;
|
|
22604
|
+
}
|
|
22605
|
+
);
|
|
21927
22606
|
result = result.replace(
|
|
21928
22607
|
/Counter\((Int|Long)\((-?\d+)\)\)/g,
|
|
21929
22608
|
(_, type, value) => {
|
|
@@ -21984,6 +22663,20 @@ function postprocessValue(value) {
|
|
|
21984
22663
|
value: value.__yson_data
|
|
21985
22664
|
};
|
|
21986
22665
|
}
|
|
22666
|
+
if (value.__yson_type === "DedupCounter" && typeof value.__yson_data === "object" && typeof value.__yson_registers === "string") {
|
|
22667
|
+
const counterValue = postprocessValue(value.__yson_data);
|
|
22668
|
+
if (typeof counterValue === "object" && counterValue !== null && "type" in counterValue && counterValue.type === "Int") {
|
|
22669
|
+
return {
|
|
22670
|
+
type: "DedupCounter",
|
|
22671
|
+
value: counterValue,
|
|
22672
|
+
registers: value.__yson_registers
|
|
22673
|
+
};
|
|
22674
|
+
}
|
|
22675
|
+
throw new YorkieError(
|
|
22676
|
+
Code.ErrInvalidArgument,
|
|
22677
|
+
"DedupCounter must contain Int"
|
|
22678
|
+
);
|
|
22679
|
+
}
|
|
21987
22680
|
if (value.__yson_type === "Counter" && typeof value.__yson_data === "object") {
|
|
21988
22681
|
const counterValue = postprocessValue(value.__yson_data);
|
|
21989
22682
|
if (typeof counterValue === "object" && counterValue !== null && "type" in counterValue && (counterValue.type === "Int" || counterValue.type === "Long")) {
|
|
@@ -22072,6 +22765,7 @@ const YSON = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty
|
|
|
22072
22765
|
isBinData,
|
|
22073
22766
|
isCounter,
|
|
22074
22767
|
isDate,
|
|
22768
|
+
isDedupCounter,
|
|
22075
22769
|
isInt,
|
|
22076
22770
|
isLong,
|
|
22077
22771
|
isObject,
|
|
@@ -22098,7 +22792,7 @@ if (typeof globalThis !== "undefined") {
|
|
|
22098
22792
|
};
|
|
22099
22793
|
}
|
|
22100
22794
|
const name = "@yorkie-js/react";
|
|
22101
|
-
const version = "0.7.
|
|
22795
|
+
const version = "0.7.7";
|
|
22102
22796
|
const pkg = {
|
|
22103
22797
|
name,
|
|
22104
22798
|
version
|