moose_core 1.3.0 copy "moose_core: ^1.3.0" to clipboard
moose_core: ^1.3.0 copied to clipboard

Core architecture for modular Flutter e-commerce applications with plugin-based architecture, repository pattern, and configurable UI sections.

moose_core #

pub package

A comprehensive, production-ready core architecture package for building modular Flutter e-commerce applications.

Features #

  • Plugin-Based Architecture: Modular feature plugins with clean boundaries
  • Repository Pattern: Abstract data layer with swappable backend adapters
  • BLoC State Management: Built-in support for predictable state management
  • FeatureSection Pattern: Configurable, reusable UI sections
  • Registry Systems: Widget, Adapter, Action, Hook, and Addon registries
  • Cache Management: Multi-layer caching with TTL support
  • Configuration System: JSON-based external configuration
  • Modular Imports: Import entire package or specific modules for optimized builds
  • Type-Safe APIs: Generic methods with compile-time type checking
  • AI-Ready Documentation: Comprehensive documentation for AI-assisted development

Quick Start #

Installation #

Add to your pubspec.yaml:

dependencies:
  moose_core: ^1.0.0

Import Options #

// Option 1: Import everything (recommended for most cases)
import 'package:moose_core/moose_core.dart';

// Option 2: Import specific modules (for optimized builds)
import 'package:moose_core/app.dart';            // MooseAppContext, MooseScope, MooseBootstrapper
import 'package:moose_core/entities.dart';       // Domain entities
import 'package:moose_core/repositories.dart';   // Repository interfaces
import 'package:moose_core/plugin.dart';         // Plugin system
import 'package:moose_core/widgets.dart';        // UI components
import 'package:moose_core/adapters.dart';       // Adapter pattern
import 'package:moose_core/cache.dart';          // Caching system
import 'package:moose_core/services.dart';       // Utilities & helpers

Basic Usage #

import 'package:moose_core/moose_core.dart';

// 1. Bootstrap the app with MooseAppContext + MooseScope
void main() async {
  WidgetsFlutterBinding.ensureInitialized();
  await CacheManager.initPersistentCache();
  final appContext = MooseAppContext();
  runApp(MooseScope(
    appContext: appContext,
    child: AppBootstrap(appContext: appContext),
  ));
}

class AppBootstrap extends StatefulWidget {
  final MooseAppContext appContext;
  const AppBootstrap({super.key, required this.appContext});
  @override State<AppBootstrap> createState() => _AppBootstrapState();
}

class _AppBootstrapState extends State<AppBootstrap> {
  bool _ready = false;

  @override
  void initState() {
    super.initState();
    MooseBootstrapper(appContext: widget.appContext).run(
      config: {'adapters': {'woocommerce': {'baseUrl': 'https://mystore.com'}}},
      adapters: [WooCommerceAdapter()],
      plugins: [() => ProductsPlugin()],
    ).then((_) { if (mounted) setState(() => _ready = true); });
  }

  @override
  Widget build(BuildContext context) => _ready
      ? const MyApp()
      : const Scaffold(body: Center(child: CircularProgressIndicator()));
}

// 2. Create a plugin — use inherited registry getters (hookRegistry, widgetRegistry, etc.)
class ProductsPlugin extends FeaturePlugin {
  @override String get name => 'products';
  @override String get version => '1.0.0';

  @override
  void onRegister() {
    // widgetRegistry, hookRegistry, addonRegistry, etc. delegate to injected appContext
    widgetRegistry.register(
      'products.featured',
      (context, {data, onEvent}) => FeaturedProductsSection(
        settings: data?['settings'] as Map<String, dynamic>?,
      ),
    );
  }

  @override Future<void> onInit() async {}

  @override
  Map<String, WidgetBuilder>? getRoutes() => {
    '/products': (_) => ProductsListScreen(),
  };
}

// 3. Create a FeatureSection — use adaptersOf(context) inside build()
class FeaturedProductsSection extends FeatureSection {
  const FeaturedProductsSection({super.key, super.settings});

  @override
  Map<String, dynamic> getDefaultSettings() => {
    'title': 'FEATURED PRODUCTS',
    'itemCount': 10,
  };

