Webpack sass loader 解析绝对路径

5

我希望在@import语句中能够使用绝对路径,例如:

@import '/templates/common/variables'

然而,Sass似乎将其解析为文件系统中的绝对URL。我希望它查找我的项目文件夹。例如,我的文件实际上位于/home/username/project/templates/common/_variables.scss

这种情况有可能吗?

我已经查看了includePaths,但似乎没有任何作用。

我正在使用Encore编写我的Webpack文件,它大致如下:

const Encore = require('@symfony/webpack-encore');
Encore
    .setOutputPath("web/build/")
    .setPublicPath("/build")
    // [...]
    .enableSassLoader(options => {
        options.includePaths = [path.resolve(__dirname, '/web')];
    })
;

这里还有生成的webpack配置(非常冗长,我没有用上面示例路径替换我的真实路径):

{  
    context:'/var/www',
    entry:{  
        index:[  
            './polyfills.js',
            './web/typo3conf/ext/hn_project/ext_index.js',
            './web/typo3conf/ext/hn_templates/ext_index.js'
        ],
        backend:[  
            './polyfills.js',
            './web/typo3conf/ext/hn_project/ext_backend.js'
        ]
    },
    output:{  
        path:'/var/www/web/build',
        filename:'[name].[chunkhash:8].js',
        publicPath:'/build/',
        pathinfo:false
    },
    module:{  
        rules:[  
            {  
                test:/\.jsx?$/,
                exclude:/(node_modules|bower_components)/,
                use:[  
                    {  
                        loader:'babel-loader',
                        options:{  
                            cacheDirectory:true,
                            presets:[  
                                [  
                                    'env',
                                    {  
                                        modules:false,
                                        targets:{  
                                            browsers:[  
                                                'and_chr 67',
                                                'and_uc 11.8',
                                                'chrome 67',
                                                'chrome 66',
                                                'chrome 65',
                                                'edge 17',
                                                'edge 16',
                                                'firefox 60',
                                                'firefox 59',
                                                'firefox 52',
                                                'ie 11',
                                                'ie 10',
                                                'ie_mob 11',
                                                'ie_mob 10',
                                                'ios_saf 11.3',
                                                'ios_saf 11.0-11.2',
                                                'opera 53',
                                                'opera 52',
                                                'safari 11.1',
                                                'safari 11',
                                                'samsung 6.2'
                                            ],
                                            uglify:true
                                        },
                                        useBuiltIns:true
                                    }
                                ]
                            ],
                            plugins:[  

                            ]
                        }
                    }
                ]
            },
            {  
                test:/\.css$/,
                use:[  
                    {  
                        loader:'/var/www/node_modules/extract-text-webpack-plugin/dist/loader.js',
                        options:{  
                            omit:1,
                            remove:true
                        }
                    },
                    {  
                        loader:'style-loader'
                    },
                    {  
                        loader:'css-loader',
                        options:{  
                            minimize:true,
                            sourceMap:false,
                            importLoaders:1
                        }
                    },
                    {  
                        loader:'postcss-loader',
                        options:{  
                            sourceMap:false,
                            ident:'postcss',
                            plugins:[  
                                {  
                                    [  
                                        Function:plugin
                                    ]                                    options:{  
                                        grid:false
                                    },
                                    browsers:undefined,
                                    info:[  
                                        Function
                                    ],
                                    postcssPlugin:'autoprefixer',
                                    postcssVersion:'6.0.23'
                                }
                            ]
                        }
                    }
                ]
            },
            {  
                test:/\.(png|jpg|jpeg|gif|ico|svg|webp)$/,
                loader:'url-loader',
                options:{  
                    name:'images/[name].[hash:8].[ext]',
                    publicPath:'/build/',
                    limit:4096
                }
            },
            {  
                test:/\.(woff|woff2|ttf|eot|otf)$/,
                loader:'url-loader',
                options:{  
                    name:'fonts/[name].[hash:8].[ext]',
                    publicPath:'/build/',
                    limit:4096
                }
            },
            {  
                test:/\.s[ac]ss$/,
                use:[  
                    {  
                        loader:'/var/www/node_modules/extract-text-webpack-plugin/dist/loader.js',
                        options:{  
                            omit:1,
                            remove:true
                        }
                    },
                    {  
                        loader:'style-loader'
                    },
                    {  
                        loader:'css-loader',
                        options:{  
                            minimize:true,
                            sourceMap:false,
                            importLoaders:1
                        }
                    },
                    {  
                        loader:'postcss-loader',
                        options:{  
                            sourceMap:false,
                            ident:'postcss',
                            plugins:[  
                                {  
                                    [  
                                        Function:plugin
                                    ]                                    options:{  
                                        grid:false
                                    },
                                    browsers:undefined,
                                    info:[  
                                        Function
                                    ],
                                    postcssPlugin:'autoprefixer',
                                    postcssVersion:'6.0.23'
                                }
                            ]
                        }
                    },
                    {  
                        loader:'resolve-url-loader',
                        options:{  
                            sourceMap:false
                        }
                    },
                    {  
                        loader:'sass-loader',
                        options:{  
                            sourceMap:true,
                            includePaths:[  
                                '/web'
                            ]
                        }
                    }
                ]
            }
        ]
    },
    plugins:[  
        ExtractTextPlugin        {  
            filename:'[name].[contenthash:8].css',
            id:1,
            options:{  
                allChunks:false
            }
        },
        DeleteUnusedEntriesJSPlugin        {  
            entriesToDelete:[  

            ]
        },
        ManifestPlugin        {  
            opts:{  
                publicPath:null,
                basePath:'build/',
                fileName:'manifest.json',
                transformExtensions:/^(gz|map)$/i,
                writeToFileEmit:true,
                seed:null,
                filter:null,
                map:null,
                generate:null,
                sort:null,
                serialize:[  
                    Function:serialize
                ]
            }
        },
        LoaderOptionsPlugin        {  
            options:{  
                debug:false,
                options:{  
                    context:'/var/www',
                    output:{  
                        path:'/var/www/web/build'
                    }
                },
                test:{  
                    test:[  
                        Function:test
                    ]
                }
            }
        },
        HashedModuleIdsPlugin        {  
            options:{  
                hashFunction:'md5',
                hashDigest:'base64',
                hashDigestLength:4
            }
        },
        WebpackChunkHash        {  
            algorithm:'md5',
            digest:'hex',
            additionalHashContent:[  
                Function
            ]
        },
        ProvidePlugin        {  
            definitions:{  
                '$':'jquery',
                jQuery:'jquery',
                'window.jQuery':'jquery'
            }
        },
        CleanWebpackPlugin        {  
            paths:[  
                '**/*'
            ],
            options:{  
                root:'/var/www/web/build',
                verbose:false,
                allowExternal:false,
                dry:false
            }
        },
        DefinePlugin        {  
            definitions:{  
                'process.env':{  
                    NODE_ENV:'"production"'
                }
            }
        },
        UglifyJsPlugin        {  
            options:{  
                sourceMap:false
            }
        },
        FriendlyErrorsWebpackPlugin        {  
            compilationSuccessInfo:{  
                messages:[  

                ]
            },
            onErrors:undefined,
            shouldClearConsole:false,
            formatters:[  
                [  
                    Function:format
                ],
                [  
                    Function:format
                ],
                [  
                    Function:format
                ],
                [  
                    Function:format
                ],
                [  
                    Function:format
                ],
                [  
                    Function:format
                ]
            ],
            transformers:[  
                [  
                    Function:transform
                ],
                [  
                    Function:transform
                ],
                [  
                    Function:transform
                ],
                [  
                    Function:transform
                ],
                [  
                    Function:transform
                ],
                [  
                    Function:transform
                ]
            ]
        },
        AssetOutputDisplayPlugin        {  
            outputPath:'web/build',
            friendlyErrorsPlugin:FriendlyErrorsWebpackPlugin            {  
                compilationSuccessInfo:{  
                    messages:[  

                    ]
                },
                onErrors:undefined,
                shouldClearConsole:false,
                formatters:[  
                    [  
                        Function:format
                    ],
                    [  
                        Function:format
                    ],
                    [  
                        Function:format
                    ],
                    [  
                        Function:format
                    ],
                    [  
                        Function:format
                    ],
                    [  
                        Function:format
                    ]
                ],
                transformers:[  
                    [  
                        Function:transform
                    ],
                    [  
                        Function:transform
                    ],
                    [  
                        Function:transform
                    ],
                    [  
                        Function:transform
                    ],
                    [  
                        Function:transform
                    ],
                    [  
                        Function:transform
                    ]
                ]
            }
        },
        {  
            apply:[  
                Function:bound apply
            ]
        },
        ZopfliPlugin        {  
            asset:'[path].gz[query]',
            algorithm:[  
                Function
            ],
            filename:false,
            compressionOptions:{  
                verbose:false,
                verbose_more:false,
                numiterations:15,
                blocksplitting:true,
                blocksplittinglast:false,
                blocksplittingmax:15
            },
            test:/\.(js|css|svg|ttf)$/,
            threshold:1400,
            minRatio:0.8,
            deleteOriginalAssets:false
        },
        BrotliPlugin        {  
            asset:'[path].br[query]',
            test:/\.(js|css|svg|ttf)$/,
            threshold:1400,
            minRatio:0.8,
            deleteOriginalAssets:false,
            compress:[  
                Function
            ]
        }
    ],
    performance:{  
        hints:false
    },
    stats:{  
        hash:false,
        version:false,
        timings:false,
        assets:false,
        chunks:false,
        maxModules:0,
        modules:false,
        reasons:false,
        children:false,
        source:false,
        errors:false,
        errorDetails:false,
        warnings:false,
        publicPath:false
    },
    resolve:{  
        extensions:[  
            '.js',
            '.jsx',
            '.vue',
            '.ts',
            '.tsx'
        ],
        alias:{  

        }
    },
    externals:{  

    }
}

