annotate piecrust/processing/less.py @ 834:10c482d57c79

Allow an individual page to override pretty_urls in it config
author Ben Artin <ben@artins.org>
date Mon, 02 Jan 2017 20:33:57 -0500
parents 35d4c172e5a6
children 4850f8c21b6e
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
3
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
1 import os
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
2 import os.path
221
f82262f59600 bake: Fix processing record bugs and error logging for external processes.
Ludovic Chabant <ludovic@chabant.com>
parents: 195
diff changeset
3 import sys
3
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
4 import json
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
5 import hashlib
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
6 import logging
17
de6a296744f7 The LESS compiler must be launched in a shell on Windows.
Ludovic Chabant <ludovic@chabant.com>
parents: 7
diff changeset
7 import platform
3
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
8 import subprocess
221
f82262f59600 bake: Fix processing record bugs and error logging for external processes.
Ludovic Chabant <ludovic@chabant.com>
parents: 195
diff changeset
9 from piecrust.processing.base import (
f82262f59600 bake: Fix processing record bugs and error logging for external processes.
Ludovic Chabant <ludovic@chabant.com>
parents: 195
diff changeset
10 SimpleFileProcessor, ExternalProcessException)
3
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
11 from piecrust.processing.tree import FORCE_BUILD
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
12
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
13
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
14 logger = logging.getLogger(__name__)
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
15
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
16
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
17 class LessProcessor(SimpleFileProcessor):
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
18 PROCESSOR_NAME = 'less'
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
19
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
20 def __init__(self):
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
21 super(LessProcessor, self).__init__({'less': 'css'})
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
22 self._conf = None
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
23 self._map_dir = None
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
24
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
25 def onPipelineStart(self, pipeline):
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
26 self._map_dir = os.path.join(pipeline.tmp_dir, 'less')
414
c4b3a7fd2f87 bake: Make pipeline processing multi-process.
Ludovic Chabant <ludovic@chabant.com>
parents: 240
diff changeset
27 if (pipeline.is_first_worker and
c4b3a7fd2f87 bake: Make pipeline processing multi-process.
Ludovic Chabant <ludovic@chabant.com>
parents: 240
diff changeset
28 not os.path.isdir(self._map_dir)):
3
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
29 os.makedirs(self._map_dir)
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
30
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
31 def getDependencies(self, path):
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
32 map_path = self._getMapPath(path)
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
33 try:
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
34 with open(map_path, 'r') as f:
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
35 dep_map = json.load(f)
498
35d4c172e5a6 less: Fix issues with the map file on Windows.
Ludovic Chabant <ludovic@chabant.com>
parents: 414
diff changeset
36 except OSError:
3
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
37 # Map file not found... rebuild.
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
38 logger.debug("No map file found for LESS file '%s' at '%s'. "
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
39 "Rebuilding" % (path, map_path))
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
40 return FORCE_BUILD
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
41
498
35d4c172e5a6 less: Fix issues with the map file on Windows.
Ludovic Chabant <ludovic@chabant.com>
parents: 414
diff changeset
42 # Check the version, since the `sources` list has changed
35d4c172e5a6 less: Fix issues with the map file on Windows.
Ludovic Chabant <ludovic@chabant.com>
parents: 414
diff changeset
43 # meanings over time.
35d4c172e5a6 less: Fix issues with the map file on Windows.
Ludovic Chabant <ludovic@chabant.com>
parents: 414
diff changeset
44 if dep_map.get('version') != 3:
35d4c172e5a6 less: Fix issues with the map file on Windows.
Ludovic Chabant <ludovic@chabant.com>
parents: 414
diff changeset
45 logger.warning("Unknown LESS map version. Force rebuilding.")
35d4c172e5a6 less: Fix issues with the map file on Windows.
Ludovic Chabant <ludovic@chabant.com>
parents: 414
diff changeset
46 return FORCE_BUILD
35d4c172e5a6 less: Fix issues with the map file on Windows.
Ludovic Chabant <ludovic@chabant.com>
parents: 414
diff changeset
47
35d4c172e5a6 less: Fix issues with the map file on Windows.
Ludovic Chabant <ludovic@chabant.com>
parents: 414
diff changeset
48 # Get the sources, but make all paths absolute.
35d4c172e5a6 less: Fix issues with the map file on Windows.
Ludovic Chabant <ludovic@chabant.com>
parents: 414
diff changeset
49 sources = dep_map.get('sources')
35d4c172e5a6 less: Fix issues with the map file on Windows.
Ludovic Chabant <ludovic@chabant.com>
parents: 414
diff changeset
50 path_dir = os.path.dirname(path)
35d4c172e5a6 less: Fix issues with the map file on Windows.
Ludovic Chabant <ludovic@chabant.com>
parents: 414
diff changeset
51
35d4c172e5a6 less: Fix issues with the map file on Windows.
Ludovic Chabant <ludovic@chabant.com>
parents: 414
diff changeset
52 def _makeAbs(p):
35d4c172e5a6 less: Fix issues with the map file on Windows.
Ludovic Chabant <ludovic@chabant.com>
parents: 414
diff changeset
53 return os.path.join(path_dir, p)
35d4c172e5a6 less: Fix issues with the map file on Windows.
Ludovic Chabant <ludovic@chabant.com>
parents: 414
diff changeset
54 deps = list(map(_makeAbs, sources))
35d4c172e5a6 less: Fix issues with the map file on Windows.
Ludovic Chabant <ludovic@chabant.com>
parents: 414
diff changeset
55 return [map_path] + deps
35d4c172e5a6 less: Fix issues with the map file on Windows.
Ludovic Chabant <ludovic@chabant.com>
parents: 414
diff changeset
56
3
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
57 def _doProcess(self, in_path, out_path):
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
58 self._ensureInitialized()
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
59
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
60 map_path = self._getMapPath(in_path)
498
35d4c172e5a6 less: Fix issues with the map file on Windows.
Ludovic Chabant <ludovic@chabant.com>
parents: 414
diff changeset
61 map_url = '/' + os.path.relpath(
35d4c172e5a6 less: Fix issues with the map file on Windows.
Ludovic Chabant <ludovic@chabant.com>
parents: 414
diff changeset
62 map_path, self.app.root_dir).replace('\\', '/')
35d4c172e5a6 less: Fix issues with the map file on Windows.
Ludovic Chabant <ludovic@chabant.com>
parents: 414
diff changeset
63
35d4c172e5a6 less: Fix issues with the map file on Windows.
Ludovic Chabant <ludovic@chabant.com>
parents: 414
diff changeset
64 # On Windows, it looks like LESSC is confused with paths when the
35d4c172e5a6 less: Fix issues with the map file on Windows.
Ludovic Chabant <ludovic@chabant.com>
parents: 414
diff changeset
65 # map file is not to be created in the same directory as the input
35d4c172e5a6 less: Fix issues with the map file on Windows.
Ludovic Chabant <ludovic@chabant.com>
parents: 414
diff changeset
66 # file (it ends up writing invalid dependencies in the map file, with
35d4c172e5a6 less: Fix issues with the map file on Windows.
Ludovic Chabant <ludovic@chabant.com>
parents: 414
diff changeset
67 # a mix of relative and absolute paths stuck together).
35d4c172e5a6 less: Fix issues with the map file on Windows.
Ludovic Chabant <ludovic@chabant.com>
parents: 414
diff changeset
68 # So create it there and move it afterwards... :(
35d4c172e5a6 less: Fix issues with the map file on Windows.
Ludovic Chabant <ludovic@chabant.com>
parents: 414
diff changeset
69 temp_map_path = os.path.join(
35d4c172e5a6 less: Fix issues with the map file on Windows.
Ludovic Chabant <ludovic@chabant.com>
parents: 414
diff changeset
70 os.path.dirname(in_path),
35d4c172e5a6 less: Fix issues with the map file on Windows.
Ludovic Chabant <ludovic@chabant.com>
parents: 414
diff changeset
71 os.path.basename(map_path))
35d4c172e5a6 less: Fix issues with the map file on Windows.
Ludovic Chabant <ludovic@chabant.com>
parents: 414
diff changeset
72
240
c1d4e86a3918 less: Generate a proper, available URL for the LESS CSS map file.
Ludovic Chabant <ludovic@chabant.com>
parents: 221
diff changeset
73 args = [self._conf['bin'],
498
35d4c172e5a6 less: Fix issues with the map file on Windows.
Ludovic Chabant <ludovic@chabant.com>
parents: 414
diff changeset
74 '--source-map=%s' % temp_map_path,
240
c1d4e86a3918 less: Generate a proper, available URL for the LESS CSS map file.
Ludovic Chabant <ludovic@chabant.com>
parents: 221
diff changeset
75 '--source-map-url=%s' % map_url]
3
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
76 args += self._conf['options']
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
77 args.append(in_path)
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
78 args.append(out_path)
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
79 logger.debug("Processing LESS file: %s" % args)
17
de6a296744f7 The LESS compiler must be launched in a shell on Windows.
Ludovic Chabant <ludovic@chabant.com>
parents: 7
diff changeset
80
de6a296744f7 The LESS compiler must be launched in a shell on Windows.
Ludovic Chabant <ludovic@chabant.com>
parents: 7
diff changeset
81 # On Windows, we need to run the process in a shell environment
de6a296744f7 The LESS compiler must be launched in a shell on Windows.
Ludovic Chabant <ludovic@chabant.com>
parents: 7
diff changeset
82 # otherwise it looks like `PATH` isn't taken into account.
116
1c13f3389fcb Cosmetic fix.
Ludovic Chabant <ludovic@chabant.com>
parents: 17
diff changeset
83 shell = (platform.system() == 'Windows')
17
de6a296744f7 The LESS compiler must be launched in a shell on Windows.
Ludovic Chabant <ludovic@chabant.com>
parents: 7
diff changeset
84 try:
221
f82262f59600 bake: Fix processing record bugs and error logging for external processes.
Ludovic Chabant <ludovic@chabant.com>
parents: 195
diff changeset
85 proc = subprocess.Popen(
f82262f59600 bake: Fix processing record bugs and error logging for external processes.
Ludovic Chabant <ludovic@chabant.com>
parents: 195
diff changeset
86 args, shell=shell,
f82262f59600 bake: Fix processing record bugs and error logging for external processes.
Ludovic Chabant <ludovic@chabant.com>
parents: 195
diff changeset
87 stderr=subprocess.PIPE)
f82262f59600 bake: Fix processing record bugs and error logging for external processes.
Ludovic Chabant <ludovic@chabant.com>
parents: 195
diff changeset
88 stdout_data, stderr_data = proc.communicate()
17
de6a296744f7 The LESS compiler must be launched in a shell on Windows.
Ludovic Chabant <ludovic@chabant.com>
parents: 7
diff changeset
89 except FileNotFoundError as ex:
de6a296744f7 The LESS compiler must be launched in a shell on Windows.
Ludovic Chabant <ludovic@chabant.com>
parents: 7
diff changeset
90 logger.error("Tried running LESS processor with command: %s" %
195
b4724e577a8c cosmetic: Fix some PEP8 issues.
Ludovic Chabant <ludovic@chabant.com>
parents: 119
diff changeset
91 args)
17
de6a296744f7 The LESS compiler must be launched in a shell on Windows.
Ludovic Chabant <ludovic@chabant.com>
parents: 7
diff changeset
92 raise Exception("Error running LESS processor. "
de6a296744f7 The LESS compiler must be launched in a shell on Windows.
Ludovic Chabant <ludovic@chabant.com>
parents: 7
diff changeset
93 "Did you install it?") from ex
221
f82262f59600 bake: Fix processing record bugs and error logging for external processes.
Ludovic Chabant <ludovic@chabant.com>
parents: 195
diff changeset
94 if proc.returncode != 0:
f82262f59600 bake: Fix processing record bugs and error logging for external processes.
Ludovic Chabant <ludovic@chabant.com>
parents: 195
diff changeset
95 raise ExternalProcessException(
f82262f59600 bake: Fix processing record bugs and error logging for external processes.
Ludovic Chabant <ludovic@chabant.com>
parents: 195
diff changeset
96 stderr_data.decode(sys.stderr.encoding))
f82262f59600 bake: Fix processing record bugs and error logging for external processes.
Ludovic Chabant <ludovic@chabant.com>
parents: 195
diff changeset
97
498
35d4c172e5a6 less: Fix issues with the map file on Windows.
Ludovic Chabant <ludovic@chabant.com>
parents: 414
diff changeset
98 logger.debug("Moving map file: %s -> %s" % (temp_map_path, map_path))
35d4c172e5a6 less: Fix issues with the map file on Windows.
Ludovic Chabant <ludovic@chabant.com>
parents: 414
diff changeset
99 if os.path.exists(map_path):
35d4c172e5a6 less: Fix issues with the map file on Windows.
Ludovic Chabant <ludovic@chabant.com>
parents: 414
diff changeset
100 os.remove(map_path)
35d4c172e5a6 less: Fix issues with the map file on Windows.
Ludovic Chabant <ludovic@chabant.com>
parents: 414
diff changeset
101 os.rename(temp_map_path, map_path)
35d4c172e5a6 less: Fix issues with the map file on Windows.
Ludovic Chabant <ludovic@chabant.com>
parents: 414
diff changeset
102
3
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
103 return True
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
104
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
105 def _ensureInitialized(self):
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
106 if self._conf is not None:
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
107 return
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
108
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
109 self._conf = self.app.config.get('less') or {}
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
110 self._conf.setdefault('bin', 'lessc')
195
b4724e577a8c cosmetic: Fix some PEP8 issues.
Ludovic Chabant <ludovic@chabant.com>
parents: 119
diff changeset
111 self._conf.setdefault('options', ['--compress'])
3
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
112 if not isinstance(self._conf['options'], list):
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
113 raise Exception("The `less/options` configuration setting "
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
114 "must be an array of arguments.")
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
115
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
116 def _getMapPath(self, path):
119
0811f92cbdc7 Slightly more robust dependency handling for the LESS processor.
Ludovic Chabant <ludovic@chabant.com>
parents: 116
diff changeset
117 map_name = "%s_%s.map" % (
0811f92cbdc7 Slightly more robust dependency handling for the LESS processor.
Ludovic Chabant <ludovic@chabant.com>
parents: 116
diff changeset
118 os.path.basename(path),
0811f92cbdc7 Slightly more robust dependency handling for the LESS processor.
Ludovic Chabant <ludovic@chabant.com>
parents: 116
diff changeset
119 hashlib.md5(path.encode('utf8')).hexdigest())
3
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
120 map_path = os.path.join(self._map_dir, map_name)
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
121 return map_path
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
122