We are currently solving the following issue within our repository. Here is the issue text:
--- BEGIN ISSUE ---
Rename copy_without_render()
Since `copy_without_render()` no longer performs any actual copying, it should be renamed:

```
def copy_without_render(path, context):
    """
    Returns True if `path` matches some pattern in the
    `_copy_without_render` context setting.

    :param path: A file-system path referring to a file or dir that
        should be rendered or just copied.
    :param context: cookiecutter context.
    """
    try:
        for dont_render in context['cookiecutter']['_copy_without_render']:
            if fnmatch.fnmatch(path, dont_render):
                return True
    except KeyError:
        return False

    return False
```


--- END ISSUE ---

Below are some code segments, each from a relevant file. One or more of these files may contain bugs.
--- BEGIN FILES ---
Path: `cookiecutter/generate.py`
Content:
```
1 # -*- coding: utf-8 -*-
2 
3 """Functions for generating a project from a project template."""
4 from __future__ import unicode_literals
5 from collections import OrderedDict
6 import fnmatch
7 import io
8 import json
9 import logging
10 import os
11 import shutil
12 
13 from jinja2 import FileSystemLoader
14 from cookiecutter.environment import StrictEnvironment
15 from jinja2.exceptions import TemplateSyntaxError, UndefinedError
16 from binaryornot.check import is_binary
17 
18 from .exceptions import (
19     NonTemplatedInputDirException,
20     ContextDecodingException,
21     FailedHookException,
22     OutputDirExistsException,
23     UndefinedVariableInTemplate
24 )
25 from .find import find_template
26 from .utils import make_sure_path_exists, work_in, rmtree
27 from .hooks import run_hook
28 
29 logger = logging.getLogger(__name__)
30 
31 
32 def copy_without_render(path, context):
33     """Return True if `path` matches context dict pattern.
34 
35     :param path: A file-system path referring to a file or dir that
36         should be rendered or just copied.
37     :param context: cookiecutter context.
38     """
39     try:
40         for dont_render in context['cookiecutter']['_copy_without_render']:
41             if fnmatch.fnmatch(path, dont_render):
42                 return True
43     except KeyError:
44         return False
45 
46     return False
47 
48 
49 def apply_overwrites_to_context(context, overwrite_context):
50     """Modify the given context in place based on the overwrite_context."""
51     for variable, overwrite in overwrite_context.items():
52         if variable not in context:
53             # Do not include variables which are not used in the template
54             continue
55 
56         context_value = context[variable]
57 
58         if isinstance(context_value, list):
59             # We are dealing with a choice variable
60             if overwrite in context_value:
61                 # This overwrite is actually valid for the given context
62                 # Let's set it as default (by definition first item in list)
63                 # see ``cookiecutter.prompt.prompt_choice_for_config``
64                 context_value.remove(overwrite)
65                 context_value.insert(0, overwrite)
66         else:
67             # Simply overwrite the value for this variable
68             context[variable] = overwrite
69 
70 
71 def generate_context(context_file='cookiecutter.json', default_context=None,
72                      extra_context=None):
73     """Generate the context for a Cookiecutter project template.
74 
75     Loads the JSON file as a Python object, with key being the JSON filename.
76 
77     :param context_file: JSON file containing key/value pairs for populating
78         the cookiecutter's variables.
79     :param default_context: Dictionary containing config to take into account.
80     :param extra_context: Dictionary containing configuration overrides
81     """
82     context = {}
83 
84     try:
85         with open(context_file) as file_handle:
86             obj = json.load(file_handle, object_pairs_hook=OrderedDict)
87     except ValueError as e:
88         # JSON decoding error.  Let's throw a new exception that is more
89         # friendly for the developer or user.
90         full_fpath = os.path.abspath(context_file)
91         json_exc_message = str(e)
92         our_exc_message = (
93             'JSON decoding error while loading "{0}".  Decoding'
94             ' error details: "{1}"'.format(full_fpath, json_exc_message))
95         raise ContextDecodingException(our_exc_message)
96 
97     # Add the Python object to the context dictionary
98     file_name = os.path.split(context_file)[1]
99     file_stem = file_name.split('.')[0]
100     context[file_stem] = obj
101 
102     # Overwrite context variable defaults with the default context from the
103     # user's global config, if available
104     if default_context:
105         apply_overwrites_to_context(obj, default_context)
106     if extra_context:
107         apply_overwrites_to_context(obj, extra_context)
108 
109     logger.debug('Context generated is {}'.format(context))
110     return context
111 
112 
113 def generate_file(project_dir, infile, context, env):
114     """Render filename of infile as name of outfile, handle infile correctly.
115 
116     Dealing with infile appropriately:
117 
118         a. If infile is a binary file, copy it over without rendering.
119         b. If infile is a text file, render its contents and write the
120            rendered infile to outfile.
121 
122     Precondition:
123 
124         When calling `generate_file()`, the root template dir must be the
125         current working directory. Using `utils.work_in()` is the recommended
126         way to perform this directory change.
127 
128     :param project_dir: Absolute path to the resulting generated project.
129     :param infile: Input file to generate the file from. Relative to the root
130         template dir.
131     :param context: Dict for populating the cookiecutter's variables.
132     :param env: Jinja2 template execution environment.
133     """
134     logger.debug('Processing file {}'.format(infile))
135 
136     # Render the path to the output file (not including the root project dir)
137     outfile_tmpl = env.from_string(infile)
138 
139     outfile = os.path.join(project_dir, outfile_tmpl.render(**context))
140     file_name_is_empty = os.path.isdir(outfile)
141     if file_name_is_empty:
142         logger.debug('The resulting file name is empty: {0}'.format(outfile))
143         return
144 
145     logger.debug('Created file at {0}'.format(outfile))
146 
147     # Just copy over binary files. Don't render.
148     logger.debug("Check {} to see if it's a binary".format(infile))
149     if is_binary(infile):
150         logger.debug(
151             'Copying binary {} to {} without rendering'
152             ''.format(infile, outfile)
153         )
154         shutil.copyfile(infile, outfile)
155     else:
156         # Force fwd slashes on Windows for get_template
157         # This is a by-design Jinja issue
158         infile_fwd_slashes = infile.replace(os.path.sep, '/')
159 
160         # Render the file
161         try:
162             tmpl = env.get_template(infile_fwd_slashes)
163         except TemplateSyntaxError as exception:
164             # Disable translated so that printed exception contains verbose
165             # information about syntax error location
166             exception.translated = False
167             raise
168         rendered_file = tmpl.render(**context)
169 
170         logger.debug('Writing contents to file {}'.format(outfile))
171 
172         with io.open(outfile, 'w', encoding='utf-8') as fh:
173             fh.write(rendered_file)
174 
175     # Apply file permissions to output file
176     shutil.copymode(infile, outfile)
177 
178 
179 def render_and_create_dir(dirname, context, output_dir, environment,
180                           overwrite_if_exists=False):
181     """Render name of a directory, create the directory, return its path."""
182     name_tmpl = environment.from_string(dirname)
183     rendered_dirname = name_tmpl.render(**context)
184 
185     dir_to_create = os.path.normpath(
186         os.path.join(output_dir, rendered_dirname)
187     )
188 
189     logger.debug('Rendered dir {} must exist in output_dir {}'.format(
190         dir_to_create,
191         output_dir
192     ))
193 
194     output_dir_exists = os.path.exists(dir_to_create)
195 
196     if overwrite_if_exists:
197         if output_dir_exists:
198             logger.debug(
199                 'Output directory {} already exists,'
200                 'overwriting it'.format(dir_to_create)
201             )
202     else:
203         if output_dir_exists:
204             msg = 'Error: "{}" directory already exists'.format(dir_to_create)
205             raise OutputDirExistsException(msg)
206 
207     make_sure_path_exists(dir_to_create)
208     return dir_to_create
209 
210 
211 def ensure_dir_is_templated(dirname):
212     """Ensure that dirname is a templated directory name."""
213     if '{{' in dirname and '}}' in dirname:
214         return True
215     else:
216         raise NonTemplatedInputDirException
217 
218 
219 def _run_hook_from_repo_dir(repo_dir, hook_name, project_dir, context):
220     """Run hook from repo directory, clean project directory if hook fails."""
221     with work_in(repo_dir):
222         try:
223             run_hook(hook_name, project_dir, context)
224         except FailedHookException:
225             rmtree(project_dir)
226             logger.error(
227                 "Stopping generation because {} hook "
228                 "script didn't exit successfully".format(hook_name)
229             )
230             raise
231 
232 
233 def generate_files(repo_dir, context=None, output_dir='.',
234                    overwrite_if_exists=False):
235     """Render the templates and saves them to files.
236 
237     :param repo_dir: Project template input directory.
238     :param context: Dict for populating the template's variables.
239     :param output_dir: Where to output the generated project dir into.
240     :param overwrite_if_exists: Overwrite the contents of the output directory
241         if it exists.
242     """
243     template_dir = find_template(repo_dir)
244     logger.debug('Generating project from {}...'.format(template_dir))
245     context = context or {}
246 
247     unrendered_dir = os.path.split(template_dir)[1]
248     ensure_dir_is_templated(unrendered_dir)
249     env = StrictEnvironment(
250         context=context,
251         keep_trailing_newline=True,
252     )
253     try:
254         project_dir = render_and_create_dir(
255             unrendered_dir,
256             context,
257             output_dir,
258             env,
259             overwrite_if_exists
260         )
261     except UndefinedError as err:
262         msg = "Unable to create project directory '{}'".format(unrendered_dir)
263         raise UndefinedVariableInTemplate(msg, err, context)
264 
265     # We want the Jinja path and the OS paths to match. Consequently, we'll:
266     #   + CD to the template folder
267     #   + Set Jinja's path to '.'
268     #
269     #  In order to build our files to the correct folder(s), we'll use an
270     # absolute path for the target folder (project_dir)
271 
272     project_dir = os.path.abspath(project_dir)
273     logger.debug('Project directory is {}'.format(project_dir))
274 
275     _run_hook_from_repo_dir(repo_dir, 'pre_gen_project', project_dir, context)
276 
277     with work_in(template_dir):
278         env.loader = FileSystemLoader('.')
279 
280         for root, dirs, files in os.walk('.'):
281             # We must separate the two types of dirs into different lists.
282             # The reason is that we don't want ``os.walk`` to go through the
283             # unrendered directories, since they will just be copied.
284             copy_dirs = []
285             render_dirs = []
286 
287             for d in dirs:
288                 d_ = os.path.normpath(os.path.join(root, d))
289                 # We check the full path, because that's how it can be
290                 # specified in the ``_copy_without_render`` setting, but
291                 # we store just the dir name
292                 if copy_without_render(d_, context):
293                     copy_dirs.append(d)
294                 else:
295                     render_dirs.append(d)
296 
297             for copy_dir in copy_dirs:
298                 indir = os.path.normpath(os.path.join(root, copy_dir))
299                 outdir = os.path.normpath(os.path.join(project_dir, indir))
300                 logger.debug(
301                     'Copying dir {} to {} without rendering'
302                     ''.format(indir, outdir)
303                 )
304                 shutil.copytree(indir, outdir)
305 
306             # We mutate ``dirs``, because we only want to go through these dirs
307             # recursively
308             dirs[:] = render_dirs
309             for d in dirs:
310                 unrendered_dir = os.path.join(project_dir, root, d)
311                 try:
312                     render_and_create_dir(
313                         unrendered_dir,
314                         context,
315                         output_dir,
316                         env,
317                         overwrite_if_exists
318                     )
319                 except UndefinedError as err:
320                     rmtree(project_dir)
321                     _dir = os.path.relpath(unrendered_dir, output_dir)
322                     msg = "Unable to create directory '{}'".format(_dir)
323                     raise UndefinedVariableInTemplate(msg, err, context)
324 
325             for f in files:
326                 infile = os.path.normpath(os.path.join(root, f))
327                 if copy_without_render(infile, context):
328                     outfile_tmpl = env.from_string(infile)
329                     outfile_rendered = outfile_tmpl.render(**context)
330                     outfile = os.path.join(project_dir, outfile_rendered)
331                     logger.debug(
332                         'Copying file {} to {} without rendering'
333                         ''.format(infile, outfile)
334                     )
335                     shutil.copyfile(infile, outfile)
336                     shutil.copymode(infile, outfile)
337                     continue
338                 try:
339                     generate_file(project_dir, infile, context, env)
340                 except UndefinedError as err:
341                     rmtree(project_dir)
342                     msg = "Unable to create file '{}'".format(infile)
343                     raise UndefinedVariableInTemplate(msg, err, context)
344 
345     _run_hook_from_repo_dir(repo_dir, 'post_gen_project', project_dir, context)
346 
347     return project_dir
348
```
--- END FILES ---

