Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Web of Trust Setup #305

Open
wants to merge 4 commits into
base: develop
Choose a base branch
from
Open

Web of Trust Setup #305

wants to merge 4 commits into from

Conversation

iammajid
Copy link

Added a Web of Trust section in the Admin Settings to allow administrators to set values for Trust Level (wot_max_depth) and Maximum Chain Length (wot_id_verify_len). This addresses Issue #297.

Copy link

coderabbitai bot commented Jan 25, 2025

Walkthrough

The pull request introduces a new Web of Trust configuration feature for the application. The changes span multiple files in the frontend and backend, including the addition of a put method in the SettingsService for updating settings, enhancements to the AdminSettings.vue component for managing trust-related parameters, and updates to localization files for English and German.

The SettingsService class now includes a method that allows for updating settings via a PUT request to the /settings endpoint. The AdminSettings.vue component has been modified to include input fields for configuring trust level (ranging from 0 to 10) and maximum chain length, with validation logic to ensure valid inputs. Localization files have been updated to provide necessary translations for the new Web of Trust settings, including titles, descriptions, and error messages.

Possibly related PRs

  • Add create-vaults role #296: The main PR introduces a new method in the SettingsService class for updating settings, which is related to the changes in the VaultResource class that involve managing permissions for creating vaults, as both involve backend functionality for managing settings and permissions.

📜 Recent review details

Configuration used: CodeRabbit UI
Review profile: CHILL
Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 475b2e8 and cf49107.

📒 Files selected for processing (1)
  • backend/src/main/java/org/cryptomator/hub/entities/events/EventLogger.java (1 hunks)
🚧 Files skipped from review as they are similar to previous changes (1)
  • backend/src/main/java/org/cryptomator/hub/entities/events/EventLogger.java
⏰ Context from checks skipped due to timeout of 90000ms (1)
  • GitHub Check: Build and Test

Thank you for using CodeRabbit. We offer it for free to the OSS community and would appreciate your support in helping us grow. If you find it useful, would you consider giving us a shout-out on your favorite social media?

❤️ Share
🪧 Tips

Chat

There are 3 ways to chat with CodeRabbit:

  • Review comments: Directly reply to a review comment made by CodeRabbit. Example:
    • I pushed a fix in commit <commit_id>, please review it.
    • Generate unit testing code for this file.
    • Open a follow-up GitHub issue for this discussion.
  • Files and specific lines of code (under the "Files changed" tab): Tag @coderabbitai in a new review comment at the desired location with your query. Examples:
    • @coderabbitai generate unit testing code for this file.
    • @coderabbitai modularize this function.
  • PR comments: Tag @coderabbitai in a new PR comment to ask questions about the PR branch. For the best results, please provide a very specific query, as very limited context is provided in this mode. Examples:
    • @coderabbitai gather interesting stats about this repository and render them as a table. Additionally, render a pie chart showing the language distribution in the codebase.
    • @coderabbitai read src/utils.ts and generate unit testing code.
    • @coderabbitai read the files in the src/scheduler package and generate a class diagram using mermaid and a README in the markdown format.
    • @coderabbitai help me debug CodeRabbit configuration file.

Note: Be mindful of the bot's finite context window. It's strongly recommended to break down tasks such as reading entire modules into smaller chunks. For a focused discussion, use review comments to chat about specific files and their changes, instead of using the PR comments.

CodeRabbit Commands (Invoked using PR comments)

  • @coderabbitai pause to pause the reviews on a PR.
  • @coderabbitai resume to resume the paused reviews.
  • @coderabbitai review to trigger an incremental review. This is useful when automatic reviews are disabled for the repository.
  • @coderabbitai full review to do a full review from scratch and review all the files again.
  • @coderabbitai summary to regenerate the summary of the PR.
  • @coderabbitai generate docstrings to generate docstrings for this PR. (Beta)
  • @coderabbitai resolve resolve all the CodeRabbit review comments.
  • @coderabbitai configuration to show the current CodeRabbit configuration for the repository.
  • @coderabbitai help to get help.