  @override
  Widget build(BuildContext context) {
    final repository = adaptersOf(context).getRepository<ProductsRepository>();
    return BlocProvider(
      create: (_) => FeaturedProductsBloc(repository)
        ..add(const LoadFeaturedProducts()),
      child: BlocBuilder<FeaturedProductsBloc, FeaturedProductsState>(
        builder: (context, state) {
          if (state is FeaturedProductsLoaded) return _buildProducts(state.products);
          if (state is FeaturedProductsError) return Text(state.message);
          return const CircularProgressIndicator();
        },
      ),
    );
  }
}

// 4. Create a backend adapter — hookRegistry and eventBus are set before initializeFromConfig
class WooCommerceAdapter extends BackendAdapter {
  @override String get name => 'woocommerce';
  @override String get version => '1.0.0';

  @override
  Future<void> initializeFromConfig({ConfigManager? configManager}) async {
    registerRepositoryFactory<ProductsRepository>(
      () => WooProductsRepository(apiClient, hookRegistry: hookRegistry, eventBus: eventBus),
    );
    registerRepositoryFactory<CartRepository>(
      () => WooCartRepository(apiClient, hookRegistry: hookRegistry, eventBus: eventBus),
    );
  }
}

Core Concepts #

Plugin System #

Every feature is a self-contained plugin:

class MyPlugin extends FeaturePlugin {
  @override
  String get name => 'my_plugin';

  @override
  void onRegister() {
    // widgetRegistry, hookRegistry, actionRegistry, etc. are available as
    // inherited getters backed by the injected MooseAppContext
    widgetRegistry.register('my.section', (ctx, {data, onEvent}) => MySection());
    hookRegistry.register('my:hook', (data) => processData(data));
    actionRegistry.register('my.action', (ctx, payload) async { /* ... */ });
  }

  @override
  Future<void> onInit() async {
    // Async initialization (called after all plugins are registered)
  }

  @override
  Map<String, WidgetBuilder>? getRoutes() => {
    '/my-route': (_) => MyScreen(),
  };
}

Repository Pattern #

Abstract interfaces with backend-specific implementations:

// Core repository interface (abstract, defined in moose_core)
abstract class ProductsRepository extends CoreRepository {
  Future<ProductListResult> getProducts({ProductFilters? filters});
  Future<Product> getProductById(String id);
}

// Backend implementation — forward hookRegistry and eventBus to super
class WooProductsRepository extends ProductsRepository {
  final ApiClient _apiClient;

  WooProductsRepository(this._apiClient, {
    required super.hookRegistry,
    required super.eventBus,
  });

  @override
  Future<ProductListResult> getProducts({ProductFilters? filters}) async {
    // WooCommerce-specific implementation
  }
}

FeatureSection Pattern #

Configurable UI sections:

class MySection extends FeatureSection {
  const MySection({super.key, super.settings});

  @override
  Map<String, dynamic> getDefaultSettings() {
    return {
      'title': 'Default Title',
      'itemCount': 5,
    };
  }

  @override
  Widget build(BuildContext context) {
    final title = getSetting<String>('title');
    final count = getSetting<int>('itemCount');
    // Build UI...
  }
}

Registry Systems #

WidgetRegistry

Dynamic widget composition. In plugins use the inherited getter; in widgets use context.moose:

// In a plugin's onRegister():
widgetRegistry.register('my.widget', (context, {data, onEvent}) => MyWidget());

// In any widget's build(context):
final widget = context.moose.widgetRegistry.build('my.widget', context);

AdapterRegistry

Backend adapter management. In FeatureSection.build() use adaptersOf(context):

// In a FeatureSection's build(context):
final repo = adaptersOf(context).getRepository<ProductsRepository>();

// In any other widget's build(context):
final repo = context.moose.adapterRegistry.getRepository<ProductsRepository>();

ActionRegistry

Custom action handling:

// In a plugin's onRegister():
actionRegistry.register('custom_action', (context, payload) async {
  // Handle action
});

// In any widget's build(context):
context.moose.actionRegistry.execute('custom_action', context, payload);

EventBus

Asynchronous event-driven communication between plugins:

// In a plugin — fire events using the inherited getter:
eventBus.fire(
  'cart.item.added',
  data: {'productId': 'prod-123', 'quantity': 2},
  metadata: {'cartTotal': 99.99},
);

// In a plugin — subscribe to events:
final subscription = eventBus.on('cart.item.added', (event) {
  final productId = event.data['productId'];
});