这里还有一些可能有用的软件包版本信息

@symfony/webpack-encore@0.20.1
node-sass@4.9.0
sass-loader@7.0.3
webpack@3.12.0
3个回答

7
你可以使用Webpack的别名功能。将每个导入的/templates解析为你项目中的templates/文件夹。
const path = require('path');

module.exports = {
  // ...
  resolve: {
    alias: {
      '/templates': path.resolve(__dirname, './templates')
    }
  }
};

我阅读了`@sympony/webpack-encore`并发现了`addAliases`设置。你可以使用以下示例:
const path = require('path');
const Encore = require('@symfony/webpack-encore');

Encore
  // ...
  .addAliases({
    '/templates': path.resolve(__dirname, './templates')
  });

在你的Scss/SASS中,使用~来引入文件路径。
@import '~/templates/common/variables'

这在scss / sass中不起作用。但是在js导入中可以工作,这很好。 - Nemo64
Webpack可以解析其他文件的导入。https://github.com/webpack-contrib/sass-loader#imports - VitorLuizC
你只需要在导入路径前面添加~。比如@import '~/templates/... .scss'。我将更新我的答案。 - VitorLuizC
~/ 代表主目录,但是简单的 ~templates 也可以达到效果!谢谢 :) - Andreew4x4

1