Other keywords and placeholders

  • Add @coderabbitai ignore anywhere in the PR description to prevent this PR from being reviewed.
  • Add @coderabbitai summary to generate the high-level summary at a specific location in the PR description.
  • Add @coderabbitai anywhere in the PR title to generate the title automatically.

CodeRabbit Configuration File (.coderabbit.yaml)

  • You can programmatically configure CodeRabbit by adding a .coderabbit.yaml file to the root of your repository.
  • Please see the configuration documentation for more information.
  • If your editor has YAML language server enabled, you can add the path at the top of this file to enable auto-completion and validation: # yaml-language-server: $schema=https://coderabbit.ai/integrations/schema.v2.json

Documentation and Community

  • Visit our Documentation for detailed information on how to use CodeRabbit.
  • Join our Discord Community to get help, request features, and share feedback.
  • Follow us on X/Twitter for updates and announcements.

Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

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

Actionable comments posted: 3

🧹 Nitpick comments (2)
frontend/src/common/backend.ts (1)

370-372: Consider adding specific error handling for settings updates.

The put method could benefit from explicit error handling to catch and convert specific HTTP status codes, similar to other methods in the codebase that use rethrowAndConvertIfExpected.

  public async put(settings: SettingsDto): Promise<void> {
-   return axiosAuth.put('/settings', settings);
+   return axiosAuth.put('/settings', settings)
+     .catch((error) => rethrowAndConvertIfExpected(error, 400, 403));
  }
frontend/src/components/AdminSettings.vue (1)

373-396: Improve the save operation implementation.

Several improvements can be made to the save operation:

  1. Remove the artificial delay (setTimeout)
  2. Add success feedback
  3. Consider disabling inputs during processing
 async function saveWebOfTrust() {
   onSaveError.value = null;
   trustLevelError.value = trustLevel.value < 0 || trustLevel.value > 10;
   maxChainLengthError.value = maxChainLength.value < 0;

   if (trustLevelError.value || maxChainLengthError.value) {
     return;
   }
   try {
     processing.value = true;
     const settings = {
       wotMaxDepth: trustLevel.value,
       wotIdVerifyLen: maxChainLength.value,
       hubId: admin.value?.hubId ?? ''
     };
     await backend.settings.put(settings);
-    await new Promise(resolve => setTimeout(resolve, 500));
+    // Show success message
+    const toast = useToast();
+    toast.success(t('admin.webOfTrust.saveSuccess'));
   } catch (error) {
     console.error('Failed to save settings:', error);
     onSaveError.value = error instanceof Error ? error : new Error('Unknown reason');
   } finally {
     processing.value = false;
   }
 }
📜 Review details

Configuration used: CodeRabbit UI
Review profile: CHILL
Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 3ef58ed and 209eeb2.

📒 Files selected for processing (4)
  • frontend/src/common/backend.ts (1 hunks)
  • frontend/src/components/AdminSettings.vue (5 hunks)
  • frontend/src/i18n/de-DE.json (1 hunks)
  • frontend/src/i18n/en-US.json (1 hunks)

Comment on lines +124 to +145

<div class="col-span-6 sm:col-span-3">
<label for="trustLevel" class="block text-sm font-medium text-gray-700">{{ t('admin.webOfTrust.trustLevel.title') }}</label>
<input id="trustLevel" v-model="trustLevel" type="number" min="0" max="10" step="1" class="mt-1 block w-full shadow-sm sm:text-sm rounded-md border-gray-300 focus:ring-primary focus:border-primary [appearance:textfield] [&::-webkit-outer-spin-button]:appearance-none [&::-webkit-inner-spin-button]:appearance-none" :class="{ 'invalid:border-red-300 invalid:text-red-900 focus:invalid:ring-red-500 focus:invalid:border-red-500': trustLevelError }" />
<p v-if="trustLevelError" class="mt-1 text-sm text-red-900">
{{ t('admin.webOfTrust.trustLevel.error') }}
</p>
</div>