// Async event handlers:
eventBus.onAsync('order.placed', (event) async {
  await sendConfirmationEmail(event.data['orderId']);
});

// In a widget — use context.moose:
context.moose.eventBus.fire('my.event', data: {});

// Clean up
await subscription.cancel();

HookRegistry

Synchronous data transformation and service hooks:

// In a plugin's onRegister() — expose hooks using inherited getter:
hookRegistry.register('cart:get_cart_item_count', (data) {
  if (state is CartLoaded) return state.cart.itemCount;
  return 0;
});

hookRegistry.register('cart:item_count_stream', (data) {
  return cartBloc.stream.map((state) => state.totalItems).distinct();
});

// In a widget — consume hooks via context.moose:
final count = context.moose.hookRegistry.execute<int>('cart:get_cart_item_count', 0);
final stream = context.moose.hookRegistry.execute<Stream<int>>(
  'cart:item_count_stream',
  const Stream<int>.empty(),
);

Architecture #

┌─────────────────────────────────────────────┐
│         Presentation Layer                  │
│         (Screens, Sections)                 │
└──────────────────┬──────────────────────────┘
                   │ Events/States
┌──────────────────▼──────────────────────────┐
│         Business Logic (BLoC)               │
└──────────────────┬──────────────────────────┘
                   │ Repository Calls
┌──────────────────▼──────────────────────────┐
│         Repository Interfaces               │
└──────────────────┬──────────────────────────┘
                   │ Implementation
┌──────────────────▼──────────────────────────┐
│         Backend Adapters                    │
│         (WooCommerce, Shopify, etc.)        │
└─────────────────────────────────────────────┘

Package Modules #

The package is organized into focused modules for better maintainability and selective imports:

Module Description Key Exports
app.dart Scoped architecture MooseAppContext, MooseScope, MooseBootstrapper
entities.dart Domain entities Product, Cart, Order, Category, etc.
repositories.dart Repository interfaces ProductsRepository, CartRepository, etc.
plugin.dart Plugin system FeaturePlugin, PluginRegistry
widgets.dart UI components FeatureSection, WidgetRegistry, AddonRegistry
adapters.dart Adapter pattern BackendAdapter, AdapterRegistry
cache.dart Caching system CacheManager, MemoryCache, PersistentCache
services.dart Utilities & helpers EventBus, HookRegistry, ActionRegistry, ApiClient, Logger

Documentation #

  • Architecture Guide - Complete architectural patterns
  • Plugin System - Creating and using plugins
  • FeatureSection Guide - Building configurable sections
  • Adapter Pattern - Backend adapter implementation
  • Event System Guide - EventBus and HookRegistry usage
  • Registries - Using registry systems
  • Anti-Patterns - What to avoid
  • API Reference - Complete API documentation
  • Migration Guide - Modular structure migration

Example Projects #

See the example directory for complete working examples:

  • Basic plugin implementation
  • Custom adapter creation
  • FeatureSection usage
  • Full app integration

AI-Assisted Development #

This package is designed for AI-assisted development with comprehensive AI-ready documentation. See doc/ai-ready/README.md for:

  • Architectural patterns for AI agents
  • Code generation guidelines
  • Anti-patterns to avoid
  • Best practices

Requirements #

  • Dart SDK: >=3.0.0 <4.0.0
  • Flutter: >=3.0.0

Dependencies #

  • flutter_bloc - State management
  • equatable - Value equality
  • dio - HTTP client
  • shared_preferences - Local storage
  • intl - Internationalization

Contributing #

Contributions are welcome! Please read our Contributing Guide for details.

License #

This project is licensed under the MIT License - see the LICENSE file for details.

Support #

Changelog #

See CHANGELOG.md for version history.

0
likes
0
points
508
downloads

Publisher

verified publishermooseapp.ai

Weekly Downloads

Core architecture for modular Flutter e-commerce applications with plugin-based architecture, repository pattern, and configurable UI sections.

Repository (GitHub)
View/report issues

Topics

#ecommerce #architecture #plugin #repository-pattern #bloc

Documentation

Documentation

License

unknown (license)

Dependencies

dio, equatable, flutter, flutter_bloc, intl, json_schema, shared_preferences

More

Packages that depend on moose_core