仅当数据库,模式和表不存在时才自动创建它们
我想创建一个简单的网络应用程序
I want to create a simple webapp that
- 允许远程客户端跟踪发布请求中的某些内容
- 将所有跟踪保持在轻量级数据库中
- 在获取请求时返回所有跟踪
关于数据库,我想
- 将其位置放入我的Web应用程序的属性文件中(并将此位置用于persistence.xml中设置的hibernate.location.url)
- 如果数据库和架构和表尚不存在,则使用它们创建数据库
- 使用现有的数据库和架构以及表和数据(如果存在)
所以我用以下方法创建了一个Maven项目:
So I created a maven project with:
pom.xml
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>org.my.tracker</groupId>
<artifactId>tracker-webapp</artifactId>
<version>0.1-SNAPSHOT</version>
<packaging>war</packaging>
<properties>
<hibernate.version>4.3.8.Final</hibernate.version>
<h2.version>1.4.185</h2.version>
</properties>
<build>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-eclipse-plugin</artifactId>
<version>2.9</version>
<configuration>
<downloadSources>true</downloadSources>
<downloadJavadocs>false</downloadJavadocs>
</configuration>
</plugin>
<!-- Set a compiler level -->
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-compiler-plugin</artifactId>
</plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-war-plugin</artifactId>
<version>2.6</version>
</plugin>
</plugins>
</build>
<dependencies>
<!-- Servlet API -->
<dependency>
<groupId>javax.servlet</groupId>
<artifactId>javax.servlet-api</artifactId>
<version>3.1.0</version>
<scope>provided</scope>
</dependency>
<!-- JPA Provider (Hibernate) -->
<dependency>
<groupId>org.hibernate</groupId>
<artifactId>hibernate-entitymanager</artifactId>
<version>${hibernate.version}</version>
</dependency>
<dependency>
<groupId>org.hibernate</groupId>
<artifactId>hibernate-core</artifactId>
<version>${hibernate.version}</version>
</dependency>
<!-- Database (H2) -->
<dependency>
<groupId>com.h2database</groupId>
<artifactId>h2</artifactId>
<version>${h2.version}</version>
</dependency>
</dependencies>
</project>
src/main/resources/META-INF/persistence.xml
src/main/resources/META-INF/persistence.xml
<?xml version="1.0" encoding="UTF-8" ?>
<persistence xmlns="http://java.sun.com/xml/ns/persistence"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://java.sun.com/xml/ns/persistence
http://java.sun.com/xml/ns/persistence/persistence_1_0.xsd" version="1.0">
<persistence-unit name="thePersistenceUnit" transaction-type="RESOURCE_LOCAL">
<provider>org.hibernate.ejb.HibernatePersistence</provider>
<class>org.my.tracker.Event</class>
<properties>
<property name="connection.driver_class" value="org.h2.Driver"/>
<property name="hibernate.connection.url" value="jdbc:h2:./db/repository"/>
<property name="hibernate.dialect" value="org.hibernate.dialect.H2Dialect"/>
<property name="hibernate.hbm2ddl.auto" value="create"/>
<property name="hibernate.show_sql" value="true" />
</properties>
</persistence-unit>
</persistence>
src/main/webapp/WEB-INF/web.xml
src/main/webapp/WEB-INF/web.xml
<?xml version="1.0" encoding="ISO-8859-1"?>
<web-app
xmlns="http://java.sun.com/xml/ns/javaee"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd"
version="2.5">
<servlet>
<servlet-name>orc-event</servlet-name>
<servlet-class>org.my.tracker.EventServlet</servlet-class>
</servlet>
<servlet-mapping>
<servlet-name>orc-event</servlet-name>
<url-pattern>/event/*</url-pattern>
</servlet-mapping>
</web-app>
src/main/java/org/my/tracker/EventServlet.java
src/main/java/org/my/tracker/EventServlet.java
package org.my.tracker;
import java.io.IOException;
import java.io.PrintWriter;
import java.util.List;
import javax.persistence.EntityManager;
import javax.persistence.EntityManagerFactory;
import javax.persistence.Persistence;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import com.google.gson.Gson;
public class EventServlet extends HttpServlet {
private static final Logger LOGGER = LoggerFactory.getLogger(EventServlet.class);
private static final long serialVersionUID = 1L;
public static final String HTML_START="<html><body>";
public static final String HTML_END="</body></html>";
private static EntityManager manager;
static {
EntityManagerFactory factory = Persistence.createEntityManagerFactory("thePersistenceUnit");
manager = factory.createEntityManager();
}
/**
* @see HttpServlet#doGet(HttpServletRequest request, HttpServletResponse response)
*/
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
PrintWriter out = response.getWriter();
try {
manager.getTransaction().begin();
@SuppressWarnings("unchecked")
List<Event> events = manager.createQuery("from Event").getResultList();
Gson gson = new Gson();
out.print(gson.toJson(events));
manager.getTransaction().commit();
} catch (Exception e) {
manager.getTransaction().rollback();
}
}
/**
* @see HttpServlet#doPost(HttpServletRequest request, HttpServletResponse response)
*/
protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
String body = (String)request.getParameter("body");
if (null != body) {
try {
manager.getTransaction().begin();
Event event = new Event();
event.setBody(body);
manager.persist(event);
manager.getTransaction().commit();
} catch (Exception e) {
manager.getTransaction().rollback();
}
} else {
LOGGER.error("null body, cannot track");
}
}
}
src/main/java/org/my/tracker/Event.java
src/main/java/org/my/tracker/Event.java
package org.my.tracker;
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.Id;
@Entity
public class Event {
@Id
@GeneratedValue
private Integer id;
private String body;
public Integer getId() {
return id;
}
public void setId(Integer id) {
this.id = id;
}
public String getBody() {
return body;
}
public void setBody(String body) {
this.body = body;
}
}
好吧,感谢所有这些强大的工具,它很简单并且运行得很好,除了我不能
Well, thanks to all these powerful tools, this is simple and works quite nicely, except that I could not
-
查看如何通过属性(只能通过tomcat server.xml调音(我不能为此做的事不属于我))或spring(这是一个很弱的原因)来设置数据库位置在我的项目中放入一些弹簧,仅用于1个属性注入...),
see how to set my db location through a property (is it only possible through tomcat server.xml tune (that I cannot do for it does not belong to me) or spring (which is quite a weak reason to put some spring in my project only for 1 property injection...),
(和3.),每次启动Webapp时,我的数据库都是空的.当然,您会告诉我的,因为我在persistence.xml中放置了创建"值
(and 3.) each time I launch my webapp, my database is empty. Of course, you will tell me, since I put "create" value in persistence.xml
<property name="hibernate.hbm2ddl.auto" value="create"/>
好吧,我可以说
- create-drop:在我的情况下,结果与"create"相同(这是预料之中的,因为"drop"的含义与在关机时保持一切"的反义词很相似:D)
- 无:但是第一次未部署Webapp时不会创建数据库
- validate:好吧,我可以在webapp重新启动时恢复我的内容,但是没有,首先,如果它不存在,则不会创建数据库架构和表,并且我的webapp无法使用它:)
所以我想尽可能使事情像上面一样简单,有可能吗?
So I would like if possible to keep things as simple as they are above, is it possible ?
如果没有其他方法可以编写一个sql脚本来初始化我的数据库(只有当它不存在时),我将不胜感激,因为我是该领域的佼佼者,请提供代码或一些提示.
If there is no other way than writing an sql script to initialize my db only if it does not exist, I would appreciate you give the code or some hints, for I am a complete dumb in this field.
修改
因此,当我发表评论时,实际上,更新"是我想要的值. 像魅力一样工作.
So as I put in one comment, actually, "update" is the value I was looking for. Work like a charm.
除了spring以外,我没有其他方法可以传递变量而不是常量值.但是,嘿,无论如何在这种领域都是很常见的:)(并且也增加了它的orm层)
I did not find any other way than spring to pass variables instead of constant values. But hey that is quite common in such field anyway :) (and spring its orm layer too)
JPA 2.1提供了用于创建架构的标准属性.寻找
JPA 2.1 provides standard properties for creating schema. Look for
javax.persistence.schema-generation.database.action
并设置为create
或drop-and-create
.同样,有一些属性可以在启动EMF时执行脚本.任何符合要求的JPA实施的文档都应记录在文档中
and set to create
or drop-and-create
. Similarly there are properties for executing scripts at startup of an EMF. Docs for any compliant JPA implementation should document them