Please first localize the bug based on the issue statement, and then generate a patch according to the `git diff` format fenced by three backticks.

Here is an example:

```diff
diff --git a/examples/server_async.py b/examples/server_async.py
--- a/examples/server_async.py
+++ b/examples/server_async.py
@@ -313,4 +313,4 @@
 
 
 if __name__ == "__main__":
-    asyncio.run(run_async_server("."), debug=True)
+    asyncio.run(run_async_server(), debug=True)
diff --git a/examples/server_sync.py b/examples/server_sync.py
--- a/examples/server_sync.py
+++ b/examples/server_sync.py
@@ -313,5 +313,5 @@
 
 
 if __name__ == "__main__":
-    server = run_sync_server(".")
+    server = run_sync_server()
     server.shutdown()

```

diff --git a/cookiecutter/generate.py b/cookiecutter/generate.py
--- a/cookiecutter/generate.py
+++ b/cookiecutter/generate.py
@@ -29,8 +29,12 @@
 logger = logging.getLogger(__name__)
 
 
-def copy_without_render(path, context):
-    """Return True if `path` matches context dict pattern.
+def is_copy_only_path(path, context):
+    """Check whether the given `path` should only be copied as opposed to being
+    rendered.
+
+    Returns True if `path` matches a pattern in the given `context` dict,
+    otherwise False.
 
     :param path: A file-system path referring to a file or dir that
         should be rendered or just copied.
