0
点赞
收藏
分享

微信扫一扫

如何在rails 6中使用js

kmoon_b426 2022-02-08 阅读 25


如何在rails 6中使用js_css


文章目录


  • ​​NPM​​
  • ​​Yarn​​
  • ​​ES6​​
  • ​​Babel​​
  • ​​Webpack​​
  • ​​Webpacker​​
  • ​​Sprockets 4​​
  • ​​不要以使用Sprockets的方式使用Webpacker​​
  • ​​更多细节参考[原文链接](https://blog.capsens.eu/how-to-write-javascript-in-rails-6-webpacker-yarn-and-sprockets-cdf990387463)​​


在这篇文章中我们会介绍

Webpacker

Yarn

Sprockets

.


如何在rails 6中使用js_html_02

和以往的版本不同,6之前的js脚本存放目录是​​app/assets/javascripts​​​,但是到了6,官方推荐的js脚本存放位置是​​app/javascript​​目录

在这篇文章中,我会一步一步地介绍如何将bootstrap和FontAwesome 5加入到rails 6项目中

NPM

这个没啥好介绍的,他就是node.js的包管理工具,就像python的pip,ruby的gem和php的composer

npm install bootstrap

npm会自动将下载下来的包存放到node_modules目录中,并在package.json中维护一个列表

{
"name": "demo",
"private": true,
"dependencies": {
"@rails/actioncable": "^6.0.0",
"@rails/activestorage": "^6.0.0",
"@rails/ujs": "^6.0.0",
"@rails/webpacker": "4.2.2",
"turbolinks": "^5.2.0",
"markdown": "0.5.0"
},
"version": "0.1.0",
"devDependencies": {
"webpack-dev-server": "^3.10.3"
}
}

Yarn

yarn也是js的包管理工具,但是它比npm更强大

yarn会根据package.json文件中的内容自动更新我们所需要的包,你可以在​​yarn.lock​​文件中锁定我们的包版本,这样yarn就不会自动更新他们了

在rails 6中,如果我们需要一个js库,我们只需要执行​​yarn add package_name​​即可

ES6

js的新标准,他提供了一系列新的特性,这里暂且不表

Babel

因为大部分浏览器都还不支持ES6,所以我们需要Babel将ES6编译成ES5,Babel就是这个负责转换ES6到ES5的工具

Webpack

现在我们有了Babel和Yarn和他们的配置文件,现在我们需要一个工具使得这些东西能够自动执行和配置,以此让我们更在专注于代码的编写

Webpack将会帮助我们编译assets,webpack会把他们编译成适当的插件,然后这些插件又会被我们的程序使用进行各种处理工作

以下是webpack可以帮我们做到的:


  • 处理ES6代码
  • 使用babel-loader插件使得Babel自动将ES6代码转换为ES5代码
  • 将输出结果打包到一个我们可以将其包含到html dom中的js文件如下所示:

<script type="text/javascript" src="path-to-es5-javascript-pack.js"></script>

Webpacker

注意不要将其和Webpack混淆

Webpacker是一个gem,他将webpack包含进我们的rails应用中。它自身带有一些初始配置(足够我们起步),这样我们就可以不用操心配置的问题,直接开始编写实际的代码

Webpacker的默认配置:


  • ​app/javascript/packs​​目录应该包含你的js代码
  • 你可以在你的视图中使用如下方式包含js代码​​javascrit_pack_tag '<pack_name>'​

举个例子:

<%= javascript_pack_tag 'my_app' %>

对应的html代码就是:​​src="app/javascript/packs/my_app.js")​

在文章的最后我将会讲解所有的这些到底是如何工作的,不过在此之前我们先讲一下Sprockets

有的读者肯能会问,既然js已经转移到了​​app/javascript​​目录,那么css文件呢?

这一点我们可以通过查看​​config/webpacker.yml​​文件来解答:

# Extract and emit a css file
extract_css: false

通过注释我们可以看到,webpacker是可以做到将css也放在新的位置而不是​​app/assets/stylesheets​​​中,而且webpacker也提供了对应的引用标签​​stylesheet_pack_tag​​​,但是我们有看到​​extract_css​​​的值是​​false​​​,可以得知默认css的提取是关闭的,所以我们依然可以使用​​Sprockets​​​,使用旧目录​​app/assets/stylesheets​

另外一点值得注意的地方是,你可能会认为在运行​​rails assets:precompile​​​时,rails只会预编译​​app/assets​​​中的文件,但是实际上rails会将​​app/javascrit​​​和Sprockets的​​app/assets​​中的文件都进行预编译

Sprockets 4

正如Webpack,Sprockets也是一个资源管道,这意味着她也是负责处理资源文件(js、css、images、字体文件等等),将它们转换为目标格式

在rails 6中webpack(er)代替了Sprockets成为了在rails应用中编写js的新标准。尽管如此,Sprockets仍然是css文件的默认处理方式

在rails 5,Sprockets 3中,我们需要将assets清单添加到​​config.assets.precompile​​文件中

而在rails 6,Sprockets 4中,我们则需要将assets清单写到​​app/assets/config/manifest.js​​中

如果你想向Sprockets添加资源,你要完成以下事情


  • 讲你的css文件放到​​app/assets/stylesheets/​​目录下
  • 确保你的​​app/assets/config/manifest.js​​​对​​stylesheet_link_tag​​​或者​​link_tree​​​、​​link_directory​​​、​​link​​语句是可用的
  • 使​​stylesheet_link_tag​​​将其引入到你的视图中​​<%= stylesheet_link_tag 'my_makeup' %>​

当然,也有​​其他的引入方式​​

不要以使用Sprockets的方式使用Webpacker

理解下面的内容对你来说将是很重要的,它可以帮你省去好几个小时的时间

在编译模块这方面,Webpack和Sprockets是有很大的差异的

在rails 6中,你所编写的js都被模块化了,存放在不同的命名空间下,不能直接被全局访问,你需要先导入模块,然后方可调用相应的方法,看一下下面的例子你就明白了

这是使用Sprockets的写法

​app/assets/javascripts/hello.js​

内容如下:

function hello(name) {
console.log("Hello " + name + "!");
}

​app/assets/javascripts/user_greeting.js​

内容如下

function greet_user(last_name, first_name) {
hello(last_name + " " + first_name);
}

视图​​app/views/my_controller/index.html.erb​​内容如下:

<%= javascript_link_tag 'hello' %>
<%= javascript_link_tag 'user_greeting' %>
<button onclick="greet_user('Dire', 'Straits')">Hey!</button>

上面的例子很好理解,没有什么特殊的地方

但是在Webpacker中怎么写呢

如果你认为只需要直接将上面两个js文件移动到​​app/javascript/packs​​那你就大错特错了

因为​​hello()​​​会被编译成ES6 模块,​​user_greeting()​​也一样,尽管包含这两个文件的相应的编译后的js文件你被包含了进来,其实hello方法也是不存在的

那么我们应该怎么做呢?

​app/javascript/packs/hello.js​​:

export function hello(name) {
console.log("Hello " + name + "!");
}

​app/javascript/packs/user_greeting.js​​:

import { hello } from './hello';
function greet_user(last_name, first_name) {
hello(last_name + " " + first_name);
}

​app/views/my_controller/index.html.erb​​:

<%= javascript_pack_tag 'user_greeting' %>
<button onclick="greet_user('Dire', 'Straits')">Hey!</button>

这样就行了吗?

大师是否定的,因为​​greet_user​​是不可被访问到的,一旦被编译,它就被隐藏到了一个模块中

最终我们找到了这一章节的重点:


  • Sprockets:视图可以直接和js文件进行交互,比如调用js中的方法和变量等等等
  • webpack:视图没办法直接访问js

那么我们到底该怎么做呢?

请看下面的

我们使用​​jquery​​举例子:

import $ from 'jquery';
import { hello } from './hello';
function greet_user(last_name, first_name) {
hello(last_name + " " + first_name);
}
$(document).ready(function() {
$('button#greet-user-button').on(
'click',
function() {
greet_user('Dire', 'Strait');
}
);
});
/* Or the ES6 version for this: */
$(() =>
$('button#greet-user-button').on('click', () => greet_user('Dire', 'Strait'))
);

​app/views/my_controller/index.html.erb​​:

<%= javascript_pack_tag 'user_greeting' %>
<button id="greet-user-button">Hey!</button>

我们使用​​<%= javascript_pack_tag 'user_greeting' %>​​引入​​app/javascript/packs/user_greeting.js​

可以看到我们是监听事件,而不是直接在视图中调用js中的function

更多细节参考​​原文链接​​



举报

相关推荐

0 条评论