Why COLA 3.0 Cuts Complexity: An Ockham’s Razor‑Driven Redesign

The article reviews the COLA framework’s evolution to version 3.0, explaining how the author applied Ockham’s razor to remove unnecessary commands, interceptors, converters, validators and class‑scanning logic, resulting in a leaner, more maintainable Java backend architecture.

ITPUB
ITPUB
ITPUB
Why COLA 3.0 Cuts Complexity: An Ockham’s Razor‑Driven Redesign

Background

COLA (Component Oriented Lightweight Architecture) is an application‑architecture framework that aims to provide a simple, reproducible and controllable set of guidelines. The author found that the original design contained many superfluous concepts, so COLA 2.0 was upgraded to COLA 3.0 by removing unnecessary features without adding new functionality.

Ockham’s Razor as the Guiding Principle

The upgrade follows Ockham’s razor – “entities should not be multiplied unnecessarily”. The simplest solution that works is preferred, avoiding extra abstraction and indirection.

Design Pitfalls: Over‑Design and Twisty Logic

From a system‑boundary perspective, unclear responsibilities and excessive abstraction lead to “twisty” designs. From an application‑architecture view, over‑design for flexibility creates wrappers, hidden layers and pipelines that hurt readability and increase maintenance cost.

Example Pipeline (original)

public class CreateCSPUExecutor {
    @Resource private InitContextStep initContextStep;
    @Resource private CheckRequiredParamStep checkRequiredParamStep;
    @Resource private CheckUnitStep checkUnitStep;
    @Resource private CheckExpiringDateStep checkExpiringDateStep;
    @Resource private CheckBarCodeStep checkBarCodeStep;
    @Resource private CheckBarCodeImgStep checkBarCodeImgStep;
    @Resource private CheckBrandCategoryStep checkBrandCategoryStep;
    @Resource private CheckProductDetailStep checkProductDetailStep;
    @Resource private CheckSpecImgStep checkSpecImgStep;
    @Resource private CreateCSPUStep createCSPUStep;
    @Resource private CreateCSPULogStep createCSPULogStep;
    @Resource private SendCSPUCreatedEventStep sendCSPUCreatedEventStep;
    public Long create(MyCspuSaveParam myCspuSaveParam){
        SaveCSPUContext context = initContextStep.initContext(myCspuSaveParam);
        checkRequiredParamStep.check(context);
        checkUnitStep.check(context);
        checkExpiringDateStep.check(context);
        checkBarCodeStep.check(context);
        checkBarCodeImgStep.check(context);
        checkBrandCategoryStep.check(context);
        checkProductDetailStep.check(context);
        checkSpecImgStep.check(context);
        createCSPUStep.create(context);
        createCSPULogStep.log(context);
        sendCSPUCreatedEventStep.sendEvent(context);
        return context.getCspu().getId();
    }
}

The author argues that while reusable, this approach adds unnecessary cognitive load. A simpler, more direct implementation is preferred.

Removing the Command Pattern

Initially COLA adopted CQRS with a Command‑Bus to separate commands and queries, but the indirection made the actual executor hidden.

Original command‑bus version

public class MetricsServiceImpl implements MetricsServiceI {
    @Autowired private CommandBusI commandBus;
    @Override public Response addATAMetric(ATAMetricAddCmd cmd){ return commandBus.send(cmd); }
    @Override public Response addSharingMetric(SharingMetricAddCmd cmd){ return commandBus.send(cmd); }
    @Override public Response addPatentMetric(PatentMetricAddCmd cmd){ return commandBus.send(cmd); }
    @Override public Response addPaperMetric(PaperMetricAddCmd cmd){ return commandBus.send(cmd); }
}

After removing the bus, the service directly injects the executors.

After removal

public class MetricsServiceImpl implements MetricsServiceI {
    @Resource private ATAMetricAddCmdExe ataMetricAddCmdExe;
    @Resource private SharingMetricAddCmdExe sharingMetricAddCmdExe;
    @Resource private PatentMetricAddCmdExe patentMetricAddCmdExe;
    @Resource private PaperMetricAddCmdExe paperMetricAddCmdExe;
    @Override public Response addATAMetric(ATAMetricAddCmd cmd){ return ataMetricAddCmdExe.execute(cmd); }
    @Override public Response addSharingMetric(SharingMetricAddCmd cmd){ return sharingMetricAddCmdExe.execute(cmd); }
    @Override public Response addPatentMetric(PatentMetricAddCmd cmd){ return patentMetricAddCmdExe.execute(cmd); }
    @Override public Response addPaperMetric(PaperMetricAddCmd cmd){ return paperMetricAddCmdExe.execute(cmd); }
}

Dropping Interceptors, Converters, Validators, and Assemblers

The framework originally provided interceptor hooks, converters, validators and assemblers to standardise cross‑cutting concerns. Spring’s native AOP already covers most interceptor needs, and naming conventions (Validator vs. Checker) are team‑level decisions. Therefore these components were removed.

Class‑Scanning Optimization

COLA previously copied the TMF (Taobao Middleware Framework) class‑scanning mechanism, which is redundant because Spring already performs classpath scanning. The upgrade switches to Spring’s ListableBeanFactory.getBeansWithAnnotation to discover beans annotated with @Extension, eliminating the custom scanner.

Overall Impact of the Upgrade

The core architectural ideas (onion, adapter, DDD, clean architecture, TMF) remain unchanged. CQRS becomes optional, the command bus is removed, and many auxiliary components are stripped away, leaving a lightweight extension‑point model that aligns with Ockham’s razor.

COLA open‑source address: https://github.com/alibaba/COLA
Original Source

Signed-in readers can open the original source through BestHub's protected redirect.

Sign in to view source
Republication Notice

This article has been distilled and summarized from source material, then republished for learning and reference. If you believe it infringes your rights, please contactadmin@besthub.devand we will review it promptly.

JavaarchitectureCOLAOckham's RazorFramework Simplification
ITPUB
Written by

ITPUB

Official ITPUB account sharing technical insights, community news, and exciting events.

0 followers
Reader feedback

How this landed with the community

Sign in to like

Rate this article

Was this worth your time?

Sign in to rate
Discussion

0 Comments

Thoughtful readers leave field notes, pushback, and hard-won operational detail here.