Commit graph

2669 commits

Author SHA1 Message Date
82abfeb8ff
feat(sync) Add a belongsTo property in the schema
This new property allows to know what's the relation with the schema
property and the different object types (map, datalayer, feature).

This serves two goals:

1. Check that the incoming messages make sense (it's possible to change
   this property in this object)
2. Document where the property is used in practice. Because there is a
   lot of properties, it's hard to keep track of where they are used.
   This makes it explicit.
2024-05-16 13:50:07 +02:00
56244cf701
chore(sync): remove belongsTo for now
As it requires more discussion, it will happen in a separate
pull-request.
2024-05-16 13:47:43 +02:00
f115e75976
test(sync): WIP 2024-05-16 13:47:22 +02:00
cb54cbb4ab
chore(test): remove empty test 2024-05-16 13:42:55 +02:00
81b2bba045
chore(test): fix a typo
(but I would really like to see what web socker would look like)
2024-05-16 13:40:22 +02:00
d897bb5924
chore(sync): relax some validation logic on the websocket server
Messages are now checked for conformity with the procol we defined, but
stop at the `operation` boundary. Values aren't checked.
2024-05-15 18:59:48 +02:00
a64690912b
chore(sync): Sync engine now retrieves auth token
It's now it's responsability to get the authentication token from
the http server and pass it to the websocket server, it will make it
possible to redo the roundtrip when getting disconnected.
2024-05-15 18:56:54 +02:00
bfdc87a537
chore(sync): use sync=false everywhere to stop propagation
In some cases, you want to stop the propagation of events. The previous
code was using `fromSync=true` and `sync=false` interchangeably. This
makes it use `sync=false` everywhere.
2024-05-15 18:54:56 +02:00
0bc5af20bf
chore(utils): remove console.log calls 2024-05-15 18:53:49 +02:00
ea66e6a5c6
fix(schema): dashArray belongs to features as well 2024-05-15 18:50:28 +02:00
35c51a815e
test(sync): Ensure datalayer properties are synced 2024-05-15 15:03:59 +02:00
2ca27c3c20
test(sync): Ensure map properties are synced
This tests that the name of the map, and that zoom-control visibility is
properly synced over websockets.
2024-05-15 14:47:55 +02:00
550a43c6d1
test(sync): ensure polygon drag-n-drop is synced 2024-05-15 14:31:53 +02:00
98c3849165
test(sync): Ensure polygons and their edits can be synced 2024-05-15 12:25:02 +02:00
4c6e0a86d5
test(sync): Marker drag-n-drop and delete are synced 2024-05-15 12:25:02 +02:00
2c9b8230ab
tests(sync): Test that marker sync works properly
This commit handles the start and stop of the websocket server during
the tests, using the xprocess library
2024-05-15 12:25:01 +02:00
fff2235c3d
chore(tests): Rename "collaboration" tests to "optimistic merge"
As "collaboration" can be mistaken between "websocket" and
"server-merge". This naming makes it explicit.
2024-05-15 12:25:01 +02:00
c0212eeb93
chore(sync): Add message-dispatcher unit tests 2024-05-15 12:25:01 +02:00
6618f38b17
feat(sync): Add JS unittests for updateObjectValue, and refactor.
The new implementation uses `reduce`, in the hopes of producing a more
readable version than old-style loops and reassignment of object values.
2024-05-15 12:25:01 +02:00
d95d8d4cba
feat(sync): add tests for the websocket token view 2024-05-15 12:25:01 +02:00
991add938c
refactor(sync): Remove unnecessary complexity
Because we're relying on the `geoJSONToFeatures` method, we don't need
anymore updaters, the default ones (map, datalayer, feature) are enough.

