m2m 0.2.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA1:
3
+ metadata.gz: 3fe6f9904ec77946ac882d1a5d9f039deb5dd6c6
4
+ data.tar.gz: a155f0805fc7ed72cdc7d6ceb9375fe2f091998b
5
+ SHA512:
6
+ metadata.gz: 3b0a43fdefd67a318acfcc8d62359af77f0ac7e4288f66eb627cd6607e094e0d4117d03aaff5f1861dca53d753b9842e3e186bc76157ad115e60eb357bf8d80c
7
+ data.tar.gz: ba2bd537a3bc26dbe21af62edf27641e57dcc19cce8851f9836f711652c26a85da159b64737e69f5a77a213082b8401c067b2c77cbb570a5aaaa7f25adf84e82
@@ -0,0 +1,39 @@
1
+ *.gem
2
+ *.rbc
3
+ /.config
4
+ /coverage/
5
+ /InstalledFiles
6
+ /pkg/
7
+ /spec/reports/
8
+ /spec/examples.txt
9
+ /test/tmp/
10
+ /test/version_tmp/
11
+ /tmp/
12
+
13
+ ## Specific to RubyMotion:
14
+ .dat*
15
+ .repl_history
16
+ build/
17
+
18
+ ## Documentation cache and generated files:
19
+ /.yardoc/
20
+ /_yardoc/
21
+ /doc/
22
+ /rdoc/
23
+
24
+ ## Environment normalization:
25
+ /.bundle/
26
+ /vendor/bundle
27
+ /lib/bundler/man/
28
+
29
+ # for a library or gem, you might want to ignore these files since the code is
30
+ # intended to run in multiple environments; otherwise, check them in:
31
+ # Gemfile.lock
32
+ # .ruby-version
33
+ # .ruby-gemset
34
+
35
+ # unless supporting rvm < 1.11.0 or doing something fancy, ignore this:
36
+ .rvmrc
37
+ .idea
38
+ kiteam-blog
39
+ test*
data/Gemfile ADDED
@@ -0,0 +1,11 @@
1
+ source "https://ruby.taobao.org/"
2
+
3
+ gem 'nokogiri', '1.6.7'
4
+ gem 'mustache', '1.0.3'
5
+ gem 'kramdown', '1.10.0'
6
+ gem 'commander', '4.4.0'
7
+ gem 'mail', '2.6.4'
8
+ gem 'webrick', '1.3.1'
9
+ gem 'aescrypt', '1.0.0'
10
+
11
+ gemspec
@@ -0,0 +1,23 @@
1
+ GEM
2
+ remote: https://ruby.taobao.org/
3
+ specs:
4
+ commander (4.4.0)
5
+ highline (~> 1.7.2)
6
+ highline (1.7.8)
7
+ kramdown (1.10.0)
8
+ mini_portile2 (2.0.0)
9
+ mustache (1.0.0)
10
+ nokogiri (1.6.7)
11
+ mini_portile2 (~> 2.0.0.rc2)
12
+
13
+ PLATFORMS
14
+ ruby
15
+
16
+ DEPENDENCIES
17
+ commander (= 4.4.0)
18
+ kramdown (= 1.10.0)
19
+ mustache (= 1.0.3)
20
+ nokogiri (= 1.6.7)
21
+
22
+ BUNDLED WITH
23
+ 1.11.2
data/LICENSE ADDED
@@ -0,0 +1,21 @@
1
+ The MIT License (MIT)
2
+
3
+ Copyright (c) 2016
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
@@ -0,0 +1,89 @@
1
+ # m2m
2
+
3
+ > Markdown to More
4
+
5
+ 将Markdown转换为其它格式的内容,如一个博客,一个网站,或者是一封邮件
6
+
7
+ 它还能将你的博客或网站自动提交到git,或者发布到你的服务器上。也可以通过简单的命令将最近的Markdown作为邮件发送,并将邮件中的图片插入到邮件中。
8
+
9
+ ## 如何安装
10
+
11
+ * 请确认你的电脑上已经安装了`ruby`环境,`Mac OSX`系统已经自带`Ruby`环境,Windows系统,请移步Ruby官方网站进行安装:https://www.ruby-lang.org/zh_cn/downloads/
12
+ * 打开命令行,执行`sudo gem install m2m`即可安装
13
+
14
+ ## 配置文件
15
+
16
+ 在你要生成的文件目录,创建一个`m2m.config`的文件,`m2m.config`是一个JSON格式的文件,格式如下:
17
+
18
+
19
+ {
20
+ "blog":{
21
+ "title": "m2m官方博客",
22
+ "host": "https://github.com/wvv8oo/m2m/"
23
+ },
24
+ "theme": "hyde",
25
+ "target": "./site"
26
+ }
27
+
28
+ * `blog.title`:博客的标题
29
+ * `blog.host`:博客的网址
30
+ * `theme`:主题,目前仅提供一个主题
31
+ * `target`:生成的目的目录,如果不设置,则会生成到`~/.m2m/[project_name]`
32
+
33
+ **很快m2m将会提供自动生成配置文件的功能**
34
+
35
+ ## 命令介绍
36
+
37
+ ### m2m build
38
+
39
+ 将当前目录下的markdown生成博客,也可以使用别名`m2m`,`m2m build`提供多个参数:
40
+
41
+ * `m2m --target`或`m2m -t`:指定生成的目标
42
+ * `m2m --source`或`m2m -s`:指定工作目录,默认为当前目录
43
+
44
+ ### m2m mail
45
+
46
+ m2m提供将最近改动的markdown发送到指定邮箱的功能,也可以指定发送某个Markdown文件,此功能提供给需要写周报的同学使用,你懂的。
47
+
48
+ 你需要在`m2m.config`文件中增加如下配置:
49
+
50
+
51
+ "mail": {
52
+ "smtp": "SMTP的地址",
53
+ "port": "端口,一般是25",
54
+ "account": "你的帐号",
55
+ "password": "密码",
56
+ "ssl": false,
57
+ "from": "发件人",
58
+ "to": "收件人,多个以逗号为分隔",
59
+ "format": "%Y-%m-%d",
60
+ "subject": "邮件标题"
61
+ }
62
+
63
+ * 发件人可以用`姓名 <yourname@email.com>`这种格式,注意姓名与邮件地址中间的空格,否则会造成发不出邮件的情况
64
+ * 邮件标题中,可以添加`$last_week`(上周)与`$now`(今天)两个占位符,发邮件时会自动替换
65
+ * `format`是邮件标题中时间占位符的格式化字符,默认为`%Y-%m-%d`,生成结果参考:`2016-06-04`
66
+ * 给个邮件标题的设置例子吧:`部门-姓名(花名) $last_week ~ $now`
67
+
68
+ `m2m mail`蛮多个参数:
69
+
70
+ * `--subject`或`-s`:指定邮件主题,优先级高于`m2m.config`的设置
71
+ * `--markdown`或`-m`:指定相对于当前目录的markdown文件,适用于要发送指定的markdown文件,如果不指定,则会发送最近修改的markdown文件
72
+ * `--slient`:静默发送,如果指定了此参数,将不会让用户确认直接发送
73
+ * `--addressee`或`-a`:指定发件人,优先级高于`m2m.config`的设置
74
+
75
+ ### 邮件件发收件人
76
+
77
+ 你有三个地方可以配置邮件主题与收件人,优先级为:`markdown文件>命令行参数指定>m2m.config文件`
78
+
79
+ 在markdown文件中,你可以通过写入meta的方式来指定邮件主题以及收件人,书写的方式如下:
80
+
81
+ <!--
82
+ subject: 我指定的邮件主题,也可以使用$last_week和$now两个变量
83
+ addressee: mail@example.com,other@example.com
84
+ -->
85
+ 这是你的markdown文件内容
86
+
87
+ ### m2m pdf(暂未提供)
88
+
89
+ m2m允许将指定的Markdown文件生成pdf
@@ -0,0 +1,14 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ require "bundler/setup"
4
+ require "m2m"
5
+
6
+ # You can add fixtures and/or initialization code here to make experimenting
7
+ # with your gem easier. You can also use a different console, if you like.
8
+
9
+ # (If you use this, don't forget to add pry to your Gemfile!)
10
+ # require "pry"
11
+ # Pry.start
12
+
13
+ require "irb"
14
+ IRB.start
data/exe/m2m ADDED
@@ -0,0 +1,51 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ require 'rubygems'
4
+ require 'commander'
5
+ require_relative '../lib/generator'
6
+ require_relative './site'
7
+ require_relative './mailer'
8
+ require_relative './setup'
9
+ require_relative './server'
10
+
11
+ class Application
12
+ include Commander::Methods
13
+ # include whatever modules you need
14
+ include SiteCommand
15
+ include MailCommand
16
+ include ServerCommand
17
+ include SetupCommand
18
+
19
+ def run
20
+ program :name, 'm2m'
21
+ program :version, '0.0.1'
22
+ program :description, 'Markdown to More'
23
+ default_command :site
24
+
25
+ #生成博客
26
+ command :site do |c|
27
+ self.site(c)
28
+ end
29
+
30
+ #启动服务器
31
+ command :server do |c|
32
+ self.server(c)
33
+ end
34
+
35
+ #发送邮件
36
+ command :mail do |c|
37
+ self.mail(c)
38
+ end
39
+
40
+ #配置相关
41
+ command :setup do |c|
42
+ self.setup c
43
+ end
44
+
45
+ run!
46
+ end
47
+ end
48
+
49
+ Application.new.run
50
+
51
+ # MyApplication.new.run if $0 == __FILE__
@@ -0,0 +1,21 @@
1
+ require 'commander'
2
+ require_relative '../lib/mailer'
3
+
4
+ module MailCommand
5
+ def mail(c)
6
+ c.syntax = 'm2m mail [options]'
7
+ c.summary = '将Markdown转换为HTML,并邮件发送给某人'
8
+ c.description = ''
9
+ c.option '-s STRING', '--subject STRING', String, '邮件主题,可选'
10
+ c.option '-a STRING', '--addressee STRING', String, '收件人,可选'
11
+ c.option '--silent', '静默发送,不提示'
12
+ c.option '-m STRING', '--markdown STRING', String, '要发送的markdown文件,如果不指定,则使用最近修改的文件'
13
+ c.action do |args, options|
14
+ util = Util.instance
15
+ #合并目录
16
+ util.workbench = util.get_merge_path('./')
17
+ mailer = Mailer.new
18
+ mailer.send options.addressee, options.markdown, options.subject, options.silent
19
+ end
20
+ end
21
+ end
@@ -0,0 +1,21 @@
1
+ require 'commander'
2
+ require_relative '../lib/generator'
3
+ require_relative '../lib/setup'
4
+ require_relative '../lib/server'
5
+
6
+ module ServerCommand
7
+ def server(c)
8
+ c.syntax = 'm2m server [options]'
9
+ c.summary = ''
10
+ c.description = '创建一个服务器'
11
+ c.option '-p INTEGER', '--port INTEGER', Integer, '生成的目标目录'
12
+ c.action do |args, options|
13
+ util = Util.instance
14
+ setup = Setup.instance
15
+
16
+ #合并目录
17
+ util.workbench = util.get_merge_path './'
18
+ Server.new.start options.port
19
+ end
20
+ end
21
+ end
@@ -0,0 +1,27 @@
1
+ require 'commander'
2
+ require_relative '../lib/setup'
3
+ require_relative '../lib/util'
4
+
5
+ module SetupCommand
6
+ def setup(c)
7
+ c.syntax = 'm2m setup [options]'
8
+ c.summary = ''
9
+ c.description = '配置M2M'
10
+ c.option '--mail', '配置邮件相关的信息'
11
+ c.option '--mail-password', '配置邮件相关的信息'
12
+ c.option '--site', '在当前目录下,配置网站相关信息'
13
+ c.action do |args, options|
14
+ setup = Setup.instance
15
+ util = Util.instance
16
+
17
+ if options.mail
18
+ setup.ask_mail
19
+ elsif options.mail_password
20
+ setup.ask_mail_password
21
+ elsif options.site
22
+ util.workbench = util.get_merge_path './'
23
+ setup.ask_site
24
+ end
25
+ end
26
+ end
27
+ end
@@ -0,0 +1,37 @@
1
+ require 'commander'
2
+ require_relative '../lib/generator'
3
+ require_relative '../lib/setup'
4
+
5
+ module SiteCommand
6
+ def site(c)
7
+ c.syntax = 'm2m site [options]'
8
+ c.summary = ''
9
+ c.description = ''
10
+ c.option '-s STRING', '--source STRING', String, 'Markdown源文件的目录'
11
+ c.option '-t STRING', '--target STRING', String, '生成的目标目录'
12
+ c.option '--force', String, '强行生成,如果目录存在,则会被删除'
13
+ c.action do |args, options|
14
+ target = options.target
15
+ source = options.source
16
+
17
+
18
+ util = Util.instance
19
+ setup = Setup.instance
20
+
21
+ #合并目录
22
+ util.workbench = util.get_merge_path(source)
23
+ #设置构建目录
24
+ setup.target_dir = target
25
+
26
+ #检查目标目录是否存在
27
+ if File::exists? setup.target_dir
28
+ question = "目标目录已经存在,您确认需要删除吗?[y/n]"
29
+ tips = "目标目录存在,生成失败"
30
+ util.error tips if not (options.force or agree question)
31
+ end
32
+
33
+ #执行生成
34
+ Generator.new
35
+ end
36
+ end
37
+ end
@@ -0,0 +1,63 @@
1
+ #读取文件内容
2
+ require 'nokogiri'
3
+ require 'kramdown'
4
+ require 'digest'
5
+
6
+ require_relative 'meta'
7
+ require_relative 'toc'
8
+ require_relative 'util'
9
+ require_relative 'setup'
10
+
11
+ class Article
12
+ def initialize
13
+ @meta = Meta.new
14
+ @toc = TOC.new
15
+ @util = Util.instance
16
+ @setup = Setup.instance
17
+ end
18
+
19
+ #转换文件
20
+ def convert(relative_path)
21
+ result = Hash.new
22
+
23
+ file = File::join @setup.content_dir, relative_path
24
+
25
+ #原始路径
26
+ result['file'] = file
27
+ #路径的MD5值
28
+ result['relative_path_md5'] = Digest::SHA256.hexdigest(relative_path.to_s)[0..15]
29
+
30
+ result['mtime'] = File::ctime file
31
+
32
+ #读取原始内容
33
+ original = IO.read(file)
34
+ result['original'] = original
35
+
36
+ #相对路径
37
+ result['relative_path'] = relative_path
38
+ result['relative_url'] = relative_path.to_s.gsub(/\.md$/, '.html')
39
+
40
+
41
+ meta_result = @meta.analysis original
42
+ meta = meta_result['meta'] || {}
43
+ body = meta_result['body']
44
+
45
+ meta['title'] = File::basename(file, '.md') if !meta['title']
46
+ meta['publish_date'] = result['mtime'] if !meta['publish_date']
47
+
48
+ result['meta'] = meta
49
+ result['body_markdown'] = body
50
+
51
+ if body
52
+ #创建markdown实例
53
+ markdown = Kramdown::Document.new(body)
54
+ html = result['body_html'] = markdown.to_html
55
+
56
+ result['excerpt'] = Nokogiri::HTML(html).text[0..99]
57
+ #获取toc相关的内容
58
+ result['toc_html'] = @toc.to_html markdown.to_toc
59
+ end
60
+
61
+ result
62
+ end
63
+ end
@@ -0,0 +1,77 @@
1
+ #使用模板转换为HTML
2
+
3
+ require 'mustache'
4
+ require 'pathname'
5
+ require 'fileutils'
6
+
7
+ require_relative './util'
8
+ require_relative './setup'
9
+
10
+ class Compiler
11
+ def initialize()
12
+ @util = Util.instance
13
+ @setup = Setup.instance
14
+
15
+ #当前的工作目录
16
+ @workbench = @util.workbench
17
+ @theme_dir = self.get_theme_dir
18
+ @template_dir = File::join(@theme_dir, 'template')
19
+ Mustache.template_path = File::join(@template_dir, 'partials')
20
+
21
+ end
22
+
23
+ def theme_dir
24
+ @theme_dir
25
+ end
26
+
27
+ #获取target, 如果存在, 则删除
28
+ def ensure_target()
29
+ dir = @util.target_dir
30
+ #存在则先删除
31
+ FileUtils.rm_rf(dir) if File::exists?(dir)
32
+ #创建目录
33
+ Dir::mkdir(dir)
34
+ dir
35
+ end
36
+
37
+ #根据配置获取theme, 如果没有, 则使用默认的theme
38
+ def get_theme_dir()
39
+ #先从当前工作目录下查找theme目录
40
+ dir = File::join(@workbench, @util.local_theme_dir)
41
+ #当前有theme目录
42
+ return dir if(File::exists?(dir))
43
+
44
+ base_dir = File::join(Pathname.new(File.dirname(__FILE__)), 'themes')
45
+
46
+
47
+ #根据用户配置获取theme
48
+ theme_name = @setup.get_merged_config['theme'] || 'hyde'
49
+ theme_dir = File::join(base_dir, theme_name)
50
+
51
+ #如果没有找到对应的theme, 则
52
+ return theme_dir if(File.exists?(theme_dir))
53
+ File::join(base_dir, 'hyde')
54
+ end
55
+
56
+
57
+ #读取模板
58
+ def read_template(name)
59
+ file = File::join(@template_dir, name + '.mustache')
60
+ IO.read(file)
61
+ end
62
+
63
+ #执行生成,
64
+ #filename: 相对文件路径
65
+ def execute(type, data, auto_save = true, filename = '')
66
+ data['site'] = @setup.get_merged_config['site']
67
+ data['m2m'] = @util.get_product
68
+
69
+ template = self.read_template type
70
+ html = Mustache.render(template, data)
71
+
72
+ return html if not auto_save
73
+
74
+ file = File::join @setup.target_dir, filename
75
+ @util.write_file file, html
76
+ end
77
+ end