<div class="col-span-6 sm:col-span-3">
<label for="maxChainLength" class="block text-sm font-medium text-gray-700">{{ t('admin.webOfTrust.maxChainLength.title') }}</label>
<input id="maxChainLength" v-model="maxChainLength" type="number" min="0" step="1" class="mt-1 block w-full shadow-sm sm:text-sm rounded-md border-gray-300 focus:ring-primary focus:border-primary [appearance:textfield] [&::-webkit-outer-spin-button]:appearance-none [&::-webkit-inner-spin-button]:appearance-none" :class="{ 'invalid:border-red-300 invalid:text-red-900 focus:invalid:ring-red-500 focus:invalid:border-red-500': maxChainLengthError }" />
<p v-if="maxChainLengthError" class="mt-1 text-sm text-red-900">
{{ t('admin.webOfTrust.maxChainLength.error') }}
</p>
</div>

<div class="col-span-6 flex justify-end space-x-3">
<button type="button" class="inline-flex justify-center py-2 px-4 border border-transparent shadow-sm text-sm font-medium rounded-md text-white bg-primary hover:bg-primary-d1 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-primary" @click="saveWebOfTrust">
{{ t('admin.webOfTrust.save') }}
</button>
</div>
Copy link

Choose a reason for hiding this comment

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

⚠️ Potential issue

Remove duplicate Web of Trust section.

This section is duplicated. The same content appears again at lines 200-242. Remove this instance and keep the one with better error handling and processing state management.

"admin.webOfTrust.description": "Configure the Web of Trust settings to manage how trust is established between users in the system. These settings affect the verification of user identities and key signatures.",
"admin.webOfTrust.trustLevel.error": "Trust level must be between 0 and 10.",
"admin.webOfTrust.trustLevel.title": "Trust Level",
"admin.webOfTrust.maxChainLength.error": "Maximum chain length must be greater than 0.",
Copy link

Choose a reason for hiding this comment

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

⚠️ Potential issue

Fix inconsistency in error message.

The error message states "must be greater than 0" but the validation in AdminSettings.vue checks for "greater than or equal to 0" (value < 0). Either update the message or the validation to match.

Choose one of these approaches:

  1. If zero is allowed:
-  "admin.webOfTrust.maxChainLength.error": "Maximum chain length must be greater than 0.",
+  "admin.webOfTrust.maxChainLength.error": "Maximum chain length must not be negative.",
  1. If zero is not allowed (recommended for chain length):
// In AdminSettings.vue
-maxChainLengthError.value = maxChainLength.value < 0;
+maxChainLengthError.value = maxChainLength.value <= 0;
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
"admin.webOfTrust.maxChainLength.error": "Maximum chain length must be greater than 0.",
"admin.webOfTrust.maxChainLength.error": "Maximum chain length must not be negative.",

"admin.webOfTrust.description": "Konfigurieren Sie die Web of Trust-Einstellungen, um zu verwalten, wie Vertrauen zwischen Benutzern im System aufgebaut wird. Diese Einstellungen beeinflussen die Überprüfung von Benutzeridentitäten und Schlüssel-Signaturen.",
"admin.webOfTrust.trustLevel.error": "Das Vertrauensniveau muss zwischen 0 und 10 liegen.",
"admin.webOfTrust.trustLevel.title": "Vertrauensniveau",
"admin.webOfTrust.maxChainLength.error": "Die maximale Kettenlänge muss größer als 0 sein.",
Copy link

Choose a reason for hiding this comment

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

⚠️ Potential issue

Fix inconsistency in German error message.

The same inconsistency exists in the German translation. Update it to match the English version once the validation logic is decided.

Choose one of these approaches based on the decision made for the English translation:

  1. If zero is allowed:
