Repository: nuxt/create-nuxt-app
Pull request #160 (2018-12-30 06:26:09)

docs: Happy New Year! :gift:
Happy New Year 2019! :christmas_tree: 


Patch:
diff --git a/README.md b/README.md
index e2c5c1f..ea07a19 100644
--- a/README.md
+++ b/README.md
@@ -45,9 +45,13 @@ yarn create nuxt-app <my-project>
     - [Ant Design Vue](https://github.com/vueComponent/ant-design-vue)
     - [Buefy](https://buefy.github.io)
     - [iView](https://www.iviewui.com/)
-3. Add [axios module](https://github.com/nuxt-community/axios-module) to make HTTP request easily into your application.
-4. Add [ESLint](https://eslint.org/) to Lint your code on save.
-5. Add [Prettier](https://prettier.io/) to prettify your code on save.
+3. Choose your favorite test framework:
+    - None
+    - [Jest](https://github.com/facebook/jest)
+    - [AVA](https://github.com/avajs/ava)
+4. Add [axios module](https://github.com/nuxt-community/axios-module) to make HTTP request easily into your application.
+5. Add [ESLint](https://eslint.org/) to Lint your code on save.
+6. Add [Prettier](https://prettier.io/) to prettify your code on save.
 
 ## Optional
 
diff --git a/sao.js b/sao.js
index 61aafa5..4cc4beb 100644
--- a/sao.js
+++ b/sao.js
@@ -59,6 +59,16 @@ module.exports = {
       ],
       default: 'none'
     },
+    test: {
+      message: 'Use a custom test framework',
+      type: 'list',
+      choices: [
+        'none',
+        'jest',
+        'ava'
+      ],
+      default: 'none'
+    },
     mode: {
       message: 'Choose rendering mode',
       type: 'list',
@@ -117,6 +127,8 @@ module.exports = {
     'frameworks/tailwind/**': 'ui === "tailwind"',
     'frameworks/buefy/**': 'ui === "buefy"',
     'frameworks/iview/**': 'ui === "iview"',
+    'frameworks/jest/**': 'test === "jest"',
+    'frameworks/ava/**': 'test === "ava"',
     '_.eslintrc.js': 'eslint === "yes"',
     '.prettierrc': 'prettier === "yes"'
   },
@@ -145,6 +157,7 @@ module.exports = {
       move('nuxt', nuxtDir),
       moveFramework(answers.server),
       moveFramework(answers.ui, nuxtDir),
+      moveFramework(answers.test, nuxtDir),
       answers.server === 'adonis'
         ? {
             'server/index-*.js': 'server.js',
@@ -182,6 +195,12 @@ module.exports = {
     cd()
     console.log(`\t ${meta.answers.pm} run build`)
     console.log(`\t ${meta.answers.pm} start`)
+
+    if (meta.answers.test !== 'none') {
+      console.log(chalk.bold(`\n  To test:\n`))
+      cd()
+      console.log(`\t ${meta.answers.pm} run test`)
+    }
     console.log()
   }
 }
diff --git a/template/_package.json b/template/_package.json
index f2cd019..0f5e764 100644
--- a/template/_package.json
+++ b/template/_package.json
@@ -14,7 +14,8 @@
     "start": "<% if (server === 'none') { %>nuxt start<% } else { %>cross-env NODE_ENV=production node server/index.js<% } %>",
     "generate": "nuxt generate"<% } %><% if (eslint === 'yes') { %>,
     "lint": "eslint --ext .js,.vue --ignore-path .gitignore .",
-    "precommit": "npm run lint"<% } %>
+    "precommit": "npm run lint"<% } %><% if (test !== 'none') { %>,
+    "test": "<%= test %>"<% } %>
   },
   "dependencies": {
     "cross-env": "^5.2.0"<% if (edge) { %>,
@@ -67,6 +68,16 @@
     "autoprefixer": "^8.6.4",
     "tailwindcss": "^0.7.0"<% } else if (ui === 'vuetify') { %>,
     "stylus": "^0.54.5",
-    "stylus-loader": "^3.0.2"<% } %>
+    "stylus-loader": "^3.0.2"<% } %><% if (test !== 'none') { %>,
+    "@vue/test-utils": "^1.0.0-beta.27"<% } %><% if (test === 'jest') { %>,
+    "babel-core": "7.0.0-bridge.0",
+    "babel-jest": "^23.6.0",
+    "jest": "^23.6.0",
+    "vue-jest": "^3.0.2"<% } %><% if (test === 'ava') { %>,
+    "ava": "^1.0.1",
+    "browser-env": "^3.2.5",
+    "require-extension-hooks": "^0.3.3",
+    "require-extension-hooks-babel": "^0.1.1",
+    "require-extension-hooks-vue": "^2.0.0"<% } %>
   }
 }
diff --git a/template/frameworks/ava/ava.config.js b/template/frameworks/ava/ava.config.js
new file mode 100644
index 0000000..f754e39
--- /dev/null
+++ b/template/frameworks/ava/ava.config.js
@@ -0,0 +1,5 @@
+export default {
+  require: [
+    "./test/helpers/setup.js"
+  ]
+}
diff --git a/template/frameworks/jest/.babelrc b/template/frameworks/jest/.babelrc
new file mode 100644
index 0000000..c495b7a
--- /dev/null
+++ b/template/frameworks/jest/.babelrc
@@ -0,0 +1,17 @@
+{
+  "env": {
+    "test": {
+      "presets": [
+        [
+          "@babel/preset-env",
+          {
+            "targets": {
+              "node": "current"
+            }
+          }
+        ],
+        "@nuxt/babel-preset-app"
+      ]
+    }
+  }
+}
diff --git a/template/frameworks/jest/jest.config.js b/template/frameworks/jest/jest.config.js
new file mode 100644
index 0000000..304dd96
--- /dev/null
+++ b/template/frameworks/jest/jest.config.js
@@ -0,0 +1,12 @@
+module.exports = {
+  moduleNameMapper: {
+    '^@/(.*)$': '<rootDir>/$1',
+    '^~/(.*)$': '<rootDir>/$1',
+    '^vue$': 'vue/dist/vue.common.js'
+  },
+  moduleFileExtensions: ['js', 'vue', 'json'],
+  transform: {
+    '^.+\\.js$': 'babel-jest',
+    '.*\\.(vue)$': 'vue-jest',
+  }
+}
diff --git a/template/frameworks/vuetify/layouts/default.vue b/template/frameworks/vuetify/layouts/default.vue
index ffaeea2..6ffb004 100644
--- a/template/frameworks/vuetify/layouts/default.vue
+++ b/template/frameworks/vuetify/layouts/default.vue
@@ -80,7 +80,7 @@
       :fixed="fixed"
       app
     >
-      <span>&copy; 2018</span>
+      <span>&copy; 2019</span>
     </v-footer>
   </v-app>
 </template>


Test patch:
diff --git a/template/frameworks/ava/test/helpers/setup.js b/template/frameworks/ava/test/helpers/setup.js
new file mode 100644
index 0000000..4b651f9
--- /dev/null
+++ b/template/frameworks/ava/test/helpers/setup.js
@@ -0,0 +1,8 @@
+require('browser-env')()
+const hooks = require('require-extension-hooks')
+const Vue = require('vue')
+
+Vue.config.productionTip = false
+
+hooks('vue').plugin('vue').push();
+hooks(['vue', 'js']).plugin('babel').push();
diff --git a/template/frameworks/ava/test/specs/Logo.spec.js b/template/frameworks/ava/test/specs/Logo.spec.js
new file mode 100644
index 0000000..f92102e
--- /dev/null
+++ b/template/frameworks/ava/test/specs/Logo.spec.js
@@ -0,0 +1,8 @@
+import { mount } from '@vue/test-utils'
+import test from 'ava'
+import Logo from '../../components/Logo.vue'
+
+test('is a Vue instance', t => {
+  const wrapper = mount(Logo)
+  t.is(wrapper.isVueInstance(), true)
+})
diff --git a/template/frameworks/jest/test/Logo.spec.js b/template/frameworks/jest/test/Logo.spec.js
new file mode 100644
index 0000000..1628640
--- /dev/null
+++ b/template/frameworks/jest/test/Logo.spec.js
@@ -0,0 +1,9 @@
+import { mount } from '@vue/test-utils'
+import Logo from '@/components/Logo.vue'
+
+describe('Logo', () => {
+  test('is a Vue instance', () => {
+    const wrapper = mount(Logo)
+    expect(wrapper.isVueInstance()).toBeTruthy()
+  })
+})
diff --git a/test/index.test.js b/test/index.test.js
index 39ded87..5a827c2 100644
--- a/test/index.test.js
+++ b/test/index.test.js
@@ -61,6 +61,18 @@ test('use axios', async t => {
   })
 })
 
+test('use jest', async t => {
+  await verifyPkg(t, {
+    test: 'jest'
+  })
+})
+
+test('use ava', async t => {
+  await verifyPkg(t, {
+    test: 'ava'
+  })
+})
+
 test('use eslint', async t => {
   await verifyPkg(t, {
     eslint: 'yes'
diff --git a/test/snapshots/index.test.js.md b/test/snapshots/index.test.js.md
index e81545b..a9cec75 100644
--- a/test/snapshots/index.test.js.md
+++ b/test/snapshots/index.test.js.md
@@ -467,4 +467,109 @@ Generated by [AVA](https://ava.li).
         generate: 'nuxt generate',
         start: 'nuxt start',
       },
-    }
+    
+
+## use jest
+
+> Generated files
+
+    [
+      '.babelrc',
+      '.editorconfig',
+      '.gitignore',
+      'README.md',
+      'assets/README.md',
+      'components/Logo.vue',
+      'components/README.md',
+      'jest.config.js',
+      'layouts/README.md',
+      'layouts/default.vue',
+      'middleware/README.md',
+      'nuxt.config.js',
+      'package.json',
+      'pages/README.md',
+      'pages/index.vue',
+      'plugins/README.md',
+      'static/README.md',
+      'static/favicon.ico',
+      'store/README.md',
+      'test/Logo.spec.js',
+    ]
+
+> package.json
+
+    {
+      dependencies: {
+        'cross-env': '^5.2.0',
+        nuxt: '^2.3.4',
+      },
+      devDependencies: {
+        '@vue/test-utils': '^1.0.0-beta.27',
+        'babel-core': '7.0.0-bridge.0',
+        'babel-jest': '^23.6.0',
+        jest: '^23.6.0',
+        nodemon: '^1.18.9',
+        'vue-jest': '^3.0.2',
+      },
+      private: true,
+      scripts: {
+        build: 'nuxt build',
+        dev: 'nuxt',
+        generate: 'nuxt generate',
+        start: 'nuxt start',
+        test: 'jest',
+      },
+    
+
+## use ava
+
+> Generated files
+
+    [
+      '.editorconfig',
+      '.gitignore',
+      'README.md',
+      'assets/README.md',
+      'ava.config.js',
+      'components/Logo.vue',
+      'components/README.md',
+      'layouts/README.md',
+      'layouts/default.vue',
+      'middleware/README.md',
+      'nuxt.config.js',
+      'package.json',
+      'pages/README.md',
+      'pages/index.vue',
+      'plugins/README.md',
+      'static/README.md',
+      'static/favicon.ico',
+      'store/README.md',
+      'test/helpers/setup.js',
+      'test/specs/Logo.spec.js',
+    ]
+
+> package.json
+
+    {
+      dependencies: {
+        'cross-env': '^5.2.0',
+        nuxt: '^2.3.4',
+      },
+      devDependencies: {
+        '@vue/test-utils': '^1.0.0-beta.27',
+        ava: '^1.0.1',
+        'browser-env': '^3.2.5',
+        nodemon: '^1.18.9',
+        'require-extension-hooks': '^0.3.3',
+        'require-extension-hooks-babel': '^0.1.1',
+        'require-extension-hooks-vue': '^2.0.0',
+      },
+      private: true,
+      scripts: {
+        build: 'nuxt build',
+        dev: 'nuxt',
+        generate: 'nuxt generate',
+        start: 'nuxt start',
+        test: 'ava',
+      },
+    }
\ No newline at end of file