fronde 0.3.4 → 0.5.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.
Files changed (62) hide show
  1. checksums.yaml +4 -4
  2. data/bin/fronde +15 -30
  3. data/lib/ext/nil_time.rb +25 -0
  4. data/lib/ext/r18n.rb +37 -0
  5. data/lib/ext/time.rb +39 -0
  6. data/lib/ext/time_no_time.rb +23 -0
  7. data/lib/fronde/cli/commands.rb +97 -104
  8. data/lib/fronde/cli/data/Rakefile +8 -0
  9. data/lib/fronde/cli/data/config.yml +13 -0
  10. data/lib/fronde/cli/data/gitignore +6 -0
  11. data/lib/fronde/cli/data/zsh_completion +37 -0
  12. data/lib/fronde/cli/helpers.rb +55 -0
  13. data/lib/fronde/cli/opt_parse.rb +140 -0
  14. data/lib/fronde/cli/throbber.rb +110 -0
  15. data/lib/fronde/cli.rb +42 -42
  16. data/lib/fronde/config/data/org-config.el +25 -0
  17. data/lib/fronde/config/data/ox-fronde.el +158 -0
  18. data/lib/fronde/config/data/themes/umaneti/css/htmlize.css +364 -0
  19. data/lib/fronde/config/data/themes/umaneti/css/style.css +250 -0
  20. data/lib/fronde/config/data/themes/umaneti/img/bottom.png +0 -0
  21. data/lib/fronde/config/data/themes/umaneti/img/content.png +0 -0
  22. data/lib/fronde/config/data/themes/umaneti/img/tic.png +0 -0
  23. data/lib/fronde/config/data/themes/umaneti/img/top.png +0 -0
  24. data/lib/fronde/config/helpers.rb +62 -0
  25. data/lib/fronde/config/lisp.rb +80 -0
  26. data/lib/fronde/config.rb +148 -98
  27. data/lib/fronde/emacs.rb +23 -20
  28. data/lib/fronde/index/atom_generator.rb +55 -66
  29. data/lib/fronde/index/data/all_tags.org +19 -0
  30. data/lib/fronde/index/data/template.org +26 -0
  31. data/lib/fronde/index/data/template.xml +37 -0
  32. data/lib/fronde/index/org_generator.rb +72 -88
  33. data/lib/fronde/index.rb +57 -86
  34. data/lib/fronde/org/file.rb +299 -0
  35. data/lib/fronde/org/file_extracter.rb +101 -0
  36. data/lib/fronde/org.rb +105 -0
  37. data/lib/fronde/preview.rb +43 -39
  38. data/lib/fronde/slug.rb +54 -0
  39. data/lib/fronde/source/gemini.rb +34 -0
  40. data/lib/fronde/source/html.rb +67 -0
  41. data/lib/fronde/source.rb +209 -0
  42. data/lib/fronde/sync/neocities.rb +220 -0
  43. data/lib/fronde/sync/rsync.rb +46 -0
  44. data/lib/fronde/sync.rb +32 -0
  45. data/lib/fronde/templater.rb +101 -71
  46. data/lib/fronde/version.rb +1 -1
  47. data/lib/tasks/cli.rake +33 -0
  48. data/lib/tasks/org.rake +58 -43
  49. data/lib/tasks/site.rake +66 -31
  50. data/lib/tasks/sync.rake +37 -40
  51. data/lib/tasks/tags.rake +11 -7
  52. data/locales/en.yml +61 -14
  53. data/locales/fr.yml +69 -14
  54. metadata +77 -95
  55. data/lib/fronde/config/lisp_config.rb +0 -340
  56. data/lib/fronde/config/org-config.el +0 -19
  57. data/lib/fronde/config/ox-fronde.el +0 -121
  58. data/lib/fronde/org_file/class_methods.rb +0 -72
  59. data/lib/fronde/org_file/extracter.rb +0 -72
  60. data/lib/fronde/org_file/htmlizer.rb +0 -43
  61. data/lib/fronde/org_file.rb +0 -298
  62. data/lib/fronde/utils.rb +0 -229
