10083 Commits

Author SHA1 Message Date
68a9b46726 full width banner image
Some checks failed
tests / tests (0, 5) (push) Has been cancelled
tests / tests (1, 5) (push) Has been cancelled
tests / tests (2, 5) (push) Has been cancelled
tests / tests (3, 5) (push) Has been cancelled
tests / tests (4, 5) (push) Has been cancelled
tests / coveralls (push) Has been cancelled
schema / schema (push) Has been cancelled
2025-12-11 11:28:59 +03:00
9a52ec378f add KES currency
Some checks failed
schema / schema (push) Has been cancelled
tests / tests (0, 5) (push) Has been cancelled
tests / tests (1, 5) (push) Has been cancelled
tests / tests (2, 5) (push) Has been cancelled
tests / tests (3, 5) (push) Has been cancelled
tests / tests (4, 5) (push) Has been cancelled
tests / coveralls (push) Has been cancelled
2025-12-10 21:18:23 +03:00
2492347fa6 basic customization
Some checks failed
schema / schema (push) Has been cancelled
tests / tests (0, 5) (push) Has been cancelled
tests / tests (1, 5) (push) Has been cancelled
tests / tests (2, 5) (push) Has been cancelled
tests / tests (3, 5) (push) Has been cancelled
tests / tests (4, 5) (push) Has been cancelled
tests / coveralls (push) Has been cancelled
2025-12-10 17:21:40 +03:00
Javi Martín
c0624cd19b Release version 2.4.1 2025-11-17 18:02:46 +01:00
Javi Martín
5a432da498 Update old usages of investments JSON data
We aren't using these properties since commit 3fa3c90db. An old test was
failing when checking for Axe accessibility issues because of this.
2025-11-17 15:45:28 +01:00
Javi Martín
288f62cdd2 Use coordinates as marker labels when there's only one mappable
When editing/showing a proposal or an investment, the most relevant
information regarding the marker are the coordinates. The title of the
proposal or investment is redundant because we already know the marker
is about that proposal/investment.

There's one problem with this approach, though: when editing a proposal
or an investment, the aria-label of the marker isn't updated
automatically when we move the marker to a different place. This
behaviour will only affect people who use both a screen reader and a
mouse, since keyboard users can't change the position of the marker in
the first place. We'll deal with this issue when we make it possible to
change the position of a marker using the keyboard.
2025-11-17 15:39:36 +01:00
Javi Martín
99696cb302 Add aria-label to markers in admin map settings
We forgot to do so in commit b896fc4bb. Back then, we said:

> Note that we aren't providing a proper aria-label for markers on the
> map we use in the form to create a proposal or an investment. Adding
> one isn't trivial given the current code, and keyboard users can't add
> a marker in the first place. We'll have to revisit this issue when we
> add keyboard support for this.

However, in the admin section, the marker is already there, so it should
have a label. In this case, we're using the coordinates as label because
it's the most relevant text for the marker in the context of a form. We
could also use "Default map location" instead, but that information is
already present on the page.

Axe was reporting the same accessibility error we mentioned in commit
b896fc4bb in this situation.
2025-11-17 15:39:36 +01:00
Javi Martín
1693aa5d9c Use render_map to render the admin settings map
This way we remove duplication.

Note that to check whether to render the button to remove a marker,
we're checking whether the map location belongs to a mappable. This
means we're changing the code that renders the map in the "new proposal"
and "new investment" forms so the map location belongs to a proposal or
investment. We're association the map location to a new record because
writing something like:

```
def map_location
  proposal.map_location || MapLocation.new(proposal: proposal)
end
```

Would change the `proposal` object because of the way Rails treats
non-persisted `has_one` associations. Although probably safe in this
case, changing an object when rendering a view could have side effects.

