@company-semantics/contracts 0.49.0 → 0.51.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@company-semantics/contracts",
3
- "version": "0.49.0",
3
+ "version": "0.51.0",
4
4
  "private": false,
5
5
  "repository": {
6
6
  "type": "git",
package/src/auth/index.ts CHANGED
@@ -16,3 +16,10 @@ export enum OTPErrorCode {
16
16
  AlreadyUsed = 'already_used',
17
17
  NotFound = 'not_found',
18
18
  }
19
+
20
+ export type AuthStartMode = "otp" | "sso" | "hybrid";
21
+
22
+ export type AuthStartResponse =
23
+ | { mode: "otp"; devOtp?: string }
24
+ | { mode: "sso"; providers: string[]; redirectUrl: string }
25
+ | { mode: "hybrid"; providers: string[]; recommendedProvider?: string; otpAllowed: true; devOtp?: string };
@@ -0,0 +1,29 @@
1
+ /**
2
+ * Company admin types — shared vocabulary for cross-org admin control plane.
3
+ *
4
+ * These types support the company admin MVP (read-only).
5
+ * @see PRD-00113 for design rationale.
6
+ */
7
+
8
+ /** Read-only capabilities for company admin MVP. */
9
+ export type CompanyCapability =
10
+ | 'company.view_orgs'
11
+ | 'company.view_audit'
12
+ | 'company.view_system';
13
+
14
+ /** Context attached to company-admin requests after auth middleware validation. */
15
+ export interface CompanyAdminContext {
16
+ readonly kind: 'company';
17
+ readonly adminEmail: string;
18
+ readonly capabilities: readonly CompanyCapability[];
19
+ }
20
+
21
+ /**
22
+ * Discriminated union for request contexts.
23
+ *
24
+ * Org-scoped requests carry OrgScopedContext (kind: 'org').
25
+ * Company admin requests carry CompanyAdminContext (kind: 'company').
26
+ */
27
+ export type RequestContext =
28
+ | (import('./org/types').OrgScopedContext & { readonly kind: 'org' })
29
+ | CompanyAdminContext;
@@ -50,6 +50,13 @@ export interface EmailPayloads {
50
50
  /** User agent of the request (for security context) */
51
51
  userAgent?: string
52
52
  }
53
+ 'org.invite': {
54
+ inviterName: string
55
+ orgName: string
56
+ role: 'admin' | 'member'
57
+ acceptUrl: string
58
+ expiresInDays: number
59
+ }
53
60
  'security.alert': {
54
61
  /** Type of security alert */
55
62
  alertType: 'excessive_otp_requests' | 'unusual_login_location'
@@ -6,7 +6,14 @@
6
6
  */
7
7
 
8
8
  // Types
9
- export type { ISODateString, NameSource, UserIdentity } from './types';
9
+ export type {
10
+ ISODateString,
11
+ NameSource,
12
+ UserIdentity,
13
+ UserLifecycleStatus,
14
+ DeletionBlocker,
15
+ AccountDeletionEligibility,
16
+ } from './types';
10
17
 
11
18
  // Functions - Display Name
12
19
  export {
@@ -94,3 +94,36 @@ export type UserIdentity = {
94
94
  */
95
95
  slackAvatarLastSyncedAt?: ISODateString;
96
96
  };
97
+
98
+ // =============================================================================
99
+ // User Lifecycle
100
+ // =============================================================================
101
+
102
+ /**
103
+ * User lifecycle status. Replaces the boolean `isActive` field.
104
+ *
105
+ * State transitions:
106
+ * active → pending_deletion (self-service deletion request)
107
+ * pending_deletion → active (cancel during grace period)
108
+ * pending_deletion → deleted (async purge after grace period)
109
+ * deleted → (terminal, no transitions)
110
+ * active → deleted (FORBIDDEN — must pass through pending_deletion)
111
+ */
112
+ export type UserLifecycleStatus = 'active' | 'pending_deletion' | 'deleted';
113
+
114
+ /**
115
+ * Conditions that block account deletion.
116
+ * Discriminated union — extend with new blocker types without breaking changes.
117
+ */
118
+ export type DeletionBlocker =
119
+ | { type: 'sole_workspace_owner'; workspaceId: string; workspaceName: string }
120
+ | { type: 'active_legal_hold'; holdId: string };
121
+
122
+ /**
123
+ * Result of an account deletion eligibility check.
124
+ * Invariant: eligible=true ↔ blockers.length === 0
125
+ */
126
+ export type AccountDeletionEligibility = {
127
+ eligible: boolean;
128
+ blockers: DeletionBlocker[];
129
+ };
package/src/index.ts CHANGED
@@ -106,7 +106,14 @@ export type { Compatibility, Deprecation } from './compatibility'
106
106
 
107
107
  // User identity types and functions
108
108
  // @see ADR-CONT-032 for design rationale
109
- export type { ISODateString, NameSource, UserIdentity } from './identity/index'
109
+ export type {
110
+ ISODateString,
111
+ NameSource,
112
+ UserIdentity,
113
+ UserLifecycleStatus,
114
+ DeletionBlocker,
115
+ AccountDeletionEligibility,
116
+ } from './identity/index'
110
117
  export { extractFirstWord, resolveDisplayName, deriveFullName } from './identity/index'
111
118
 
112
119
  // Avatar types and functions
@@ -337,6 +344,14 @@ export type {
337
344
  // Ralph constants (cross-repo support)
338
345
  export { REPO_PRECEDENCE } from './ralph/index'
339
346
 
347
+ // Company admin types (cross-org control plane)
348
+ // @see PRD-00113 for design rationale
349
+ export type {
350
+ CompanyCapability,
351
+ CompanyAdminContext,
352
+ RequestContext,
353
+ } from './company-admin'
354
+
340
355
  // Rate limit domain types
341
356
  // @see PRD-00013 for contracts integration
342
357
  export type { RateLimitConfig, RateLimitResult } from './rate-limit/index'
package/src/org/types.ts CHANGED
@@ -328,6 +328,8 @@ export interface UserOrgMembership {
328
328
  joinedAt: string;
329
329
  /** Whether this membership is currently active. */
330
330
  isActive: boolean;
331
+ /** Organization type (personal vs shared). */
332
+ orgType: OrgType;
331
333
  }
332
334
 
333
335
  // ─────────────────────────────────────────────────────────────────────────────