jekyll-ai-related 0.1.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.
checksums.yaml ADDED
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA256:
3
+ metadata.gz: c6c5970e2385796a4427d62cc98a5b8af07ed5db0fa802253be813b4056ec1d7
4
+ data.tar.gz: b3760a97b593a9698a97bf1e86c6959bb6f9eb2c391aa7a996c42704b8785911
5
+ SHA512:
6
+ metadata.gz: 88b16028bbd9e10b7bbdf446163d94d8e73ed91920f27ea0c77b84aa47171ca4d01f65e2f0ab0d52d4fb899c6ee115ff67f7f188b6a3c8558c948bd239a4c33e
7
+ data.tar.gz: f00a1813f500da3003320ec0e1a1d53c0a76ed8c643b5c85c54767d02504bb78c1eab66d07f3e1d1f566ebfa1bec842eb8cef3094cb7d1472b726f39a45bd806
data/.editorconfig ADDED
@@ -0,0 +1,24 @@
1
+ # EditorConfig is awesome: https://EditorConfig.org
2
+
3
+ # top-most EditorConfig file
4
+ root = true
5
+
6
+ [*]
7
+ indent_style = space
8
+ indent_size = 2
9
+ end_of_line = lf
10
+ charset = utf-8
11
+ trim_trailing_whitespace = true
12
+ insert_final_newline = true
13
+
14
+ [*.rb]
15
+ indent_size = 2
16
+
17
+ [*.py]
18
+ indent_size = 4
19
+
20
+ [*.sh]
21
+ indent_size = 4
22
+
23
+ [*.js]
24
+ indent_size = 2
@@ -0,0 +1,31 @@
1
+ name: Release
2
+
3
+ on:
4
+ push:
5
+ tags:
6
+ - 'v*.*.*'
7
+
8
+ permissions:
9
+ contents: write
10
+
11
+ jobs:
12
+ release:
13
+ name: Release
14
+ runs-on: ubuntu-latest
15
+ steps:
16
+ - name: Create release and upload assets
17
+ uses: softprops/action-gh-release@v2
18
+ with:
19
+ name: ${{ github.ref_name }}
20
+ tag_name: ${{ github.ref_name }}
21
+ body: |
22
+ Release notes for `${{ github.ref_name }}` are available here: https://github.com/pirafrank/jekyll-ai-related/blob/main/CHANGELOG.md
23
+ generate_release_notes: false
24
+ draft: false
25
+ prerelease: false
26
+ # Note: drafts and prereleases cannot be set as latest.
27
+ make_latest: true
28
+ fail_on_unmatched_files: true
29
+ # no need to specify GITHUB_TOKEN here, it is automatically provided by GitHub Actions
30
+ # https://github.com/softprops/action-gh-release#-customizing
31
+ # https://docs.github.com/en/actions/security-for-github-actions/security-guides/automatic-token-authentication
data/.gitignore ADDED
@@ -0,0 +1,29 @@
1
+ ### Ruby ###
2
+ *.gem
3
+ *.rbc
4
+ /.config
5
+ /coverage/
6
+ /InstalledFiles
7
+ /pkg/
8
+ /spec/reports/
9
+ /spec/examples.txt
10
+ /test/tmp/
11
+ /test/version_tmp/
12
+ /tmp/
13
+
14
+ ## Documentation cache and generated files:
15
+ /.yardoc/
16
+ /_yardoc/
17
+ /doc/
18
+ /rdoc/
19
+
20
+ ## Environment normalization:
21
+ /.bundle/
22
+ /vendor/bundle
23
+ /lib/bundler/man/
24
+
25
+ # unless supporting rvm < 1.11.0 or doing something fancy, ignore this:
26
+ .rvmrc
27
+
28
+ # Used by RuboCop. Remote config files pulled in from inherit_from directive.
29
+ .rubocop-https?--*
data/.rubocop.yml ADDED
@@ -0,0 +1,25 @@
1
+ require: rubocop-jekyll
2
+
3
+ inherit_gem:
4
+ rubocop-jekyll: .rubocop.yml
5
+
6
+ AllCops:
7
+ TargetRubyVersion: 3.2
8
+ Exclude:
9
+ - vendor/**/*
10
+
11
+ Metrics/LineLength:
12
+ Max: 154
13
+
14
+ Metrics/MethodLength:
15
+ Max: 40
16
+
17
+ Style/StringLiterals:
18
+ EnforcedStyle: double_quotes
19
+
20
+ Style/StringLiteralsInInterpolation:
21
+ EnforcedStyle: double_quotes
22
+
23
+ Style/HashSyntax:
24
+ EnforcedStyle: no_mixed_keys
25
+ EnforcedShorthandSyntax: consistent
data/.ruby-version ADDED
@@ -0,0 +1 @@
1
+ 3.2.2
data/CHANGELOG.md ADDED
@@ -0,0 +1,18 @@
1
+ # Changelog
2
+
3
+ All notable changes to this project will be documented in this file.
4
+
5
+ ## [0.1.0] - 2025-02-15
6
+
7
+ ### ๐Ÿš€ Features
8
+
9
+ - Project setup
10
+ - Supabase SQL scripts
11
+ - First full implementation
12
+
13
+ ### โš™๏ธ Miscellaneous Tasks
14
+
15
+ - Readme update
16
+ - Rakefile
17
+
18
+ <!-- generated by git-cliff -->
@@ -0,0 +1,132 @@
1
+ # Contributor Covenant Code of Conduct
2
+
3
+ ## Our Pledge
4
+
5
+ We as members, contributors, and leaders pledge to make participation in our
6
+ community a harassment-free experience for everyone, regardless of age, body
7
+ size, visible or invisible disability, ethnicity, sex characteristics, gender
8
+ identity and expression, level of experience, education, socio-economic status,
9
+ nationality, personal appearance, race, caste, color, religion, or sexual
10
+ identity and orientation.
11
+
12
+ We pledge to act and interact in ways that contribute to an open, welcoming,
13
+ diverse, inclusive, and healthy community.
14
+
15
+ ## Our Standards
16
+
17
+ Examples of behavior that contributes to a positive environment for our
18
+ community include:
19
+
20
+ * Demonstrating empathy and kindness toward other people
21
+ * Being respectful of differing opinions, viewpoints, and experiences
22
+ * Giving and gracefully accepting constructive feedback
23
+ * Accepting responsibility and apologizing to those affected by our mistakes,
24
+ and learning from the experience
25
+ * Focusing on what is best not just for us as individuals, but for the overall
26
+ community
27
+
28
+ Examples of unacceptable behavior include:
29
+
30
+ * The use of sexualized language or imagery, and sexual attention or advances of
31
+ any kind
32
+ * Trolling, insulting or derogatory comments, and personal or political attacks
33
+ * Public or private harassment
34
+ * Publishing others' private information, such as a physical or email address,
35
+ without their explicit permission
36
+ * Other conduct which could reasonably be considered inappropriate in a
37
+ professional setting
38
+
39
+ ## Enforcement Responsibilities
40
+
41
+ Community leaders are responsible for clarifying and enforcing our standards of
42
+ acceptable behavior and will take appropriate and fair corrective action in
43
+ response to any behavior that they deem inappropriate, threatening, offensive,
44
+ or harmful.
45
+
46
+ Community leaders have the right and responsibility to remove, edit, or reject
47
+ comments, commits, code, wiki edits, issues, and other contributions that are
48
+ not aligned to this Code of Conduct, and will communicate reasons for moderation
49
+ decisions when appropriate.
50
+
51
+ ## Scope
52
+
53
+ This Code of Conduct applies within all community spaces, and also applies when
54
+ an individual is officially representing the community in public spaces.
55
+ Examples of representing our community include using an official email address,
56
+ posting via an official social media account, or acting as an appointed
57
+ representative at an online or offline event.
58
+
59
+ ## Enforcement
60
+
61
+ Instances of abusive, harassing, or otherwise unacceptable behavior may be
62
+ reported to the community leaders responsible for enforcement at
63
+ [INSERT CONTACT METHOD].
64
+ All complaints will be reviewed and investigated promptly and fairly.
65
+
66
+ All community leaders are obligated to respect the privacy and security of the
67
+ reporter of any incident.
68
+
69
+ ## Enforcement Guidelines
70
+
71
+ Community leaders will follow these Community Impact Guidelines in determining
72
+ the consequences for any action they deem in violation of this Code of Conduct:
73
+
74
+ ### 1. Correction
75
+
76
+ **Community Impact**: Use of inappropriate language or other behavior deemed
77
+ unprofessional or unwelcome in the community.
78
+
79
+ **Consequence**: A private, written warning from community leaders, providing
80
+ clarity around the nature of the violation and an explanation of why the
81
+ behavior was inappropriate. A public apology may be requested.
82
+
83
+ ### 2. Warning
84
+
85
+ **Community Impact**: A violation through a single incident or series of
86
+ actions.
87
+
88
+ **Consequence**: A warning with consequences for continued behavior. No
89
+ interaction with the people involved, including unsolicited interaction with
90
+ those enforcing the Code of Conduct, for a specified period of time. This
91
+ includes avoiding interactions in community spaces as well as external channels
92
+ like social media. Violating these terms may lead to a temporary or permanent
93
+ ban.
94
+
95
+ ### 3. Temporary Ban
96
+
97
+ **Community Impact**: A serious violation of community standards, including
98
+ sustained inappropriate behavior.
99
+
100
+ **Consequence**: A temporary ban from any sort of interaction or public
101
+ communication with the community for a specified period of time. No public or
102
+ private interaction with the people involved, including unsolicited interaction
103
+ with those enforcing the Code of Conduct, is allowed during this period.
104
+ Violating these terms may lead to a permanent ban.
105
+
106
+ ### 4. Permanent Ban
107
+
108
+ **Community Impact**: Demonstrating a pattern of violation of community
109
+ standards, including sustained inappropriate behavior, harassment of an
110
+ individual, or aggression toward or disparagement of classes of individuals.
111
+
112
+ **Consequence**: A permanent ban from any sort of public interaction within the
113
+ community.
114
+
115
+ ## Attribution
116
+
117
+ This Code of Conduct is adapted from the [Contributor Covenant][homepage],
118
+ version 2.1, available at
119
+ [https://www.contributor-covenant.org/version/2/1/code_of_conduct.html][v2.1].
120
+
121
+ Community Impact Guidelines were inspired by
122
+ [Mozilla's code of conduct enforcement ladder][Mozilla CoC].
123
+
124
+ For answers to common questions about this code of conduct, see the FAQ at
125
+ [https://www.contributor-covenant.org/faq][FAQ]. Translations are available at
126
+ [https://www.contributor-covenant.org/translations][translations].
127
+
128
+ [homepage]: https://www.contributor-covenant.org
129
+ [v2.1]: https://www.contributor-covenant.org/version/2/1/code_of_conduct.html
130
+ [Mozilla CoC]: https://github.com/mozilla/diversity
131
+ [FAQ]: https://www.contributor-covenant.org/faq
132
+ [translations]: https://www.contributor-covenant.org/translations
data/Gemfile ADDED
@@ -0,0 +1,6 @@
1
+ # frozen_string_literal: true
2
+
3
+ source "https://rubygems.org"
4
+
5
+ # Specify your gem's dependencies in jekyll-ai-related.gemspec
6
+ gemspec
data/Gemfile.lock ADDED
@@ -0,0 +1,135 @@
1
+ PATH
2
+ remote: .
3
+ specs:
4
+ jekyll-ai-related (0.1.0)
5
+ httparty (~> 0.22.0)
6
+ jekyll (>= 3.7, < 5.0)
7
+ json (~> 2.7)
8
+
9
+ GEM
10
+ remote: https://rubygems.org/
11
+ specs:
12
+ addressable (2.8.7)
13
+ public_suffix (>= 2.0.2, < 7.0)
14
+ ast (2.4.2)
15
+ base64 (0.2.0)
16
+ bigdecimal (3.1.9)
17
+ colorator (1.1.0)
18
+ concurrent-ruby (1.3.5)
19
+ csv (3.3.2)
20
+ em-websocket (0.5.3)
21
+ eventmachine (>= 0.12.9)
22
+ http_parser.rb (~> 0)
23
+ eventmachine (1.2.7)
24
+ ffi (1.17.1)
25
+ ffi (1.17.1-x86_64-linux-gnu)
26
+ forwardable-extended (2.6.0)
27
+ google-protobuf (4.29.3)
28
+ bigdecimal
29
+ rake (>= 13)
30
+ google-protobuf (4.29.3-x86_64-linux)
31
+ bigdecimal
32
+ rake (>= 13)
33
+ http_parser.rb (0.8.0)
34
+ httparty (0.22.0)
35
+ csv
36
+ mini_mime (>= 1.0.0)
37
+ multi_xml (>= 0.5.2)
38
+ i18n (1.14.7)
39
+ concurrent-ruby (~> 1.0)
40
+ jekyll (4.4.1)
41
+ addressable (~> 2.4)
42
+ base64 (~> 0.2)
43
+ colorator (~> 1.0)
44
+ csv (~> 3.0)
45
+ em-websocket (~> 0.5)
46
+ i18n (~> 1.0)
47
+ jekyll-sass-converter (>= 2.0, < 4.0)
48
+ jekyll-watch (~> 2.0)
49
+ json (~> 2.6)
50
+ kramdown (~> 2.3, >= 2.3.1)
51
+ kramdown-parser-gfm (~> 1.0)
52
+ liquid (~> 4.0)
53
+ mercenary (~> 0.3, >= 0.3.6)
54
+ pathutil (~> 0.9)
55
+ rouge (>= 3.0, < 5.0)
56
+ safe_yaml (~> 1.0)
57
+ terminal-table (>= 1.8, < 4.0)
58
+ webrick (~> 1.7)
59
+ jekyll-sass-converter (3.1.0)
60
+ sass-embedded (~> 1.75)
61
+ jekyll-watch (2.2.1)
62
+ listen (~> 3.0)
63
+ json (2.10.1)
64
+ kramdown (2.5.1)
65
+ rexml (>= 3.3.9)
66
+ kramdown-parser-gfm (1.1.0)
67
+ kramdown (~> 2.0)
68
+ language_server-protocol (3.17.0.4)
69
+ liquid (4.0.4)
70
+ listen (3.9.0)
71
+ rb-fsevent (~> 0.10, >= 0.10.3)
72
+ rb-inotify (~> 0.9, >= 0.9.10)
73
+ mercenary (0.4.0)
74
+ mini_mime (1.1.5)
75
+ multi_xml (0.7.1)
76
+ bigdecimal (~> 3.1)
77
+ parallel (1.26.3)
78
+ parser (3.3.7.1)
79
+ ast (~> 2.4.1)
80
+ racc
81
+ pathutil (0.16.2)
82
+ forwardable-extended (~> 2.6)
83
+ public_suffix (6.0.1)
84
+ racc (1.8.1)
85
+ rainbow (3.1.1)
86
+ rake (13.2.1)
87
+ rb-fsevent (0.11.2)
88
+ rb-inotify (0.11.1)
89
+ ffi (~> 1.0)
90
+ regexp_parser (2.10.0)
91
+ rexml (3.4.0)
92
+ rouge (4.5.1)
93
+ rubocop (1.57.2)
94
+ json (~> 2.3)
95
+ language_server-protocol (>= 3.17.0)
96
+ parallel (~> 1.10)
97
+ parser (>= 3.2.2.4)
98
+ rainbow (>= 2.2.2, < 4.0)
99
+ regexp_parser (>= 1.8, < 3.0)
100
+ rexml (>= 3.2.5, < 4.0)
101
+ rubocop-ast (>= 1.28.1, < 2.0)
102
+ ruby-progressbar (~> 1.7)
103
+ unicode-display_width (>= 2.4.0, < 3.0)
104
+ rubocop-ast (1.38.0)
105
+ parser (>= 3.3.1.0)
106
+ rubocop-jekyll (0.14.0)
107
+ rubocop (~> 1.57.0)
108
+ rubocop-performance (~> 1.2)
109
+ rubocop-performance (1.23.1)
110
+ rubocop (>= 1.48.1, < 2.0)
111
+ rubocop-ast (>= 1.31.1, < 2.0)
112
+ ruby-progressbar (1.13.0)
113
+ safe_yaml (1.0.5)
114
+ sass-embedded (1.83.4)
115
+ google-protobuf (~> 4.29)
116
+ rake (>= 13)
117
+ sass-embedded (1.83.4-x86_64-linux-gnu)
118
+ google-protobuf (~> 4.29)
119
+ terminal-table (3.0.2)
120
+ unicode-display_width (>= 1.1.1, < 3)
121
+ unicode-display_width (2.6.0)
122
+ webrick (1.9.1)
123
+
124
+ PLATFORMS
125
+ ruby
126
+ x86_64-linux
127
+
128
+ DEPENDENCIES
129
+ bundler (~> 2.6)
130
+ jekyll-ai-related!
131
+ rake (~> 13.0)
132
+ rubocop-jekyll (~> 0.14)
133
+
134
+ BUNDLED WITH
135
+ 2.6.3
data/LICENSE.txt ADDED
@@ -0,0 +1,21 @@
1
+ The MIT License (MIT)
2
+
3
+ Copyright (c) 2025 Francesco Pira
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
13
+ all 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
21
+ THE SOFTWARE.
data/README.md ADDED
@@ -0,0 +1,133 @@
1
+ # Jekyll AI Related
2
+
3
+ [![Gem Version](https://badge.fury.io/rb/jekyll-ai-related.svg)](https://badge.fury.io/rb/jekyll-ai-related)
4
+
5
+ A [Jekyll](https://jekyllrb.com/) [command](https://jekyllrb.com/docs/plugins/commands/) plugin to generate list of related posts using AI.
6
+
7
+ The plugin uses uses OpenAI API to generate embeddings from posts content, and stores them on Supabase vector database. A query on Supabase provides a similarity score between the post and all other posts on the site. The plugin then selects the most similar posts to generate the list of related posts.
8
+
9
+ To avoid unnecessary API calls or slowing down the website generation, the plugin stores the list of related posts in the site's `_data` folder. This way you can `jekyll build` without calling the plugin or making API calls, while still having the list of related posts available as site data.
10
+
11
+ ## Getting started
12
+
13
+ 1. Setup Supabase
14
+ 2. Install the plugin
15
+ 3. Configure the plugin
16
+ 4. Run the plugin
17
+
18
+ ## Requirements
19
+
20
+ - OpenAI account and API key
21
+ - Supabase account and API key
22
+ - Supabase URL of the project where the DB is located
23
+
24
+ ### Supabase setup
25
+
26
+ Use the `create.sql` script in the `sql\supabase` folder of this repo to create the required table and functions on your Supabase project. You can run the script in the SQL editor of the Supabase dashboard.
27
+
28
+ You can always revert the changes by running the `drop.sql` script.
29
+
30
+ ## Installation
31
+
32
+ 1. Add the plugin to you Jekyll site's `Gemfile` in the `:jekyll_plugins` group:
33
+
34
+ ```Gemfile
35
+ gem 'jekyll-ai-related', git: 'https://github.com/pirafrank/jekyll-ai-related', branch: 'main'
36
+ ```
37
+
38
+ 2. Run `bundle install`
39
+
40
+ ### Update
41
+
42
+ ```sh
43
+ bundle update jekyll-ai-related
44
+ ```
45
+
46
+ ## Configuration
47
+
48
+ Sample configuration to add to your `_config.yml`:
49
+
50
+ ```yaml
51
+ jekyll-ai-related:
52
+ post_unique_field: slug
53
+ post_updated_field: date
54
+ output_path: related_posts
55
+ include_drafts: false
56
+ include_future: false
57
+ related_posts_limit: 3
58
+ related_posts_score_threshold: 0.5
59
+ ```
60
+
61
+ Configuration is optional. The plugin will use the default values if not provided.
62
+
63
+ ### Configuration options
64
+
65
+ | Option | Type | Description | Default Value |
66
+ | --- | --- | --- | --- |
67
+ | `post_unique_field` | string | A field that uniquely identifies a post | `slug` |
68
+ | `post_updated_field` | string | A field that indicates when the post was last updated | `date` |
69
+ | `output_path` | string | The subdir inside `_data` where related posts will be stored | `related_posts` |
70
+ | `include_drafts` | boolean | Whether to include drafts in the list of related posts | `false` |
71
+ | `include_future` | boolean | Whether to include future posts in the list of related posts | `false` |
72
+ | `related_posts_limit` | integer | The maximum number of related posts to extract per post | `3` |
73
+ | `related_posts_score_threshold` | float | The minimum similarity score to consider a post related | `0.5` |
74
+
75
+ **Note**: `related_posts_limit` and `related_posts_score_threshold` are used to filter the list of related posts. The plugin will return the top `related_posts_limit` posts with a similarity score greater than `related_posts_score_threshold`. A post may have 0 or more than `related_posts_limit` related posts, but only the top `related_posts_limit` will be returned, if any.
76
+
77
+ ### Advanced configuration
78
+
79
+ You can customize the unique and updated fields, for example if you have a plugin that generates a unique ID for each post, or if you have a custom field that indicates when the post was last updated.
80
+
81
+ Check the [post-metadata.rb](https://github.com/pirafrank/fpiracom/blob/8cc17a5801a73f7c8cbad4cbee099db18389b187/_plugins/post-metadata.rb) plugin of mine for an example. You can download and place it in your `_plugins` folder. It will add metadata to each `post` object and makes it accessible anywhere the `post` object is.
82
+
83
+ If you do so, you could use the following configuration:
84
+
85
+ ```yaml
86
+ jekyll-ai-related:
87
+ post_unique_field: uid
88
+ post_updated_field: most_recent_edit
89
+ ```
90
+
91
+ ## Usage
92
+
93
+ To run, the plugin needs the OpenAI and Supabase API keys, and Supabase URL. The plugin expects them as environment variables.
94
+
95
+ ```sh
96
+ export OPENAI_API_KEY="your_openai_api_key"
97
+ export SUPABASE_URL="your_supabase_url"
98
+ export SUPABASE_KEY="your_supabase_api_key"
99
+ ```
100
+
101
+ Never write API keys in your code or configuration files you commit.
102
+
103
+ Then you can run the plugin with:
104
+
105
+ ```txt
106
+ bundle exec jekyll related
107
+ ```
108
+
109
+ ## Development
110
+
111
+ Clone and run `bundle install` to get started.
112
+
113
+ Code lives in `lib/jekyll` directory. `lib/jekyll/commands/generator.rb` is the entry point of the plugin, as per Jekyll documentation. More details [here](https://jekyllrb.com/docs/plugins/commands/).
114
+
115
+ ## Contributing
116
+
117
+ [Bug reports](https://github.com/pirafrank/jekyll-ai-related/issues) and [pull requests](https://github.com/pirafrank/jekyll-ai-related/pulls) are welcome on GitHub.
118
+
119
+ ## Code of Conduct
120
+
121
+ Everyone interacting in the project's codebase, issue trackers, chat rooms and mailing lists is expected to follow the [code of conduct](https://github.com/pirafrank/jekyll-ai-related/blob/main/CODE_OF_CONDUCT.md).
122
+
123
+ ## Guarantee
124
+
125
+ This plugin is provided as is, without any guarantee. Use at your own risk.
126
+
127
+ ## Disclaimer
128
+
129
+ This plugin uses OpenAI API and Supabase, and you are responsible for complying with their respective terms of service. This plugin is not affiliated with OpenAI or Supabase.
130
+
131
+ ## License
132
+
133
+ The gem is available as open source under the terms of the [MIT License](https://opensource.org/licenses/MIT).
data/Rakefile ADDED
@@ -0,0 +1,31 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "bundler/gem_tasks"
4
+ require "rubocop/rake_task"
5
+
6
+ RuboCop::RakeTask.new
7
+
8
+ task :default do
9
+ sh "rake -AT"
10
+ end
11
+
12
+ task lint: :rubocop
13
+
14
+ task :changelog do
15
+ sh "git cliff --tag #{Gem::Specification.load('jekyll-ai-related.gemspec').version} -o CHANGELOG.md"
16
+ end
17
+
18
+ task :mkrelease do
19
+ version = Gem::Specification.load("jekyll-ai-related.gemspec").version
20
+ gem_file = "jekyll-ai-related-#{version}.gem"
21
+ sh "git cliff --tag #{version} -o CHANGELOG.md"
22
+ sh "git add CHANGELOG.md"
23
+ sh "git commit -m 'chore: update CHANGELOG.md'"
24
+ sh "git tag -s -a -m 'v#{version}' #{version}"
25
+ sh "git push origin #{version}"
26
+ sh "gem build jekyll-ai-related.gemspec"
27
+ end
28
+
29
+ task :publish do
30
+ sh "gem push #{gem_file}"
31
+ end
data/cliff.toml ADDED
@@ -0,0 +1,84 @@
1
+ # git-cliff ~ default configuration file
2
+ # https://git-cliff.org/docs/configuration
3
+ #
4
+ # Lines starting with "#" are comments.
5
+ # Configuration options are organized into tables and keys.
6
+ # See documentation for more information on available options.
7
+
8
+ [changelog]
9
+ # template for the changelog header
10
+ header = """
11
+ # Changelog\n
12
+ All notable changes to this project will be documented in this file.\n
13
+ """
14
+ # template for the changelog body
15
+ # https://keats.github.io/tera/docs/#introduction
16
+ body = """
17
+ {% if version %}\
18
+ ## [{{ version | trim_start_matches(pat="v") }}] - {{ timestamp | date(format="%Y-%m-%d") }}
19
+ {% else %}\
20
+ ## [unreleased]
21
+ {% endif %}\
22
+ {% for group, commits in commits | group_by(attribute="group") %}
23
+ ### {{ group | striptags | trim | upper_first }}
24
+ {% for commit in commits %}
25
+ - {% if commit.scope %}*({{ commit.scope }})* {% endif %}\
26
+ {% if commit.breaking %}[**breaking**] {% endif %}\
27
+ {{ commit.message | upper_first }}\
28
+ {% endfor %}
29
+ {% endfor %}\n
30
+ """
31
+ # template for the changelog footer
32
+ footer = """
33
+ <!-- generated by git-cliff -->
34
+ """
35
+ # remove the leading and trailing s
36
+ trim = true
37
+ # postprocessors
38
+ postprocessors = [
39
+ # { pattern = '<REPO>', replace = "https://github.com/orhun/git-cliff" }, # replace repository URL
40
+ ]
41
+ # render body even when there are no releases to process
42
+ # render_always = true
43
+ # output file path
44
+ # output = "test.md"
45
+
46
+ [git]
47
+ # parse the commits based on https://www.conventionalcommits.org
48
+ conventional_commits = true
49
+ # filter out the commits that are not conventional
50
+ filter_unconventional = true
51
+ # process each line of a commit as an individual commit
52
+ split_commits = false
53
+ # regex for preprocessing the commit messages
54
+ commit_preprocessors = [
55
+ # Replace issue numbers
56
+ #{ pattern = '\((\w+\s)?#([0-9]+)\)', replace = "([#${2}](<REPO>/issues/${2}))"},
57
+ # Check spelling of the commit with https://github.com/crate-ci/typos
58
+ # If the spelling is incorrect, it will be automatically fixed.
59
+ #{ pattern = '.*', replace_command = 'typos --write-changes -' },
60
+ ]
61
+ # regex for parsing and grouping commits
62
+ commit_parsers = [
63
+ { message = "^feat", group = "<!-- 0 -->๐Ÿš€ Features" },
64
+ { message = "^fix", group = "<!-- 1 -->๐Ÿ› Bug Fixes" },
65
+ { message = "^doc", group = "<!-- 3 -->๐Ÿ“š Documentation" },
66
+ { message = "^perf", group = "<!-- 4 -->โšก Performance" },
67
+ { message = "^refactor", group = "<!-- 2 -->๐Ÿšœ Refactor" },
68
+ { message = "^style", group = "<!-- 5 -->๐ŸŽจ Styling" },
69
+ { message = "^test", group = "<!-- 6 -->๐Ÿงช Testing" },
70
+ { message = "^chore\\(release\\): prepare for", skip = true },
71
+ { message = "^chore\\(deps.*\\)", skip = true },
72
+ { message = "^chore\\(pr\\)", skip = true },
73
+ { message = "^chore\\(pull\\)", skip = true },
74
+ { message = "^chore|^ci", group = "<!-- 7 -->โš™๏ธ Miscellaneous Tasks" },
75
+ { body = ".*security", group = "<!-- 8 -->๐Ÿ›ก๏ธ Security" },
76
+ { message = "^revert", group = "<!-- 9 -->โ—€๏ธ Revert" },
77
+ { message = ".*", group = "<!-- 10 -->๐Ÿ’ผ Other" },
78
+ ]
79
+ # filter out the commits that are not matched by commit parsers
80
+ filter_commits = false
81
+ # sort the tags topologically
82
+ topo_order = false
83
+ # sort the commits inside sections by oldest/newest order
84
+ sort_commits = "oldest"