📣 Rhino: Feedback wanted on updating behaviour on receive!

Hi everyone. Speckle newbie here and apologies if the questions have been answered before but I looked and couldn’t find anything so here it comes :slight_smile:

Trying to wrap my head around how Speckle works I have the following questions on sending and receiving geometry: [I’ll create separate posts for questions on other topics]:

1- When I send a geometry from one Rhino file, receiving works fine on another Rhino instance on my machine. But when I update the geometry, send and receive it again, a new geometry is created (as opposed to the same geometry getting updated). So for instance I end up with two surfaces after receiving for the second time. If I receive a third time, there will be three surfaces. Am I right in expecting the same geometry to be updated? Could there be any settings I’ve missed?

2- If say my file has three boxes in it and I change one box only, do I need to select entire boxes again when I want to commit my change? Seems like the concept of staging and committing a single file in git, doesn’t have an equivalent here where file = geometry(data)?


1 Like

Hey Hoss,

Great to see you here :wave:!

Thanks for your questions, we give these concepts for granted but we should definitely clarify them in our docs!

  • currently, the only connector that upon receiving takes care of updating/deleting previously received objects and geometry is the Revit one. In Rhino, AutoCAD etc the newly received geometry is instead added to a new Layer. We thought this to be the most intuitive way of handling updates, but we’d be happy to hear if instead you’d like a different behaviour.

  • we have borrowed many ideas from git, but our version control systems behave a bit differently => if only one of your three boxes has changed you should still send them all (and actually if you have created a filter by layer, for instance, that will happen automatically). What happens in the background is that Specke will realize only 1 of those 3 boxes is new and in our database, only the new one will be stored. This is why you should see commits more like snapshots in time of your model rather than diffs.

Hope it makes sense!

1 Like

This question appeared a few times in the past! Funnily enough, 1.0 Rhino behaviour was exactly that - we’d diff and update geometry, deleting things that were no longer there, etc. There was some pushback - some grasshopper scripts would fail, and geometry would need to be re-referenced, hence we’ve taken this more cautious approach in 2.0. To get rid of old stuff, you just need to delete/hide the old commit’s layer.

We’re totally up to be convinced to go the other way though! Any feedback here is much appreciated, so anyone with strong opinions on this, let rip!

1 Like

I’m new as well to speckle and trying to wrap my head around it so I can communicate to my project team (and evetually my firm) .

Since you asked, Im going to ramble what I’ve been thinking about how it should function :slight_smile:

I think the expected update behavior comes down to the intended audience. I envision a team made up of a few people who understand speckle on a deep level, but the majority will not want to understand or need to understand it. they just want it work as simply as possible.

As I’m thinking through this project, and trying to plan/strategize how we approach streams and branches and how they are set up, what I keep coming back to is simplicity & truth. Ultimately i think the most important thing is that everyone is confident that they are using the most up to date geometry (data). There is no confusion as to which version what stream/branch i should be referencing. eg: if Im in Revit, I have the most current landscape and façade model referenced in from Rhino. And if im in Rhino working on the facade, there is no doubt which Revit interior model i should have loaded in as I work.

What is great about speckle is that if I have loaded in a stream, it will notify me that the stream has been updated. However like the OP mentioned, it doesn’t quite work like I expected. In Rhino, it isn’t that hard to know that I need to delete the entire layer structure out to remove any old geometry when I load in a new. A small negative about the approach of having to delete the previous commits as i bring in new ones is that i might have accidently modeled something on one of those layers (or copied geometry to iterate on) and then it would be gone since I bulk deleted those layers.

however, in Rhino, I would think it would be more intuitive if I have chosen to have the ‘latest’ branch linked in, that it would update all that geometry that was in the already existing layers speckle created. if for some reason I want to know what has changed, or reference something from a previous commit, then I would load in that specific commit, and it would add in a new layer structure with that specific commit. but the ‘latest’ layer structure would always remain unchanged and would be the most recent receive i have done.

Regarding breaking references to grasshopper scripts, i would expect grasshopper references to break regardless of how its updated. I would probably structure what I’m sending in to speckle in a way that I would use a ‘Human’ ‘Dynamic Geometry pipeline’ to grab things from that specific layer.

The biggest issue that I’m wondering/struggling wrapping my head around is actually Revit and how bringing in rhino geometry into Revit seems to work. This concern comes from me messing around with stream branches. If I have 2 rhino branchs like:

  • /facade/option1
  • /facade/option2

