#667 - add sanity messages when data is read before type is added to a document.
This commit is contained in:
parent
8cd1a482bb
commit
3bf44b9850
@ -17,6 +17,12 @@ import * as map from 'lib0/map'
|
||||
import * as iterator from 'lib0/iterator'
|
||||
import * as error from 'lib0/error'
|
||||
import * as math from 'lib0/math'
|
||||
import * as log from 'lib0/logging'
|
||||
|
||||
/**
|
||||
* https://docs.yjs.dev/getting-started/working-with-shared-types#caveats
|
||||
*/
|
||||
export const warnPrematureAccess = () => { log.warn('Invalid access: Add Yjs type to a document before reading data.') }
|
||||
|
||||
const maxSearchMarker = 80
|
||||
|
||||
@ -215,6 +221,7 @@ export const updateMarkerChanges = (searchMarker, index, len) => {
|
||||
* @return {Array<Item>}
|
||||
*/
|
||||
export const getTypeChildren = t => {
|
||||
t.doc ?? warnPrematureAccess()
|
||||
let s = t._start
|
||||
const arr = []
|
||||
while (s) {
|
||||
@ -408,6 +415,7 @@ export class AbstractType {
|
||||
* @function
|
||||
*/
|
||||
export const typeListSlice = (type, start, end) => {
|
||||
type.doc ?? warnPrematureAccess()
|
||||
if (start < 0) {
|
||||
start = type._length + start
|
||||
}
|
||||
@ -443,6 +451,7 @@ export const typeListSlice = (type, start, end) => {
|
||||
* @function
|
||||
*/
|
||||
export const typeListToArray = type => {
|
||||
type.doc ?? warnPrematureAccess()
|
||||
const cs = []
|
||||
let n = type._start
|
||||
while (n !== null) {
|
||||
@ -492,6 +501,7 @@ export const typeListToArraySnapshot = (type, snapshot) => {
|
||||
export const typeListForEach = (type, f) => {
|
||||
let index = 0
|
||||
let n = type._start
|
||||
type.doc ?? warnPrematureAccess()
|
||||
while (n !== null) {
|
||||
if (n.countable && !n.deleted) {
|
||||
const c = n.content.getContent()
|
||||
@ -606,6 +616,7 @@ export const typeListForEachSnapshot = (type, f, snapshot) => {
|
||||
* @function
|
||||
*/
|
||||
export const typeListGet = (type, index) => {
|
||||
type.doc ?? warnPrematureAccess()
|
||||
const marker = findMarker(type, index)
|
||||
let n = type._start
|
||||
if (marker !== null) {
|
||||
@ -874,6 +885,7 @@ export const typeMapSet = (transaction, parent, key, value) => {
|
||||
* @function
|
||||
*/
|
||||
export const typeMapGet = (parent, key) => {
|
||||
parent.doc ?? warnPrematureAccess()
|
||||
const val = parent._map.get(key)
|
||||
return val !== undefined && !val.deleted ? val.content.getContent()[val.length - 1] : undefined
|
||||
}
|
||||
@ -890,6 +902,7 @@ export const typeMapGetAll = (parent) => {
|
||||
* @type {Object<string,any>}
|
||||
*/
|
||||
const res = {}
|
||||
parent.doc ?? warnPrematureAccess()
|
||||
parent._map.forEach((value, key) => {
|
||||
if (!value.deleted) {
|
||||
res[key] = value.content.getContent()[value.length - 1]
|
||||
@ -907,6 +920,7 @@ export const typeMapGetAll = (parent) => {
|
||||
* @function
|
||||
*/
|
||||
export const typeMapHas = (parent, key) => {
|
||||
parent.doc ?? warnPrematureAccess()
|
||||
const val = parent._map.get(key)
|
||||
return val !== undefined && !val.deleted
|
||||
}
|
||||
@ -957,10 +971,13 @@ export const typeMapGetAllSnapshot = (parent, snapshot) => {
|
||||
}
|
||||
|
||||
/**
|
||||
* @param {Map<string,Item>} map
|
||||
* @param {AbstractType<any> & { _map: Map<string, Item> }} type
|
||||
* @return {IterableIterator<Array<any>>}
|
||||
*
|
||||
* @private
|
||||
* @function
|
||||
*/
|
||||
export const createMapIterator = map => iterator.iteratorFilter(map.entries(), /** @param {any} entry */ entry => !entry[1].deleted)
|
||||
export const createMapIterator = type => {
|
||||
type.doc ?? warnPrematureAccess()
|
||||
return iterator.iteratorFilter(type._map.entries(), /** @param {any} entry */ entry => !entry[1].deleted)
|
||||
}
|
||||
|
@ -16,6 +16,7 @@ import {
|
||||
YArrayRefID,
|
||||
callTypeObservers,
|
||||
transact,
|
||||
warnPrematureAccess,
|
||||
ArraySearchMarker, UpdateDecoderV1, UpdateDecoderV2, UpdateEncoderV1, UpdateEncoderV2, Doc, Transaction, Item // eslint-disable-line
|
||||
} from '../internals.js'
|
||||
import { typeListSlice } from './AbstractType.js'
|
||||
@ -104,6 +105,7 @@ export class YArray extends AbstractType {
|
||||
}
|
||||
|
||||
get length () {
|
||||
this.doc ?? warnPrematureAccess()
|
||||
return this._length
|
||||
}
|
||||
|
||||
|
@ -13,6 +13,7 @@ import {
|
||||
YMapRefID,
|
||||
callTypeObservers,
|
||||
transact,
|
||||
warnPrematureAccess,
|
||||
UpdateDecoderV1, UpdateDecoderV2, UpdateEncoderV1, UpdateEncoderV2, Doc, Transaction, Item // eslint-disable-line
|
||||
} from '../internals.js'
|
||||
|
||||
@ -121,6 +122,7 @@ export class YMap extends AbstractType {
|
||||
* @return {Object<string,any>}
|
||||
*/
|
||||
toJSON () {
|
||||
this.doc ?? warnPrematureAccess()
|
||||
/**
|
||||
* @type {Object<string,MapType>}
|
||||
*/
|
||||
@ -140,7 +142,7 @@ export class YMap extends AbstractType {
|
||||
* @return {number}
|
||||
*/
|
||||
get size () {
|
||||
return [...createMapIterator(this._map)].length
|
||||
return [...createMapIterator(this)].length
|
||||
}
|
||||
|
||||
/**
|
||||
@ -149,7 +151,7 @@ export class YMap extends AbstractType {
|
||||
* @return {IterableIterator<string>}
|
||||
*/
|
||||
keys () {
|
||||
return iterator.iteratorMap(createMapIterator(this._map), /** @param {any} v */ v => v[0])
|
||||
return iterator.iteratorMap(createMapIterator(this), /** @param {any} v */ v => v[0])
|
||||
}
|
||||
|
||||
/**
|
||||
@ -158,7 +160,7 @@ export class YMap extends AbstractType {
|
||||
* @return {IterableIterator<MapType>}
|
||||
*/
|
||||
values () {
|
||||
return iterator.iteratorMap(createMapIterator(this._map), /** @param {any} v */ v => v[1].content.getContent()[v[1].length - 1])
|
||||
return iterator.iteratorMap(createMapIterator(this), /** @param {any} v */ v => v[1].content.getContent()[v[1].length - 1])
|
||||
}
|
||||
|
||||
/**
|
||||
@ -167,7 +169,7 @@ export class YMap extends AbstractType {
|
||||
* @return {IterableIterator<[string, MapType]>}
|
||||
*/
|
||||
entries () {
|
||||
return iterator.iteratorMap(createMapIterator(this._map), /** @param {any} v */ v => /** @type {any} */ ([v[0], v[1].content.getContent()[v[1].length - 1]]))
|
||||
return iterator.iteratorMap(createMapIterator(this), /** @param {any} v */ v => /** @type {any} */ ([v[0], v[1].content.getContent()[v[1].length - 1]]))
|
||||
}
|
||||
|
||||
/**
|
||||
@ -176,6 +178,7 @@ export class YMap extends AbstractType {
|
||||
* @param {function(MapType,string,YMap<MapType>):void} f A function to execute on every element of this YArray.
|
||||
*/
|
||||
forEach (f) {
|
||||
this.doc ?? warnPrematureAccess()
|
||||
this._map.forEach((item, key) => {
|
||||
if (!item.deleted) {
|
||||
f(item.content.getContent()[item.length - 1], key, this)
|
||||
|
@ -26,6 +26,7 @@ import {
|
||||
typeMapGetAll,
|
||||
updateMarkerChanges,
|
||||
ContentType,
|
||||
warnPrematureAccess,
|
||||
ArraySearchMarker, UpdateDecoderV1, UpdateDecoderV2, UpdateEncoderV1, UpdateEncoderV2, ID, Doc, Item, Snapshot, Transaction // eslint-disable-line
|
||||
} from '../internals.js'
|
||||
|
||||
@ -875,6 +876,7 @@ export class YText extends AbstractType {
|
||||
* @type {number}
|
||||
*/
|
||||
get length () {
|
||||
this.doc ?? warnPrematureAccess()
|
||||
return this._length
|
||||
}
|
||||
|
||||
@ -931,6 +933,7 @@ export class YText extends AbstractType {
|
||||
* @public
|
||||
*/
|
||||
toString () {
|
||||
this.doc ?? warnPrematureAccess()
|
||||
let str = ''
|
||||
/**
|
||||
* @type {Item|null}
|
||||
@ -1004,6 +1007,7 @@ export class YText extends AbstractType {
|
||||
* @public
|
||||
*/
|
||||
toDelta (snapshot, prevSnapshot, computeYChange) {
|
||||
this.doc ?? warnPrematureAccess()
|
||||
/**
|
||||
* @type{Array<any>}
|
||||
*/
|
||||
|
@ -17,6 +17,7 @@ import {
|
||||
transact,
|
||||
typeListGet,
|
||||
typeListSlice,
|
||||
warnPrematureAccess,
|
||||
UpdateDecoderV1, UpdateDecoderV2, UpdateEncoderV1, UpdateEncoderV2, Doc, ContentType, Transaction, Item, YXmlText, YXmlHook // eslint-disable-line
|
||||
} from '../internals.js'
|
||||
|
||||
@ -66,6 +67,7 @@ export class YXmlTreeWalker {
|
||||
*/
|
||||
this._currentNode = /** @type {Item} */ (root._start)
|
||||
this._firstCall = true
|
||||
root.doc ?? warnPrematureAccess()
|
||||
}
|
||||
|
||||
[Symbol.iterator] () {
|
||||
@ -177,6 +179,7 @@ export class YXmlFragment extends AbstractType {
|
||||
}
|
||||
|
||||
get length () {
|
||||
this.doc ?? warnPrematureAccess()
|
||||
return this._prelimContent === null ? this._length : this._prelimContent.length
|
||||
}
|
||||
|
||||
|
Loading…
x
Reference in New Issue
Block a user