这里有我的脚丫印😄

程序媛


  • 首页

  • 归档

Rails Model 中使用 Enum (枚举)

发表于 2017-10-26 |

使用场景与个人理解:用作 model 中类似 status 这种字段的翻译。数据库中通常会把这样的字段存成 Integer 类型,比如 0 (激活),1 (存档)。我们在代码中引用的话用英文代表相应的 Integer 值,可增加代码可读性,否则直接写在 sql 中或者直接写 0 或者 1 很难知道它们到底代表什么。所以,枚举类型其实是 { active: 0, archived: 1 } 。那么又如何把 active 翻译成中文呢?所以就得用 i18n 这种去翻译成中文了。

参考:
关于在 Rails Model 中使用 Enum (枚举) 的若干总结

ActiveRecord::Enum

相关gem:
enumerate_it

rspec 测试书写规范

发表于 2017-10-26 |

之前很为写测试头痛,从现在开始测试也要认真写啊 😂 。
总是搞不懂 describe context it let subject before/after 之间先后顺序以及含义。大概看了一个 rspec-style-guide,可以有一定的了解。本文摘自 The RSpec Style Guide,详尽的请参考原文。

完整结构:

class

1
2
3
4
5
6
7
8
9
class Article
def summary
#...
end
def self.latest
#...
end
end

article_spec.rb

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
describe Article do
subject { FactoryGirl.create(:some_article) }
let(:user) { FactoryGirl.create(:user) }
before do
# ...
end
after do
# ...
end
describe '#summary' do
context 'when there is a summary' do
it 'returns the summary' do
# ...
end
end
end
describe '.latest' do
context 'when latest' do
it 'returns the latest data' do
# ...
end
end
end
end

articles_controller_spec.rb

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
# A classic example for use of contexts in a controller spec is creation or update when the object saves successfully or not.
describe ArticlesController do
let(:article) { double(Article) }
describe 'POST create' do
before { allow(Article).to receive(:new).and_return(article) }
it 'creates a new article with the given attributes' do
expect(Article).to receive(:new).with(title: 'The New Article Title').and_return(article)
post :create, article: { title: 'The New Article Title' }
end
it 'saves the article' do
expect(article).to receive(:save)
post :create
end
context 'when the article saves successfully' do
before do
allow(article).to receive(:save).and_return(true)
end
it 'sets a flash[:notice] message' do
post :create
expect(flash[:notice]).to eq('The article was saved successfully.')
end
it 'redirects to the Articles index' do
post :create
expect(response).to redirect_to(action: 'index')
end
end
context 'when the article fails to save' do
before do
allow(article).to receive(:save).and_return(false)
end
it 'assigns @article' do
post :create
expect(assigns[:article]).to eq(article)
end
it 're-renders the 'new' template' do
post :create
expect(response).to render_template('new')
end
end
end
end

rails 中 polymorphic 的使用, 以及获取 unscoped 对象属性

发表于 2017-10-25 |

注意:本文小写的变量都为实例变量,如:employee

使用 polymorphic

场景: Employee 和 Product 都 has_many pictures, 但是又不希望创建两个类似的 pictures 表。也就是我们希望Employee 和 Product 可以同时关联上 Picture, 最后能从 pictures 表中各取所需,也可以在 Picture 的每个实例对象中获得所属对象。最终结果:

  • rails 中
1
2
3
employee.pictures
product.pictures
picture.imageable # 是一个具体的 employee 或者 product 对象
  • 存在表里的是:
id name imageable_id imageable_type
1 sun 1 Product
2 moon 1 Employee
  • 示例代码
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
class Picture < ApplicationRecord
belongs_to :imageable, polymorphic: true
end
class Employee < ApplicationRecord
has_many :pictures, as: :imageable
end
class Product < ApplicationRecord
has_many :pictures, as: :imageable
default_scope { where(published: true) }
end
class CreatePictures < ActiveRecord::Migration[5.0]
def change
create_table :pictures do |t|
t.string :name
t.integer :imageable_id
t.string :imageable_type
t.timestamps
end
add_index :pictures, [:imageable_type, :imageable_id]
end
end
  • 注意事项

