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

Use component method calls for multi deployer logging. #630

Merged
merged 2 commits into from
Sep 21, 2023

Conversation

ghemawat
Copy link
Collaborator

We plan to make it easier to create deployers by providing pluggable system facilities (logging for example). We will achieve this by using component method calls to communicate between a weavelet and its envelope.

This change starts us on this path by adding a logging component and changing the multi deployer to collect log entries via method calls made by the weavelet:

  1. The weavelet contains a Logger component that logs to stderr.
  2. The multi deployer has a different component multiLogger that has the same set of methods as the Logger component, but writes log entries to the multi deployer's database.
  3. This multiLogger component is made available over a unix domain socket.
  4. The multi deployer passes configuration information to the weavelet asking it to redirect calls made to the Logger component to the multiLogger component.
  5. The weavelet calls a Logger method to write log entries (though for the benefit of other deployers, it falls back to using the envelope pipe protocol if a Logger redirect is not available).

Other related improvements

The multi deplopyer could previously lose log messages since the process could exit before the log messages written to the logs database could be read and printed to stderr. We now write log messages to stderr as soon as they arrive instead of routing them through the logs database.

Other Details

  • Fix generator so it can handle components defined in the weaver package.
  • multi deployer creates a temporary directory and a unix domain socket inside it.
  • The Logger component method accepts a batch of log entries, which should help efficiency when the rate of logging is high.
  • Fixed comment with outdated example of logging output.
  • Added a list of redirects to EnvelopeInfo proto.

Added helpers

  • call.NewHandlerMap() provides a single place to register ready method.
  • FixedListener provides a call.Listener that serves a fixed set of components that are not subject to any communication graph constraints.
  • reflection.ComponentName[T] returns the name of component T.
  • codegen.Find returns registration by name.
  • dirs.NewTempDir makes a provate temporary directory.
  • logger.IsSystemGenerated determines whether a log entry is system generated.

We plan to make it easier to create deployers by providing pluggable system
facilities (logging for example). We will achieve this by using component method
calls to communicate between a weavelet and its envelope.

This change starts us on this path by adding a logging component and changing
the multi deployer to collect log entries via method calls made by the weavelet:

1. The weavelet contains a Logger component that logs to stderr.
2. The multi deployer has a different component multiLogger that has the same
   set of methods as the Logger component, but writes log entries to the multi
   deployer's database.
3. This multiLogger component is made available over a unix domain socket.
4. The multi deployer passes configuration information to the weavelet asking it
   to redirect calls made to the Logger component to the multiLogger component.
5. The weavelet calls a Logger method to write log entries (though for the
   benefit of other deployers, it falls back to using the envelope pipe protocol
   if a Logger redirect is not available).

Other related improvements
--------------------------

The multi deplopyer could previously lose log messages since the process could
exit before the log messages written to the logs database could be read and
printed to stderr. We now write log messages to stderr as soon as they arrive
instead of routing them through the logs database.

Other Details
-------------
* Fix generator so it can handle components defined in the weaver package.
* multi deployer creates a temporary directory and a unix domain socket inside it.
* The Logger component method accepts a batch of log entries, which should
  help efficiency when the rate of logging is high.
* Fixed comment with outdated example of logging output.
* Added a list of redirects to `EnvelopeInfo` proto.

Added helpers
-------------
* `call.NewHandlerMap()` provides a single place to register ready method.
* `FixedListener` provides a call.Listener that serves a fixed set of components
  that are not subject to any communication graph constraints.
* `reflection.ComponentName[T]` returns the name of component T.
* `codegen.Find` returns registration by name.
* `dirs.NewTempDir` makes a provate temporary directory.
* `logger.IsSystemGenerated` determines whether a log entry is system generated.
Copy link
Contributor

@spetrovic77 spetrovic77 left a comment

Choose a reason for hiding this comment

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

Good job fitting this in so nicely.

fp := MakeMethodKey(component, method)
hm.handlers[fp] = handler
hm.names[fp] = component + "." + method
}

// addHandlers adds handlers for all methods of the component with the
// specified name, The handlers invoke methods on the specified impl.
Copy link
Contributor

Choose a reason for hiding this comment

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

, -> .

Copy link
Collaborator Author

Choose a reason for hiding this comment

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

Done.

Addr() net.Addr
}

// FixedListener returns a listener allows all calls to supplied
Copy link
Contributor

Choose a reason for hiding this comment

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

This sentence doesn't parse.

