Create a SessionFactory and DataSource17:34 with Chris Ramacciotti
With our dependencies added to the application, we now begin coding the necessary configuration for using Hibernate to manage application data. In particular, we configure a Hibernate SessionFactory that can be managed in the Spring container (ApplicationContext), as well as a data source that allows database connections to be reused, using connection pooling with the Apache DBCP library. We also discuss the use of properties files in Java and Spring as a form of externalization.
Git Command to Sync Your Code to the Start of this Video
git checkout -f s1v5
Using Github With This Course
You can complete this course entirely using code created by you on your local machine. However, if you choose to use the code I've made available to you, you have two options:
- Use the project files linked at the bottom of this page, or
- Use the Github repository I've made available (recommended)
If you choose the recommended option of using the Github repository, it can be found at
To utilize Github with this course, you can download the Github desktop client for your system or use the command line interface provided with Git.
Clone this repository to your machine using the Github desktop client, or using the following command:
git clone email@example.com:treehouse/giflib-hibernate.git
To update your local repository to match a video's starting point, you can use the
git checkout command in combination with the stage and video number. For example, to update your local repository to match the starting point of Stage 5, Video 4, you'd use the following:
git checkout -f s5v4
Notice the use of the -f option. This forces Git to override all local changes, so be aware: this will cause any changes you made to be lost.
Over the last couple videos, we've spent some time configuring our Spring app for 0:00 use with Hibernate. 0:04 All of this is pretty standard for Spring and Hibernate and 0:05 really had nothing specific to our Give Lip application. 0:08 That said, it's time to get to work on the code that will be unique to Give Lip. 0:11 We ended the last video adding our dependencies for 0:17 spring, hibernate and each to our database provider. 0:19 Now we'll need to include some configuration that Spring will detect upon 0:22 booting our application. 0:26 For this we'll follow the same pattern you've seen with app config and 0:27 template config. 0:31 That is we'll create another configuration class that is specific 0:32 to configuring our data source. 0:36 Let's call it data config. 0:38 So I'm wanna right click on config and choose new Java class and 0:40 I'll call it data config. 0:44 So that Spring picks it up at boot time will annotate this class with 0:47 configuration. 0:51 Next will create a spring bean that's configured on boot and 0:55 available throughout our app. 0:58 This will be the spring equivalent of what the hibernate session factory was 1:00 in our hibernate basics course, so 1:03 that spring is able to manage hibernate sessions in the spring container 1:06 application context instead of directly configuring a session factory. 1:09 We'll create a local session factory being object. 1:13 Let's create that method now we'll annotated with the @Bean annotation 1:16 we'll call it public LocalSessionFactoryBean. 1:21 Now and make sure that you choose the one that comes from the hibernate 1:25 five package, you see I chose the hibernate 1:30 four while I couldn't actually see the package names in my. 1:33 Auto suggests, so I'll just change that to hibernate5, 1:36 I know that package exists, and I'll call this method, sessionFactory. 1:39 You can call it whatever you like. 1:44 For now, I will just have this return null. 1:46 Let's start by loading a class path resource from hibernate.cfg.xml. 1:50 We'll store this into a spring resource object. 1:55 So we'll start by creating that object. 1:57 Resource, there it is right there from the spring framework. 2:00 I'll call it can config, new classpath resource. 2:02 Since this file, this hibernate.cfg that XML file is on the classpath, 2:06 hibernate.cfg.x.m.l. 2:13 Next we'll create a local session factory and be an object. 2:19 So let's do that here local session factory bean. 2:22 I'll call it session factory. 2:26 You can call it session factory bean if you like. 2:27 I'll just use the default constructor. 2:32 And next, I will set the config location to that class path resource we just 2:35 created and for that I'll use the session factory dot set config location method. 2:40 And I'll pass it, that resource object I created right here. 2:47 And so that I don't forget to update my return value, it's the session 2:53 factory variable, which holds that local session factory being object. 2:57 It's the session factory that I want to return so let's replace no with that. 3:01 In our next step, we'll actually use Spring to scan for JPA annotated entities, 3:07 instead of adding an XML mapping element that specifies each annotated entity 3:12 separately, like we did in Hibernate basics. 3:17 This is a handy feature that Spring offers. 3:20 We can use the sessionFactories set packages to scan method to do this, so 3:23 I'll do that before I return that, session factory.setPackagesToscan. 3:27 Now we don't wanna hard code this package name into our source code here. 3:34 So this is a good candidate for what's called externalization. 3:42 That is, let's stick the package name in our properties file and 3:45 load it from this Java method. 3:49 Let's open app.properties. 3:52 You'll find that in the resources directory. 3:54 It will open app.properties. 3:56 Now, this property's file is a standard way to specify 3:59 all sorts of configuration in Java. 4:02 And then use Java code to load these values into memory. 4:04 In general, you'll start with a property name right here, that'll be followed by 4:07 an equals sign, and then you'll have the property value listed. 4:14 Using these files allows you to externalize values that might change and 4:20 prevents you from having to weave these into your source code. 4:23 You see only one property in here already. 4:27 Which serves as an initializer value or salt for 4:30 the hash IDs library we discussed earlier. 4:34 Let's add another property here where we can stick the name of the package that 4:38 contains our JPA annotated entities for hibernate to load. 4:41 Let me add a comment referencing what we're about to do here. 4:46 So this is gonna be the property that holds the package where our entities 4:49 which are just our models are located. 4:55 Then I'll call this property giflib.entity.package. 4:59 Now the package where entity classes are located or 5:04 com.teamtreehouse.giflib.Model, and there are our category and gif entities there. 5:08 So we want to use com.teamtreehouse.giflib.model 5:15 as our entity package name.Com.teamtreehouse. 5:19 you see I get my nice auto suggest here for my IDE, .model. 5:24 Now, after saving those changes, we'll flip back to the data config class. 5:31 Now where it's not too difficult to write Java code to create a properties object 5:36 and read the properties file with an input stream, 5:40 Spring provide some handy functionality for us. 5:43 We can annotate the class with properties source up here. 5:46 It's a property source and 5:51 in parentheses we can provide the name of the properties file, that will 5:53 contain the properties we like to use in this class in our case app dot properties. 5:58 Then to gain access to these values we can 6:04 auto wire a Spring environment object as an instance field. 6:07 Here's how that looks. 6:11 So we use that auto wired annotation private Environment there's that Spring 6:13 framework Environment class I'll just abbreviated env So 6:18 what will happen here is spring will load all the properties from app.properties. 6:24 Store them into this environment object and 6:29 now we can use this environment object throughout this classes methods, 6:32 to grab specific property values that came from app.properties. 6:37 Let me show you how that looks. 6:42 Back to where we wanted to set the package to scan for our entity classes. 6:44 What we can do is use ENV dot get property and then all we need to do 6:50 is.reference the exact property name that we used in app dot properties. 6:55 So the property name remembers is on the left hand side of that equals sign. 7:01 So I will drop that in quotes right there. 7:06 So this expression right here will evaluate. 7:09 To whatever value in app up properties. 7:15 The property name to get flipped.entity.package holds 7:18 In other words, that expression I have highlighted there will evaluate to 7:22 this value at run time, which is exactly what I want. 7:27 So I avoid hard coding values in my source code, 7:31 it's a wonderful practice to get in the habit of. 7:35 The final piece we need to configure for the SessionFactory is the data source. 7:38 Now we can do this by using the setDataSource method. 7:42 So we use SessionFactory.setDataSource and 7:45 I will call a dataSource method here which doesn't actually exist yet. 7:49 So let's use the IDE to create that. 7:54 When I create this method, now be careful here. 7:58 If you are going to annotate this as a bean so that Spring can 8:01 manage it in its container, you better set this as a public method. 8:05 And your IDE by default, 8:09 if this method isn't used outside of the class, will generate this as private. 8:11 So be sure that this bean method is listed as a public method. 8:16 Now this method is where we'll be using that dbcp library from Apache 8:22 to handle database connection pooling. 8:27 In this method we'll start by creating a basic 8:29 data source object which comes from that Apache library. 8:32 I'll abbreviate that name, ds, standing for data source, and 8:36 I will use its default constructor to start that object. 8:41 Now it's this object that we'll eventually want to return, but before we return 8:45 that object, we better have set a bunch of properties related to the DataSource. 8:50 Let me add comments here for the things that we need to set. 8:55 First we'll need to set the Driver class name. 8:58 Then we'll need to set the URL. 9:02 If you recall from Hibernate basics, this is going to be our full connection string. 9:04 And then, we need to set the username and password. 9:09 Now let's go through each one of these pieces of information that we have to set 9:14 related to the data source, and drop in a line of code Code or two. 9:18 So for the driver class name, this is going to be ds.setDriverClassName. 9:22 You'll find that these method names, in the DataSource object, 9:28 this basic DataSource object, are gonna be quite intuitive. 9:31 Now, we are going to be using that same idea of externalization and 9:34 these values will come from that app.properties file. 9:39 So we're going to end up using env.get property followed by some string. 9:43 So in this case for the name of the driver class let's use gifLib.db.driver and 9:50 then for the URL again ds.set, 9:58 there's that nice intuitive method name there ds.setUrl and 10:02 again env.getProperty and 10:07 then I will call this one giflib.db.url and let's do the same thing for 10:11 the username and password ds.setUsername. 10:16 That will be env.getProperty. 10:23 We'll say giflib.db.username and the same thing for the password, 10:26 setPassword env.getProperty 10:33 giflib.db.password. 10:39 Excellent, now that we've referenced all these property values, 10:43 giflib.db.driver .db.url and username and password. 10:47 Without actually having placed them in the app.properties file, 10:52 we should probably add those now. 10:56 Let's switch to app.properties and do that. 10:58 So at the end of the file, let me drop a comment about what we're about to do. 11:01 So these will be the details for our data source. 11:05 Now we'll need four properties here. 11:09 That's going to be the driver of the URL, the username, and the password, so 11:12 let's get those in here, giflib.db.driver. 11:15 And this is going to be org.h2.driver. 11:18 When the values are package names of libraries that are already on 11:24 the classpath, IntelliJ will nicely suggest those for 11:28 you so you don't have to memorize them. 11:31 Very handy. 11:34 Next is going to be that connection string so gif lib dot db dot URL. 11:36 Now this one is going to be a little longer because it is a connection string. 11:41 Just like you saw in hibernate basics this is going to leverage JDBC. 11:45 Remember that stands for Java Database Connectivity. 11:50 This is an H 2 database now here we're going to be using the TCP protocol. 11:53 TCP stands for Transmission Control Protocol. 11:58 And allows us to leverage network connectivity to a database server. 12:01 So, theoretically we could connect to this database from another machine 12:06 if we configured our ports to do so. 12:10 This is as opposed to using H2's file based mode. 12:14 I'm doing this for purposes of demonstration and 12:18 to show you that we can connect to a database with our application, 12:21 using tcp mode, as well as, 12:27 monitor the contents of the database through a web console that h2 offers. 12:30 I'll show you more about that in a few minutes. 12:36 So let's finish this connection string. 12:38 Okay this is going to go to a local host that's our own machine here. 12:40 That squiggly stands for the home directory on our machine. 12:45 Now you're going to want to make sure that the director you reference here 12:49 is a relative to your home directory. 12:53 So most likely your path from here to the end is going to be different 12:55 from mine unless your directory structure on your computer looks exactly like mine. 13:01 So I have a code directory and in there I have a screen cast directory. 13:07 And this project is gifLib.hibernate on my machine, and 13:13 I'm storing it in a data directory I'll call the database gifLib. 13:17 Now, because I just referenced the data directory that's within the root directory 13:22 of my project, well I better create that directory. 13:27 So, if you don't have a data directory on your local machine here, 13:32 you better go ahead and create that. 13:37 Let me show you exactly what you'd have to do. 13:39 I'll delete mine. 13:42 Just so you can see what it looks like, without the directory and 13:43 then, it's very simple. 13:47 You just right click the project New Directory, and stick data in there. 13:48 Now, you do not need to create a file named gif lib, 13:53 when our application tried to connect to the h2 database named giflib, 13:57 if a file does not exist in this location here, one will be created by h2 for you. 14:03 So I'll let h2 take care of that for us. 14:10 So again make sure that you have a data directory at the root of your project 14:14 in any case you have a data directory at the location specified here. 14:19 Okay two more properties to go. 14:26 We have a username gifLib.db.username I'm going 14:28 to use as a giflib.db.password I will leave blank. 14:34 Now, you could leave both of these blank, you could put a specific username and 14:39 password in there, you can do whatever you like here. 14:43 Just make sure that on the next step 14:46 you use the same password when firing up the web consul that you used here. 14:48 We'll see that in just a moment. 14:54 Now speaking of that H2 database server, 14:56 I want to show you how we can use the command line to start this 15:01 H2 database server that we'll be using for the rest of the course. 15:04 Using this server mode, 15:08 we can simultaneously allow our application to use the database, as well 15:09 as use a web console that I was referring to to monitor the database separately. 15:13 Now in order to do this you want to open a terminal 15:18 in the root directory of the project. 15:21 Now I'm just gonna use IntelliJ terminal here because when I open it it will come 15:22 right up in the root directory of the project. 15:27 Now all ready in the root directory of this project is this H2 15:31 jar file right there. 15:35 This is here not because we need it to integrate h2 into our application, but 15:37 rather we need it to quickly access the tools needed to 15:42 fire up an h2 database server. 15:44 So how do we use this jar file to fire up a database server? 15:47 Well, in the terminal here we can use the java command and 15:51 specify the jar file as the class path. 15:56 So the class path is going to be h2. 16:00 Blah blah blah jar, I just use the tab to auto complete that line. 16:03 And then the main class that we want to run is or 16:07 org.h2.tools .Server and then you'll just hit enter and what should happen 16:10 is a browser tab should open up with a console that looks like this. 16:15 This is the login screen so to speak of your database. 16:19 Now what you want to do here is with the database URL, you want to make sure this 16:25 value here matches exactly what you put in your app.properties file. 16:29 So that I can ensure that that's the case, I'm going to switch back to IntelliJ and 16:34 copy this whole value right here. 16:39 And paste it right here. 16:42 So with that value in there make sure you've entered the username and 16:45 password that you used in your properties file. 16:48 This is what I used SA and a blank password and I will click connect. 16:51 And now you have a database server running. 16:57 And note this database has no tables yet. 17:00 We'd see those listed here if we had tables. 17:02 It has no tables yet but 17:05 that will change soon as we run our job application with JPA annotated entities. 17:06 At that point, hibernates HBM to DDL tool will generate our database schema. 17:11 Assuming that in hibernate dot CFG dot XML, let me open that, 17:16 assuming that in here, we've used either the update create or 17:22 create drop property for hbm2ddl.auto 17:27
You need to sign up for Treehouse in order to download course files.Sign up