model 中的 imageable 需要与表中的 imageable_id 和 imageable_type 对应,如果你的是 object_id 和 object_type,那么 model 中应该是 belongs_to :object, polymorphic: true

覆盖 Picture 中的 imageable

上述代码中,Product 有 scope,当你用 picture.imageable 的时候,会把 scope 也带上,有可能你需要的是所有的 imageable ,而不是 scope 下的,这个时候可以通过覆盖掉 imageable 这个方法来解决。

比如:

1
2
3
4
5
6
7
class Picture < ApplicationRecord
belongs_to :imageable, polymorphic: true
def imageable
@imageable ||= imageable_type.constantize.unscoped.find_by_id imageable_id
end
end

这里面通过 imageable_type 获取类名,constantize 把字符串的类名转化为对象,再调用 unscoped 方法,最后通过 imageable_id 找到具体的 imageable 对象。定义 @imageable 是为了一次请求中不多次查询imageable,因为 rails 会缓存。

根据 RubyChina 上的反馈做出调整

参考:https://ruby-china.org/topics/34429

  1. 一开始文中写的是 scope ,是写错了,现在改正过来了。
  2. 最好不使用 default_scope
  3. 如果非要使用 default_scope 可以用比文中更好一点的解决方法:(此方法发现 bug ,暂时还是不使用了,因为我们暂时不牵扯到)

    1
    belongs_to :imageable, -> { unscope(:where) }, polymorphic: true

    文中的方法会导致 includes 无效等问题。

postgresql 安装和使用

发表于 2017-10-24 |

参考:
Getting Started with PostgreSQL on Mac OSX

Documentation

目录:

  • 安装 Homebrew
  • 安装 Postgres
  • 进入 psql postgres 命令行
    • 创建角色用户
    • 给用户添加权限
    • 创建数据库

安装 Homebrew

如果你安装过了,可以跳过这一步。

1
/usr/bin/ruby -e "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/master/install)"

安装过程中,按照要求,输入回车键;如果需要输入电脑系统密码,就输入密码按回车即可。

安装 Postgres

brew install postgresql

安装固定版本,brew install postgresql@9.4

安装好之后,会有一些简单的说明。也告诉了启动方式。

比如:

1
2
3
4
To have launchd start postgresql@9.4 now and restart at login:
brew services start postgresql@9.4
Or, if you don't want/need a background service you can just run:
pg_ctl -D /usr/local/var/postgresql@9.4 start

执行命令:pg_ctl -D /usr/local/var/postgres start && brew services start postgresql

然后输入:postgres -V,会返回安装的相应的版本。

配置 Postgres

命令行输入:psql postgres,(或者 sudo psql postgres)

(如果刚安装好,输入此命令,提示说没有这个命令,可以重启电脑试试)

进入 psql 命令行, postgres=# 开头

输入:postgres=# \du

可以看到:

创建一个角色用户:

postgres=# CREATE ROLE patrick WITH LOGIN PASSWORD 'Getting started';

再次输入 \du

会发现上图中多了一个 patrick,

修改角色的权限:

postgres=# ALTER ROLE patrick CREATEDB;

再输入 \du,会看到 patrick 多了个权限。

如果我们想给角色 Superuser 权限,可以修改为 postgres=# ALTER ROLE patrick Superuser;

创建数据库 CREATE DATABASE databasename;

我把面试题总结到 RubyChina 上带来的反思

发表于 2017-10-19 |

我去面试了一圈,被问了很多问题。所以回来的时候就回忆问题,罗列出来,精心把答案都找了一遍后,总结成一篇文章,在我的博客和我的简书上各发了一下,后来想想,RubyChina 上技术氛围更好,也发到那里吧。

发文章的初衷就是想大家就着面试题一起讨论一起学习一下。没想到这会涉及暴露面试题的诚信问题。有不少人回帖说我这样做不好,并且把自己置身于风险之中。

