[
https://issues.apache.org/jira/browse/CASSANDRA-7837?page=com.atlassian.jira.plugin.system.issuetabpanels:comment-tabpanel&focusedCommentId=14111671#comment-14111671
]
Blake Eggleston commented on CASSANDRA-7837:
--------------------------------------------
[~yukim], I'd vote for doing just what's needed to remove static initialization
at first. Removing static initialization is a big project, removing static
initialization and reworking the api is a *huge* project. Now, removing static
initialization, singletons, etc will naturally entail rethinking some parts of
the api, especially after proposed step 2 is completed, but I'm worried that if
we go in trying to do both, the scope and complexity will get out of control.
We can always continue to refine afterwards.
> Factor out static initialization / singletons
> ---------------------------------------------
>
> Key: CASSANDRA-7837
> URL: https://issues.apache.org/jira/browse/CASSANDRA-7837
> Project: Cassandra
> Issue Type: Improvement
> Reporter: Blake Eggleston
>
> I've been spending some time experimenting with ways to factor out static
> initialization and static singletons in Cassandra.
> This is a known issue, with obvious implications on testability and
> extensibility. It also leads to subtle changes in behavior of the database
> and tests, as access patterns to static methods reorder the initialization
> order of the static state. For instance, the test
> org.apache.cassandra.config.DatabaseDescriptorTest.testKSMetaDataSerialization
> is no longer testing anything, because Schema.getKeyspaceDefinitions() is
> now returning an empty array. Once the initialization order is changed, the
> test fails because system keyspaces aren't being filtered out, and fromThrift
> throws an exceptions when it sees LocalStrategy. Removing static state and
> singletons will make testing each component in isolation easier, leading to
> fewer regressions.
> With a large refactor like this, we'd want to avoid having the refactor
> branch, and the trunk branch diverging too far, or for too long. After a few
> failed attempts, I've worked out a way to perform the refactor in a way that
> can be performed with a series of (relatively) small patches, and avoid a
> big, scary merge. Each patch will build, the tests will pass, and can be
> merged into trunk daily/regularly as they are completed.
> The process is as follows:
> # Condense all static state into static singletons.
> (DatabaseDescriptor.getPartitioner() ->
> DatabaseDescriptor.instance.getPartitioner())
> ** In some cases, classes will need to be split into pairs of instance and
> factory classes, like in the case of Keyspace and ColumnFamilyStore
> # Identify all non-singleton usages of static state (grep for '.instance.'),
> and refactor to pass dependencies into their constructors from their
> instantiating services.
> # Work out and implement an initialization order for the singletons,
> preferring final members passed into their constructor, using volatile
> members assigned during startup where there are circular dependencies.
> ** We should consider splitting some of the singletons into more component
> specific classes before this step. There is definitely a case for making that
> another ticket, but with the non-singleton dependencies clearly defined at
> this point, we will have a clear idea of what can be split up. Doing that
> would reduce the number of circular dependencies between singletons, and make
> this stage a lot easier, with the additional benefit of further modularizing
> the code.
> # Remove static singleton instances. Initialize and start C* from a static
> method that takes a configuration as an argument.
> ** CassandraDaemon and utilities will need to be updated, and we'll need a
> helper method so tests can instantiate the database with a one or two liner.
> Obviously, this is a lot of work, but I think it's worth the effort. I've
> already gone through a few practice runs, and it's doable. I'm happy to do
> the work, with guidance and input from the C* team.
> Thoughts?
--
This message was sent by Atlassian JIRA
(v6.2#6252)