也许你已经自己找到了答案,但以防万一其他人来到这里,使用与导入文件相关的相对路径的url()的常见方法是使用resolve-url-loader。还要注意,在前面的加载程序中必须将sourceMap设置为true。

https://www.npmjs.com/package/resolve-url-loader

That's an example on how to use it:

{
    // Note that sourceMap is needed to be true at least in sass-loader so resolve-url-loader works fine
    test: /\.scss$/,
    use: [
        {
            loader: "style-loader",
            options: { sourceMap: true }
        }, // Adds CSS to the DOM by injecting a <style> tag
        {
            loader: "css-loader",
            options: { sourceMap: true }
        }, // The css-loader interprets @import and url() like import/require() and will resolve them.
        {
            loader: "postcss-loader",
            options: {
                sourceMap: true,
                plugins: [
                    require("autoprefixer")({ browsers: ["last 2 versions"] })
                ]
            }
        }, // Adds prefix for cross-browser support
        {
            loader: "resolve-url-loader",
            options: { sourceMap: true }
        }, // Webpack loader that resolves relative paths in url() statements based on the original source file.
        {
            loader: "sass-loader",
            options: { sourceMap: true }
        } // Loads a Sass/SCSS file and compiles it to CSS.
    ]
}

你谈论的是另一个问题。Sass在自身内部导入其他Sass文件,因此在这一点上resolve-url-loader已经太晚了。我仍然没有找到解决方法。Less有一个paths选项。看起来includePaths是我正在寻找的,但它不起作用。我现在有点接受了这一点。 - Nemo64

0

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接