我因为在 RubyChina 上发帖,觉得每次得到的回馈都不在技术上,就不太敢在上面发帖了,这次信心满满的,把自己用心整理的东西给大家一起参考学习,结果还是落的一鼻子灰,心情却是有点不好受。

当然,最后反思还是我自己做的不对。我也有辩驳说,“发之前也看到 RubyChina 上有人讨论面试题的帖子,看到大家并没有担忧什么啊”,“这些东西网上一搜一大把啊”。有回复说,大家都做的事情,并不代表是对的事情。一想想这也对着呢。所以,我自己或许没有遵循行业的规则(甚至根本都没意识到这是个问题)。

所以,我觉得更多的生活感悟以及自己的学习,还是写到自己的博客上比较好,因为很多东西,在自己的天地里面,就没有那么多的规则束缚,但是同时,也都是跟自己交流的比较多了。我想扩大交流圈,就要符合那个交流圈的规则。很多东西不是自己觉得没问题就没问题了。

至于,发布面试题到底是不是牵扯到道德问题、诚信问题,我自己的考虑,是觉得,或许这是个公开的秘密,只是不能把他捅破似的。就算大家做的事情不一定都是对的事情,可是很多人做了,那却也不是秘密了,但是作为一个有原则的人,也不能跟着一起去做这个事情。

下次如果再发帖,文章内容最好不要涉及一些敏感的话题。

不只是工作,生活中,或许有不少的公开的秘密和潜规则,都不能捅破,或许经历过一次次碰壁,我会慢慢学好这些规则。只是,真的害怕像有些人所说,阻碍了我更高的发展。不过,希望社会给我犯错的机会,真想低下头来说:“小人无知,请大人恕罪”。不然,犯了这些错之后,除了低头认错,我也不知有什么更好的解决方案了,毕竟,你犯错了,还找理由,不是显得你更“小人”了么?“不知者无罪”也是人家宽宏大量,才对你说的,谁让你不知的呢?(是不是傻)

昨天,看到一篇阮一峰的网络日志我为什么喜欢编程,里面有一句话,

我们生活的这个国家,是一个禁止自由思考、党决定一切的国家。在这里,如果你想不撒谎、不干坏事、并且被公正地对待,那么可能你只能去编程了。

我一度也这么认为,庆幸自己做了编程,现在想想就算一门心思栽倒在技术的海洋,你也只能是一个技术工吧,除非你牛逼到一定的程度。

想在社会活下去,就得满足这样那样的规则束缚,随心所欲都还得加个不逾矩,你以为呢?或许这篇说的有些悲观,但是,必须这样来,不然,就会像我一样,做出别人口中不成熟的事情。突然感觉,最悲催的事情就是,做了一个大家觉得有问题的事情,而你自己连这是个问题都没有意识到。

ruby 问题总结

