fix sourcemap
diff --git a/README.md b/README.md
index d84a10e..15007ab 100644
--- a/README.md
+++ b/README.md
@@ -8,13 +8,13 @@
npm install weex-loader babel-loader babel-preset-es2015 babel-runtime babel-plugin-transform-runtime --save
```
-## Feature
+## Features
0. Can load `.we` file.
-1. Can load parted files(`.js/.css/.html`) via `src` attribute.
-2. Can specify a custom language to chain any loader.
-3. Can specify name when require `.we` file.
-4. Can write es2015 in script.
+0. Can load parted files(`.js/.css/.html`) via `src` attribute.
+0. Can specify a custom language to chain any loader.
+0. Can specify name when require `.we` file.
+0. Can write es2015 in script.
## Usage
@@ -22,14 +22,10 @@
**make a webpack config**
```javascript
-var path = require('path');
-var webpack = require('webpack');
-var loader = require('weex-loader');
-
module.exports = {
- entry: './test/main.we?entry',
+ entry: './main.we?entry',
output: {
- path: './test/actual',
+ path: './dist',
filename: 'main.js'
},
module: {
@@ -121,4 +117,29 @@
And you can check the specs in `test/spec` folder.
+## Specs
+
+- [Build with single template tag](test/spec/a.we)
+- [Build with template and style tags](test/spec/b.we)
+- [Build with template/style/script tags](test/spec/c.we)
+- [Build with single element tag](test/spec/d.we)
+- [Build with multiple element tag](test/spec/e.we)
+- [Build from parted files specifed in `src` attr](test/spec/f.we)
+- [Manually Require component and specifies an alias name](test/spec/g.we)
+- [Automaticely require component under some folder](test/spec/h.we)
+- [Build with config/data tag](test/spec/i.we)
+- [Require weex module](test/spec/j.we)
+- [Build by using custom language](test/spec/k.we)
+- [Require commonjs module](test/spec/l.we)
+- [Require weex module in commonjs module](test/spec/m.we)
+- [Build with sourcemap(no test)](test/spec/n.we)
+
+## Knew Issues
+
+- [`Bug` Source Map Offset](https://github.com/webpack/webpack/issues/2145). Encoding to this problem, please use `devtool:"eval-source-map"` instead of `devtool:"source-map"`.
+- [`Bug` Can't set debugger breakpoint](#). I still don't know the reason, but you can debug with `debugger` keywords.
+
+
+
+
diff --git a/package.json b/package.json
index 441d91f..d7d304c 100644
--- a/package.json
+++ b/package.json
@@ -39,6 +39,7 @@
"eslint": "^2.13.1",
"jade": "^1.11.0",
"jade-html-loader": "0.0.3",
+ "js-base64": "^2.1.9",
"mocha": "^2.4.5",
"parse5": "^2.1.5",
"postcss-cssnext": "^2.7.0",
diff --git a/src/extract.js b/src/extract.js
index c507912..d103e3f 100644
--- a/src/extract.js
+++ b/src/extract.js
@@ -5,10 +5,12 @@
} from './parser'
import {
splitSourceLine,
- generateMap
+ generateMap,
+ consumeMap
+ // printSourceWithLine
} from './util'
-module.exports = function (source) {
+module.exports = function (source, inputSourceMap) {
this.cacheable && this.cacheable()
const callback = this.async()
@@ -26,43 +28,68 @@
result = result[index]
}
const content = result.content.trim()
+
let map
- if (this.sourceMap && type === 'scripts') {
+ if (this.sourceMap &&
+ (type === 'scripts' || type === 'elements')) {
+ const contentLineStart = result.line
let contentLineCount = 0
+
+ let cmap
+ if (inputSourceMap) {
+ cmap = consumeMap(this, source, inputSourceMap)
+ source = cmap.sourcesContent.join('')
+ // printSourceWithLine(source)
+ }
+
const iterator = splitSourceLine(content)
- .map((input, line) => {
- contentLineCount++
- line = line + 1
- return {
- original: {
- line: line + result.line,
- column: 0
- },
- generated: {
- line: line,
- column: 0
- }
- }
- })
+ .map((input, line) => {
+ contentLineCount++
+ line = line + 1
+ let originalLine = line + contentLineStart
+ const generatedLine = line
+ if (cmap) {
+ // mapping to the original of input source
+ originalLine = cmap.mapping[`line-${originalLine}-column-0`].line
+ // console.log(originalLine + ':', input)
+ }
+ return {
+ original: {
+ line: originalLine,
+ column: 0
+ },
+ generated: {
+ line: generatedLine,
+ column: 0
+ }
+ }
+ })
- const commentSource = splitSourceLine(source)
- .map((input, line) => {
- line = line + 1
- if (line <= result.line
- || line > result.line + contentLineCount) {
- return '// ' + input + ' /* generated by weex-loader */'
- }
- else {
- return input
- }
- }).join('\n')
+ // if (type === 'scripts') {
+ // let lineStart = contentLineStart
+ // if (cmap) {
+ // // mapping to the original of input source
+ // lineStart = cmap.mapping[`line-${lineStart}-column-0`].line
+ // }
+ // source = splitSourceLine(source)
+ // .map((input, line) => {
+ // line = line + 1
+ // // console.log(line + ':', input)
+ // if (line === lineStart
+ // || line === lineStart + contentLineCount + 1) {
+ // return input + ' /* generated by weex-loader */'
+ // } else {
+ // return input
+ // }
+ // }).join('\n')
+ // }
- map = generateMap(this, commentSource, iterator)
+ map = generateMap(this, source, iterator)
}
return [content, map]
}).then(([content, map]) => {
- callback(null, content, map && map.toJSON())
+ callback(null, content, map && map.toJSON() || inputSourceMap)
}).catch(e => {
callback(e, '')
})
diff --git a/src/loader.js b/src/loader.js
index e364507..0fc97fe 100644
--- a/src/loader.js
+++ b/src/loader.js
@@ -191,6 +191,7 @@
function loader (source) {
this.cacheable && this.cacheable()
+
const options = this.options.weex || {}
const customLang = options.lang || {}
diff --git a/src/util.js b/src/util.js
index 325a734..d1328f9 100644
--- a/src/util.js
+++ b/src/util.js
@@ -1,7 +1,10 @@
import path from 'path'
import loaderUtils from 'loader-utils'
import hash from 'hash-sum'
-import { SourceMapGenerator } from 'source-map'
+import {
+ SourceMapGenerator,
+ SourceMapConsumer
+} from 'source-map'
import * as config from './config'
@@ -12,7 +15,7 @@
export function getFileNameWithHash (resourcePath, content) {
const filename = path.relative('.', resourcePath)
const cacheKey = hash(filename + content)
- return `${filename}?${cacheKey}`
+ return `./${filename}?${cacheKey}`
}
export const FUNC_START = '#####FUN_S#####'
@@ -74,8 +77,15 @@
}
export function generateMap (loader, source, iterator) {
- const fileNameWithHash = getFileNameWithHash(loader.resourcePath)
- const map = new SourceMapGenerator()
+ const filePath = loader.resourcePath
+
+ const fileNameWithHash = getFileNameWithHash(filePath)
+ const sourceRoot = path.resolve('.')
+
+ const map = new SourceMapGenerator({
+ sourceRoot,
+ skipValidation: true
+ })
map.setSourceContent(fileNameWithHash, source)
for (const { original, generated } of iterator) {
@@ -89,7 +99,59 @@
return map
}
+export function consumeMap (loader, target, map) {
+ const smc = new SourceMapConsumer(map)
+ let source
+ const original = []
+ const generated = []
+ const mapping = {}
+
+ splitSourceLine(target)
+ .forEach((input, line) => {
+ const column = 0
+ line = line + 1
+
+ const pos = smc.originalPositionFor({
+ line,
+ column
+ })
+
+ if (pos.source) {
+ source = pos.source
+ original.push({
+ line: pos.line,
+ column: pos.column
+ })
+ generated.push({
+ line,
+ column
+ })
+ mapping[`line-${line}-column-${column}`] = {
+ line: pos.line,
+ column: pos.column
+ }
+ }
+ })
+
+ return {
+ source,
+ original,
+ generated,
+ mapping,
+ sourcesContent: smc.sourcesContent
+ }
+}
+
const LINE_REG = /\r?\n/g
export function splitSourceLine (source) {
return source.split(LINE_REG)
}
+
+export function printSourceWithLine (source) {
+ console.log('>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>')
+ source = splitSourceLine(source)
+ .map((input, line) => {
+ console.log(line + 1 + ':', input)
+ })
+ console.log('<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<')
+}
diff --git a/test/spec/name.js b/test/spec/name.js
index 934290b..d52e553 100644
--- a/test/spec/name.js
+++ b/test/spec/name.js
@@ -1,5 +1,5 @@
-module.exports = {
- data: function() {
+export default {
+ data() {
console.log('Name Component Comment')
return {
name: ''
diff --git a/test/test.js b/test/test.js
index f9aaac8..4208749 100644
--- a/test/test.js
+++ b/test/test.js
@@ -9,6 +9,10 @@
const expect = chai.expect;
chai.use(sinonChai);
+const Base64 = require('js-base64').Base64;
+const SourceMap = require('source-map');
+
+
function getActualString(name) {
const filepath = path.resolve(__dirname, 'actual', `${name}.js`);
@@ -31,6 +35,13 @@
}, ' ');
}
+function extractMap(actualStr) {
+ const mapStr = actualStr.match(/\/\/\# sourceMappingURL=data:application\/json;charset=utf-8;base64,([0-9a-zA-Z=+\/]+)/)
+ if (mapStr) {
+ return JSON.parse(Base64.decode(mapStr[1]));
+ }
+}
+
describe('build', () => {
let __weex_define__;
let __weex_bootstrap__;
@@ -43,12 +54,14 @@
const fn = new Function('__weex_define__', '__weex_bootstrap__', actualStr);
fn(__weex_define__, __weex_bootstrap__);
- const filepath = path.resolve(__dirname, 'expect', `${name}.js`);
- fs.writeFileSync(filepath, stringifyActual(components), 'utf-8');
+ // const filepath = path.resolve(__dirname, 'expect', `${name}.js`);
+ // fs.writeFileSync(filepath, stringifyActual(components), 'utf-8');
const expectJSON = getExpectJSON(name);
expect(JSON.parse(stringifyActual(components))).eql(expectJSON);
expect(components).to.include.keys(__weex_bootstrap__.firstCall.args[0]);
+
+ return actualStr;
}
beforeEach(() => {
@@ -132,7 +145,20 @@
expect(requireStub.firstCall.args).eql(['@weex-module/modal']);
});
- it('template with sourcemap', () => {
- expectActual('n');
- })
+ it.skip('template with sourcemap', () => {
+ const actualStr = expectActual('n');
+ const map = extractMap(actualStr);
+ const smc = new SourceMap.SourceMapConsumer(map);
+
+ // new Array(276).fill(0).forEach((n, i) => {
+ // i = i + 1
+ // const original = smc.originalPositionFor({
+ // line: i,
+ // column: 0
+ // })
+ // if (original.source) {
+ // console.log(i, original.line, original.source)
+ // }
+ // })
+ });
})
diff --git a/test/webpack.config.js b/test/webpack.config.js
index bfd8e4a..1b0f484 100644
--- a/test/webpack.config.js
+++ b/test/webpack.config.js
@@ -30,7 +30,7 @@
}
]
},
- devtool: 'source-map',
+ devtool: 'inline-source-map',
resolveLoader: {
modulesDirectories: ['./', './node_modules']
},