Java 从web应用程序中使用Cassandra驱动程序的正确方法是什么

Java 从web应用程序中使用Cassandra驱动程序的正确方法是什么,java,cassandra,cassandra-2.0,Java,Cassandra,Cassandra 2.0,我想用Java和Cassandra2.x(在Jersey框架上)构建一个RESTful API。我对这两种技术都是新手,所以我想问你们,集成和共享Cassandra驱动程序的正确方法是什么 0。通过Maven获得驱动程序 <dependency> <groupId>com.datastax.cassandra</groupId> <artifactId>cassandra-driver-core<

我想用Java和Cassandra2.x(在Jersey框架上)构建一个RESTful API。我对这两种技术都是新手,所以我想问你们,集成和共享Cassandra驱动程序的正确方法是什么

0。通过Maven获得驱动程序

<dependency>
            <groupId>com.datastax.cassandra</groupId>
            <artifactId>cassandra-driver-core</artifactId>
            <version>2.0.3</version>
</dependency>
2。我在ContextListener中不满足于客户端,并通过上下文属性共享它

package com.example.listener;

import javax.servlet.ServletContext;
import javax.servlet.ServletContextEvent;
import javax.servlet.ServletContextListener;

import com.example.cassandra.Client;

public class ExampleContextListener implements ServletContextListener {

    Client cassandraClient;

    public void contextInitialized(ServletContextEvent servletContextEvent) {
        ServletContext ctx = servletContextEvent.getServletContext();

        cassandraClient = new Client( ctx.getInitParameter( "DBHost" ) );
        ctx.setAttribute( "DB", cassandraClient );
    }

    public void contextDestroyed(ServletContextEvent servletContextEvent) {
        cassandraClient.close();
    }

}
3。现在我从servlet的上下文中获取客户机并使用它

Client client =  (Client) context.getAttribute("DB");
client.execute("USE testspace;");

ResultSet rs = client.execute("SELECT * from users;");
for (Row row : rs ) {
    output += row.getString("lname") + "|";
}
这是正确的方法吗(从性能和体系结构的角度)


完整示例可从以下站点获得:

我刚刚开发了您将要开发的内容。你写的东西很管用,但不是我最喜欢的方法。我宁愿创建一个单例(因为一个应用程序只需要一个会话)。遵循Joshua Bloch enum的singleton模式,我就是这么做的

    public enum Cassandra {

        DB;

        private Session session;
        private Cluster cluster;
        private static final Logger LOGGER = LoggerFactory.getLogger(Cassandra.class);

        /**
         * Connect to the cassandra database based on the connection configuration provided.
         * Multiple call to this method will have no effects if a connection is already established
         * @param conf the configuration for the connection
         */
        public void connect(ConnectionCfg conf) {
            if (cluster == null && session == null) {
                cluster = Cluster.builder().withPort(conf.getPort()).withCredentials(conf.getUsername(), conf.getPassword()).addContactPoints(conf.getSeeds()).build();
                session = cluster.connect(conf.getKeyspace());
            }
            Metadata metadata = cluster.getMetadata();
            LOGGER.info("Connected to cluster: " + metadata.getClusterName() + " with partitioner: " + metadata.getPartitioner());
            metadata.getAllHosts().stream().forEach((host) -> {
                LOGGER.info("Cassandra datacenter: " + host.getDatacenter() + " | address: " + host.getAddress() + " | rack: " + host.getRack());
            });
        }

        /**
         * Invalidate and close the session and connection to the cassandra database
         */
        public void shutdown() {
            LOGGER.info("Shutting down the whole cassandra cluster");
            if (null != session) {
                session.close();
            }
            if (null != cluster) {
                cluster.close();
            }
        }

        public Session getSession() {
            if (session == null) {
                throw new IllegalStateException("No connection initialized");
            }
            return session;
        }
}
在上下文侦听器中,我调用connect或shutdown。 由于新驱动程序中的所有异常都未选中,所以我给您的提示是创建自己的Jersey ExceptionMapping DriverException实现。还有一件事,请考虑使用PreparedStatements而不是字符串,以便Cassandra只解析查询一次。在我的应用程序中,对于查询,我也遵循了上述模式(第一次加载时准备语句的枚举单例,然后公开使用这些语句的方法)

嗯,,
卡洛

再次感谢你,卡洛。正如你所看到的,我放弃了PHP,转而使用Java。这里的司机不会有任何问题;)绝对没有问题。这位新车手做得很好,泽西为restful提供的开箱即用的服务令人惊叹。你不会后悔你的选择!享受吧,CarloHi Carlo,你的意思是说一个单一的Cassandra会话对象对于一个web应用程序来说就足够了。如果我的应用程序用户计数为1000。单个会话对象能满足我的场景吗?请澄清我的疑问。谢谢,我的意思是您只能创建一个会话对象。我已经用过1000多个用户,没有任何问题。请看这里:——“会话实例是线程安全的,通常每个应用程序一个实例就足够了”——HTH,CarloHi,我想知道您是否可以告诉我您在web应用程序中采用的最佳方式?
    public enum Cassandra {

        DB;

        private Session session;
        private Cluster cluster;
        private static final Logger LOGGER = LoggerFactory.getLogger(Cassandra.class);

        /**
         * Connect to the cassandra database based on the connection configuration provided.
         * Multiple call to this method will have no effects if a connection is already established
         * @param conf the configuration for the connection
         */
        public void connect(ConnectionCfg conf) {
            if (cluster == null && session == null) {
                cluster = Cluster.builder().withPort(conf.getPort()).withCredentials(conf.getUsername(), conf.getPassword()).addContactPoints(conf.getSeeds()).build();
                session = cluster.connect(conf.getKeyspace());
            }
            Metadata metadata = cluster.getMetadata();
            LOGGER.info("Connected to cluster: " + metadata.getClusterName() + " with partitioner: " + metadata.getPartitioner());
            metadata.getAllHosts().stream().forEach((host) -> {
                LOGGER.info("Cassandra datacenter: " + host.getDatacenter() + " | address: " + host.getAddress() + " | rack: " + host.getRack());
            });
        }

        /**
         * Invalidate and close the session and connection to the cassandra database
         */
        public void shutdown() {
            LOGGER.info("Shutting down the whole cassandra cluster");
            if (null != session) {
                session.close();
            }
            if (null != cluster) {
                cluster.close();
            }
        }

        public Session getSession() {
            if (session == null) {
                throw new IllegalStateException("No connection initialized");
            }
            return session;
        }
}