@@ -289,7 +293,7 @@
                 # We check the full path, because that's how it can be
                 # specified in the ``_copy_without_render`` setting, but
                 # we store just the dir name
-                if copy_without_render(d_, context):
+                if is_copy_only_path(d_, context):
                     copy_dirs.append(d)
                 else:
                     render_dirs.append(d)
@@ -324,7 +328,7 @@
 
             for f in files:
                 infile = os.path.normpath(os.path.join(root, f))
-                if copy_without_render(infile, context):
+                if is_copy_only_path(infile, context):
                     outfile_tmpl = env.from_string(infile)
                     outfile_rendered = outfile_tmpl.render(**context)
                     outfile = os.path.join(project_dir, outfile_rendered)

{"golden_diff": "diff --git a/cookiecutter/generate.py b/cookiecutter/generate.py\n--- a/cookiecutter/generate.py\n+++ b/cookiecutter/generate.py\n@@ -29,8 +29,12 @@\n logger = logging.getLogger(__name__)\n \n \n-def copy_without_render(path, context):\n-    \"\"\"Return True if `path` matches context dict pattern.\n+def is_copy_only_path(path, context):\n+    \"\"\"Check whether the given `path` should only be copied as opposed to being\n+    rendered.\n+\n+    Returns True if `path` matches a pattern in the given `context` dict,\n+    otherwise False.\n \n     :param path: A file-system path referring to a file or dir that\n         should be rendered or just copied.\n@@ -289,7 +293,7 @@\n                 # We check the full path, because that's how it can be\n                 # specified in the ``_copy_without_render`` setting, but\n                 # we store just the dir name\n-                if copy_without_render(d_, context):\n+                if is_copy_only_path(d_, context):\n                     copy_dirs.append(d)\n                 else:\n                     render_dirs.append(d)\n@@ -324,7 +328,7 @@\n \n             for f in files:\n                 infile = os.path.normpath(os.path.join(root, f))\n-                if copy_without_render(infile, context):\n+                if is_copy_only_path(infile, context):\n                     outfile_tmpl = env.from_string(infile)\n                     outfile_rendered = outfile_tmpl.render(**context)\n                     outfile = os.path.join(project_dir, outfile_rendered)\n", "issue": "Rename copy_without_render()\nSince `copy_without_render()` no longer performs any actual copying, it should be renamed:\n\n```\ndef copy_without_render(path, context):\n    \"\"\"\n    Returns True if `path` matches some pattern in the\n    `_copy_without_render` context setting.\n\n    :param path: A file-system path referring to a file or dir that\n        should be rendered or just copied.\n    :param context: cookiecutter context.\n    \"\"\"\n    try:\n        for dont_render in context['cookiecutter']['_copy_without_render']:\n            if fnmatch.fnmatch(path, dont_render):\n                return True\n    except KeyError:\n        return False\n\n    return False\n```\n\n", "before_files": [{"content": "# -*- coding: utf-8 -*-\n\n\"\"\"Functions for generating a project from a project template.\"\"\"\nfrom __future__ import unicode_literals\nfrom collections import OrderedDict\nimport fnmatch\nimport io\nimport json\nimport logging\nimport os\nimport shutil\n\nfrom jinja2 import FileSystemLoader\nfrom cookiecutter.environment import StrictEnvironment\nfrom jinja2.exceptions import TemplateSyntaxError, UndefinedError\nfrom binaryornot.check import is_binary\n\nfrom .exceptions import (\n    NonTemplatedInputDirException,\n    ContextDecodingException,\n    FailedHookException,\n    OutputDirExistsException,\n    UndefinedVariableInTemplate\n)\nfrom .find import find_template\nfrom .utils import make_sure_path_exists, work_in, rmtree\nfrom .hooks import run_hook\n\nlogger = logging.getLogger(__name__)\n\n\ndef copy_without_render(path, context):\n    \"\"\"Return True if `path` matches context dict pattern.\n\n    :param path: A file-system path referring to a file or dir that\n        should be rendered or just copied.\n    :param context: cookiecutter context.\n    \"\"\"\n    try:\n        for dont_render in context['cookiecutter']['_copy_without_render']:\n            if fnmatch.fnmatch(path, dont_render):\n                return True\n    except KeyError:\n        return False\n\n    return False\n\n\ndef apply_overwrites_to_context(context, overwrite_context):\n    \"\"\"Modify the given context in place based on the overwrite_context.\"\"\"\n    for variable, overwrite in overwrite_context.items():\n        if variable not in context:\n            # Do not include variables which are not used in the template\n            continue\n\n        context_value = context[variable]\n\n        if isinstance(context_value, list):\n            # We are dealing with a choice variable\n            if overwrite in context_value:\n                # This overwrite is actually valid for the given context\n                # Let's set it as default (by definition first item in list)\n                # see ``cookiecutter.prompt.prompt_choice_for_config``\n                context_value.remove(overwrite)\n                context_value.insert(0, overwrite)\n        else:\n            # Simply overwrite the value for this variable\n            context[variable] = overwrite\n\n\ndef generate_context(context_file='cookiecutter.json', default_context=None,\n                     extra_context=None):\n    \"\"\"Generate the context for a Cookiecutter project template.\n\n    Loads the JSON file as a Python object, with key being the JSON filename.\n\n    :param context_file: JSON file containing key/value pairs for populating\n        the cookiecutter's variables.\n    :param default_context: Dictionary containing config to take into account.\n    :param extra_context: Dictionary containing configuration overrides\n    \"\"\"\n    context = {}\n\n    try:\n        with open(context_file) as file_handle:\n            obj = json.load(file_handle, object_pairs_hook=OrderedDict)\n    except ValueError as e:\n        # JSON decoding error.  Let's throw a new exception that is more\n        # friendly for the developer or user.\n        full_fpath = os.path.abspath(context_file)\n        json_exc_message = str(e)\n        our_exc_message = (\n            'JSON decoding error while loading \"{0}\".  Decoding'\n            ' error details: \"{1}\"'.format(full_fpath, json_exc_message))\n        raise ContextDecodingException(our_exc_message)\n\n    # Add the Python object to the context dictionary\n    file_name = os.path.split(context_file)[1]\n    file_stem = file_name.split('.')[0]\n    context[file_stem] = obj\n\n    # Overwrite context variable defaults with the default context from the\n    # user's global config, if available\n    if default_context:\n        apply_overwrites_to_context(obj, default_context)\n    if extra_context:\n        apply_overwrites_to_context(obj, extra_context)\n\n    logger.debug('Context generated is {}'.format(context))\n    return context\n\n\ndef generate_file(project_dir, infile, context, env):\n    \"\"\"Render filename of infile as name of outfile, handle infile correctly.\n\n    Dealing with infile appropriately:\n\n        a. If infile is a binary file, copy it over without rendering.\n        b. If infile is a text file, render its contents and write the\n           rendered infile to outfile.\n\n    Precondition:\n\n        When calling `generate_file()`, the root template dir must be the\n        current working directory. Using `utils.work_in()` is the recommended\n        way to perform this directory change.\n\n    :param project_dir: Absolute path to the resulting generated project.\n    :param infile: Input file to generate the file from. Relative to the root\n        template dir.\n    :param context: Dict for populating the cookiecutter's variables.\n    :param env: Jinja2 template execution environment.\n    \"\"\"\n    logger.debug('Processing file {}'.format(infile))\n\n    # Render the path to the output file (not including the root project dir)\n    outfile_tmpl = env.from_string(infile)\n\n    outfile = os.path.join(project_dir, outfile_tmpl.render(**context))\n    file_name_is_empty = os.path.isdir(outfile)\n    if file_name_is_empty:\n        logger.debug('The resulting file name is empty: {0}'.format(outfile))\n        return\n\n    logger.debug('Created file at {0}'.format(outfile))\n\n    # Just copy over binary files. Don't render.\n    logger.debug(\"Check {} to see if it's a binary\".format(infile))\n    if is_binary(infile):\n        logger.debug(\n            'Copying binary {} to {} without rendering'\n            ''.format(infile, outfile)\n        )\n        shutil.copyfile(infile, outfile)\n    else:\n        # Force fwd slashes on Windows for get_template\n        # This is a by-design Jinja issue\n        infile_fwd_slashes = infile.replace(os.path.sep, '/')\n\n        # Render the file\n        try:\n            tmpl = env.get_template(infile_fwd_slashes)\n        except TemplateSyntaxError as exception:\n            # Disable translated so that printed exception contains verbose\n            # information about syntax error location\n            exception.translated = False\n            raise\n        rendered_file = tmpl.render(**context)\n\n        logger.debug('Writing contents to file {}'.format(outfile))\n\n        with io.open(outfile, 'w', encoding='utf-8') as fh:\n            fh.write(rendered_file)\n\n    # Apply file permissions to output file\n    shutil.copymode(infile, outfile)\n\n\ndef render_and_create_dir(dirname, context, output_dir, environment,\n                          overwrite_if_exists=False):\n    \"\"\"Render name of a directory, create the directory, return its path.\"\"\"\n    name_tmpl = environment.from_string(dirname)\n    rendered_dirname = name_tmpl.render(**context)\n\n    dir_to_create = os.path.normpath(\n        os.path.join(output_dir, rendered_dirname)\n    )\n\n    logger.debug('Rendered dir {} must exist in output_dir {}'.format(\n        dir_to_create,\n        output_dir\n    ))\n\n    output_dir_exists = os.path.exists(dir_to_create)\n\n    if overwrite_if_exists:\n        if output_dir_exists:\n            logger.debug(\n                'Output directory {} already exists,'\n                'overwriting it'.format(dir_to_create)\n            )\n    else:\n        if output_dir_exists:\n            msg = 'Error: \"{}\" directory already exists'.format(dir_to_create)\n            raise OutputDirExistsException(msg)\n\n    make_sure_path_exists(dir_to_create)\n    return dir_to_create\n\n\ndef ensure_dir_is_templated(dirname):\n    \"\"\"Ensure that dirname is a templated directory name.\"\"\"\n    if '{{' in dirname and '}}' in dirname:\n        return True\n    else:\n        raise NonTemplatedInputDirException\n\n\ndef _run_hook_from_repo_dir(repo_dir, hook_name, project_dir, context):\n    \"\"\"Run hook from repo directory, clean project directory if hook fails.\"\"\"\n    with work_in(repo_dir):\n        try:\n            run_hook(hook_name, project_dir, context)\n        except FailedHookException:\n            rmtree(project_dir)\n            logger.error(\n                \"Stopping generation because {} hook \"\n                \"script didn't exit successfully\".format(hook_name)\n            )\n            raise\n\n\ndef generate_files(repo_dir, context=None, output_dir='.',\n                   overwrite_if_exists=False):\n    \"\"\"Render the templates and saves them to files.\n\n    :param repo_dir: Project template input directory.\n    :param context: Dict for populating the template's variables.\n    :param output_dir: Where to output the generated project dir into.\n    :param overwrite_if_exists: Overwrite the contents of the output directory\n        if it exists.\n    \"\"\"\n    template_dir = find_template(repo_dir)\n    logger.debug('Generating project from {}...'.format(template_dir))\n    context = context or {}\n\n    unrendered_dir = os.path.split(template_dir)[1]\n    ensure_dir_is_templated(unrendered_dir)\n    env = StrictEnvironment(\n        context=context,\n        keep_trailing_newline=True,\n    )\n    try:\n        project_dir = render_and_create_dir(\n            unrendered_dir,\n            context,\n            output_dir,\n            env,\n            overwrite_if_exists\n        )\n    except UndefinedError as err:\n        msg = \"Unable to create project directory '{}'\".format(unrendered_dir)\n        raise UndefinedVariableInTemplate(msg, err, context)\n\n    # We want the Jinja path and the OS paths to match. Consequently, we'll:\n    #   + CD to the template folder\n    #   + Set Jinja's path to '.'\n    #\n    #  In order to build our files to the correct folder(s), we'll use an\n    # absolute path for the target folder (project_dir)\n\n    project_dir = os.path.abspath(project_dir)\n    logger.debug('Project directory is {}'.format(project_dir))\n\n    _run_hook_from_repo_dir(repo_dir, 'pre_gen_project', project_dir, context)\n\n    with work_in(template_dir):\n        env.loader = FileSystemLoader('.')\n\n        for root, dirs, files in os.walk('.'):\n            # We must separate the two types of dirs into different lists.\n            # The reason is that we don't want ``os.walk`` to go through the\n            # unrendered directories, since they will just be copied.\n            copy_dirs = []\n            render_dirs = []\n\n            for d in dirs:\n                d_ = os.path.normpath(os.path.join(root, d))\n                # We check the full path, because that's how it can be\n                # specified in the ``_copy_without_render`` setting, but\n                # we store just the dir name\n                if copy_without_render(d_, context):\n                    copy_dirs.append(d)\n                else:\n                    render_dirs.append(d)\n\n            for copy_dir in copy_dirs:\n                indir = os.path.normpath(os.path.join(root, copy_dir))\n                outdir = os.path.normpath(os.path.join(project_dir, indir))\n                logger.debug(\n                    'Copying dir {} to {} without rendering'\n                    ''.format(indir, outdir)\n                )\n                shutil.copytree(indir, outdir)\n\n            # We mutate ``dirs``, because we only want to go through these dirs\n            # recursively\n            dirs[:] = render_dirs\n            for d in dirs:\n                unrendered_dir = os.path.join(project_dir, root, d)\n                try:\n                    render_and_create_dir(\n                        unrendered_dir,\n                        context,\n                        output_dir,\n                        env,\n                        overwrite_if_exists\n                    )\n                except UndefinedError as err:\n                    rmtree(project_dir)\n                    _dir = os.path.relpath(unrendered_dir, output_dir)\n                    msg = \"Unable to create directory '{}'\".format(_dir)\n                    raise UndefinedVariableInTemplate(msg, err, context)\n\n            for f in files:\n                infile = os.path.normpath(os.path.join(root, f))\n                if copy_without_render(infile, context):\n                    outfile_tmpl = env.from_string(infile)\n                    outfile_rendered = outfile_tmpl.render(**context)\n                    outfile = os.path.join(project_dir, outfile_rendered)\n                    logger.debug(\n                        'Copying file {} to {} without rendering'\n                        ''.format(infile, outfile)\n                    )\n                    shutil.copyfile(infile, outfile)\n                    shutil.copymode(infile, outfile)\n                    continue\n                try:\n                    generate_file(project_dir, infile, context, env)\n                except UndefinedError as err:\n                    rmtree(project_dir)\n                    msg = \"Unable to create file '{}'\".format(infile)\n                    raise UndefinedVariableInTemplate(msg, err, context)\n\n    _run_hook_from_repo_dir(repo_dir, 'post_gen_project', project_dir, context)\n\n    return project_dir\n", "path": "cookiecutter/generate.py"}], "after_files": [{"content": "# -*- coding: utf-8 -*-\n\n\"\"\"Functions for generating a project from a project template.\"\"\"\nfrom __future__ import unicode_literals\nfrom collections import OrderedDict\nimport fnmatch\nimport io\nimport json\nimport logging\nimport os\nimport shutil\n\nfrom jinja2 import FileSystemLoader\nfrom cookiecutter.environment import StrictEnvironment\nfrom jinja2.exceptions import TemplateSyntaxError, UndefinedError\nfrom binaryornot.check import is_binary\n\nfrom .exceptions import (\n    NonTemplatedInputDirException,\n    ContextDecodingException,\n    FailedHookException,\n    OutputDirExistsException,\n    UndefinedVariableInTemplate\n)\nfrom .find import find_template\nfrom .utils import make_sure_path_exists, work_in, rmtree\nfrom .hooks import run_hook\n\nlogger = logging.getLogger(__name__)\n\n\ndef is_copy_only_path(path, context):\n    \"\"\"Check whether the given `path` should only be copied as opposed to being\n    rendered.\n\n    Returns True if `path` matches a pattern in the given `context` dict,\n    otherwise False.\n\n    :param path: A file-system path referring to a file or dir that\n        should be rendered or just copied.\n    :param context: cookiecutter context.\n    \"\"\"\n    try:\n        for dont_render in context['cookiecutter']['_copy_without_render']:\n            if fnmatch.fnmatch(path, dont_render):\n                return True\n    except KeyError:\n        return False\n\n    return False\n\n\ndef apply_overwrites_to_context(context, overwrite_context):\n    \"\"\"Modify the given context in place based on the overwrite_context.\"\"\"\n    for variable, overwrite in overwrite_context.items():\n        if variable not in context:\n            # Do not include variables which are not used in the template\n            continue\n\n        context_value = context[variable]\n\n        if isinstance(context_value, list):\n            # We are dealing with a choice variable\n            if overwrite in context_value:\n                # This overwrite is actually valid for the given context\n                # Let's set it as default (by definition first item in list)\n                # see ``cookiecutter.prompt.prompt_choice_for_config``\n                context_value.remove(overwrite)\n                context_value.insert(0, overwrite)\n        else:\n            # Simply overwrite the value for this variable\n            context[variable] = overwrite\n\n\ndef generate_context(context_file='cookiecutter.json', default_context=None,\n                     extra_context=None):\n    \"\"\"Generate the context for a Cookiecutter project template.\n\n    Loads the JSON file as a Python object, with key being the JSON filename.\n\n    :param context_file: JSON file containing key/value pairs for populating\n        the cookiecutter's variables.\n    :param default_context: Dictionary containing config to take into account.\n    :param extra_context: Dictionary containing configuration overrides\n    \"\"\"\n    context = {}\n\n    try:\n        with open(context_file) as file_handle:\n            obj = json.load(file_handle, object_pairs_hook=OrderedDict)\n    except ValueError as e:\n        # JSON decoding error.  Let's throw a new exception that is more\n        # friendly for the developer or user.\n        full_fpath = os.path.abspath(context_file)\n        json_exc_message = str(e)\n        our_exc_message = (\n            'JSON decoding error while loading \"{0}\".  Decoding'\n            ' error details: \"{1}\"'.format(full_fpath, json_exc_message))\n        raise ContextDecodingException(our_exc_message)\n\n    # Add the Python object to the context dictionary\n    file_name = os.path.split(context_file)[1]\n    file_stem = file_name.split('.')[0]\n    context[file_stem] = obj\n\n    # Overwrite context variable defaults with the default context from the\n    # user's global config, if available\n    if default_context:\n        apply_overwrites_to_context(obj, default_context)\n    if extra_context:\n        apply_overwrites_to_context(obj, extra_context)\n\n    logger.debug('Context generated is {}'.format(context))\n    return context\n\n\ndef generate_file(project_dir, infile, context, env):\n    \"\"\"Render filename of infile as name of outfile, handle infile correctly.\n\n    Dealing with infile appropriately:\n\n        a. If infile is a binary file, copy it over without rendering.\n        b. If infile is a text file, render its contents and write the\n           rendered infile to outfile.\n\n    Precondition:\n\n        When calling `generate_file()`, the root template dir must be the\n        current working directory. Using `utils.work_in()` is the recommended\n        way to perform this directory change.\n\n    :param project_dir: Absolute path to the resulting generated project.\n    :param infile: Input file to generate the file from. Relative to the root\n        template dir.\n    :param context: Dict for populating the cookiecutter's variables.\n    :param env: Jinja2 template execution environment.\n    \"\"\"\n    logger.debug('Processing file {}'.format(infile))\n\n    # Render the path to the output file (not including the root project dir)\n    outfile_tmpl = env.from_string(infile)\n\n    outfile = os.path.join(project_dir, outfile_tmpl.render(**context))\n    file_name_is_empty = os.path.isdir(outfile)\n    if file_name_is_empty:\n        logger.debug('The resulting file name is empty: {0}'.format(outfile))\n        return\n\n    logger.debug('Created file at {0}'.format(outfile))\n\n    # Just copy over binary files. Don't render.\n    logger.debug(\"Check {} to see if it's a binary\".format(infile))\n    if is_binary(infile):\n        logger.debug(\n            'Copying binary {} to {} without rendering'\n            ''.format(infile, outfile)\n        )\n        shutil.copyfile(infile, outfile)\n    else:\n        # Force fwd slashes on Windows for get_template\n        # This is a by-design Jinja issue\n        infile_fwd_slashes = infile.replace(os.path.sep, '/')\n\n        # Render the file\n        try:\n            tmpl = env.get_template(infile_fwd_slashes)\n        except TemplateSyntaxError as exception:\n            # Disable translated so that printed exception contains verbose\n            # information about syntax error location\n            exception.translated = False\n            raise\n        rendered_file = tmpl.render(**context)\n\n        logger.debug('Writing contents to file {}'.format(outfile))\n\n        with io.open(outfile, 'w', encoding='utf-8') as fh:\n            fh.write(rendered_file)\n\n    # Apply file permissions to output file\n    shutil.copymode(infile, outfile)\n\n\ndef render_and_create_dir(dirname, context, output_dir, environment,\n                          overwrite_if_exists=False):\n    \"\"\"Render name of a directory, create the directory, return its path.\"\"\"\n    name_tmpl = environment.from_string(dirname)\n    rendered_dirname = name_tmpl.render(**context)\n\n    dir_to_create = os.path.normpath(\n        os.path.join(output_dir, rendered_dirname)\n    )\n\n    logger.debug('Rendered dir {} must exist in output_dir {}'.format(\n        dir_to_create,\n        output_dir\n    ))\n\n    output_dir_exists = os.path.exists(dir_to_create)\n\n    if overwrite_if_exists:\n        if output_dir_exists:\n            logger.debug(\n                'Output directory {} already exists,'\n                'overwriting it'.format(dir_to_create)\n            )\n    else:\n        if output_dir_exists:\n            msg = 'Error: \"{}\" directory already exists'.format(dir_to_create)\n            raise OutputDirExistsException(msg)\n\n    make_sure_path_exists(dir_to_create)\n    return dir_to_create\n\n\ndef ensure_dir_is_templated(dirname):\n    \"\"\"Ensure that dirname is a templated directory name.\"\"\"\n    if '{{' in dirname and '}}' in dirname:\n        return True\n    else:\n        raise NonTemplatedInputDirException\n\n\ndef _run_hook_from_repo_dir(repo_dir, hook_name, project_dir, context):\n    \"\"\"Run hook from repo directory, clean project directory if hook fails.\"\"\"\n    with work_in(repo_dir):\n        try:\n            run_hook(hook_name, project_dir, context)\n        except FailedHookException:\n            rmtree(project_dir)\n            logger.error(\n                \"Stopping generation because {} hook \"\n                \"script didn't exit successfully\".format(hook_name)\n            )\n            raise\n\n\ndef generate_files(repo_dir, context=None, output_dir='.',\n                   overwrite_if_exists=False):\n    \"\"\"Render the templates and saves them to files.\n\n    :param repo_dir: Project template input directory.\n    :param context: Dict for populating the template's variables.\n    :param output_dir: Where to output the generated project dir into.\n    :param overwrite_if_exists: Overwrite the contents of the output directory\n        if it exists.\n    \"\"\"\n    template_dir = find_template(repo_dir)\n    logger.debug('Generating project from {}...'.format(template_dir))\n    context = context or {}\n\n    unrendered_dir = os.path.split(template_dir)[1]\n    ensure_dir_is_templated(unrendered_dir)\n    env = StrictEnvironment(\n        context=context,\n        keep_trailing_newline=True,\n    )\n    try:\n        project_dir = render_and_create_dir(\n            unrendered_dir,\n            context,\n            output_dir,\n            env,\n            overwrite_if_exists\n        )\n    except UndefinedError as err:\n        msg = \"Unable to create project directory '{}'\".format(unrendered_dir)\n        raise UndefinedVariableInTemplate(msg, err, context)\n\n    # We want the Jinja path and the OS paths to match. Consequently, we'll:\n    #   + CD to the template folder\n    #   + Set Jinja's path to '.'\n    #\n    #  In order to build our files to the correct folder(s), we'll use an\n    # absolute path for the target folder (project_dir)\n\n    project_dir = os.path.abspath(project_dir)\n    logger.debug('Project directory is {}'.format(project_dir))\n\n    _run_hook_from_repo_dir(repo_dir, 'pre_gen_project', project_dir, context)\n\n    with work_in(template_dir):\n        env.loader = FileSystemLoader('.')\n\n        for root, dirs, files in os.walk('.'):\n            # We must separate the two types of dirs into different lists.\n            # The reason is that we don't want ``os.walk`` to go through the\n            # unrendered directories, since they will just be copied.\n            copy_dirs = []\n            render_dirs = []\n\n            for d in dirs:\n                d_ = os.path.normpath(os.path.join(root, d))\n                # We check the full path, because that's how it can be\n                # specified in the ``_copy_without_render`` setting, but\n                # we store just the dir name\n                if is_copy_only_path(d_, context):\n                    copy_dirs.append(d)\n                else:\n                    render_dirs.append(d)\n\n            for copy_dir in copy_dirs:\n                indir = os.path.normpath(os.path.join(root, copy_dir))\n                outdir = os.path.normpath(os.path.join(project_dir, indir))\n                logger.debug(\n                    'Copying dir {} to {} without rendering'\n                    ''.format(indir, outdir)\n                )\n                shutil.copytree(indir, outdir)\n\n            # We mutate ``dirs``, because we only want to go through these dirs\n            # recursively\n            dirs[:] = render_dirs\n            for d in dirs:\n                unrendered_dir = os.path.join(project_dir, root, d)\n                try:\n                    render_and_create_dir(\n                        unrendered_dir,\n                        context,\n                        output_dir,\n                        env,\n                        overwrite_if_exists\n                    )\n                except UndefinedError as err:\n                    rmtree(project_dir)\n                    _dir = os.path.relpath(unrendered_dir, output_dir)\n                    msg = \"Unable to create directory '{}'\".format(_dir)\n                    raise UndefinedVariableInTemplate(msg, err, context)\n\n            for f in files:\n                infile = os.path.normpath(os.path.join(root, f))\n                if is_copy_only_path(infile, context):\n                    outfile_tmpl = env.from_string(infile)\n                    outfile_rendered = outfile_tmpl.render(**context)\n                    outfile = os.path.join(project_dir, outfile_rendered)\n                    logger.debug(\n                        'Copying file {} to {} without rendering'\n                        ''.format(infile, outfile)\n                    )\n                    shutil.copyfile(infile, outfile)\n                    shutil.copymode(infile, outfile)\n                    continue\n                try:\n                    generate_file(project_dir, infile, context, env)\n                except UndefinedError as err:\n                    rmtree(project_dir)\n                    msg = \"Unable to create file '{}'\".format(infile)\n                    raise UndefinedVariableInTemplate(msg, err, context)\n\n    _run_hook_from_repo_dir(repo_dir, 'post_gen_project', project_dir, context)\n\n    return project_dir\n", "path": "cookiecutter/generate.py"}]}