走在前端的大道上javascript
新建目錄 ss 和 test.js 文件:css
mkdir ss cd ss touch test.js
初始化目錄生成 package.jsonhtml
npm init
npm set
用來設置項目初始化時默認值前端
$ npm set init-author-name 'your name' $ npm set init-author-email 'your email' $ npm set init-author-url 'your name' $ npm set init-license 'MIT'
首先nodejs默認已經安裝vue
1.1 若是你的電腦是沒有安裝過vue-cli
,那麼須要全局安裝執行npm install vue-cli -g
,用vue -V
查看版本,用vue list
查看可選工具java
1.2 執行vue init webpack vuedemo3
在當前目錄下建立vuedemo3的項目
安裝選項能夠參照下圖node
而後就能夠在目錄中看到生成vuedemo3文件夾webpack
1.3 切換到vuedemo3文件夾
執行npm install
,就下載了項目所須要的包依賴ios
new Vue({ el:'#app', router, template:<App/>, components:{App} }) 或 new Vue({ router, template:<App/>, components:{App} }).$mount("#app");
new Vue({ router, render: h=>h(App) }).$mount("#app"); 或 new Vue({ router, render: function(h){ return h(App); ) }).$mount("#app");
在子組件<hello>裏git
<slot name='world'></slot>
父組件使用
<hello> <span slot='world'> .... </span> </hello>
在項目中須要使用vue-resource
來與後臺進行數據交互,項目前期使用本地json數據來模仿後臺獲取數據的流程
說明:查看版本vue -V
操做方法:
a、項目結構:本地的json文件放在最外層和index.html同級,叫作db.json。
b、在build的dev-server.js進行加入代碼,位置如截圖:
var apiServer = express() var bodyParser = require('body-parser') apiServer.use(bodyParser.urlencoded({ extended: true })) apiServer.use(bodyParser.json()) var apiRouter = express.Router() var fs = require('fs') apiRouter.route('/:apiName') .all(function (req, res) { fs.readFile('./db.json', 'utf8', function (err, data) { if (err) throw err var data = JSON.parse(data) if (data[req.params.apiName]) { res.json(data[req.params.apiName]) } else { res.send('no such api name') } }) }) apiServer.use('/api', apiRouter); apiServer.listen(port + 1, function (err) { if (err) { console.log(err) return } console.log('Listening at http://localhost:' + (port + 1) + '\n') })
在瀏覽器中查看(我安裝了chrome遊覽器插件‘jsonView jsonViewer json formatter’,因此頁面上的格式是美化過的)
vue使用element-ui的el-input監聽不了回車事件,固然其餘組件也有不能監聽原生事件的
<el-input v-model="taskSeachText" @keyup.enter="handleClick"></el-input>
須要在事件後面加上.native
<el-input v-model="taskSeachText" @keyup.enter.native="handleClick"></el-input>
總結:寫在一個封裝好的組件上,有些標籤的原生事件要.native 修飾符才能生效 #vue給組件綁定原生事件
咱們平時本地前端開發環境dev地址大可能是 localhost:8080,然後臺服務器的訪問地址就有不少種狀況了,好比 127.0.0.1:8889,當前端與後臺進行數據交互時,天然就出現跨域問題(後臺服務沒作處理狀況下)。
如今經過在前端修改 vue-cli 的配置可解決:
vue-cli中的 client/config/index.js 下配置 dev選項的 {proxyTable}:
proxyTable: { // proxy all requests starting with /api to jsonplaceholder '/api': { target: 'http://127.0.0.1:8889/api', changeOrigin: true, onProxyReq (proxyReq, req, res) { } } }
實際上這是由於腳手架使用了中間件 http-proxy-middleware
源地址 | 轉發地址 |
---|---|
localhost:8080/api | api.example.com/api |
localhost:8080/api/notifications | api.example.com/api/notifications |
若是咱們要去掉 api.example.com的api路徑?
設置 pathRewrite
proxyTable: { '/api': { target: 'http://api.example.com', changeOrigin: true, pathRewrite: '^/api' : '', onProxyReq (proxyReq, req, res) { } } }
源地址 | 轉發地址 |
---|---|
localhost:8080/api | api.example.com |
localhost:8080/api/notifications | api.example.com/notifications |
代理的好處 | 代理的問題 |
---|---|
解決開發時跨域問題 | 代碼須要設置環境變量,prod環境下不存在 http-proxy-middleware 中間件 |
新建 ajax.js
import axios from 'axios' import store from '../store' // 超時設置 const http = axios.create({ timeout: 5000, baseURL: process.env.API_URL }) 或 // axios.defaults.baseURL = 'https://api.github.com'; // http request 攔截器 // 每次請求都爲http頭增長Authorization字段,其內容爲token http.interceptors.request.use( config => { if (store.state.user.token) { config.headers.Authorization = `token ${store.state.user.token}`; } return config }, err => { return Promise.reject(err) } ); export default http
在入口文件 main.js 引入 ajax.js,並將其掛在到 Vue 全局方法下,即註冊到Vue原型上。這樣在.vue文件中直接使用this.$axios便可。固然你也能夠在每一個須要用到axios的文件中單獨引入。
import axios from './ajax' ... Vue.prototype.$axios = axios
*.vue
methods: { // 請求到數據並賦值給data裏聲明的變量 getData () { this.$axios.get('../../static/data/index.json').then((response) => { this.data = response.data }, (response) => { // error }) } }
一些經常使用的庫也能夠掛載到 Vue 的原型上,避免在每一個.vue單頁面頻繁import引入
非父子間的組件通訊官方的叫法 global bus。
// one.vue <template> <div> 這是one組件 <button @click="commit">給two組件發送信息</button> <p> {{ message }}</p> </div> </template> <script type="text/javascript"> import { bus } from './bus' export default { name: 'one', data () { return { message: '', } }, methods:{ commit () { bus.$emit('sendMsg',{ msg: '這條信息來自於one' }) } }, mounted () { bus.$on('backMsg', (data) => { this.message = data.msg; }) } }
// two.vue <template> <div @click="commit"> <p>這是two組件<button @click="commit">給one組件發送信息</button></p> <p>{{ message }}</p> </div> </template> <script type="text/javascript"> import { bus } from './bus' export default { name: 'two', data () { return { message: '' } }, methods:{ commit () { bus.$emit('backMsg',{ msg: '這條信息來自於two' }) } }, mounted () { bus.$on('sendMsg', (data) => { this.message = data.msg; }) } } </script>
最關鍵的bus,倒是最簡單的
// bus.vue <script> import Vue from 'vue' export default { bus: new Vue(), } </script>
routes:[ { path:'/cart', name:'cart' component:Cart }, { path:'/goods/:goodId/post/:name', name:'goods' component:goodsList } ] html: <span>{{$route.params.goodId}}</span> <span>{{$route.params.name}}</span>
routes:[ { path:'/goods', name:'goods' component:goodsList, children:[ { path:'title', // 這裏title不能加 / name:'title', compoent: Title }, { path:'img', name:'img', compoent: Image } ] } ] html: <router-link to="/goods/title">顯示標題</router-link> <router-link to="/goods/img">顯示圖片</router-link> <router-view></router-view>
備註:
<router-view></router-view> 標籤是盛放一級路由的 <router-link to="/goods/title"></router-link> 是路由跳轉
$router.push("name") // name=/title $router.push({path:"name"}) $router.push({path:"name?goodId=123"}) 或者 $router.push({path:"name",query:{goodId:123}}) $router.go(1)
html獲取參數 <span>{{$route.query.goodId}}</span>
備註:
獲取頁面跳轉(js $router.push("name") )的參數 $route.query
獲取路由的參數$route.params
命名的路由
<router-link :to="{name:'cart'}"></router-link> <router-link :to="{name:'goods',params:{goodId:123}}"></router-link>
命名的視圖
<router-view></router-view> <router-view name="title"></router-view> <router-view name="img"></router-view> routes:[ { path:'/goods', name:'goods' components:{ default:GoodsList, title:Title, img:Image } },{ path:'/cart', name:'cart' component:Cart }]
vue-Resource 和 axios區別:resource是掛載到vue實例裏面的
,axios是暴露了axios全局變量;axios的失敗回調經過catch捕獲
公用地址配置
http:{ //和methods 一級(並列) root: "http://" }
攔截器interceptors
munted:function(){ Vue.http.interceptors.push(function(request,next){ console.log("request init") next(function(response){ console.log("response init") return response }) }) }, methods:{ }
REST風格,7種API
methods: //同Vue.http.get this.$http.get('package.json',{ //http://www.imooc.com/course/AjaxCourseMembers?ids=796 params:{ userId:"101" }, headers:{ token:"abcd" } }).then(res => { this.msg = res.data; },error =>{ this.msg = error })
methods: this.$http.jsonp('http://www.imooc.com/course/AjaxCourseMembers?ids=796',{ this.msg = res.data; })
methods: this.$http.post('package.json',{ userId:"102" },{ headers:{ access_token:"abc" } }).then(res => { this.msg = res.data; },error =>{ this.msg = error })
methods: http:function(){ this.$http({ url:'package.json', methods:'GET', params:{ userId:'103' }, header:{ token:'123' }, timeout:50, before:function(){ console.log("before init") } }).then(function(res){ this.msg = res.data }) }
vue-Resource 和 axios區別:resource是掛載到vue實例裏面的
,axios是暴露了axios全局變量;axios的失敗回調經過catch捕獲
公用地址配置
axios.defaults.baseURL = 'https://112...Server'
攔截器interceptors
munted:function(){ axios.interceptors.request.use(function(request){ console.log("request init") return request }) axios.interceptors.response.use(function(response){ console.log("request init") return response }) }, methods:{ }
axios.get('package.json',{ //http://www.imooc.com/course/AjaxCourseMembers?ids=796 params:{ userId:"999" }, headers:{ token:"jack" } }).then(res => { this.msg = res.data; }).catch(error =>{ console.log('error init') })
axios.post('package.json',{ //http://www.imooc.com/course/AjaxCourseMembers?ids=796 userId:"888" },{ headers:{ token:"tom" } }).then(res => { this.msg = res.data; }).catch(error =>{ console.log('error init') })
methods: http:function(){ axios({ url:'package.json', methods:'post', params:{ // get方式傳參 userId:'111' }, data:{ // post方式傳參 userId:'666' }, header:{ token:'http-test' } }).then(function(res){ this.msg = res.data }) }
同時須要stylus-loader
1.在項目根目錄下安裝
cnpm install --save js-base64
2.在項目文件中引入
let Base64 = require('js-base64').Base64;
3.在項目文件中使用
Base64.encode('dankogai'); // ZGFua29nYWk= Base64.encode('小飼弾'); // 5bCP6aO85by+ Base64.encodeURI('小飼弾'); // 5bCP6aO85by- Base64.decode('ZGFua29nYWk='); // dankogai Base64.decode('5bCP6aO85by+'); // 小飼弾 // note .decodeURI() is unnecessary since it accepts both flavors Base64.decode('5bCP6aO85by-'); // 小飼弾
1.在項目根目錄下安裝
cnpm install --save js-md5
2.在項目文件中引入
import md5 from 'js-md5';
3.在項目文件中使用
md5(''); // d41d8cd98f00b204e9800998ecf8427e md5('The quick brown fox jumps over the lazy dog'); // 9e107d9d372bb6826bd81d3542a419d6 md5('The quick brown fox jumps over the lazy dog.'); // e4d909c290d0fb1ca068ffaddf22cbd0 // It also supports UTF-8 encoding md5('中文'); // a7bac2239fcdcb3a067903d8077c4a07 // It also supports byte `Array`, `Uint8Array`, `ArrayBuffer` md5([]); // d41d8cd98f00b204e9800998ecf8427e md5(new Uint8Array([])); // d41d8cd98f00b204e9800998ecf8427e // Different output md5(''); // d41d8cd98f00b204e9800998ecf8427e md5.hex(''); // d41d8cd98f00b204e9800998ecf8427e md5.array(''); // [212, 29, 140, 217, 143, 0, 178, 4, 233, 128, 9, 152, 236, 248, 66, 126] md5.digest(''); // [212, 29, 140, 217, 143, 0, 178, 4, 233, 128, 9, 152, 236, 248, 66, 126] md5.arrayBuffer(''); // ArrayBuffer md5.buffer(''); // ArrayBuffer, deprecated, This maybe confuse with Buffer in node.js. Please use arrayBuffer instead.
本節參考文章:vue中使用base64和md5
解決本地和服務器上資源url解析的問題
問題描述:
1.在img中的圖片是徹底正確的, 但css中background-image: url()
的圖片怎麼都找不到.
2.最尷尬的是: 在npm run dev的時候一切正常
解決方法:
在 config/index.js 中修改 assetsPublicPath 爲 ./ 在 build/utils.js 中的 ExtractTextPlugin.extract 傳入參數 publicPath: '../../'
axios
的 post 請求後臺接受不到!axios默認是 json 格式提交,確認後臺是否作了對應的支持;
如果只能接受傳統的表單序列化,就須要本身寫一個轉義的方法...
固然還有一個更加省事的方案,裝一個小模塊qs
npm install qs -S // 而後在對應的地方轉就好了..單一請求也行,攔截器也行...我是寫在攔截器的. // 具體能夠看看我 axios 封裝那篇文章 //POST傳參序列化(添加請求攔截器) Axios.interceptors.request.use( config => { // 在發送請求以前作某件事 if ( config.method === "post" ) { // 序列化 config.data = qs.stringify(config.data); // ***** 這裏轉義 } // 如果有作鑑權token , 就給頭部帶上token if (localStorage.token) { config.headers.Authorization = localStorage.token; } return config; }, error => { Message({ // 餓了麼的消息彈窗組件,相似toast showClose: true, message: error, type: "error.data.error.message" }); return Promise.reject(error.data.error.message); } );
element-ui 2.0 表單或者input組件 驗證輸入的數字檢測出來是string
數字類型的驗證須要在 v-model
處加上 .number
的修飾符,這是 Vue 自身提供的用於將綁定值轉化爲 number 類型的修飾符。el-input 的 type 屬性設置爲 "number"
<el-form-item label="年齡" prop="age"> <el-input type="number" v-model.number="ruleForm2.age"></el-input> </el-form-item>
解決方法:
.el-table__body-wrapper, .el-table__footer-wrapper, .el-table__header-wrapper{ width: 101%; }
更多問題總結: