refactor: sync sparse tlprofile runtime
This commit is contained in:
parent
5ecf4e912d
commit
25ab04a254
93 changed files with 2983 additions and 1615 deletions
|
|
@ -12,7 +12,7 @@ import (
|
|||
"github.com/iamxvbaba/td/bin"
|
||||
"github.com/iamxvbaba/td/crypto"
|
||||
"github.com/iamxvbaba/td/proto"
|
||||
"github.com/iamxvbaba/td/tg"
|
||||
"github.com/iamxvbaba/td/tlprofile"
|
||||
"github.com/iamxvbaba/td/transport"
|
||||
)
|
||||
|
||||
|
|
@ -279,7 +279,7 @@ func (c *Conn) isPhysicalTransportCurrentOpen() bool {
|
|||
// LayerProfile returns the exact TL profile currently selected for this
|
||||
// connection. ok is false until admission or an inherited auth-key default
|
||||
// supplies a supported generated profile.
|
||||
func (c *Conn) LayerProfile() (profile tg.LayerProfile, ok bool) {
|
||||
func (c *Conn) LayerProfile() (profile tlprofile.Profile, ok bool) {
|
||||
state := c.LayerProfileState()
|
||||
return state.Profile, state.Origin != LayerProfileUnknown
|
||||
}
|
||||
|
|
@ -288,7 +288,7 @@ func (c *Conn) LayerProfile() (profile tg.LayerProfile, ok bool) {
|
|||
// admission. Repeating the same value is idempotent. A later well-formed
|
||||
// invokeWithLayer may replace either an inherited default or older explicit
|
||||
// evidence; already-admitted requests retain their own immutable profile.
|
||||
func (c *Conn) FreezeLayerProfile(profile tg.LayerProfile) error {
|
||||
func (c *Conn) FreezeLayerProfile(profile tlprofile.Profile) error {
|
||||
_, err := c.setLayerProfile(profile, LayerProfileExplicit, true)
|
||||
return err
|
||||
}
|
||||
|
|
@ -298,14 +298,14 @@ func (c *Conn) FreezeLayerProfile(profile tg.LayerProfile) error {
|
|||
// msg_id carrying another Layer is a protocol conflict. Advancing the evidence
|
||||
// cursor at an unchanged Layer does not rotate the outbound epoch because the
|
||||
// wire profile itself did not change.
|
||||
func (c *Conn) FreezeLayerProfileAt(profile tg.LayerProfile, msgID int64) (bool, error) {
|
||||
func (c *Conn) FreezeLayerProfileAt(profile tlprofile.Profile, msgID int64) (bool, error) {
|
||||
return c.freezeLayerProfileAt(profile, msgID)
|
||||
}
|
||||
|
||||
// SeedLayerProfile restores explicit evidence previously proven for this exact
|
||||
// logical session. It is kept as the compatible same-session restore API;
|
||||
// auth-key-wide metadata must use SeedInheritedLayerProfile instead.
|
||||
func (c *Conn) SeedLayerProfile(profile tg.LayerProfile) error {
|
||||
func (c *Conn) SeedLayerProfile(profile tlprofile.Profile) error {
|
||||
_, err := c.setLayerProfile(profile, LayerProfileExplicit, true)
|
||||
return err
|
||||
}
|
||||
|
|
@ -313,7 +313,7 @@ func (c *Conn) SeedLayerProfile(profile tg.LayerProfile) error {
|
|||
// SeedInheritedLayerProfile installs an auth-key-wide default only while the
|
||||
// connection is still unknown. It never overwrites explicit evidence or an
|
||||
// already selected inherited default; client protocol evidence owns correction.
|
||||
func (c *Conn) SeedInheritedLayerProfile(profile tg.LayerProfile) error {
|
||||
func (c *Conn) SeedInheritedLayerProfile(profile tlprofile.Profile) error {
|
||||
_, err := c.setLayerProfile(profile, LayerProfileInherited, false)
|
||||
return err
|
||||
}
|
||||
|
|
|
|||
|
|
@ -5,7 +5,7 @@ import (
|
|||
"fmt"
|
||||
"math"
|
||||
|
||||
"github.com/iamxvbaba/td/tg"
|
||||
"github.com/iamxvbaba/td/tlprofile"
|
||||
"go.uber.org/zap"
|
||||
)
|
||||
|
||||
|
|
@ -24,7 +24,7 @@ const (
|
|||
// profile. Epoch advances on every effective correction, including promotion
|
||||
// from inherited to explicit evidence at the same numeric layer.
|
||||
type LayerProfileSnapshot struct {
|
||||
Profile tg.LayerProfile
|
||||
Profile tlprofile.Profile
|
||||
Origin LayerProfileOrigin
|
||||
Epoch uint32
|
||||
}
|
||||
|
|
@ -49,7 +49,7 @@ func unpackLayerProfileState(raw uint64) LayerProfileSnapshot {
|
|||
return LayerProfileSnapshot{}
|
||||
}
|
||||
return LayerProfileSnapshot{
|
||||
Profile: tg.LayerProfile(raw & layerProfileValueMask),
|
||||
Profile: tlprofile.Profile(raw & layerProfileValueMask),
|
||||
Origin: LayerProfileOrigin((raw >> layerProfileOriginShift) & layerProfileOriginMask),
|
||||
Epoch: uint32(raw >> layerProfileEpochShift),
|
||||
}
|
||||
|
|
@ -63,7 +63,7 @@ func (c *Conn) LayerProfileState() LayerProfileSnapshot {
|
|||
return unpackLayerProfileState(c.layerProfileState.Load())
|
||||
}
|
||||
|
||||
func (c *Conn) setLayerProfile(profile tg.LayerProfile, origin LayerProfileOrigin, replace bool) (bool, error) {
|
||||
func (c *Conn) setLayerProfile(profile tlprofile.Profile, origin LayerProfileOrigin, replace bool) (bool, error) {
|
||||
if err := validateLayerProfile(profile); err != nil {
|
||||
return false, err
|
||||
}
|
||||
|
|
@ -104,8 +104,8 @@ func (c *Conn) setLayerProfile(profile tg.LayerProfile, origin LayerProfileOrigi
|
|||
}
|
||||
}
|
||||
|
||||
func validateLayerProfile(profile tg.LayerProfile) error {
|
||||
resolved, ok := tg.ResolveLayerProfile(int(profile))
|
||||
func validateLayerProfile(profile tlprofile.Profile) error {
|
||||
resolved, ok := tlprofile.ResolveProfile(int(profile))
|
||||
if !ok || resolved != profile || uint64(profile) > layerProfileValueMask {
|
||||
return fmt.Errorf("%w: %d", ErrLayerProfileUnsupported, profile)
|
||||
}
|
||||
|
|
@ -138,7 +138,7 @@ func (c *Conn) layerProfileRawEvidenceState() (LayerProfileSnapshot, int, int64)
|
|||
// freezeLayerProfileAt is the production explicit-evidence transition. The
|
||||
// positive client msg_id is the protocol ordering authority across TCP
|
||||
// reconnects and cached request replays.
|
||||
func (c *Conn) freezeLayerProfileAt(profile tg.LayerProfile, msgID int64) (bool, error) {
|
||||
func (c *Conn) freezeLayerProfileAt(profile tlprofile.Profile, msgID int64) (bool, error) {
|
||||
if c == nil {
|
||||
return false, fmt.Errorf("nil connection layer profile")
|
||||
}
|
||||
|
|
@ -158,7 +158,7 @@ func (c *Conn) freezeRawLayerProfileAt(layer int, msgID int64) (bool, error) {
|
|||
if layer <= 0 || msgID <= 0 {
|
||||
return false, fmt.Errorf("invalid raw layer evidence layer=%d msg_id=%d", layer, msgID)
|
||||
}
|
||||
profile, supported := tg.ResolveLayerProfile(layer)
|
||||
profile, supported := tlprofile.ResolveProfile(layer)
|
||||
c.layerProfileMu.Lock()
|
||||
defer c.layerProfileMu.Unlock()
|
||||
|
||||
|
|
@ -206,7 +206,7 @@ func (c *Conn) freezeRawLayerProfileAt(layer int, msgID int64) (bool, error) {
|
|||
|
||||
// seedOrderedLayerProfile restores exact-session evidence atomically before
|
||||
// any request on a replacement physical connection is admitted.
|
||||
func (c *Conn) seedOrderedLayerProfile(profile tg.LayerProfile, msgID int64) error {
|
||||
func (c *Conn) seedOrderedLayerProfile(profile tlprofile.Profile, msgID int64) error {
|
||||
if c == nil {
|
||||
return nil
|
||||
}
|
||||
|
|
@ -248,7 +248,7 @@ func (c *Conn) seedRawLayerEvidence(layer int, msgID int64) error {
|
|||
// auth.bindTempAuthKey: once a raw temporary key is resolved to its permanent
|
||||
// key, the permanent key's default supersedes an older raw-key shadow. Explicit
|
||||
// evidence on the concrete session is never overwritten.
|
||||
func (c *Conn) refreshInheritedLayerProfile(profile tg.LayerProfile) (bool, error) {
|
||||
func (c *Conn) refreshInheritedLayerProfile(profile tlprofile.Profile) (bool, error) {
|
||||
if c == nil {
|
||||
return false, nil
|
||||
}
|
||||
|
|
@ -339,7 +339,7 @@ func (s *Server) seedInitialLayerProfile(
|
|||
// Older in-process exact-session registries did not retain a message
|
||||
// watermark. Keep that compatibility-only seed usable without treating
|
||||
// it as durable ordered evidence; real durable stores never persist zero.
|
||||
profile, supported := tg.ResolveLayerProfile(layer)
|
||||
profile, supported := tlprofile.ResolveProfile(layer)
|
||||
if !supported {
|
||||
return nil
|
||||
}
|
||||
|
|
@ -353,7 +353,7 @@ func (s *Server) seedInitialLayerProfile(
|
|||
if msgID > 0 {
|
||||
return c.seedRawLayerEvidence(layer, msgID)
|
||||
}
|
||||
profile, supported := tg.ResolveLayerProfile(layer)
|
||||
profile, supported := tlprofile.ResolveProfile(layer)
|
||||
if !supported {
|
||||
return nil
|
||||
}
|
||||
|
|
@ -361,7 +361,7 @@ func (s *Server) seedInitialLayerProfile(
|
|||
}
|
||||
} else if resolver, ok := s.layerRPC.(LayerRPCSessionProfileResolver); ok {
|
||||
if layer, found := resolver.NegotiatedSessionLayer(c.authKeyID, c.sessionID); found {
|
||||
profile, supported := tg.ResolveLayerProfile(layer)
|
||||
profile, supported := tlprofile.ResolveProfile(layer)
|
||||
if !supported {
|
||||
return nil
|
||||
}
|
||||
|
|
@ -373,7 +373,7 @@ func (s *Server) seedInitialLayerProfile(
|
|||
// row again. Unsupported metadata remains unknown and must not fall through
|
||||
// to a weaker mirror.
|
||||
if c.authKeyExpiresAt == 0 && fetchedLayer != 0 {
|
||||
profile, supported := tg.ResolveLayerProfile(fetchedLayer)
|
||||
profile, supported := tlprofile.ResolveProfile(fetchedLayer)
|
||||
if !supported {
|
||||
return nil
|
||||
}
|
||||
|
|
@ -406,7 +406,7 @@ func (s *Server) seedInitialLayerProfile(
|
|||
// Fall through to a raw auth-key shadow when the resolver has no
|
||||
// canonical permanent-key default (for example an unbound temp key).
|
||||
} else {
|
||||
profile, supported := tg.ResolveLayerProfile(layer)
|
||||
profile, supported := tlprofile.ResolveProfile(layer)
|
||||
if !supported {
|
||||
return nil
|
||||
}
|
||||
|
|
@ -414,7 +414,7 @@ func (s *Server) seedInitialLayerProfile(
|
|||
}
|
||||
}
|
||||
if fetchedLayer != 0 {
|
||||
profile, supported := tg.ResolveLayerProfile(fetchedLayer)
|
||||
profile, supported := tlprofile.ResolveProfile(fetchedLayer)
|
||||
if !supported {
|
||||
return nil
|
||||
}
|
||||
|
|
@ -446,7 +446,7 @@ func (s *Server) refreshActivatedInheritedLayerProfile(ctx context.Context, c *C
|
|||
if fetchedLayer == 0 {
|
||||
return nil
|
||||
}
|
||||
profile, ok := tg.ResolveLayerProfile(fetchedLayer)
|
||||
profile, ok := tlprofile.ResolveProfile(fetchedLayer)
|
||||
if !ok {
|
||||
return c.clearInheritedLayerProfile()
|
||||
}
|
||||
|
|
@ -472,7 +472,7 @@ func (s *Server) refreshActivatedInheritedLayerProfile(ctx context.Context, c *C
|
|||
zap.String("auth_key_id", c.authKeyHex), zap.Error(err))
|
||||
}
|
||||
} else if found {
|
||||
profile, supported := tg.ResolveLayerProfile(layer)
|
||||
profile, supported := tlprofile.ResolveProfile(layer)
|
||||
if !supported {
|
||||
return c.clearInheritedLayerProfile()
|
||||
}
|
||||
|
|
@ -483,7 +483,7 @@ func (s *Server) refreshActivatedInheritedLayerProfile(ctx context.Context, c *C
|
|||
if fetchedLayer == 0 {
|
||||
return nil
|
||||
}
|
||||
profile, ok := tg.ResolveLayerProfile(fetchedLayer)
|
||||
profile, ok := tlprofile.ResolveProfile(fetchedLayer)
|
||||
if !ok {
|
||||
return c.clearInheritedLayerProfile()
|
||||
}
|
||||
|
|
|
|||
|
|
@ -9,6 +9,7 @@ import (
|
|||
|
||||
"github.com/iamxvbaba/td/proto"
|
||||
"github.com/iamxvbaba/td/tg"
|
||||
"github.com/iamxvbaba/td/tlprofile"
|
||||
)
|
||||
|
||||
// TestPushSkipsConnReboundToOtherUser 锁定跨账号投递窗口的修复:pushToUserWithSender 在锁外
|
||||
|
|
@ -28,7 +29,7 @@ func TestPushSkipsConnReboundToOtherUser(t *testing.T) {
|
|||
c.userID.Store(userA)
|
||||
c.userIDResolved.Store(true)
|
||||
c.receivesUpdates.Store(true)
|
||||
if err := c.FreezeLayerProfile(tg.LayerProfileCanonical); err != nil {
|
||||
if err := c.FreezeLayerProfile(tlprofile.ProfileCanonical); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
sm.Register(c)
|
||||
|
|
|
|||
|
|
@ -6,7 +6,7 @@ import (
|
|||
|
||||
"github.com/iamxvbaba/td/bin"
|
||||
"github.com/iamxvbaba/td/proto"
|
||||
"github.com/iamxvbaba/td/tg"
|
||||
"github.com/iamxvbaba/td/tlprofile"
|
||||
)
|
||||
|
||||
const (
|
||||
|
|
@ -20,8 +20,8 @@ var errDestroyAuthKeyMustBeExclusive = errors.New("wrapped destroy_auth_key must
|
|||
// wrappedDestroyAuthKeyTerminal accepts only evidence emitted by the generated
|
||||
// exact wrapper parser after it has legally reached the innermost non-API
|
||||
// terminal. It never re-parses wrapper bytes at runtime.
|
||||
func wrappedDestroyAuthKeyTerminal(err error) (*tg.LayerRPCUnknownTerminalError, bool) {
|
||||
var terminal *tg.LayerRPCUnknownTerminalError
|
||||
func wrappedDestroyAuthKeyTerminal(err error) (*tlprofile.UnknownTerminalError, bool) {
|
||||
var terminal *tlprofile.UnknownTerminalError
|
||||
if !errors.As(err, &terminal) || terminal == nil || terminal.WireID != destroyAuthKeyRequestTypeID {
|
||||
return nil, false
|
||||
}
|
||||
|
|
@ -35,7 +35,7 @@ func wrappedDestroyAuthKeyTerminal(err error) (*tg.LayerRPCUnknownTerminalError,
|
|||
// invokeWithLayer(initConnection(destroy_auth_key)); an already initialized
|
||||
// connection sends the bare service message and is classified before Layer RPC
|
||||
// admission.
|
||||
func validWrappedDestroyAuthKeyChain(terminal *tg.LayerRPCUnknownTerminalError) bool {
|
||||
func validWrappedDestroyAuthKeyChain(terminal *tlprofile.UnknownTerminalError) bool {
|
||||
if terminal == nil || terminal.WrapperCount() != 2 {
|
||||
return false
|
||||
}
|
||||
|
|
@ -44,8 +44,8 @@ func validWrappedDestroyAuthKeyChain(terminal *tg.LayerRPCUnknownTerminalError)
|
|||
return outerOK && innerOK &&
|
||||
outer.Profile() == terminal.Profile &&
|
||||
inner.Profile() == terminal.Profile &&
|
||||
outer.Semantic() == tg.LayerSemanticMethodInvokeWithLayer &&
|
||||
inner.Semantic() == tg.LayerSemanticMethodInitConnection
|
||||
outer.Semantic() == tlprofile.SemanticMethodInvokeWithLayer &&
|
||||
inner.Semantic() == tlprofile.SemanticMethodInitConnection
|
||||
}
|
||||
|
||||
type destroyAuthKeyRequest struct{}
|
||||
|
|
|
|||
|
|
@ -20,10 +20,10 @@ import (
|
|||
"github.com/iamxvbaba/td/mt"
|
||||
"github.com/iamxvbaba/td/proto"
|
||||
"github.com/iamxvbaba/td/proto/codec"
|
||||
"github.com/iamxvbaba/td/tg"
|
||||
"github.com/iamxvbaba/td/tgerr"
|
||||
"github.com/iamxvbaba/td/transport"
|
||||
|
||||
"github.com/iamxvbaba/td/tlprofile"
|
||||
"telesrv/internal/observability/dbtrace"
|
||||
"telesrv/internal/postresponse"
|
||||
"telesrv/internal/store"
|
||||
|
|
@ -701,8 +701,8 @@ func (s *Server) handleRPC(ctx context.Context, c *Conn, msgID int64, method str
|
|||
// obey the production exact-codec invariant. Admit a defensive copy using
|
||||
// the generated current profile before the legacy router consumes b.
|
||||
admissionBody := &bin.Buffer{Buf: append([]byte(nil), b.Buf...)}
|
||||
admitted, err := tg.NewServerDispatcher(nil).AdmitDefaultLayerWithLimits(
|
||||
tg.LayerProfileCanonical,
|
||||
admitted, err := tlprofile.NewDispatcher().AdmitDefault(
|
||||
tlprofile.ProfileCanonical,
|
||||
admissionBody,
|
||||
inboundLayerDecodeLimits,
|
||||
)
|
||||
|
|
|
|||
|
|
@ -16,6 +16,7 @@ import (
|
|||
"github.com/iamxvbaba/td/exchange"
|
||||
"github.com/iamxvbaba/td/proto"
|
||||
"github.com/iamxvbaba/td/tg"
|
||||
"github.com/iamxvbaba/td/tlprofile"
|
||||
"github.com/iamxvbaba/td/transport"
|
||||
)
|
||||
|
||||
|
|
@ -23,7 +24,7 @@ import (
|
|||
// by old connection-state tests. Production exact-path tests must instead call
|
||||
// FreezeLayerProfile/SeedLayerProfile with protocol evidence.
|
||||
func legacyCanonicalTestConn(t testing.TB, c *Conn) *Conn {
|
||||
return legacyLayerWireTestConn(t, c, int(tg.LayerProfileCanonical))
|
||||
return legacyLayerWireTestConn(t, c, int(tlprofile.ProfileCanonical))
|
||||
}
|
||||
|
||||
// legacyLayerWireTestConn preserves only the old tests' profile setup. It does
|
||||
|
|
@ -34,7 +35,7 @@ func legacyLayerWireTestConn(t testing.TB, c *Conn, layer int) *Conn {
|
|||
if c == nil {
|
||||
t.Fatal("nil legacy exact-layer test Conn")
|
||||
}
|
||||
profile, ok := tg.ResolveLayerProfile(layer)
|
||||
profile, ok := tlprofile.ResolveProfile(layer)
|
||||
if !ok {
|
||||
t.Fatalf("unsupported generated test Layer %d", layer)
|
||||
}
|
||||
|
|
@ -62,7 +63,6 @@ func exactTestUpdatesEncoded(t testing.TB, c *Conn, body []byte) *encodedOutboun
|
|||
typeID: tg.UpdatesTooLongTypeID,
|
||||
layer: &outboundLayerBinding{
|
||||
profile: state.Profile,
|
||||
typ: tg.LayerClassUpdatesType().Ref(),
|
||||
epoch: state.Epoch,
|
||||
},
|
||||
}
|
||||
|
|
@ -86,8 +86,7 @@ func (r *opaqueExactTestRPCResult) Encode(b *bin.Buffer) error { return r.result
|
|||
|
||||
func (r *opaqueExactTestRPCResult) exactLayerRPCResultBinding() outboundLayerBinding {
|
||||
return outboundLayerBinding{
|
||||
profile: tg.LayerProfileCanonical,
|
||||
typ: tg.LayerClassUpdatesType().Ref(),
|
||||
profile: tlprofile.ProfileCanonical,
|
||||
kind: outboundLayerBindingRequest,
|
||||
}
|
||||
}
|
||||
|
|
@ -180,7 +179,7 @@ func dialTransportOnly(t *testing.T, addr string) transport.Conn {
|
|||
// profile that a production invokeWithLayer admission would have proven. It is
|
||||
// intentionally explicit: handshake/new_session_created alone never implies a
|
||||
// TL Layer, and production push code must keep failing closed in that state.
|
||||
func freezeActiveTestSessionProfile(t *testing.T, sessions *SessionManager, authKeyID [8]byte, sessionID int64, profile tg.LayerProfile) {
|
||||
func freezeActiveTestSessionProfile(t *testing.T, sessions *SessionManager, authKeyID [8]byte, sessionID int64, profile tlprofile.Profile) {
|
||||
t.Helper()
|
||||
if sessions == nil {
|
||||
t.Fatal("freeze test session profile on nil SessionManager")
|
||||
|
|
|
|||
|
|
@ -9,10 +9,11 @@ import (
|
|||
"github.com/iamxvbaba/td/mt"
|
||||
"github.com/iamxvbaba/td/tg"
|
||||
"github.com/iamxvbaba/td/tgerr"
|
||||
"github.com/iamxvbaba/td/tlprofile"
|
||||
"go.uber.org/zap"
|
||||
)
|
||||
|
||||
var inboundLayerDecodeLimits = tg.LayerDecodeLimits{
|
||||
var inboundLayerDecodeLimits = tlprofile.Limits{
|
||||
MaxWireBytes: maxInflightRPCBytes,
|
||||
// contacts.editCloseFriends and contacts.setBlocked deliberately allow
|
||||
// 5,000 entries. Keep the coarse generated allocation ceiling above every
|
||||
|
|
@ -48,7 +49,7 @@ type layerRPCDependencySet struct {
|
|||
}
|
||||
|
||||
type layerRPCProfileEvidence struct {
|
||||
profile tg.LayerProfile
|
||||
profile tlprofile.Profile
|
||||
admissionSeq uint64
|
||||
present bool
|
||||
fresh bool
|
||||
|
|
@ -67,7 +68,7 @@ type layerRPCAdmissionCursor struct {
|
|||
evidenceMsgID int64
|
||||
}
|
||||
|
||||
func (c *layerRPCAdmissionCursor) observe(profile tg.LayerProfile, msgID int64) error {
|
||||
func (c *layerRPCAdmissionCursor) observe(profile tlprofile.Profile, msgID int64) error {
|
||||
return c.observeRaw(int(profile), msgID)
|
||||
}
|
||||
|
||||
|
|
@ -90,7 +91,7 @@ func (c *layerRPCAdmissionCursor) observeRaw(layer int, msgID int64) error {
|
|||
}
|
||||
}
|
||||
c.state = LayerProfileSnapshot{}
|
||||
if profile, supported := tg.ResolveLayerProfile(layer); supported {
|
||||
if profile, supported := tlprofile.ResolveProfile(layer); supported {
|
||||
c.state = LayerProfileSnapshot{Profile: profile, Origin: LayerProfileExplicit}
|
||||
}
|
||||
c.rawLayer = layer
|
||||
|
|
@ -136,7 +137,7 @@ func (s *Server) initialLayerRPCAdmissionCursor(ctx context.Context, c *Conn) (l
|
|||
if registryMsgID == 0 {
|
||||
if cursor.evidenceMsgID == 0 {
|
||||
cursor.state = LayerProfileSnapshot{}
|
||||
if profile, supported := tg.ResolveLayerProfile(layer); supported {
|
||||
if profile, supported := tlprofile.ResolveProfile(layer); supported {
|
||||
cursor.state = LayerProfileSnapshot{Profile: profile, Origin: LayerProfileExplicit}
|
||||
}
|
||||
cursor.rawLayer = layer
|
||||
|
|
@ -466,7 +467,7 @@ func (s *Server) prepareInboundLayerRPCBatch(ctx context.Context, c *Conn, plan
|
|||
}
|
||||
plan.rejectNewRPCOwners(indices)
|
||||
for _, index := range candidateItems {
|
||||
plan.items[index].admitted = tg.LayerRequest{}
|
||||
plan.items[index].admitted = tlprofile.Admission{}
|
||||
}
|
||||
if err := reservation.retain(nil, nil); err != nil {
|
||||
return err
|
||||
|
|
@ -534,7 +535,7 @@ func (s *Server) prepareInboundLayerRPCBatch(ctx context.Context, c *Conn, plan
|
|||
}
|
||||
plan.rewrapAliases = keptAliases
|
||||
for _, index := range candidateItems {
|
||||
plan.items[index].admitted = tg.LayerRequest{}
|
||||
plan.items[index].admitted = tlprofile.Admission{}
|
||||
}
|
||||
if err := reservation.retain(nil, nil); err != nil {
|
||||
return err
|
||||
|
|
@ -581,7 +582,7 @@ func (s *Server) prepareInboundLayerRPCBatch(ctx context.Context, c *Conn, plan
|
|||
}
|
||||
if len(specs) == 0 {
|
||||
for _, index := range candidateItems {
|
||||
plan.items[index].admitted = tg.LayerRequest{}
|
||||
plan.items[index].admitted = tlprofile.Admission{}
|
||||
}
|
||||
if err := reservation.retain(nil, nil); err != nil {
|
||||
return err
|
||||
|
|
@ -604,7 +605,7 @@ func (s *Server) prepareInboundLayerRPCBatch(ctx context.Context, c *Conn, plan
|
|||
// Tasks now own the admitted request leases. Drop the plan's value copies
|
||||
// before non-fresh reservations become reusable.
|
||||
for _, index := range candidateItems {
|
||||
plan.items[index].admitted = tg.LayerRequest{}
|
||||
plan.items[index].admitted = tlprofile.Admission{}
|
||||
}
|
||||
if err := reservation.retain(reservationIndices, specs); err != nil {
|
||||
return err
|
||||
|
|
@ -628,7 +629,7 @@ func (s *Server) acquireAdmittedLayerRPC(
|
|||
return rpcResultAcquire{}, ErrRPCResultFlightInvalid
|
||||
}
|
||||
acquire := func() (rpcResultAcquire, error) {
|
||||
profile := tg.LayerProfile(0)
|
||||
profile := tlprofile.Profile(0)
|
||||
if effective, known := item.admitted.EffectiveProfile(); known {
|
||||
profile = effective
|
||||
}
|
||||
|
|
@ -671,7 +672,7 @@ func (s *Server) acquireAdmittedLayerRPC(
|
|||
return acquire()
|
||||
}
|
||||
|
||||
func (s *Server) prepareAdmittedLayerRPCReplay(ctx context.Context, c *Conn, msgID int64, admissionSeq uint64, profileEvidenceFresh bool, request tg.LayerRequest) (func() error, error) {
|
||||
func (s *Server) prepareAdmittedLayerRPCReplay(ctx context.Context, c *Conn, msgID int64, admissionSeq uint64, profileEvidenceFresh bool, request tlprofile.Admission) (func() error, error) {
|
||||
preparer, ok := s.layerRPC.(LayerRPCReplayPreparer)
|
||||
if !ok || c == nil {
|
||||
return nil, nil
|
||||
|
|
@ -703,26 +704,26 @@ func (s *Server) withLayerRPCProfileEvidenceFresh(ctx context.Context, fresh boo
|
|||
// admitInboundLayerRPC is the force-style compatibility entry point used by
|
||||
// focused tests and old embedders. Production must call admitInboundLayerRPCAt
|
||||
// with the real inner MTProto client msg_id.
|
||||
func (s *Server) admitInboundLayerRPC(c *Conn, body []byte) (tg.LayerRequest, string, error) {
|
||||
func (s *Server) admitInboundLayerRPC(c *Conn, body []byte) (tlprofile.Admission, string, error) {
|
||||
return s.admitInboundLayerRPCAt(c, 0, body)
|
||||
}
|
||||
|
||||
func (s *Server) admitInboundLayerRPCAt(c *Conn, msgID int64, body []byte) (tg.LayerRequest, string, error) {
|
||||
func (s *Server) admitInboundLayerRPCAt(c *Conn, msgID int64, body []byte) (tlprofile.Admission, string, error) {
|
||||
if s == nil || s.layerRPC == nil || c == nil || len(body) < bin.Word {
|
||||
return tg.LayerRequest{}, "unknown", fmt.Errorf("invalid exact RPC admission input")
|
||||
return tlprofile.Admission{}, "unknown", fmt.Errorf("invalid exact RPC admission input")
|
||||
}
|
||||
request, method, err := s.decodeInboundLayerRPC(c.LayerProfileState(), body)
|
||||
if err != nil {
|
||||
return tg.LayerRequest{}, method, err
|
||||
return tlprofile.Admission{}, method, err
|
||||
}
|
||||
if profile, hasEvidence := request.ProfileEvidence(); hasEvidence {
|
||||
if _, err := s.commitLayerProfileEvidence(context.Background(), c, profile, msgID); err != nil {
|
||||
if !isLayerEvidenceDurabilityUnavailable(err) {
|
||||
return tg.LayerRequest{}, method, err
|
||||
return tlprofile.Admission{}, method, err
|
||||
}
|
||||
if msgID > 0 {
|
||||
if _, localErr := c.freezeLayerProfileAt(profile, msgID); localErr != nil {
|
||||
return tg.LayerRequest{}, method, localErr
|
||||
return tlprofile.Admission{}, method, localErr
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -737,8 +738,8 @@ func (s *Server) admitInboundLayerRPCAt(c *Conn, msgID int64, body []byte) (tg.L
|
|||
// constructed, so the bounded fallback walks only transparent wrapper prefixes
|
||||
// whose query offset is fixed and allocation-free.
|
||||
func layerRPCAdmissionHasExplicitSelector(body []byte, admissionErr error) bool {
|
||||
var codecErr *tg.LayerCodecError
|
||||
if errors.As(admissionErr, &codecErr) && codecErr.Semantic == tg.LayerSemanticMethodInvokeWithLayer {
|
||||
var codecErr *tlprofile.LayerCodecError
|
||||
if errors.As(admissionErr, &codecErr) && codecErr.Semantic == tlprofile.SemanticMethodInvokeWithLayer {
|
||||
return true
|
||||
}
|
||||
|
||||
|
|
@ -784,13 +785,13 @@ func layerRPCAdmissionHasExplicitSelector(body []byte, admissionErr error) bool
|
|||
// it with a wire-ordered provisional profile cursor, then publishes explicit
|
||||
// evidence only after the full request identity has acquired an owner (or a
|
||||
// genuine new-msg_id rewrap alias).
|
||||
func (s *Server) decodeInboundLayerRPC(state LayerProfileSnapshot, body []byte) (tg.LayerRequest, string, error) {
|
||||
func (s *Server) decodeInboundLayerRPC(state LayerProfileSnapshot, body []byte) (tlprofile.Admission, string, error) {
|
||||
if s == nil || s.layerRPC == nil || len(body) < bin.Word {
|
||||
return tg.LayerRequest{}, "unknown", fmt.Errorf("invalid exact RPC admission input")
|
||||
return tlprofile.Admission{}, "unknown", fmt.Errorf("invalid exact RPC admission input")
|
||||
}
|
||||
b := &bin.Buffer{Buf: body}
|
||||
var (
|
||||
request tg.LayerRequest
|
||||
request tlprofile.Admission
|
||||
err error
|
||||
)
|
||||
if state.Origin != LayerProfileUnknown {
|
||||
|
|
@ -806,19 +807,19 @@ func (s *Server) decodeInboundLayerRPC(state LayerProfileSnapshot, body []byte)
|
|||
}
|
||||
method := "unknown"
|
||||
if err == nil {
|
||||
_, method, _ = tg.LayerSemanticName(request.Call().Method())
|
||||
_, method, _ = tlprofile.SemanticName(request.Call().Method())
|
||||
if b.Len() != 0 {
|
||||
return tg.LayerRequest{}, method, fmt.Errorf("exact RPC admission left %d bytes", b.Len())
|
||||
return tlprofile.Admission{}, method, fmt.Errorf("exact RPC admission left %d bytes", b.Len())
|
||||
}
|
||||
if effective, known := request.EffectiveProfile(); known && effective != request.Call().Profile() {
|
||||
return tg.LayerRequest{}, method, fmt.Errorf("%w: effective profile %d differs from call profile %d", ErrLayerProfileConflict, effective, request.Call().Profile())
|
||||
return tlprofile.Admission{}, method, fmt.Errorf("%w: effective profile %d differs from call profile %d", ErrLayerProfileConflict, effective, request.Call().Profile())
|
||||
}
|
||||
// A generated invariant terminal may use canonical decoding internally
|
||||
// before the client declares a layer. Only explicit invokeWithLayer (or the
|
||||
// strict compatibility fallback above) publishes new profile evidence.
|
||||
if profile, hasEvidence := request.ProfileEvidence(); hasEvidence {
|
||||
if profile != request.Call().Profile() {
|
||||
return tg.LayerRequest{}, method, fmt.Errorf("%w: generated profile evidence %d differs from call profile %d", ErrLayerProfileConflict, profile, request.Call().Profile())
|
||||
return tlprofile.Admission{}, method, fmt.Errorf("%w: generated profile evidence %d differs from call profile %d", ErrLayerProfileConflict, profile, request.Call().Profile())
|
||||
}
|
||||
}
|
||||
return request, method, nil
|
||||
|
|
@ -834,9 +835,9 @@ func (s *Server) decodeInboundLayerRPC(state LayerProfileSnapshot, body []byte)
|
|||
if id, peekErr := (&bin.Buffer{Buf: body}).PeekID(); peekErr == nil {
|
||||
method = s.typeName(id)
|
||||
}
|
||||
if codecErr := new(tg.LayerCodecError); errors.As(err, &codecErr) {
|
||||
if codecErr := new(tlprofile.LayerCodecError); errors.As(err, &codecErr) {
|
||||
if codecErr.Semantic != 0 {
|
||||
if _, semanticMethod, ok := tg.LayerSemanticName(codecErr.Semantic); ok && semanticMethod != "" {
|
||||
if _, semanticMethod, ok := tlprofile.SemanticName(codecErr.Semantic); ok && semanticMethod != "" {
|
||||
method = semanticMethod
|
||||
}
|
||||
} else if codecErr.WireID != 0 {
|
||||
|
|
@ -846,7 +847,7 @@ func (s *Server) decodeInboundLayerRPC(state LayerProfileSnapshot, body []byte)
|
|||
method = s.typeName(codecErr.WireID)
|
||||
}
|
||||
}
|
||||
if errors.Is(err, tg.ErrLayerUnknownRPCMethod) && s.log != nil {
|
||||
if errors.Is(err, tlprofile.ErrUnknownRPCMethod) && s.log != nil {
|
||||
if terminal, recognized := wrappedDestroyAuthKeyTerminal(err); recognized {
|
||||
method = "destroy_auth_key"
|
||||
s.log.Debug("Generated wrapper admission exposed MTProto service terminal",
|
||||
|
|
@ -860,7 +861,7 @@ func (s *Server) decodeInboundLayerRPC(state LayerProfileSnapshot, body []byte)
|
|||
zap.String("method", method), zap.Error(err))
|
||||
}
|
||||
}
|
||||
return tg.LayerRequest{}, method, err
|
||||
return tlprofile.Admission{}, method, err
|
||||
}
|
||||
|
||||
// commitLayerProfileEvidence publishes one generated invokeWithLayer proof.
|
||||
|
|
@ -868,7 +869,7 @@ func (s *Server) decodeInboundLayerRPC(state LayerProfileSnapshot, body []byte)
|
|||
// point; the Conn cursor then prevents a concurrent older admission from
|
||||
// overwriting its local wire epoch. Older cached duplicates remain decodable
|
||||
// and request-bound, but cannot mutate session/profile state.
|
||||
func (s *Server) commitLayerProfileEvidence(ctx context.Context, c *Conn, profile tg.LayerProfile, msgID int64) (bool, error) {
|
||||
func (s *Server) commitLayerProfileEvidence(ctx context.Context, c *Conn, profile tlprofile.Profile, msgID int64) (bool, error) {
|
||||
if s == nil || c == nil {
|
||||
return false, fmt.Errorf("invalid layer profile evidence target")
|
||||
}
|
||||
|
|
@ -890,7 +891,7 @@ func (s *Server) commitLayerProfileEvidence(ctx context.Context, c *Conn, profil
|
|||
} else if _, err := c.freezeRawLayerProfileAt(layer, authoritativeMsgID); err != nil {
|
||||
return false, err
|
||||
}
|
||||
authoritative, supported := tg.ResolveLayerProfile(layer)
|
||||
authoritative, supported := tlprofile.ResolveProfile(layer)
|
||||
return supported && authoritative == profile && authoritativeMsgID == msgID && publishShared, nil
|
||||
}
|
||||
if registry, ok := s.layerRPC.(LayerRPCOrderedSessionProfileRegistry); ok {
|
||||
|
|
@ -909,7 +910,7 @@ func (s *Server) commitLayerProfileEvidence(ctx context.Context, c *Conn, profil
|
|||
if !found || authoritativeMsgID <= 0 {
|
||||
return false, fmt.Errorf("%w: ordered exact session evidence disappeared after commit", ErrLayerProfileConflict)
|
||||
}
|
||||
authoritative, supported := tg.ResolveLayerProfile(layer)
|
||||
authoritative, supported := tlprofile.ResolveProfile(layer)
|
||||
if s.conns != nil {
|
||||
if _, err := s.conns.ApplyOrderedRawLayerForSession(c, c.authKeyID, c.sessionID, layer, authoritativeMsgID); err != nil {
|
||||
return false, err
|
||||
|
|
@ -980,34 +981,34 @@ func layerRPCAdmissionError(err error) *mt.RPCError {
|
|||
if errors.Is(err, errDefaultLayerAdmission) {
|
||||
return &mt.RPCError{ErrorCode: 400, ErrorMessage: "CONNECTION_LAYER_INVALID"}
|
||||
}
|
||||
if errors.Is(err, tg.ErrLayerProfileRequired) {
|
||||
if errors.Is(err, tlprofile.ErrProfileRequired) {
|
||||
return &mt.RPCError{ErrorCode: 400, ErrorMessage: "CONNECTION_NOT_INITED"}
|
||||
}
|
||||
var rpcErr *tgerr.Error
|
||||
if errors.As(err, &rpcErr) {
|
||||
return &mt.RPCError{ErrorCode: rpcErr.Code, ErrorMessage: rpcErr.Message}
|
||||
}
|
||||
if errors.Is(err, tg.ErrLayerUnknownRPCMethod) {
|
||||
if errors.Is(err, tlprofile.ErrUnknownRPCMethod) {
|
||||
return &mt.RPCError{ErrorCode: 501, ErrorMessage: "NOT_IMPLEMENTED"}
|
||||
}
|
||||
return &mt.RPCError{ErrorCode: 400, ErrorMessage: "INPUT_REQUEST_INVALID"}
|
||||
}
|
||||
|
||||
func (s *Server) layerRPCDependencies(c *Conn, msgID int64, request tg.LayerRequest) layerRPCDependencySet {
|
||||
func (s *Server) layerRPCDependencies(c *Conn, msgID int64, request tlprofile.Admission) layerRPCDependencySet {
|
||||
result := layerRPCDependencySet{}
|
||||
seen := make(map[int64]struct{})
|
||||
for index := 0; index < request.WrapperCount(); index++ {
|
||||
wrapper, _ := request.Wrapper(index)
|
||||
var ids []int64
|
||||
switch wrapper.Semantic() {
|
||||
case tg.LayerSemanticMethodInvokeAfterMsg:
|
||||
case tlprofile.SemanticMethodInvokeAfterMsg:
|
||||
id, err := layerRPCWrapperRequired[int64](wrapper, "msg_id")
|
||||
if err != nil {
|
||||
result.failed = true
|
||||
continue
|
||||
}
|
||||
ids = []int64{id}
|
||||
case tg.LayerSemanticMethodInvokeAfterMsgs:
|
||||
case tlprofile.SemanticMethodInvokeAfterMsgs:
|
||||
var err error
|
||||
ids, err = layerRPCWrapperRequired[[]int64](wrapper, "msg_ids")
|
||||
if err != nil || len(ids) > maxLayerRPCDependencyIDs {
|
||||
|
|
@ -1045,16 +1046,16 @@ func (s *Server) layerRPCDependencies(c *Conn, msgID int64, request tg.LayerRequ
|
|||
return result
|
||||
}
|
||||
|
||||
func admittedRPCRewrapInit(request tg.LayerRequest) (rpcRewrapInit, bool) {
|
||||
func admittedRPCRewrapInit(request tlprofile.Admission) (rpcRewrapInit, bool) {
|
||||
if request.WrapperCount() != 2 {
|
||||
return rpcRewrapInit{}, false
|
||||
}
|
||||
layerWrapper, ok := request.Wrapper(0)
|
||||
if !ok || layerWrapper.Semantic() != tg.LayerSemanticMethodInvokeWithLayer {
|
||||
if !ok || layerWrapper.Semantic() != tlprofile.SemanticMethodInvokeWithLayer {
|
||||
return rpcRewrapInit{}, false
|
||||
}
|
||||
initWrapper, ok := request.Wrapper(1)
|
||||
if !ok || initWrapper.Semantic() != tg.LayerSemanticMethodInitConnection {
|
||||
if !ok || initWrapper.Semantic() != tlprofile.SemanticMethodInitConnection {
|
||||
return rpcRewrapInit{}, false
|
||||
}
|
||||
layer, err := layerRPCWrapperRequired[int](layerWrapper, "layer")
|
||||
|
|
@ -1095,7 +1096,7 @@ func admittedRPCRewrapInit(request tg.LayerRequest) (rpcRewrapInit, bool) {
|
|||
}, true
|
||||
}
|
||||
|
||||
func layerRPCWrapperRequired[T any](wrapper tg.LayerRPCWrapper, name string) (T, error) {
|
||||
func layerRPCWrapperRequired[T any](wrapper tlprofile.Wrapper, name string) (T, error) {
|
||||
var zero T
|
||||
value, present, ok, err := wrapper.Value(name)
|
||||
if err != nil || !ok || !present {
|
||||
|
|
|
|||
|
|
@ -4,6 +4,7 @@ import (
|
|||
"context"
|
||||
"errors"
|
||||
"fmt"
|
||||
"strings"
|
||||
"sync"
|
||||
"sync/atomic"
|
||||
"testing"
|
||||
|
|
@ -15,6 +16,7 @@ import (
|
|||
"github.com/iamxvbaba/td/tg"
|
||||
"go.uber.org/zap/zaptest"
|
||||
|
||||
"github.com/iamxvbaba/td/tlprofile"
|
||||
"telesrv/internal/rpc"
|
||||
"telesrv/internal/store"
|
||||
"telesrv/internal/store/memory"
|
||||
|
|
@ -29,17 +31,17 @@ func exactLayerRPCBody(t *testing.T, request bin.Encoder) []byte {
|
|||
return body.Copy()
|
||||
}
|
||||
|
||||
func exactOutboundLayerRPCBody(t *testing.T, profile tg.LayerProfile, request bin.Object) []byte {
|
||||
func exactOutboundLayerRPCBody(t *testing.T, profile tlprofile.Profile, request bin.Object) []byte {
|
||||
t.Helper()
|
||||
outbound, err := tg.PrepareLayerOutboundCall(profile, request)
|
||||
if err != nil {
|
||||
var body bin.Buffer
|
||||
if err := tlprofile.EncodeObject(profile, request, &body); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
return exactLayerRPCBody(t, outbound)
|
||||
return body.Copy()
|
||||
}
|
||||
|
||||
type admissionOnlyLayerRPC struct {
|
||||
dispatcher *tg.ServerDispatcher
|
||||
dispatcher *tlprofile.Dispatcher
|
||||
mu sync.Mutex
|
||||
published []publishedLayerEvidence
|
||||
}
|
||||
|
|
@ -128,8 +130,8 @@ func (s unavailableEdgeSessionLayerStore) DeleteExpiredSessionLayers(context.Con
|
|||
type dispatchProfileCaptureRouter struct {
|
||||
*rpc.Router
|
||||
mu sync.Mutex
|
||||
requestProfile tg.LayerProfile
|
||||
resultProfile tg.LayerProfile
|
||||
requestProfile tlprofile.Profile
|
||||
resultProfile tlprofile.Profile
|
||||
}
|
||||
|
||||
func (h *dispatchProfileCaptureRouter) DispatchAdmitted(
|
||||
|
|
@ -138,8 +140,8 @@ func (h *dispatchProfileCaptureRouter) DispatchAdmitted(
|
|||
sessionID int64,
|
||||
msgID int64,
|
||||
admissionSeq uint64,
|
||||
request tg.LayerRequest,
|
||||
) (tg.LayerRPCResult, string, error) {
|
||||
request tlprofile.Admission,
|
||||
) (tlprofile.Result, string, error) {
|
||||
result, method, err := h.Router.DispatchAdmitted(ctx, authKeyID, sessionID, msgID, admissionSeq, request)
|
||||
h.mu.Lock()
|
||||
h.requestProfile = request.Call().Profile()
|
||||
|
|
@ -150,7 +152,7 @@ func (h *dispatchProfileCaptureRouter) DispatchAdmitted(
|
|||
return result, method, err
|
||||
}
|
||||
|
||||
func (h *dispatchProfileCaptureRouter) profiles() (tg.LayerProfile, tg.LayerProfile) {
|
||||
func (h *dispatchProfileCaptureRouter) profiles() (tlprofile.Profile, tlprofile.Profile) {
|
||||
h.mu.Lock()
|
||||
defer h.mu.Unlock()
|
||||
return h.requestProfile, h.resultProfile
|
||||
|
|
@ -189,7 +191,7 @@ func (h *capacityAdmissionOnlyLayerRPC) FreezeNegotiatedSessionLayerAt([8]byte,
|
|||
type replayProfileCaptureLayerRPC struct {
|
||||
*admissionOnlyLayerRPC
|
||||
mu sync.Mutex
|
||||
profiles []tg.LayerProfile
|
||||
profiles []tlprofile.Profile
|
||||
known []bool
|
||||
}
|
||||
|
||||
|
|
@ -199,7 +201,7 @@ func (h *replayProfileCaptureLayerRPC) PrepareAdmittedReplay(
|
|||
_ int64,
|
||||
_ int64,
|
||||
_ uint64,
|
||||
request tg.LayerRequest,
|
||||
request tlprofile.Admission,
|
||||
) (func() error, error) {
|
||||
profile, known := request.EffectiveProfile()
|
||||
h.mu.Lock()
|
||||
|
|
@ -209,14 +211,14 @@ func (h *replayProfileCaptureLayerRPC) PrepareAdmittedReplay(
|
|||
return nil, nil
|
||||
}
|
||||
|
||||
func (h *replayProfileCaptureLayerRPC) capturedProfiles() ([]tg.LayerProfile, []bool) {
|
||||
func (h *replayProfileCaptureLayerRPC) capturedProfiles() ([]tlprofile.Profile, []bool) {
|
||||
h.mu.Lock()
|
||||
defer h.mu.Unlock()
|
||||
return append([]tg.LayerProfile(nil), h.profiles...), append([]bool(nil), h.known...)
|
||||
return append([]tlprofile.Profile(nil), h.profiles...), append([]bool(nil), h.known...)
|
||||
}
|
||||
|
||||
func newAdmissionOnlyLayerRPC() *admissionOnlyLayerRPC {
|
||||
return &admissionOnlyLayerRPC{dispatcher: tg.NewServerDispatcher(nil)}
|
||||
return &admissionOnlyLayerRPC{dispatcher: tlprofile.NewDispatcher()}
|
||||
}
|
||||
|
||||
func newOrderedAdmissionOnlyLayerRPC() *orderedAdmissionOnlyLayerRPC {
|
||||
|
|
@ -259,19 +261,19 @@ func (h *orderedAdmissionOnlyLayerRPC) FreezeNegotiatedSessionLayerAt(authKeyID
|
|||
return true, nil
|
||||
}
|
||||
|
||||
func (h *admissionOnlyLayerRPC) AdmitLayer(profile tg.LayerProfile, b *bin.Buffer, limits tg.LayerDecodeLimits) (tg.LayerRequest, error) {
|
||||
return h.dispatcher.AdmitLayerWithLimits(profile, b, limits)
|
||||
func (h *admissionOnlyLayerRPC) AdmitLayer(profile tlprofile.Profile, b *bin.Buffer, limits tlprofile.Limits) (tlprofile.Admission, error) {
|
||||
return h.dispatcher.Admit(profile, b, limits)
|
||||
}
|
||||
|
||||
func (h *admissionOnlyLayerRPC) AdmitDefaultLayer(profile tg.LayerProfile, b *bin.Buffer, limits tg.LayerDecodeLimits) (tg.LayerRequest, error) {
|
||||
return h.dispatcher.AdmitDefaultLayerWithLimits(profile, b, limits)
|
||||
func (h *admissionOnlyLayerRPC) AdmitDefaultLayer(profile tlprofile.Profile, b *bin.Buffer, limits tlprofile.Limits) (tlprofile.Admission, error) {
|
||||
return h.dispatcher.AdmitDefault(profile, b, limits)
|
||||
}
|
||||
|
||||
func (h *admissionOnlyLayerRPC) AdmitUnprofiled(b *bin.Buffer, limits tg.LayerDecodeLimits) (tg.LayerRequest, error) {
|
||||
return h.dispatcher.AdmitUnprofiledWithLimits(b, limits)
|
||||
func (h *admissionOnlyLayerRPC) AdmitUnprofiled(b *bin.Buffer, limits tlprofile.Limits) (tlprofile.Admission, error) {
|
||||
return h.dispatcher.AdmitUnprofiled(b, limits)
|
||||
}
|
||||
|
||||
func (*admissionOnlyLayerRPC) DispatchAdmitted(context.Context, [8]byte, int64, int64, uint64, tg.LayerRequest) (tg.LayerRPCResult, string, error) {
|
||||
func (*admissionOnlyLayerRPC) DispatchAdmitted(context.Context, [8]byte, int64, int64, uint64, tlprofile.Admission) (tlprofile.Result, string, error) {
|
||||
return nil, "", fmt.Errorf("admission-only handler")
|
||||
}
|
||||
|
||||
|
|
@ -302,7 +304,7 @@ func (h *admissionOnlyLayerRPC) publications() []publishedLayerEvidence {
|
|||
func TestNestedExplicitLayerAdmissionErrorsAreNotDefaultFailures(t *testing.T) {
|
||||
handler := newAdmissionOnlyLayerRPC()
|
||||
s := New(Options{DC: 2, LayerRPC: handler})
|
||||
state := LayerProfileSnapshot{Profile: tg.LayerProfile227, Origin: LayerProfileInherited}
|
||||
state := LayerProfileSnapshot{Profile: tlprofile.Profile227, Origin: LayerProfileInherited}
|
||||
|
||||
unsupported := exactLayerRPCBody(t, &tg.InvokeAfterMsgRequest{
|
||||
MsgID: 1,
|
||||
|
|
@ -334,12 +336,11 @@ func TestNestedExplicitLayerAdmissionErrorsAreNotDefaultFailures(t *testing.T) {
|
|||
malformedSelectedQuery.PutID(tg.MessagesGetHistoryRequestTypeID)
|
||||
|
||||
for _, test := range []struct {
|
||||
name string
|
||||
body []byte
|
||||
wantSemantic bool
|
||||
name string
|
||||
body []byte
|
||||
}{
|
||||
{name: "unsupported", body: unsupported, wantSemantic: true},
|
||||
{name: "conflict", body: conflict, wantSemantic: true},
|
||||
{name: "unsupported", body: unsupported},
|
||||
{name: "conflict", body: conflict},
|
||||
{name: "truncated_selector", body: truncatedSelector.Copy()},
|
||||
{name: "malformed_selected_query", body: malformedSelectedQuery.Copy()},
|
||||
} {
|
||||
|
|
@ -351,10 +352,14 @@ func TestNestedExplicitLayerAdmissionErrorsAreNotDefaultFailures(t *testing.T) {
|
|||
if errors.Is(err, errDefaultLayerAdmission) {
|
||||
t.Fatalf("explicit admission was misclassified as stale default: %v", err)
|
||||
}
|
||||
if test.wantSemantic {
|
||||
var codecErr *tg.LayerCodecError
|
||||
if !errors.As(err, &codecErr) || codecErr.Semantic != tg.LayerSemanticMethodInvokeWithLayer {
|
||||
t.Fatalf("explicit error semantic = %#v, err=%v", codecErr, err)
|
||||
switch test.name {
|
||||
case "unsupported":
|
||||
if !strings.Contains(err.Error(), "unsupported exact profile 229") {
|
||||
t.Fatalf("unsupported selector error = %v", err)
|
||||
}
|
||||
case "conflict":
|
||||
if !errors.Is(err, tlprofile.ErrProfileConflict) {
|
||||
t.Fatalf("conflicting selector error = %v", err)
|
||||
}
|
||||
}
|
||||
})
|
||||
|
|
@ -376,7 +381,7 @@ func TestBatchProvisionalCursorKeepsRegistryWatermarkAcrossOldReplay(t *testing.
|
|||
t.Fatal(err)
|
||||
}
|
||||
c := &Conn{authKeyID: authKeyID, sessionID: sessionID, metrics: NopMetrics{}}
|
||||
if err := c.SeedInheritedLayerProfile(tg.LayerProfile225); err != nil {
|
||||
if err := c.SeedInheritedLayerProfile(tlprofile.Profile225); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
c.startInboundRPCScheduler(s.rpcScheduler, 1, 8, time.Second)
|
||||
|
|
@ -384,7 +389,7 @@ func TestBatchProvisionalCursorKeepsRegistryWatermarkAcrossOldReplay(t *testing.
|
|||
|
||||
oldBody := exactLayerRPCBody(t, &tg.InvokeWithLayerRequest{Layer: 225, Query: &tg.HelpGetConfigRequest{}})
|
||||
oldAdmitted, _, err := s.decodeInboundLayerRPC(
|
||||
LayerProfileSnapshot{Profile: tg.LayerProfile225, Origin: LayerProfileExplicit}, oldBody,
|
||||
LayerProfileSnapshot{Profile: tlprofile.Profile225, Origin: LayerProfileExplicit}, oldBody,
|
||||
)
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
|
|
@ -398,7 +403,7 @@ func TestBatchProvisionalCursorKeepsRegistryWatermarkAcrossOldReplay(t *testing.
|
|||
oldClaim.owner.CompleteExecution(true)
|
||||
s.rpcResults.Put(authKeyID, sessionID, 100, &encodedOutboundMessage{body: []byte{1}, reqMsgID: 100})
|
||||
|
||||
nakedBody := exactOutboundLayerRPCBody(t, tg.LayerProfile227, &tg.MessagesGetHistoryRequest{
|
||||
nakedBody := exactOutboundLayerRPCBody(t, tlprofile.Profile227, &tg.MessagesGetHistoryRequest{
|
||||
Peer: &tg.InputPeerSelf{}, Limit: 1,
|
||||
})
|
||||
plan := &inboundPlan{items: []inboundItem{
|
||||
|
|
@ -412,7 +417,7 @@ func TestBatchProvisionalCursorKeepsRegistryWatermarkAcrossOldReplay(t *testing.
|
|||
if plan.items[0].kind != inboundItemReplayRPC {
|
||||
t.Fatalf("old explicit item kind=%d, want completed replay", plan.items[0].kind)
|
||||
}
|
||||
if profile, ok := s.rpcResults.ExactAdmissionProfile(authKeyID, sessionID, 108); !ok || profile != tg.LayerProfile227 {
|
||||
if profile, ok := s.rpcResults.ExactAdmissionProfile(authKeyID, sessionID, 108); !ok || profile != tlprofile.Profile227 {
|
||||
t.Fatalf("following naked admission profile = (%d,%v), want registry Layer 227", profile, ok)
|
||||
}
|
||||
}
|
||||
|
|
@ -423,7 +428,7 @@ func TestBatchProvisionalCursorUsesPendingNewerExplicitEvidence(t *testing.T) {
|
|||
authKeyID := [8]byte{0x31, 0x02}
|
||||
const sessionID = int64(3102)
|
||||
c := &Conn{authKeyID: authKeyID, sessionID: sessionID, metrics: NopMetrics{}}
|
||||
if err := c.seedOrderedLayerProfile(tg.LayerProfile225, 100); err != nil {
|
||||
if err := c.seedOrderedLayerProfile(tlprofile.Profile225, 100); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
c.startInboundRPCScheduler(s.rpcScheduler, 1, 8, time.Second)
|
||||
|
|
@ -431,7 +436,7 @@ func TestBatchProvisionalCursorUsesPendingNewerExplicitEvidence(t *testing.T) {
|
|||
|
||||
explicitBody := exactLayerRPCBody(t, &tg.InvokeWithLayerRequest{Layer: 227, Query: &tg.HelpGetConfigRequest{}})
|
||||
explicit, _, err := s.decodeInboundLayerRPC(
|
||||
LayerProfileSnapshot{Profile: tg.LayerProfile227, Origin: LayerProfileExplicit}, explicitBody,
|
||||
LayerProfileSnapshot{Profile: tlprofile.Profile227, Origin: LayerProfileExplicit}, explicitBody,
|
||||
)
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
|
|
@ -444,7 +449,7 @@ func TestBatchProvisionalCursorUsesPendingNewerExplicitEvidence(t *testing.T) {
|
|||
}
|
||||
defer pending.owner.Abort()
|
||||
|
||||
nakedBody := exactOutboundLayerRPCBody(t, tg.LayerProfile227, &tg.MessagesGetHistoryRequest{
|
||||
nakedBody := exactOutboundLayerRPCBody(t, tlprofile.Profile227, &tg.MessagesGetHistoryRequest{
|
||||
Peer: &tg.InputPeerSelf{}, Limit: 1,
|
||||
})
|
||||
plan := &inboundPlan{items: []inboundItem{
|
||||
|
|
@ -458,10 +463,10 @@ func TestBatchProvisionalCursorUsesPendingNewerExplicitEvidence(t *testing.T) {
|
|||
if plan.items[0].kind != inboundItemRewrappedRPC {
|
||||
t.Fatalf("pending explicit item kind=%d, want pending replay", plan.items[0].kind)
|
||||
}
|
||||
if profile, ok := s.rpcResults.ExactAdmissionProfile(authKeyID, sessionID, 108); !ok || profile != tg.LayerProfile227 {
|
||||
if profile, ok := s.rpcResults.ExactAdmissionProfile(authKeyID, sessionID, 108); !ok || profile != tlprofile.Profile227 {
|
||||
t.Fatalf("following naked admission profile = (%d,%v), want pending Layer 227", profile, ok)
|
||||
}
|
||||
if state, msgID := c.layerProfileEvidenceState(); state.Profile != tg.LayerProfile227 || state.Origin != LayerProfileExplicit || msgID != 104 {
|
||||
if state, msgID := c.layerProfileEvidenceState(); state.Profile != tlprofile.Profile227 || state.Origin != LayerProfileExplicit || msgID != 104 {
|
||||
t.Fatalf("pending full-identity evidence was not committed = %#v msgID:%d", state, msgID)
|
||||
}
|
||||
if got := handler.publications(); len(got) != 0 {
|
||||
|
|
@ -500,7 +505,7 @@ func TestFutureExactLayerWatermarkAllowsOnlyNewerSupportedSelfHeal(t *testing.T)
|
|||
t.Fatal(err)
|
||||
}
|
||||
c := &Conn{authKeyID: authKeyID, sessionID: sessionID, metrics: NopMetrics{}}
|
||||
if err := c.SeedInheritedLayerProfile(tg.LayerProfile225); err != nil {
|
||||
if err := c.SeedInheritedLayerProfile(tlprofile.Profile225); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
c.startInboundRPCScheduler(s.rpcScheduler, 1, 8, time.Second)
|
||||
|
|
@ -513,7 +518,7 @@ func TestFutureExactLayerWatermarkAllowsOnlyNewerSupportedSelfHeal(t *testing.T)
|
|||
},
|
||||
{
|
||||
kind: inboundItemRPC, msgID: 104,
|
||||
body: exactOutboundLayerRPCBody(t, tg.LayerProfile227, &tg.MessagesGetHistoryRequest{
|
||||
body: exactOutboundLayerRPCBody(t, tlprofile.Profile227, &tg.MessagesGetHistoryRequest{
|
||||
Peer: &tg.InputPeerSelf{}, Limit: 1,
|
||||
}),
|
||||
},
|
||||
|
|
@ -549,7 +554,7 @@ func TestFutureExactLayerWatermarkAllowsOnlyNewerSupportedSelfHeal(t *testing.T)
|
|||
if err := s.prepareInboundLayerRPCBatch(context.Background(), c, newPlan); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
if state, rawLayer, msgID := c.layerProfileRawEvidenceState(); state.Profile != tg.LayerProfile227 || state.Origin != LayerProfileExplicit || rawLayer != 227 || msgID != 108 {
|
||||
if state, rawLayer, msgID := c.layerProfileRawEvidenceState(); state.Profile != tlprofile.Profile227 || state.Origin != LayerProfileExplicit || rawLayer != 227 || msgID != 108 {
|
||||
t.Fatalf("newer supported self-heal = %#v raw:%d msgID:%d", state, rawLayer, msgID)
|
||||
}
|
||||
if got := handler.publications(); len(got) != 1 || got[0].layer != 227 || got[0].msgID != 108 {
|
||||
|
|
@ -602,7 +607,7 @@ func TestDurabilityOutageKeepsExplicitLayerConnectionLocal(t *testing.T) {
|
|||
if !plan.items[0].profileEvidenceFresh() {
|
||||
t.Fatal("durability fallback incorrectly disabled current-connection wrapper effects")
|
||||
}
|
||||
if state, msgID := c.layerProfileEvidenceState(); state.Profile != tg.LayerProfile227 || state.Origin != LayerProfileExplicit || msgID != 100 {
|
||||
if state, msgID := c.layerProfileEvidenceState(); state.Profile != tlprofile.Profile227 || state.Origin != LayerProfileExplicit || msgID != 100 {
|
||||
t.Fatalf("connection-local evidence = %#v msgID:%d", state, msgID)
|
||||
}
|
||||
if _, _, found := handler.NegotiatedSessionLayerEvidence(c.authKeyID, c.sessionID); found {
|
||||
|
|
@ -679,7 +684,7 @@ func TestDurabilityOutageInitializesOnlyCurrentConnection(t *testing.T) {
|
|||
if !c.rpcRewrapInitialized.Load() {
|
||||
t.Fatal("current connection did not retain successful init wrapper state")
|
||||
}
|
||||
if state, evidenceMsgID := c.layerProfileEvidenceState(); state.Profile != tg.LayerProfile227 || state.Origin != LayerProfileExplicit || evidenceMsgID != msgID {
|
||||
if state, evidenceMsgID := c.layerProfileEvidenceState(); state.Profile != tlprofile.Profile227 || state.Origin != LayerProfileExplicit || evidenceMsgID != msgID {
|
||||
t.Fatalf("current connection profile = %#v msg:%d", state, evidenceMsgID)
|
||||
}
|
||||
if _, _, found := router.NegotiatedSessionLayerEvidence(c.authKeyID, c.sessionID); found {
|
||||
|
|
@ -710,7 +715,7 @@ func TestDurabilityOutageInitializesOnlyCurrentConnection(t *testing.T) {
|
|||
t.Fatal(err)
|
||||
}
|
||||
encoded, err := fanout.prepareForConn(ctx, c)
|
||||
if err != nil || encoded.layer == nil || encoded.layer.profile != tg.LayerProfile227 {
|
||||
if err != nil || encoded.layer == nil || encoded.layer.profile != tlprofile.Profile227 {
|
||||
t.Fatalf("outage-local push profile = encoded:%#v err:%v", encoded, err)
|
||||
}
|
||||
|
||||
|
|
@ -723,7 +728,7 @@ func TestDurabilityOutageInitializesOnlyCurrentConnection(t *testing.T) {
|
|||
if state := replacement.LayerProfileState(); state.Origin != LayerProfileUnknown {
|
||||
t.Fatalf("new session inherited outage-local profile: %#v", state)
|
||||
}
|
||||
naked := exactOutboundLayerRPCBody(t, tg.LayerProfile227, &tg.MessagesGetHistoryRequest{
|
||||
naked := exactOutboundLayerRPCBody(t, tlprofile.Profile227, &tg.MessagesGetHistoryRequest{
|
||||
Peer: &tg.InputPeerSelf{}, Limit: 1,
|
||||
})
|
||||
if _, _, err := s.admitInboundLayerRPCAt(replacement, msgID+4, naked); err == nil {
|
||||
|
|
@ -782,7 +787,7 @@ func TestInvariantReplayNeverCachesInternalCanonicalProfile(t *testing.T) {
|
|||
}
|
||||
profiled := newConn()
|
||||
defer profiled.Close()
|
||||
if err := profiled.seedOrderedLayerProfile(tg.LayerProfile225, 104); err != nil {
|
||||
if err := profiled.seedOrderedLayerProfile(tlprofile.Profile225, 104); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
completed := &inboundPlan{items: []inboundItem{{kind: inboundItemRPC, msgID: 100, body: body}}}
|
||||
|
|
@ -793,7 +798,7 @@ func TestInvariantReplayNeverCachesInternalCanonicalProfile(t *testing.T) {
|
|||
if completed.items[0].kind != inboundItemReplayRPC {
|
||||
t.Fatalf("profiled invariant completed replay kind=%d", completed.items[0].kind)
|
||||
}
|
||||
if state, msgID := profiled.layerProfileEvidenceState(); state.Profile != tg.LayerProfile225 || state.Origin != LayerProfileExplicit || msgID != 104 {
|
||||
if state, msgID := profiled.layerProfileEvidenceState(); state.Profile != tlprofile.Profile225 || state.Origin != LayerProfileExplicit || msgID != 104 {
|
||||
t.Fatalf("invariant replay polluted explicit profile = %#v msgID:%d", state, msgID)
|
||||
}
|
||||
}
|
||||
|
|
@ -804,21 +809,21 @@ func TestSameMsgIDNakedReplayUsesWinnerAdmissionProfile(t *testing.T) {
|
|||
s.rpcResults = newRPCResultCacheWithFlightLimit(time.Now, 8)
|
||||
authKeyID := [8]byte{0x22, 0x99}
|
||||
const sessionID = int64(2299)
|
||||
body := exactOutboundLayerRPCBody(t, tg.LayerProfile225, &tg.MessagesGetHistoryRequest{
|
||||
body := exactOutboundLayerRPCBody(t, tlprofile.Profile225, &tg.MessagesGetHistoryRequest{
|
||||
Peer: &tg.InputPeerSelf{}, Limit: 1,
|
||||
})
|
||||
|
||||
item220 := inboundItem{msgID: 100, body: body}
|
||||
var err error
|
||||
item220.admitted, item220.method, err = s.decodeInboundLayerRPC(
|
||||
LayerProfileSnapshot{Profile: tg.LayerProfile225, Origin: LayerProfileInherited}, body,
|
||||
LayerProfileSnapshot{Profile: tlprofile.Profile225, Origin: LayerProfileInherited}, body,
|
||||
)
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
item227 := inboundItem{msgID: 100, body: body}
|
||||
item227.admitted, item227.method, err = s.decodeInboundLayerRPC(
|
||||
LayerProfileSnapshot{Profile: tg.LayerProfile227, Origin: LayerProfileInherited}, body,
|
||||
LayerProfileSnapshot{Profile: tlprofile.Profile227, Origin: LayerProfileInherited}, body,
|
||||
)
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
|
|
@ -836,13 +841,13 @@ func TestSameMsgIDNakedReplayUsesWinnerAdmissionProfile(t *testing.T) {
|
|||
if err != nil || loser.state != rpcResultAcquirePending || loser.admissionSeq != winner.admissionSeq {
|
||||
t.Fatalf("loser join = state:%d seq:%d err:%v, winner seq:%d", loser.state, loser.admissionSeq, err, winner.admissionSeq)
|
||||
}
|
||||
if got := item227.admitted.Call().Profile(); got != tg.LayerProfile225 {
|
||||
if got := item227.admitted.Call().Profile(); got != tlprofile.Profile225 {
|
||||
t.Fatalf("loser re-admitted profile = %d, want winner 225", got)
|
||||
}
|
||||
|
||||
changed := inboundItem{msgID: 100, body: exactLayerRPCBody(t, &tg.HelpGetNearestDCRequest{})}
|
||||
changed.admitted, changed.method, err = s.decodeInboundLayerRPC(
|
||||
LayerProfileSnapshot{Profile: tg.LayerProfile225, Origin: LayerProfileInherited}, changed.body,
|
||||
LayerProfileSnapshot{Profile: tlprofile.Profile225, Origin: LayerProfileInherited}, changed.body,
|
||||
)
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
|
|
@ -854,7 +859,7 @@ func TestSameMsgIDNakedReplayUsesWinnerAdmissionProfile(t *testing.T) {
|
|||
}
|
||||
|
||||
func TestInheritedLayerServesRepeatedNakedRPCsWithoutSelectorRefresh(t *testing.T) {
|
||||
for _, profile := range []tg.LayerProfile{tg.LayerProfile225, tg.LayerProfile227} {
|
||||
for _, profile := range []tlprofile.Profile{tlprofile.Profile225, tlprofile.Profile227} {
|
||||
t.Run(fmt.Sprintf("layer_%d", profile), func(t *testing.T) {
|
||||
s := New(Options{DC: 2, LayerRPC: newAdmissionOnlyLayerRPC()})
|
||||
c := &Conn{authKeyID: [8]byte{0x71, byte(profile)}, sessionID: int64(profile), metrics: NopMetrics{}}
|
||||
|
|
@ -985,7 +990,7 @@ func TestOldCompletedLayerRequestCannotRollBackCorrectedSession(t *testing.T) {
|
|||
if err := s.prepareInboundLayerRPCBatch(context.Background(), c, correctPlan); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
if state, msgID := c.layerProfileEvidenceState(); state.Profile != tg.LayerProfile227 || msgID != 104 {
|
||||
if state, msgID := c.layerProfileEvidenceState(); state.Profile != tlprofile.Profile227 || msgID != 104 {
|
||||
t.Fatalf("corrected Conn = %#v msgID:%d", state, msgID)
|
||||
}
|
||||
|
||||
|
|
@ -1002,7 +1007,7 @@ func TestOldCompletedLayerRequestCannotRollBackCorrectedSession(t *testing.T) {
|
|||
if replay.items[0].kind != inboundItemReplayRPC {
|
||||
t.Fatalf("old request kind=%d, want completed replay", replay.items[0].kind)
|
||||
}
|
||||
if state, msgID := replacement.layerProfileEvidenceState(); state.Profile != tg.LayerProfile227 || msgID != 104 {
|
||||
if state, msgID := replacement.layerProfileEvidenceState(); state.Profile != tlprofile.Profile227 || msgID != 104 {
|
||||
t.Fatalf("old replay rolled replacement back = %#v msgID:%d", state, msgID)
|
||||
}
|
||||
if layer, msgID, ok := handler.NegotiatedSessionLayerEvidence(authKeyID, sessionID); !ok || layer != 227 || msgID != 104 {
|
||||
|
|
@ -1069,11 +1074,11 @@ func TestLogicalSessionLayerWatermarkSurvivesResultExpiryAndOldContainer(t *test
|
|||
if err := s.seedInitialLayerProfile(context.Background(), replacement, 0, LayerProfileSnapshot{}); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
if state, msgID := replacement.layerProfileEvidenceState(); state.Profile != tg.LayerProfile227 || state.Origin != LayerProfileInherited || msgID != 0 {
|
||||
if state, msgID := replacement.layerProfileEvidenceState(); state.Profile != tlprofile.Profile227 || state.Origin != LayerProfileInherited || msgID != 0 {
|
||||
t.Fatalf("replacement seed = %#v msgID:%d, want inherited Layer 227", state, msgID)
|
||||
}
|
||||
freshMsgID := proto.NewMessageIDGen(now.Now).New(proto.MessageFromClient)
|
||||
nakedBody := exactOutboundLayerRPCBody(t, tg.LayerProfile227, &tg.MessagesGetHistoryRequest{
|
||||
nakedBody := exactOutboundLayerRPCBody(t, tlprofile.Profile227, &tg.MessagesGetHistoryRequest{
|
||||
Peer: &tg.InputPeerSelf{}, Limit: 1,
|
||||
})
|
||||
replayPlan := &inboundPlan{items: []inboundItem{
|
||||
|
|
@ -1090,10 +1095,10 @@ func TestLogicalSessionLayerWatermarkSurvivesResultExpiryAndOldContainer(t *test
|
|||
if err := s.prepareInboundLayerRPCBatch(context.Background(), replacement, replayPlan); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
if profile, ok := s.rpcResults.ExactAdmissionProfile(authKeyID, sessionID, freshMsgID); !ok || profile != tg.LayerProfile227 {
|
||||
if profile, ok := s.rpcResults.ExactAdmissionProfile(authKeyID, sessionID, freshMsgID); !ok || profile != tlprofile.Profile227 {
|
||||
t.Fatalf("naked request after expired old replay = (%d,%v), want Layer 227", profile, ok)
|
||||
}
|
||||
if state, msgID := replacement.layerProfileEvidenceState(); state.Profile != tg.LayerProfile227 || state.Origin != LayerProfileInherited || msgID != 0 {
|
||||
if state, msgID := replacement.layerProfileEvidenceState(); state.Profile != tlprofile.Profile227 || state.Origin != LayerProfileInherited || msgID != 0 {
|
||||
t.Fatalf("old request-bound flight rolled replacement back = %#v msgID:%d", state, msgID)
|
||||
}
|
||||
if _, _, ok := router.NegotiatedSessionLayerEvidence(authKeyID, sessionID); ok {
|
||||
|
|
@ -1156,14 +1161,14 @@ func TestDurableLayerEvidenceRestoresAcrossEdgeRouterRestart(t *testing.T) {
|
|||
t.Fatal(err)
|
||||
}
|
||||
state, rawLayer, evidenceMsgID := replacement.layerProfileRawEvidenceState()
|
||||
if state.Profile != tg.LayerProfile225 || state.Origin != LayerProfileExplicit || rawLayer != 225 || evidenceMsgID != selectorMsgID {
|
||||
if state.Profile != tlprofile.Profile225 || state.Origin != LayerProfileExplicit || rawLayer != 225 || evidenceMsgID != selectorMsgID {
|
||||
t.Fatalf("restart seed = state:%#v raw:%d msg:%d", state, rawLayer, evidenceMsgID)
|
||||
}
|
||||
|
||||
nakedMsgID := msgIDs.New(proto.MessageFromClient)
|
||||
nakedPlan := &inboundPlan{items: []inboundItem{{
|
||||
kind: inboundItemRPC, msgID: nakedMsgID,
|
||||
body: exactOutboundLayerRPCBody(t, tg.LayerProfile225, &tg.MessagesGetHistoryRequest{
|
||||
body: exactOutboundLayerRPCBody(t, tlprofile.Profile225, &tg.MessagesGetHistoryRequest{
|
||||
Peer: &tg.InputPeerSelf{}, Limit: 1,
|
||||
}),
|
||||
layerProfileEvidenceFreshness: inboundLayerProfileEvidenceFresh,
|
||||
|
|
@ -1173,7 +1178,7 @@ func TestDurableLayerEvidenceRestoresAcrossEdgeRouterRestart(t *testing.T) {
|
|||
t.Fatal(err)
|
||||
}
|
||||
profile, profiled := restartedEdge.rpcResults.ExactAdmissionProfile(authKeyID, sessionID, nakedMsgID)
|
||||
if len(nakedPlan.rpcTasks) != 1 || !profiled || profile != tg.LayerProfile225 {
|
||||
if len(nakedPlan.rpcTasks) != 1 || !profiled || profile != tlprofile.Profile225 {
|
||||
t.Fatalf("restart naked admission = tasks:%d item:%+v", len(nakedPlan.rpcTasks), nakedPlan.items[0])
|
||||
}
|
||||
}
|
||||
|
|
@ -1207,7 +1212,7 @@ func TestPhysicalConnectionReadsDurableLayerOnceBeforeAdmissionHotPath(t *testin
|
|||
t.Fatalf("connection seed GetSessionLayer calls=%d, want 1", got)
|
||||
}
|
||||
|
||||
body := exactOutboundLayerRPCBody(t, tg.LayerProfile225, &tg.HelpGetConfigRequest{})
|
||||
body := exactOutboundLayerRPCBody(t, tlprofile.Profile225, &tg.HelpGetConfigRequest{})
|
||||
for i := 0; i < 64; i++ {
|
||||
plan := &inboundPlan{items: []inboundItem{{
|
||||
kind: inboundItemRPC, msgID: msgIDs.New(proto.MessageFromClient), body: body,
|
||||
|
|
@ -1237,12 +1242,12 @@ func TestDurableExactSeedOutageKeepsFetchedAuthKeyDefaultServing(t *testing.T) {
|
|||
t.Fatal(err)
|
||||
}
|
||||
initial := c.LayerProfileState()
|
||||
if initial.Profile != tg.LayerProfile225 || initial.Origin != LayerProfileInherited {
|
||||
if initial.Profile != tlprofile.Profile225 || initial.Origin != LayerProfileInherited {
|
||||
t.Fatalf("outage seed discarded fetched auth-key default: %#v", initial)
|
||||
}
|
||||
|
||||
msgIDs := proto.NewMessageIDGen(time.Now)
|
||||
body := exactOutboundLayerRPCBody(t, tg.LayerProfile225, &tg.MessagesGetHistoryRequest{
|
||||
body := exactOutboundLayerRPCBody(t, tlprofile.Profile225, &tg.MessagesGetHistoryRequest{
|
||||
Peer: &tg.InputPeerSelf{}, Limit: 1,
|
||||
})
|
||||
for i := 0; i < 64; i++ {
|
||||
|
|
@ -1280,12 +1285,12 @@ func TestBoundTempSeedOutageKeepsRawFetchedLayerServingCurrentConn(t *testing.T)
|
|||
t.Fatal(err)
|
||||
}
|
||||
initial := c.LayerProfileState()
|
||||
if initial.Profile != tg.LayerProfile225 || initial.Origin != LayerProfileInherited {
|
||||
if initial.Profile != tlprofile.Profile225 || initial.Origin != LayerProfileInherited {
|
||||
t.Fatalf("bound-temp outage discarded same-frame raw default: %#v", initial)
|
||||
}
|
||||
|
||||
msgIDs := proto.NewMessageIDGen(time.Now)
|
||||
body := exactOutboundLayerRPCBody(t, tg.LayerProfile225, &tg.MessagesGetHistoryRequest{
|
||||
body := exactOutboundLayerRPCBody(t, tlprofile.Profile225, &tg.MessagesGetHistoryRequest{
|
||||
Peer: &tg.InputPeerSelf{}, Limit: 1,
|
||||
})
|
||||
for i := 0; i < 64; i++ {
|
||||
|
|
@ -1347,7 +1352,7 @@ func TestLiveConnectionKeepsFrozenLayerUntilItsOwnExplicitCorrection(t *testing.
|
|||
t.Fatal(err)
|
||||
}
|
||||
oldPlan.close()
|
||||
if state, raw, msgID := connA.layerProfileRawEvidenceState(); state.Profile != tg.LayerProfile225 || raw != 225 || msgID != oldMsgID {
|
||||
if state, raw, msgID := connA.layerProfileRawEvidenceState(); state.Profile != tlprofile.Profile225 || raw != 225 || msgID != oldMsgID {
|
||||
t.Fatalf("A initial profile = state:%#v raw:%d msg:%d", state, raw, msgID)
|
||||
}
|
||||
|
||||
|
|
@ -1366,18 +1371,18 @@ func TestLiveConnectionKeepsFrozenLayerUntilItsOwnExplicitCorrection(t *testing.
|
|||
oldNakedMsgID := msgIDs.New(proto.MessageFromClient)
|
||||
oldNakedPlan := &inboundPlan{items: []inboundItem{{
|
||||
kind: inboundItemRPC, msgID: oldNakedMsgID,
|
||||
body: exactOutboundLayerRPCBody(t, tg.LayerProfile225, &tg.HelpGetConfigRequest{}),
|
||||
body: exactOutboundLayerRPCBody(t, tlprofile.Profile225, &tg.HelpGetConfigRequest{}),
|
||||
layerProfileEvidenceFreshness: inboundLayerProfileEvidenceFresh,
|
||||
}}}
|
||||
if err := edgeA.prepareInboundLayerRPCBatch(ctx, connA, oldNakedPlan); err != nil {
|
||||
oldNakedPlan.close()
|
||||
t.Fatal(err)
|
||||
}
|
||||
if state, raw, msgID := connA.layerProfileRawEvidenceState(); state.Profile != tg.LayerProfile225 || raw != 225 || msgID != oldMsgID {
|
||||
if state, raw, msgID := connA.layerProfileRawEvidenceState(); state.Profile != tlprofile.Profile225 || raw != 225 || msgID != oldMsgID {
|
||||
oldNakedPlan.close()
|
||||
t.Fatalf("remote durable advance rewrote live A = state:%#v raw:%d msg:%d", state, raw, msgID)
|
||||
}
|
||||
if profile, ok := edgeA.rpcResults.ExactAdmissionProfile(authKeyID, sessionID, oldNakedMsgID); !ok || profile != tg.LayerProfile225 {
|
||||
if profile, ok := edgeA.rpcResults.ExactAdmissionProfile(authKeyID, sessionID, oldNakedMsgID); !ok || profile != tlprofile.Profile225 {
|
||||
oldNakedPlan.close()
|
||||
t.Fatalf("old naked admission profile = (%d,%v), want 225", profile, ok)
|
||||
}
|
||||
|
|
@ -1388,7 +1393,7 @@ func TestLiveConnectionKeepsFrozenLayerUntilItsOwnExplicitCorrection(t *testing.
|
|||
mismatchMsgID := msgIDs.New(proto.MessageFromClient)
|
||||
mismatchPlan := &inboundPlan{items: []inboundItem{{
|
||||
kind: inboundItemRPC, msgID: mismatchMsgID,
|
||||
body: exactOutboundLayerRPCBody(t, tg.LayerProfile227, &tg.ChannelsJoinChannelRequest{
|
||||
body: exactOutboundLayerRPCBody(t, tlprofile.Profile227, &tg.ChannelsJoinChannelRequest{
|
||||
Channel: &tg.InputChannelEmpty{},
|
||||
}),
|
||||
layerProfileEvidenceFreshness: inboundLayerProfileEvidenceFresh,
|
||||
|
|
@ -1402,7 +1407,7 @@ func TestLiveConnectionKeepsFrozenLayerUntilItsOwnExplicitCorrection(t *testing.
|
|||
t.Fatalf("new naked grammar kind=%d, want admission error", mismatchPlan.items[0].kind)
|
||||
}
|
||||
mismatchPlan.close()
|
||||
if state, raw, msgID := connA.layerProfileRawEvidenceState(); state.Profile != tg.LayerProfile225 || raw != 225 || msgID != oldMsgID {
|
||||
if state, raw, msgID := connA.layerProfileRawEvidenceState(); state.Profile != tlprofile.Profile225 || raw != 225 || msgID != oldMsgID {
|
||||
t.Fatalf("failed naked correction mutated A = state:%#v raw:%d msg:%d", state, raw, msgID)
|
||||
}
|
||||
|
||||
|
|
@ -1418,10 +1423,10 @@ func TestLiveConnectionKeepsFrozenLayerUntilItsOwnExplicitCorrection(t *testing.
|
|||
if err := edgeA.prepareInboundLayerRPCBatch(ctx, connA, correctionPlan); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
if state, raw, msgID := connA.layerProfileRawEvidenceState(); state.Profile != tg.LayerProfile227 || raw != 227 || msgID != correctionMsgID {
|
||||
if state, raw, msgID := connA.layerProfileRawEvidenceState(); state.Profile != tlprofile.Profile227 || raw != 227 || msgID != correctionMsgID {
|
||||
t.Fatalf("A explicit correction = state:%#v raw:%d msg:%d", state, raw, msgID)
|
||||
}
|
||||
if profile, ok := edgeA.rpcResults.ExactAdmissionProfile(authKeyID, sessionID, correctionMsgID); !ok || profile != tg.LayerProfile227 {
|
||||
if profile, ok := edgeA.rpcResults.ExactAdmissionProfile(authKeyID, sessionID, correctionMsgID); !ok || profile != tlprofile.Profile227 {
|
||||
t.Fatalf("corrected admission profile = (%d,%v), want 227", profile, ok)
|
||||
}
|
||||
if len(correctionPlan.rpcTasks) != 1 {
|
||||
|
|
@ -1431,7 +1436,7 @@ func TestLiveConnectionKeepsFrozenLayerUntilItsOwnExplicitCorrection(t *testing.
|
|||
t.Fatal(err)
|
||||
}
|
||||
requestProfile, resultProfile := handlerA.profiles()
|
||||
if requestProfile != tg.LayerProfile227 || resultProfile != tg.LayerProfile227 {
|
||||
if requestProfile != tlprofile.Profile227 || resultProfile != tlprofile.Profile227 {
|
||||
t.Fatalf("dispatch/result profiles = %d/%d, want 227/227", requestProfile, resultProfile)
|
||||
}
|
||||
}
|
||||
|
|
@ -1488,7 +1493,7 @@ func TestExactSessionProfileSurvivesUnregisterAndSeedsNakedReplay(t *testing.T)
|
|||
if !ok || layer != 225 {
|
||||
t.Fatalf("reconnect seed = (%d,%v), want (225,true)", layer, ok)
|
||||
}
|
||||
profile, ok := tg.ResolveLayerProfile(layer)
|
||||
profile, ok := tlprofile.ResolveProfile(layer)
|
||||
if !ok {
|
||||
t.Fatalf("resolve retained profile %d", layer)
|
||||
}
|
||||
|
|
@ -1500,7 +1505,7 @@ func TestExactSessionProfileSurvivesUnregisterAndSeedsNakedReplay(t *testing.T)
|
|||
if err != nil {
|
||||
t.Fatalf("same-session naked replay admission: %v", err)
|
||||
}
|
||||
if method != "help.getConfig" || admitted.Call().Profile() != tg.LayerProfile225 {
|
||||
if method != "help.getConfig" || admitted.Call().Profile() != tlprofile.Profile225 {
|
||||
t.Fatalf("naked replay = method:%q profile:%d", method, admitted.Call().Profile())
|
||||
}
|
||||
}
|
||||
|
|
@ -1523,7 +1528,7 @@ func TestSameAuthKeyNewSessionRequiresOwnLayerEvidence(t *testing.T) {
|
|||
if err != nil {
|
||||
t.Fatalf("Bob session layer 227: %v", err)
|
||||
}
|
||||
if bobRequest.Call().Profile() != tg.LayerProfile227 {
|
||||
if bobRequest.Call().Profile() != tlprofile.Profile227 {
|
||||
t.Fatalf("Bob profile = %d, want 227", bobRequest.Call().Profile())
|
||||
}
|
||||
|
||||
|
|
@ -1532,7 +1537,7 @@ func TestSameAuthKeyNewSessionRequiresOwnLayerEvidence(t *testing.T) {
|
|||
Peer: &tg.InputPeerSelf{},
|
||||
Limit: 1,
|
||||
}
|
||||
naked228 := exactOutboundLayerRPCBody(t, tg.LayerProfile228, profileDependent)
|
||||
naked228 := exactOutboundLayerRPCBody(t, tlprofile.Profile228, profileDependent)
|
||||
if _, _, err := s.admitInboundLayerRPC(aliceConn, naked228); err == nil {
|
||||
t.Fatal("new session inherited another session's Layer for naked application RPC")
|
||||
}
|
||||
|
|
@ -1551,7 +1556,7 @@ func TestSameAuthKeyNewSessionRequiresOwnLayerEvidence(t *testing.T) {
|
|||
if err != nil {
|
||||
t.Fatalf("Alice session own layer 228 evidence: %v", err)
|
||||
}
|
||||
if aliceRequest.Call().Profile() != tg.LayerProfile228 {
|
||||
if aliceRequest.Call().Profile() != tlprofile.Profile228 {
|
||||
t.Fatalf("Alice profile = %d, want 228", aliceRequest.Call().Profile())
|
||||
}
|
||||
if layer, ok := router.NegotiatedSessionLayer(authKeyID, bobSession); !ok || layer != 227 {
|
||||
|
|
@ -1573,7 +1578,7 @@ func TestExactSessionRegistryAllowsOrderedExplicitCorrection(t *testing.T) {
|
|||
// A later well-formed invokeWithLayer is authoritative correction, including
|
||||
// when same-session recovery initially restored an older explicit profile.
|
||||
c := &Conn{authKeyID: authKeyID, sessionID: sessionID, metrics: NopMetrics{}}
|
||||
if err := c.SeedLayerProfile(tg.LayerProfile225); err != nil {
|
||||
if err := c.SeedLayerProfile(tlprofile.Profile225); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
wrapped := exactLayerRPCBody(t, &tg.InvokeWithLayerRequest{
|
||||
|
|
@ -1584,10 +1589,10 @@ func TestExactSessionRegistryAllowsOrderedExplicitCorrection(t *testing.T) {
|
|||
if err != nil {
|
||||
t.Fatalf("profile correction: %v", err)
|
||||
}
|
||||
if request.Call().Profile() != tg.LayerProfile227 {
|
||||
if request.Call().Profile() != tlprofile.Profile227 {
|
||||
t.Fatalf("corrected request profile = %d", request.Call().Profile())
|
||||
}
|
||||
if got := c.LayerProfileState(); got.Profile != tg.LayerProfile227 || got.Origin != LayerProfileExplicit || got.Epoch < 2 {
|
||||
if got := c.LayerProfileState(); got.Profile != tlprofile.Profile227 || got.Origin != LayerProfileExplicit || got.Epoch < 2 {
|
||||
t.Fatalf("corrected Conn profile = %#v", got)
|
||||
}
|
||||
if layer, ok := router.NegotiatedSessionLayer(authKeyID, sessionID); !ok || layer != 227 {
|
||||
|
|
@ -1599,17 +1604,17 @@ func TestRestoredExplicitProfileNakedFailureRequestsLayerCorrection(t *testing.T
|
|||
router := rpc.New(rpc.Config{DC: 2}, rpc.Deps{}, zaptest.NewLogger(t), clock.System)
|
||||
s := New(Options{DC: 2, LayerRPC: router})
|
||||
c := &Conn{authKeyID: [8]byte{2, 2, 0, 2}, sessionID: 220227, metrics: NopMetrics{}}
|
||||
if err := c.SeedLayerProfile(tg.LayerProfile225); err != nil {
|
||||
if err := c.SeedLayerProfile(tlprofile.Profile225); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
request := &tg.ChannelsJoinChannelRequest{Channel: &tg.InputChannelEmpty{}}
|
||||
naked227 := exactOutboundLayerRPCBody(t, tg.LayerProfile227, request)
|
||||
naked227 := exactOutboundLayerRPCBody(t, tlprofile.Profile227, request)
|
||||
if _, _, err := s.admitInboundLayerRPC(c, naked227); err == nil {
|
||||
t.Fatal("stale explicit profile admitted newer naked constructor")
|
||||
} else if rpcErr := layerRPCAdmissionError(err); rpcErr.ErrorCode != 400 || rpcErr.ErrorMessage != "CONNECTION_LAYER_INVALID" {
|
||||
t.Fatalf("stale explicit profile error = (%d,%q): %v", rpcErr.ErrorCode, rpcErr.ErrorMessage, err)
|
||||
}
|
||||
if got := c.LayerProfileState(); got.Profile != tg.LayerProfile225 || got.Origin != LayerProfileExplicit {
|
||||
if got := c.LayerProfileState(); got.Profile != tlprofile.Profile225 || got.Origin != LayerProfileExplicit {
|
||||
t.Fatalf("failed naked admission changed profile = %#v", got)
|
||||
}
|
||||
|
||||
|
|
@ -1618,10 +1623,10 @@ func TestRestoredExplicitProfileNakedFailureRequestsLayerCorrection(t *testing.T
|
|||
if err != nil {
|
||||
t.Fatalf("explicit correction retry: %v", err)
|
||||
}
|
||||
if admitted.Call().Profile() != tg.LayerProfile227 {
|
||||
if admitted.Call().Profile() != tlprofile.Profile227 {
|
||||
t.Fatalf("corrected call profile = %d", admitted.Call().Profile())
|
||||
}
|
||||
if got := c.LayerProfileState(); got.Profile != tg.LayerProfile227 || got.Origin != LayerProfileExplicit || got.Epoch < 2 {
|
||||
if got := c.LayerProfileState(); got.Profile != tlprofile.Profile227 || got.Origin != LayerProfileExplicit || got.Epoch < 2 {
|
||||
t.Fatalf("corrected profile = %#v", got)
|
||||
}
|
||||
}
|
||||
|
|
@ -1675,9 +1680,9 @@ func TestUnprofiledInvariantBindKeepsProfileUnknownAndReturnsExactBool(t *testin
|
|||
if err := envelope.Decode(&bin.Buffer{Buf: encoded.body}); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
for _, profile := range []tg.LayerProfile{tg.LayerProfile225, tg.LayerProfile227} {
|
||||
for _, profile := range []tlprofile.Profile{tlprofile.Profile225, tlprofile.Profile227} {
|
||||
inner := bin.Buffer{Buf: append([]byte(nil), envelope.Result...)}
|
||||
decoded, err := tg.DecodeLayer(profile, tg.LayerClassBoolType(), &inner)
|
||||
decoded, err := tlprofile.DecodeObject(profile, &inner, tlprofile.Limits{})
|
||||
if err != nil {
|
||||
t.Fatalf("decode invariant Bool at layer %d: %v", profile, err)
|
||||
}
|
||||
|
|
@ -1688,13 +1693,13 @@ func TestUnprofiledInvariantBindKeepsProfileUnknownAndReturnsExactBool(t *testin
|
|||
|
||||
// The same immutable bytes remain legal if profile evidence arrives before
|
||||
// the queued bind result is physically written.
|
||||
if err := c.FreezeLayerProfile(tg.LayerProfile225); err != nil {
|
||||
if err := c.FreezeLayerProfile(tlprofile.Profile225); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
if err := validateOutboundLayerBinding(c, encoded); err != nil {
|
||||
t.Fatalf("validate invariant result after layer 225 freeze: %v", err)
|
||||
}
|
||||
profiledBody := exactOutboundLayerRPCBody(t, tg.LayerProfile225, bind)
|
||||
profiledBody := exactOutboundLayerRPCBody(t, tlprofile.Profile225, bind)
|
||||
profiled, _, err := s.admitInboundLayerRPC(c, profiledBody)
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
|
|
@ -1714,13 +1719,13 @@ func TestLayerRPCBatchCapacityKeepsExistingPendingReplay(t *testing.T) {
|
|||
metrics: NopMetrics{},
|
||||
}
|
||||
c.startInboundRPCScheduler(s.rpcScheduler, 1, 8, time.Second)
|
||||
if err := c.FreezeLayerProfile(tg.LayerProfile225); err != nil {
|
||||
if err := c.FreezeLayerProfile(tlprofile.Profile225); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
|
||||
firstBody := exactLayerRPCBody(t, &tg.HelpGetConfigRequest{})
|
||||
identityBuffer := &bin.Buffer{Buf: append([]byte(nil), firstBody...)}
|
||||
admitted, err := router.AdmitLayer(tg.LayerProfile225, identityBuffer, tg.LayerDecodeLimits{})
|
||||
admitted, err := router.AdmitLayer(tlprofile.Profile225, identityBuffer, tlprofile.Limits{})
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
|
|
@ -1768,7 +1773,7 @@ func TestLayerRPCBatchCapacityAbortsRejectedRewrapOwner(t *testing.T) {
|
|||
sessionID = int64(779)
|
||||
msgID = int64(900)
|
||||
)
|
||||
identity := rpcFlightExactIdentity(t, tg.LayerProfile225, &tg.HelpGetConfigRequest{})
|
||||
identity := rpcFlightExactIdentity(t, tlprofile.Profile225, &tg.HelpGetConfigRequest{})
|
||||
claim, err := cache.AcquireIdentified(authKeyID, sessionID, msgID, identity)
|
||||
if err != nil || claim.state != rpcResultAcquireOwner || claim.owner == nil {
|
||||
t.Fatalf("rewrap owner = state:%d err:%v", claim.state, err)
|
||||
|
|
@ -1819,7 +1824,7 @@ func TestLayerRPCDependencyGateUsesBusinessOutcome(t *testing.T) {
|
|||
MsgID: test.dependency,
|
||||
Query: &tg.HelpGetConfigRequest{},
|
||||
})
|
||||
admitted, err := router.AdmitLayer(tg.LayerProfile225, &bin.Buffer{Buf: body}, tg.LayerDecodeLimits{})
|
||||
admitted, err := router.AdmitLayer(tlprofile.Profile225, &bin.Buffer{Buf: body}, tlprofile.Limits{})
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
|
|
@ -1847,7 +1852,7 @@ func TestLayerRPCDependencyGateUsesBusinessOutcome(t *testing.T) {
|
|||
MsgID: 300,
|
||||
Query: &tg.HelpGetConfigRequest{},
|
||||
})
|
||||
missing, err := router.AdmitLayer(tg.LayerProfile225, &bin.Buffer{Buf: missingBody}, tg.LayerDecodeLimits{})
|
||||
missing, err := router.AdmitLayer(tlprofile.Profile225, &bin.Buffer{Buf: missingBody}, tlprofile.Limits{})
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
|
|
@ -1874,12 +1879,12 @@ func TestLayerRPCTimeoutMessageDistinguishesDependencyWait(t *testing.T) {
|
|||
}
|
||||
|
||||
func TestLayerRPCAdmissionErrorUsesTypedUnknownClassification(t *testing.T) {
|
||||
err := &tg.LayerCodecError{
|
||||
err := &tlprofile.LayerCodecError{
|
||||
Operation: "admit RPC request",
|
||||
Profile: tg.LayerProfile225,
|
||||
Profile: tlprofile.Profile225,
|
||||
WireID: 0x01020304,
|
||||
Reason: "wording may change",
|
||||
Cause: tg.ErrLayerUnknownRPCMethod,
|
||||
Cause: tlprofile.ErrUnknownRPCMethod,
|
||||
}
|
||||
rpcErr := layerRPCAdmissionError(err)
|
||||
if rpcErr.ErrorCode != 501 || rpcErr.ErrorMessage != "NOT_IMPLEMENTED" {
|
||||
|
|
@ -1888,11 +1893,11 @@ func TestLayerRPCAdmissionErrorUsesTypedUnknownClassification(t *testing.T) {
|
|||
}
|
||||
|
||||
func TestLayerRPCAdmissionErrorDistinguishesUnknownAndInheritedProfiles(t *testing.T) {
|
||||
profileRequired := &tg.LayerCodecError{Operation: "admit", Cause: tg.ErrLayerProfileRequired}
|
||||
profileRequired := &tlprofile.LayerCodecError{Operation: "admit", Cause: tlprofile.ErrProfileRequired}
|
||||
if rpcErr := layerRPCAdmissionError(profileRequired); rpcErr.ErrorCode != 400 || rpcErr.ErrorMessage != "CONNECTION_NOT_INITED" {
|
||||
t.Fatalf("unknown profile admission = (%d,%q)", rpcErr.ErrorCode, rpcErr.ErrorMessage)
|
||||
}
|
||||
inherited := fmt.Errorf("%w: %w", errDefaultLayerAdmission, tg.ErrLayerUnknownRPCMethod)
|
||||
inherited := fmt.Errorf("%w: %w", errDefaultLayerAdmission, tlprofile.ErrUnknownRPCMethod)
|
||||
if rpcErr := layerRPCAdmissionError(inherited); rpcErr.ErrorCode != 400 || rpcErr.ErrorMessage != "CONNECTION_LAYER_INVALID" {
|
||||
t.Fatalf("inherited profile admission = (%d,%q)", rpcErr.ErrorCode, rpcErr.ErrorMessage)
|
||||
}
|
||||
|
|
|
|||
|
|
@ -13,7 +13,7 @@ import (
|
|||
"github.com/iamxvbaba/td/bin"
|
||||
"github.com/iamxvbaba/td/mt"
|
||||
"github.com/iamxvbaba/td/proto"
|
||||
"github.com/iamxvbaba/td/tg"
|
||||
"github.com/iamxvbaba/td/tlprofile"
|
||||
)
|
||||
|
||||
type inboundItemKind uint8
|
||||
|
|
@ -58,7 +58,7 @@ type inboundItem struct {
|
|||
content bool
|
||||
body []byte
|
||||
payload any
|
||||
admitted tg.LayerRequest
|
||||
admitted tlprofile.Admission
|
||||
method string
|
||||
replayAfterSuccessfulDelivery func() error
|
||||
layerProfileEvidenceFreshness inboundLayerProfileEvidenceFreshness
|
||||
|
|
@ -108,7 +108,7 @@ func (p *inboundPlan) close() {
|
|||
// advertise the same bytes to another connection while this plan still kept
|
||||
// the old graph reachable until its caller returned.
|
||||
for i := range p.items {
|
||||
p.items[i].admitted = tg.LayerRequest{}
|
||||
p.items[i].admitted = tlprofile.Admission{}
|
||||
}
|
||||
for i := range p.rpcTasks {
|
||||
p.rpcTasks[i] = inboundRPC{}
|
||||
|
|
|
|||
|
|
@ -14,6 +14,7 @@ import (
|
|||
"github.com/iamxvbaba/td/tg"
|
||||
"go.uber.org/zap/zaptest"
|
||||
|
||||
"github.com/iamxvbaba/td/tlprofile"
|
||||
appfiles "telesrv/internal/app/files"
|
||||
"telesrv/internal/rpc"
|
||||
)
|
||||
|
|
@ -102,17 +103,17 @@ func (h *failingReplayLayerRPC) PrepareAdmittedReplay(
|
|||
int64,
|
||||
int64,
|
||||
uint64,
|
||||
tg.LayerRequest,
|
||||
tlprofile.Admission,
|
||||
) (func() error, error) {
|
||||
return nil, h.err
|
||||
}
|
||||
|
||||
func (h *countingLayerRPCAdmission) AdmitLayer(profile tg.LayerProfile, b *bin.Buffer, limits tg.LayerDecodeLimits) (tg.LayerRequest, error) {
|
||||
func (h *countingLayerRPCAdmission) AdmitLayer(profile tlprofile.Profile, b *bin.Buffer, limits tlprofile.Limits) (tlprofile.Admission, error) {
|
||||
h.decodeCalls.Add(1)
|
||||
return h.LayerRPCHandler.AdmitLayer(profile, b, limits)
|
||||
}
|
||||
|
||||
func (h *countingLayerRPCAdmission) AdmitUnprofiled(b *bin.Buffer, limits tg.LayerDecodeLimits) (tg.LayerRequest, error) {
|
||||
func (h *countingLayerRPCAdmission) AdmitUnprofiled(b *bin.Buffer, limits tlprofile.Limits) (tlprofile.Admission, error) {
|
||||
h.decodeCalls.Add(1)
|
||||
return h.LayerRPCHandler.AdmitUnprofiled(b, limits)
|
||||
}
|
||||
|
|
@ -166,13 +167,13 @@ func TestLayerRPCAdmissionTransfersOriginalReservationToFreshOwner(t *testing.T)
|
|||
s := New(Options{DC: 2, LayerRPC: router})
|
||||
c := &Conn{authKeyID: [8]byte{8, 3}, sessionID: 83, metrics: NopMetrics{}}
|
||||
c.startInboundRPCScheduler(s.rpcScheduler, 1, 4, time.Second)
|
||||
if err := c.FreezeLayerProfile(tg.LayerProfile225); err != nil {
|
||||
if err := c.FreezeLayerProfile(tlprofile.Profile225); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
|
||||
bad := make([]byte, bin.Word)
|
||||
bad[0], bad[1], bad[2], bad[3] = 0x04, 0x03, 0x02, 0x01
|
||||
fresh := exactOutboundLayerRPCBody(t, tg.LayerProfile225, &tg.HelpGetConfigRequest{})
|
||||
fresh := exactOutboundLayerRPCBody(t, tlprofile.Profile225, &tg.HelpGetConfigRequest{})
|
||||
plan := &inboundPlan{items: []inboundItem{
|
||||
{kind: inboundItemRPC, msgID: 100, body: bad},
|
||||
{kind: inboundItemRPC, msgID: 104, body: fresh},
|
||||
|
|
@ -211,13 +212,13 @@ func TestLayerRPCAdmissionPendingReplayReleasesProvisionalEntry(t *testing.T) {
|
|||
s := New(Options{DC: 2, LayerRPC: router})
|
||||
c := &Conn{authKeyID: [8]byte{8, 4}, sessionID: 84, metrics: NopMetrics{}}
|
||||
c.startInboundRPCScheduler(s.rpcScheduler, 1, 4, time.Second)
|
||||
if err := c.FreezeLayerProfile(tg.LayerProfile225); err != nil {
|
||||
if err := c.FreezeLayerProfile(tlprofile.Profile225); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
|
||||
pendingBody := exactOutboundLayerRPCBody(t, tg.LayerProfile225, &tg.HelpGetConfigRequest{})
|
||||
pendingBody := exactOutboundLayerRPCBody(t, tlprofile.Profile225, &tg.HelpGetConfigRequest{})
|
||||
identityBuffer := &bin.Buffer{Buf: append([]byte(nil), pendingBody...)}
|
||||
pendingRequest, err := router.AdmitLayer(tg.LayerProfile225, identityBuffer, tg.LayerDecodeLimits{})
|
||||
pendingRequest, err := router.AdmitLayer(tlprofile.Profile225, identityBuffer, tlprofile.Limits{})
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
|
|
@ -226,7 +227,7 @@ func TestLayerRPCAdmissionPendingReplayReleasesProvisionalEntry(t *testing.T) {
|
|||
t.Fatalf("pending owner = %v, %v", pending.owner, err)
|
||||
}
|
||||
|
||||
freshBody := exactOutboundLayerRPCBody(t, tg.LayerProfile225, &tg.HelpGetNearestDCRequest{})
|
||||
freshBody := exactOutboundLayerRPCBody(t, tlprofile.Profile225, &tg.HelpGetNearestDCRequest{})
|
||||
plan := &inboundPlan{items: []inboundItem{
|
||||
{kind: inboundItemRPC, msgID: 100, body: pendingBody},
|
||||
{kind: inboundItemRPC, msgID: 104, body: freshBody},
|
||||
|
|
@ -253,12 +254,12 @@ func TestLayerRPCAdmissionCompletedReplayReleasesWholeProvisionalBatch(t *testin
|
|||
s := New(Options{DC: 2, LayerRPC: router})
|
||||
c := &Conn{authKeyID: [8]byte{8, 8}, sessionID: 88, metrics: NopMetrics{}}
|
||||
c.startInboundRPCScheduler(s.rpcScheduler, 1, 2, time.Second)
|
||||
if err := c.FreezeLayerProfile(tg.LayerProfile225); err != nil {
|
||||
if err := c.FreezeLayerProfile(tlprofile.Profile225); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
body := exactOutboundLayerRPCBody(t, tg.LayerProfile225, &tg.HelpGetConfigRequest{})
|
||||
body := exactOutboundLayerRPCBody(t, tlprofile.Profile225, &tg.HelpGetConfigRequest{})
|
||||
identityBuffer := &bin.Buffer{Buf: append([]byte(nil), body...)}
|
||||
request, err := router.AdmitLayer(tg.LayerProfile225, identityBuffer, tg.LayerDecodeLimits{})
|
||||
request, err := router.AdmitLayer(tlprofile.Profile225, identityBuffer, tlprofile.Limits{})
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
|
|
@ -299,12 +300,12 @@ func TestLayerRPCAdmissionReplayPreparationErrorIsNotSilentlyDelivered(t *testin
|
|||
}})
|
||||
c := &Conn{authKeyID: [8]byte{8, 9}, sessionID: 89, metrics: NopMetrics{}}
|
||||
c.startInboundRPCScheduler(s.rpcScheduler, 1, 2, time.Second)
|
||||
if err := c.FreezeLayerProfile(tg.LayerProfile225); err != nil {
|
||||
if err := c.FreezeLayerProfile(tlprofile.Profile225); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
body := exactOutboundLayerRPCBody(t, tg.LayerProfile225, &tg.HelpGetConfigRequest{})
|
||||
body := exactOutboundLayerRPCBody(t, tlprofile.Profile225, &tg.HelpGetConfigRequest{})
|
||||
identityBuffer := &bin.Buffer{Buf: append([]byte(nil), body...)}
|
||||
request, err := router.AdmitLayer(tg.LayerProfile225, identityBuffer, tg.LayerDecodeLimits{})
|
||||
request, err := router.AdmitLayer(tlprofile.Profile225, identityBuffer, tlprofile.Limits{})
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
|
|
@ -343,12 +344,12 @@ func TestLayerRPCAdmissionTransferredBatchClosesWithoutLeak(t *testing.T) {
|
|||
s := New(Options{DC: 2, LayerRPC: router})
|
||||
c := &Conn{authKeyID: [8]byte{8, 5}, sessionID: 85, metrics: NopMetrics{}}
|
||||
c.startInboundRPCScheduler(s.rpcScheduler, 1, 2, time.Second)
|
||||
if err := c.FreezeLayerProfile(tg.LayerProfile225); err != nil {
|
||||
if err := c.FreezeLayerProfile(tlprofile.Profile225); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
plan := &inboundPlan{items: []inboundItem{{
|
||||
kind: inboundItemRPC, msgID: 100,
|
||||
body: exactOutboundLayerRPCBody(t, tg.LayerProfile225, &tg.HelpGetConfigRequest{}),
|
||||
body: exactOutboundLayerRPCBody(t, tlprofile.Profile225, &tg.HelpGetConfigRequest{}),
|
||||
}}}
|
||||
defer plan.close()
|
||||
if err := s.prepareInboundLayerRPCBatch(context.Background(), c, plan); err != nil {
|
||||
|
|
@ -378,10 +379,10 @@ func TestLayerRPCAdmissionTransferredBatchCommitsConservativeCharge(t *testing.T
|
|||
s := New(Options{DC: 2, LayerRPC: router})
|
||||
c := &Conn{authKeyID: [8]byte{8, 6}, sessionID: 86, metrics: NopMetrics{}}
|
||||
c.startInboundRPCScheduler(s.rpcScheduler, 1, 2, time.Second)
|
||||
if err := c.FreezeLayerProfile(tg.LayerProfile225); err != nil {
|
||||
if err := c.FreezeLayerProfile(tlprofile.Profile225); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
body := exactOutboundLayerRPCBody(t, tg.LayerProfile225, &tg.HelpGetConfigRequest{})
|
||||
body := exactOutboundLayerRPCBody(t, tlprofile.Profile225, &tg.HelpGetConfigRequest{})
|
||||
plan := &inboundPlan{items: []inboundItem{{kind: inboundItemRPC, msgID: 100, body: body}}}
|
||||
defer plan.close()
|
||||
if err := s.prepareInboundLayerRPCBatch(context.Background(), c, plan); err != nil {
|
||||
|
|
@ -418,10 +419,10 @@ func TestLayerRPCAdmissionLocalDuplicateConsumesNoProvisionalEntry(t *testing.T)
|
|||
s := New(Options{DC: 2, LayerRPC: router})
|
||||
c := &Conn{authKeyID: [8]byte{8, 7}, sessionID: 87, metrics: NopMetrics{}}
|
||||
c.startInboundRPCScheduler(s.rpcScheduler, 1, 2, time.Second)
|
||||
if err := c.FreezeLayerProfile(tg.LayerProfile225); err != nil {
|
||||
if err := c.FreezeLayerProfile(tlprofile.Profile225); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
body := exactOutboundLayerRPCBody(t, tg.LayerProfile225, &tg.HelpGetConfigRequest{})
|
||||
body := exactOutboundLayerRPCBody(t, tlprofile.Profile225, &tg.HelpGetConfigRequest{})
|
||||
plan := &inboundPlan{items: []inboundItem{
|
||||
{kind: inboundItemDuplicate, msgID: 96, body: body},
|
||||
{kind: inboundItemRPC, msgID: 100, body: body},
|
||||
|
|
|
|||
|
|
@ -13,13 +13,13 @@ import (
|
|||
"github.com/iamxvbaba/td/bin"
|
||||
"github.com/iamxvbaba/td/proto"
|
||||
"github.com/iamxvbaba/td/tg"
|
||||
"github.com/iamxvbaba/td/tlprofile"
|
||||
"go.uber.org/zap/zaptest"
|
||||
)
|
||||
|
||||
type countingLayerRPCResult struct {
|
||||
inner tg.LayerRPCResult
|
||||
encodeCalls atomic.Int32
|
||||
prepareCalls atomic.Int32
|
||||
inner tlprofile.Result
|
||||
encodeCalls atomic.Int32
|
||||
}
|
||||
|
||||
const (
|
||||
|
|
@ -27,15 +27,15 @@ const (
|
|||
testChannelWireID228 uint32 = 0xd49f34c6
|
||||
)
|
||||
|
||||
func testChannelWireID(profile tg.LayerProfile) uint32 {
|
||||
if profile == tg.LayerProfile228 {
|
||||
func testChannelWireID(profile tlprofile.Profile) uint32 {
|
||||
if profile == tlprofile.Profile228 {
|
||||
return testChannelWireID228
|
||||
}
|
||||
return testChannelWireID227
|
||||
}
|
||||
|
||||
func testOtherChannelWireID(profile tg.LayerProfile) uint32 {
|
||||
if profile == tg.LayerProfile228 {
|
||||
func testOtherChannelWireID(profile tlprofile.Profile) uint32 {
|
||||
if profile == tlprofile.Profile228 {
|
||||
return testChannelWireID227
|
||||
}
|
||||
return testChannelWireID228
|
||||
|
|
@ -55,28 +55,21 @@ func (r *countingLayerRPCResult) Encode(b *bin.Buffer) error {
|
|||
return r.inner.Encode(b)
|
||||
}
|
||||
|
||||
func (r *countingLayerRPCResult) Prepared() tg.LayerPreparedCall { return r.inner.Prepared() }
|
||||
func (r *countingLayerRPCResult) Prepared() tlprofile.PreparedCall { return r.inner.Prepared() }
|
||||
|
||||
func (r *countingLayerRPCResult) WireInvariant() bool { return r.inner.WireInvariant() }
|
||||
|
||||
func (r *countingLayerRPCResult) Freeze() (tg.LayerFrozenResult, error) {
|
||||
return r.inner.Freeze()
|
||||
}
|
||||
|
||||
func (r *countingLayerRPCResult) Prepare() (tg.LayerPreparedResult, error) {
|
||||
r.prepareCalls.Add(1)
|
||||
return r.inner.Prepare()
|
||||
}
|
||||
func (r *countingLayerRPCResult) CanonicalValue() any { return r.inner.CanonicalValue() }
|
||||
|
||||
func TestExactLayerRPCResultEncodesDifferenceWithAdmittedCodec(t *testing.T) {
|
||||
for _, profile := range []tg.LayerProfile{tg.LayerProfile225, tg.LayerProfile227, tg.LayerProfile228} {
|
||||
for _, profile := range []tlprofile.Profile{tlprofile.Profile225, tlprofile.Profile227, tlprofile.Profile228} {
|
||||
t.Run(fmt.Sprintf("layer_%d", profile), func(t *testing.T) {
|
||||
testExactLayerRPCResultEncodesDifferenceWithAdmittedCodec(t, profile)
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
func testExactLayerRPCResultEncodesDifferenceWithAdmittedCodec(t *testing.T, profile tg.LayerProfile) {
|
||||
func testExactLayerRPCResultEncodesDifferenceWithAdmittedCodec(t *testing.T, profile tlprofile.Profile) {
|
||||
t.Helper()
|
||||
diff := &tg.UpdatesDifference{
|
||||
NewMessages: []tg.MessageClass{
|
||||
|
|
@ -95,23 +88,21 @@ func testExactLayerRPCResultEncodesDifferenceWithAdmittedCodec(t *testing.T, pro
|
|||
State: tg.UpdatesState{Pts: 2, Date: 1},
|
||||
}
|
||||
|
||||
dispatcher := tg.NewServerDispatcher(nil)
|
||||
dispatcher.OnUpdatesGetDifference(func(context.Context, *tg.UpdatesGetDifferenceRequest) (tg.UpdatesDifferenceClass, error) {
|
||||
dispatcher := tlprofile.NewDispatcher()
|
||||
if err := dispatcher.Register(tlprofile.SemanticMethodUpdatesGetDifference, func(context.Context, bin.Object) (any, error) {
|
||||
return diff, nil
|
||||
})
|
||||
outbound, err := tg.PrepareLayerOutboundCall(profile, &tg.UpdatesGetDifferenceRequest{Pts: 1, Date: 1})
|
||||
if err != nil {
|
||||
}); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
var requestBody bin.Buffer
|
||||
if err := outbound.Encode(&requestBody); err != nil {
|
||||
if err := tlprofile.EncodeObject(profile, &tg.UpdatesGetDifferenceRequest{Pts: 1, Date: 1}, &requestBody); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
admitted, err := dispatcher.AdmitLayer(profile, &requestBody)
|
||||
admitted, err := dispatcher.Admit(profile, &requestBody, tlprofile.Limits{})
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
serverResult, err := dispatcher.DispatchAdmitted(context.Background(), admitted)
|
||||
serverResult, err := dispatcher.Dispatch(context.Background(), admitted)
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
|
|
@ -124,9 +115,9 @@ func testExactLayerRPCResultEncodesDifferenceWithAdmittedCodec(t *testing.T, pro
|
|||
}
|
||||
// Simulate an invokeWithLayer correction admitted while this handler was
|
||||
// still running. The result must retain the request's admitted profile.
|
||||
corrected := tg.LayerProfile227
|
||||
if profile == tg.LayerProfile227 {
|
||||
corrected = tg.LayerProfile225
|
||||
corrected := tlprofile.Profile227
|
||||
if profile == tlprofile.Profile227 {
|
||||
corrected = tlprofile.Profile225
|
||||
}
|
||||
if err := c.FreezeLayerProfile(corrected); err != nil {
|
||||
t.Fatal(err)
|
||||
|
|
@ -136,14 +127,11 @@ func testExactLayerRPCResultEncodesDifferenceWithAdmittedCodec(t *testing.T, pro
|
|||
if err != nil {
|
||||
t.Fatalf("encode rpc_result: %v", err)
|
||||
}
|
||||
if got := counted.prepareCalls.Load(); got != 0 {
|
||||
t.Fatalf("generated Prepare calls = %d, want 0; inbound workers must not snapshot result bytes", got)
|
||||
}
|
||||
if got := counted.encodeCalls.Load(); got != 1 {
|
||||
t.Fatalf("generated Encode calls = %d, want exactly 1 under outbound admission", got)
|
||||
}
|
||||
if encoded.layer == nil || encoded.layer.profile != profile || encoded.layer.typ != admitted.Call().WireResultType() {
|
||||
t.Fatalf("result binding = %#v, want profile %d and admitted result TypeRef", encoded.layer, profile)
|
||||
if encoded.layer == nil || encoded.layer.profile != profile {
|
||||
t.Fatalf("result binding = %#v, want profile %d", encoded.layer, profile)
|
||||
}
|
||||
if encoded.layer.kind != outboundLayerBindingRequest {
|
||||
t.Fatalf("exact RPC result binding kind = %d, want request-bound", encoded.layer.kind)
|
||||
|
|
@ -171,7 +159,7 @@ func testExactLayerRPCResultEncodesDifferenceWithAdmittedCodec(t *testing.T, pro
|
|||
t.Fatalf("profile %d offline difference leaked channel constructor %#08x", profile, otherChannelID)
|
||||
}
|
||||
inner := bin.Buffer{Buf: rpcEnvelope.Result}
|
||||
decoded, err := tg.DecodeLayer(profile, tg.LayerClassUpdatesDifferenceType(), &inner)
|
||||
decoded, err := tlprofile.DecodeObject(profile, &inner, tlprofile.Limits{})
|
||||
if err != nil {
|
||||
t.Fatalf("decode exact difference: %v", err)
|
||||
}
|
||||
|
|
@ -199,27 +187,25 @@ func testExactLayerRPCResultEncodesDifferenceWithAdmittedCodec(t *testing.T, pro
|
|||
}
|
||||
|
||||
func TestExactLayerRPCResultUsesHistoricalMethodResultType(t *testing.T) {
|
||||
const profile = tg.LayerProfile225
|
||||
dispatcher := tg.NewServerDispatcher(nil)
|
||||
dispatcher.OnChannelsJoinChannel(func(context.Context, tg.InputChannelClass) (tg.MessagesChatInviteJoinResultClass, error) {
|
||||
const profile = tlprofile.Profile225
|
||||
dispatcher := tlprofile.NewDispatcher()
|
||||
if err := dispatcher.Register(tlprofile.SemanticMethodChannelsJoinChannel, func(context.Context, bin.Object) (any, error) {
|
||||
return &tg.MessagesChatInviteJoinResultOk{Updates: &tg.UpdatesTooLong{}}, nil
|
||||
})
|
||||
outbound, err := tg.PrepareLayerOutboundCall(profile, &tg.ChannelsJoinChannelRequest{Channel: &tg.InputChannelEmpty{}})
|
||||
if err != nil {
|
||||
}); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
var requestBody bin.Buffer
|
||||
if err := outbound.Encode(&requestBody); err != nil {
|
||||
if err := tlprofile.EncodeObject(profile, &tg.ChannelsJoinChannelRequest{Channel: &tg.InputChannelEmpty{}}, &requestBody); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
admitted, err := dispatcher.AdmitLayer(profile, &requestBody)
|
||||
admitted, err := dispatcher.Admit(profile, &requestBody, tlprofile.Limits{})
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
if admitted.Call().WireID() == tg.ChannelsJoinChannelRequestTypeID {
|
||||
t.Fatal("historical request unexpectedly retained canonical method id")
|
||||
}
|
||||
serverResult, err := dispatcher.DispatchAdmitted(context.Background(), admitted)
|
||||
serverResult, err := dispatcher.Dispatch(context.Background(), admitted)
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
|
|
@ -237,7 +223,7 @@ func TestExactLayerRPCResultUsesHistoricalMethodResultType(t *testing.T) {
|
|||
t.Fatal(err)
|
||||
}
|
||||
inner := bin.Buffer{Buf: rpcEnvelope.Result}
|
||||
updates, err := tg.DecodeLayer(profile, tg.LayerClassUpdatesType(), &inner)
|
||||
updates, err := tlprofile.DecodeObject(profile, &inner, tlprofile.Limits{})
|
||||
if err != nil {
|
||||
t.Fatalf("decode historical channels.joinChannel result: %v", err)
|
||||
}
|
||||
|
|
@ -251,7 +237,7 @@ func TestExactLayerRPCResultUsesHistoricalMethodResultType(t *testing.T) {
|
|||
|
||||
func TestProductionUnboundApplicationResultFailsClosedForLayer227(t *testing.T) {
|
||||
c := &Conn{metrics: NopMetrics{}}
|
||||
if err := c.FreezeLayerProfile(tg.LayerProfile227); err != nil {
|
||||
if err := c.FreezeLayerProfile(tlprofile.Profile227); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
encoded, err := (&Server{log: zaptest.NewLogger(t)}).encodeRPCResult(c, 12345, testLayerChannel())
|
||||
|
|
@ -265,7 +251,7 @@ func TestProductionUnboundApplicationResultFailsClosedForLayer227(t *testing.T)
|
|||
|
||||
func TestProductionUnboundApplicationPushFailsClosedForLayer227(t *testing.T) {
|
||||
c := &Conn{metrics: NopMetrics{}}
|
||||
if err := c.FreezeLayerProfile(tg.LayerProfile227); err != nil {
|
||||
if err := c.FreezeLayerProfile(tlprofile.Profile227); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
frame, err := c.buildFrame(context.Background(), proto.MessageFromServer, testLayerChannelUpdatesValue(321), nil)
|
||||
|
|
|
|||
|
|
@ -7,7 +7,7 @@ import (
|
|||
"sync"
|
||||
"testing"
|
||||
|
||||
"github.com/iamxvbaba/td/tg"
|
||||
"github.com/iamxvbaba/td/tlprofile"
|
||||
)
|
||||
|
||||
type countingInheritedLayerResolver struct {
|
||||
|
|
@ -40,66 +40,66 @@ func TestConnLayerProfileUnknownFreezeAndIdempotence(t *testing.T) {
|
|||
t.Fatalf("initial LayerProfile = (%d, %v), want (0, false)", profile, ok)
|
||||
}
|
||||
|
||||
if err := c.FreezeLayerProfile(tg.LayerProfile225); err != nil {
|
||||
if err := c.FreezeLayerProfile(tlprofile.Profile225); err != nil {
|
||||
t.Fatalf("freeze layer 225: %v", err)
|
||||
}
|
||||
if err := c.FreezeLayerProfile(tg.LayerProfile225); err != nil {
|
||||
if err := c.FreezeLayerProfile(tlprofile.Profile225); err != nil {
|
||||
t.Fatalf("repeat freeze layer 225: %v", err)
|
||||
}
|
||||
if profile, ok := c.LayerProfile(); !ok || profile != tg.LayerProfile225 {
|
||||
if profile, ok := c.LayerProfile(); !ok || profile != tlprofile.Profile225 {
|
||||
t.Fatalf("LayerProfile = (%d, %v), want (225, true)", profile, ok)
|
||||
}
|
||||
}
|
||||
|
||||
func TestConnLayerProfileInheritedCanBeCorrectedExplicitly(t *testing.T) {
|
||||
c := &Conn{}
|
||||
if err := c.SeedInheritedLayerProfile(tg.LayerProfile225); err != nil {
|
||||
if err := c.SeedInheritedLayerProfile(tlprofile.Profile225); err != nil {
|
||||
t.Fatalf("seed inherited layer 225: %v", err)
|
||||
}
|
||||
initial := c.LayerProfileState()
|
||||
if initial.Profile != tg.LayerProfile225 || initial.Origin != LayerProfileInherited || initial.Epoch != 1 {
|
||||
if initial.Profile != tlprofile.Profile225 || initial.Origin != LayerProfileInherited || initial.Epoch != 1 {
|
||||
t.Fatalf("initial inherited state = %#v", initial)
|
||||
}
|
||||
if err := c.SeedInheritedLayerProfile(tg.LayerProfile226); err != nil {
|
||||
if err := c.SeedInheritedLayerProfile(tlprofile.Profile226); err != nil {
|
||||
t.Fatalf("repeat inherited seed: %v", err)
|
||||
}
|
||||
if got := c.LayerProfileState(); got != initial {
|
||||
t.Fatalf("second inherited seed replaced selected default: got %#v want %#v", got, initial)
|
||||
}
|
||||
if err := c.FreezeLayerProfile(tg.LayerProfile225); err != nil {
|
||||
if err := c.FreezeLayerProfile(tlprofile.Profile225); err != nil {
|
||||
t.Fatalf("promote inherited evidence: %v", err)
|
||||
}
|
||||
promoted := c.LayerProfileState()
|
||||
if promoted.Profile != tg.LayerProfile225 || promoted.Origin != LayerProfileExplicit || promoted.Epoch != initial.Epoch+1 {
|
||||
if promoted.Profile != tlprofile.Profile225 || promoted.Origin != LayerProfileExplicit || promoted.Epoch != initial.Epoch+1 {
|
||||
t.Fatalf("promoted explicit state = %#v", promoted)
|
||||
}
|
||||
if err := c.FreezeLayerProfile(tg.LayerProfile227); err != nil {
|
||||
if err := c.FreezeLayerProfile(tlprofile.Profile227); err != nil {
|
||||
t.Fatalf("correct explicit layer: %v", err)
|
||||
}
|
||||
corrected := c.LayerProfileState()
|
||||
if corrected.Profile != tg.LayerProfile227 || corrected.Origin != LayerProfileExplicit || corrected.Epoch != promoted.Epoch+1 {
|
||||
if corrected.Profile != tlprofile.Profile227 || corrected.Origin != LayerProfileExplicit || corrected.Epoch != promoted.Epoch+1 {
|
||||
t.Fatalf("corrected explicit state = %#v", corrected)
|
||||
}
|
||||
}
|
||||
|
||||
func TestConnSeedLayerProfile(t *testing.T) {
|
||||
c := &Conn{}
|
||||
if err := c.SeedLayerProfile(tg.LayerProfile226); err != nil {
|
||||
if err := c.SeedLayerProfile(tlprofile.Profile226); err != nil {
|
||||
t.Fatalf("seed layer 226: %v", err)
|
||||
}
|
||||
if err := c.SeedLayerProfile(tg.LayerProfile226); err != nil {
|
||||
if err := c.SeedLayerProfile(tlprofile.Profile226); err != nil {
|
||||
t.Fatalf("repeat seed layer 226: %v", err)
|
||||
}
|
||||
if err := c.FreezeLayerProfile(tg.LayerProfile226); err != nil {
|
||||
if err := c.FreezeLayerProfile(tlprofile.Profile226); err != nil {
|
||||
t.Fatalf("freeze seeded layer 226: %v", err)
|
||||
}
|
||||
if profile, ok := c.LayerProfile(); !ok || profile != tg.LayerProfile226 {
|
||||
if profile, ok := c.LayerProfile(); !ok || profile != tlprofile.Profile226 {
|
||||
t.Fatalf("LayerProfile = (%d, %v), want (226, true)", profile, ok)
|
||||
}
|
||||
}
|
||||
|
||||
func TestConnLayerProfileRejectsUnsupported(t *testing.T) {
|
||||
for _, profile := range []tg.LayerProfile{0, 219, 229} {
|
||||
for _, profile := range []tlprofile.Profile{0, 219, 229} {
|
||||
t.Run(fmt.Sprintf("layer_%d", profile), func(t *testing.T) {
|
||||
c := &Conn{}
|
||||
if err := c.FreezeLayerProfile(profile); !errors.Is(err, ErrLayerProfileUnsupported) {
|
||||
|
|
@ -120,16 +120,16 @@ func TestConnLayerProfileConcurrentCorrectionsRemainAtomic(t *testing.T) {
|
|||
c := &Conn{}
|
||||
start := make(chan struct{})
|
||||
errs := make([]error, goroutines)
|
||||
profiles := make([]tg.LayerProfile, goroutines)
|
||||
profiles := make([]tlprofile.Profile, goroutines)
|
||||
var wg sync.WaitGroup
|
||||
wg.Add(goroutines)
|
||||
for i := range goroutines {
|
||||
profile := tg.LayerProfile225
|
||||
profile := tlprofile.Profile225
|
||||
if i%2 != 0 {
|
||||
profile = tg.LayerProfile227
|
||||
profile = tlprofile.Profile227
|
||||
}
|
||||
profiles[i] = profile
|
||||
go func(index int, requested tg.LayerProfile) {
|
||||
go func(index int, requested tlprofile.Profile) {
|
||||
defer wg.Done()
|
||||
<-start
|
||||
errs[index] = c.FreezeLayerProfile(requested)
|
||||
|
|
@ -139,7 +139,7 @@ func TestConnLayerProfileConcurrentCorrectionsRemainAtomic(t *testing.T) {
|
|||
wg.Wait()
|
||||
|
||||
state := c.LayerProfileState()
|
||||
if state.Origin != LayerProfileExplicit || (state.Profile != tg.LayerProfile225 && state.Profile != tg.LayerProfile227) {
|
||||
if state.Origin != LayerProfileExplicit || (state.Profile != tlprofile.Profile225 && state.Profile != tlprofile.Profile227) {
|
||||
t.Fatalf("concurrent final state = %#v, want supported explicit contender", state)
|
||||
}
|
||||
if state.Epoch == 0 || state.Epoch > goroutines {
|
||||
|
|
@ -154,23 +154,23 @@ func TestConnLayerProfileConcurrentCorrectionsRemainAtomic(t *testing.T) {
|
|||
|
||||
func TestConnLayerProfileEvidenceUsesClientMessageOrder(t *testing.T) {
|
||||
c := &Conn{}
|
||||
if err := c.seedOrderedLayerProfile(tg.LayerProfile225, 100); err != nil {
|
||||
if err := c.seedOrderedLayerProfile(tlprofile.Profile225, 100); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
if applied, err := c.FreezeLayerProfileAt(tg.LayerProfile227, 104); err != nil || !applied {
|
||||
if applied, err := c.FreezeLayerProfileAt(tlprofile.Profile227, 104); err != nil || !applied {
|
||||
t.Fatalf("newer correction applied=%v err=%v", applied, err)
|
||||
}
|
||||
corrected := c.LayerProfileState()
|
||||
if applied, err := c.FreezeLayerProfileAt(tg.LayerProfile225, 100); err != nil || applied {
|
||||
if applied, err := c.FreezeLayerProfileAt(tlprofile.Profile225, 100); err != nil || applied {
|
||||
t.Fatalf("old duplicate applied=%v err=%v", applied, err)
|
||||
}
|
||||
if got := c.LayerProfileState(); got != corrected {
|
||||
t.Fatalf("old duplicate changed profile: got %#v want %#v", got, corrected)
|
||||
}
|
||||
if applied, err := c.FreezeLayerProfileAt(tg.LayerProfile225, 104); !errors.Is(err, ErrLayerProfileConflict) || applied {
|
||||
if applied, err := c.FreezeLayerProfileAt(tlprofile.Profile225, 104); !errors.Is(err, ErrLayerProfileConflict) || applied {
|
||||
t.Fatalf("same-msg conflicting evidence applied=%v err=%v", applied, err)
|
||||
}
|
||||
if applied, err := c.FreezeLayerProfileAt(tg.LayerProfile227, 108); err != nil || !applied {
|
||||
if applied, err := c.FreezeLayerProfileAt(tlprofile.Profile227, 108); err != nil || !applied {
|
||||
t.Fatalf("same-layer newer evidence applied=%v err=%v", applied, err)
|
||||
}
|
||||
state, msgID := c.layerProfileEvidenceState()
|
||||
|
|
@ -185,10 +185,10 @@ func TestSessionManagerSeedsOnlyUnknownRawAuthKeyConnections(t *testing.T) {
|
|||
unknown := &Conn{authKeyID: authKeyID, sessionID: 1}
|
||||
explicit := &Conn{authKeyID: authKeyID, sessionID: 2}
|
||||
inherited := &Conn{authKeyID: authKeyID, sessionID: 3}
|
||||
if err := explicit.FreezeLayerProfile(tg.LayerProfile225); err != nil {
|
||||
if err := explicit.FreezeLayerProfile(tlprofile.Profile225); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
if err := inherited.SeedInheritedLayerProfile(tg.LayerProfile226); err != nil {
|
||||
if err := inherited.SeedInheritedLayerProfile(tlprofile.Profile226); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
for _, c := range []*Conn{unknown, explicit, inherited} {
|
||||
|
|
@ -200,13 +200,13 @@ func TestSessionManagerSeedsOnlyUnknownRawAuthKeyConnections(t *testing.T) {
|
|||
if seeded := m.SeedInheritedLayerForRawAuthKey(authKeyID, 227); seeded != 1 {
|
||||
t.Fatalf("seeded connections = %d, want 1", seeded)
|
||||
}
|
||||
if got := unknown.LayerProfileState(); got.Profile != tg.LayerProfile227 || got.Origin != LayerProfileInherited {
|
||||
if got := unknown.LayerProfileState(); got.Profile != tlprofile.Profile227 || got.Origin != LayerProfileInherited {
|
||||
t.Fatalf("unknown connection seed = %#v", got)
|
||||
}
|
||||
if got := explicit.LayerProfileState(); got.Profile != tg.LayerProfile225 || got.Origin != LayerProfileExplicit {
|
||||
if got := explicit.LayerProfileState(); got.Profile != tlprofile.Profile225 || got.Origin != LayerProfileExplicit {
|
||||
t.Fatalf("explicit connection was overwritten = %#v", got)
|
||||
}
|
||||
if got := inherited.LayerProfileState(); got.Profile != tg.LayerProfile226 || got.Origin != LayerProfileInherited {
|
||||
if got := inherited.LayerProfileState(); got.Profile != tlprofile.Profile226 || got.Origin != LayerProfileInherited {
|
||||
t.Fatalf("existing inherited connection was overwritten = %#v", got)
|
||||
}
|
||||
if seeded := m.SeedInheritedLayerForRawAuthKey(authKeyID, 229); seeded != 0 {
|
||||
|
|
@ -220,10 +220,10 @@ func TestSessionManagerRefreshesInheritedRawKeyShadowAtBind(t *testing.T) {
|
|||
unknown := &Conn{authKeyID: authKeyID, sessionID: 1}
|
||||
inherited := &Conn{authKeyID: authKeyID, sessionID: 2}
|
||||
explicit := &Conn{authKeyID: authKeyID, sessionID: 3}
|
||||
if err := inherited.SeedInheritedLayerProfile(tg.LayerProfile225); err != nil {
|
||||
if err := inherited.SeedInheritedLayerProfile(tlprofile.Profile225); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
if err := explicit.FreezeLayerProfile(tg.LayerProfile225); err != nil {
|
||||
if err := explicit.FreezeLayerProfile(tlprofile.Profile225); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
for _, c := range []*Conn{unknown, inherited, explicit} {
|
||||
|
|
@ -236,11 +236,11 @@ func TestSessionManagerRefreshesInheritedRawKeyShadowAtBind(t *testing.T) {
|
|||
t.Fatalf("refreshed connections = %d, want 2", refreshed)
|
||||
}
|
||||
for name, c := range map[string]*Conn{"unknown": unknown, "inherited": inherited} {
|
||||
if got := c.LayerProfileState(); got.Profile != tg.LayerProfile227 || got.Origin != LayerProfileInherited {
|
||||
if got := c.LayerProfileState(); got.Profile != tlprofile.Profile227 || got.Origin != LayerProfileInherited {
|
||||
t.Fatalf("%s refresh = %#v", name, got)
|
||||
}
|
||||
}
|
||||
if got := explicit.LayerProfileState(); got.Profile != tg.LayerProfile225 || got.Origin != LayerProfileExplicit {
|
||||
if got := explicit.LayerProfileState(); got.Profile != tlprofile.Profile225 || got.Origin != LayerProfileExplicit {
|
||||
t.Fatalf("explicit evidence overwritten = %#v", got)
|
||||
}
|
||||
}
|
||||
|
|
@ -251,10 +251,10 @@ func TestSessionManagerClearsOnlyInheritedRawKeyShadowAtBind(t *testing.T) {
|
|||
inherited := &Conn{authKeyID: authKeyID, sessionID: 1}
|
||||
explicit := &Conn{authKeyID: authKeyID, sessionID: 2}
|
||||
unknown := &Conn{authKeyID: authKeyID, sessionID: 3}
|
||||
if err := inherited.SeedInheritedLayerProfile(tg.LayerProfile225); err != nil {
|
||||
if err := inherited.SeedInheritedLayerProfile(tlprofile.Profile225); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
if err := explicit.seedOrderedLayerProfile(tg.LayerProfile227, 104); err != nil {
|
||||
if err := explicit.seedOrderedLayerProfile(tlprofile.Profile227, 104); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
for _, c := range []*Conn{inherited, explicit, unknown} {
|
||||
|
|
@ -269,7 +269,7 @@ func TestSessionManagerClearsOnlyInheritedRawKeyShadowAtBind(t *testing.T) {
|
|||
if got := inherited.LayerProfileState(); got.Origin != LayerProfileUnknown || got.Profile != 0 {
|
||||
t.Fatalf("inherited shadow after clear = %#v, want unknown", got)
|
||||
}
|
||||
if got := explicit.LayerProfileState(); got.Profile != tg.LayerProfile227 || got.Origin != LayerProfileExplicit {
|
||||
if got := explicit.LayerProfileState(); got.Profile != tlprofile.Profile227 || got.Origin != LayerProfileExplicit {
|
||||
t.Fatalf("explicit evidence was cleared = %#v", got)
|
||||
}
|
||||
if state, msgID := explicit.layerProfileEvidenceState(); state.Origin != LayerProfileExplicit || msgID != 104 {
|
||||
|
|
@ -292,10 +292,10 @@ func TestSessionManagerSeedsUnknownSessionsAcrossBusinessAuthKey(t *testing.T) {
|
|||
second := &Conn{authKeyID: rawTwo, sessionID: 2}
|
||||
explicit := &Conn{authKeyID: rawTwo, sessionID: 3}
|
||||
inherited := &Conn{authKeyID: rawOne, sessionID: 4}
|
||||
if err := explicit.FreezeLayerProfile(tg.LayerProfile225); err != nil {
|
||||
if err := explicit.FreezeLayerProfile(tlprofile.Profile225); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
if err := inherited.SeedInheritedLayerProfile(tg.LayerProfile225); err != nil {
|
||||
if err := inherited.SeedInheritedLayerProfile(tlprofile.Profile225); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
for _, c := range []*Conn{first, second, explicit, inherited} {
|
||||
|
|
@ -308,14 +308,14 @@ func TestSessionManagerSeedsUnknownSessionsAcrossBusinessAuthKey(t *testing.T) {
|
|||
t.Fatalf("business auth-key seeded=%d, want 2", seeded)
|
||||
}
|
||||
for name, c := range map[string]*Conn{"first": first, "second": second} {
|
||||
if got := c.LayerProfileState(); got.Profile != tg.LayerProfile227 || got.Origin != LayerProfileInherited {
|
||||
if got := c.LayerProfileState(); got.Profile != tlprofile.Profile227 || got.Origin != LayerProfileInherited {
|
||||
t.Fatalf("%s business default = %#v", name, got)
|
||||
}
|
||||
}
|
||||
if got := explicit.LayerProfileState(); got.Profile != tg.LayerProfile225 || got.Origin != LayerProfileExplicit {
|
||||
if got := explicit.LayerProfileState(); got.Profile != tlprofile.Profile225 || got.Origin != LayerProfileExplicit {
|
||||
t.Fatalf("business seed overwrote explicit = %#v", got)
|
||||
}
|
||||
if got := inherited.LayerProfileState(); got.Profile != tg.LayerProfile225 || got.Origin != LayerProfileInherited {
|
||||
if got := inherited.LayerProfileState(); got.Profile != tlprofile.Profile225 || got.Origin != LayerProfileInherited {
|
||||
t.Fatalf("business seed overwrote inherited = %#v", got)
|
||||
}
|
||||
}
|
||||
|
|
@ -325,7 +325,7 @@ func TestSessionManagerExplicitLayerEvidenceUsesLiveExactSession(t *testing.T) {
|
|||
authKeyID := [8]byte{2, 2, 9}
|
||||
const sessionID = int64(229)
|
||||
c := &Conn{authKeyID: authKeyID, sessionID: sessionID}
|
||||
if err := c.seedOrderedLayerProfile(tg.LayerProfile226, 1234); err != nil {
|
||||
if err := c.seedOrderedLayerProfile(tlprofile.Profile226, 1234); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
if err := m.Register(c); err != nil {
|
||||
|
|
@ -336,7 +336,7 @@ func TestSessionManagerExplicitLayerEvidenceUsesLiveExactSession(t *testing.T) {
|
|||
}
|
||||
|
||||
inherited := &Conn{authKeyID: authKeyID, sessionID: sessionID + 1}
|
||||
if err := inherited.SeedInheritedLayerProfile(tg.LayerProfile227); err != nil {
|
||||
if err := inherited.SeedInheritedLayerProfile(tlprofile.Profile227); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
if err := m.Register(inherited); err != nil {
|
||||
|
|
@ -353,10 +353,10 @@ func TestSessionManagerExplicitLayerEvidenceChoosesNewestActiveOrClaim(t *testin
|
|||
const sessionID = int64(230)
|
||||
active := &Conn{authKeyID: authKeyID, sessionID: sessionID}
|
||||
claim := &Conn{authKeyID: authKeyID, sessionID: sessionID}
|
||||
if err := active.seedOrderedLayerProfile(tg.LayerProfile225, 100); err != nil {
|
||||
if err := active.seedOrderedLayerProfile(tlprofile.Profile225, 100); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
if err := claim.seedOrderedLayerProfile(tg.LayerProfile227, 104); err != nil {
|
||||
if err := claim.seedOrderedLayerProfile(tlprofile.Profile227, 104); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
key := sessionKey{authKeyID: authKeyID, sessionID: sessionID}
|
||||
|
|
@ -384,15 +384,15 @@ func TestOrderedSessionLayerBroadcastConvergesAcrossPhysicalGenerations(t *testi
|
|||
m.bySession[sessionKey{authKeyID: authKeyID, sessionID: sessionID}] = current
|
||||
m.mu.Unlock()
|
||||
|
||||
if applied, err := m.ApplyOrderedLayerProfileForSession(oldPhysical, authKeyID, sessionID, tg.LayerProfile227, 300); err != nil || applied != 2 {
|
||||
if applied, err := m.ApplyOrderedLayerProfileForSession(oldPhysical, authKeyID, sessionID, tlprofile.Profile227, 300); err != nil || applied != 2 {
|
||||
t.Fatalf("newer broadcast applied=%d err=%v", applied, err)
|
||||
}
|
||||
if applied, err := m.ApplyOrderedLayerProfileForSession(oldPhysical, authKeyID, sessionID, tg.LayerProfile225, 200); err != nil || applied != 0 {
|
||||
if applied, err := m.ApplyOrderedLayerProfileForSession(oldPhysical, authKeyID, sessionID, tlprofile.Profile225, 200); err != nil || applied != 0 {
|
||||
t.Fatalf("delayed older broadcast applied=%d err=%v", applied, err)
|
||||
}
|
||||
for name, c := range map[string]*Conn{"old": oldPhysical, "current": current} {
|
||||
state, msgID := c.layerProfileEvidenceState()
|
||||
if state.Profile != tg.LayerProfile227 || state.Origin != LayerProfileExplicit || msgID != 300 {
|
||||
if state.Profile != tlprofile.Profile227 || state.Origin != LayerProfileExplicit || msgID != 300 {
|
||||
t.Fatalf("%s physical state = %#v msgID:%d", name, state, msgID)
|
||||
}
|
||||
}
|
||||
|
|
@ -409,7 +409,7 @@ func TestInitialProfileSeedAvoidsPermanentKeyResolverAndPrefersPermForTemp(t *te
|
|||
if resolver.calls != 0 {
|
||||
t.Fatalf("permanent resolver calls = %d, want 0", resolver.calls)
|
||||
}
|
||||
if got := c.LayerProfileState(); got.Profile != tg.LayerProfile227 || got.Origin != LayerProfileInherited {
|
||||
if got := c.LayerProfileState(); got.Profile != tlprofile.Profile227 || got.Origin != LayerProfileInherited {
|
||||
t.Fatalf("permanent seed = %#v", got)
|
||||
}
|
||||
})
|
||||
|
|
@ -424,7 +424,7 @@ func TestInitialProfileSeedAvoidsPermanentKeyResolverAndPrefersPermForTemp(t *te
|
|||
if resolver.calls != 1 {
|
||||
t.Fatalf("temporary resolver calls = %d, want 1", resolver.calls)
|
||||
}
|
||||
if got := c.LayerProfileState(); got.Profile != tg.LayerProfile227 || got.Origin != LayerProfileInherited {
|
||||
if got := c.LayerProfileState(); got.Profile != tlprofile.Profile227 || got.Origin != LayerProfileInherited {
|
||||
t.Fatalf("temporary canonical seed = %#v", got)
|
||||
}
|
||||
})
|
||||
|
|
@ -465,7 +465,7 @@ func TestInitialProfileSeedRestoresOrderedExactSessionEvidence(t *testing.T) {
|
|||
t.Fatal(err)
|
||||
}
|
||||
state, msgID := c.layerProfileEvidenceState()
|
||||
if state.Profile != tg.LayerProfile226 || state.Origin != LayerProfileExplicit || msgID != resolver.msgID {
|
||||
if state.Profile != tlprofile.Profile226 || state.Origin != LayerProfileExplicit || msgID != resolver.msgID {
|
||||
t.Fatalf("ordered exact seed = state:%#v msgID:%d", state, msgID)
|
||||
}
|
||||
}
|
||||
|
|
@ -487,10 +487,10 @@ func TestInheritedLayerResolverAvailabilityUsesOnlySupportedRawTempShadow(t *tes
|
|||
for _, tt := range []struct {
|
||||
name string
|
||||
fetchedLayer int
|
||||
wantProfile tg.LayerProfile
|
||||
wantProfile tlprofile.Profile
|
||||
wantOrigin LayerProfileOrigin
|
||||
}{
|
||||
{name: "supported raw shadow", fetchedLayer: 225, wantProfile: tg.LayerProfile225, wantOrigin: LayerProfileInherited},
|
||||
{name: "supported raw shadow", fetchedLayer: 225, wantProfile: tlprofile.Profile225, wantOrigin: LayerProfileInherited},
|
||||
{name: "future raw shadow stays unknown", fetchedLayer: 229, wantOrigin: LayerProfileUnknown},
|
||||
} {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
|
|
@ -529,7 +529,7 @@ func TestActivationClaimRecheckClosesTempBindLayerRace(t *testing.T) {
|
|||
if err := s.refreshActivatedInheritedLayerProfile(context.Background(), c, 225); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
if got := c.LayerProfileState(); got.Profile != tg.LayerProfile227 || got.Origin != LayerProfileInherited {
|
||||
if got := c.LayerProfileState(); got.Profile != tlprofile.Profile227 || got.Origin != LayerProfileInherited {
|
||||
t.Fatalf("post-claim permanent recheck = %#v", got)
|
||||
}
|
||||
})
|
||||
|
|
@ -537,7 +537,7 @@ func TestActivationClaimRecheckClosesTempBindLayerRace(t *testing.T) {
|
|||
t.Run("claim wins before bind refresh", func(t *testing.T) {
|
||||
m := NewSessionManager(nil)
|
||||
c := &Conn{authKeyID: authKeyID, sessionID: 402, authKeyExpiresAt: 1_900_000_000}
|
||||
if err := c.SeedInheritedLayerProfile(tg.LayerProfile225); err != nil {
|
||||
if err := c.SeedInheritedLayerProfile(tlprofile.Profile225); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
if err := m.BeginActivation(c); err != nil {
|
||||
|
|
@ -547,7 +547,7 @@ func TestActivationClaimRecheckClosesTempBindLayerRace(t *testing.T) {
|
|||
if refreshed := m.RefreshInheritedLayerForRawAuthKey(authKeyID, 227); refreshed != 1 {
|
||||
t.Fatalf("bind refresh count = %d, want 1", refreshed)
|
||||
}
|
||||
if got := c.LayerProfileState(); got.Profile != tg.LayerProfile227 || got.Origin != LayerProfileInherited {
|
||||
if got := c.LayerProfileState(); got.Profile != tlprofile.Profile227 || got.Origin != LayerProfileInherited {
|
||||
t.Fatalf("claim-visible bind refresh = %#v", got)
|
||||
}
|
||||
})
|
||||
|
|
@ -556,7 +556,7 @@ func TestActivationClaimRecheckClosesTempBindLayerRace(t *testing.T) {
|
|||
resolver := &countingInheritedLayerResolver{layer: 229, found: true}
|
||||
s := &Server{layerRPC: resolver}
|
||||
c := &Conn{authKeyID: authKeyID, sessionID: 403, authKeyExpiresAt: 1_900_000_000}
|
||||
if err := c.SeedInheritedLayerProfile(tg.LayerProfile225); err != nil {
|
||||
if err := c.SeedInheritedLayerProfile(tlprofile.Profile225); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
if err := s.refreshActivatedInheritedLayerProfile(context.Background(), c, 225); err != nil {
|
||||
|
|
@ -574,7 +574,7 @@ func TestActivationClaimRecheckClosesTempBindLayerRace(t *testing.T) {
|
|||
if err := s.refreshActivatedInheritedLayerProfile(context.Background(), c, 225); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
if got := c.LayerProfileState(); got.Profile != tg.LayerProfile225 || got.Origin != LayerProfileInherited {
|
||||
if got := c.LayerProfileState(); got.Profile != tlprofile.Profile225 || got.Origin != LayerProfileInherited {
|
||||
t.Fatalf("availability recheck lost raw shadow = %#v", got)
|
||||
}
|
||||
})
|
||||
|
|
@ -583,7 +583,7 @@ func TestActivationClaimRecheckClosesTempBindLayerRace(t *testing.T) {
|
|||
resolver := &countingInheritedLayerResolver{err: errors.New("invalid binding identity")}
|
||||
s := &Server{layerRPC: resolver}
|
||||
c := &Conn{authKeyID: authKeyID, sessionID: 405, authKeyExpiresAt: 1_900_000_000}
|
||||
if err := c.SeedInheritedLayerProfile(tg.LayerProfile225); err != nil {
|
||||
if err := c.SeedInheritedLayerProfile(tlprofile.Profile225); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
if err := s.refreshActivatedInheritedLayerProfile(context.Background(), c, 225); err != nil {
|
||||
|
|
|
|||
|
|
@ -7,10 +7,10 @@ import (
|
|||
|
||||
"github.com/iamxvbaba/td/bin"
|
||||
"github.com/iamxvbaba/td/mt"
|
||||
"github.com/iamxvbaba/td/tg"
|
||||
"github.com/iamxvbaba/td/tgerr"
|
||||
"go.uber.org/zap"
|
||||
|
||||
"github.com/iamxvbaba/td/tlprofile"
|
||||
"telesrv/internal/observability/dbtrace"
|
||||
"telesrv/internal/postresponse"
|
||||
)
|
||||
|
|
@ -20,8 +20,8 @@ import (
|
|||
// the inbound worker. The only Encode call happens later under outbound encode
|
||||
// and retained-byte admission.
|
||||
type layerRPCResultEncoder struct {
|
||||
call tg.LayerCall
|
||||
result tg.LayerRPCResult
|
||||
call tlprofile.Call
|
||||
result tlprofile.Result
|
||||
}
|
||||
|
||||
func (e *layerRPCResultEncoder) Encode(b *bin.Buffer) error {
|
||||
|
|
@ -40,7 +40,6 @@ func (e *layerRPCResultEncoder) exactLayerRPCResultBinding() outboundLayerBindin
|
|||
}
|
||||
return outboundLayerBinding{
|
||||
profile: e.call.Profile(),
|
||||
typ: e.call.WireResultType(),
|
||||
wireInvariant: e.call.WireInvariant(),
|
||||
kind: outboundLayerBindingRequest,
|
||||
}
|
||||
|
|
@ -55,7 +54,7 @@ type exactLayerRPCResultEncoder interface {
|
|||
// hook onto the generated result codec. The hook may still exercise the old
|
||||
// scheduling API, but it no longer has a canonical-bytes escape hatch.
|
||||
type legacyTestRPCResultEncoder struct {
|
||||
call tg.LayerCall
|
||||
call tlprofile.Call
|
||||
result bin.Encoder
|
||||
}
|
||||
|
||||
|
|
@ -63,7 +62,7 @@ func (e *legacyTestRPCResultEncoder) Encode(b *bin.Buffer) error {
|
|||
if e == nil || e.result == nil {
|
||||
return errors.New("nil legacy test RPC result")
|
||||
}
|
||||
return e.call.EncodeResult(e.result, b)
|
||||
return e.result.Encode(b)
|
||||
}
|
||||
|
||||
func (e *legacyTestRPCResultEncoder) exactLayerRPCResultBinding() outboundLayerBinding {
|
||||
|
|
@ -72,7 +71,6 @@ func (e *legacyTestRPCResultEncoder) exactLayerRPCResultBinding() outboundLayerB
|
|||
}
|
||||
return outboundLayerBinding{
|
||||
profile: e.call.Profile(),
|
||||
typ: e.call.WireResultType(),
|
||||
wireInvariant: e.call.WireInvariant(),
|
||||
kind: outboundLayerBindingRequest,
|
||||
}
|
||||
|
|
@ -85,7 +83,7 @@ var errLayerRPCResultIdentityMismatch = errors.New("layer RPC result does not ma
|
|||
// result capability created from this exact admission; accepting a result from
|
||||
// another request would pair the wrong result TypeRef/profile with this
|
||||
// flight/cache identity even when both methods happen to share a Go type.
|
||||
func bindAdmittedLayerRPCResult(request tg.LayerRequest, result tg.LayerRPCResult) (*layerRPCResultEncoder, error) {
|
||||
func bindAdmittedLayerRPCResult(request tlprofile.Admission, result tlprofile.Result) (*layerRPCResultEncoder, error) {
|
||||
if result == nil {
|
||||
return nil, nil
|
||||
}
|
||||
|
|
@ -101,7 +99,7 @@ func (s *Server) newInboundLayerRPCTask(
|
|||
admissionSeq uint64,
|
||||
method string,
|
||||
profileEvidenceFresh bool,
|
||||
request tg.LayerRequest,
|
||||
request tlprofile.Admission,
|
||||
dependencies layerRPCDependencySet,
|
||||
owner *rpcResultOwnerLease,
|
||||
) inboundRPC {
|
||||
|
|
@ -202,7 +200,7 @@ func (s *Server) handleAdmittedLayerRPC(
|
|||
msgID int64,
|
||||
admissionSeq uint64,
|
||||
method string,
|
||||
request tg.LayerRequest,
|
||||
request tlprofile.Admission,
|
||||
owner *rpcResultOwnerLease,
|
||||
) error {
|
||||
if s.layerRPC == nil {
|
||||
|
|
|
|||
|
|
@ -11,24 +11,25 @@ import (
|
|||
"github.com/iamxvbaba/td/mt"
|
||||
"github.com/iamxvbaba/td/proto"
|
||||
"github.com/iamxvbaba/td/tg"
|
||||
"github.com/iamxvbaba/td/tlprofile"
|
||||
)
|
||||
|
||||
// preparedOnlyLayerRPCResult is intentionally incapable of encoding. The
|
||||
// binding guard must reject it solely from immutable admission identity before
|
||||
// any result method other than Prepared can be observed.
|
||||
type preparedOnlyLayerRPCResult struct {
|
||||
tg.LayerRPCResult
|
||||
prepared tg.LayerPreparedCall
|
||||
tlprofile.Result
|
||||
prepared tlprofile.PreparedCall
|
||||
}
|
||||
|
||||
func (r *preparedOnlyLayerRPCResult) Prepared() tg.LayerPreparedCall { return r.prepared }
|
||||
func (r *preparedOnlyLayerRPCResult) Prepared() tlprofile.PreparedCall { return r.prepared }
|
||||
|
||||
func TestBindAdmittedLayerRPCResultRequiresExactRequestIdentity(t *testing.T) {
|
||||
dispatcher := tg.NewServerDispatcher(nil)
|
||||
admit := func(request bin.Encoder) tg.LayerRequest {
|
||||
dispatcher := tlprofile.NewDispatcher()
|
||||
admit := func(request bin.Encoder) tlprofile.Admission {
|
||||
t.Helper()
|
||||
body := &bin.Buffer{Buf: exactLayerRPCBody(t, request)}
|
||||
admitted, err := dispatcher.AdmitLayer(tg.LayerProfile227, body)
|
||||
admitted, err := dispatcher.Admit(tlprofile.Profile227, body, tlprofile.Limits{})
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
|
|
@ -53,7 +54,7 @@ func TestBindAdmittedLayerRPCResultRequiresExactRequestIdentity(t *testing.T) {
|
|||
|
||||
type mismatchedProjectionLayerRPC struct {
|
||||
*admissionOnlyLayerRPC
|
||||
result tg.LayerRPCResult
|
||||
result tlprofile.Result
|
||||
calls atomic.Int32
|
||||
}
|
||||
|
||||
|
|
@ -63,18 +64,18 @@ func (h *mismatchedProjectionLayerRPC) DispatchAdmitted(
|
|||
int64,
|
||||
int64,
|
||||
uint64,
|
||||
tg.LayerRequest,
|
||||
) (tg.LayerRPCResult, string, error) {
|
||||
tlprofile.Admission,
|
||||
) (tlprofile.Result, string, error) {
|
||||
h.calls.Add(1)
|
||||
return h.result, "help.getConfig", nil
|
||||
}
|
||||
|
||||
func TestProjectionFailureCachesInternalWithoutRepeatingBusiness(t *testing.T) {
|
||||
dispatcher := tg.NewServerDispatcher(nil)
|
||||
admit := func(request bin.Encoder) tg.LayerRequest {
|
||||
dispatcher := tlprofile.NewDispatcher()
|
||||
admit := func(request bin.Encoder) tlprofile.Admission {
|
||||
t.Helper()
|
||||
body := &bin.Buffer{Buf: exactLayerRPCBody(t, request)}
|
||||
admitted, err := dispatcher.AdmitLayer(tg.LayerProfile227, body)
|
||||
admitted, err := dispatcher.Admit(tlprofile.Profile227, body, tlprofile.Limits{})
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
|
|
@ -93,7 +94,7 @@ func TestProjectionFailureCachesInternalWithoutRepeatingBusiness(t *testing.T) {
|
|||
const reqMsgID = int64(410100)
|
||||
claim, err := s.rpcResults.AcquireLayerIdentified(
|
||||
c.authKeyID, c.sessionID, reqMsgID,
|
||||
tg.LayerProfile227, request.Prepared().Identity(),
|
||||
tlprofile.Profile227, request.Prepared().Identity(),
|
||||
)
|
||||
if err != nil || claim.owner == nil {
|
||||
t.Fatalf("owner acquisition err=%v", err)
|
||||
|
|
@ -110,7 +111,7 @@ func TestProjectionFailureCachesInternalWithoutRepeatingBusiness(t *testing.T) {
|
|||
for {
|
||||
completed, err = s.rpcResults.AcquireLayerIdentified(
|
||||
c.authKeyID, c.sessionID, reqMsgID,
|
||||
tg.LayerProfile227, request.Prepared().Identity(),
|
||||
tlprofile.Profile227, request.Prepared().Identity(),
|
||||
)
|
||||
if err == nil && completed.state == rpcResultAcquireCompleted {
|
||||
break
|
||||
|
|
@ -142,7 +143,7 @@ func TestProjectionFailureCachesInternalWithoutRepeatingBusiness(t *testing.T) {
|
|||
// success.
|
||||
replay, err := s.rpcResults.AcquireLayerIdentified(
|
||||
c.authKeyID, c.sessionID, reqMsgID,
|
||||
tg.LayerProfile227, request.Prepared().Identity(),
|
||||
tlprofile.Profile227, request.Prepared().Identity(),
|
||||
)
|
||||
if err != nil || replay.state != rpcResultAcquireCompleted || replay.encoded != completed.encoded {
|
||||
t.Fatalf("projection replay = state:%d err:%v", replay.state, err)
|
||||
|
|
|
|||
|
|
@ -8,6 +8,7 @@ import (
|
|||
|
||||
"github.com/iamxvbaba/td/bin"
|
||||
"github.com/iamxvbaba/td/tg"
|
||||
"github.com/iamxvbaba/td/tlprofile"
|
||||
)
|
||||
|
||||
var (
|
||||
|
|
@ -36,8 +37,7 @@ const (
|
|||
)
|
||||
|
||||
type outboundLayerBinding struct {
|
||||
profile tg.LayerProfile
|
||||
typ *tg.LayerTypeRef
|
||||
profile tlprofile.Profile
|
||||
wireInvariant bool
|
||||
kind outboundLayerBindingKind
|
||||
// epoch is required for proactive updates. Zero is accepted only for older
|
||||
|
|
@ -52,26 +52,26 @@ type preparedLayerUpdates struct {
|
|||
}
|
||||
|
||||
// layerUpdatesFanout is one immutable canonical Updates snapshot plus a
|
||||
// request-scoped cache of exact prepared bytes. FreezeLayer and
|
||||
// PrepareFrozenLayer are the same generated TypeRef codec used by RPC results
|
||||
// request-scoped cache of exact prepared bytes. FreezeObject and
|
||||
// FrozenObject.Prepare use the same sparse TypeRef execution plans as RPC results
|
||||
// and differences; this type adds only fan-out singleflight and ownership.
|
||||
type layerUpdatesFanout struct {
|
||||
frozen tg.LayerFrozen[tg.UpdatesClass]
|
||||
frozen *tlprofile.FrozenObject
|
||||
size int
|
||||
|
||||
mu sync.Mutex
|
||||
prepared map[tg.LayerProfile]*preparedLayerUpdates
|
||||
prepared map[tlprofile.Profile]*preparedLayerUpdates
|
||||
}
|
||||
|
||||
func newLayerUpdatesFanout(value tg.UpdatesClass) (*layerUpdatesFanout, error) {
|
||||
frozen, err := tg.FreezeLayer(tg.LayerClassUpdatesType(), value)
|
||||
frozen, err := tlprofile.FreezeObject(value)
|
||||
if err != nil {
|
||||
return nil, fmt.Errorf("freeze exact layer updates: %w", err)
|
||||
}
|
||||
return &layerUpdatesFanout{
|
||||
frozen: frozen,
|
||||
size: frozen.CanonicalSize(),
|
||||
prepared: make(map[tg.LayerProfile]*preparedLayerUpdates),
|
||||
prepared: make(map[tlprofile.Profile]*preparedLayerUpdates),
|
||||
}, nil
|
||||
}
|
||||
|
||||
|
|
@ -107,7 +107,7 @@ func (u *layerUpdatesFanout) prepareForConn(ctx context.Context, c *Conn) (*enco
|
|||
return &encoded, nil
|
||||
}
|
||||
|
||||
func (u *layerUpdatesFanout) prepare(ctx context.Context, profile tg.LayerProfile) (*encodedOutboundMessage, error) {
|
||||
func (u *layerUpdatesFanout) prepare(ctx context.Context, profile tlprofile.Profile) (*encodedOutboundMessage, error) {
|
||||
if ctx == nil {
|
||||
ctx = context.Background()
|
||||
}
|
||||
|
|
@ -149,7 +149,7 @@ func (u *layerUpdatesFanout) prepare(ctx context.Context, profile tg.LayerProfil
|
|||
return entry.encoded, entry.err
|
||||
}
|
||||
|
||||
func (u *layerUpdatesFanout) discardPrepared(profile tg.LayerProfile, encoded *encodedOutboundMessage) {
|
||||
func (u *layerUpdatesFanout) discardPrepared(profile tlprofile.Profile, encoded *encodedOutboundMessage) {
|
||||
if u == nil || encoded == nil {
|
||||
return
|
||||
}
|
||||
|
|
@ -172,18 +172,13 @@ func (u *layerUpdatesFanout) discardPrepared(profile tg.LayerProfile, encoded *e
|
|||
|
||||
func prepareFrozenLayerUpdatesContext(
|
||||
ctx context.Context,
|
||||
profile tg.LayerProfile,
|
||||
frozen tg.LayerFrozen[tg.UpdatesClass],
|
||||
profile tlprofile.Profile,
|
||||
frozen *tlprofile.FrozenObject,
|
||||
) (*encodedOutboundMessage, error) {
|
||||
var encoded *encodedOutboundMessage
|
||||
err := withOutboundEncodeSlot(ctx, nil, func() error {
|
||||
prepared, err := tg.PrepareFrozenLayer(profile, frozen)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
var body bin.Buffer
|
||||
typ := tg.LayerClassUpdatesType()
|
||||
if err := prepared.Encode(profile, typ, &body); err != nil {
|
||||
if err := frozen.Encode(profile, &body); err != nil {
|
||||
return err
|
||||
}
|
||||
id, err := body.PeekID()
|
||||
|
|
@ -192,7 +187,7 @@ func prepareFrozenLayerUpdatesContext(
|
|||
}
|
||||
encoded = &encodedOutboundMessage{
|
||||
body: body.Copy(), typeID: id,
|
||||
layer: &outboundLayerBinding{profile: profile, typ: prepared.TypeRef()},
|
||||
layer: &outboundLayerBinding{profile: profile},
|
||||
}
|
||||
return nil
|
||||
})
|
||||
|
|
@ -206,9 +201,6 @@ func validateOutboundLayerBinding(c *Conn, encoded *encodedOutboundMessage) erro
|
|||
if encoded == nil || encoded.layer == nil {
|
||||
return nil
|
||||
}
|
||||
if encoded.layer.typ == nil {
|
||||
return errors.New("outbound exact layer TypeRef is nil")
|
||||
}
|
||||
if encoded.layer.wireInvariant || encoded.layer.kind == outboundLayerBindingRequest {
|
||||
return nil
|
||||
}
|
||||
|
|
|
|||
|
|
@ -11,6 +11,7 @@ import (
|
|||
|
||||
"github.com/iamxvbaba/td/bin"
|
||||
"github.com/iamxvbaba/td/tg"
|
||||
"github.com/iamxvbaba/td/tlprofile"
|
||||
)
|
||||
|
||||
type epochBlockingTransport struct {
|
||||
|
|
@ -65,7 +66,7 @@ func testLayerChannelUpdatesValue(expires int) tg.UpdatesClass {
|
|||
}
|
||||
}
|
||||
|
||||
func testConnWithLayerProfile(t *testing.T, profile tg.LayerProfile) *Conn {
|
||||
func testConnWithLayerProfile(t *testing.T, profile tlprofile.Profile) *Conn {
|
||||
t.Helper()
|
||||
c := &Conn{}
|
||||
if err := c.FreezeLayerProfile(profile); err != nil {
|
||||
|
|
@ -79,7 +80,7 @@ func TestLayerUpdatesFanoutPreparesExactMixedProfiles(t *testing.T) {
|
|||
if err != nil {
|
||||
t.Fatalf("freeze updates: %v", err)
|
||||
}
|
||||
for _, profile := range []tg.LayerProfile{tg.LayerProfile225, tg.LayerProfile227, tg.LayerProfile228} {
|
||||
for _, profile := range []tlprofile.Profile{tlprofile.Profile225, tlprofile.Profile227, tlprofile.Profile228} {
|
||||
t.Run(fmt.Sprintf("layer_%d", profile), func(t *testing.T) {
|
||||
c := testConnWithLayerProfile(t, profile)
|
||||
encoded, err := fanout.prepareForConn(context.Background(), c)
|
||||
|
|
@ -90,7 +91,7 @@ func TestLayerUpdatesFanoutPreparesExactMixedProfiles(t *testing.T) {
|
|||
t.Fatalf("binding = %#v, want profile %d", encoded.layer, profile)
|
||||
}
|
||||
input := bin.Buffer{Buf: encoded.body}
|
||||
decoded, err := tg.DecodeLayer(profile, tg.LayerClassUpdatesType(), &input)
|
||||
decoded, err := tlprofile.DecodeObject(profile, &input, tlprofile.Limits{})
|
||||
if err != nil {
|
||||
t.Fatalf("decode profile %d: %v", profile, err)
|
||||
}
|
||||
|
|
@ -121,7 +122,7 @@ func TestLayerUpdatesFanoutFreezesDefensivelyAndSharesPreparedProfile(t *testing
|
|||
}
|
||||
value.(*tg.UpdateShort).Update.(*tg.UpdateUserStatus).Status.(*tg.UserStatusOnline).Expires = 999
|
||||
|
||||
c := testConnWithLayerProfile(t, tg.LayerProfile225)
|
||||
c := testConnWithLayerProfile(t, tlprofile.Profile225)
|
||||
const workers = 16
|
||||
prepared := make([]*encodedOutboundMessage, workers)
|
||||
prepareErrs := make([]error, workers)
|
||||
|
|
@ -149,7 +150,7 @@ func TestLayerUpdatesFanoutFreezesDefensivelyAndSharesPreparedProfile(t *testing
|
|||
}
|
||||
|
||||
input := bin.Buffer{Buf: prepared[0].body}
|
||||
decoded, err := tg.DecodeLayer(tg.LayerProfile225, tg.LayerClassUpdatesType(), &input)
|
||||
decoded, err := tlprofile.DecodeObject(tlprofile.Profile225, &input, tlprofile.Limits{})
|
||||
if err != nil {
|
||||
t.Fatalf("decode frozen value: %v", err)
|
||||
}
|
||||
|
|
@ -165,7 +166,7 @@ func TestLayerUpdatesEpochBecomesStaleWithoutRetiringProfile(t *testing.T) {
|
|||
t.Fatal(err)
|
||||
}
|
||||
c := &Conn{}
|
||||
if err := c.SeedInheritedLayerProfile(tg.LayerProfile225); err != nil {
|
||||
if err := c.SeedInheritedLayerProfile(tlprofile.Profile225); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
encoded, err := fanout.prepareForConn(context.Background(), c)
|
||||
|
|
@ -173,14 +174,14 @@ func TestLayerUpdatesEpochBecomesStaleWithoutRetiringProfile(t *testing.T) {
|
|||
t.Fatal(err)
|
||||
}
|
||||
oldEpoch := encoded.layer.epoch
|
||||
if err := c.FreezeLayerProfile(tg.LayerProfile227); err != nil {
|
||||
if err := c.FreezeLayerProfile(tlprofile.Profile227); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
if err := validateOutboundLayerBinding(c, encoded); !errors.Is(err, ErrOutboundLayerProfileStale) {
|
||||
t.Fatalf("old push validation = %v, want ErrOutboundLayerProfileStale", err)
|
||||
}
|
||||
state := c.LayerProfileState()
|
||||
if state.Profile != tg.LayerProfile227 || state.Origin != LayerProfileExplicit || state.Epoch <= oldEpoch {
|
||||
if state.Profile != tlprofile.Profile227 || state.Origin != LayerProfileExplicit || state.Epoch <= oldEpoch {
|
||||
t.Fatalf("corrected profile state = %#v, old epoch %d", state, oldEpoch)
|
||||
}
|
||||
}
|
||||
|
|
@ -190,13 +191,13 @@ func TestRequestBoundLayerResultSurvivesConnectionCorrection(t *testing.T) {
|
|||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
c := testConnWithLayerProfile(t, tg.LayerProfile225)
|
||||
encoded, err := fanout.prepare(context.Background(), tg.LayerProfile225)
|
||||
c := testConnWithLayerProfile(t, tlprofile.Profile225)
|
||||
encoded, err := fanout.prepare(context.Background(), tlprofile.Profile225)
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
encoded.layer.kind = outboundLayerBindingRequest
|
||||
if err := c.FreezeLayerProfile(tg.LayerProfile227); err != nil {
|
||||
if err := c.FreezeLayerProfile(tlprofile.Profile227); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
if err := validateOutboundLayerBinding(c, encoded); err != nil {
|
||||
|
|
@ -207,7 +208,7 @@ func TestRequestBoundLayerResultSurvivesConnectionCorrection(t *testing.T) {
|
|||
func TestProfileCorrectionLinearizesAfterStartedPushWrite(t *testing.T) {
|
||||
transport := newEpochBlockingTransport()
|
||||
c := newOutboundTestConn(t, transport, nil)
|
||||
if err := c.FreezeLayerProfile(tg.LayerProfile225); err != nil {
|
||||
if err := c.FreezeLayerProfile(tlprofile.Profile225); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
fanout, err := newLayerUpdatesFanout(testLayerUpdatesValue(123))
|
||||
|
|
@ -228,7 +229,7 @@ func TestProfileCorrectionLinearizesAfterStartedPushWrite(t *testing.T) {
|
|||
}
|
||||
|
||||
corrected := make(chan error, 1)
|
||||
go func() { corrected <- c.FreezeLayerProfile(tg.LayerProfile227) }()
|
||||
go func() { corrected <- c.FreezeLayerProfile(tlprofile.Profile227) }()
|
||||
select {
|
||||
case err := <-corrected:
|
||||
t.Fatalf("profile correction crossed an old-epoch physical write: %v", err)
|
||||
|
|
@ -252,7 +253,7 @@ func TestProfileCorrectionLinearizesAfterStartedPushWrite(t *testing.T) {
|
|||
|
||||
func TestStaleLayerPushIsRemovedFromResendTracking(t *testing.T) {
|
||||
c := &Conn{metrics: NopMetrics{}}
|
||||
if err := c.FreezeLayerProfile(tg.LayerProfile225); err != nil {
|
||||
if err := c.FreezeLayerProfile(tlprofile.Profile225); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
fanout, err := newLayerUpdatesFanout(testLayerUpdatesValue(123))
|
||||
|
|
@ -263,7 +264,7 @@ func TestStaleLayerPushIsRemovedFromResendTracking(t *testing.T) {
|
|||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
if err := c.FreezeLayerProfile(tg.LayerProfile227); err != nil {
|
||||
if err := c.FreezeLayerProfile(tlprofile.Profile227); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
frame := &outboundFrame{msgID: 100, body: encoded.body, layer: encoded.layer}
|
||||
|
|
@ -285,14 +286,14 @@ func TestOutboundLayerBindingRejectsUnknownAndMismatchedConnections(t *testing.T
|
|||
if err != nil {
|
||||
t.Fatalf("freeze updates: %v", err)
|
||||
}
|
||||
encoded, err := fanout.prepare(context.Background(), tg.LayerProfile225)
|
||||
encoded, err := fanout.prepare(context.Background(), tlprofile.Profile225)
|
||||
if err != nil {
|
||||
t.Fatalf("prepare profile 225: %v", err)
|
||||
}
|
||||
if _, err := (&Conn{}).buildFrame(context.Background(), 0, nil, encoded); !errors.Is(err, ErrOutboundLayerProfileUnknown) {
|
||||
t.Fatalf("unknown profile error = %v", err)
|
||||
}
|
||||
wrong := testConnWithLayerProfile(t, tg.LayerProfile227)
|
||||
wrong := testConnWithLayerProfile(t, tlprofile.Profile227)
|
||||
if _, err := wrong.buildFrame(context.Background(), 0, nil, encoded); !errors.Is(err, ErrOutboundLayerProfileMismatch) {
|
||||
t.Fatalf("profile mismatch error = %v", err)
|
||||
}
|
||||
|
|
@ -307,13 +308,13 @@ func TestPendingPushReservationAccountsPreparedProfilesOnce(t *testing.T) {
|
|||
reservation.bytes.Store(100)
|
||||
reservation.refs.Store(1)
|
||||
|
||||
if !reservation.reservePrepared(tg.LayerProfile225, 80) {
|
||||
if !reservation.reservePrepared(tlprofile.Profile225, 80) {
|
||||
t.Fatal("reserve first profile")
|
||||
}
|
||||
if !reservation.reservePrepared(tg.LayerProfile225, 80) {
|
||||
if !reservation.reservePrepared(tlprofile.Profile225, 80) {
|
||||
t.Fatal("reuse first profile reservation")
|
||||
}
|
||||
if !reservation.reservePrepared(tg.LayerProfile227, 120) {
|
||||
if !reservation.reservePrepared(tlprofile.Profile227, 120) {
|
||||
t.Fatal("reserve second profile")
|
||||
}
|
||||
if got := budget.snapshot(); got != 300 {
|
||||
|
|
|
|||
|
|
@ -16,6 +16,7 @@ import (
|
|||
"github.com/iamxvbaba/td/mt"
|
||||
"github.com/iamxvbaba/td/proto"
|
||||
"github.com/iamxvbaba/td/tg"
|
||||
"github.com/iamxvbaba/td/tlprofile"
|
||||
"github.com/iamxvbaba/td/transport"
|
||||
)
|
||||
|
||||
|
|
@ -545,7 +546,7 @@ func TestOutboundActorSerializesConcurrentSends(t *testing.T) {
|
|||
clientMsgID := proto.NewMessageIDGen(time.Now)
|
||||
sendEncrypted(t, conn, cipher, auth, clientMsgID.New(proto.MessageFromClient), &mt.PingRequest{PingID: 1})
|
||||
collectReplies(t, conn, cipher, auth.AuthKey, mt.MsgsAckTypeID)
|
||||
freezeActiveTestSessionProfile(t, srv.Conns(), auth.AuthKey.ID, auth.SessionID, tg.LayerProfileCanonical)
|
||||
freezeActiveTestSessionProfile(t, srv.Conns(), auth.AuthKey.ID, auth.SessionID, tlprofile.ProfileCanonical)
|
||||
srv.Conns().SetReceivesUpdates(auth.SessionID, true)
|
||||
|
||||
const sends = 64
|
||||
|
|
@ -1035,7 +1036,7 @@ func TestOutboundResendAndAckState(t *testing.T) {
|
|||
clientMsgID := proto.NewMessageIDGen(time.Now)
|
||||
sendEncrypted(t, conn, cipher, auth, clientMsgID.New(proto.MessageFromClient), &mt.PingRequest{PingID: 1})
|
||||
collectReplies(t, conn, cipher, auth.AuthKey, mt.MsgsAckTypeID)
|
||||
freezeActiveTestSessionProfile(t, srv.Conns(), auth.AuthKey.ID, auth.SessionID, tg.LayerProfileCanonical)
|
||||
freezeActiveTestSessionProfile(t, srv.Conns(), auth.AuthKey.ID, auth.SessionID, tlprofile.ProfileCanonical)
|
||||
srv.Conns().SetReceivesUpdates(auth.SessionID, true)
|
||||
|
||||
ctx, cancel := context.WithTimeout(context.Background(), 5*time.Second)
|
||||
|
|
|
|||
|
|
@ -8,6 +8,7 @@ import (
|
|||
"github.com/iamxvbaba/td/mt"
|
||||
"github.com/iamxvbaba/td/proto"
|
||||
"github.com/iamxvbaba/td/tg"
|
||||
"github.com/iamxvbaba/td/tlprofile"
|
||||
)
|
||||
|
||||
// TestSetReceivesUpdatesFlushesPendingBeforeActivation 验证置位时先排空暂存推送
|
||||
|
|
@ -23,7 +24,7 @@ func TestSetReceivesUpdatesFlushesPendingBeforeActivation(t *testing.T) {
|
|||
collectReplies(t, conn, cipher, auth.AuthKey, mt.MsgsAckTypeID)
|
||||
|
||||
raw := auth.AuthKey.ID
|
||||
freezeActiveTestSessionProfile(t, srv.Conns(), raw, auth.SessionID, tg.LayerProfileCanonical)
|
||||
freezeActiveTestSessionProfile(t, srv.Conns(), raw, auth.SessionID, tlprofile.ProfileCanonical)
|
||||
ctx := context.Background()
|
||||
|
||||
// 完全就绪还要求 membership 路由建立(ReceivesUpdatesForAuthKey 的另一半条件)。
|
||||
|
|
|
|||
|
|
@ -11,6 +11,7 @@ import (
|
|||
"github.com/iamxvbaba/td/bin"
|
||||
"github.com/iamxvbaba/td/proto"
|
||||
"github.com/iamxvbaba/td/tg"
|
||||
"github.com/iamxvbaba/td/tlprofile"
|
||||
)
|
||||
|
||||
var ErrSessionAmbiguous = errors.New("session id is shared by multiple auth keys")
|
||||
|
|
@ -154,7 +155,7 @@ func (m *SessionManager) SetReceivesUpdates(sessionID int64, receives bool) {
|
|||
}
|
||||
}
|
||||
|
||||
func (m *SessionManager) SetLayerProfile(sessionID int64, profile tg.LayerProfile) bool {
|
||||
func (m *SessionManager) SetLayerProfile(sessionID int64, profile tlprofile.Profile) bool {
|
||||
m.mu.RLock()
|
||||
c, _, ok, ambiguous := m.uniqueSessionForTestLocked(sessionID)
|
||||
m.mu.RUnlock()
|
||||
|
|
|
|||
|
|
@ -6,7 +6,7 @@ import (
|
|||
"sync"
|
||||
"sync/atomic"
|
||||
|
||||
"github.com/iamxvbaba/td/tg"
|
||||
"github.com/iamxvbaba/td/tlprofile"
|
||||
)
|
||||
|
||||
const rpcResultFlightDefaultMaxPending = 8192
|
||||
|
|
@ -26,7 +26,7 @@ var (
|
|||
// re-decode the same naked body under that grammar even if the winner aborts
|
||||
// immediately after the mismatch is returned.
|
||||
type rpcResultIdentityMismatchError struct {
|
||||
profile tg.LayerProfile
|
||||
profile tlprofile.Profile
|
||||
hasProfile bool
|
||||
}
|
||||
|
||||
|
|
@ -40,11 +40,11 @@ func identityMismatch(identity rpcResultRequestIdentity) error {
|
|||
}
|
||||
|
||||
type rpcResultRequestIdentity struct {
|
||||
exact tg.LayerPreparedCallIdentity
|
||||
// profile is retained separately because LayerPreparedCallIdentity is opaque.
|
||||
exact tlprofile.PreparedIdentity
|
||||
// profile is retained separately because PreparedIdentity is opaque.
|
||||
// It lets a same-msg_id replay be re-admitted with the original request
|
||||
// grammar after the session default has moved to another Layer.
|
||||
profile tg.LayerProfile
|
||||
profile tlprofile.Profile
|
||||
valid bool
|
||||
}
|
||||
|
||||
|
|
@ -474,7 +474,7 @@ func (c *rpcResultCache) Acquire(authKeyID [8]byte, sessionID, reqMsgID int64) (
|
|||
func (c *rpcResultCache) AcquireIdentified(
|
||||
authKeyID [8]byte,
|
||||
sessionID, reqMsgID int64,
|
||||
identity tg.LayerPreparedCallIdentity,
|
||||
identity tlprofile.PreparedIdentity,
|
||||
) (rpcResultAcquire, error) {
|
||||
return c.acquire(authKeyID, sessionID, reqMsgID, rpcResultRequestIdentity{exact: identity, valid: true})
|
||||
}
|
||||
|
|
@ -485,8 +485,8 @@ func (c *rpcResultCache) AcquireIdentified(
|
|||
func (c *rpcResultCache) AcquireLayerIdentified(
|
||||
authKeyID [8]byte,
|
||||
sessionID, reqMsgID int64,
|
||||
profile tg.LayerProfile,
|
||||
identity tg.LayerPreparedCallIdentity,
|
||||
profile tlprofile.Profile,
|
||||
identity tlprofile.PreparedIdentity,
|
||||
) (rpcResultAcquire, error) {
|
||||
return c.acquire(authKeyID, sessionID, reqMsgID, rpcResultRequestIdentity{
|
||||
exact: identity, profile: profile, valid: true,
|
||||
|
|
@ -497,7 +497,7 @@ func (c *rpcResultCache) AcquireLayerIdentified(
|
|||
// owner/result. It does not create or join a flight. Callers still perform
|
||||
// AcquireLayerIdentified after decode, which atomically rejects a same-msg_id
|
||||
// body change by comparing the full prepared identity.
|
||||
func (c *rpcResultCache) ExactAdmissionProfile(authKeyID [8]byte, sessionID, reqMsgID int64) (tg.LayerProfile, bool) {
|
||||
func (c *rpcResultCache) ExactAdmissionProfile(authKeyID [8]byte, sessionID, reqMsgID int64) (tlprofile.Profile, bool) {
|
||||
if c == nil || reqMsgID == 0 {
|
||||
return 0, false
|
||||
}
|
||||
|
|
|
|||
|
|
@ -9,19 +9,20 @@ import (
|
|||
|
||||
"github.com/iamxvbaba/td/bin"
|
||||
"github.com/iamxvbaba/td/tg"
|
||||
"github.com/iamxvbaba/td/tlprofile"
|
||||
)
|
||||
|
||||
func rpcFlightTestAuthID(seed byte) [8]byte {
|
||||
return [8]byte{seed, seed + 1, seed + 2, seed + 3}
|
||||
}
|
||||
|
||||
func rpcFlightExactIdentity(t *testing.T, profile tg.LayerProfile, request bin.Encoder) tg.LayerPreparedCallIdentity {
|
||||
func rpcFlightExactIdentity(t *testing.T, profile tlprofile.Profile, request bin.Object) tlprofile.PreparedIdentity {
|
||||
t.Helper()
|
||||
var body bin.Buffer
|
||||
if err := request.Encode(&body); err != nil {
|
||||
if err := tlprofile.EncodeObject(profile, request, &body); err != nil {
|
||||
t.Fatalf("encode exact request: %v", err)
|
||||
}
|
||||
admitted, err := tg.NewServerDispatcher(nil).AdmitLayer(profile, &body)
|
||||
admitted, err := tlprofile.NewDispatcher().Admit(profile, &body, tlprofile.Limits{})
|
||||
if err != nil {
|
||||
t.Fatalf("admit exact request: %v", err)
|
||||
}
|
||||
|
|
@ -223,8 +224,8 @@ func TestRPCResultFlightRepeatedReplayJoinsStayBoundedAndPutCleansExecution(t *t
|
|||
func TestRPCResultFlightExactIdentityGuardsPendingAndCompletedReuse(t *testing.T) {
|
||||
cache := newRPCResultCacheWithFlightLimit(time.Now, 2)
|
||||
authKeyID := rpcFlightTestAuthID(90)
|
||||
firstIdentity := rpcFlightExactIdentity(t, tg.LayerProfile225, &tg.HelpGetConfigRequest{})
|
||||
otherIdentity := rpcFlightExactIdentity(t, tg.LayerProfile225, &tg.HelpGetNearestDCRequest{})
|
||||
firstIdentity := rpcFlightExactIdentity(t, tlprofile.Profile225, &tg.HelpGetConfigRequest{})
|
||||
otherIdentity := rpcFlightExactIdentity(t, tlprofile.Profile225, &tg.HelpGetNearestDCRequest{})
|
||||
|
||||
owner, err := cache.AcquireIdentified(authKeyID, 90, 900, firstIdentity)
|
||||
if err != nil || owner.state != rpcResultAcquireOwner || owner.owner == nil {
|
||||
|
|
@ -255,23 +256,23 @@ func TestRPCResultFlightExactIdentityGuardsPendingAndCompletedReuse(t *testing.T
|
|||
func TestRPCResultFlightAdmissionSequenceAllocatedOnceAndReplayed(t *testing.T) {
|
||||
cache := newRPCResultCacheWithFlightLimit(time.Now, 4)
|
||||
authKeyID := rpcFlightTestAuthID(89)
|
||||
identity := rpcFlightExactIdentity(t, tg.LayerProfile225, &tg.HelpGetConfigRequest{})
|
||||
owner, err := cache.AcquireLayerIdentified(authKeyID, 89, 890, tg.LayerProfile225, identity)
|
||||
identity := rpcFlightExactIdentity(t, tlprofile.Profile225, &tg.HelpGetConfigRequest{})
|
||||
owner, err := cache.AcquireLayerIdentified(authKeyID, 89, 890, tlprofile.Profile225, identity)
|
||||
if err != nil || owner.state != rpcResultAcquireOwner || owner.owner == nil || owner.admissionSeq == 0 {
|
||||
t.Fatalf("owner = state:%d seq:%d err:%v", owner.state, owner.admissionSeq, err)
|
||||
}
|
||||
pending, err := cache.AcquireLayerIdentified(authKeyID, 89, 890, tg.LayerProfile225, identity)
|
||||
pending, err := cache.AcquireLayerIdentified(authKeyID, 89, 890, tlprofile.Profile225, identity)
|
||||
if err != nil || pending.state != rpcResultAcquirePending || pending.admissionSeq != owner.admissionSeq {
|
||||
t.Fatalf("pending = state:%d seq:%d err:%v, want seq:%d", pending.state, pending.admissionSeq, err, owner.admissionSeq)
|
||||
}
|
||||
owner.owner.CompleteExecution(true)
|
||||
encoded := &encodedOutboundMessage{body: []byte{1}, reqMsgID: 890}
|
||||
cache.Put(authKeyID, 89, 890, encoded)
|
||||
completed, err := cache.AcquireLayerIdentified(authKeyID, 89, 890, tg.LayerProfile225, identity)
|
||||
completed, err := cache.AcquireLayerIdentified(authKeyID, 89, 890, tlprofile.Profile225, identity)
|
||||
if err != nil || completed.state != rpcResultAcquireCompleted || completed.admissionSeq != owner.admissionSeq {
|
||||
t.Fatalf("completed = state:%d seq:%d err:%v, want seq:%d", completed.state, completed.admissionSeq, err, owner.admissionSeq)
|
||||
}
|
||||
second, err := cache.AcquireLayerIdentified(authKeyID, 89, 894, tg.LayerProfile225, identity)
|
||||
second, err := cache.AcquireLayerIdentified(authKeyID, 89, 894, tlprofile.Profile225, identity)
|
||||
if err != nil || second.admissionSeq <= owner.admissionSeq {
|
||||
t.Fatalf("second owner seq=%d err=%v, want > %d", second.admissionSeq, err, owner.admissionSeq)
|
||||
}
|
||||
|
|
@ -286,12 +287,12 @@ func TestRPCResultFlightAdmissionSequenceAllocatedOnceAndReplayed(t *testing.T)
|
|||
func TestRPCAdmissionSafeFloorTracksOwnersUntilPutOrAbort(t *testing.T) {
|
||||
cache := newRPCResultCacheWithFlightLimit(time.Now, 4)
|
||||
authKeyID := rpcFlightTestAuthID(86)
|
||||
identity := rpcFlightExactIdentity(t, tg.LayerProfile225, &tg.HelpGetConfigRequest{})
|
||||
first, err := cache.AcquireLayerIdentified(authKeyID, 86, 860, tg.LayerProfile225, identity)
|
||||
identity := rpcFlightExactIdentity(t, tlprofile.Profile225, &tg.HelpGetConfigRequest{})
|
||||
first, err := cache.AcquireLayerIdentified(authKeyID, 86, 860, tlprofile.Profile225, identity)
|
||||
if err != nil || first.owner == nil {
|
||||
t.Fatalf("first owner err=%v", err)
|
||||
}
|
||||
second, err := cache.AcquireLayerIdentified(authKeyID, 86, 864, tg.LayerProfile225, identity)
|
||||
second, err := cache.AcquireLayerIdentified(authKeyID, 86, 864, tlprofile.Profile225, identity)
|
||||
if err != nil || second.owner == nil {
|
||||
t.Fatalf("second owner err=%v", err)
|
||||
}
|
||||
|
|
@ -315,12 +316,12 @@ func TestRPCAdmissionSequenceExhaustionCannotWrap(t *testing.T) {
|
|||
cache := newRPCResultCacheWithFlightLimit(time.Now, 2)
|
||||
cache.nextAdmissionSeq.Store(^uint64(0) - 1)
|
||||
authKeyID := rpcFlightTestAuthID(85)
|
||||
identity := rpcFlightExactIdentity(t, tg.LayerProfile225, &tg.HelpGetConfigRequest{})
|
||||
last, err := cache.AcquireLayerIdentified(authKeyID, 85, 850, tg.LayerProfile225, identity)
|
||||
identity := rpcFlightExactIdentity(t, tlprofile.Profile225, &tg.HelpGetConfigRequest{})
|
||||
last, err := cache.AcquireLayerIdentified(authKeyID, 85, 850, tlprofile.Profile225, identity)
|
||||
if err != nil || last.admissionSeq != ^uint64(0) || last.owner == nil {
|
||||
t.Fatalf("last sequence=%d owner:%v err=%v", last.admissionSeq, last.owner != nil, err)
|
||||
}
|
||||
if _, err := cache.AcquireLayerIdentified(authKeyID, 85, 854, tg.LayerProfile225, identity); !errors.Is(err, ErrRPCAdmissionSeqExhausted) {
|
||||
if _, err := cache.AcquireLayerIdentified(authKeyID, 85, 854, tlprofile.Profile225, identity); !errors.Is(err, ErrRPCAdmissionSeqExhausted) {
|
||||
t.Fatalf("post-max allocation err=%v, want %v", err, ErrRPCAdmissionSeqExhausted)
|
||||
}
|
||||
if got := cache.nextAdmissionSeq.Load(); got != ^uint64(0) {
|
||||
|
|
@ -333,15 +334,15 @@ func TestRPCIdentityMismatchCarriesWinnerProfileAcrossAbort(t *testing.T) {
|
|||
cache := newRPCResultCacheWithFlightLimit(time.Now, 2)
|
||||
authKeyID := rpcFlightTestAuthID(88)
|
||||
request := &tg.MessagesGetHistoryRequest{Peer: &tg.InputPeerSelf{}, Limit: 1}
|
||||
winnerIdentity := rpcFlightExactIdentity(t, tg.LayerProfile225, request)
|
||||
loserIdentity := rpcFlightExactIdentity(t, tg.LayerProfile227, request)
|
||||
winner, err := cache.AcquireLayerIdentified(authKeyID, 88, 880, tg.LayerProfile225, winnerIdentity)
|
||||
winnerIdentity := rpcFlightExactIdentity(t, tlprofile.Profile225, request)
|
||||
loserIdentity := rpcFlightExactIdentity(t, tlprofile.Profile227, request)
|
||||
winner, err := cache.AcquireLayerIdentified(authKeyID, 88, 880, tlprofile.Profile225, winnerIdentity)
|
||||
if err != nil || winner.owner == nil {
|
||||
t.Fatalf("winner owner err=%v", err)
|
||||
}
|
||||
_, err = cache.AcquireLayerIdentified(authKeyID, 88, 880, tg.LayerProfile227, loserIdentity)
|
||||
_, err = cache.AcquireLayerIdentified(authKeyID, 88, 880, tlprofile.Profile227, loserIdentity)
|
||||
var mismatch *rpcResultIdentityMismatchError
|
||||
if !errors.As(err, &mismatch) || !mismatch.hasProfile || mismatch.profile != tg.LayerProfile225 {
|
||||
if !errors.As(err, &mismatch) || !mismatch.hasProfile || mismatch.profile != tlprofile.Profile225 {
|
||||
t.Fatalf("mismatch = %#v err=%v", mismatch, err)
|
||||
}
|
||||
if !winner.owner.Abort() {
|
||||
|
|
@ -358,17 +359,17 @@ func TestRPCAdmissionProfileHintSurvivesCompletedEvictionWindow(t *testing.T) {
|
|||
now := time.Unix(1_900_000_000, 0)
|
||||
cache := newRPCResultCacheWithFlightLimit(func() time.Time { return now }, 2)
|
||||
authKeyID := rpcFlightTestAuthID(87)
|
||||
identity := rpcFlightExactIdentity(t, tg.LayerProfile225, &tg.MessagesGetHistoryRequest{
|
||||
identity := rpcFlightExactIdentity(t, tlprofile.Profile225, &tg.MessagesGetHistoryRequest{
|
||||
Peer: &tg.InputPeerSelf{}, Limit: 1,
|
||||
})
|
||||
claim, err := cache.AcquireLayerIdentified(authKeyID, 87, 870, tg.LayerProfile225, identity)
|
||||
claim, err := cache.AcquireLayerIdentified(authKeyID, 87, 870, tlprofile.Profile225, identity)
|
||||
if err != nil || claim.owner == nil {
|
||||
t.Fatalf("owner err=%v", err)
|
||||
}
|
||||
claim.owner.CompleteExecution(true)
|
||||
cache.Put(authKeyID, 87, 870, &encodedOutboundMessage{body: []byte{1}, reqMsgID: 870})
|
||||
profile, ok := cache.ExactAdmissionProfile(authKeyID, 87, 870)
|
||||
if !ok || profile != tg.LayerProfile225 {
|
||||
if !ok || profile != tlprofile.Profile225 {
|
||||
t.Fatalf("profile hint = (%d,%v)", profile, ok)
|
||||
}
|
||||
// Admission already copied the hint into its local decoder cursor. Expiry
|
||||
|
|
@ -385,7 +386,7 @@ func TestRPCAdmissionProfileHintSurvivesCompletedEvictionWindow(t *testing.T) {
|
|||
func TestRPCInvariantIdentityDoesNotExposeCanonicalProfileHint(t *testing.T) {
|
||||
cache := newRPCResultCacheWithFlightLimit(time.Now, 2)
|
||||
authKeyID := rpcFlightTestAuthID(84)
|
||||
identity := rpcFlightExactIdentity(t, tg.LayerProfile227, &tg.AuthBindTempAuthKeyRequest{
|
||||
identity := rpcFlightExactIdentity(t, tlprofile.Profile227, &tg.AuthBindTempAuthKeyRequest{
|
||||
PermAuthKeyID: 1, Nonce: 2, ExpiresAt: 3, EncryptedMessage: []byte("bind"),
|
||||
})
|
||||
claim, err := cache.AcquireLayerIdentified(authKeyID, 84, 840, 0, identity)
|
||||
|
|
|
|||
|
|
@ -15,6 +15,7 @@ import (
|
|||
"github.com/iamxvbaba/td/crypto"
|
||||
"github.com/iamxvbaba/td/proto"
|
||||
"github.com/iamxvbaba/td/tg"
|
||||
"github.com/iamxvbaba/td/tlprofile"
|
||||
)
|
||||
|
||||
type opaqueRPCResult struct{ body []byte }
|
||||
|
|
@ -491,8 +492,7 @@ func encodedRPCResultForPriorityTest(reqMsgID int64, payloadBytes int) *encodedO
|
|||
return &encodedOutboundMessage{
|
||||
typeID: proto.ResultTypeID, reqMsgID: reqMsgID, body: b.Raw(),
|
||||
layer: &outboundLayerBinding{
|
||||
profile: tg.LayerProfileCanonical,
|
||||
typ: tg.LayerClassBoolType().Ref(),
|
||||
profile: tlprofile.ProfileCanonical,
|
||||
kind: outboundLayerBindingRequest,
|
||||
},
|
||||
}
|
||||
|
|
|
|||
|
|
@ -15,6 +15,7 @@ import (
|
|||
"github.com/iamxvbaba/td/bin"
|
||||
"github.com/iamxvbaba/td/proto"
|
||||
"github.com/iamxvbaba/td/tg"
|
||||
"github.com/iamxvbaba/td/tlprofile"
|
||||
)
|
||||
|
||||
// rpcRewrapRegistry links only an explicit official-client transition:
|
||||
|
|
@ -40,8 +41,8 @@ type rpcRewrapSessionKey struct {
|
|||
type rpcRewrapKey struct {
|
||||
rpcRewrapSessionKey
|
||||
fingerprint [sha256.Size]byte
|
||||
semantic tg.LayerSemanticRequestIdentity
|
||||
call tg.LayerCallIdentity
|
||||
semantic tlprofile.SemanticIdentity
|
||||
call tlprofile.CallIdentity
|
||||
exact bool
|
||||
}
|
||||
|
||||
|
|
@ -110,8 +111,8 @@ func (r *rpcRewrapRegistry) register(c *Conn, body []byte, reqMsgID int64, metho
|
|||
|
||||
func (r *rpcRewrapRegistry) registerSemantic(
|
||||
c *Conn,
|
||||
identity tg.LayerSemanticRequestIdentity,
|
||||
call tg.LayerCallIdentity,
|
||||
identity tlprofile.SemanticIdentity,
|
||||
call tlprofile.CallIdentity,
|
||||
reqMsgID int64,
|
||||
method string,
|
||||
owner *rpcResultOwnerLease,
|
||||
|
|
@ -183,8 +184,8 @@ func (r *rpcRewrapRegistry) claim(c *Conn, inner []byte) *rpcRewrapCandidate {
|
|||
|
||||
func (r *rpcRewrapRegistry) claimSemantic(
|
||||
c *Conn,
|
||||
identity tg.LayerSemanticRequestIdentity,
|
||||
call tg.LayerCallIdentity,
|
||||
identity tlprofile.SemanticIdentity,
|
||||
call tlprofile.CallIdentity,
|
||||
) *rpcRewrapCandidate {
|
||||
if r == nil || c == nil || identity.Method() == 0 || identity.CanonicalSize() <= 0 {
|
||||
return nil
|
||||
|
|
|
|||
|
|
@ -17,11 +17,12 @@ import (
|
|||
"github.com/iamxvbaba/td/tgerr"
|
||||
"github.com/iamxvbaba/td/transport"
|
||||
|
||||
"github.com/iamxvbaba/td/tlprofile"
|
||||
"telesrv/internal/rpc"
|
||||
)
|
||||
|
||||
// TestRPCGetConfig 验证 M3:握手后 client 加密 help.getConfig,
|
||||
// server 经 tg.ServerDispatcher 路由并回 rpc_result(含本地 DC),外加 new_session_created + ack。
|
||||
// server 经 tlprofile.Dispatcher 路由并回 rpc_result(含本地 DC),外加 new_session_created + ack。
|
||||
func TestRPCGetConfig(t *testing.T) {
|
||||
const (
|
||||
dc = 2
|
||||
|
|
@ -80,7 +81,7 @@ func TestLayerRPCGetConfigUsesExactAdmittedProfile(t *testing.T) {
|
|||
clientMsgID := proto.NewMessageIDGen(time.Now)
|
||||
reqMsgID := clientMsgID.New(proto.MessageFromClient)
|
||||
request := &tg.InvokeWithLayerRequest{
|
||||
Layer: int(tg.LayerProfile225),
|
||||
Layer: int(tlprofile.Profile225),
|
||||
Query: &tg.InitConnectionRequest{
|
||||
APIID: 123,
|
||||
DeviceModel: "Desktop",
|
||||
|
|
@ -104,10 +105,14 @@ func TestLayerRPCGetConfigUsesExactAdmittedProfile(t *testing.T) {
|
|||
t.Fatalf("rpc_result req_msg_id = %d, want %d", result.RequestMessageID, reqMsgID)
|
||||
}
|
||||
exact := &bin.Buffer{Buf: result.Result}
|
||||
config, err := tg.DecodeLayer(tg.LayerProfile225, tg.LayerConstructorConfigType(), exact)
|
||||
configObject, err := tlprofile.DecodeObject(tlprofile.Profile225, exact, tlprofile.Limits{})
|
||||
if err != nil {
|
||||
t.Fatalf("decode layer 225 config: %v", err)
|
||||
}
|
||||
config, ok := configObject.(*tg.Config)
|
||||
if !ok {
|
||||
t.Fatalf("layer 225 config = %T, want *tg.Config", configObject)
|
||||
}
|
||||
if exact.Len() != 0 || config.ThisDC != dc {
|
||||
t.Fatalf("layer 225 config = dc:%d remaining:%d", config.ThisDC, exact.Len())
|
||||
}
|
||||
|
|
|
|||
|
|
@ -25,6 +25,7 @@ import (
|
|||
"github.com/iamxvbaba/td/tmap"
|
||||
"github.com/iamxvbaba/td/transport"
|
||||
|
||||
"github.com/iamxvbaba/td/tlprofile"
|
||||
"telesrv/internal/store"
|
||||
"telesrv/internal/store/memory"
|
||||
)
|
||||
|
|
@ -57,25 +58,25 @@ type legacyRPCHandlerWithMethod interface {
|
|||
// validate wrapper dependencies and establish exact request identity before
|
||||
// flight/cache/scheduler ownership is acquired.
|
||||
type LayerRPCHandler interface {
|
||||
AdmitLayer(profile tg.LayerProfile, b *bin.Buffer, limits tg.LayerDecodeLimits) (tg.LayerRequest, error)
|
||||
AdmitUnprofiled(b *bin.Buffer, limits tg.LayerDecodeLimits) (tg.LayerRequest, error)
|
||||
AdmitLayer(profile tlprofile.Profile, b *bin.Buffer, limits tlprofile.Limits) (tlprofile.Admission, error)
|
||||
AdmitUnprofiled(b *bin.Buffer, limits tlprofile.Limits) (tlprofile.Admission, error)
|
||||
DispatchAdmitted(
|
||||
ctx context.Context,
|
||||
authKeyID [8]byte,
|
||||
sessionID int64,
|
||||
msgID int64,
|
||||
admissionSeq uint64,
|
||||
request tg.LayerRequest,
|
||||
) (tg.LayerRPCResult, string, error)
|
||||
request tlprofile.Admission,
|
||||
) (tlprofile.Result, string, error)
|
||||
}
|
||||
|
||||
// LayerRPCDefaultProfileAdmitter decodes with a recoverable inherited/default
|
||||
// profile. Production handlers should implement it with the same generated
|
||||
// ServerDispatcher and adapter registry used by AdmitLayer. The split keeps old
|
||||
// profile. Production handlers should implement it with the same sparse
|
||||
// tlprofile dispatcher and semantic adapter registry used by AdmitLayer. The split keeps old
|
||||
// test doubles source-compatible while allowing invokeWithLayer to correct even
|
||||
// a previously explicit Conn profile.
|
||||
type LayerRPCDefaultProfileAdmitter interface {
|
||||
AdmitDefaultLayer(profile tg.LayerProfile, b *bin.Buffer, limits tg.LayerDecodeLimits) (tg.LayerRequest, error)
|
||||
AdmitDefaultLayer(profile tlprofile.Profile, b *bin.Buffer, limits tlprofile.Limits) (tlprofile.Admission, error)
|
||||
}
|
||||
|
||||
// LayerRPCSessionProfileResolver may restore an exact profile only when it was
|
||||
|
|
@ -168,7 +169,7 @@ type LayerRPCReplayPreparer interface {
|
|||
sessionID int64,
|
||||
msgID int64,
|
||||
admissionSeq uint64,
|
||||
request tg.LayerRequest,
|
||||
request tlprofile.Admission,
|
||||
) (afterSuccessfulDelivery func() error, err error)
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -14,6 +14,7 @@ import (
|
|||
|
||||
"github.com/iamxvbaba/td/proto"
|
||||
"github.com/iamxvbaba/td/tg"
|
||||
"github.com/iamxvbaba/td/tlprofile"
|
||||
)
|
||||
|
||||
// ErrSessionNotFound 表示目标 session 当前无活跃连接。
|
||||
|
|
@ -82,7 +83,7 @@ type pendingPushReservation struct {
|
|||
refs atomic.Int32
|
||||
|
||||
mu sync.Mutex
|
||||
profiles map[tg.LayerProfile]struct{}
|
||||
profiles map[tlprofile.Profile]struct{}
|
||||
}
|
||||
|
||||
func (r *pendingPushReservation) retain() {
|
||||
|
|
@ -110,7 +111,7 @@ func (r *pendingPushReservation) release() {
|
|||
// reservePrepared accounts the profile-specific immutable body retained by the
|
||||
// semantic pending fanout. Multiple queued sessions sharing this reservation
|
||||
// and profile share both the bytes and this one budget charge.
|
||||
func (r *pendingPushReservation) reservePrepared(profile tg.LayerProfile, bytes int) bool {
|
||||
func (r *pendingPushReservation) reservePrepared(profile tlprofile.Profile, bytes int) bool {
|
||||
if r == nil || bytes < 0 {
|
||||
return false
|
||||
}
|
||||
|
|
@ -123,7 +124,7 @@ func (r *pendingPushReservation) reservePrepared(profile tg.LayerProfile, bytes
|
|||
return false
|
||||
}
|
||||
if r.profiles == nil {
|
||||
r.profiles = make(map[tg.LayerProfile]struct{})
|
||||
r.profiles = make(map[tlprofile.Profile]struct{})
|
||||
}
|
||||
r.profiles[profile] = struct{}{}
|
||||
r.bytes.Add(int64(bytes))
|
||||
|
|
@ -274,7 +275,7 @@ func (m *SessionManager) SeedInheritedLayerForBusinessAuthKey(businessAuthKeyID
|
|||
if m == nil || businessAuthKeyID == ([8]byte{}) {
|
||||
return 0
|
||||
}
|
||||
profile, ok := tg.ResolveLayerProfile(layer)
|
||||
profile, ok := tlprofile.ResolveProfile(layer)
|
||||
if !ok {
|
||||
return 0
|
||||
}
|
||||
|
|
@ -313,7 +314,7 @@ func (m *SessionManager) applyInheritedLayerForRawAuthKey(rawAuthKeyID [8]byte,
|
|||
if m == nil {
|
||||
return 0
|
||||
}
|
||||
profile, ok := tg.ResolveLayerProfile(layer)
|
||||
profile, ok := tlprofile.ResolveProfile(layer)
|
||||
if !ok {
|
||||
return 0
|
||||
}
|
||||
|
|
@ -364,7 +365,7 @@ func (m *SessionManager) ApplyOrderedLayerProfileForSession(
|
|||
primary *Conn,
|
||||
rawAuthKeyID [8]byte,
|
||||
sessionID int64,
|
||||
profile tg.LayerProfile,
|
||||
profile tlprofile.Profile,
|
||||
msgID int64,
|
||||
) (int, error) {
|
||||
if err := validateLayerProfile(profile); err != nil {
|
||||
|
|
@ -452,7 +453,7 @@ func (m *SessionManager) ExplicitLayerEvidenceForAuthKey(rawAuthKeyID [8]byte, s
|
|||
if c.isRetired() || state.Origin != LayerProfileExplicit {
|
||||
continue
|
||||
}
|
||||
profile, supported := tg.ResolveLayerProfile(int(state.Profile))
|
||||
profile, supported := tlprofile.ResolveProfile(int(state.Profile))
|
||||
if !supported || profile != state.Profile {
|
||||
continue
|
||||
}
|
||||
|
|
@ -477,7 +478,7 @@ func (m *SessionManager) SetClientLayerForAuthKey(rawAuthKeyID [8]byte, sessionI
|
|||
if m == nil {
|
||||
return
|
||||
}
|
||||
profile, ok := tg.ResolveLayerProfile(layer)
|
||||
profile, ok := tlprofile.ResolveProfile(layer)
|
||||
if !ok {
|
||||
return
|
||||
}
|
||||
|
|
|
|||
|
|
@ -15,6 +15,7 @@ import (
|
|||
"github.com/iamxvbaba/td/mt"
|
||||
"github.com/iamxvbaba/td/proto"
|
||||
"github.com/iamxvbaba/td/tg"
|
||||
"github.com/iamxvbaba/td/tlprofile"
|
||||
)
|
||||
|
||||
type closeCountingTransport struct {
|
||||
|
|
@ -226,7 +227,7 @@ func TestSessionManagerBestEffortFanoutPreparesOncePerProfile(t *testing.T) {
|
|||
c.userID.Store(userID)
|
||||
c.userIDResolved.Store(true)
|
||||
c.receivesUpdates.Store(true)
|
||||
if err := c.FreezeLayerProfile(tg.LayerProfile225); err != nil {
|
||||
if err := c.FreezeLayerProfile(tlprofile.Profile225); err != nil {
|
||||
t.Fatalf("freeze profile: %v", err)
|
||||
}
|
||||
sm.Register(c)
|
||||
|
|
@ -263,7 +264,7 @@ func TestSessionManagerMixedLayerFanoutUsesProfileBoundBodies(t *testing.T) {
|
|||
sm := NewSessionManager(zaptest.NewLogger(t))
|
||||
const userID = int64(103)
|
||||
authKeyID := [8]byte{0x22, 0x70, 0x22, 0x80}
|
||||
profiles := []tg.LayerProfile{tg.LayerProfile225, tg.LayerProfile227, tg.LayerProfile228}
|
||||
profiles := []tlprofile.Profile{tlprofile.Profile225, tlprofile.Profile227, tlprofile.Profile228}
|
||||
conns := make([]*Conn, 0, len(profiles))
|
||||
for _, profile := range profiles {
|
||||
c := &Conn{
|
||||
|
|
@ -277,8 +278,8 @@ func TestSessionManagerMixedLayerFanoutUsesProfileBoundBodies(t *testing.T) {
|
|||
c.userID.Store(userID)
|
||||
c.userIDResolved.Store(true)
|
||||
c.receivesUpdates.Store(true)
|
||||
if profile == tg.LayerProfile228 {
|
||||
if err := c.SeedInheritedLayerProfile(tg.LayerProfile227); err != nil {
|
||||
if profile == tlprofile.Profile228 {
|
||||
if err := c.SeedInheritedLayerProfile(tlprofile.Profile227); err != nil {
|
||||
t.Fatalf("seed Alice inherited profile: %v", err)
|
||||
}
|
||||
}
|
||||
|
|
@ -319,7 +320,7 @@ func TestSessionManagerMixedLayerFanoutUsesProfileBoundBodies(t *testing.T) {
|
|||
t.Fatalf("profile %d push leaked channel constructor %#08x", profiles[i], otherChannelID)
|
||||
}
|
||||
input := bin.Buffer{Buf: op.encoded.body}
|
||||
decoded, decodeErr := tg.DecodeLayer(profiles[i], tg.LayerClassUpdatesType(), &input)
|
||||
decoded, decodeErr := tlprofile.DecodeObject(profiles[i], &input, tlprofile.Limits{})
|
||||
if decodeErr != nil || input.Len() != 0 {
|
||||
t.Fatalf("decode profile %d: remaining=%d err=%v", profiles[i], input.Len(), decodeErr)
|
||||
}
|
||||
|
|
@ -397,7 +398,7 @@ func TestSessionManagerBestEffortFanoutUsesOneBudgetAndDropsOnlySlowConsumers(t
|
|||
c.userID.Store(userID)
|
||||
c.userIDResolved.Store(true)
|
||||
c.receivesUpdates.Store(true)
|
||||
if err := c.FreezeLayerProfile(tg.LayerProfile227); err != nil {
|
||||
if err := c.FreezeLayerProfile(tlprofile.Profile227); err != nil {
|
||||
t.Fatalf("freeze profile: %v", err)
|
||||
}
|
||||
sm.Register(c)
|
||||
|
|
@ -415,7 +416,7 @@ func TestSessionManagerBestEffortFanoutUsesOneBudgetAndDropsOnlySlowConsumers(t
|
|||
healthy.userID.Store(userID)
|
||||
healthy.userIDResolved.Store(true)
|
||||
healthy.receivesUpdates.Store(true)
|
||||
if err := healthy.FreezeLayerProfile(tg.LayerProfile227); err != nil {
|
||||
if err := healthy.FreezeLayerProfile(tlprofile.Profile227); err != nil {
|
||||
t.Fatalf("freeze healthy profile: %v", err)
|
||||
}
|
||||
sm.Register(healthy)
|
||||
|
|
@ -747,7 +748,7 @@ func TestPushToUserAuthKeyUsesOneDeadlineAndDropsOnlySlowPFSConnections(t *testi
|
|||
outboundStop: make(chan struct{}),
|
||||
}
|
||||
c.receivesUpdates.Store(true)
|
||||
if err := c.FreezeLayerProfile(tg.LayerProfile227); err != nil {
|
||||
if err := c.FreezeLayerProfile(tlprofile.Profile227); err != nil {
|
||||
t.Fatalf("freeze profile: %v", err)
|
||||
}
|
||||
if queueFull {
|
||||
|
|
@ -912,7 +913,7 @@ func TestPushToSessionForAuthKeyImmediateBypassesReadinessQueue(t *testing.T) {
|
|||
outboundControl: make(chan outboundOp, 1),
|
||||
outboundStop: make(chan struct{}),
|
||||
}
|
||||
if err := c.FreezeLayerProfile(tg.LayerProfile227); err != nil {
|
||||
if err := c.FreezeLayerProfile(tlprofile.Profile227); err != nil {
|
||||
t.Fatalf("freeze profile: %v", err)
|
||||
}
|
||||
sm.Register(c)
|
||||
|
|
@ -991,7 +992,7 @@ func TestSessionManagerWithholdsUpdatesReadinessUntilExactProfile(t *testing.T)
|
|||
default:
|
||||
}
|
||||
|
||||
if err := c.FreezeLayerProfile(tg.LayerProfile225); err != nil {
|
||||
if err := c.FreezeLayerProfile(tlprofile.Profile225); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
c.membershipsSynced.Store(true)
|
||||
|
|
@ -1002,7 +1003,7 @@ func TestSessionManagerWithholdsUpdatesReadinessUntilExactProfile(t *testing.T)
|
|||
case <-time.After(time.Second):
|
||||
t.Fatal("profiled readiness did not flush pending update")
|
||||
}
|
||||
if op.encoded == nil || op.encoded.layer == nil || op.encoded.layer.profile != tg.LayerProfile225 {
|
||||
if op.encoded == nil || op.encoded.layer == nil || op.encoded.layer.profile != tlprofile.Profile225 {
|
||||
t.Fatalf("flushed update layer binding = %#v", op.encoded)
|
||||
}
|
||||
op.releaseReservation(c.outboundTrackedBudget)
|
||||
|
|
@ -1062,7 +1063,7 @@ func TestPendingFlushGlobalBodyPressureDoesNotTerminateHealthyConnection(t *test
|
|||
const userID = int64(606)
|
||||
c.userID.Store(userID)
|
||||
c.userIDResolved.Store(true)
|
||||
if err := c.FreezeLayerProfile(tg.LayerProfileCanonical); err != nil {
|
||||
if err := c.FreezeLayerProfile(tlprofile.ProfileCanonical); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
sm.Register(c)
|
||||
|
|
@ -1160,8 +1161,8 @@ func TestSessionManagerPush(t *testing.T) {
|
|||
if got := srv.Conns().Online(); got != 2 {
|
||||
t.Fatalf("online = %d, want 2", got)
|
||||
}
|
||||
if !srv.Conns().SetLayerProfile(auth1.SessionID, tg.LayerProfile227) ||
|
||||
!srv.Conns().SetLayerProfile(auth2.SessionID, tg.LayerProfile227) {
|
||||
if !srv.Conns().SetLayerProfile(auth1.SessionID, tlprofile.Profile227) ||
|
||||
!srv.Conns().SetLayerProfile(auth2.SessionID, tlprofile.Profile227) {
|
||||
t.Fatal("seed exact test profiles")
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -5,7 +5,7 @@ import (
|
|||
"testing"
|
||||
"time"
|
||||
|
||||
"github.com/iamxvbaba/td/tg"
|
||||
"github.com/iamxvbaba/td/tlprofile"
|
||||
"go.uber.org/zap/zaptest"
|
||||
)
|
||||
|
||||
|
|
@ -67,7 +67,7 @@ func TestSetSessionChannelMembershipsDetectsConcurrentIncrementalUpdates(t *test
|
|||
sm := NewSessionManager(zaptest.NewLogger(t))
|
||||
raw := [8]byte{1, 2, 3}
|
||||
c := &Conn{sessionID: 42, authKeyID: raw}
|
||||
if err := c.FreezeLayerProfile(tg.LayerProfile227); err != nil {
|
||||
if err := c.FreezeLayerProfile(tlprofile.Profile227); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
sm.Register(c)
|
||||
|
|
|
|||
|
|
@ -3,7 +3,7 @@ package mtprotoedge
|
|||
import (
|
||||
"testing"
|
||||
|
||||
"github.com/iamxvbaba/td/tg"
|
||||
"github.com/iamxvbaba/td/tlprofile"
|
||||
"go.uber.org/zap/zaptest"
|
||||
)
|
||||
|
||||
|
|
@ -16,7 +16,7 @@ func TestReceivesUpdatesForAuthKeyRequiresMembershipSync(t *testing.T) {
|
|||
sm := NewSessionManager(zaptest.NewLogger(t))
|
||||
raw := [8]byte{1, 2, 3}
|
||||
c := &Conn{sessionID: 42, authKeyID: raw}
|
||||
if err := c.FreezeLayerProfile(tg.LayerProfile227); err != nil {
|
||||
if err := c.FreezeLayerProfile(tlprofile.Profile227); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
sm.Register(c)
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue