Skip to content

Latest commit

 

History

History
153 lines (113 loc) · 12.2 KB

File metadata and controls

153 lines (113 loc) · 12.2 KB

Changelog

All notable changes to this project will be documented in this file.

[Unreleased]

✨ New Features

  • Eloquent: Model.fill now accepts a strict flag. When true, any non-fillable key throws MassAssignmentException instead of being silently dropped. Pair with validated request payloads to catch schema drift at the boundary. (#69)
  • Validation: FormRequest — Laravel-style request object that collapses authorize → prepare → validate into a single class. Throws AuthorizationException on denied access and ValidationException with a field-keyed error map on rule failure. Pairs with Model.fill(validated, strict: true). (#66)
  • HTTP: MagicController.authorize(ability, [arguments]), a Laravel-style controller helper that delegates to Gate.allows() and throws AuthorizationException on denial. Avoids hand-rolling gate checks in every action. (#72)
  • Auth: Gate.allowsAny(abilities, [arguments]) and Gate.allowsAll(abilities, [arguments]), short-circuiting sugar for checking multiple abilities at once. (#72)
  • Routing: MagicRoute.resource(name, controller, {only, except}) auto-wires up to four canonical routes (index, create, show, edit) to a controller that mixes in ResourceController. Controllers declare supported methods via resourceMethods; only / except narrow the set further. Each route gets an auto-assigned {slug}.{method} name and title. (#67)
  • Validation: AsyncRule contract plus Unique(endpoint, field: ...) rule, an async uniqueness check with per-instance debounce (coalesces rapid calls) and a pluggable .via() resolver. Network errors log and pass so they never block submission. Validator.validateAsync() runs async rules after sync rules; sync failures short-circuit per field. (#68)
  • Session: Add Session facade with Laravel-style flash data — Session.flash(data), Session.flashErrors(errors), Session.old(field, [fallback]), Session.error(field), Session.errors(field), Session.hasError(field), Session.hasFlash, Session.tick(). Two-bucket store promotes flashed data exactly one navigation hop so forms can repopulate after a failed submit. Top-level helpers old() and error() mirror Laravel's Blade API
  • UI: MagicFormData.validate() automatically flashes form data on validation failure — downstream views can repopulate via old('field') without manual wiring
  • Validation: In<T> rule accepts a primitive whitelist (strings, ints, etc.) and InList<T extends Enum> validates enum-backed fields, accepting either the enum instance or a wire string. InList supports caseInsensitive: and an optional wire: mapper for snake_case or custom representations. Both emit the shared validation.in message with a comma-joined :values parameter. (#81)

[1.0.0-alpha.13] - 2026-04-16

✨ New Features

  • Routing: Add currentPath getter to MagicRouter — returns the current route path without query string, complementing the existing currentLocation property

🐛 Bug Fixes

  • Routing: Use GoRouter.pop() instead of Navigator.pop() in back() — syncs router state and preserves custom page transitions on reverse animation. Add StateError guard when router is not initialized, consistent with to() and replace()

🔧 Improvements

  • Skill: Optimize magic-framework skill for Claude Code progressive disclosure — split frontmatter, extract templates to references, compress sections (669 → 416 lines). Add version frontmatter and source-to-skill mapping in release command
  • Deps: Bump magic version constraint in example app

[1.0.0-alpha.12] - 2026-04-09

✨ New Features

  • Broadcasting: Client-side activity monitor — detects silent connection loss using Pusher protocol activity_timeout and pusher:ping/pusher:pong. Automatically reconnects when the server stops responding
  • Broadcasting: Random jitter (up to 30%) on reconnection backoff delay — prevents thundering herd when many clients reconnect simultaneously after a server restart
  • Broadcasting: Configurable connection establishment timeout (default 15s) — prevents indefinite hang when server doesn't complete the Pusher handshake. Automatically triggers reconnect on timeout

[1.0.0-alpha.11] - 2026-04-07

🐛 Bug Fixes

  • Routing: Fix intermittent page title loss on web — Flutter's Title widget was overwriting TitleManager's route-level title on didChangeDependencies() rebuilds. Use onGenerateTitle to keep both in sync

⚠️ Breaking Changes

  • file_picker: Upgrade from ^10.3.10 to ^11.0.2 — migrates to static API (FilePicker.platform removed). Consumers using FilePicker.platform directly (via magic.dart re-export) must switch to static calls (FilePicker.pickFiles(), FilePicker.getDirectoryPath(), FilePicker.saveFile()). Includes Android path traversal security fix (CWE-22) and WASM web support

[1.0.0-alpha.10] - 2026-04-07

✨ New Features

  • Routing: Route-level page title management with TitleManager singleton. Per-route titles via RouteDefinition.title(), automatic suffix pattern via MagicApplication(titleSuffix:), declarative MagicTitle widget for data-dependent titles, and imperative MagicRoute.setTitle() / MagicRoute.currentTitle API. Title resolution: MagicTitle > setTitle > RouteDefinition.title > MagicApplication.title. (#49)

🔧 Improvements

  • Dependencies: Bump magic_cli to ^0.0.1-alpha.6 (scaffold templates now include .title() and titleSuffix)

[1.0.0-alpha.9] - 2026-04-07

🐛 Bug Fixes

  • Broadcasting: Auth failures in private/presence channels now surface via Log.error() and interceptor onError() chain instead of being silently swallowed. Reconnect resubscribes all channels with awaitonReconnect stream emits only after completion. Per-channel error handling ensures one auth failure does not block other channels. (#45)
  • Database: sqlite3.wasm now loads via absolute URI (/sqlite3.wasm) instead of relative — fixes 404s on deep routes when using path URL strategy. (#46)

[1.0.0-alpha.8] - 2026-04-07

✨ Features

  • feat: config-driven path URL strategy for Flutter web (#40)

[1.0.0-alpha.7] - 2026-04-06

✨ Features

  • Broadcasting: Echo facade, BroadcastManager, ReverbBroadcastDriver (Pusher-compatible WebSocket with reconnection, dedup, heartbeat), NullBroadcastDriver, BroadcastInterceptor pipeline, FakeBroadcastManager, BroadcastServiceProvider. Laravel Echo equivalent for real-time channels. (#38)
  • Router Observers: MagicRouter.instance.addObserver() enables NavigatorObserver integration for analytics/monitoring (Sentry, Firebase Analytics, custom observers). Observers are passed to GoRouter automatically. (#34)
  • Network Driver Plugin Hook: DioNetworkDriver.configureDriver() exposes the underlying Dio instance for SDK integrations (sentry_dio, certificate pinning, custom adapters). (#35)
  • Custom Log Drivers: LogManager.extend() enables custom LoggerDriver registration (Sentry, file, Slack). Config-driven resolution with built-in override support. (#36)

[1.0.0-alpha.6] - 2026-04-05

✨ Features

  • Http Faking: Http.fake() enables Laravel-style HTTP faking for testing. Swap the real network driver with a FakeNetworkDriver that records requests and returns stubbed responses. Supports URL pattern stubs, callback stubs, and assertion methods (assertSent, assertNotSent, assertNothingSent, assertSentCount). (#18)
  • Facade Faking: Auth.fake(), Cache.fake(), Vault.fake(), Log.fake() — Laravel-style facade faking for testing. Swap real service implementations with in-memory fakes that record operations and expose assertion helpers. (#19)
  • Fetch Helpers: fetchList() / fetchOne() on MagicStateMixin — auto state management for HTTP fetches with defensive type guards against malformed responses (#20)
  • MagicTest: MagicTest.init() / MagicTest.boot() — standardized test bootstrap helper, package:magic/testing.dart barrel export (#21)

🐛 Bug Fixes

  • Log.channel(): Now returns LoggerDriver via _manager.driver(name) instead of LogManager, enabling Log.channel('slack').error(...) as documented (#27)
  • Http.response() null data: Sentinel pattern allows Http.response(null, 204) for No Content stubs while Http.response() still returns mutable empty map (#26)
  • URL pattern escaping: FakeNetworkDriver stub patterns now escape regex metacharacters (., ?, +) via RegExp.escape() — only * is treated as wildcard (#26)
  • fetchList/fetchOne defensive guards: Type-check response.data as Map before indexing, filter non-Map elements in lists via whereType<Map>(), guard fetchOne data cast (#28)

[1.0.0-alpha.5] - 2026-03-29

🐛 Bug Fixes

  • Route Back Navigation: MagicRoute.back() now works after go()-based navigation (cross-shell). Maintains lightweight history stack with automatic fallback. Optional fallback parameter for explicit control. (#11)

[1.0.0-alpha.4] - 2026-03-29

🔧 Improvements

  • Localization Hot Restart: Translation JSON changes now reflect on hot restart during development. Uses fetch with cache-busting on web and best-effort disk reads on desktop, bypassing Flutter's asset bundle cache. Zero impact on release builds.

[1.0.0-alpha.3] - 2026-03-24

🐛 Bug Fixes

  • Logo on pub.dev: Use absolute URL for logo image so it renders correctly on pub.dev

🔧 Improvements

  • TDD Development Flow: Added strict TDD rules and verification cycle to CLAUDE.md

[1.0.0-alpha.2] - 2026-03-24

⚠️ Breaking Changes

  • Pub.dev Migration: Replaced git submodule path dependencies with pub.dev hosted packages (fluttersdk_wind: ^1.0.0-alpha.4, magic_cli: ^0.0.1-alpha.3). Removed plugins/ directory entirely.
  • SDK Bump: Dart >=3.11.0 <4.0.0, Flutter >=3.41.0 (previously Dart >=3.4.0, Flutter >=3.22.0)

✨ New Features

  • Launch Facade: URL, email, phone, and SMS launching via url_launcher with Launch.url(), Launch.email(), Launch.phone(), Launch.sms()
  • Form Processing: process(), isProcessing, and processingListenable on MagicFormData for form-scoped loading state
  • Reactive Auth State: stateNotifier on Guard contract and BaseGuard for reactive auth state UI
  • Query Parameters: Request.query(), Request.queryAll, MagicRouter.queryParameter() for URL query parameter access
  • Localization Interceptor: Automatic Accept-Language and X-Timezone headers on HTTP requests
  • Theme Persistence: Auto-persist dark/light theme preference via Vault in MagicApplication
  • Validation Helpers: clearErrors() and clearFieldError() on ValidatesRequests mixin
  • Route Names: Route name registration on RouteDefinition

🐛 Bug Fixes

  • Auth Config: Default config now properly wrapped under 'auth' key
  • Session Restore: Guards against missing userFactory — gracefully skips instead of throwing
  • Barrel Export: FileStore exported from barrel file
  • Package Name: Renamed internal references from fluttersdk_magic to magic

🔧 Improvements

  • Dependency Upgrades: go_router ^17.1.0, sqlite3 ^3.2.0, share_plus ^12.0.1, file_picker ^10.3.10, flutter_lints ^6.0.0, and more
  • CLI Docs: Rewrote Magic CLI documentation with all 16 commands and dart run magic:magic syntax
  • Wind UI Docs: Moved to wind.fluttersdk.com, removed local copy
  • Example App: Rebuilt with fresh flutter create and magic install
  • CI Pipeline: Upgraded GitHub Actions, added validate gate to publish workflow
  • Claude Code: Added path-scoped .claude/rules/ for 8 domains, auto-format and auto-analyze hooks

[1.0.0-alpha.1] - 2026-02-05

✨ Core Features

  • Laravel-inspired MVC architecture
  • Eloquent-style ORM with relationships
  • GoRouter-based routing with middleware support
  • Service Provider pattern
  • Facade pattern for global access
  • Policy-based authorization

📦 Package Structure

  • Complete model system with HasTimestamps, InteractsWithPersistence
  • HTTP client with interceptors
  • Form validation system
  • Event/Listener system

🔧 Developer Experience

  • Magic CLI integration
  • Hot reload support
  • AI agent documentation