-  "admin.webOfTrust.maxChainLength.error": "Die maximale Kettenlänge muss größer als 0 sein.",
+  "admin.webOfTrust.maxChainLength.error": "Die maximale Kettenlänge darf nicht negativ sein.",
  1. If zero is not allowed (recommended for chain length):
// Keep the current message as it's already correct for this case

Committable suggestion skipped: line range outside the PR's diff.

Copy link
Member

@overheadhunter overheadhunter left a comment

Choose a reason for hiding this comment

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

Thanks, this is a good start!

Comment on lines +354 to +367
// Add validation functions
function validateTrustLevel(value: number) {
return value < 0 || value > 10;
}

function validateMaxChainLength(value: number) {
return value < 0;
}

class FormValidationFailedError extends Error {
constructor() {
super('The form is invalid.');
}
}
Copy link
Member

Choose a reason for hiding this comment

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

form validation isn't yet hooked up to the HTML, is it?

Comment on lines -128 to -134

<div v-if="admin.hasLicense" class="flex justify-end items-center">
<button type="button" class="flex-none inline-flex justify-center py-2 px-4 border border-transparent shadow-sm text-sm font-medium rounded-md text-white bg-primary hover:bg-primary-d1 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-primary disabled:opacity-50 disabled:hover:bg-primary disabled:cursor-not-allowed" @click="manageSubscription()">
<ArrowTopRightOnSquareIcon class="-ml-1 mr-2 h-5 w-5" aria-hidden="true" />
{{ t('admin.licenseInfo.manageSubscription') }}
</button>
</div>
Copy link
Member

Choose a reason for hiding this comment

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

probably deleted accidentally?

{{ t('admin.webOfTrust.description') }}
</p>
</div>
<div class="mt-5 md:mt-0 md:col-span-2">
Copy link
Member

Choose a reason for hiding this comment

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

div can be a form, so the contained input fields and buttons are semantically grouped. Furthermore form validation might be easier this way (triggered by submit event instead of click event - so pressing enter works as well)

Comment on lines +272 to +273
const trustLevel = ref<number>(0);
const maxChainLength = ref<number>(0);
Copy link
Member

Choose a reason for hiding this comment

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

use the same names as in the database and backend (i.e. wotMaxDepth and wotIdVerifyLen) to avoid confusion. Especially since we have a trust level in other places, which has a completely different meaning.

Comment on lines +56 to +59
"admin.webOfTrust.trustLevel.error": "Trust level must be between 0 and 10.",
"admin.webOfTrust.trustLevel.title": "Trust Level",
"admin.webOfTrust.maxChainLength.error": "Maximum chain length must be greater than 0.",
"admin.webOfTrust.maxChainLength.title": "Maximum Chain Length",
Copy link
Member

Choose a reason for hiding this comment

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

Please adjust the names. Furthermore, we probably need to explain the meaning of both values, so you should add some description field.

Suggested change
"admin.webOfTrust.trustLevel.error": "Trust level must be between 0 and 10.",
"admin.webOfTrust.trustLevel.title": "Trust Level",
"admin.webOfTrust.maxChainLength.error": "Maximum chain length must be greater than 0.",
"admin.webOfTrust.maxChainLength.title": "Maximum Chain Length",
"admin.webOfTrust.wotMaxDepth.error": "Maximum WoT Depth must be between 0 and 10.",
"admin.webOfTrust.wotMaxDepth.title": "Maximum WoT Depth",
"admin.webOfTrust.wotMaxDepth.description": "Maximum distance between two users, so an indirect acquaintanceship is still considered trustworthy (assuming intermediate identities have been verified).",
"admin.webOfTrust.wotIdVerifyLen.error": "Fingerprint Verification Preciseness must be positive.",
"admin.webOfTrust.wotIdVerifyLen.title": "Fingerprint Verification Preciseness",
"admin.webOfTrust.wotIdVerifyLen.description": "How many digits of another users fingerprint one needs to enter to verify their identity.",

Copy link
Member

@SailReal SailReal left a comment

