Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Allow sending signals to specific clients #17729

Merged

Conversation

GaryWilber
Copy link
Contributor

@GaryWilber GaryWilber commented Oct 11, 2023

Description

This PR adds the ability for clients to send signals to specific clients instead of always broadcasting signals to everyone. This can be used by Loop applications to drastically reduce the number of signal packets being sent in client join scenarios, which will reduce server resource utilization.

Brief rationale behind this change:

  • Assume you have a session with 50 users and all those users clicked into a component, so they all have a presence somewhere.
  • Now a 51st user joins

Current system:

  • The existing 50 users will broadcast a signal to everyone to tell that new user where they are.
  • Those signals are broadcast to everyone in the session. The number of WebSocket packets sent out in total would be 50 * 51 = 2550

Future system that leverages this change:

  • The existing 50 users will send a signal to that specific new user to tell them where they are.
  • These signals are broadcast to only the new user, so the number of WebSocket packets sent out in total would be 50

So this change would result in a large reduction in the number of packets being sent out for that case.

Breaking Changes

  • Adding a targetClientId?: string argument to submitSignal / submitDataStoreSignal

Reviewer Guidance

  • This only applies to the odsp-driver. I focused on ODSP because:
    • This is a high priority issue as signals are very popular for us and there is a lot of throttling actively occurring in production due to signals.
    • It was more straight forward to add this to the odsp-driver now since we have an existing mechanism for enabling new client functionality via IConnect.supportedFeatures
  • R11s / AFR will need staged changes in order to support this in a non-breaking manner.

@github-actions github-actions bot added area: driver Driver related issues area: loader Loader related issues area: odsp-driver area: runtime Runtime related issues area: server Server related issues (routerlicious) public api change Changes to a public API base: main PRs targeted against main branch labels Oct 11, 2023
@github-actions github-actions bot removed the area: server Server related issues (routerlicious) label Oct 11, 2023
@msfluid-bot
Copy link
Collaborator

msfluid-bot commented Oct 11, 2023

@fluid-example/bundle-size-tests: +483 Bytes
Metric NameBaseline SizeCompare SizeSize Diff
aqueduct.js 446.47 KB 446.49 KB +20 Bytes
connectionState.js 680 Bytes 680 Bytes No change
containerRuntime.js 239.56 KB 239.58 KB +16 Bytes
loader.js 178.76 KB 178.77 KB +18 Bytes
map.js 48.06 KB 48.06 KB No change
matrix.js 141.84 KB 141.84 KB No change
odspDriver.js 90.27 KB 90.27 KB No change
odspPrefetchSnapshot.js 41.9 KB 41.9 KB No change
sharedString.js 162.75 KB 162.75 KB No change
sharedTree2.js 263.54 KB 263.54 KB No change
Total Size 1.72 MB 1.72 MB +483 Bytes

Baseline commit: 7c8cdb8

Generated by 🚫 dangerJS against c17070a

@GaryWilber GaryWilber marked this pull request as ready for review October 12, 2023 16:40
@GaryWilber GaryWilber requested review from msfluid-bot and a team as code owners October 12, 2023 16:40
public submitSignal(message: IDocumentMessage): void {
this.emitMessages("submitSignal", [[message]]);
public submitSignal(content: unknown, targetClientId?: string): void {
const signal: ISentSignalMessage = {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

where does this get unwrapped? does the server do it? i worry the change is shape won't be handles by clients. over all this needs tests

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The server will process the ISentSignalMessage's and send the signal to the specific client when specified.
The signals received by clients will look identical to how they are today - there is no breaking change / requirements for clients to all be on a new version.

};

// back-compat: the typing for this method and emitMessages is incorrect, will be fixed in a future PR
this.emitMessages("submitSignal", [signal] as any);
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

should this be [[signal]], as that is what was done before

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I currently have PUSH setup to accept a single batch of signals per submitSignal emit when the client is passing submit_signals_v2 in supportedFeature. The server typing looks like sentSignalMessages: ISentSignalMessage[] so this is correct.
It did not seem like nesting a single signal into 2 arrays was ever used / necessary, especially given that existing clients cannot currently be sent a batch of signals - the server always needs to split them up anyway.

@@ -296,8 +298,11 @@ export class OdspDocumentDeltaConnection extends DocumentDeltaConnection {
relayUserAgent: [client.details.environment, ` driverVersion:${pkgVersion}`].join(";"),
};

connectMessage.supportedFeatures = {
[feature_submit_signals_v2]: true,
};
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is there a value for client to convey this info? Just curions

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yes. Push will handle the submit_signal event differently when this feature is passed. It changes the structure of the incoming message and adds support for the targetClientId property

};

// back-compat: the typing for this method and emitMessages is incorrect, will be fixed in a future PR
this.emitMessages("submitSignal", [signal] as any);
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This change assumes PUSH can handle (auto-detect) old and new format, right?
It used to be IDocumentMessage[][], now it's {content: IDocumentMessage, targetClientId?: string}[]

I'm not sure why it was same shape as ops (essentially indicating support for some kind of batching).

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

IDocumentMessage[][] has never been the correct typing. content: IDocumentMessage is also wrong.
It should be content: unknown but I'm not going to introduce a breaking typing change in this PR to resolve this

Copy link
Contributor

@vladsud vladsud left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It looks fine to me, but we will need to open a separate item to cover it with some end-to-end tests.
Is this something that is already working on ODSP side? I can follow up with tests part probably....

@GaryWilber
Copy link
Contributor Author

It looks fine to me, but we will need to open a separate item to cover it with some end-to-end tests. Is this something that is already working on ODSP side? I can follow up with tests part probably....

Yes the ODSP side of this is ready.

@GaryWilber GaryWilber merged commit b59e8a3 into microsoft:main Oct 26, 2023
28 checks passed
@GaryWilber GaryWilber deleted the user/garywilb/sent_signal_changes branch October 26, 2023 22:46
WillieHabi added a commit that referenced this pull request Feb 5, 2024
## Description

Follow up to #17729
 
There was a missing change in this PR to add targetClientId support for
signals. Confirmed with the PR author that this was an accidental
omission.
alexvy86 pushed a commit to alexvy86/FluidFramework that referenced this pull request Feb 13, 2024
…9475)

## Description

Follow up to microsoft#17729
 
There was a missing change in this PR to add targetClientId support for
signals. Confirmed with the PR author that this was an accidental
omission.
WillieHabi added a commit that referenced this pull request Feb 14, 2024
## Description
Updating ISignalMessage to inlcude optional targetSignalid. 

This can be useful for receiving clients trying to understand the
overall approximate load on service and maybe other understanding. If
received signal has that property, then we know it wasn't broadcast to
everyone.

### FF API Council Context
I have a minor API change related to ISignalMessage. [ODSP had made
changes to allow for targeted
signals](#17729) and I
have been tasked with doing some of the follow-up work related to this.
Initially the idea was for the server to strip the targetClientId before
sending the signal message to the targeted client, however Jason and
Gary came to an agreement that it would be beneficial to leave this
information on the message, which would involve adding an optional
targetClientId member to ISignalMessage(Base). This could be useful for
receiving clients trying to understand the overall approximate load on
service and maybe other understanding. If received signal has that
property, then we know it wasn't broadcast to everyone. Thanks.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
area: driver Driver related issues area: loader Loader related issues area: odsp-driver area: runtime Runtime related issues base: main PRs targeted against main branch public api change Changes to a public API
Projects
None yet
Development

Successfully merging this pull request may close these issues.

None yet

4 participants