It also makes the codebase compatible with our eslint configuration.
2024-05-15 12:25:00 +02:00
124b7278da
chore(sync) make the test pass 2024-05-15 12:25:00 +02:00
b85ee4011e
chore(docker) remove ws.py for now 2024-05-15 12:25:00 +02:00
90e85f1465
fix(sync) only send datalayer options 2024-05-15 12:25:00 +02:00
190c3535fe
fix(sync): do not call getSyncMetadata if it doesn't exist
This can arise when the form isn't bound to a "syncable" object. We
might want to provide an utility to check an object is *syncable*, or a
specific form to not attempt to sync objects which don't need it.
2024-05-15 12:24:59 +02:00
47070d148f
feat(sync): Allow the sync of datalayer creation 2024-05-15 12:24:59 +02:00
178eb2ac1c
fix(sync): allow features geometries to be synced
By defining the `geometry` property in the schema.
2024-05-15 12:24:59 +02:00
61d8ccbdaf
chore(docker): run the websocket server as a separate command 2024-05-15 12:24:59 +02:00
57355eb4c5
chore(sync): remove useless dependencies from ws.py 2024-05-15 12:24:58 +02:00
81554d1e2e
feat(settings): allow reading socket-related settings from ENV variables 2024-05-15 12:24:58 +02:00
cbdcfba720
fix(sync): intialize the sync engine before entering edit mode.
Otherwise `this.sync` is not defined.
2024-05-15 12:24:58 +02:00
1f0782665b
feat(sync): handle syncing of map limitbounds. 2024-05-15 12:24:58 +02:00
a491a7c837
feat(sync): Avoid syncing remote datalayers' features
They will be synced on their own, and we dont want them to be present
twice on the map.
2024-05-15 12:24:58 +02:00
1d2cf981d1
fix(sync): Initialize tilelayerand remoteData earlier.
It makes it possible to set these values on a remote peer.
2024-05-15 12:24:57 +02:00
1aad9013f5
fix(sync): Allow overlays to sync
`this.options.overlay` is now set during `map.initialize()`, which makes
it possible to be set by incoming websocket operations.
2024-05-15 12:24:57 +02:00
bfd7613d68
chore(sync): Ensure properties can be updated before doing it.
When receiving a message, this checks the given properties belong to
the "subject" before applying the message.
2024-05-15 12:24:57 +02:00
1c1dd4af82
chore(schema): Add a belongsTo field in the schema.
The goal is to use this as a security measure, to check that the
updated properties belong the the "subject" when receiving sync
operations.
2024-05-15 12:24:57 +02:00
0bddba24fd
fix(sync): Allow cloning of features
Removing the `id` from the feature when cloning makes it generate a new
one. Without this change, the cloned feature keep the already existing
`id`, and during sync, the original object is lost (replaced by the
clone).

Nobody wants to be replaced by a clone.
2024-05-15 12:24:57 +02:00
5a32a3d0ca
feat(sync): Sync only when the edition of a feature is over.
It's less spectacular than sending the position as it changes, but takes
less bandwidth and seems good enough.
2024-05-15 12:24:56 +02:00
99e24d9b41
fix(sync): Import the data when syncing GeoJSON objects.
Prior to these changes, the data wasn't transmitted over WebSocket, and
even if present it wasn't taken into account.
2024-05-15 12:24:56 +02:00
23d1c3bda9
fix(sync): Keep features IDs for Polygons and Lines
It wasn't passed previously, so objects where duplicated.
2024-05-15 12:24:56 +02:00
f964bfff0f
feat(sync): Only sync when on edit mode
The is done to save server resources, for accessed maps which
aren't currently being edited.
2024-05-15 12:24:56 +02:00
346391b311
chore(sync): Move the sync flag in the options
The goal being for it to be hidden for now.

- Add a `is_owner` method on the map and use it in the view
- Remove duplicated line in `global.js`
- Rename `Datalayer` to `DataLayer` everywhere
- Move the sync flag in the map options (next to slideshow)
2024-05-15 12:24:55 +02:00
33108a9ae0
feat(sync): Add WebSocket specific settings
`WEBSOCKET_ENABLED`, `WEBSOCKET_HOST`, `WEBSOCKET_PORT` and
`WEBSOCKET_URI` have been added.

They are being transmitted to the client via the `map.options`.
When `WEBSOCKET_ENABLED` is set to `False`, the client doesn't have
the ability to be synced.
2024-05-15 12:24:55 +02:00
c4db041494
feat(sync): Add a enableSync option.
This changes how the syncEngine works. At the moment, it's always
instanciated, even if no syncing is configured. It just does nothing.

This is to avoid doing `if (engine) engine.update()` calls everywhere
we use it.

You now need to `start()` and `stop()` it.
2024-05-15 12:24:55 +02:00
1ed47848b4
feat(sync): initialize datalayers internal objects in the constructor.
Otherwise, an event can come from the websocket, trying to update an
`undefined` property.
2024-05-15 12:24:55 +02:00
2bd96d2517
feat(sync): sync layer's properties.
This also changes the interface between the synced classes and the sync
engine.

The sync engines only requires two methods now:

- `getSyncMetadata()` which returns all the metadata needed, including
the `engine`.
- `render()` which renders the object, updating the needed parts.
2024-05-15 12:24:54 +02:00
8a4c50d379
feat(sync): Sync features over websockets
Added a new `geometryToFeature` method in `umap.layer.js` which can
update a given geometry if needed.

A new `id` property can also be passed to the features on creation, to
make it possible to have the same features `id` on different peers.
2024-05-15 12:24:54 +02:00
cd09cacf19
feat(sync): sync map properties over websocket
All keystrokes are currently sent, which is not ideal because it will
use a lot of bandwidth.
2024-05-15 12:24:54 +02:00
4474f06ed4
feat(sync): sync features and map properties
Synced objects now expose different methods, such as:
- `getSyncEngine` which returns the location of the sync object.
- `getMetadata` which returns the associated metadata with the object.

Hooks have been added when features are created or changed, so the
changes can be synced with other peers.
2024-05-15 12:24:53 +02:00