Choose a reason for hiding this comment

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

Since any user with the admin role can change the WoT setting at runtime, we should add an audit log event when the setting is changed so that the change does not go unnoticed.

Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

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

Actionable comments posted: 1

🧹 Nitpick comments (2)
backend/src/main/java/org/cryptomator/hub/entities/events/SettingWotUpdateEvent.java (1)

21-25: Add validation constraints for numeric fields.

Consider adding validation annotations to ensure the numeric fields have appropriate bounds:

 @Column(name = "wot_max_depth")
+@Min(0) @Max(9)
 private int wotMaxDepth;

 @Column(name = "wot_id_verify_len")
+@Min(0)
 private int wotIdVerifyLen;
backend/src/main/resources/org/cryptomator/hub/flyway/V17__Create_Audit_Event_Setting_WoT.sql (1)

1-6: Consider adding CHECK constraints for the numeric columns.

The table structure looks good with appropriate column types and NOT NULL constraints. However, consider adding CHECK constraints to ensure wot_max_depth and wot_id_verify_len are positive integers, as negative values wouldn't make sense for these settings.

 CREATE TABLE "audit_event_setting_wot_update"
 (
 	"id"                BIGINT NOT NULL,
 	"updated_by"        VARCHAR(255) COLLATE "C" NOT NULL,
-	"wot_max_depth"     INTEGER NOT NULL,
-	"wot_id_verify_len" INTEGER NOT NULL,
+	"wot_max_depth"     INTEGER NOT NULL CHECK ("wot_max_depth" > 0),
+	"wot_id_verify_len" INTEGER NOT NULL CHECK ("wot_id_verify_len" > 0),
📜 Review details

Configuration used: CodeRabbit UI
Review profile: CHILL
Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 209eeb2 and 475b2e8.

📒 Files selected for processing (5)
  • backend/src/main/java/org/cryptomator/hub/api/AuditLogResource.java (4 hunks)
  • backend/src/main/java/org/cryptomator/hub/api/SettingsResource.java (2 hunks)
  • backend/src/main/java/org/cryptomator/hub/entities/events/EventLogger.java (1 hunks)
  • backend/src/main/java/org/cryptomator/hub/entities/events/SettingWotUpdateEvent.java (1 hunks)
  • backend/src/main/resources/org/cryptomator/hub/flyway/V17__Create_Audit_Event_Setting_WoT.sql (1 hunks)
⏰ Context from checks skipped due to timeout of 90000ms (1)
  • GitHub Check: Build and Test
🔇 Additional comments (5)
backend/src/main/java/org/cryptomator/hub/entities/events/SettingWotUpdateEvent.java (1)

1-63: LGTM! Well-structured event entity.

The implementation follows JPA entity best practices with proper inheritance, field mapping, and equals/hashCode implementation.

backend/src/main/java/org/cryptomator/hub/api/SettingsResource.java (1)

56-63: LGTM! Proper change detection and event logging.

The implementation correctly tracks and logs WoT setting changes only when values actually change.

backend/src/main/java/org/cryptomator/hub/entities/events/EventLogger.java (1)

103-110: LGTM! Consistent logging implementation.

The new logging method follows the established pattern and properly sets all required fields.

backend/src/main/java/org/cryptomator/hub/api/AuditLogResource.java (1)

85-85: LGTM! Proper audit event integration.

The implementation correctly integrates the new WoT settings update event into the audit system:

  • Proper JsonSubTypes registration
  • Well-structured DTO record
  • Correct conversion logic in fromEntity

Also applies to: 109-109, 133-134

backend/src/main/resources/org/cryptomator/hub/flyway/V17__Create_Audit_Event_Setting_WoT.sql (1)

7-9: LGTM! Well-structured constraints.

The constraints are properly defined:

  • Primary key ensures unique audit events
  • Foreign key with CASCADE delete ensures referential integrity and automatic cleanup of audit records when the parent event is deleted

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants