Heads up! To view this whole video, sign in with your Courses account or enroll in your free 7-day trial. Sign In Enroll
Well done!
You have completed Python for File Systems!
You have completed Python for File Systems!
Preview
We need to handle creating files in place using templates.
Treehouse Courses
Related Discussions
Have questions about this video? Start a discussion with the community and Treehouse staff.
Sign upRelated Discussions
Have questions about this video? Start a discussion with the community and Treehouse staff.
Sign up
We have most of the bits and
pieces for our tool done.
0:00
Now, though, we need to do something
that can be a little tricky.
0:03
We need to handle creating
files in place using templates.
0:05
Since we're using Flask and
0:08
Flask's Jinja2 templates use the same
curly braces as the placeholders for
0:10
the format method, we'll have to keep
that in mind when we create the files.
0:13
But less talk, more rock, right?
0:17
First let's make a dictionary
of final file locations and
0:19
the template that will be used for them.
0:23
And I'm gonna use the location as
the key and the template as the value.
0:25
You could switch those
around if you wanted,
0:28
whichever way makes more sense to you.
0:30
You could even do it as a two tuple or
a named tuple but I like dictionaries and
0:32
dictionaries are easy.
0:36
So let's call this files, and
it's gonna be a dictionary.
0:39
So we're gonna say '{project_slug}
/requirements.txt'.
0:45
And that's gonna be
'requirements.txt.template'.
0:52
And then we'll do '{project
_slug}/app.py' and
0:57
that will be 'app.py.template'.
1:02
And then we'll have
1:06
'{project_slug}/static/css/{project_slug.-
css}'.
1:08
And this will go to
'project.css.template'.
1:17
And then
1:21
'{project_slug}/static/js/{project_slug.-
js}'.
1:22
Actually, we should close
both of these there.
1:32
And this will be 'project.js.template'.
1:37
And lastly, we need
'{project_slug}/templates/index.html'.
1:42
And that's going to go to
'index.html.template'.
1:52
Have you noticed a trend here of
doing the .template on all of these?
1:56
So again I'm gonna use format
to toss in the project_slug.
2:00
Mostly I'm doing it this way just so
2:03
I don't have to pay too much attention
to what directory I'm working in.
2:05
If you take this further and build
some sort of larger command line tool,
2:07
you'll probably want to use chdir
to change where you're working.
2:11
I'm not gonna worry about that though.
2:14
Now I think I'll create my templates, so
2:16
I'm gonna create a new directory
here that I'm gonna call templates.
2:18
And then inside of templates
I'm gonna create some files.
2:25
So the first one I'm gonna create
will be requirements.txt.template.
2:28
And inside of that I'm
gonna put Flask 0.12.2.
2:32
Then I'm going to create another new
2:38
file inside there which I'm
gonna call project.js.template.
2:42
And I'm just gonna put a comment
in here which says JavaScript for
2:47
the {project_name} project.
2:52
Okay, nothing too special there.
2:55
I'm gonna do the same thing
with a project.css template.
2:58
And this is almost
exactly the same thing..
3:02
This is gonna be css for
the {project_name} project.
3:04
And then lastly, or not lastly,
I have two more to make,
3:11
I'm going to make app.py.template.
3:15
This one will have a bit more in it.
3:19
So we'll have from flask import Flask,
and render_template.
3:21
We'll say app = Flask(_name_).
3:29
And then we'll say @app.route('/'),
def home():.
3:34
And we'll return
render_template('index.html') and
3:41
that's it for that file.
3:46
And then we will do index.html.template.
3:48
And this one has a bit more in it so
I'm gonna copy and
3:52
paste this from my own file.
3:55
And we'll put this into the teacher's
notes, so you can copy it yourself.
3:58
This just pulls in static and
the project_slugs, things like that.
4:02
Nothing too special in these.
4:06
You'll see that some of them have
placeholders that we want to replace,
4:07
like the project_name stuff.
4:10
Now like I said earlier that
index.html.template is gonna be a trickier
4:12
beast because it has these
little things here to deal with.
4:16
Okay, so let's close these
cuz we don't need them open.
4:21
And let's work on the function that's
going to create our files for us.
4:26
I'm gonna do it down here
near the create_dirs.
4:30
So def create_files and I need to take
the root, the slug, and the project name.
4:34
So I'm going to call it root.
4:41
I'm gonna take in root, slug, and name.
4:42
So for file_name and
4:45
template_name in FILES.items().
4:48
Then I'm gonna try and
do template_file = open
4:55
(os.path.join('templates',
template_name)).
5:00
Let's see if I can make this window
a little bit wider for all of you.
5:07
There we go, that's a little bit better.
5:10
And then we're gonna say
file_content = template_file.read.
5:13
So I'm gonna read in that
whole bit of file content.
5:18
And then I'm gonna do file_content =
5:23
flask_template_prepare with
the (file_content).
5:27
And then I'm gonna say
file_content = file_content.format
5:32
where the project_name =
name that was passed in.
5:38
And the project_slug =
slug that was passed in.
5:43
And then I'm gonna revert those changes.
5:47
I'm gonna say
file_content=flask_template_repair
5:48
with the file_content.
5:54
Now, this flask_template_prepare and
flask_template_repair don't exist yet.
5:56
We're gonna make those a little bit later.
6:00
So now, let's Let's say
target_file=open(os.path.join(root,
6:03
file_name.format(project_slug=slug)).
6:11
And we're gonna open all
of these with the 'w'.
6:17
We want to delete any data that happens
to be there and replace it with our own.
6:20
There shouldn't be any though.
6:26
So then we'll do
target_file.write(file_content).
6:28
All right, so
that's all the work that we want to do.
6:34
But if there's an OS error,
6:37
then we want to print
Couldn't create something and
6:40
we wanna say file_name.format
where the project_slug= slug.
6:45
And I need to delete these
quote marks out there.
6:53
And finally, no matter whether
we have an exception or not,
6:58
we wanna call template_file.close.
7:02
And we wanna call target_file.close.
7:05
Think that was pretty straight forward.
7:10
But first of all,
we're gonna get the file_name and
7:12
the template_name from
our dictionary rather.
7:15
Then for each one of those pairs,
we're gonna try and create the template.
7:19
First we'll open up the template_file
from our templates directory.
7:21
We'll read the contents of
the template_file into a new variable.
7:23
I'm gonna write later these two
functions that make our templates safer,
7:27
if they have Jinja2 structures in them.
7:30
And then one that will
revert those changes.
7:32
I'll use their names here.
7:35
We're gonna write the functions
in the next video.
7:36
I think that flask_template_prepare and
flask_template_repair make sense for these
7:38
because we're preparing it and then we're
repairing the changes that we made to it.
7:41
So then I need to open the target_file
location which again I'm
7:46
using os.path.join.
7:50
And I'm gonna write the contents of the
template_file with placeholders filled in
7:52
and the Flask changes are then gonna
be reverted to the output file.
7:56
If any of this failed,
8:00
then we're just gonna tell user
what file we couldn't create.
8:01
Should we end the program here?
8:04
Maybe, but if we did it's kind of
annoying that we're leaving these partial
8:06
files in place.
8:09
If we're going to kill it,
we should have used temporary files.
8:10
Again though, that's something I'm
gonna let you change if you want,
8:12
to make things a little bit nicer.
8:15
And finally, no matter what,
8:17
we need to close both of those
file pointers that we opened.
8:18
Great, all we're missing now is the two
Flask translation functions and
8:21
we'll be done.
8:24
You need to sign up for Treehouse in order to download course files.
Sign upYou need to sign up for Treehouse in order to set up Workspace
Sign up