Also note that we're changing the HTML ID of the map element from
`admin-map` to `new_map_location` (the latter is returned by the
`dom_id` method).  We were only using this ID in tests since commit
289426c1c, so changing it doesn't really affect us.
2025-11-17 15:39:36 +01:00
Javi Martín
8a575ae83c Remove duplicate map location translations
We were using the same texts twice. For the remove marker label text,
however, we were using the text defined in proposals for both proposals
and investments.

Ideally the translation keys for these texts would go in another
namespace, since they no longer refer to just proposals. However,
renaming the translation keys would mean losing the existing
translations in every language we manage through Crowdin. So we aren't
doing so.
2025-11-17 15:39:31 +01:00
Javi Martín
b9adef481a Simplify variable name in map location fields
The `m_l` prefix isn't really necessary when we're talking about map
locations, and sometimes when searching the project I think `m_l_`
stands for "machine learning" and get confused.
2025-11-17 15:37:20 +01:00
Javi Martín
29e5adc233 Move map location fields partial to a component
This way it'll be easier to test it and refactor it.
2025-11-17 15:37:06 +01:00
Javi Martín
67e00654bd Extract methods to get map location in form components
This way changing them will be easier.
2025-11-17 15:28:57 +01:00
Javi Martín
8b3ac5ac97 Use a legend instead of a label in map location fields
The label was invalid HTML since it wasn't referencing any existing
element.
2025-11-17 15:28:52 +01:00
Javi Martín
2d85bd5351 Remove duplication rendering map location fields
We're going to move the partial to a component, and this makes it
easier.
2025-11-17 02:04:11 +01:00
Javi Martín
0ec7c65b9b Don't pass unused parameter to map location fields partial
We don't use this parameter since commit c34aa5412.
2025-11-17 02:04:11 +01:00
Javi Martín
d0b57868af Move settings map inside the form
That's what we usually do, and it makes sense since clicking on the map
changes the content of hidden fields in the form.
2025-11-17 02:04:11 +01:00
Javi Martín
dd2fb6469f Merge pull request #6144 from consuldemocracy/serious_accessibility_issues
Fix most Axe serious accessibility issues
2025-11-14 15:49:51 +01:00
Sebastia
ebac669fd0 Merge pull request #6125 from consuldemocracy/remove-obsolete-scopes
Add missing investments filter on admin activity page
2025-11-14 15:38:25 +01:00
taitus
4e455578d1 Rename User.by_authors to with_ids
The "by_authors" scope was the last remaining name from the removed
family of `by_author` scopes. It no longer reflects its purpose: it
simply loads users by IDs.
2025-11-14 14:52:52 +01:00
taitus
a3a44f527b Give purpose to previously unused on_budget_investments scope
The "on_budget_investments" scope in Activity has never been used
anywhere in the codebase. It was introduced in commit d9d38482b3
("extends Activity to include Investment valuations") but no references
were ever added.

