Skip to content

luci-app-nordvpnlite: update to meet all feature. - #1801

Merged
3 commits merged into
NordSecurity:mainfrom
pesa1234:luci-fix-nordvpnlit
Sep 11, 2026
Merged

3 commits merged into
NordSecurity:mainfrom
pesa1234:luci-fix-nordvpnlit

Conversation

@pesa1234

@pesa1234 pesa1234 commented Jun 3, 2026

Copy link
Copy Markdown
Contributor

Dear NordVPN team, as suggest I reopen it and I hope now it will be reviewed by the team.

Extend the NordVPN Lite LuCI backend ACLs and RPC handlers so the settings page can query service state, runtime status, country lists and per-server WireGuard metadata.

Rework the settings view to support recommended, country and specific server selection, fetch country and server data on demand, expose service start/restart/stop/enable/disable controls, and restart the service after Save & Apply while polling for the updated runtime state.

Example:
immagine
immagine
immagine

Changes:

  • Port the expanded LuCI settings view from the standalone luci-app-nordvpnlite app.

  • Add service enabled flag handling through UCI.

  • Add service status and control actions for start, restart, stop, enable and disable.

  • Add runtime status lookup and display for Telio state, tunnel IP and exit node details.

  • Add VPN selection modes for recommended server, country code and specific server.

  • Add country list lookup from the nordvpnlite command.

  • Add NordVPN server lookup using the public API, hostname normalization and automatic IP/public key fill.

  • Expand the rpcd ucode backend with the new config, service, lookup and runtime status methods.

  • Expand the LuCI ACL grants and update the menu ACL dependency for the app.

  • Add runtime dependencies required by the new LuCI backend: curl, jq and ca-bundle.

Problem

Not so useful Luci app

Solution

After merged is more complete

Run tested on openwrt snapshot

@jjanowsk

jjanowsk commented Jun 9, 2026

Copy link
Copy Markdown
Collaborator

Hi! Just to let you know, I've just started looking at it. Most likely I'll send you my feedback tomorrow. I've also send the ipk to our QA engineer so he can give his opinion on the UI/UX. Thanks again for the contribution and for your patience

@olekoliinyk olekoliinyk added the run tests PR is ready for CI label Jun 10, 2026

@jjanowsk jjanowsk left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Hi! I'll leave my comments free standing because they are mostly UI/UX related. Once we polish that I'll review the code itself.

Major:

  1. I'm having trouble understanding what is the point of "Enabled" button. Can you please explain that?
  2. It's a little counter intuitive when you install the app, paste the "Authentication token" and try to start the service for the first time. It will fail, because the token is not yet saved in the config file. It's obvious to us what's happening, but not very clear to the user. It might be hard to figure out that he needs to first click the "Save & Apply" button, and only then he should click the "Start" button. Moreover the app just hangs in that situation.
  3. Similar situation happens when the user changes configuration e.g. from recommended server to the server from the country list. Changing those settings and clicking restart does not apply the new configuration. That's again counter-intuitive.
  4. Touching on the server configuration. I'm not sure I'm sold on the idea of selecting "Specific server" via hostname. Right now the nordvpnlite config allows only configuration via pub key and IP address and we could leave it this way in the OpenWRT UI. The problem I see with the current solution is that you need to query ~30MB server list and filter it in memory on the device. It can be slow. Also, by dropping this feature we can get rid of extra dependencies for our app.
  5. Why is clicking "Disable autostart", blocking "Start", "Restart", "Stop" buttons? It seems to be a bug.

Minor:

  1. Status texts should not end with ".". E.g. "Stopped" not "Stopped."
  2. Field names and field values are unaligned, at least in chrome:
image

@pesa1234

Copy link
Copy Markdown
Contributor Author

Hi @jjanowsk,
thank you for the detailed feedback. I’ve addressed all the points.

The service switch is a runtime master switch stored in /etc/config/nordvpnlite. Unlike autostart, it determines whether the init script is allowed to start the daemon.
I renamed it to “Enable service”, clarified its description and aligned the embedded init script with the OpenWrt package implementation.
Start and Restart now validate and save the current form configuration before controlling the service. A startup failure also produces a notification instead of leaving the UI apparently hanging.

Consequently, changing the selected country or other settings and clicking Restart now applies the new configuration.