@@ -0,0 +1,140 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Fronde
4
+ module CLI
5
+ # Helper code to help build the fronde option parser
6
+ module OptParse
7
+ # @return [Hash] the possible ~fronde~ options and their
8
+ # configuration
9
+ FRONDE_OPTIONS = {
10
+ '-a' => { long: 'author' },
11
+ '-f' => { long: 'force', boolean: true },
12
+ '-h' => { long: 'help', boolean: true, method: :on_tail,
13
+ help: R18n.t.fronde.bin.options.help },
14
+ '-l' => { long: 'lang', keyword: 'LOCALE' },
15
+ '-o' => { long: 'output', keyword: 'FORMAT', choices: %w[gemini html] },
16
+ '-t' => { long: 'title' },
17
+ '-v' => { long: 'verbose', boolean: true, method: :on_tail },
18
+ '-V' => { long: 'version', boolean: true, method: :on_tail,
19
+ help: R18n.t.fronde.bin.options.version }
20
+ }.freeze
21
+
22
+ # TODO: jekyll new [path] / jekyll build / jekyll clean / jekyll serve
23
+ # TODO: hugo new site [path] / hugo / hugo new content / hugo server
24
+ # TODO: zola init [path] / zola build --root path_to_project / zola serve
25
+
26
+ # @return [Hash] the possible ~fronde~ subcommands and their
27
+ # configuration
28
+ FRONDE_COMMANDS = {
29
+ 'new' => { opts: ['-a', '-l', '-o', '-t', '-v'], label: 'new <path>' },
30
+ 'init' => { alias: 'new' },
31
+ 'update' => {},
32
+ 'config' => { alias: 'update' },
33
+ 'preview' => {},
34
+ 'open' => { opts: ['-a', '-l', '-t', '-v'], label: 'open <path>' },
35
+ 'edit' => { alias: 'open' },
36
+ 'build' => { opts: ['-f'] },
37
+ 'publish' => {},
38
+ 'help' => {},
39
+ 'basic' => { opts: ['-h', '-V'], label: '<command>' }
40
+ }.freeze
41
+
42
+ class << self
43
+ # Returns the short and long options specification for a given
44
+ # short option.
45
+ #
46
+ # This method use the {Fronde::CLI::OptParse::FRONDE_OPTIONS}
47
+ # Hash to retrieve corresponding values.
48
+ #
49
+ # @example
50
+ # spec = Fronde::CLI::OptParse.decorate_option('-a')
51
+ # => ['-a AUTHOR', '--author AUTHOR']
52
+ #
53
+ # @param short [String] the short option to decorate
54
+ # @return [Array] the short and long specification for an option
55
+ def decorate_option(short)
56
+ opt = FRONDE_OPTIONS[short]
57
+ long = "--#{opt[:long]}"
58
+ if opt[:boolean]
59
+ config = [short, long]
60
+ else
61
+ key = opt[:keyword] || opt[:long].upcase
62
+ config = [short, format('%<long>s %<key>s', long: long, key: key)]
63
+ end
64
+ config.push opt[:choices], opt[:help]
65
+ config.compact
66
+ end
67
+
68
+ # Returns the ~fronde~ help summary for a given command.
69
+ #
70
+ # @param command [String] the command for which a summary
71
+ # should be given
72
+ # @return [String]
73
+ def summarize_command(command)
74
+ (FRONDE_COMMANDS[command][:opts] || []).map do |k|
75
+ short, long = decorate_option(k)
76
+ opt = FRONDE_OPTIONS[k]
77
+ label = [short, long].join(', ')
78
+ line = [format(' %<opt>s', opt: label).ljust(30), opt[:help]]
79
+ choices = opt[:choices]
80
+ line << "(#{choices.join(', ')})" if choices
81
+ line.compact.join(' ')
82
+ end.join("\n")
83
+ end
84
+
85
+ def help_command_body(command)
86
+ command_opts_doc = summarize_command(command)
87
+ return '' if command_opts_doc == ''
88
+
89
+ body = [R18n.t.fronde.bin.options.cmd_title, command_opts_doc]
90
+ if command == 'basic'
91
+ body += ['', R18n.t.fronde.bin.commands.cmd_title, list_commands]
92
+ end
93
+ body.join("\n")
94
+ end
95
+
96
+ # Returns a formatted list of available commands for ~fronde~.
97
+ #
98
+ # @return [String]
99
+ def list_commands
100
+ FRONDE_COMMANDS.filter_map do |cmd, opt|
101
+ next if cmd == 'basic'
102
+
103
+ line = [' ', cmd.ljust(10)]
104
+ if opt.has_key? :alias
105
+ line << R18n.t.fronde.bin.commands.alias(opt[:alias])
106
+ else
107
+ line << R18n.t.fronde.bin.commands[cmd]
108
+ end
109
+ line.join(' ')
110
+ end.join("\n")
111
+ end
112
+
113
+ # Returns the real command name for a given command, which may be
114
+ # an alias.
115
+ #
116
+ # @param command [String] the command to resolve
117
+ # @return [String]
118
+ def resolve_possible_alias(command)
119
+ return 'basic' unless FRONDE_COMMANDS.include?(command)
120
+
121
+ cmd_opt = FRONDE_COMMANDS[command]
122
+ return cmd_opt[:alias] if cmd_opt.has_key?(:alias)
123
+
124
+ command
125
+ end
126
+
127
+ # Returns the given command options.
128
+ #
129
+ # This method will first try to resolve command alias, if any.
130
+ #
131
+ # @param command [String] the command, which options should be returned
132
+ # @return [Hash] the command options
133
+ def command_options(command)
134
+ cmd = resolve_possible_alias command
135
+ FRONDE_COMMANDS[cmd].merge(name: cmd)
136
+ end
137
+ end
138
+ end
139
+ end
140
+ end
@@ -0,0 +1,110 @@
1
+ # frozen_string_literal: true
2
+
3
+ require 'rainbow'
4
+
5
+ module Fronde
6
+ module CLI
7
+ # Decorations for the command line
8
+ class Throbber
9
+ # @return [Hash] the possible throbber themes
10
+ THROBBER_FRAMES = {
11
+ 'basic' => '-\|/',
12
+ 'basicdots' => '⋯⋱⋮⋰',
13
+ 'moon' => '🌑🌒🌓🌔🌕🌖🌗🌘',
14
+ 'clock' => '🕛🕐🕑🕒🕓🕔🕕🕖🕗🕘🕙🕚',
15
+ 'bricks' => '⣷⣯⣟⡿⢿⣻⣽⣾',
16
+ 'points' => '·⁘⁛⁘',
17
+ 'quadrant' => '▙▛▜▟',
18
+ 'default' => ['⠁ ⠂ ⠄ ⡀ ⠄ ⠂ ⠁', '⠂ ⠁ ⠂ ⠄ ⡀ ⠄ ⠂', '⠄ ⠂ ⠁ ⠂ ⠄ ⡀ ⠄',
19
+ '⡀ ⠄ ⠂ ⠁ ⠂ ⠄ ⡀', '⠄ ⡀ ⠄ ⠂ ⠁ ⠂ ⠄', '⠂ ⠄ ⡀ ⠄ ⠂ ⠁ ⠂']
20
+ }.freeze
21
+
22
+ def initialize(thread, message)
23
+ @frames = select_frames
24
+ @term_width = terminal_width
25
+ @thread = thread
26
+ @thread.abort_on_exception = false
27
+ @thread.report_on_exception = false
28
+ @message = message
29
+ end
30
+
31
+ def run
32
+ thread_loop
33
+ rescue RuntimeError => e
34
+ show_error
35
+ raise e
36
+ # :nocov: not sure how to emulate a Ctrl+c in rspec
37
+ rescue Interrupt => e
38
+ show_message Rainbow(R18n.t.fronde.bin.interrupted).red, "\n"
39
+ raise e
40
+ # :nocov:
41
+ else
42
+ show_message Rainbow(R18n.t.fronde.bin.done).green, "\n"
43
+ end
44
+
45
+ class << self
46
+ # Animates strings in the user console to alert him that something
47
+ # is running in the background.
48
+ #
49
+ # The animation is chosen among a bunch of themes, with the
50
+ # configuration option ~throbber~ (retrieved via
51
+ # {Fronde::Config::Store#get}).
52
+ #
53
+ # @example
54
+ # long_stuff = Thread.new { very_long_operation }
55
+ # Fronde::CLI::Throbber.run(long_stuff, 'Computing hard stuff:')
56
+ #
57
+ # @param thread [Thread] the long-running operation to decorate
58
+ # @param message [String] the message to display before the throbber
59
+ # @return [void]
60
+ def run(thread, message)
61
+ throbber = new(thread, message)
62
+ throbber.run
63
+ end
64
+ end
65
+
66
+ private
67
+
68
+ def thread_loop
69
+ frames_len = @frames.length
70
+ current = 0
71
+ while @thread.alive?
72
+ sleep 0.1
73
+ show_message @frames[current % frames_len]
74
+ current += 1
75
+ end
76
+ @thread.join # Ensure any inner exception is re-raised
77
+ end
78
+
79
+ def terminal_width
80
+ # Not a tty. Docker?
81
+ return 0 unless system('test -t 0')
82
+
83
+ `stty size`.strip.split[1].to_i - 1
84
+ end
85
+
86
+ def show_message(suffix, end_of_line = "\r")
87
+ message = "#{@message} #{suffix}".ljust(@term_width)
88
+ print "#{message}#{end_of_line}"
89
+ end
90
+
91
+ def show_error
92
+ warn(
93
+ format(
94
+ "%<message>s %<label>s\n%<explanation>s",
95
+ message: @message,
96
+ label: Rainbow(R18n.t.fronde.error.bin.label).bold.red,
97
+ explanation: Rainbow(R18n.t.fronde.error.bin.explanation).bold
98
+ )
99
+ )
100
+ end
101
+
102
+ def select_frames
103
+ model = Fronde::CONFIG.get 'throbber', 'default'
104
+ model = 'default' unless THROBBER_FRAMES.has_key?(model)
105
+
106
+ THROBBER_FRAMES[model]
107
+ end
108
+ end
109
+ end
110
+ end
data/lib/fronde/cli.rb CHANGED
@@ -1,60 +1,60 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  require 'rake'
4
- require 'fronde/cli/commands'
4
+ require_relative 'cli/commands'
5
5
 
6
6
  module Fronde
7
- # Fronde CLI app
8
- class CLI
9
- def initialize(opts = {})
10
- @options = { verbose: false }.merge(opts)
11
- init_required_files
12
- init_rake
13
- end
7
+ module CLI
8
+ # Fronde CLI app
9
+ class App
10
+ def initialize(opts = {})
11
+ @options = { verbose: false }.merge(opts)
12
+ @command = @rake = nil
13
+ @argv = []
14
+ end
14
15
 
15
- include Fronde::CLICommands
16
+ include Commands
16
17
 
17
- private
18
+ def run(argv)
19
+ @argv = argv
20
+ @command = OptParse.resolve_possible_alias(@argv.shift || 'basic')
18
21
 
19
- def init_required_files
20
- init_rakefile unless File.exist?('Rakefile')
21
- init_gitignore unless File.exist?('.gitignore')
22
- end
22
+ if help_param_given?
23
+ return 2 if @options[:recover_from_error]
23
24
 
24
- def init_rake
25
- @rake = Rake.application
26
- Rake.verbose(false) unless @options[:verbose]
27
- @rake.raw_load_rakefile
28
- end
25
+ return true
26
+ end
29
27
 
30
- def init_rakefile
31
- rakefile = <<~RAKE
32
- # frozen_string_literal: true
28
+ init_rake if %w[build preview publish].include?(@command)
33
29
 