Also, I'm not sure what listener to compare this one to, to understand what is its distinctive property. "Fixed" by itself doesn't describe that property. (I'm guessing the distinctive property is that it allows any/all clients to invoke it, without security checks.)

Copy link
Collaborator Author

Choose a reason for hiding this comment

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

Fixed sentence.

I had intended "Fixed" to mean that a fixed set of components were being served, not the dynamic set in our normal mTLS based protocol.

I am happy to adopt a different name if that helps.

In the meantime I extended the comment:

// FixedListener returns a listener that allows all calls to supplied
// components. FixedListener is intended for local system services and access
// control happens at the net.Listener level (e.g., by using Unix domain
// sockets).
//
// Note that this differs from the normal listener used for application
// components (that listener only allows component A to call component B if A
// has an edge to B in the component graph).
//
// Each components map entry has the full component name as the key, and the
// component implementation as the value.

"github.com/ServiceWeaver/weaver/runtime/protos"
)

// remoteLogger sends log entries to a specified component method.
Copy link
Contributor

Choose a reason for hiding this comment

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

specified component method dst.

Copy link
Collaborator Author

Choose a reason for hiding this comment

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

Redid comments on the type and on run().

const loggerPath = "github.com/ServiceWeaver/weaver/Logger"
r, ok := w.redirects[loggerPath]
if !ok {
// For now fall back to sending over the pipe to the weavelet.
Copy link
Contributor

Choose a reason for hiding this comment

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

Nit: comma after now

Copy link
Collaborator Author

Choose a reason for hiding this comment

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

Done.

runtime/dir.go Outdated
@@ -53,3 +53,19 @@ func DataDir() (string, error) {

return regDir, nil
}

// NewTempDir returns a new directory, e.g., to hold Unix domain sockets for
// internal communication. The new directory is not accessible by others.
Copy link
Contributor

Choose a reason for hiding this comment

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

nit: others seems too generic

Copy link
Collaborator Author

Choose a reason for hiding this comment

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

Done.

return rl
}

func (rl *remoteLogger) send(entry *protos.LogEntry) {
Copy link
Contributor

Choose a reason for hiding this comment

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

send -> log ? (since we aren't sending yet.)

Copy link
Collaborator Author

Choose a reason for hiding this comment

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

Done.

Copy link
Collaborator Author

@ghemawat ghemawat left a comment

Choose a reason for hiding this comment

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

Thanks!

fp := MakeMethodKey(component, method)
hm.handlers[fp] = handler
hm.names[fp] = component + "." + method
}

// addHandlers adds handlers for all methods of the component with the
// specified name, The handlers invoke methods on the specified impl.
Copy link
Collaborator Author

Choose a reason for hiding this comment

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

Done.

Addr() net.Addr
}

// FixedListener returns a listener allows all calls to supplied
Copy link
Collaborator Author

Choose a reason for hiding this comment

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

Fixed sentence.

I had intended "Fixed" to mean that a fixed set of components were being served, not the dynamic set in our normal mTLS based protocol.

I am happy to adopt a different name if that helps.

In the meantime I extended the comment:

// FixedListener returns a listener that allows all calls to supplied
// components. FixedListener is intended for local system services and access
// control happens at the net.Listener level (e.g., by using Unix domain
// sockets).
//
// Note that this differs from the normal listener used for application
// components (that listener only allows component A to call component B if A
// has an edge to B in the component graph).
//
// Each components map entry has the full component name as the key, and the
// component implementation as the value.

"github.com/ServiceWeaver/weaver/runtime/protos"
)

// remoteLogger sends log entries to a specified component method.
Copy link
Collaborator Author

Choose a reason for hiding this comment

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

Redid comments on the type and on run().

return rl
}

func (rl *remoteLogger) send(entry *protos.LogEntry) {
Copy link
Collaborator Author

Choose a reason for hiding this comment

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

Done.

const loggerPath = "github.com/ServiceWeaver/weaver/Logger"
r, ok := w.redirects[loggerPath]
if !ok {
// For now fall back to sending over the pipe to the weavelet.
Copy link
Collaborator Author

Choose a reason for hiding this comment

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

Done.

runtime/dir.go Outdated
@@ -53,3 +53,19 @@ func DataDir() (string, error) {

return regDir, nil
}

// NewTempDir returns a new directory, e.g., to hold Unix domain sockets for
// internal communication. The new directory is not accessible by others.
Copy link
Collaborator Author

Choose a reason for hiding this comment

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

Done.

@ghemawat ghemawat merged commit c841224 into ServiceWeaver:main Sep 21, 2023
7 checks passed
@ghemawat ghemawat deleted the logger branch September 21, 2023 16:41
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

None yet

2 participants