Instead of removing it, we make use of the scope by adding the missing
"Budget investments" filter to the admin Activity section. This aligns
it with the rest of the activity filters and gives the scope the purpose
it was originally intended for.
2025-11-14 14:31:01 +01:00
taitus
0332160627 Remove unused by_official_level scope from Proposal
The "by_official_level" scope in Proposal is no longer used anywhere in
the code. Its last use was removed in commit 9f1f912d84 ("Remove
official level filter from advanced search").
2025-11-14 13:56:11 +01:00
taitus
4183734468 Remove unused sort_by_most_commented scope from Debate
The "sort_by_most_commented" scope in Debate is no longer used anywhere in
the code. Its last use was removed in commit b89f39bfef ("Removes
unused orders from debates controller")
2025-11-14 13:56:11 +01:00
taitus
8938b781c3 Remove unused created_by scope from Proposal
The "created_by" scope in Proposal is no longer used anywhere in the code.
It was introduced in 77dd604 and its last usage was dropped in commit 64258baf97
("Refactor getting the public activity information").
2025-11-14 13:44:12 +01:00
taitus
29f4edd466 Remove unused scopes from Legislation::Proposal
The "for_render", "sort_by_hot_score" and "sort_by_most_commented"
scopes in Legislation::Proposal are no longer used
anywhere in the code. They were all introduced in commit 335399e571
("Created Legislation Proposals model") and have never been
referenced since.
2025-11-14 13:44:12 +01:00
taitus
c4368b077a Remove unused by_geozone_id scope from Poll
The "by_geozone_id" scope in Poll is no longer used anywhere in the code.
It was first introduced in commit 20cb044015 ("adds search and filter
for poll questions") and later moved to the Poll model in commit
d024505960 ("moves geozones from poll question to poll in models"),
but has never been referenced since.
2025-11-14 13:44:12 +01:00
taitus
151b12bd35 Remove unused by_email scope from VerifiedUser
The "by_email" scope in VerifiedUser is no longer used anywhere in the
code. Its last occurrence was removed in commit 76daee1fb0 ("removes
unmasked emails and phones in forms").
2025-11-14 13:44:12 +01:00
Javi Martín
9a898495ac Add menuitem role to sign out button
Back in commit c6f0a3761, we replaced the link to sign out with a
button. However, this button is a child of a data-responsive-menu
dropdown element. Since Foundation adds the `menubar` role to responsive
menus, its children are supposed to have a `menuitem` role. So we're
adding it.

Note we're adding the role with JavaScript because, when JavaScript is
disabled, Foundation won't change the `responsive-menu` role to
`menubar`. So we can't have a `menuitem` in this case.

Axe was reporting the following issue:

```
Found 1 accessibility violation:

1) aria-required-children: Certain ARIA roles must contain
   particular children (critical)
    https://dequeuniversity.com/rules/axe/4.11/aria-required-children?application=axeAPI
    The following 1 node violate this rule:

        Selector: .account-menu
        HTML: <ul class="account-menu menu dropdown"
                  data-responsive-menu="medium-dropdown" role="menubar"
                  data-dropdown-menu="cabp3q-dropdown-menu"
                  data-mutate="ph8tvp-responsive-menu">
        Fix any of the following:
        - Element has children which are not allowed: button[tabindex]
```
2025-11-14 12:53:56 +01:00
Javi Martín
b896fc4bba Add aria-label to map markers
Axe was reporting an accessibility error:

```
Found 1 accessibility violation:

1) aria-command-name: ARIA commands must have an accessible name
   (serious)
   https://dequeuniversity.com/rules/axe/4.11/aria-command-name?application=axeAPI
   The following 1 node violate this rule:

     Selector: .leaflet-marker-icon
     HTML: <div class="leaflet-marker-icon map-marker
                       leaflet-zoom-animated leaflet-interactive"
                tabindex="0" role="button">
                <div class="map-icon"></div>
           </div>
     Fix any of the following:
     - Element does not have text that is visible to screen readers
     - aria-label attribute does not exist or is empty
     - aria-labelledby attribute does not exist, references elements
       that do not exist or references elements that are empty
     - Element has no title attribute
```

Using the title of the proposal/investment as the text of the marker is
definitely a good solution when there are several markers on the map.
Not sure whether there's a better option when there's only one marker,
though.

Note that we aren't providing a proper aria-label for markers on the map
we use in the form to create a proposal or an investment. Adding one
isn't trivial given the current code, and keyboard users can't add a
marker in the first place. We'll have to revisit this issue when we add
keyboard support for this.

We're also changing a test to make sure that titles with quotes in their
names don't break the markup due to an invalid aria-label attribute.
2025-11-14 12:53:37 +01:00
Javi Martín
b5d939565b Make fullscreen editor preview focusable
This part of the page can be scrolled independently with the mouse, and
so the same should be possible with a keyboard.

Axe was reporting this error:

```
1) scrollable-region-focusable: Scrollable region must have
   keyboard access (serious)
    https://dequeuniversity.com/rules/axe/4.11/scrollable-region-focusable?application=axeAPI
    The following 1 node violate this rule:

      Selector: .fullscreen > .markdown-preview.medium-6.small-12
      HTML: <div class="small-12 medium-6 column markdown-preview">
      Fix any of the following:
      - Element should have focusable content
      - Element should be focusable
```
2025-11-07 16:25:37 +01:00
Javi Martín
2c74f9f35b Merge pull request #6123 from consuldemocracy/max_empty_lines
Add and apply stylistic/max-empty-lines rule
2025-11-06 13:25:39 +01:00
Javi Martín
a563108a03 Merge pull request #6124 from consuldemocracy/menu_button_flashing
Don't flash the menu button on desktop screens
2025-11-06 13:25:00 +01:00
Javi Martín
3584ab048c Replace word-break: break-word with overflow-wrap
According to W3C documentation [1]:

> For compatibility with legacy content, the word-break property also
> supports a deprecated break-word keyword. When specified, this has the
> same effect as word-break: normal and overflow-wrap: anywhere,
> regardless of the actual value of the overflow-wrap property.

This is currently *not* detected by the `property-no-deprecated`
stylelint rule. However, since this rule detects other places where we
should use `overflow-wrap`, we're changing it as part of the same pull
request.

Note that, as of November 2025, 98.22% of the browsers support
`overflow-wrap: anywhere`. We're still making this change because we
only use this property in two specific places and it isn't very likely
that long words will really be a problem with the remaining 1.78%.

By the way, I'm not sure why we use this property in the budget
invesment show paragraphs and not in other similar places. It was
introduced in commit e3878ff43, alongside other changes which don't seem
to be related. When in doubt, we leave things as they were, so we're
doing the same thing here.

[1] https://www.w3.org/TR/css-text-3/#word-break-property
[2] https://caniuse.com/mdn-css_properties_overflow-wrap_anywhere
2025-11-05 20:16:19 +01:00
Javi Martín
d063475769 Use CSS instead of utility classes in options table
This way we make it easier to customize this component. In this specific
case, ideally we'd remove some of the CSS as well. For now we're leaving
it as it was for compatibility reasons.
2025-11-05 19:57:33 +01:00
Javi Martín
2d72144048 Extract component to render question options table
This way it's easier to know that the styles for the `break` HTML class
and the JavaScript for sortable elements (which we shouldn't use, by the
way, because of its accessibility issues) are only used here.
2025-11-05 19:57:33 +01:00
Javi Martín
d6f6b94ae4 Fix wrong selector for sortable tables
We renamed the HTML class to `table-sortable` in commit 99f8bb449. It
was incorrectly being applied to the question options table.
2025-11-05 19:57:27 +01:00
Javi Martín
a5e788dde4 Add and apply property-no-deprecated stylelint rule
This rule was introduced in stylelint 16.23. Out of the deprecated
properties it detects, we were only using `word-wrap`.

According to the CSS Working Group [1]:

> For legacy reasons, UAs must treat word-wrap as a legacy name alias of
> the overflow-wrap property.

Since there's universal browser support for `overflow-wrap: break-word`
[2], we can safely replace `word-wrap` with `overflow-wrap`.

[1] https://drafts.csswg.org/css-text/#overflow-wrap-property
[2] https://caniuse.com/mdn-css_properties_overflow-wrap_break-word
2025-11-05 19:56:00 +01:00
Javi Martín
ad654949ab Add and apply stylistic/max-empty-lines rule
We were already using a similar rule in Ruby files.
2025-11-05 14:34:00 +01:00
Javi Martín
8d7deef413 Don't flash the menu button on desktop screens
The button flashed briefly when loading the page. This was even more
obvious when using devices with slow internet connections.

Using CSS instead of JavaScript to hide the menu solves the issue, since
styles are loaded before scripts.
2025-11-05 14:33:09 +01:00
Javi Martín
618fc4b2c0 Move responsive menu styles to its proper file
We forgot to do so in commit 49cb6e010.
2025-11-05 14:33:09 +01:00
Javi Martín
d18c627392 Add and apply Layout/EmptyLinesAfterModuleInclusion rule
This rule was added in rubocop 1.79. We were inconsistent about it, so
we're adding it to get more consistency.
2025-11-05 14:27:12 +01:00
Javi Martín
7f749bb9bb Add and apply Style/CollectionQuerying rubocop rule
This rule was added in rubocop 1.77. We were following it most of the
time. It makes the code more readable in my humble opinion.
2025-11-05 14:27:12 +01:00
dependabot[bot]
1fa3cf8ce7 Bump rubocop from 1.76.1 to 1.81.1
This release includes some updates in the Style/RedundantParentheses and
Naming/PredicateMethod rules. We're changing the code accordingly.

Bumps [rubocop](https://github.com/rubocop/rubocop) from 1.76.1 to 1.81.1.
- [Release notes](https://github.com/rubocop/rubocop/releases)
- [Changelog](https://github.com/rubocop/rubocop/blob/master/CHANGELOG.md)
- [Commits](https://github.com/rubocop/rubocop/compare/v1.76.1...v1.81.1)

---
updated-dependencies:
- dependency-name: rubocop
  dependency-version: 1.81.1
  dependency-type: direct:development
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <support@github.com>
2025-11-05 14:27:11 +01:00
Javi Martín
413d0ed9be Return the persisted line in add_investment
This method was returning a boolean value and caused a
`Naming/PredicateMethod` when upgrading rubocop.

So, instead, we're returning the created line when it was successfully
created, and `nil` when it wasn't.

Having said that, I'm not sure why we added the `.persisted?` back in
commit 3eb22ab7b since as far as I can tell we don't use the return
value for anything. The test added in commit da43e9e2e for this change
passes if we simply return `lines.create(investment: investment)`.

For now I'm leaving the `persisted?` check just in case, but removing it
might be fine.
2025-11-05 14:27:11 +01:00
Javi Martín
15f7632f3d Refactor notifiable_available? method
This method was calling `check_availability`, which returned a boolean
value and caused a `Naming/PredicateMethod` when upgrading rubocop.

So we're changing the logic a little bit to remove the
`check_availability` method and merge the tests of `check_availability`
and `notifiable_available?` (which were almost identical) together.
2025-11-05 14:27:11 +01:00
Javi Martín
2fdfefe55d Use Verification::Email.valid_token? instead of .find
This way it's more obvious that the method is supposed to return a
boolean. When upgrading rubocop, we get a `Naming/PredicateMethod` error
due to `.find` returning a boolean.
2025-11-05 14:27:11 +01:00
Javi Martín
0ca94e5443 Add and apply Rails/FindByOrAssignmentMemoization rule
This rule was added in rubocop-rails 2.33.

At first, I wasn't very fond of this rule. It made the code less
readable even if it improved performace in some cases.

Then I realized that in the `Admin::MachineLearning::SettingComponent`
we were using `find_by` when we should be using `find_by!` instead, and
we detected that thanks to this rule.

So, only for that reason, I'm adding this rule, but I'm fine if we
remove it.
2025-11-05 11:51:23 +01:00
Javi Martín
048bdb2e9e Add and apply Rails/OrderArguments rubocop rule
This rule was introduced in rubocop-rails 2.33. We were following it
most of the time.
2025-11-05 11:51:23 +01:00
Javi Martín
1404197014 Merge pull request #6129 from consuldemocracy/fix_mark_featured_debate
Fix mark as featured button being rendered to everyone
2025-11-03 15:55:32 +01:00
Sebastia
7cf5e7fdae Merge pull request #6122 from consuldemocracy/obsolete-meta
Remove obsolete Foundation meta generator tag from layout
2025-11-03 15:21:17 +01:00
Javi Martín
251968ae72 Fix mark as featured button being rendered to everyone
We introduced this issue in commit f8faabf7d.

Since this component didn't have any tests (there are system tests for
it, though), we're also adding tests that check that only the right
buttons are rendered when accessing as administrator.
2025-10-31 16:01:33 +01:00