Then if I choose to load in /facade/option1 into revit and then want to switch evert thing over to /facade/option2 then it seems like i need to somehow select manually all 100s of things imported for /facade/Option1 and delete them? there is no way to remove what speckle has brought into revit.

(Or if for some reason the stream connection is broken, then I’m left with possibly 100s of generic models that I have no idea how old they are and if they are correct or actualy the mot current /correct geomtery. )

It would be nice if when i bring in rhino geometry into Revit that it gives me option to put them in a specific workset, or at least group them So if a user sees a group of a bunch of geometry, they would know that its from speckle, and if it seems wrong, i can delete the entire group quickly and reimport what I want. Or maybe even the option to remove that import from revit using the speckle stream plugin (all this could already be in there, so apologies if it is)

Like i said its about reducing complexity, and increasing the knowledge and confidence in the team that they are working with the newest/correct geometry.


Hi @RJCoolpix880! thanks for taking the time to give us this feedback - it’s super helpful, and packed of actionable advice.

Starting from your end - I must disclose sometimes, getting stuck in code, we miss obvious things; so your feedback is like music to our ears :slight_smile:

Agreed 100%. I think this is something we should probably implement across all rhino-like connectors, inc. autocad, blender, etc. - wherever this makes sense (e.g., not Revit). What does @SpeckleTeam connector owners think on this one?

I like a lot the very simple demarcation -

  • “latest” receiving mode → swaps the old for the new, where possible (e.g., if you explode a brep, that won’t work anymore - i have to double check)
  • “commit” receiving mode → create layers as per current behaviour.

Good point, and using the geometry pipeline component or similar is an easy way of overcoming this - especially in “latest” mode, where theoretically layers won’t bounce around that much anymore.

Regarding Revit, things do get a bit more complicated because of associativity stuff. Nevertheless

This sounds like a good way forward. In the past we were musing on adding a “delete associated elements” button next to the stream itself (this won’t work though if you loose that stream link in revit). I’ll have to poke @teocomi & co. re workset grouping.

Also, as a PS:

Consider it an open invitation 🙇‍♂️


Just wanted to chime in really quickly and say I am in support of this and think @RJCoolpix880 's observation is right on point!

It also conceptually aligns nicely with the use cases of either (1) typically leaving the receiver on the default latest commit selection or (2) actively selecting a specific commit for a less common purpose


Another way to think about it is that people have used Revit for decades. And when we sync to a workshared model, and reload latest, then we know that we are seeing the most current state of everything. You actively have to TRY to not see the current state of the model. This is the perspective that I would bet the industry sees the data/geometry for a speckle stream.

Honestly the way that it I see it in the NewUI , it should already be acting that way, if I choose always receive latest commit, then that is what ill be getting in rhino. So you may not really even need to change how the UI works in speckle?

I wonder if when you bring in a speckle stream that it locks those layers in Rhino by default? It would take an extra step for people to mess with it. But still let me hide individual layers

I also don’t know how you would handle it (from a tech perspective) if layers were deleted in the latest commit. I would expect for the removed layer to be removed in my Rhino model when i receive the latest commit. Maybe a warning window could popup saying something like the standard Rhino layer deletion popup that says “you are about to delete x layers with y objects and create z new layers and q new objects”?

in Revit - Another option is just writing the commit id (eg: main @ 31451b8a26] to all the imported objects to a ‘Speckle’ Parameter in ‘Identity Data’ . This alone would be a huge improvement because then i can can write a simple dynamo script to select and modify everything in that specific commit. like grouping it, adding it to a workset, deleting it, or i would be able to identify all the revit object that have a speckle parameter, and filter out everything that doesn’t match the latest commit and delete it. basically it allow me to do maintence on a model if it is needed. This would also help once we get to the end of design and we need to delete all the ‘facade’ geometry that is in Revit for refence and we replace it with native Revit geometry and families.


currently, the only connector that upon receiving takes care of updating/deleting previously received objects and geometry is the Revit one. In Rhino, AutoCAD etc the newly received geometry is instead added to a new Layer. We thought this to be the most intuitive way of handling updates, but we’d be happy to hear if instead you’d like a different behaviour.

Thanks Matteo! Super excited to finally start dabbling in Speckle and super amazed by the work you’ve done so far! With the introduction of the Sketchup connector, Speckle ecosystem can help us a lot. Keen to start using it in our firm.