发表于 2017-10-17 |
  1. ruby 的命名规则
    局部变量:以英文字母或者_开头,如:

    1
    name = "this is a local variable"

    全局变量:以 $ 开头,如:

    1
    $name = "this is a global variable"

    实例变量:以@开头,如:

    1
    @name = 'lily'

    类变量:以@@开头,如:

    1
    @@name = 'lily'

    常量:全大写字母,如:

    1
    NAME

    类名和模块名:以首字母大写,驼峰命名法。如:

    1
    HelloWorld

    方法名:小写用_隔开,如:

    1
    sort_by_name
  2. ruby 中 singleton class 和 singleton method 分别是什么

    Singleton method

    A method which belongs to a single object rather than to an entire class and other objects.
    一个方法只属于一个对象,而不是整个类和其他实例化对象。

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    firstObj = ClassMethods.new
    secondObj = ClassMethods.new
    def firstObj.singletonMethod
    "Hi am a singlton method available only for firstObj"
    end
    firstObj.singletonMethod # "Hi am a singlton method available only for firstObj"
    secondObj.singletonMethod #undefined method `singletonMethod' for #<ClassMethods:0x32754d8> (NoMethodError)

    So this “singletonMethod” belongs only to the firstObj object and won’t be available for other objects of this class.
    If you try to make the secondObj.singletonMethod Ruby will inform you that singletonMethod is an undefined method.

    所以,singletonMethod 只属于 firstObj,不能被这个类的其他实例化对象所调用。如果你想用 secondObj.singletonMethod 调用这个单例方法,ruby 会告诉你 singletonMethod 没有定义

    If you like to find all the singleton methods for a specific object, you can say objectname.singleton_methods
    In our case
    如果你想找到一个特定对象的所有单例方法,你可以用 objectname.singleton_methods 。在我们的例子里面就是:

    1
    2
    firstObj.singleton_methods => ["singletonMethod"]
    secondObj.singleton_methods => []

    To avoid throwing undefined method error when you try to access a singleton method with some other object

    避免调用单例方法**抛出方法未定义的异常:

    1
    2
    3
    4
    5
    6
    7
    8
    9
    if secondObj.singleton_methods.include?("singletonMethod")
    secondObj.singletonMethod
    end
    # 或
    if secondObj.singleton_methods.include?( :singletonMethod )
    secondObj.singletonMethod
    end

    Singleton classes
    单例类

    A singleton class is a class which defines a single object.
    单例类就是只有一个实例对象的类。

    In our above example we have two objects firstObj and secondObj.
    We can create a separate class for the secondObj instance and that is called as a singleton class.
    So as per the definition we created a class for a single object.

    在我们上面的例子里面,我们有两个对象,firstObj 和 secondObj。我们给 secondObj 实例 创建一个单独的类,这就叫做单例类。
    所以按照定义为一个单独的对象我们创建了一个类。

    1
    2
    3
    4
    5
    class << secondObj
    def method4
    p "Hi am a singlton method available only for secondObj"
    end
    end

    When you see a class definition with the class keyword followed by two less than symbols that is a Singleton class opened for the object.
    In our ClassMethods class we had something like class << self which is also a singleton class. In Ruby a class itself is an instance of the Ruby class Let’s try something like this

    当你看到定义一个类后面跟着 << 的时候,这就是打开这个对象的单例类。
    在我们的 ClassMethods 这个类中,我们有 class << self ,所以这也是一个单例类。在 ruby 里,一个类本身也是一个 ruby 的类。让我们试试

    1
    ClassMethods.class # Class
  3. 怎么写一个 module,可以让包含这个 module 的 class 既能使用这个 module 的类方法又能使用这个 module 的实例方法
    参考 http://motion-express.com/blog/include-instance-&-class-methods-from-a-module

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    module Foo
    def self.included(m)
    def m.show1
    p "hi"
    end
    end
    def show2
    p "hello"
    end
    end
    class Bar
    include Foo
    end
    Bar.new.show2 #=> "hello"
    Bar.show1 #=> "hi"
    Bar.show2 #=> NoMethodError: undefined method `show2' for Bar:Class
    Bar.new.show1 #=> NoMethodError: undefined method `show1' for #<Bar:0x007fa1fb8c2ce8>

    或

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    module A
    def b
    puts "method b from module A"
    end
    def c
    puts "method c from module A"
    end
    end
    class B
    include A
    extend A
    end
    B.new.b # => "method b from module A"
    B.b # => "method b from module A"
    B.new.c # => "method c from module A"
    B.c # => "method c from module A"
  4. require load auto_load 以及 require_dependency 的区别
    require,load用于文件,如.rb等等结尾的文件。
    include则用于包含一个文件(.rb等结尾的文件)中的模块。
    require一般情况下用于加载库文件,而load则用于加载配置文件。
    require加载一次,load可加载多次。

    详细参考: 浅谈Ruby中的类加载机制

    Require/load/autoload的区别和用法

    ActiveSupport::Autoload 学习

    Here are the differences between Require, Load, Include and

  1. 描述 object, class, module 的关系是什么,并画图表示。
    从继承关系来说,是Class –> Module –> Object,即Object是继承树的顶层,紧接着是Module,然后是Class。
    Modules, Classes, and Objects

    1
    2
    3
    4
    Object -> Module -> Class -> MyClass
    另外:
    Object.class = Class
    Class.superclass = Module
  2. 为什么在 model 中可以调用 validates,自己怎么实现 model 中的 validates,试着实现一下?

    validations

  3. ruby 中 ? 或者 ! 作为后缀的方法有什么不同?
    It’s “just sugarcoating” for readability, but they do have common meanings:

    Methods ending in ! perform some permanent or potentially dangerous change; for example:
    Enumerable#sort returns a sorted version of the object while Enumerable#sort! sorts it in place.
    In Rails, ActiveRecord::Base#save returns false if saving failed, while ActiveRecord::Base#save! raises an exception.
    Kernel::exit causes a script to exit, while Kernel::exit! does so immediately, bypassing any exit handlers.
    Methods ending in ? return a boolean, which makes the code flow even more intuitively like a sentence — if number.zero? reads like “if the number is zero”, but if number.zero just looks weird.

    在Ruby中,以问号(?)结尾,被用于标示谓词,即返回Boolean值的方法,如Array.empty?(判断数组中元素是否为空)。

    在Ruby中,以问号(?)结尾,出现在方法名词尾部,表示使用该yyifc是需要多加小心的。
    而通常情况下,不带感叹号的方法不带感叹号的方法返调用该方法的一个拷贝,二带感叹号的方法则是一个可变方法,该方法会修改原来的对象,如Array类中的sort和sort!

  4. 有没有读过 rails 源码?
    只瞅过几眼
  5. rails 本身是由什么组成的?
    Rails组成和项目结构
  6. 有没有读过 《ruby 元编程》?
    没有呢(心里想,回去赶紧买一本拜读一下)
  7. 工作中遇到过哪些挑战和困难,怎么解决的?
  8. 不使用 ActiveJob,sidekiq 单独使用可以不?
    Active Job 和 Sidekiq 简介
    Active Job
    Rails: 使用Active Job来处理异步任务
  9. bundler 和 gem 的关系?bundler 是 gem 么?
    bundler
    Rvm 与 Bundler 的爱恨情仇
    RVM,RubyGems和Bundler的日常使用

  10. passenger, nginx, 还有一个是什么,忘记了,这三个各自干什么的,怎么结合起来一起工作,缺一可以不
    Ruby 服务器对比

  11. each 和 map 的区别
    each: 顺序返回各个元素
    collect: 把原数组的各个元素顺序返回,并组装新的数组
    map: 与 collect一样,会创建一个新的数组
    select: 与collect一样,会创建一个新的数组

    Ruby: 聊一聊关于集合遍历的各种方法
    Pluck vs. map and select

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    $ a = [1,2,3,4]
    => [1, 2, 3, 4]
    $ a.each {|n| n*2}
    => [1, 2, 3, 4]
    $ a
    => [1, 2, 3, 4]
    $ a.map {|n| n*2}
    => [2, 4, 6, 8]
    $ a
    => [1, 2, 3, 4]
    $ a.collect {|n| n*2}
    => [2, 4, 6, 8]
    $ a
    => [1, 2, 3, 4]
  12. find 和 find_by 的区别
    rails中find/find_by/where的区别

  13. 解决 N+1 Query 的方法有哪些
    浅谈 ActiveRecord 的 N + 1 查询问题
    Rails使用include和join避免N+1 queries
    面试官说了片段缓存,也可以解决查询问题

  14. 单表继承
    Rails 之单表继承 (Single Table Inheritance)
    Inheritance 单表继承
    ActiveRecord-连接多张表之单表继承
  15. rack 是什么
    Rails on Rack

  16. 安全问题。怎么破 XSS 和 CSRF攻击
    解法:
    对于XSS:首先说说什么是XSS(Cross-site scripting),跨站脚本攻击,攻击者在客户端注入可执行代码。
    对策:
    过滤恶意输入非常重要,但是转义 Web 应用的输出同样也很重要。
    过滤恶意输入白名单比黑名单要有效,特别是在需要显示未经过滤的用户输入时(例如前面提到的的搜索表单的例子)。使用 escapeHTML() 方法(或其别名 h() 方法),把 HTML 中的字符 &、”、< 和 > 替换为对应的转义字符 &、”、< 和 >。

    对于CSRF:Cross Site Request Forgery,跨站请求伪造。通俗理解:攻击者盗用当前用户身份,发请当前用户的恶意请求:如邮件,银行转账等。

    对策:首先,根据 W3C 的要求,应该适当地使用 GET 和 POST HTTP 方法。其次,在非 GET 请求中使用安全令牌(security token)可以防止应用受到 CSRF 攻击。

  17. ActiveSupport::Concern 的工作原理
    参考 ActiveSupport::Concern
    [ActiveSupport::Concern 的工作原理](http://xiewenwei.github.io/blog/2014/01/13/how-activesupport-corncern-work/)
    
  18. Rails: pluck与select的区别
  19. yield self 的用法,写个例子

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    class Builder
    def initialize arguments
    # do somthing by init arguments
    end
    # you can use Builder's method in block
    def build
    yield self if block_given?
    end
    end
  20. scope 的实现原理
    核心是延迟计算,将where、order、limit子句变为Relation对象,然后在最终调用each/to_a时组装sql

heroku 上 action_mailer 的配置

发表于 2017-10-06 |

参考 http://usingname.space/2015/07/25/gmail-smtp-ruby-on-rails-actionmailer-and-you/

1
2
3
4
5
6
7
8
9
10
11
12
13
14
config.action_mailer.default_url_options = { host: 'myapp.herokuapp.com' }
config.action_mailer.delivery_method = :smtp
config.action_mailer.perform_deliveries = true
config.action_mailer.raise_delivery_errors = false
config.action_mailer.default :charset => "utf-8"
config.action_mailer.smtp_settings = {
address: "smtp.gmail.com",
port: 587,
domain: "myapp.herokuapp.com",
authentication: "plain",
enable_starttls_auto: true,
user_name: ENV["GMAIL_USERNAME"],
password: ENV["GMAIL_PASSWORD"]
}

这块我都弄好部署到 heroku 了,但是还是发送不成功, hero 的 log 中可以看到,gmail 有一些安全验证,就算拿到了 gamil 的账户和密码,gmail 也会阻止不安全的应用登录,我修改了gmail的配置,也没有行,所以,我觉得测试到这里就差不多了,我也有点害怕把邮箱搞的不安全了。

使用 figaro 管理密码

发表于 2017-10-06 |
  1. 安装 figaro
    gem figaro 加到gemfile 中
    bundle install
    figaro install
    会自动生成 config/application.yml 文件并自动添加到 .gitignore 档案里

  2. 设置机密信息
    cp config/application.yml config/application.yml.example
    application.yml 被加入到 .gitignore 中,为了方便协作,把 application.yml 复制一个样例放入 application.yml.example 中

  3. figaro 配置到 heroku 环境变量中
    figaro heroku:set -e production
    这会把 config/application.yml 中设置的变量写入 heroku 环境变量中,使用 heroku config 可以列出目前所有的配置

如何在 Heroku 设置环境变数,参考 https://devcenter.heroku.com/articles/config-vars

如何在本地设置环境变数,参考 http://thejavashop.net/blog/?p=5

部署 app 到 heroku

发表于 2017-10-06 |

1.首先先注册一个 Heroku 帐号

打开网站:https://www.heroku.com/
注册网站时,注意三点:

  • Email不能选用国内的邮箱,建议使用gmail邮箱
  • 语言选 Ruby
  • 勾选人机验证

2.安裝Heroku Command Line(Heroku Toolbelt)
Heroku 所推出的环境命列工具包。
前往 https://toolbelt.heroku.com/
依照网站指示下载安装。

检查是否完成安装,可以输入 heroku –version
应该会看到heroku 的版本

3.完成 Heroku 的 SSH-key 的设定
先输入 heroku login 确认登入,输入email、密码(密码不会显示,输入完直接按return即可)

再输入 heroku keys:add 即可

  1. 在终端(Terminal)里输入heroku create
    每输入一次 heroku create 都会生成一个新的 herokuapp ,免费帐号预设上限为5个。超过5个的时候,请手动登入自己的heroku网址删除app。

  2. 最后再输入 git push heroku master

  3. 部署成功后,输入 heroku run rake db:migrate
  4. 输入 heroku open 可以打开刚刚部署成功的 app 了

spring boot 初步学习

发表于 2017-10-02 |

环境配置

Mac 上搭建 java 开发环境

初始化项目

参考链接 从此链接中输入项目名,并选择相应的依赖,点击生成项目,
下载下来,在 IDEA 中打开这个项目,可以看到基本的框架已经生成了。然后就可以开发了。跟两年前写
servlet 和 配置 ssh 相关的 xml 文件相比,这真是十分的简单了。

可以试着写一个小小的 demo,有很多视频教程跟着一步步做就成,我是跟着慕课网上的视频学习的。
下面是我记录的一些我得到的新的知识点。

spring boot项目启动方式:

  1. 可以使用 IDEA 的启动按钮启动
  2. 进入项目文件夹下,在命令行启动,输入 mvn spring-boot:run
  3. 进入项目文件夹下,输入 mvn install,再继续输入 cd target,进入 target 目录,
    输入 ll,可以看见一个 SNAPSHOT.jar结尾的文件,我的是 girl-0.0.1-SNAPSHOT.jar ,输入 java -jar target/girl-0.0.1-SNAPSHOT.jar --spring.profiles.active=prod 即可启动。

spring data jpa 与 mybatis

spring data jpa 是对 Hibernate 的封装,几乎不用写 sql,写代码显得十分简洁。和 rails
框架类似,不用写 sql ,而且它还可以反向生成表结构,所以,几乎不用登录数据库,不用和 sql 直接打交道。
(对于写快一年 ruby on rails 的我来说初学这个还是很欣喜的。)
不过我做的项目团队选择使用 mybatis,可以自由写 sql,也不错哈。
更详细的说明,可以阅读大致了解 ORM:Hibernate、Mybatis与Spring Data JPA的区别
mybatis 学习参考mybatis 使用注解或xml

mysql

使用 brew 安装: brew install mysql
根据提示可看到怎么设置密码,怎么开启和关闭。
两种方式开启(关闭同理):brew services start mysql 或者 mysql.server start
因为安装后初始没有密码(We’ve installed your MySQL database without a root password)所以输入 mysql_secure_installation 修改密码,会让你输入密码强度,本地输入0最低就好了,这样才能设置 123456 这种简单的密码。如果长度太短(我这里要输入25个字符),可以登录进入修改密码长度。
通过输入 mysql -uroot 登录到 mysql,
输入 set global validate_password_policy=0; 设置密码校验强度为 0,
输入 set global validate_password_length=4; 设置密码长度至少为 4
然后退出 mysql,继续输入 mysql_secure_installation 修改密码,可以设置为 123456 这种密码了。后面还会问一些问题,仔细看看问的什么,选择你需要的输入 y 或者 n 就好了。

使用root登录进入数据库:
mysql -u root -p
输入密码

create database dbtest; (创建数据库 dbtest)
use dbtest; (启用数据库 dbtest)
(创建表 users 表)
create table users (id integer auto_increment primary key, name varchar(225), salary integer);
show tables; (列出所有表)
desc users; (列出 users 表结构)

maven

mvn clean package (执行测试)
mvn clean package -Dmaven.test.skip=true (跳过单元测试)

1234…9

陈云莉 m18301662790@gmail.com

记录一些技术点,留下一些生活感悟

82 日志
25 标签
© 2017 陈云莉 m18301662790@gmail.com
由 Hexo 强力驱动
|
主题 — NexT.Gemini v5.1.3