Weave Code
Weaver
Helps Laravel developers discover, compare, and choose open-source packages. See popularity, security, maintainers, and scores at a glance to make better decisions.
Feedback
Share your thoughts, report bugs, or suggest improvements.
Subject
Message

Settings Module Laravel Package

anomaly/settings-module

Anomaly Settings Module provides a Laravel-based settings management interface for Anomaly CMS, letting administrators define, organize, and edit configurable settings through Streams fields and a simple control panel.

View on GitHub
Deep Wiki
Context7

Getting Started

The settings module ships as part of the Streams Platform ecosystem (and PyroCMS), so in most projects it is already present transitively — confirm with composer show anomaly/settings-module before adding it explicitly. If you do need it, composer require anomaly/settings-module inside a Streams-enabled Laravel app is the only install step; Streams auto-discovers modules in vendor/ and addons/, so no manual service-provider wiring is required.

The first place to look is the repository contract, not the Eloquent model:

  • Anomaly\SettingsModule\Setting\Contract\SettingRepositoryInterface
  • Anomaly\SettingsModule\Setting\SettingRepository
  • The setting() helper (defined by the module) for the 90% case

Your first real use case is almost always "read a stored setting with a sane fallback," e.g. in a view composer or controller:

$value = setting('anomaly.module.settings::example', 'default');

If you plan to expose settings in the control panel, the next stop is a module's resources/config/settings.php, which the settings module renders into an admin form automatically. Treat that config file as the source of truth for the setting key, field type, and default.

Implementation Patterns

Repository over helper for anything non-trivial. Resolve the repository via the container rather than importing the model:

use Anomaly\SettingsModule\Setting\Contract\SettingRepositoryInterface;

public function __construct(SettingRepositoryInterface $settings)
{
    $this->settings = $settings;
}

get() returns a setting entry object, not a raw scalar. Access the value through the entry ($entry->value or the entry's presenter/value accessor), or use the setting() helper when you genuinely want the processed scalar. Don't assume $settings->get('foo') is a string.

Namespace aggressively. Settings are scoped by namespace. The default namespace is the settings module itself; for addons use the vendor.module pattern:

$this->settings->namespace('acme.module.blog')->get('per_page', 10);

Set the namespace once in a service provider or a base class so every call in a package is scoped consistently.

Define settings declaratively. In resources/config/settings.php:

return [
    'per_page' => [
        'type' => 'anomaly.field_type.integer',
        'default' => 15,
    ],
    'enabled' => [
        'type' => 'anomaly.field_type.boolean',
        'default' => true,
    ],
];

The module uses the field type to render the CP form and to translate the stored value back into a typed value. This is the idiomatic integration point — resist the urge to build a bespoke settings page.

Reads in hot paths. Settings are DB-backed; if you read the same key on every request (e.g. in a middleware or a Blade component rendered many times), wrap the lookup or cache the result per-request. The repository does not guarantee per-request memoization across namespaces.

Writes and reset. For programmatic writes, use set()/forget() on the repository, and prefer doing so in migrations, seeders, or installers so the settings table is populated consistently. Direct SettingModel access bypasses field-type casting and will produce values that don't round-trip through the CP form.

Testing. Because everything resolves through SettingRepositoryInterface, bind a fake or in-memory implementation in tests instead of touching the database; that keeps tests fast and decoupled from the module's migrations.

Gotchas and Tips

  • Entry vs scalar. $settings->get('key') yields an entry object. The most common bug is treating it as a string. Use ->value (or the helper) deliberately and be explicit about which you want.
  • Namespace leakage. Unprefixed keys resolve against whatever namespace is currently active. In shared code, always call namespace(...) before get()/set(), otherwise a different service provider's default can silently win.
  • Settings vs. config precedence. DB-backed settings do not replace framework config — they sit alongside it. Decide which layer is authoritative (typically: config default, settings override) and document it, or you'll get "it works locally but not in prod" bugs.
  • Serialization of complex field types. Boolean, select, editor, and relationship field types are not stored as plain strings. Reading them raw from the settings table will mislead you during debugging; always read through the repository so the field type casts the value.
  • Missing keys return null/default, not an exception. has() is your friend when you need to distinguish "unset" from "set to null/default." Don't rely on get() alone to tell the difference.
  • Direct DB edits are a trap. Editing the settings table by hand skips validation and casting. If you must, re-save through the CP or a seeder afterward so the field type re-casts the value.
  • Extension points. Custom setting types come from anomaly/field_type-* packages, not from the settings module itself. If you need a new control, add a field type rather than forking settings. Custom settings sections are registered from a module's service provider; keep them in the module that owns the settings, not in a central place.
  • Debugging workflow. When a setting "doesn't stick," in order: (1) dump $settings->namespace(...)->get('key') including the entry, (2) verify the key exists in resources/config/settings.php and the field type is installed, (3) check the settings table row's namespace column matches what your code expects, (4) clear any settings/cache layer.
  • Small package, large blast radius. One star and zero direct dependents undercount its importance — it is infrastructure for Streams/Pyro, so support, security posture, and release cadence follow the parent platform, not this repo's activity. Follow the Streams Platform release notes rather than this package's issue tracker.
  • License is NOASSERTION. There's no machine-readable license declaration. Confirm licensing terms with the vendor or the parent Streams repository before shipping it in a commercial product.
Weaver

How can I help you explore Laravel packages today?

Conversation history is not saved when not logged in.
Prompt
Add packages to context
No packages found.
elsayed85/laravel-api-exceptions
ouhssini/laravel-demo-mode
daworks/ncloud-outbound-mailer-driver
gp247/cms
ignibyte/aic-gates
nexa-merchant/blog
novasa/laravel-language-center
opencage/geocode
adolfoholzer/parameters
livenetworks/ln-starter
shitoudev/permissionmanager
johannesclimacus/laravel-tui
hocvt/seotools
vitalybaev/sypexgeo
amphibee/themosis-ignition
gito-me/fast-excel
frankyso/laravel-ipaymu
geolize-studio/laravel-chile
boomerangui/chat
cgv/localized-resource