dante2-editor 0.2.0 → 0.3.1
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/.babelrc +20 -0
- data/.eslint +13 -0
- data/.gitignore +15 -0
- data/README.md +5 -1
- data/dante2.gemspec +2 -4
- data/{app → demo}/assets/index.html +2 -2
- data/{app → demo}/assets/license.html +1 -1
- data/{app → demo}/assets/options.html +1 -5
- data/{app → demo}/assets/store.json +0 -0
- data/demo/data/poc.js +9 -0
- data/demo/demo.js +9 -0
- data/demo/initialize.js +7 -0
- data/{app → demo}/styles/layout/layout.scss +0 -0
- data/{app → demo}/styles/layout/normalize.css +0 -0
- data/{app → demo}/styles/layout/scaffold.scss +0 -0
- data/{app → demo}/styles/layout/tooltips.scss +0 -0
- data/dist/Dante2.js +2995 -0
- data/dist/Dante2.min.js +3 -0
- data/dist/Dante2.min.js.map +1 -0
- data/dist/DanteStyles.css +2 -0
- data/dist/DanteStyles.css.map +1 -0
- data/dist/DanteStyles.js +102 -0
- data/dist/DanteStyles.min.js +2 -0
- data/dist/DanteStyles.min.js.map +1 -0
- data/dist/dante-vendors.js +48316 -0
- data/dist/dante-vendors.min.js +29 -0
- data/dist/dante-vendors.min.js.map +1 -0
- data/{app/styles/fonts/dante → dist/fonts}/dante.eot +0 -0
- data/{app/styles/fonts/dante → dist/fonts}/dante.svg +0 -0
- data/{app/styles/fonts/dante → dist/fonts}/dante.ttf +0 -0
- data/{app/styles/fonts/dante → dist/fonts}/dante.woff +0 -0
- data/{app/styles/fonts/dante → dist/fonts}/fontello.eot +0 -0
- data/{app/styles/fonts/dante → dist/fonts}/fontello.svg +0 -0
- data/{app/styles/fonts/dante → dist/fonts}/fontello.ttf +0 -0
- data/{app/styles/fonts/dante → dist/fonts}/fontello.woff +0 -0
- data/docs/app.css +430 -1
- data/docs/app.css.map +1 -1
- data/docs/app.js +62 -2
- data/docs/app.js.map +1 -1
- data/docs/dante-vendors.js +49513 -22
- data/docs/dante-vendors.js.map +1 -1
- data/docs/dante.css +1602 -1
- data/docs/dante.css.map +1 -1
- data/docs/dante.js +3310 -3
- data/docs/dante.js.map +1 -1
- data/docs/doc.html +3 -7
- data/docs/index.html +4 -4
- data/docs/license.html +3 -3
- data/docs/options.html +53 -0
- data/package.json +47 -17
- data/rb_lib/dante2-editor/rails.rb +15 -0
- data/{lib → rb_lib}/dante2-editor/version.rb +1 -1
- data/{lib → rb_lib}/dante2-editor.rb +0 -0
- data/src/components/blocks/embed.js +126 -0
- data/src/components/blocks/image.js +377 -0
- data/src/components/blocks/placeholder.js +68 -0
- data/src/components/blocks/video.js +80 -0
- data/src/components/dante.js +291 -0
- data/src/components/dante_editor.js +928 -0
- data/src/components/debug.js +104 -0
- data/src/components/decorators/link.js +64 -0
- data/src/components/popovers/addButton.js +318 -0
- data/src/components/popovers/image.js +188 -0
- data/src/components/popovers/link.js +107 -0
- data/src/components/popovers/toolTip.js +402 -0
- data/{app/utils/logger.coffee → src/components/wrapper.js} +0 -0
- data/{app → src}/images/dante/media-loading-placeholder.png +0 -0
- data/{app → src}/images/site/dante-demo.png +0 -0
- data/{app → src}/images/site/dante-editor-logo.png +0 -0
- data/{app → src}/images/site/github-logo.png +0 -0
- data/src/index.js +9 -0
- data/{app → src}/model/index.js +0 -0
- data/src/style.js +3 -0
- data/{app → src}/styles/dante/_animations.scss +0 -0
- data/{app → src}/styles/dante/_caption.scss +0 -0
- data/{app → src}/styles/dante/_debug.scss +0 -0
- data/{app → src}/styles/dante/_fonts.scss +0 -0
- data/{app → src}/styles/dante/_graf.scss +0 -0
- data/{app → src}/styles/dante/_icons.scss +0 -0
- data/{app → src}/styles/dante/_media.scss +0 -0
- data/{app → src}/styles/dante/_menu.scss +0 -0
- data/{app → src}/styles/dante/_needsorder.scss +0 -0
- data/{app → src}/styles/dante/_popover.scss +0 -0
- data/{app → src}/styles/dante/_post.scss +0 -0
- data/{app → src}/styles/dante/_scaffold.scss +0 -0
- data/{app → src}/styles/dante/_tooltip.scss +0 -0
- data/{app → src}/styles/dante/_utilities.scss +0 -0
- data/{app → src}/styles/dante/_variables.scss +0 -0
- data/{app → src}/styles/dante/blame.scss +0 -0
- data/{app → src}/styles/dante.scss +0 -0
- data/{app → src}/styles/draft.css +0 -0
- data/src/styles/fonts/dante/dante.eot +0 -0
- data/src/styles/fonts/dante/dante.svg +18 -0
- data/src/styles/fonts/dante/dante.ttf +0 -0
- data/src/styles/fonts/dante/dante.woff +0 -0
- data/src/styles/fonts/dante/fontello.eot +0 -0
- data/src/styles/fonts/dante/fontello.svg +36 -0
- data/src/styles/fonts/dante/fontello.ttf +0 -0
- data/src/styles/fonts/dante/fontello.woff +0 -0
- data/src/utils/find_entities.js +17 -0
- data/src/utils/html2content.js +127 -0
- data/src/utils/save_content.js +80 -0
- data/{app → src}/utils/selection.js +0 -0
- data/tools/.eslintrc +9 -0
- data/tools/amd/README.md +7 -0
- data/tools/amd/bower.json +19 -0
- data/tools/amd/build.js +36 -0
- data/tools/build-cli.js +46 -0
- data/tools/build.js +30 -0
- data/tools/buildBabel.js +32 -0
- data/tools/constants.js +10 -0
- data/tools/dist/build.js +13 -0
- data/tools/docs/build.js +12 -0
- data/tools/es/build.js +27 -0
- data/tools/exec.js +50 -0
- data/tools/fs-utils.js +35 -0
- data/tools/lib/build.js +14 -0
- data/tools/promisify.js +14 -0
- data/webpack/base.config.js +89 -0
- data/webpack/docs.config.js +147 -0
- data/webpack/webpack.config.js +78 -0
- data/webpack.config-doc.js +5 -0
- data/webpack.config.js +3 -147
- data/yarn.lock +973 -718
- metadata +108 -64
- data/app/components/App.cjsx +0 -1083
- data/app/components/blocks/embed.cjsx +0 -109
- data/app/components/blocks/image.cjsx +0 -316
- data/app/components/blocks/placeholder.cjsx +0 -60
- data/app/components/blocks/video.cjsx +0 -75
- data/app/components/debug.cjsx +0 -96
- data/app/components/decorators/link.cjsx +0 -61
- data/app/components/popovers/addButton.cjsx +0 -247
- data/app/components/popovers/image.cjsx +0 -160
- data/app/components/popovers/link.cjsx +0 -87
- data/app/components/popovers/toolTip.cjsx +0 -326
- data/app/data/poc.js +0 -15
- data/app/demo.js +0 -7
- data/app/initialize.js +0 -4
- data/app/utils/find_entities.coffee +0 -20
- data/app/utils/html2content.coffee +0 -120
- data/app/utils/save_content.coffee +0 -63
- data/lib/dante2-editor/rails.rb +0 -16
Binary file
|
@@ -0,0 +1,17 @@
|
|
1
|
+
import { Entity } from 'draft-js'
|
2
|
+
|
3
|
+
//TODO: what the f*ck is happening here? ;-;
|
4
|
+
const findEntities = (entityType, instance, contentBlock, callback) => {
|
5
|
+
return contentBlock.findEntityRanges((function(_this) {
|
6
|
+
return function(character) {
|
7
|
+
var entityKey, opts, res
|
8
|
+
entityKey = character.getEntity()
|
9
|
+
return (res = entityKey !== null && Entity.get(entityKey).getType() === entityType, res ? (opts = {
|
10
|
+
showPopLinkOver: instance.showPopLinkOver,
|
11
|
+
hidePopLinkOver: instance.hidePopLinkOver
|
12
|
+
}, Entity.mergeData(entityKey, opts)) : void 0, res)
|
13
|
+
}
|
14
|
+
})(this), callback)
|
15
|
+
}
|
16
|
+
|
17
|
+
export default findEntities
|
@@ -0,0 +1,127 @@
|
|
1
|
+
import { ContentState, genKey, Entity, CharacterMetadata, ContentBlock, convertFromHTML, getSafeBodyFromHTML } from 'draft-js'
|
2
|
+
|
3
|
+
import { List, OrderedSet, Repeat, fromJS } from 'immutable'
|
4
|
+
|
5
|
+
|
6
|
+
// { compose
|
7
|
+
// } = require('underscore')
|
8
|
+
|
9
|
+
// underscore compose function
|
10
|
+
let compose = function() {
|
11
|
+
let args = arguments
|
12
|
+
let start = args.length - 1
|
13
|
+
return function() {
|
14
|
+
let i = start
|
15
|
+
let result = args[start].apply(this, arguments)
|
16
|
+
while (i--) {
|
17
|
+
result = args[i].call(this, result)
|
18
|
+
}
|
19
|
+
return result
|
20
|
+
}
|
21
|
+
}
|
22
|
+
|
23
|
+
// from https://gist.github.com/N1kto/6702e1c2d89a33a15a032c234fc4c34e
|
24
|
+
|
25
|
+
/*
|
26
|
+
* Helpers
|
27
|
+
*/
|
28
|
+
|
29
|
+
// Prepares img meta data object based on img attributes
|
30
|
+
let getBlockSpecForElement = imgElement=> {
|
31
|
+
return {
|
32
|
+
contentType: 'image',
|
33
|
+
imgSrc: imgElement.getAttribute('src')
|
34
|
+
}
|
35
|
+
}
|
36
|
+
|
37
|
+
// Wraps meta data in HTML element which is 'understandable' by Draft, I used <blockquote />.
|
38
|
+
let wrapBlockSpec = blockSpec=> {
|
39
|
+
if (blockSpec === null) {
|
40
|
+
return null
|
41
|
+
}
|
42
|
+
|
43
|
+
let tempEl = document.createElement('blockquote')
|
44
|
+
// stringify meta data and insert it as text content of temp HTML element. We will later extract
|
45
|
+
// and parse it.
|
46
|
+
tempEl.innerText = JSON.stringify(blockSpec)
|
47
|
+
return tempEl
|
48
|
+
}
|
49
|
+
|
50
|
+
// Replaces <img> element with our temp element
|
51
|
+
let replaceElement = (oldEl, newEl)=> {
|
52
|
+
if (!(newEl instanceof HTMLElement)) {
|
53
|
+
return
|
54
|
+
}
|
55
|
+
|
56
|
+
let upEl = getUpEl(oldEl)
|
57
|
+
//parentNode = oldEl.parentNode
|
58
|
+
//return parentNode.replaceChild(newEl, oldEl)
|
59
|
+
return upEl.parentNode.insertBefore(newEl, upEl)
|
60
|
+
}
|
61
|
+
|
62
|
+
var getUpEl = el=> {
|
63
|
+
let original_el = el
|
64
|
+
while (el.parentNode) {
|
65
|
+
if (el.parentNode.tagName !== 'BODY') {
|
66
|
+
el = el.parentNode
|
67
|
+
}
|
68
|
+
if (el.parentNode.tagName === 'BODY') { return el }
|
69
|
+
}
|
70
|
+
}
|
71
|
+
|
72
|
+
let elementToBlockSpecElement = compose(wrapBlockSpec, getBlockSpecForElement)
|
73
|
+
|
74
|
+
let imgReplacer = imgElement=> {
|
75
|
+
return replaceElement(imgElement, elementToBlockSpecElement(imgElement))
|
76
|
+
}
|
77
|
+
|
78
|
+
/*
|
79
|
+
* Main function
|
80
|
+
*/
|
81
|
+
|
82
|
+
// takes HTML string and returns DraftJS ContentState
|
83
|
+
let customHTML2Content = function(HTML, blockRn){
|
84
|
+
let tempDoc = new DOMParser().parseFromString(HTML, 'text/html')
|
85
|
+
// replace all <img /> with <blockquote /> elements
|
86
|
+
|
87
|
+
let a = tempDoc.querySelectorAll('img').forEach( item=> imgReplacer(item))
|
88
|
+
|
89
|
+
// use DraftJS converter to do initial conversion. I don't provide DOMBuilder and
|
90
|
+
// blockRenderMap arguments here since it should fall back to its default ones, which are fine
|
91
|
+
console.log(tempDoc.body.innerHTML)
|
92
|
+
let contentBlocks = convertFromHTML(tempDoc.body.innerHTML,
|
93
|
+
getSafeBodyFromHTML,
|
94
|
+
blockRn
|
95
|
+
)
|
96
|
+
|
97
|
+
// now replace <blockquote /> ContentBlocks with 'atomic' ones
|
98
|
+
contentBlocks = contentBlocks.map(function(block){
|
99
|
+
let newBlock
|
100
|
+
console.log("CHECK BLOCK", block.getType())
|
101
|
+
if (block.getType() !== 'blockquote') {
|
102
|
+
return block
|
103
|
+
}
|
104
|
+
|
105
|
+
let json = ""
|
106
|
+
try {
|
107
|
+
json = JSON.parse(block.getText())
|
108
|
+
} catch (error) {
|
109
|
+
return block
|
110
|
+
}
|
111
|
+
|
112
|
+
return newBlock = block.merge({
|
113
|
+
type: "image",
|
114
|
+
text: "",
|
115
|
+
data: {
|
116
|
+
url: json.imgSrc,
|
117
|
+
forceUpload: true
|
118
|
+
}
|
119
|
+
})
|
120
|
+
})
|
121
|
+
|
122
|
+
tempDoc = null
|
123
|
+
return ContentState.createFromBlockArray(contentBlocks)
|
124
|
+
}
|
125
|
+
|
126
|
+
|
127
|
+
export default customHTML2Content
|
@@ -0,0 +1,80 @@
|
|
1
|
+
import axios from "axios"
|
2
|
+
import Immutable from 'immutable'
|
3
|
+
|
4
|
+
class SaveBehavior {
|
5
|
+
constructor(options) {
|
6
|
+
this.getLocks = options.getLocks
|
7
|
+
this.config = options.config
|
8
|
+
this.editorContent = options.editorContent
|
9
|
+
this.editorState = options.editorState
|
10
|
+
}
|
11
|
+
|
12
|
+
handleStore(ev){
|
13
|
+
return this.store()
|
14
|
+
}
|
15
|
+
|
16
|
+
store(content){
|
17
|
+
if (!this.config.data_storage.url) { return }
|
18
|
+
if (this.getLocks() > 0) { return }
|
19
|
+
|
20
|
+
clearTimeout(this.timeout)
|
21
|
+
|
22
|
+
return this.timeout = setTimeout(() => {
|
23
|
+
return this.checkforStore(content)
|
24
|
+
}
|
25
|
+
, this.config.data_storage.interval)
|
26
|
+
}
|
27
|
+
|
28
|
+
getTextFromEditor(content){
|
29
|
+
return content.blocks.map(o=> {
|
30
|
+
return o.text
|
31
|
+
}
|
32
|
+
)
|
33
|
+
.join("\n")
|
34
|
+
}
|
35
|
+
|
36
|
+
getUrl() {
|
37
|
+
let { url } = this.config.data_storage
|
38
|
+
if (typeof(url) === "function") { return url() } else { return url }
|
39
|
+
}
|
40
|
+
|
41
|
+
getMethod() {
|
42
|
+
let { method } = this.config.data_storage
|
43
|
+
if (typeof(method) === "function") { return method() } else { return method }
|
44
|
+
}
|
45
|
+
|
46
|
+
|
47
|
+
checkforStore(content){
|
48
|
+
// ENTER DATA STORE
|
49
|
+
let isChanged = !Immutable.is(Immutable.fromJS(this.editorContent), Immutable.fromJS(content))
|
50
|
+
// console.log("CONTENT CHANGED:", isChanged)
|
51
|
+
|
52
|
+
if (!isChanged) { return }
|
53
|
+
|
54
|
+
if (this.config.xhr.before_handler) { this.config.xhr.before_handler() }
|
55
|
+
// console.log "SAVING TO: #{@getMethod()} #{@getUrl()}"
|
56
|
+
|
57
|
+
return axios({
|
58
|
+
method: this.getMethod(),
|
59
|
+
url: this.getUrl(),
|
60
|
+
data: {
|
61
|
+
editor_content: JSON.stringify(content),
|
62
|
+
text_content: this.getTextFromEditor(content)
|
63
|
+
}
|
64
|
+
})
|
65
|
+
.then(result=> {
|
66
|
+
// console.log "STORING CONTENT", result
|
67
|
+
if (this.config.data_storage.success_handler) { this.config.data_storage.success_handler(result) }
|
68
|
+
if (this.config.xhr.success_handler) { return this.config.xhr.success_handler(result) }
|
69
|
+
}
|
70
|
+
)
|
71
|
+
.catch(error=> {
|
72
|
+
// console.log("ERROR: got error saving content at #{@config.data_storage.url} - #{error}")
|
73
|
+
if (this.config.xhr.failure_handler) { return this.config.xhr.failure_handler(error) }
|
74
|
+
}
|
75
|
+
)
|
76
|
+
}
|
77
|
+
}
|
78
|
+
|
79
|
+
|
80
|
+
export default SaveBehavior
|
File without changes
|
data/tools/.eslintrc
ADDED
data/tools/amd/README.md
ADDED
@@ -0,0 +1,19 @@
|
|
1
|
+
{
|
2
|
+
"name": "<%= pkg.name %>",
|
3
|
+
"version": "<%= pkg.version %>",
|
4
|
+
"homepage": "<%= pkg.homepage %>",
|
5
|
+
"author": "<%= pkg.author %>",
|
6
|
+
"license": "<%= pkg.license %>",
|
7
|
+
"main": [
|
8
|
+
"Dante2.js"
|
9
|
+
],
|
10
|
+
"keywords": [
|
11
|
+
<%= pkg.keywords.map(keyword => `"${keyword}"`).join(',\n ') %>
|
12
|
+
],
|
13
|
+
"ignore": [
|
14
|
+
"**/.*"
|
15
|
+
],
|
16
|
+
"dependencies": {
|
17
|
+
"react": "<%= pkg.peerDependencies.react %>"
|
18
|
+
}
|
19
|
+
}
|
data/tools/amd/build.js
ADDED
@@ -0,0 +1,36 @@
|
|
1
|
+
import fsp from 'fs-promise';
|
2
|
+
import template from 'lodash/template';
|
3
|
+
import path from 'path';
|
4
|
+
|
5
|
+
import { repoRoot, bowerRoot } from '../constants';
|
6
|
+
import { exec } from '../exec';
|
7
|
+
import { copy } from '../fs-utils';
|
8
|
+
|
9
|
+
const packagePath = path.join(repoRoot, 'package.json');
|
10
|
+
const bowerTemplatePath = path.join(__dirname, 'bower.json');
|
11
|
+
const bowerJson = path.join(bowerRoot, 'bower.json');
|
12
|
+
|
13
|
+
const readme = path.join(__dirname, 'README.md');
|
14
|
+
|
15
|
+
function bowerConfig() {
|
16
|
+
return Promise.all([
|
17
|
+
fsp.readFile(packagePath)
|
18
|
+
.then(json => JSON.parse(json)),
|
19
|
+
fsp.readFile(bowerTemplatePath)
|
20
|
+
.then(templateString => template(templateString))
|
21
|
+
])
|
22
|
+
.then(([pkg, compiledTemplate]) => compiledTemplate({ pkg }))
|
23
|
+
.then(config => fsp.writeFile(bowerJson, config));
|
24
|
+
}
|
25
|
+
|
26
|
+
export default function BuildBower() {
|
27
|
+
console.log('Building: '.cyan + 'bower module'.green);
|
28
|
+
|
29
|
+
return exec(`rimraf ${bowerRoot}`)
|
30
|
+
.then(() => fsp.mkdirs(bowerRoot))
|
31
|
+
.then(() => Promise.all([
|
32
|
+
bowerConfig(),
|
33
|
+
copy(readme, bowerRoot)
|
34
|
+
]))
|
35
|
+
.then(() => console.log('Built: '.cyan + 'bower module'.green));
|
36
|
+
}
|
data/tools/build-cli.js
ADDED
@@ -0,0 +1,46 @@
|
|
1
|
+
/* eslint no-process-exit: 0 */
|
2
|
+
|
3
|
+
import 'colors';
|
4
|
+
import build from './build';
|
5
|
+
import docs from './docs/build';
|
6
|
+
import { setExecOptions } from './exec';
|
7
|
+
|
8
|
+
import yargs from 'yargs';
|
9
|
+
|
10
|
+
const argv = yargs
|
11
|
+
.help('h')
|
12
|
+
.option('docs-only', {
|
13
|
+
demand: false,
|
14
|
+
default: false
|
15
|
+
})
|
16
|
+
.option('verbose', {
|
17
|
+
demand: false,
|
18
|
+
default: false,
|
19
|
+
describe: 'Increased debug output'
|
20
|
+
})
|
21
|
+
.option('dev', {
|
22
|
+
demand: false,
|
23
|
+
default: false,
|
24
|
+
describe: 'Only used when supplied with the --docs-only flag'
|
25
|
+
})
|
26
|
+
.argv;
|
27
|
+
|
28
|
+
setExecOptions(argv);
|
29
|
+
|
30
|
+
let buildProcess;
|
31
|
+
|
32
|
+
if (argv.docsOnly) {
|
33
|
+
//buildProcess = docs(argv);
|
34
|
+
} else {
|
35
|
+
buildProcess = build(argv);
|
36
|
+
}
|
37
|
+
|
38
|
+
buildProcess
|
39
|
+
.catch(err => {
|
40
|
+
if (err.stack) {
|
41
|
+
console.error(err.stack.red);
|
42
|
+
} else {
|
43
|
+
console.error(err.toString().red);
|
44
|
+
}
|
45
|
+
process.exit(1);
|
46
|
+
});
|
data/tools/build.js
ADDED
@@ -0,0 +1,30 @@
|
|
1
|
+
import 'colors';
|
2
|
+
import bower from './amd/build';
|
3
|
+
import lib from './lib/build';
|
4
|
+
import es from './es/build';
|
5
|
+
import dist from './dist/build';
|
6
|
+
import docs from './docs/build';
|
7
|
+
import { copy } from './fs-utils';
|
8
|
+
import { distRoot, bowerRoot } from './constants';
|
9
|
+
import { exec } from './exec';
|
10
|
+
|
11
|
+
function forkAndBuildDocs({verbose}) {
|
12
|
+
console.log('Building: '.cyan + 'docs'.green);
|
13
|
+
|
14
|
+
const verboseOption = verbose ? '--verbose' : '';
|
15
|
+
console.log('SKIP '.red );
|
16
|
+
return exec(`npm run docs-build -- ${verboseOption}`)
|
17
|
+
// .then(() => console.log('Built: '.cyan + 'docs'.green));
|
18
|
+
}
|
19
|
+
|
20
|
+
export default function Build(options) {
|
21
|
+
return Promise.all([
|
22
|
+
lib(),
|
23
|
+
es(),
|
24
|
+
bower(),
|
25
|
+
dist(),
|
26
|
+
docs()
|
27
|
+
//,forkAndBuildDocs(options)
|
28
|
+
])
|
29
|
+
.then(() => copy(distRoot, bowerRoot));
|
30
|
+
}
|
data/tools/buildBabel.js
ADDED
@@ -0,0 +1,32 @@
|
|
1
|
+
import { transform } from 'babel-core';
|
2
|
+
import fs from 'fs';
|
3
|
+
import path from 'path';
|
4
|
+
import outputFileSync from 'output-file-sync';
|
5
|
+
|
6
|
+
function buildContent(content, filename, destination, babelOptions = {}) {
|
7
|
+
babelOptions.filename = filename;
|
8
|
+
const result = transform(content, babelOptions);
|
9
|
+
outputFileSync(destination, result.code, {encoding: 'utf8'});
|
10
|
+
}
|
11
|
+
|
12
|
+
function buildFile(filename, destination, babelOptions = {}) {
|
13
|
+
const content = fs.readFileSync(filename, {encoding: 'utf8'});
|
14
|
+
// We only have .js files that we need to build
|
15
|
+
if (path.extname(filename) === '.js') {
|
16
|
+
const outputPath = path.join(destination, path.basename(filename));
|
17
|
+
// console.log('%s => %s', filename, outputPath);
|
18
|
+
buildContent(content, filename, outputPath, babelOptions);
|
19
|
+
}
|
20
|
+
}
|
21
|
+
|
22
|
+
export default function buildBabel(folderPath, destination, babelOptions = {}, firstFolder = true) {
|
23
|
+
let stats = fs.statSync(folderPath);
|
24
|
+
|
25
|
+
if (stats.isFile()) {
|
26
|
+
buildFile(folderPath, destination, babelOptions);
|
27
|
+
} else if (stats.isDirectory()) {
|
28
|
+
let outputPath = firstFolder ? destination : path.join(destination, path.basename(folderPath));
|
29
|
+
let files = fs.readdirSync(folderPath).map(file => path.join(folderPath, file));
|
30
|
+
files.forEach(filename => buildBabel(filename, outputPath, babelOptions, false));
|
31
|
+
}
|
32
|
+
}
|
data/tools/constants.js
ADDED
@@ -0,0 +1,10 @@
|
|
1
|
+
import path from 'path';
|
2
|
+
|
3
|
+
export const repoRoot = path.resolve(__dirname, '../');
|
4
|
+
|
5
|
+
export const srcRoot = path.join(repoRoot, 'src/');
|
6
|
+
export const distRoot = path.join(repoRoot, 'dist/');
|
7
|
+
export const libRoot = path.join(repoRoot, 'lib/');
|
8
|
+
export const esRoot = path.join(repoRoot, 'es/');
|
9
|
+
export const bowerRoot = path.join(repoRoot, 'amd/');
|
10
|
+
export const docsRoot = path.join(repoRoot, 'docs/');
|
data/tools/dist/build.js
ADDED
@@ -0,0 +1,13 @@
|
|
1
|
+
import { exec } from '../exec';
|
2
|
+
import { distRoot } from '../constants';
|
3
|
+
|
4
|
+
export default function BuildDistributable() {
|
5
|
+
console.log('Building: '.cyan + 'distributable'.green);
|
6
|
+
|
7
|
+
return exec(`rimraf ${distRoot}`)
|
8
|
+
.then(() => Promise.all([
|
9
|
+
exec(`webpack --bail`),
|
10
|
+
exec(`webpack --bail -p`)
|
11
|
+
]))
|
12
|
+
.then(() => console.log('Built: '.cyan + 'distributable'.green));
|
13
|
+
}
|
data/tools/docs/build.js
ADDED
@@ -0,0 +1,12 @@
|
|
1
|
+
import { exec } from '../exec';
|
2
|
+
import { distRoot } from '../constants';
|
3
|
+
|
4
|
+
export default function BuildDistributable() {
|
5
|
+
console.log('Building: '.cyan + 'docs'.green);
|
6
|
+
|
7
|
+
return exec(`rimraf ${distRoot}`)
|
8
|
+
.then(() => Promise.all([
|
9
|
+
exec(`webpack --config ./webpack/docs.config.js --bail`)
|
10
|
+
]))
|
11
|
+
.then(() => console.log('Built: '.cyan + 'docs'.green));
|
12
|
+
}
|
data/tools/es/build.js
ADDED
@@ -0,0 +1,27 @@
|
|
1
|
+
import 'colors';
|
2
|
+
import { exec } from '../exec';
|
3
|
+
import fsp from 'fs-promise';
|
4
|
+
import { srcRoot, esRoot } from '../constants';
|
5
|
+
import buildBabel from '../buildBabel';
|
6
|
+
|
7
|
+
export default function BuildES() {
|
8
|
+
console.log('Building: '.cyan + 'es module'.green);
|
9
|
+
|
10
|
+
return exec(`rimraf ${esRoot}`)
|
11
|
+
.then(() => fsp.mkdirs(esRoot))
|
12
|
+
.then(() => buildBabel(srcRoot, esRoot, {
|
13
|
+
babelrc: false,
|
14
|
+
presets: [
|
15
|
+
['es2015', { loose: true, modules: false }],
|
16
|
+
'stage-1',
|
17
|
+
'react'
|
18
|
+
],
|
19
|
+
plugins: [
|
20
|
+
'dev-expression',
|
21
|
+
'transform-runtime',
|
22
|
+
'transform-es3-member-expression-literals',
|
23
|
+
'transform-es3-property-literals'
|
24
|
+
]
|
25
|
+
}))
|
26
|
+
.then(() => console.log('Built: '.cyan + 'es module'.green));
|
27
|
+
}
|
data/tools/exec.js
ADDED
@@ -0,0 +1,50 @@
|
|
1
|
+
import { exec as processExec } from 'child-process-promise';
|
2
|
+
import 'colors';
|
3
|
+
|
4
|
+
let executionOptions = {
|
5
|
+
dryRun: false,
|
6
|
+
verbose: false
|
7
|
+
};
|
8
|
+
|
9
|
+
function logWithPrefix(prefix, message) {
|
10
|
+
console.log(
|
11
|
+
message.toString().trim()
|
12
|
+
.split('\n')
|
13
|
+
.map((line) => `${prefix.grey} ${line}`)
|
14
|
+
.join('\n')
|
15
|
+
);
|
16
|
+
}
|
17
|
+
|
18
|
+
export function exec(command, options = {}) {
|
19
|
+
let proc = processExec(command, options);
|
20
|
+
if (!executionOptions.verbose) {
|
21
|
+
return proc;
|
22
|
+
}
|
23
|
+
|
24
|
+
let title = options.title || command;
|
25
|
+
let output = (data, type) => logWithPrefix(`[${title}] ${type}:`, data);
|
26
|
+
|
27
|
+
return proc.progress(({stdout, stderr}) => {
|
28
|
+
stdout.on('data', data => output(data, 'stdout'));
|
29
|
+
stderr.on('data', data => output(data, 'stderr'));
|
30
|
+
})
|
31
|
+
.then(result => {
|
32
|
+
logWithPrefix(`[${title}]`, 'Complete'.cyan);
|
33
|
+
return result;
|
34
|
+
});
|
35
|
+
}
|
36
|
+
|
37
|
+
export function safeExec(command, options = {}) {
|
38
|
+
let title = options.title || command;
|
39
|
+
|
40
|
+
if (executionOptions.dryRun) {
|
41
|
+
logWithPrefix(`[${title}]`.grey, 'DRY RUN'.magenta);
|
42
|
+
return Promise.resolve();
|
43
|
+
}
|
44
|
+
|
45
|
+
return exec(command, options);
|
46
|
+
}
|
47
|
+
|
48
|
+
export function setExecOptions(options) {
|
49
|
+
executionOptions = { ...executionOptions, ...options };
|
50
|
+
}
|
data/tools/fs-utils.js
ADDED
@@ -0,0 +1,35 @@
|
|
1
|
+
import path from 'path';
|
2
|
+
import fsp from 'fs-promise';
|
3
|
+
import fse from 'fs-extra';
|
4
|
+
|
5
|
+
export function copy(src, dest, options) {
|
6
|
+
options = options || {};
|
7
|
+
|
8
|
+
return Promise.all([
|
9
|
+
fsp.stat(src),
|
10
|
+
fsp.exists(dest)
|
11
|
+
.then(exists => {
|
12
|
+
if (!exists) {
|
13
|
+
return false;
|
14
|
+
}
|
15
|
+
|
16
|
+
return fsp.stat(dest);
|
17
|
+
})
|
18
|
+
])
|
19
|
+
.then(([srcStat, destStat]) => {
|
20
|
+
if (srcStat.isFile() && destStat && destStat.isDirectory()) {
|
21
|
+
let filename = path.basename(src);
|
22
|
+
dest = path.join(dest, filename);
|
23
|
+
}
|
24
|
+
|
25
|
+
return new Promise((resolve, reject) => {
|
26
|
+
fse.copy(src, dest, options, err => {
|
27
|
+
if (err) {
|
28
|
+
reject(err);
|
29
|
+
}
|
30
|
+
|
31
|
+
resolve();
|
32
|
+
});
|
33
|
+
});
|
34
|
+
});
|
35
|
+
}
|
data/tools/lib/build.js
ADDED
@@ -0,0 +1,14 @@
|
|
1
|
+
import 'colors';
|
2
|
+
import { exec } from '../exec';
|
3
|
+
import fsp from 'fs-promise';
|
4
|
+
import { srcRoot, libRoot } from '../constants';
|
5
|
+
import buildBabel from '../buildBabel';
|
6
|
+
|
7
|
+
export default function BuildCommonJs() {
|
8
|
+
console.log('Building: '.cyan + 'npm module'.green);
|
9
|
+
|
10
|
+
return exec(`rimraf ${libRoot}`)
|
11
|
+
.then(() => fsp.mkdirs(libRoot))
|
12
|
+
.then(() => buildBabel(srcRoot, libRoot))
|
13
|
+
.then(() => console.log('Built: '.cyan + 'npm module'.green));
|
14
|
+
}
|
data/tools/promisify.js
ADDED
@@ -0,0 +1,14 @@
|
|
1
|
+
export default function promisify(fn) {
|
2
|
+
return (...args) => {
|
3
|
+
return new Promise((resolve, reject) => {
|
4
|
+
function finish(err, result) {
|
5
|
+
if (err) {
|
6
|
+
return reject(err);
|
7
|
+
}
|
8
|
+
resolve(result);
|
9
|
+
}
|
10
|
+
|
11
|
+
fn.apply(null, args.concat(finish));
|
12
|
+
});
|
13
|
+
};
|
14
|
+
}
|
@@ -0,0 +1,89 @@
|
|
1
|
+
import webpack from 'webpack';
|
2
|
+
import yargs from 'yargs';
|
3
|
+
|
4
|
+
var path = require('path');
|
5
|
+
|
6
|
+
var ExtractTextPlugin = require("extract-text-webpack-plugin");
|
7
|
+
var HtmlWebpackPlugin = require('html-webpack-plugin');
|
8
|
+
var CommonsChunkPlugin = require("webpack/lib/optimize/CommonsChunkPlugin");
|
9
|
+
|
10
|
+
|
11
|
+
export const options = yargs
|
12
|
+
.alias('p', 'optimize-minimize')
|
13
|
+
.alias('d', 'debug')
|
14
|
+
.option('port', {
|
15
|
+
default: '8080',
|
16
|
+
type: 'string'
|
17
|
+
})
|
18
|
+
.argv;
|
19
|
+
|
20
|
+
export const jsLoader = 'babel?cacheDirectory';
|
21
|
+
|
22
|
+
const baseConfig = {
|
23
|
+
entry: undefined,
|
24
|
+
|
25
|
+
output: undefined,
|
26
|
+
|
27
|
+
externals: undefined,
|
28
|
+
|
29
|
+
resolve: {
|
30
|
+
root: path.resolve('./src'),
|
31
|
+
extensions: ['', '.js', '.jsx', '.es6', '.css', '.scss']
|
32
|
+
},
|
33
|
+
|
34
|
+
module: {
|
35
|
+
loaders: [
|
36
|
+
{ test: /\.js/, loader: jsLoader, exclude: /node_modules/ },
|
37
|
+
{
|
38
|
+
test: /\.css$/,
|
39
|
+
loader: ExtractTextPlugin.extract("style-loader", "css-loader")
|
40
|
+
},
|
41
|
+
{
|
42
|
+
test: /\.scss$/,
|
43
|
+
loader: ExtractTextPlugin.extract("style-loader", "css-loader!sass-loader")
|
44
|
+
},
|
45
|
+
|
46
|
+
{ test: path.resolve("./src/components/dante_editor.js"),
|
47
|
+
loaders: ["expose?DanteEditor", "babel-loader?presets[]=es2015"]},
|
48
|
+
{ test: path.resolve("./src/components/dante.js"),
|
49
|
+
loaders: ["expose?Dante", "babel-loader?presets[]=es2015"]},
|
50
|
+
|
51
|
+
{
|
52
|
+
test: /\.(eot|svg|ttf|woff|woff2)$/,
|
53
|
+
loader: 'file?name=fonts/[name].[ext]',
|
54
|
+
exclude: /node_modules/
|
55
|
+
},
|
56
|
+
{
|
57
|
+
test: /\.(png|jpg)$/,
|
58
|
+
loader:'file?limit=1024&name=images/[name].[ext]'
|
59
|
+
}
|
60
|
+
|
61
|
+
]
|
62
|
+
},
|
63
|
+
|
64
|
+
plugins: [
|
65
|
+
|
66
|
+
new HtmlWebpackPlugin({
|
67
|
+
title: 'Dante Demo',
|
68
|
+
template: 'demo/assets/index.html',
|
69
|
+
scripts: [
|
70
|
+
{
|
71
|
+
src: '/initialize.js',
|
72
|
+
type: 'module'
|
73
|
+
}
|
74
|
+
],
|
75
|
+
}),
|
76
|
+
|
77
|
+
new webpack.DefinePlugin({
|
78
|
+
'process.env': {
|
79
|
+
NODE_ENV: JSON.stringify(options.optimizeMinimize ? 'production' : 'development')
|
80
|
+
}
|
81
|
+
})
|
82
|
+
]
|
83
|
+
};
|
84
|
+
|
85
|
+
if (options.optimizeMinimize) {
|
86
|
+
baseConfig.devtool = 'source-map';
|
87
|
+
}
|
88
|
+
|
89
|
+
export default baseConfig;
|