34
- require 'fronde/config'
35
- require 'r18n-core'
30
+ method = :"fronde_#{@command}"
31
+ return 2 if method_unknown?(method)
36
32
 
37
- fronde_spec = Gem::Specification.find_by_name 'fronde'
38
- R18n.default_places = "\#{fronde_spec.gem_dir}/locales"
39
- R18n.set(Fronde::Config.get('lang', 'en'))
40
- R18n::Filters.on(:named_variables)
33
+ send method
34
+ end
41
35
 
42
- Dir.glob("\#{fronde_spec.gem_dir}/lib/tasks/*.rake").each { |r| import r }
36
+ private
43
37
 
44
- task default: 'site:build'
45
- RAKE
46
- File.write 'Rakefile', rakefile
47
- end
38
+ def init_rake
39
+ @rake = Rake.application
40
+ Rake.verbose(false) unless @options[:verbose]
41
+ @rake.load_rakefile
42
+ end
43
+
44
+ def help_param_given?
45
+ return false unless @options[:help]
46
+
47
+ fronde_help
48
+ true
49
+ end
50
+
51
+ def method_unknown?(method)
52
+ return false if respond_to?(method)
48
53
 
49
- def init_gitignore
50
- gitignore = <<~GITIGNORE
51
- .dir-locals.el
52
- Rakefile
53
- lib
54
- public_html
55
- var
56
- GITIGNORE
57
- File.write '.gitignore', gitignore
54
+ warn R18n.t.fronde.error.bin.no_command
55
+ fronde_help
56
+ true
57
+ end
58
58
  end
59
59
  end
60
60
  end