I removed hostname-based server lookup. Specific server configuration now accepts the IP address and WireGuard public key directly, matching the native nordvpnlite configuration. The full server-list download and the curl, jq and ca-bundle dependencies were removed.

Autostart is now independent from runtime service controls. Disabling autostart no longer blocks Start, Restart or Stop.

I also removed trailing periods from status texts and adjusted the status field alignment.

Thanks again for the review!

@olekoliinyk olekoliinyk added run tests PR is ready for CI and removed run tests PR is ready for CI labels Jul 2, 2026
@jjanowsk

jjanowsk commented Jul 7, 2026

Copy link
Copy Markdown
Collaborator

Hi @pesa1234! Thanks for the updates. I was on vacation, but I'm back now and I'll review it this week

@jjanowsk jjanowsk left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Hi! Found a few technical issues. The main issue for me though is this enable button. I still don't understand why we would need that tbh. You can try to convince me, because maybe I'm missing someting, but in my opinion it is just adding unnecessary complications without any benefit.

if (view.vpn_mode_option.formvalue('config') !== 'server')
return true;

return String(value || '').trim() !== '' ? true : _('Please provide the server public key.');

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Similar problem with _ shadowing here.


function has_service() {
let st = fs.stat(INIT_SCRIPT);
return st && st.type == 'file' && st.user_exec != false;

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

st.perm.user_exec

return trim(output);
}

function config_enabled() {

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I still don't know what we are gaining by adding this enabled flag to be honest. I would gladly get rid of it unless you have some valid reason for keeping it. It would clean up the logic in this PR by not having to deal with weird states like: Running (service disabled).

handleSaveApply: null,
handleSave: null,

handleSaveApply: function () {

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Save and apply previously was only saving the configuration and I think it was a correct decision. I've asked you to also save the configuration when you click start, so the configuration visible in the UI is applied to the start. But now you've also added restarting to the save button, even when the service is not running. This I think is incorrect. (Maybe you have not added it now, maybe I've missed that during the first review.)

if (typeof widget.addChoices === 'function')
widget.addChoices(keys, choices);

widget.setValue(code !== '' ? code : '');

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

it's just equivalent to: widget.setValue(code);

};
}

let output = read_command_output(sprintf('%s countries 2>/dev/null', SERVICE_NAME));

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

In case of lack of internet this can hang for a long time. I think we should add some kind of timeout mechanism here.

@asledzinskiy

Copy link
Copy Markdown
Contributor

One minor scenario that is not working for me:

  • Pre-condition - nordvpnlite is not running
  • Go to UI and click Get status button

Actual result - banner with message 'Failed to get status'
Expected - Service Status is displaying Not Running

@asledzinskiy

asledzinskiy commented Jul 29, 2026

Copy link
Copy Markdown
Contributor

And also another failed test case:

  1. Open Services → NordVPN Lite.
  2. Set VPN Selection = Specific server.
  3. Leave Server Public Key empty
  4. Click Save & Apply.
  5. Expected: validation error. Actual: red TypeError: _ is not a function banner

Was able to fix it with:

sed -i 's/function (_, value)/function (section_id, value)/g' \
  /www/luci-static/resources/view/nordvpnlite/settings.js

@pesa1234
pesa1234 force-pushed the luci-fix-nordvpnlit branch from 4fbbd2c to 52b055a Compare August 9, 2026 09:37
@pesa1234

pesa1234 commented Aug 9, 2026

Copy link
Copy Markdown
Contributor Author

Hi! Found a few technical issues. The main issue for me though is this enable button. I still don't understand why we would need that tbh. You can try to convince me, because maybe I'm missing someting, but in my opinion it is just adding unnecessary complications without any benefit.

All the request should be addressed, thanks for point it... please check

@pesa1234
pesa1234 requested a review from jjanowsk August 10, 2026 15:23

@jjanowsk jjanowsk left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Hi @pesa1234! Thanks again for your contribution. I've checked the code and it's +1 from me. There are now few minor things left, and I can handle them for you if you agree. Of course your commits will be left marked as authored by you, but I can just move them to my branch and do those administrative things. If you prefer to do it then I need you to:

  1. Rebase to fix deny and black lints
  2. Create .unreleased/luci_improvements file, and add short description there e.g.: nordvpnlite: OpenWRT UI improvements: Added service control
  3. Take content of dod.yml file from the root of libtelio's repo and put it in the top of your PR description. Mark all three points as done. (This part TBH I'm not sure will work for external contribution, so that's why I would prefer to just do it for you to avoid any hustle. We don't have many external contributors;))