Regarding the update behaviour, I personally would prefer to have both options or even a combination. Like seeing a list of changes and decide, per row, what the behaviour should be (delete & update, add, do nothing).
Sometimes I’ve received a geometry and have worked on it but I’m not ready to commit my work. If changes have happened by others on other parts of the geometry since I started, I would want to grab the latest, include it in my changes and then commit them. In this case, there are geometries that I want to see deleted and updated, and there are geometries that I don’t want to bring in. I guess the work around for now is to move my changes to another layer, receive updates, manually delete the parts that I don’t want and then change the layer of my changes and finally push everything.

BTW, is the multiplayer demo here not v2?

What happens in the background is that Specke will realize only 1 of those 3 boxes is new and in our database, only the new one will be stored. This is why you should see commits more like snapshots in time of your model rather than diffs.

Curious to know how this is handled using the existing data model? I understand we have an (Speckle) id and an applicationId (which is the object id in the application it was created in). So if I create a box in Rhino and send it, then receive it in Revit (creates a new Revit unique Id for it), and send it to the stream from Revit again with no change, will this change the applicationId and the object will be considered “changed”?

Other than breaking grasshopper referenced objects, were there any significant drawbacks? Could one programmatically reference the geometry from Speckle to tackle this? eg: hard code the commit id, receive the geometry on the spot (at run time) as opposed to select from Rhino file and save the GH script.

A post was split to a new topic: Rhino creates nested main layers when receiving

A “latest-mode” makes the most sense for those of us running analytics as the intent is a passive measurement of a single model.

In this scenario selecting a specific commit point in history would also be a cause for purge and replacement.

Although, I also agree with allowing the user to choose :point_down:t3:

I do find it weird that the default behaviour is to “add stuff” instead of replacing (Revit’s default)

We could have a per-stream setting that gets stored along with everything else. But we’d also need some editable connector “default” settings too, so user’s won’t have to change the settings on newly added streams everytime if our default doesn’t work for them.

On a side note:

@hzamani-i2c I think you may have just found a bug here :point_down:t3: I’ll pop a new thread from your original post to not have multi topic conversations in a single thread :+1:t3:


How do people in this thread feel about the following, in regards to receive behavior: adding an option in the receive panel that lets you decide whether to update existing elements or not?

By default, each connector could have pre-selected something we believe is the desired mode, and we’d let the user override it.




It’d be great to have those options! Even better would be to have a third option to decide the mode on the object level, rather than the stream level. For those who want to cherry-pick.

1 Like

I like this idea, maybe it’s time for a Speckle CLI as an advanced alternative to our DesktopUI? :thinking:
Possibly an idea for our HACKATHON :wink:

1 Like

Alright, so different receive modes are soon coming to the Revit Connector, we’ll follow implementing them where possible, here’s how they’ll work:

UPDATE: updates elements if they already exist and creates missing ones (current behaviour in Revit)
CREATE: always creates new elements even if pre-existing (current behavior in Rhino)
IGNORE: skips elements if they already exist

PS: Sorry, I know this thread is about Rhino, but that’s our next target! :slight_smile:



Great update @teocomi

As an further idea, would be nice is connector could threat separately geometry from data associated to geometry. I’m thinking in the a use case where some geometrically temporary state of an “object” is sent to a collaborator so he can fill some parameters related to that object. When the stream is coming back to me, I want to update only some “parts” of the objects, in Revit could be a bunch (not all) of parameters associated to that object, but not the geometry (shape) itself because I probably have been tweaking it while my collaborator has been doing its job.
Same behaviour could be of interest anywhere else, in a rhino scenario, there would be cases where a desirable behavior is just to update part of an object, lets say its geometry, but not other attributes of tha rhino.object, or maybe only “some” of them (keep layer, name and color, but update some user data)
I assume that for those cases grasshopper or dynamo could act as a “middleware” between streams and a particular document, so a more sophisticated/fine tunned elements/objects update can be elaborated as a script.
But I like a lot this direction of adding more options to the connectors that you guys from speckle team are curating. In fact, we certainly always can develop our own ad-hoc connectors (its open source!), but this topic seems of general interest.
So, in few words, I’m proposing to take in consideration that the connectors would have the option, in case that we are thinking on an update, to choose between geometry or/and data to be updated. Certainly the idea of “data” is very fuzzy here: i’m in particular thinking on those pieces of data not related to defining the “shape”, but the “information”. And this definition is probably ambiguous… for example, the “information” of what layers of material compose a particular wall affects its thickness/shape…

well, just thinking aloud…

in any case, congrats, a great addition this “udpate/create/ignore” feature


Thanks, good feedback here, and aligned to what @hzamani-i2c mentions above :wink:
We’ll look at what we can do!