@@ -0,0 +1,25 @@
1
+ ;; Add org-mode to load path
2
+ (add-to-list 'load-path (expand-file-name "org-{{ org_version }}/lisp" "{{ work_dir }}/lib"))
3
+ ;; Load last version of htmlize.el
4
+ (load-file (expand-file-name "htmlize.el" "{{ work_dir }}/lib"))
5
+
6
+ ;; Current project options
7
+ (setq fronde-version "{{ version }}"
8
+ fronde-current-work-dir "{{ work_dir }}"
9
+ fronde-domain "{{ domain }}"
10
+ user-mail-address "{{ author.email }}"
11
+ user-full-name "{{ author.name }}"
12
+ org-html-metadata-timestamp-format "{{ long_date_fmt }}"
13
+ org-gmi-timestamp-format "{{ long_date_fmt }}"
14
+ org-publish-project-alist
15
+ `({% for project in all_projects -%}
16
+ ("{{ project.name }}"
17
+ {%- for attribute in project.attributes %}
18
+ :{{ attribute[0] }} {{ attribute[1] | cast_lisp_value: attribute[0] }}
19
+ {%- endfor %})
20
+ {% endfor -%}
21
+ ("website" :components ("{{ all_projects | map: 'name' | join: '" "' | remove: '" "tags' }}"))))
22
+
23
+ ;; Load fronde lib
24
+ (load-file (expand-file-name "ox-gmi.el" "{{ work_dir }}/lib"))
25
+ (load-file (expand-file-name "ox-fronde.el" "{{ fronde_data_dir }}"))
@@ -0,0 +1,158 @@
1
+ ;;; ox-fronde.el --- Fronde Gem specific helpers for Org Export Engine -*- lexical-binding: t; -*-
2
+
3
+ ;; Copyright (C) 2011-2019 Free Software Foundation, Inc.
4
+
5
+ ;; Author: Étienne Deparis <etienne at depar dot is>
6
+ ;; Keywords: org, export
7
+
8
+ ;; This file is not part of GNU Emacs.
9
+
10
+ ;; GNU Emacs is free software: you can redistribute it and/or modify
11
+ ;; it under the terms of the GNU General Public License as published by
12
+ ;; the Free Software Foundation, either version 3 of the License, or
13
+ ;; (at your option) any later version.
14
+
15
+ ;; GNU Emacs is distributed in the hope that it will be useful,
16
+ ;; but WITHOUT ANY WARRANTY; without even the implied warranty of
17
+ ;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18
+ ;; GNU General Public License for more details.
19
+
20
+ ;; You should have received a copy of the GNU General Public License
21
+ ;; along with GNU Emacs. If not, see <https://www.gnu.org/licenses/>.
22
+
23
+ ;;; Commentary:
24
+
25
+ ;; This library implements specific helpers function, needed by the Ruby
26
+ ;; Gem Fronde, which offers an easy way to publish a static website
27
+ ;; using Org files as sources.
28
+
29
+ ;;; Code:
30
+
31
+ (require 'org)
32
+ (require 'ox-html)
33
+ (require 'ox-gmi)
34
+
35
+ ;;; Function Declarations
36
+
37
+ (defvar fronde-version ""
38
+ "Version of the current fronde installation.")
39
+
40
+ (defvar fronde-current-work-dir nil
41
+ "Location of the current fronde website base directory.")
42
+
43
+ (defvar fronde-domain ""
44
+ "Target domain with scheme of the current fronde installation.")
45
+
46
+ (defvar fronde-org-temp-dir nil
47
+ "Location of the local Org temporary directory.
48
+ This is where to place org timestamps and id locations.")
49
+
50
+ (defun fronde--format-rich-keywords (info function)
51
+ "Extract keywords from INFO and apply FUNCTION on them.
52
+ FUNCTION is expected to format each keyword for a rich display for the
53
+ current export backend. FUNCTION must receive 3 arguments: the current
54
+ KEYWORD, its related SLUG and the current project BASE-URI."
55
+ (let ((base-uri (plist-get info :fronde-base-uri))
56
+ (current-path (symbol-file 'fronde--format-rich-keywords))
57
+ sluglib)
58
+ (when current-path
59
+ (setq sluglib
60
+ (expand-file-name
61
+ (format "%s../../slug" (file-name-directory current-path)))))
62
+ (mapcar
63
+ (lambda (k)
64
+ (let ((slug (if sluglib
65
+ (string-trim-right
66
+ (shell-command-to-string
67
+ (format "ruby -r %s -e \"puts Fronde::Slug.slug '%s'\""
68
+ (shell-quote-argument sluglib)
69
+ (shell-quote-argument k))))
70
+ k)))
71
+ (funcall function k slug base-uri)))
72
+ (split-string
73
+ (org-export-data (plist-get info :keywords) info)
74
+ ",+ *"))))
75
+
76
+ (defun fronde--org-html-format-spec (upstream info)
77
+ "Advise UPSTREAM to return format specification for preamble and postamble.
78
+ INFO is a plist used as a communication channel."
79
+ (let ((output (funcall upstream info)))
80
+ (push `(?A . ,(format "<span class=\"author\">%s</span>"
81
+ (org-export-data (plist-get info :author) info)))
82
+ output)
83
+ (push `(?k . ,(org-export-data (plist-get info :keywords) info)) output)
84
+ (push `(?K . ,(format "<ul class=\"keywords-list\">\n%s</ul>"
85
+ (apply #'concat
86
+ (fronde--format-rich-keywords
87
+ info
88
+ (lambda (k slug base-uri)
89
+ (format "<li class=\"keyword\"><a href=\"%stags/%s.html\">%s</a></li>\n"
90
+ base-uri slug k))))))
91
+ output)
92
+ (push `(?l . ,(org-export-data (plist-get info :language) info)) output)
93
+ (push `(?n . ,(format "Fronde %s" fronde-version)) output)
94
+ (push `(?N . ,(format "<a href=\"https://etienne.depar.is/fronde/\">Fronde</a> %s" fronde-version)) output)
95
+ (push `(?x . ,(org-export-data (plist-get info :description) info)) output)
96
+ (push `(?X . ,(format "<p>%s</p>"
97
+ (org-export-data (plist-get info :description) info)))
98
+ output)))
99
+
100
+ (defun fronde--org-gmi-format-spec (upstream info)
101
+ "Advise UPSTREAM to return format specification for gemini postamble.
102
+ INFO is a plist used as a communication channel."
103
+ (let ((output (funcall upstream info)))
104
+ (push `(?K . ,(org-gmi--build-links-list
105
+ (fronde--format-rich-keywords
106
+ info
107
+ (lambda (k slug base-uri)
108
+ (list (format "%stags/%s.gmi" base-uri slug)
109
+ (format "🏷️ %s" k))))))
110
+ output)
111
+ (push `(?n . ,(format "Fronde %s" fronde-version)) output)))
112
+
113
+ (defun fronde--org-i18n-export (link description backend)
114
+ "Export the given i18n LINK with its DESCRIPTION for the current BACKEND."
115
+ (let* ((splitted-link (split-string link "::"))
116
+ (path (car splitted-link))
117
+ (desc (or description path))
118
+ (lang (cadr splitted-link)))
119
+ (pcase backend
120
+ (`html (if lang
121
+ (format "<a href=\"%s\" hreflang=\"%s\">%s</a>"
122
+ path lang desc)
123
+ (format "<a href=\"%s\">%s</a>" path desc)))
124
+ (_ nil))))
125
+
126
+ (defun fronde--org-i18n-follow (link)
127
+ "Visit the given i18n LINK."
128
+ (browse-url (car (split-string link "::"))))
129
+
130
+ (org-link-set-parameters "i18n"
131
+ :export #'fronde--org-i18n-export
132
+ :follow #'fronde--org-i18n-follow)
133
+
134
+
135
+ ;;; Set configuration options
136
+
137
+ (setq fronde-org-temp-dir (expand-file-name "var/tmp" fronde-current-work-dir)
138
+ org-publish-timestamp-directory (expand-file-name "timestamps/" fronde-org-temp-dir)
139
+ org-id-locations-file (expand-file-name "id-locations.el" fronde-org-temp-dir)
140
+ make-backup-files nil
141
+ enable-local-variables :all
142
+ org-confirm-babel-evaluate nil
143
+ org-export-with-broken-links t
144
+ org-html-doctype "html5"
145
+ org-html-html5-fancy t
146
+ org-html-htmlize-output-type 'css
147
+ org-html-text-markup-alist '((bold . "<strong>%s</strong>")
148
+ (code . "<code>%s</code>")
149
+ (italic . "<em>%s</em>")
150
+ (strike-through . "<del>%s</del>")
151
+ (underline . "<span class=\"underline\">%s</span>")
152
+ (verbatim . "<code>%s</code>")))
153
+ (advice-add 'org-html-format-spec :around #'fronde--org-html-format-spec)
154
+ (advice-add 'org-gmi--format-spec :around #'fronde--org-gmi-format-spec)
155
+
156
+ (provide 'ox-fronde)
157
+
158
+ ;;; ox-fronde.el ends here