Few small issues left which I can also fix:

  1. You've changed the behaviour of Save&Apply as I've asked you, but I think now the name does not match. We should use Save handler for that.
  2. timeout is not default on all openwrt images. Please add +coreutils-timeout to the dependency list.
  3. logout ucode method is unreachable. Let's get rid of it.

Let me know if you want me to handle that. If so I'll prepare new PR and link this one there.

@pesa1234

pesa1234 commented Sep 1, 2026

Copy link
Copy Markdown
Contributor Author

Hi @jjanowsk, thanks a lot for the review and for the +1!

I can take care of the remaining technical fixes on my side if you want — just let me know:

  • use the correct Save handler;
  • add coreutils-timeout;
  • remove the logout call.

If you’re happy with that, I’ll update this PR accordingly.

For the repository-specific/admin parts, especially the DoD workflow and anything that is easier to handle internally, I’d really appreciate your help.

I can also test the updated package on a real OpenWrt device afterwards, including the LuCI UI, service controls, Save/Start/Restart behaviour, and runtime status.

Thanks again for helping me get this into shape for merging!

One more thing: as long as there is no free plan, even with limited bandwidth or a restricted server selection, I won’t be able to prepare a PR for the official OpenWrt packages repository.

It might be worth considering a small free tier, as that could make it easier for more OpenWrt users and contributors to test the package and potentially increase adoption.

Andrea

@jjanowsk

jjanowsk commented Sep 1, 2026

Copy link
Copy Markdown
Collaborator

Ok, so please do those 3 + rebase, and I'll take if from there. Thanks again! Regarding your suggestion, it's outside of my scope, but I'll pass the information to the relevant people.

Just one note about the rebase: Please do it first, and force push here, and only then do your fixes. This way I'll have nice "compare" button here on github to just see your latest changes. Thanks!

Changes:

- Port the expanded LuCI settings view from the standalone luci-app-nordvpnlite app.

- Add service enabled flag handling through UCI.

- Add service status and control actions for start, restart, stop, enable and disable.

- Add runtime status lookup and display for Telio state, tunnel IP and exit node details.

- Add VPN selection modes for recommended server, country code and specific server.

- Add country list lookup from the nordvpnlite command.

- Add NordVPN server lookup using the public API, hostname normalization and automatic IP/public key fill.

- Expand the rpcd ucode backend with the new config, service, lookup and runtime status methods.

- Expand the LuCI ACL grants and update the menu ACL dependency for the app.

- Add runtime dependencies required by the new LuCI backend: curl, jq and ca-bundle.
Save pending settings before starting or restarting the service while keeping normal Save & Apply side-effect free and runtime controls independent from autostart.

Align the LuCI backend with the separate auth file and login API, preserve the upstream reload flow, remove the redundant service-enabled switch, bound external lookups, handle stopped status cleanly, and update the OpenWrt UI page object.
@pesa1234
pesa1234 force-pushed the luci-fix-nordvpnlit branch from 52b055a to b9f97ce Compare September 1, 2026 09:37
@pesa1234

pesa1234 commented Sep 1, 2026

Copy link
Copy Markdown
Contributor Author

@jjanowsk can you please check now, all the things should be done

@olekoliinyk olekoliinyk added run tests PR is ready for CI and removed run tests PR is ready for CI labels Sep 7, 2026
@jjanowsk jjanowsk mentioned this pull request Sep 8, 2026
3 tasks
@github-merge-queue github-merge-queue Bot closed this pull request by merging all changes into NordSecurity:main in e1eb075 Sep 11, 2026
@jjanowsk

Copy link
Copy Markdown
Collaborator

Merged. Thanks again @pesa1234 for your contribution!

@pesa1234
pesa1234 deleted the luci-fix-nordvpnlit branch September 11, 2026 19:32
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

run tests PR is ready for CI

Projects

None yet

Development

Successfully merging this pull request may close these issues.

4 participants