feat: alkcall 0.7.0 adoption (CF-006 identity alignment) — bump to 0.4.0
- BREAKING (ecosystem-coordination): alkcall bumped to 0.7.0. No type alktty touches changed shape (OpenEstablisher/OpenHandler/ Establishment/ChannelPlan identical to 0.6.0); the minor bump is for downstream lockstep, since alktty's public signatures reference alkcall types. - CF-006 alignment: the channels establisher and pump handler now take their identity from the per-call auth (alkcall 0.7 derives the dispatch-resolved opener — the same identity view the registry's ACL gate checked) instead of the captured install-time override. Behavior-identical in the per-connection-registry deployment; the ownership check and the ACL gate see the same subject in every deployment. make_tty_establisher / make_tty_open_handler drop their captured-identity parameter (both private). Verification: - cargo test: 113 passed (default), 156 passed (--all-features) - cargo clippy --all-targets -- -D warnings: clean - cargo fmt --check: clean - cargo doc --no-deps: clean - cargo check/clippy --target wasm32-unknown-unknown -D warnings: clean - cargo publish --dry-run --allow-dirty: clean
This commit is contained in:
1 parent
bc4a9b6024
commit
67cf253621
4 files changed
+53
-25
No files matched your search
+19
-20
@@ -98,10 +98,12 @@ pub const TTY_ALPN: &str = "alk/tty";
|
||||
/// the entry point (here by the registry's `AccessControl`), the
|
||||
/// ownership check is enforced once at the backend-selection point.
|
||||
///
|
||||
/// `auth` is the peer's `AuthContext`, captured at
|
||||
/// `install_channel_zero` time and closed over by the wrapper so the
|
||||
/// `TtyOpenHandler` receives it without the wrapper having to reach
|
||||
/// into `OperationContext` for it (per the ADR-047 §4 amendment).
|
||||
/// `auth` is the peer's `AuthContext`, the install-time context passed
|
||||
/// through to `register_openable_with_establisher`. The establisher
|
||||
/// and pump handler read their identity from the per-call context
|
||||
/// alkcall derives (alkcall 0.7, CF-006 corollary) — the
|
||||
/// dispatch-resolved opener, the same view the registry's ACL gate
|
||||
/// checked.
|
||||
///
|
||||
/// # Errors
|
||||
///
|
||||
@@ -117,8 +119,8 @@ pub fn register_openable(
|
||||
auth: AuthContext,
|
||||
) -> Result<(), String> {
|
||||
let spec = tty_open_spec();
|
||||
let establisher = make_tty_establisher(Arc::clone(&backends), ownership, auth.identity.clone());
|
||||
let open_handler = make_tty_open_handler(backends, auth.identity.clone());
|
||||
let establisher = make_tty_establisher(Arc::clone(&backends), ownership);
|
||||
let open_handler = make_tty_open_handler(backends);
|
||||
core.register_openable_with_establisher(
|
||||
spec,
|
||||
Some(establisher),
|
||||
@@ -239,11 +241,12 @@ pub fn tty_open_spec() -> OperationSpec {
|
||||
/// returned.
|
||||
///
|
||||
/// The `tty:open` scope gate is NOT checked here — the registry's
|
||||
/// `AccessControl` enforced it before the establisher ran (the
|
||||
/// identity view the registry checked, resolved from the connection,
|
||||
/// is the authoritative one; the establisher-side identity is only
|
||||
/// the ownership-check subject — the same split as the old
|
||||
/// handler-side check).
|
||||
/// `AccessControl` enforced it before the establisher ran. The
|
||||
/// establisher's `auth` is the per-call context (alkcall 0.7, CF-006
|
||||
/// corollary): its identity is the dispatch-resolved opener — the same
|
||||
/// identity view the registry's ACL gate checked — and is the
|
||||
/// ownership-check subject (the same split as the old handler-side
|
||||
/// check).
|
||||
///
|
||||
/// Mapping into the ADR-049 reason vocabulary (no new codes — the
|
||||
/// vocabulary is alkcall's one-way wire surface):
|
||||
@@ -275,12 +278,11 @@ pub fn tty_open_spec() -> OperationSpec {
|
||||
fn make_tty_establisher(
|
||||
backends: Arc<HashMap<String, Arc<dyn TtyBackend>>>,
|
||||
ownership: Option<Arc<dyn OwnershipProvider>>,
|
||||
identity: Option<alkcall::core::auth::Identity>,
|
||||
) -> OpenEstablisher {
|
||||
Arc::new(move |input: Value, auth: AuthContext| {
|
||||
let backends = Arc::clone(&backends);
|
||||
let ownership = ownership.clone();
|
||||
let identity = identity.clone().or_else(|| auth.identity.clone());
|
||||
let identity = auth.identity.clone();
|
||||
Box::pin(async move {
|
||||
let req: NegotiateRequest = match serde_json::from_value(input) {
|
||||
Ok(r) => r,
|
||||
@@ -388,17 +390,14 @@ impl AllocatedHandle {
|
||||
///
|
||||
/// The `tty:open` scope gate is enforced by the registry's `AccessControl`
|
||||
/// before this handler runs — the handler does not re-check it.
|
||||
fn make_tty_open_handler(
|
||||
backends: Arc<HashMap<String, Arc<dyn TtyBackend>>>,
|
||||
identity: Option<alkcall::core::auth::Identity>,
|
||||
) -> OpenHandler {
|
||||
fn make_tty_open_handler(backends: Arc<HashMap<String, Arc<dyn TtyBackend>>>) -> OpenHandler {
|
||||
Arc::new(
|
||||
move |input: Value,
|
||||
plan: Option<ChannelPlan>,
|
||||
channel_conn: Connection,
|
||||
auth: AuthContext| {
|
||||
let backends = Arc::clone(&backends);
|
||||
let identity = identity.clone().or_else(|| auth.identity.clone());
|
||||
let identity = auth.identity.clone();
|
||||
|
||||
tokio::spawn(async move {
|
||||
let req: NegotiateRequest = match serde_json::from_value(input) {
|
||||
@@ -523,7 +522,7 @@ mod tests {
|
||||
|
||||
let mut backends: HashMap<String, Arc<dyn TtyBackend>> = HashMap::new();
|
||||
backends.insert("mock".to_string(), Arc::new(MockBackend::with_exit_code(0)));
|
||||
let handler = make_tty_open_handler(Arc::new(backends), None);
|
||||
let handler = make_tty_open_handler(Arc::new(backends));
|
||||
|
||||
let task = handler(
|
||||
serde_json::json!({
|
||||
@@ -577,7 +576,7 @@ mod tests {
|
||||
ownership: Option<Arc<dyn OwnershipProvider>>,
|
||||
input: Value,
|
||||
) -> Result<Establishment, EstablishmentError> {
|
||||
let establisher = make_tty_establisher(backends, ownership, None);
|
||||
let establisher = make_tty_establisher(backends, ownership);
|
||||
establisher(input, AuthContext::anonymous(b"test")).await
|
||||
}
|
||||
|
||||
|
||||
Reference in new issue
Block a user