1 | /**
|
---|
2 | * Module dependencies.
|
---|
3 | */
|
---|
4 |
|
---|
5 | var Compiler = require('../visitor/compiler')
|
---|
6 | , nodes = require('../nodes')
|
---|
7 | , parse = require('url').parse
|
---|
8 | , relative = require('path').relative
|
---|
9 | , join = require('path').join
|
---|
10 | , dirname = require('path').dirname
|
---|
11 | , extname = require('path').extname
|
---|
12 | , sep = require('path').sep;
|
---|
13 |
|
---|
14 | /**
|
---|
15 | * Return a url() function which resolves urls.
|
---|
16 | *
|
---|
17 | * Options:
|
---|
18 | *
|
---|
19 | * - `paths` resolution path(s), merged with general lookup paths
|
---|
20 | * - `nocheck` don't check file existence
|
---|
21 | *
|
---|
22 | * Examples:
|
---|
23 | *
|
---|
24 | * stylus(str)
|
---|
25 | * .set('filename', __dirname + '/css/test.styl')
|
---|
26 | * .define('url', stylus.resolver({ nocheck: true }))
|
---|
27 | * .render(function(err, css){ ... })
|
---|
28 | *
|
---|
29 | * @param {Object} [options]
|
---|
30 | * @return {Function}
|
---|
31 | * @api public
|
---|
32 | */
|
---|
33 |
|
---|
34 | module.exports = function(options) {
|
---|
35 | options = options || {};
|
---|
36 |
|
---|
37 | function resolver(url) {
|
---|
38 | // Compile the url
|
---|
39 | var compiler = new Compiler(url)
|
---|
40 | , filename = url.filename;
|
---|
41 | compiler.isURL = true;
|
---|
42 | url = parse(url.nodes.map(function(node){
|
---|
43 | return compiler.visit(node);
|
---|
44 | }).join(''));
|
---|
45 |
|
---|
46 | // Parse literal
|
---|
47 | var literal = new nodes.Literal('url("' + url.href + '")')
|
---|
48 | , path = url.pathname
|
---|
49 | , dest = this.options.dest
|
---|
50 | , tail = ''
|
---|
51 | , res;
|
---|
52 |
|
---|
53 | // Absolute or hash
|
---|
54 | if (url.protocol || !path || '/' == path[0]) return literal;
|
---|
55 |
|
---|
56 | // Check that file exists
|
---|
57 | if (!options.nocheck) {
|
---|
58 | var _paths = options.paths || [];
|
---|
59 | path = require('../utils').lookup(path, _paths.concat(this.paths));
|
---|
60 | if (!path) return literal;
|
---|
61 | }
|
---|
62 |
|
---|
63 | if (this.includeCSS && extname(path) == '.css')
|
---|
64 | return new nodes.Literal(url.href);
|
---|
65 |
|
---|
66 | if (url.search) tail += url.search;
|
---|
67 | if (url.hash) tail += url.hash;
|
---|
68 |
|
---|
69 | if (dest && extname(dest) == '.css')
|
---|
70 | dest = dirname(dest);
|
---|
71 |
|
---|
72 | res = relative(dest || dirname(this.filename), options.nocheck
|
---|
73 | ? join(dirname(filename), path)
|
---|
74 | : path) + tail;
|
---|
75 |
|
---|
76 | if ('\\' == sep) res = res.replace(/\\/g, '/');
|
---|
77 |
|
---|
78 | return new nodes.Literal('url("' + res + '")');
|
---|
79 | };
|
---|
80 |
|
---|
81 | // Expose options to Evaluator
|
---|
82 | resolver.options = options;
|
---|
83 | resolver.raw = true;
|
---|
84 | return resolver;
|
---|
85 | };
|
---|